A few weeks back I began a list of questions to help build a PhoneGap/Cordova File System FAQ. (More on that at the very end.) As I work through the questions I'm building little samples (like this one) to help demonstrate various FileSystem features. Today's is really simple, but as always, I figure people can find this helpful even if it trivial. (And if I'm wrong, let me know in the comments below.) Today's example simply reads a text-based file from the file system and displays it in the application.
Let's take a look at the code and then I'll walk you through what it does.
document.addEventListener("deviceready", init, false);
function init() {
//This alias is a read-only pointer to the app itself
window.resolveLocalFileSystemURL(cordova.file.applicationDirectory + "www/index.html", gotFile, fail);
/* Yes, this works too for our specific example...
$.get("index.html", function(res) {
console.log("index.html", res);
});
*/
}
function fail(e) {
console.log("FileSystem Error");
console.dir(e);
}
function gotFile(fileEntry) {
fileEntry.file(function(file) {
var reader = new FileReader();
reader.onloadend = function(e) {
console.log("Text is: "+this.result);
document.querySelector("#textArea").innerHTML = this.result;
}
reader.readAsText(file);
});
}
After deviceready fires, we use resolveLocalFileSystemURL to translate a path into a FileEntry object. Once again I'm using one of the aliases that ship with the latest version of the File plugin: cordova.file.applicationDirectory. As you can probably guess, this points to the application itself and is read-only, which is fine for our purposes. To this path I add www/index.html
to refer to the index.html of the app itself.
As you can see in the commented out code, if I really did want to read something inside the www folder, I could just use Ajax. The example in the comment is jQuery-based. But since I wanted to demonstrate the FileSystem API I use it instead. For something this simple I'd probably just use Ajax typically.
Once we get the FileEntry object we can then run the file
method on it. This gives us a handler to the file itself (think of FileEntry as the agent for the movie star file that is too busy to give us the time of day). Once we have that, we then fire up a new FileReader object, run readAsText
on it, and wait for the read operation to end. Once it is done we have access to the contents of the file and can do - whatever - with it. In the sample app I simply added a text area to the DOM.
That's it. Full source may be found here: https://github.com/cfjedimaster/Cordova-Examples/tree/master/readtextfile.
As a quick FYI, I have begun work on the FAQ itself. You can view (and comment) on the Google doc here: https://docs.google.com/document/d/1qKB63z3U2BwCl7Gc-Ry7cPbNbQB-Cur2BaS1BRB1tV0/edit?usp=sharing
Archived Comments
Hi Raymond i have a question i don't know if this is the best place to do it but... wel... can you tell me why the examples of phonegap/cordova plugins at github are shorter than the examples of phonegap 3.3.0 ? An example:
The Camera Plugin at github (phonegap greater than 3.3.0 version):
https://github.com/apache/c...
The Camera Plugin Examples (phonegap 3.3.0):
http://docs.phonegap.com/en...
Just why? :/
Sorry the second link is
http://docs.phonegap.com/en...
I can't post the original link hehe:
http://docs.phonegap.com/en...
I am getting an error
uncaught TypeError :
cannot read property 'application directory' of undefined
can u please help me..
@Martin: Um, I think because PG is still using internal docs, where on Cordova they always link to the plugin docs itself, which is, imo, more "proper".
@anchal: Ensure you added the plugin as described in the readme.md.
Oh i see, thank you!
The HTML5Rocks web site that is referenced throughout the Cordova documentation now says:
“In April 2014, it was announced on public-webapps that the Filesystem API spec should be considered dead. Other browsers have showed little interest in implementing it.”
What is the Codova development team’s position on this?
Are they likely to change the API?
I'm concerned that I might put some considerable effort into this API (like I did before the file feature API was completely changed when it was made a plugin) and then find that it needs to be changed yet again.
One thing to keep in mind is that - obviously - even if Cordova 4.0 removes FS support your app will not all of a sudden stop working.
The best thing I can suggest is for you to post your concerns to the Cordova mailing list. That's a direct line to the people working on Cordova.
In my opinion, the FS stuff will never be removed, even though it may be dead as a spec on desktop. It is just too important for apps.
Thanks for that insight Raymond.
Ya I'm getting an error on your code also. Running Android. I did add the plugin to Cordova properly via
cordova plugin add org.apache.cordova.file
Did you check the code when running Android?
I believe it is this issue: https://issues.apache.org/j...
It came up from an issue on my repo: https://github.com/cfjedima...
Raymond,
This is handy, but I'm struggling to find good practical examples going the other direction and WRITING files.
Essentially, I want to be able to store a few files to the cordova.file.applicationStorageDirectory to keep them persistent in the app and I'm not seeing exactly how to implement that with all the conflicting spec information out there.
Can you point me in the right direction?
Until I get time to make a little demo like the one here, the best I can suggest is the docs.
Thanks anyway! I'm working my way through the docs, they are just not super clear on 'interaction' as it were. It's great that I know how to read a file from some where. I know how to write a file to somewhere, but gee golly if I can get them to all work together at the same time... well that'd be just dandy!
Anyway, I'm actually making progress regardless, but thanks for your response!
Hi Raymond,
thanks for the example here.
I am still facing that issue of android where im gettting "file Not found" with this example.
But what i am really interested in is for ANDROID, reading and writing files to/from the cordova.file.applicationStorageDirectory.
Did you come up with an example for the same ?
If yes, please share the same with us.
thanks,
Rajesh
Did you see my blog post on downloading assets? Not the same directory, but very similar.
http://www.raymondcamden.co...
thanks Raymond, your example gave me an idea about the path to the applicationStorageDirectory.
But when the file is not present how to create a file ?
for ex:
window.resolveLocalFileSystemURL(cordova.file.applicationStorageDirectory + "/path/to/file/sampleFile.txt", gotFile, fail);
here the above file "sampleFile.txt" doesnt exist. How to create the file when it doesnt exist ?
See this post, http://www.raymondcamden.co....
thanks a lot raymond especially for your quick response :)
Hi Raymond , i got a question when i run ur demo,the eclipse reports FileNotFoundException ,i don know why ,is there any problem in my config.xml?
Unfortunately this code is broken on Android due to this bug: https://issues.apache.org/j...
For now, if your code is really under www as it is in my demo, use XHR.
this approach works out .Thks a lot ! but what if i want to write something into the txt, what sould i do ?
Search the blog - I also have demos for writing. :) Or you can go to my GitHub repo where I store all of them: https://github.com/cfjedima...
(To be clear, that repo doesn't have *all* my demos - I started using it about a year ago to have a central place, but I've been blogging about PhoneGap/Cordova longer than that.)
you need to add the file plugin.
Go to your applications directory via CMD (windows). And typ the following command: cordova plugin add cordova-plugin-file
With the assumption you installed the cordova CLI.
More info Cordova CLI: https://cordova.apache.org/...
More info file plugin: https://github.com/apache/c...
After I've done
npm install cordova-plugin-file
which.js file must I include to be able to use the plugin in my Cordova app?Don't. Do cordova plugin add cordova-plugin-file.
Thanks for a very nice tutorial.
I've implemented read/write file functionality. My question is, how can I know that whether the file exist or not. And if it do not exist, so I would create a new one...
I'd check the docs on the FileSystem API (Chrome's older docs), but I believe you can make a new File object on the path and check the properties there. Definitely doable. Or - do a Directory object on the parent and get a list of files.
Right. I'll test it. Thanks
dude, simply you rock!
Thank you.
You are a life saver man!
Very informative.....a small query ..I have an external db file kept at www/example.db and Now I want it to move to root directory app/data/data/{app_package}/databases then how can I achieve ...Thanks in advance
Go to the docs for the File plugin and they link to an article talking about how to do stuff w/ the File system, including move operations.
Thank you .!!
Is there any way to read file from external SD Card?
Thanks
Check the File plugin docs and look at the 'externalStorageDirectory' values.
Please make sure externalStorageDirectory value is exist
I can't find that value.
Did you install the plugin? Did you read the docs? It isn't "just" externalStorageDirectory, it is cordova.file.externalDataDirectory or externalApplicationStorageDirectory. I typoed above - but again - read the docs for more information on the alias.
Sure, I tried all APIs , but didn't get external SD card(I inserted micro card), only got android's internal memory.
Not sure what to suggest then. Sorry.
Thanks for the simple code. i'm getting error {code:1}. can you please tell me why i'm getting this error
If you check the docs, https://www.npmjs.com/packa..., you will see a list of error codes, and that one is listed.
i am new in this framework so asking may be the stupid question but where to copy this code ?? means in which file. ?
If you are *100%* new to Cordova, I'd suggest reading their docs. I also have a book that is great for beginners: https://www.amazon.com/Apac...
What is the difference between this plugin and simple xhr request?
You can't use XHR to request a file outside of the web root of the app.
Thank you Raymond. Now I have a new related question. I am now developing an app which contains 13 mini-games. They are mini but the weight of the whole app is about 450 Mb. My question is: can I publish the app with just three games out of 13 and the user would download the other games one by one – with that File plugin? I use Intel XDK and I can't create apk expantion file (or maybe I can but just don't know).
You can't change the 'structure' of your app after release, so I'm not sure this would be allowed.
then how access external SD card data using cordova ?
I don't know - sorry.
Thank you, this is very helpful.
Thanks man!
Thanks Very Much. Just saw this awesome article. However, please help me. I want to play the audio file from the android folder "download" or Main "Music" directory and not the application directory
This comment isn't on topic for this blog post at all. I'd suggest posting your question to StackOverflow.
Could you please tell me how can I write file in applicationDirectory. Basically all I need is to update the translation file in assets folder.
You should read the docs on the file plugin and make an attempt first. The docs do cover this. When you have a complete solution, even if broken, I could try to help then.