Alan Neveu created CB-2084: ------------------------------ Summary: CordovaWP7 FileEntry.write Intermittent Errors Key: CB-2084 URL: https://issues.apache.org/jira/browse/CB-2084 Project: Apache Cordova Issue Type: Bug Components: WP7, WP8 Affects Versions: 2.3.0 Environment: Windows Phone 7, Windows Phone 8 Reporter: Alan Neveu Assignee: Jesse MacFadyen
I have found problems due to strange behavior with writing new files to the device. I found that the File.cs function called: public void write(string options) is intermittently losing the filePath value that comes in via options. This happens a lot when the file is being created and does not exist. It does not happen 100% of the time, however. What seems to be happening is that the call to getMetaData while getting a FileEntry object fails because the file does not exist and when the FileEntry is then used to write a new file to the device the filePath is null. My application needs to downloads maybe 30 files from a web service and write them all to disk. While I am looping through the files I downloaded and attempting to write them to disk, maybe 2 or 3 out of 30 will experience this problem. I wrote a simple function for writing files called write2, and it lives in my File.cs file. This is what it looks like: public void write2(string options) { string[] optStrings = JSON.JsonHelper.Deserialize<string[]>(options); string filename = optStrings[0]; string data = optStrings[1]; try { using (IsolatedStorageFile isoFile = IsolatedStorageFile.GetUserStoreForApplication()) { bool booExists = isoFile.FileExists(filename); if (booExists) { isoFile.DeleteFile(filename); } IsolatedStorageFileStream myNewIsoFS = isoFile.CreateFile(filename); byte[] bytData = System.Text.Encoding.UTF8.GetBytes(data); myNewIsoFS.Write(bytData, 0, bytData.Length); myNewIsoFS.Close(); } } catch (Exception ex) { string whaa = ex.Message; } } It’s really lame and limited, I know, but it works every time. I also had to modify cordova-2.3.0.js to shim my function in there. All I did was copy the FileWriter.prototype.write function and name mine write2, and I also made mine so that it accepts two parameters - the first being the filename and the second being the data. This allows me to pass these arguments to my write2 function in File.cs, and from there I definitely have the filename every time, which then allows me to simply write the file to disk. I spent many hours trying to figure out how/why the normal write call is sometimes losing the filename and filePath, but I just can’t figure it out. Here is what my FileWriter.prototype.write2 javascript function looks like: FileWriter.prototype.write2 = function (targetfilename, text) { // Throw an exception if we are already writing a file console.log("targetfilename=" + targetfilename); if (this.readyState === FileWriter.WRITING) { throw new FileError(FileError.INVALID_STATE_ERR); } // WRITING state this.readyState = FileWriter.WRITING; var me = this; // If onwritestart callback if (typeof me.onwritestart === "function") { me.onwritestart(new ProgressEvent("writestart", { "target": me })); } // Write file exec( // Success callback function (r) { // If DONE (cancelled), then don't do anything if (me.readyState === FileWriter.DONE) { return; } // position always increases by bytes written because file would be extended me.position += r; // The length of the file is now where we are done writing. me.length = me.position; // DONE state me.readyState = FileWriter.DONE; // If onwrite callback if (typeof me.onwrite === "function") { me.onwrite(new ProgressEvent("write", { "target": me })); } // If onwriteend callback if (typeof me.onwriteend === "function") { me.onwriteend(new ProgressEvent("writeend", { "target": me })); } }, // Error callback function (e) { // If DONE (cancelled), then don't do anything if (me.readyState === FileWriter.DONE) { return; } // DONE state me.readyState = FileWriter.DONE; // Save error me.error = new FileError(e); // If onerror callback if (typeof me.onerror === "function") { me.onerror(new ProgressEvent("error", { "target": me })); } // If onwriteend callback if (typeof me.onwriteend === "function") { me.onwriteend(new ProgressEvent("writeend", { "target": me })); } }, "File", "write2", [targetfilename, text]); }; -- This message is automatically generated by JIRA. If you think it was sent incorrectly, please contact your JIRA administrators For more information on JIRA, see: http://www.atlassian.com/software/jira