I have made an android app. I am using database in it. I have installed the .apk file on my phone and it works fine. But it does not show me any data I entered in database while I was on emulator. I need to use database tables filled previously. My database does not create on run time. How can I get the database on my phone to see app running perfectly fine with the database?
You can save your database file under assets or res/raw directory, on the app's first startup, copy that database file to /data/data/com.company.yourapp/databases/, and open your database like usual.
The difference between saving files under assets and res/raw directories is that files under res/raw are compressed, while files under assets are not. And files under res/raw cannot exceed 1 MB before Android 2.3. So I'd suggest that you compress your database file yourself and save it to assets and in your code decompress the file using GZIPInputStream.
If you need your database out side the application for testing then i think you should export it into your sdcard.
public static void exportfile(String applicationPackageName,String databaseName,String pathOfFolder) throws FileNotFoundException, IOException
{
InputStream myInput;
myInput = new FileInputStream("/data/data/"+applicationPackageName+"/databases/"+databaseName);
File directory = new File("/sdcard"+pathOfFolder);
if (!directory.exists())
{
directory.mkdirs();
}
OutputStream myOutput = new FileOutputStream(directory.getPath()+"/"+databaseName);
byte[] buffer = new byte[1024];
int length;
while ((length = myInput.read(buffer))>0)
{
myOutput.write(buffer, 0, length);
}
myOutput.flush();
myOutput.close();
myInput.close();
}
applicationPackageName :- application package name
databaseName :- database file name
pathOfFolder :- path of folder where to export the file in sdcard
don't forget to add <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/> in your manifest file.
And download any SQLite Manager to open that file.
Thanks.. hope it helps you.
Related
My project is all about media player. I want to store manually hundreds of mp3 files in my project but the problem is I don't know where I can put the large file which is the file size is 300MB into my project. I already search many times on google but the answer is always putting the file into ExternalDirectory by using this code.
File file = new File(getExternalFilesDir(null)+"/");
The problem of this code is you can only store a file to this directory once you downloaded the file. Since my project is an offline app, I don't need an internet connection to it
Here is my first attempt.
I put my one mp3 file to asset folder which is the size is 5mb and make a copy to another directory
File file = new File(getExternalFilesDir(null)+"/newFile.mp3"); please take a look below.
private void copyFile() {
InputStream inputStream;
try {
inputStream = getAssets().open("raw/original.mp3");
File file = new File(getExternalFilesDir(null)+"/newFile.mp3");
OutputStream outputStream = new FileOutputStream(file);
byte[] buffer = new byte[1024];
int length;
while ((length = inputStream.read(buffer)) > 0) {
outputStream.write(buffer,0,length);
}
outputStream.flush();
outputStream.close();
inputStream.close();
Log.d(TAG, "copyFile: copied ");
} catch (IOException e) {
e.printStackTrace();
}
}
the code above works fine. I can see that the file was successfully copied but the problem is during my research they said that asset folder or res/raw folder has a storage limit it means that I can only store a file in asset folder with a file size less than 5MB (I am not sure).
My question is what is the best way to manually store mp3 files (300MB) to my project(without downloading the files)?
Thanks and advance.
Normally to make changes in my Database I followed the following steps:
Edited Database in SQLite
Delete Database in my assets folder
Copy paste Database in assets folder again
Delete the App from my phone through settings
Rebuild/install the app
This worked for me beforehand many times. No I have the issue that somehow my project does not access this database anymore.
I figured that out by deleting the database from my asset folder and reinstalling the app. The App still works, therefore it does not access the database from my asset folder that I used beforehand, to the best of my knowledge.
I am using the following path to access it:
DB_Path = mContext.getDatabasePath(DB_Name).
Log.e("DB_path", DB_Path);
Which yields
.com.example.chris.projectartifact E/DB_path:/data/user/0/com.example.chris.projectartifact/databases/myDB.db.
Regarding the Comment:
I am using the following method to copy my Database.
This is from a tutorial and it worked fine for a very long time.
From my understanding though FileOutputStream(DB_Path)
copies it to named path.
public void copyDataBase(){
try {
InputStream myInput = mContext.getAssets().open(DB_Name);
OutputStream myOutput = new FileOutputStream(DB_Path);
byte[] buffer = new byte[1024];
int length;
while ((length=myInput.read(buffer))>0){
myOutput.write(buffer,0,length);
}
myOutput.flush();
myOutput.close();
myInput.close();
} catch (IOException e){
Log.e("Error:","in CopyDatabase, where are in catch..");
e.printStackTrace();
}
}
The Questions:
Where do I find my database in my structure?
How am I able to update it?
New Question: How do i delete my copied database and renew it from my asset folder?
If your db is in your assets folder, its not on the file system at all- its in your assets- its part of the APK file (and thus read only). If you need it to be read write, you need to copy it to the filesystem first, and then you can put it where you want (although in the database path is traditional it isn't enforced).
I guess I'm a little confused as to how files are stored on an actual machine (or emulator even).
While programming, I can save my xml file in the assets folder manually, but how to write an app that will have to connect to the network and download the file,save it somewhere and then manipulate it ? where will it store said file ?
I want to create a new file, but I read on another post that the assets folder as such is not available once packaged; So where are they created and stored ? How can they be transferred. Its just, I'm new to this platform and the file system is a little confusing.
If you want to use XML that is updated, you should think of copying the file(s) from assets to device storage. You can take a look at How to copy files from 'assets' folder to sdcard? to know how this can be done.
Another alternative is to use the database where you can store the parsed data from the XML. So that you need not parse the file whenever you need to access the contents.
You have two options: call getFilesDir() from your activity to obtain a path to the internal data folder that can only be read/write from your app.
Or, you can write/read your xml file to external storage (SD Card). Use the method Environment.getExternalStorageDirectory() to get the root path of the external storage, then create your own folder as you see fit.
Note that if you write to external storage, every app in the phone will have access to it.
Even I faced this issue. Now I have a xml file which is has application properties.This is packaged in the assets folder.Once packaged we cannot edit a file in assets folder.
Now on app load I just copy this file to path returned by
context.getFilesDir().getAbsolutePath();
And the application edit it from the same place. You can see if the file is modified in the FileExplorer panel of DDMS view. The file is stored in the folder named same as your application package name for eg: com.abhi.maps
Alternatively you can also copy it to SD card.However it is risky because, sd card may bot be available all the time.
You can use the following code to copy file from assets folder:
private static void copyFile(String filename, Context context) {
AssetManager assetManager = context.getAssets();
InputStream in = null;
OutputStream out = null;
try {
in = assetManager.open(filename);
String newFileName = context.getFilesDir() + "/" + filename;
out = new FileOutputStream(newFileName);
byte[] buffer = new byte[1024];
int read;
while ((read = in.read(buffer)) != -1) {
out.write(buffer, 0, read);
}
in.close();
in = null;
out.flush();
out.close();
out = null;
} catch (Exception e) {
Log.e("tag", e.getMessage());
}
}
Hope it helps! :)
I am developing my android application using Netbeans and java. When I am using the emulator I can access the File explorer and insert an SQLite database in to device internal memory by accessing the following path, data/data/com.example.helloandroid/database
But I can not access this location to push the SQLite File in to the phone's internal storage (location) when I am using the real device.
Can someone please help me how to add the file in to phones internal storage. Thanks
I think the device doesn't have root permission, that's why you can't access it. If you want to do in your app with programmatically then it is possible. If anybody knows better then this please share it.
EDIT: ok, first of all,
1. copy your Database.db file in your projects assets folder.
2. now using code copy database file from /asset to device's internal storage
(data/data/<package name>/database folder).
For copy file use below code,
try {
// Open your local db as the input stream
InputStream myInput = myContext.getAssets().open("your database file name");
// Path to the just created empty db
String outFileName = "/data/data/<your_app_package_name>/databases/<database_file_name>";
OutputStream myOutput = new FileOutputStream(outFileName);
// transfer bytes from the inputfile to the outputfile
byte[] buffer = new byte[1024];
int length;
while ((length = myInput.read(buffer)) > 0)
{
myOutput.write(buffer, 0, length);
}
// Close the streams
myOutput.flush();
myOutput.close();
myInput.close();
}
catch (Exception e)
{
Log.e("error", e.toString());
}
One of my applications downloads a database from a server.
When I install the application onto my phone, it downloads the file correctly and loads the information, no exceptions thrown or anything.
However, when I upload the apk into the Android Market Place and download it onto the phone, the application downloads the database and then crashes, saying that the sqlite handler was not able to open up the database.
Here's the progression of code:
In the SQLiteOpenHelper:
this.FULL_DB_PATH = new String(this.getWritableDatabase().getPath());
this.getWritableDatabase();
// Code for retrieving the database off of the server:
private void copyDataBase(){
InputStream myInput=null;
OutputStream myOutput=null;
try{
// opening connections
URL url = new URL("server_url_here");
URLConnection ucon=url.openConnection();
myInput = ucon.getInputStream();
myOutput = new FileOutputStream(this.FULL_DB_PATH);
// write to the db here
byte[] buffer = new byte[1024*1024];
int length;
while ((length = myInput.read(buffer))>0){
myOutput.write(buffer, 0, length);
}
myOutput.flush();
myOutput.close();
myInput.close();
}
catch(Exception e)
{
try{
myOutput.flush();
myOutput.close();
myInput.close();
}
catch(Exception es){}
}
}
I don't know why my colleague is saving the db with a mp3 extension but...it works when we're installing the apk ad-hoc.
For:
myOutput = new FileOutputStream(this.FULL_DB_PATH);
I've also tried:
myOutput = this.getApplicationContext().openFileOutput(this.FULL_DB_PATH, Context.MODE_WORLD_READABLE);
But that doesn't work either.
Any help is greatly appreciated!! I've been tearing my hair out for a couple of hours over this and I just want it to end haha.
What you are doing is copying the file into the /data folder in the android file system. On a normal phone with normal permissions this is not allowed for security reasons. You can do this on the emulator and rooted phones because you have been granted permission to write to /data (normally only read).
To get around this you will need to manually add the information to the database using db.insert(String, String, ContentValues) and db.update(String, ContentValues, String, String[])
It would be nice to be able to do what you are trying but for security reasons it's a very good thing you can't.
The Emulator gives you special access that real phones don't. In other words, I suspect you are directly copying the file into the databases directory on the phone? If so, you can't do that on a non-rooted phone. Hopefully someone will chime in and prove me wrong because this is a problem for me too. I'd like to easily download a db file and install it. What I end up having to do as a work-around is create a new database and load the schema and data through queries.
EDIT:
I would like to share a trick with you. It's simple really. Instead of using just db.insert/db.update/ by themselves, scope them into transactions. In fact, I would scope the whole DB Build as a transaction, or at least just individual tables. I've experienced a 10-50x increase in speed of transactions when they're scoped and then committed all at once.
The other two answers are incorrect, I do believe. I have a backup system in my app where backups are copied to the sd-card, and then copied back to the /data/-folder when the backup is restored. While I have no idea why your code wont work, here is my code to copy the database from the sd-card:
final InputStream in = new FileInputStream(from);
final OutputStream out = new FileOutputStream(to);
final byte[] buf = new byte[1024];
int len;
while ((len = in.read(buf)) > 0){
out.write(buf, 0, len);
}
in.close();
out.close();
Just to closer investigare the error, try to download to the sd-card instead and then use my code to copy it to the data-folder. The "to" object in my code I get like this:
public static final String DATABASE_PATH = "/data/data/"+SomeClass.class.getPackage().getName()+"/databases/"+ DATABASE_NAME;
final File to = new File(Constant.DATABASE_PATH);