Android External Storage with Examples

In android, we have different storage options such as shared preferencesinternal storage, external storage, SQLite storage, etc. to store and retrieve the application data based on our requirements.

 

In previous chapters, we learned how to use Shared Preferences, Internal Storage and now we will see how to use the External Storage option to store and retrieve the data from external storage media such as SD card.

 

In android, External Storage is useful to store the data files publically on the shared external storage using the FileOutputStream object. After storing the data files on external storage, we can read the data file from external storage media using a FileInputStream object.

 

The data files saved in external storage are word-readable and can be modified by the user when they enable USB mass storage to transfer files on a computer.

Grant Access to External Storage

To read or write files on the external storage, our app must acquire the WRITE_EXTERNAL_STORAGE and READ_EXTERNAL_STORAGE system permissions. For that, we need to add the following permissions in the android manifest file like as shown below.

 

<manifest>
    ....
    <
uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
    <
uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
    ....
</
manifest>

Checking External Storage Availability

Before we do any work with external storage, first we need to check whether the media is available or not by calling getExternalStorageState(). The media might be mounted to a computer, missing, read-only or in some other state. To get the media status, we need to write the code like as shown below.

 

boolean Available= false;
boolean Readable= false;
String state = Environment.getExternalStorageState();
if(Environment.MEDIA_MOUNTED.equals(state)){
   
// Both Read and write operations available
   
Available= true;
}
else if (Environment.MEDIA_MOUNTED_READ_ONLY.equals(state)){
   
// Only Read operation available
   
Available= true;
    Readable=
true;
}
else {
   
// SD card not mounted
   
Available = false;
}

If you observe the above code snippet, we used getExternalStorageState() method to know the status of media mounted to a computer, such as missing, read-only or in some other state.

 

In android, by using getExternalStoragePublishDirectory() method we can access the files from appropriate public directory by passing the type of directory we want, such as DIRECTORY_MUSIC, DIRECTORY_PICTURES, DIRECTORY_RINGTONES, etc. based on our requirements.

 

If we save our files to corresponding media-type public directory, the system's media scanner can properly categorize our files in the system.

 

Following is the example to create a directory for a new photo album in the public pictures directory.

 

// Get the directory for the user's public pictures directory.
File file = new File(Environment.getExternalStoragePublicDirectory(
        Environment.
DIRECTORY_PICTURES), albumName);
if (!file.mkdirs()) {
    Log.e(LOG_TAG,
"Directory not created");
}

In case, if we are handling the files that are not intended for other apps to use, then we should use a private storage directory on the external storage by calling getExternalFilesDir().

Write a File to External Storage

By using android FileOutputStream object and getExternalStoragePublicDirectory method, we can easily create and write data to the file in external storage public folders.

 

Following is the code snippet to create and write a public file in the device Downloads folder.

 

String FILENAME = "user_details";
String name =
"suresh";

File folder = Environment.getExternalStoragePublicDirectory(Environment.
DIRECTORY_DOWNLOADS);
File myFile =
new File(folder, FILENAME);
FileOutputStream
fstream = new FileOutputStream(myFile);

fstream.write(name.getBytes());
fstream.close();

If you observe above code, we are creating and writing a file in device public Downloads folder by using getExternalStoragePublicDirectory method. We used write() method to write the data in file and used close() method to close the stream.

Read a File from External Storage

By using the android FileInputStream object and getExternalStoragePublicDirectory method, we can easily read the file from external storage.

 

Following is the code snippet to read data from a file that is in the downloads folder.

 

String FILENAME = "user_details";
File folder = Environment.getExternalStoragePublicDirectory(Environment.
DIRECTORY_DOWNLOADS);
File myFile =
new File(folder, FILENAME);
FileInputStream
fstream = new FileInputStream(myFile);
StringBuffer sbuffer =
new StringBuffer();
int i;
while ((i = fstream.read())!= -1){
    sbuffer.append((
char)i);
}
fstream.close();

If you observe above code, we are reading a file from device Downloads folder storage by using FileInputStream object getExternalStoragePublicDirectory method with file name. We used read() method to read one character at a time from the file and used close() method to close the stream.

 

Now we will see how to save or write file to external memory and read the file data from external storage using android FileInputStream and FileOutputStream objects in android applications with examples.

Android External Storage Example

Following is the example of storing and retrieving the data files from external memory by using FileOutputStream and FileInputStream objects.

 

Create a new android application using android studio and give names as ExternalStorageExample. In case if you are not aware of creating an app in android studio check this article Android Hello World App.

 

Once we create an application, open activity_main.xml file from \res\layout folder path and write the code like as shown below.

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
   
android:orientation="vertical" android:layout_width="match_parent"
   
android:layout_height="match_parent">
    <
TextView
       
android:id="@+id/fstTxt"
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:layout_marginLeft="100dp"
       
android:layout_marginTop="150dp"
       
android:text="UserName" />
    <
EditText
       
android:id="@+id/txtName"
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:layout_marginLeft="100dp"
       
android:ems="10"/>
    <
TextView
       
android:id="@+id/secTxt"
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:text="Password"
       
android:layout_marginLeft="100dp" />
    <
EditText
       
android:id="@+id/txtPwd"
       
android:inputType="textPassword"
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:layout_marginLeft="100dp"
       
android:ems="10" />
    <
Button
       
android:id="@+id/btnSave"
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:layout_marginLeft="100dp"
       
android:text="Save" />
</
LinearLayout>

Now we will create another layout resource file details.xml in \res\layout path to get the first activity (activity_main.xml) details in second activity file for that right click on your layout folder à Go to New à select Layout Resource File and give name as details.xml.

 

Once we create a new layout resource file details.xml, open it and write the code like as shown below

details.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
   
android:orientation="vertical" android:layout_width="match_parent"
   
android:layout_height="match_parent">
    <
TextView
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:id="@+id/resultView"
       
android:layout_gravity="center"
       
android:layout_marginTop="170dp"
       
android:textSize="20dp"/>
    <
Button
        
android:id="@+id/btnBack"
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:layout_gravity="center"
       
android:layout_marginTop="20dp"
       
android:text="Back" />
</
LinearLayout>

Now open your main activity file MainActivity.java from \java\com.tutlane.externalstorageexample path and write the code like as shown below

MainActivity.java

package com.tutlane.externalstorageexample;
import android.content.Intent;
import android.os.Environment;
import android.support.v4.app.ActivityCompat;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

public class MainActivity extends AppCompatActivity {
    EditText
uname, pwd;
    Button
saveBtn;
    FileOutputStream
fstream;
    Intent
intent;
   
@Override
   
protected void onCreate(Bundle savedInstanceState) {
       
super.onCreate(savedInstanceState);
        setContentView(R.layout.
activity_main);
       
uname = (EditText)findViewById(R.id.txtName);
       
pwd = (EditText)findViewById(R.id.txtPwd);
       
saveBtn = (Button)findViewById(R.id.btnSave);
       
saveBtn.setOnClickListener(new View.OnClickListener() {
           
@Override
           
public void onClick(View v) {
                String username =
uname.getText().toString()+"\n";
                String password =
pwd.getText().toString();
               
try {
                    ActivityCompat.requestPermissions(MainActivity.
this, new String[]{android.Manifest.permission.READ_EXTERNAL_STORAGE},23);
                    File folder = Environment.getExternalStoragePublicDirectory(Environment.
DIRECTORY_DOWNLOADS);
                    File myFile =
new File(folder,"user_details");
                   
fstream = new FileOutputStream(myFile);
                   
fstream.write(username.getBytes());
                   
fstream.write(password.getBytes());
                   
fstream.close();
                    Toast.makeText(getApplicationContext(),
"Details Saved in "+myFile.getAbsolutePath(),Toast.LENGTH_SHORT).show();
                   
intent = new Intent(MainActivity.this,DetailsActivity.class);
                    startActivity(
intent);
                }
catch (FileNotFoundException e) {
                    e.printStackTrace();
                }
catch (IOException e) {
                    e.printStackTrace();
                }
            }
        });
    }
}

If you observe above code, we are taking entered username and password details and saving it in device external memory and redirecting the user to another activity.

 

Now we will create another activity file DetailsActivity.java in \java\com.tutlane.externalstorageexample path to show the details from external storage for that right-click on your application folder à Go to New à select Java Class and give name as DetailsActivity.java.

 

Once we create a new activity file DetailsActivity.java, open it and write the code like as shown below

DetailsActivity.java

package com.tutlane.externalstorageexample;
import android.content.Intent;
import android.os.Bundle;
import android.os.Environment;
import android.support.v7.app.AppCompatActivity;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/**
 * Created by tutlane on 05-01-2018.
 */

public class DetailsActivity extends AppCompatActivity {
    FileInputStream
fstream;
    Intent
intent;
   
@Override
   
protected void onCreate(Bundle savedInstanceState) {
       
super.onCreate(savedInstanceState);
        setContentView(R.layout.
details);
        TextView result = (TextView)findViewById(R.id.
resultView);
        Button back = (Button)findViewById(R.id.
btnBack);
       
try {
            File folder = Environment.getExternalStoragePublicDirectory(Environment.
DIRECTORY_DOWNLOADS);
            File myFile =
new File(folder,"user_details");
           
fstream = new FileInputStream(myFile);
            StringBuffer sbuffer =
new StringBuffer();
           
int i;
           
while ((i = fstream.read())!= -1){
                sbuffer.append((
char)i);
            }
           
fstream.close();
            String details[] = sbuffer.toString().split(
"\n");
            result.setText(
"Name: "+ details[0]+"\nPassword: "+details[1]);
        }
catch (FileNotFoundException e) {
            e.printStackTrace();
        }
catch (IOException e) {
            e.printStackTrace();
        }
        back.setOnClickListener(
new View.OnClickListener() {
           
@Override
           
public void onClick(View v) {
               
intent = new Intent(DetailsActivity.this,MainActivity.class);
                startActivity(
intent);
            }
        });
    }
}

Now we need to add this newly created activity in AndroidManifest.xml file in like as shown below.

AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
   
package="com.tutlane.externalstorageexample">
    <
uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
    <
uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
    <
application
       
android:allowBackup="true"
       
android:icon="@mipmap/ic_launcher"
       
android:label="@string/app_name"
       
android:roundIcon="@mipmap/ic_launcher_round"
       
android:supportsRtl="true"
       
android:theme="@style/AppTheme">
        <
activity android:name=".MainActivity">
            <
intent-filter>
                <
action android:name="android.intent.action.MAIN" />
                <
category android:name="android.intent.category.LAUNCHER" />
            </
intent-filter>
        </
activity>
        <
activity android:name=".DetailsActivity" android:label="External Storage - Details"></activity>
    </
application>
</
manifest>

If you observe above example, we are saving entered details file and redirecting the user to another activity file (DetailsActivity.java) to show the users details and added all the activities in AndroidManifest.xml file.

Output of Android External Storage Example

When we run above example in the android emulator we will get a result like as shown below

 

Android External Storage Example Result

 

If you observe the above result, the entered username and password details are storing in external memory and redirecting the user to another activity file to show the user details from external storage file. After that, if we click on the Back button, it will redirect the user to the login page.

 

This is how we can use the External Storage option in android applications to store and retrieve data from device external memory based on our requirements.