Android
Stockage de fichiers dans le stockage interne et externe
Recherche…
Syntaxe
- FileOutputStream openFileInput (nom de la chaîne)
- FileOutputStream openFileOutput (Nom de la chaîne, mode int)
- Fichier (répertoire du fichier, nom de la chaîne)
- Fichier (chemin de chaîne)
- Fichier getExternalStoragePublicDirectory (type de chaîne)
- Fichier getExternalFilesDir (type de chaîne)
Paramètres
Paramètre | Détails |
---|---|
prénom | Le nom du fichier à ouvrir. REMARQUE: ne peut pas contenir de séparateurs de chemin |
mode | Mode de fonctionnement. Utilisez MODE_PRIVATE pour l'opération par défaut et MODE_APPEND pour ajouter un fichier existant. Les autres modes incluent MODE_WORLD_READABLE et MODE_WORLD_WRITEABLE , tous deux obsolètes dans l'API 17. |
dir | Répertoire du fichier pour créer un nouveau fichier dans |
chemin | Chemin pour spécifier l'emplacement du nouveau fichier |
type | Type de répertoire de fichiers à récupérer. Peut être null ou l'un des suivants: DIRECTORY_MUSIC , DIRECTORY_PODCASTS , DIRECTORY_RINGTONES , DIRECTORY_ALARMS , DIRECTORY_NOTIFICATIONS , DIRECTORY_PICTURES ou DIRECTORY_MOVIES |
Utilisation du stockage interne
Par défaut, tous les fichiers que vous enregistrez dans Internal Storage sont privés pour votre application. Ils ne sont pas accessibles par d'autres applications, ni par l'utilisateur dans des circonstances normales. Ces fichiers sont supprimés lorsque l'utilisateur désinstalle l'application .
Pour écrire du texte dans un fichier
String fileName= "helloworld";
String textToWrite = "Hello, World!";
FileOutputStream fileOutputStream;
try {
fileOutputStream = openFileOutput(fileName, Context.MODE_PRIVATE);
fileOutputStream.write(textToWrite.getBytes());
fileOutputStream.close();
} catch (Exception e) {
e.printStackTrace();
}
Pour ajouter du texte à un fichier existant
Utilisez Context.MODE_APPEND
pour le paramètre de mode de openFileOutput
fileOutputStream = openFileOutput(fileName, Context.MODE_APPEND);
Utilisation du stockage externe
Le stockage "externe" est un autre type de stockage que nous pouvons utiliser pour enregistrer des fichiers sur le périphérique de l'utilisateur. Il présente certaines différences clés par rapport au stockage "interne", à savoir:
- Il n'est pas toujours disponible. Dans le cas d'un support amovible (carte SD), l'utilisateur peut simplement supprimer le stockage.
- Ce n'est pas privé. L'utilisateur (et les autres applications) ont accès à ces fichiers.
- Si l'utilisateur désinstalle l'application, les fichiers que vous enregistrez dans le répertoire extrait avec
getExternalFilesDir()
seront supprimés.
Pour utiliser le stockage externe, vous devez d'abord obtenir les autorisations appropriées. Vous devrez utiliser:
-
android.permission.WRITE_EXTERNAL_STORAGE
pour lire et écrire -
android.permission.READ_EXTERNAL_STORAGE
pour juste lire
Pour accorder ces autorisations, vous devrez les identifier dans votre AndroidManifest.xml
tant que tel.
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
REMARQUE: Étant donné qu'il s'agit d' autorisations dangereuses si vous utilisez l' API niveau 23 ou supérieur, vous devrez demander les autorisations à l'exécution .
Avant d'essayer d'écrire ou de lire à partir du stockage externe, vous devez toujours vérifier que le support de stockage est disponible.
String state = Environment.getExternalStorageState();
if (state.equals(Environment.MEDIA_MOUNTED)) {
// Available to read and write
}
if (state.equals(Environment.MEDIA_MOUNTED) ||
state.equals(Environment.MEDIA_MOUNTED_READ_ONLY)) {
// Available to at least read
}
Lorsque vous écrivez des fichiers sur le stockage externe, vous devez décider si le fichier doit être reconnu comme public ou privé. Bien que ces deux types de fichiers soient toujours accessibles à l'utilisateur et à d'autres applications sur le périphérique, il existe une distinction essentielle entre eux.
Les fichiers publics doivent rester sur le périphérique lorsque l'utilisateur désinstalle l'application. Un exemple de fichier devant être enregistré en tant que public serait les photos prises via votre application.
Les fichiers privés doivent tous être supprimés lorsque l'utilisateur désinstalle l'application. Ces types de fichiers seraient spécifiques à l'application et ne seraient pas utiles à l'utilisateur ou à d'autres applications. Ex. fichiers temporaires téléchargés / utilisés par votre application.
Voici comment accéder au répertoire Documents
pour les fichiers publics et privés.
Publique
// Access your app's directory in the device's Public documents directory
File docs = new File(Environment.getExternalStoragePublicDirectory(
Environment.DIRECTORY_DOCUMENTS), "YourAppDirectory");
// Make the directory if it does not yet exist
myDocs.mkdirs();
Privé
// Access your app's Private documents directory
File file = new File(context.getExternalFilesDir(Environment.DIRECTORY_DOCUMENTS),
"YourAppDirectory");
// Make the directory if it does not yet exist
myDocs.mkdirs();
Android: Stockage interne et externe - Clarification de la terminologie
Les développeurs Android (principalement les débutants) ont été confus en ce qui concerne la terminologie de stockage interne et externe. Il y a beaucoup de questions sur Stackoverflow à propos de la même chose. Cela est principalement dû au fait que la terminologie selon la documentation Google / Android officielle est très différente de celle de l'utilisateur normal du système d'exploitation Android. J'ai donc pensé que documenter cela aiderait.
Ce que nous pensons - Terminologie de l'utilisateur (UT)
Stockage interne (UT) | Stockage externe (UT) |
---|---|
Mémoire interne intégrée au téléphone | carte SD (Secure Digital) amovible ou stockage micro SD |
Exemple: mémoire interne de 32 Go de Nexus 6P. | Exemple: espace de stockage dans des cartes SD amovibles fournies par des fournisseurs tels que samsung, sandisk, strontium, transcend et autres |
Mais, selon Android Documentation / Guide - Terminologie de Google (GT)
Stockage interne (GT):
Par défaut, les fichiers enregistrés dans le stockage interne sont privés pour votre application et les autres applications ne peuvent pas y accéder (ni l'utilisateur).
Stockage externe (GT):
Cela peut être un support de stockage amovible (comme une carte SD) ou un stockage interne (non amovible).
Le stockage externe (GT) peut être classé en deux types:
Stockage externe primaire | Stockage externe secondaire ou stockage amovible (GT) |
---|---|
Ceci est identique à la mémoire interne intégrée du téléphone (ou) au stockage interne (UT) | Ceci est identique au stockage sur carte micro SD amovible (ou) Stockage externe (UT) |
Exemple: mémoire interne de 32 Go de Nexus 6P. | Exemple: espace de stockage dans des cartes SD amovibles fournies par des fournisseurs tels que samsung, sandisk, strontium, transcend et autres |
Ce type de stockage est accessible sur Windows PC en connectant votre téléphone au PC via un câble USB et en sélectionnant Camera (PTP) dans la notification des options USB. | Ce type de stockage est accessible sur Windows PC en connectant votre téléphone au PC via un câble USB et en sélectionnant Transfert de fichiers dans la notification des options USB. |
En un mot,
Stockage externe (GT) = Stockage interne (UT) et stockage externe (UT)
Stockage amovible (GT) = Stockage externe (UT)
Le stockage interne (GT) n'a pas de terme en UT.
Laissez-moi vous expliquer clairement,
Stockage interne (GT): par défaut, les fichiers enregistrés sur le stockage interne sont privés de votre application et les autres applications ne peuvent pas y accéder. Votre utilisateur de l'application ne peut pas non plus y accéder à l'aide du gestionnaire de fichiers. même après avoir activé l'option "Afficher les fichiers cachés" dans le gestionnaire de fichiers. Pour accéder aux fichiers dans le stockage interne (GT), vous devez rooter votre téléphone Android. De plus, lorsque l'utilisateur désinstalle votre application, ces fichiers sont supprimés / supprimés.
Donc, le stockage interne (GT) n'est pas ce que nous pensons comme la mémoire interne 32/64 Go de Nexus 6P
En règle générale, l'emplacement du stockage interne (GT) serait: /data/data/your.application.package.appname/someDirectory/
Stockage externe (GT):
Chaque appareil compatible Android prend en charge un «stockage externe» partagé que vous pouvez utiliser pour enregistrer des fichiers. Les fichiers enregistrés sur le stockage externe sont lisibles dans le monde entier et peuvent être modifiés par l'utilisateur lorsqu'ils permettent le stockage de masse USB pour transférer des fichiers sur un ordinateur.
Emplacement de stockage externe (GT): il peut se trouver n'importe où dans votre stockage interne ou dans votre stockage amovible, par exemple une carte micro SD. Cela dépend de l'OEM de votre téléphone et aussi de la version du système d'exploitation Android.
Pour lire ou écrire des fichiers sur le stockage externe (GT), votre application doit acquérir les autorisations système READ_EXTERNAL_STORAGE
ou WRITE_EXTERNAL_STORAGE
.
Par exemple:
<manifest ...>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
...
</manifest>
Si vous devez à la fois lire et écrire des fichiers, vous devez demander uniquement l'autorisation
WRITE_EXTERNAL_STORAGE
, car cela nécessite implicitement un accès en lecture.
Dans le stockage externe (GT) , vous pouvez également enregistrer des fichiers qui sont app-private
Mais,
Lorsque l'utilisateur désinstalle votre application, ce répertoire et tout son contenu sont supprimés.
Quand avez-vous besoin de sauvegarder des fichiers qui sont app-private dans External Storage (GT) ?
Si vous gérez des fichiers qui ne sont pas destinés à d'autres applications (par exemple, des textures graphiques ou des effets sonores utilisés uniquement par votre application), vous devez utiliser un répertoire de stockage privé sur le stockage externe.
Depuis Android 4.4, la lecture ou l'écriture de fichiers dans les répertoires privés de votre application ne nécessite pas les autorisations
READ_EXTERNAL_STORAGE
ouWRITE_EXTERNAL_STORAGE
. Vous pouvez donc déclarer que l'autorisation doit être demandée uniquement sur les versions inférieures d'Android en ajoutant l'attributmaxSdkVersion
:
<manifest ...>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"
android:maxSdkVersion="18" />
...
</manifest
Méthodes à stocker dans le stockage interne (GT):
Ces deux méthodes sont présentes dans la classe Context
File getDir (String name, int mode)
File getFilesDir ()
Méthodes à stocker dans le stockage externe primaire, c'est-à-dire le stockage interne (UT):
File getExternalStorageDirectory ()
File getExternalFilesDir (String type)
File getExternalStoragePublicDirectory (String type)
Au début, tout le monde utilisait Environment.getExternalStorageDirectory () , qui indiquait la racine du stockage externe primaire . En conséquence, le stockage externe principal était rempli de contenu aléatoire.
Plus tard, ces deux méthodes ont été ajoutées:
Dans la classe
Context
, ils ont ajouté getExternalFilesDir () , pointant vers un répertoire spécifique à l' application sur le stockage externe principal. Ce répertoire et son contenu seront supprimés lors de la désinstallation de l'application.Environment.getExternalStoragePublicDirectory () pour les emplacements centralisés permettant de stocker des types de fichiers connus, tels que des photos et des films. Ce répertoire et son contenu ne seront PAS supprimés lors de la désinstallation de l'application.
Méthodes de stockage dans le stockage amovible (GT), c.-à-d. Carte micro SD
Avant le niveau 19 de l'API , il n'y avait pas de moyen officiel de stocker sur une carte SD. Mais, beaucoup pourraient le faire en utilisant des bibliothèques non officielles ou des API.
Officiellement, une méthode a été introduite dans la classe Context
au niveau 19 de l’API (Android version 4.4 - Kitkat).
File[] getExternalFilesDirs (String type)
Il renvoie des chemins d'accès absolus aux répertoires spécifiques à l'application sur tous les périphériques de stockage partagés / externes sur lesquels l'application peut placer des fichiers persistants qu'elle possède. Ces fichiers sont internes à l'application et ne sont généralement pas visibles par l'utilisateur en tant que support.
Cela signifie qu'il renverra des chemins vers les deux types de stockage externe (GT) - mémoire interne et carte micro SD. Généralement, le deuxième chemin serait le chemin de stockage de la carte micro SD (mais pas toujours). Vous devez donc le vérifier en exécutant le code avec cette méthode.
Exemple avec l'extrait de code:
J'ai créé un nouveau projet Android avec une activité vide, écrit le code suivant à l'intérieur
protected void onCreate(Bundle savedInstanceState)
de MainActivity.java
File internal_m1 = getDir("custom", 0);
File internal_m2 = getFilesDir();
File external_m1 = Environment.getExternalStorageDirectory();
File external_m2 = getExternalFilesDir(null);
File external_m2_Args = getExternalFilesDir(Environment.DIRECTORY_PICTURES);
File external_m3 = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES);
File[] external_AND_removable_storage_m1 = getExternalFilesDirs(null);
File[] external_AND_removable_storage_m1_Args = getExternalFilesDirs(Environment.DIRECTORY_PICTURES);
Après avoir exécuté le code ci-dessus,
Sortie:
internal_m1: /data/data/your.application.package.appname/app_custom
internal_m2: /data/data/your.application.package.appname/files
external_m1: /storage/emulated/0
external_m2: /storage/emulated/0/Android/data/your.application.package.appname/files
external_m2_Args: /storage/emulated/0/Android/data/your.application.package.appname/files/Pictures
external_m3: /storage/emulated/0/Pictures
external_AND_removable_storage_m1 (first path):
/storage/emulated/0/Android/data/your.application.package.appname/files
external_AND_removable_storage_m1 (second path):
/storage/sdcard1/Android/data/your.application.package.appname/files
external_AND_removable_storage_m1_Args (first path):
/storage/emulated/0/Android/data/your.application.package.appname/files/Pictures
external_AND_removable_storage_m1_Args (second path): /storage/sdcard1/Android/data/your.application.package.appname/files/Pictures
Remarque: J'ai connecté mon téléphone à un PC Windows; activé les deux options de développeur, le débogage USB et ensuite exécuté ce code. Si vous ne connectez pas votre téléphone mais au lieu de cela exécuter sur l' émulateur Android , votre sortie peut varier. Mon modèle de téléphone est Coolpad Note 3 - fonctionnant sur Android 5.1
Emplacements de stockage sur mon téléphone:
Emplacement de stockage Micro SD : /storage/sdcard1
Emplacement de stockage interne (UT) : /storage/sdcard0
.
Notez que /sdcard
& /storage/emulated/0
pointe également vers le stockage interne (UT). Mais ce sont des liens symboliques vers /storage/sdcard0
.
Pour bien comprendre les différents chemins de stockage sous Android, veuillez parcourir cette réponse
Disclaimer: Tous les chemins de stockage mentionnés ci-dessus sont des chemins sur mon téléphone. Vos fichiers ne peuvent pas être stockés sur les mêmes chemins de stockage. Parce que les emplacements de stockage / chemins peuvent varier sur les autres téléphones mobiles en fonction de votre fournisseur, du fabricant et des différentes versions du système d'exploitation Android.
Enregistrer la base de données sur la carte SD (Backup DB on SD)
public static Boolean ExportDB(String DATABASE_NAME , String packageName , String folderName){
//DATABASE_NAME including ".db" at the end like "mayApp.db"
String DBName = DATABASE_NAME.substring(0, DATABASE_NAME.length() - 3);
File data = Environment.getDataDirectory();
FileChannel source=null;
FileChannel destination=null;
String currentDBPath = "/data/"+ packageName +"/databases/"+DATABASE_NAME; // getting app db path
File sd = Environment.getExternalStorageDirectory(); // getting phone SD card path
String backupPath = sd.getAbsolutePath() + folderName; // if you want to set backup in specific folder name
/* be careful , foldername must initial like this : "/myFolder" . dont forget "/" at begin of folder name
you could define foldername like this : "/myOutterFolder/MyInnerFolder" and so on ...
*/
File dir = new File(backupPath);
if(!dir.exists()) // if there was no folder at this path , it create it .
{
dir.mkdirs();
}
DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd_HH-mm-ss");
Date date = new Date();
/* use date including file name for arrange them and preventing to make file with the same*/
File currentDB = new File(data, currentDBPath);
File backupDB = new File(backupPath, DBName +"("+ dateFormat.format(date)+").db");
try {
if (currentDB.exists() && !backupDB.exists()) {
source = new FileInputStream(currentDB).getChannel();
destination = new FileOutputStream(backupDB).getChannel();
destination.transferFrom(source, 0, source.size());
source.close();
destination.close();
return true;
}
return false;
} catch(IOException e) {
e.printStackTrace();
return false;
}
}
appelle cette méthode de cette façon:
ExportDB ("myDB.db", "com.example.exam", "/ myFolder");
Récupérer le répertoire du périphérique:
Tout d'abord, ajoutez l'autorisation de stockage pour lire / récupérer le répertoire du périphérique.
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
Créer une classe de modèle
//create one directory model class
//to store directory title and type in list
public class DirectoryModel {
String dirName;
int dirType; // set 1 or 0, where 0 for directory and 1 for file.
public int getDirType() {
return dirType;
}
public void setDirType(int dirType) {
this.dirType = dirType;
}
public String getDirName() {
return dirName;
}
public void setDirName(String dirName) {
this.dirName = dirName;
}
}
Créer une liste en utilisant le modèle de répertoire pour ajouter des données de répertoire.
//define list to show directory
List<DirectoryModel> rootDir = new ArrayList<>();
Récupère le répertoire en utilisant la méthode suivante.
//to fetch device directory
private void getDirectory(String currDir) { // pass device root directory
File f = new File(currDir);
File[] files = f.listFiles();
if (files != null) {
if (files.length > 0) {
rootDir.clear();
for (File inFile : files) {
if (inFile.isDirectory()) { //return true if it's directory
// is directory
DirectoryModel dir = new DirectoryModel();
dir.setDirName(inFile.toString().replace("/storage/emulated/0", ""));
dir.setDirType(0); // set 0 for directory
rootDir.add(dir);
} else if (inFile.isFile()) { // return true if it's file
//is file
DirectoryModel dir = new DirectoryModel();
dir.setDirName(inFile.toString().replace("/storage/emulated/0", ""));
dir.setDirType(1); // set 1 for file
rootDir.add(dir);
}
}
}
printDirectoryList();
}
}
Imprimer la liste des répertoires dans le journal.
//print directory list in logs
private void printDirectoryList() {
for (int i = 0; i < rootDir.size(); i++) {
Log.e(TAG, "printDirectoryLogs: " + rootDir.get(i).toString());
}
}
Usage
//to Fetch Directory Call function with root directory.
String rootPath = Environment.getExternalStorageDirectory().toString(); // return ==> /storage/emulated/0/
getDirectory(rootPath );
Pour récupérer les fichiers / dossiers internes d'un répertoire spécifique, utilisez la même méthode, changez simplement d'argument, transmettez le chemin sélectionné dans l'argument et gérez la réponse pour le même.
Pour obtenir une extension de fichier:
private String getExtension(String filename) {
String filenameArray[] = filename.split("\\.");
String extension = filenameArray[filenameArray.length - 1];
Log.d(TAG, "getExtension: " + extension);
return extension;
}