Android Tutorial: Android Internal Storage

 ·  · 

1 What Is Android Internal Storage

Android allows your android application save or cache private data or files on the device memory, which is called internal storage.

Data saved or cached in internal storage are private and can be accessed only within your application, other applications cannot access them.

Furthermore, data of your application that is saved in internal storage will be also deleted if user remove your application.

 

2 APIs

The absolute path of internal storage folder is: /data/data/<YOUR_APP_PACKAGE_NAME>/files/. Call getFilesDir() method to obtain this path. getFilesDir() will return a java.io.File object. Then you can simply use java IO APIs to read or write files under internal storage folder.

2.1 Write

We will create a simple demo application to write a file to internal storage.

Main UI controls here:

  • A Button, click to write file;
  • Another Button, click to read saved file;
  • A TextView to display the absolute file path of internal storage;

The file to be saved named hello.txt, and we'll write a string "Hello World!" to it.

package com.codevoila.androidtutorial;

import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;

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

public class InternalStorageActivity extends AppCompatActivity implements View.OnClickListener {

    private TextView textViewPathHint;
    private Button btnWriteInternal;

    private String demoFileName = "hello.txt";
    private String demoFileContent = "Hello World!";

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_internal_storage);

        textViewPathHint = (TextView) findViewById(R.id.tv_path_hint);

        btnWriteInternal = (Button) findViewById(R.id.btn_write_internal);
        btnWriteInternal.setOnClickListener(this);
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.btn_write_internal:
                this.writeInternalDemo();
                break;
            default:
                break;
        }
    }

    private void writeInternalDemo() {
        // Path will be: /data/data/<YOUR_APP_PACKAGE_NAME>/hello.txt
        File file = new File(getFilesDir(), this.demoFileName);

        // Display the absolute path of Internal Storage
        this.textViewPathHint.setText(file.getAbsolutePath());

        FileOutputStream fos = null;

        try {
            fos = new FileOutputStream(file);
            fos.write(this.demoFileContent.getBytes());
        } catch (Exception e) {
            e.printStackTrace();
            Toast.makeText(this, "Failed: " + e.getMessage(), Toast.LENGTH_LONG).show();
        } finally {
            if (fos != null) {
                try {
                    Toast.makeText(this, "Write to " + demoFileName + " successfully!", Toast.LENGTH_LONG).show();
                    fos.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            } else {
                Toast.makeText(this, "Failed to write!", Toast.LENGTH_LONG).show();
            }
        }
    }
}

2.2 Read

Reading file from internal storage is also simple, just like the common Java IO operations.

We'll add a read button in above demo application. After clicking read button, a popup Toast will display the content read from internal storage file.

package com.codevoila.androidtutorial;

import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;

public class InternalStorageActivity extends AppCompatActivity implements View.OnClickListener {

    private TextView textViewPathHint;
    private Button btnWriteInternal;
    private Button btnReadInternal;

    private String demoFileName = "hello.txt";
    private String demoFileContent = "Hello World!";

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_internal_storage);

        textViewPathHint = (TextView) findViewById(R.id.tv_path_hint);

        btnWriteInternal = (Button) findViewById(R.id.btn_write_internal);
        btnWriteInternal.setOnClickListener(this);

        btnReadInternal = (Button) findViewById(R.id.btn_read_internal);
        btnReadInternal.setOnClickListener(this);
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.btn_write_internal:
                this.writeInternalDemo();
                break;
            case R.id.btn_read_internal:
                this.readInternalDemo();
                break;
            default:
                break;
        }
    }

    private void writeInternalDemo() {
        // ...
    }

    private void readInternalDemo() {
        File file = new File(getFilesDir(), this.demoFileName);

        if (!file.exists()) {
            this.btnReadInternal.setEnabled(false);
            Toast.makeText(this, "Failed: file does not exist", Toast.LENGTH_LONG).show();
            return;
        }

        FileInputStream fis = null;
        String textContent = "";

        try {
            fis = new FileInputStream(file);
            BufferedReader br = new BufferedReader(new InputStreamReader(fis));
            textContent = br.readLine();
        } catch (Exception e) {
            Toast.makeText(this, "Failed: " + e.getMessage(), Toast.LENGTH_LONG).show();
        } finally {
            if (fis != null) {
                Toast.makeText(this, "Read Successfully: " + textContent, Toast.LENGTH_LONG).show();
                try {
                    fis.close();
                } catch (IOException e) {
                    e.printStackTrace();
                    Toast.makeText(this, "Failed to read!", Toast.LENGTH_LONG).show();
                }
            }
        }
    }
}

2.3 Cache

Instead of getFilesDir(), getCacheDir() will return an internal storage folder path for caching data. The absolute path returned by getCacheDir() is: /data/data/<YOUR_APP_PACKAGE_NAME>/cache/. This folder is used to cache some temporary files in your application.

android_internal_storage

There are important differences between files folder and cache folder in internal storage.

  • The data saved under cache folder will be deleted automatically by Android system if the spare space of internal storage is not enough or full;
  • The data saved under files folder will NOT be deleted unless device user clear it explicitly.

Android provided UI interface to clear cache or data of an installed application. In your Android device or emulator, navigate to Settings > Apps > YOUR_APP > storage you can see two clear buttons.

android_clear_data_clear_cache

  • Clear Cache: will delete all data under /data/data/<YOUR_APP_PACKAGE_NAME>/cache/;
  • Clear Data: will delete all custom data under your application folder, including BOTH /data/data/<YOUR_APP_PACKAGE_NAME>/cache/ AND /data/data/<YOUR_APP_PACKAGE_NAME>/files/;

It is a best practice to save the important data of your application into the path that is returned by getFilesDir().