Flutter entry series - file system

Posted by Clintonio on Fri, 04 Feb 2022 05:04:56 +0100

Because fluent is only a UI system and does not have the ability to operate the native system, it can not directly operate the file system. Therefore, it can only realize this function with the help of plug-ins. provider_path is a plug-in widely used in pub. Let's start accessing the plug-in to complete the corresponding file reading and writing functions.

1, Rely on

Add dependency

dependencies:
  path_provider: ^2.0.1

2, Use

1. getApplicationSupportDirectory()

The / data/data/packagename/files directory is obtained in Android, which is equivalent to calling the getFilesDir() method, while in iOS, it is equivalent to calling the NSApplicationSupportDirectory. These directories are private to the program and will not be accessed by other programs. They are suitable for storing some private contents such as user information.

  //Create App private file / data/data/pkgname/
  //Strictly confidential data, such as user data, is recommended to be stored internally, corresponding to the getApplicationSupportDirectory method.
  void createAppSupportDir() async {
    Directory dir =  await getApplicationSupportDirectory();
    log("createApplicationSupportDir ${dir.path}");
    //createApplicationSupportDir /data/user/0/com.example.flutter_widgets/files
    String filePath = "${dir.path}/hello.txt";
    File file = File(filePath);
    if (!file.existsSync()){
         file.createSync();
    }
    //Write content to file
    file.writeAsStringSync("Happy New Year");
    //Read the contents of the file
    String data = file.readAsStringSync();
    log("readData from files $data");
  }

2. getTemporyDirectory()

In Android, it is the /data/data/packagename/cache/ directory, which is equivalent to calling the getCacheDir() method, calling NSCachesDirectory in iOS. This directory will be cleared at random. It is only suitable for storing the cache of the downloaded files.

  // On Android, this uses the `getCacheDir` API on the context.
  void createAppTempDir() async {
    Directory tempDir =  await getTemporaryDirectory();
    log("createAppTempDir ${tempDir.path}");
    //[log] createAppTempDir /data/user/0/com.example.flutter_widgets/cache
    String filePath = "${tempDir.path}/temp.txt";
    File file = File(filePath);
    if (!file.existsSync()){
      file.createSync();
    }
    //Write content to file
    file.writeAsStringSync("Happy Chinese New Year");
    //Read the contents of the file
    String data = file.readAsStringSync();
    log("readData from temp files: $data");
  }

3. getExternalCacheDirectories()

In Android, the / emulated / 0 / Android / data / packagename / cache directory is obtained, which is equivalent to calling context Getexternalcachedir() or call context below API 19 GetExternalCacheDir (), the call in iOS will throw an exception. This directory is used to specify external cache data. Because the phone may have multiple external memory cards, there may be multiple storage paths.

  //It is recommended to store all other data in Android/data / package name /,
  //Corresponds to getExternalCacheDirectories and getExternalStorageDirectories methods.
  void createAppExternalCacheDir() async {
    List<Directory>? dirs =  await getExternalCacheDirectories();
    dirs!.forEach((subDir) {
         print("subDir $subDir");
    });
    //I/flutter (22031): subDir Directory: '/storage/emulated/0/Android/data/com.example.flutter_widgets/cache'
    //I/flutter (22031): subDir Directory: '/storage/0DEB-3D0A/Android/data/com.example.flutter_widgets/cache'
  }

4. getExternalStorageDirectory()

In Android, the / mnt/sdcard/Android/data/packagename/files / directory is obtained. The highest level storage path that the application can access is equivalent to calling getExternalFilesDir(). This method can only be used in Android, iOS cannot be used, and exceptions will be thrown.

  void createExternalStorageDir() async{
    Directory? dir =  await getExternalStorageDirectory();
    log("createExternalStorageDir ${dir!.path}");
    // createExternalStorageDir /storage/emulated/0/Android/data/com.example.flutter_widgets/files
    String filePath = "${dir.path}/external_store.txt";
    File file = File(filePath);
    if (!file.existsSync()){
      file.createSync();
    }
    //Write content to file
    file.writeAsStringSync("Happy Tiger Year");
    //Read the contents of the file
    String data = file.readAsStringSync();
    ///mnt/sdcard/Android/data/com.example.flutter_widgets/files/external_store.txt
    log("readData from files $data");
  }

5. getExternalStorageDirectories()

In Android, the directory / mnt/sdcard/Android/data/packagename/files / is obtained. The implementation of this function is as follows:

Future<List<Directory>?> getExternalStorageDirectories({
  /// Optional parameter. See [StorageDirectory] for more informations on
  /// how this type translates to Android storage directories.
  StorageDirectory? type,
}) async {
  final List<String>? paths =
      await _platform.getExternalStoragePaths(type: type);
  if (paths == null) {
    return null;
  }

  return paths.map((String path) => Directory(path)).toList();
}
enum StorageDirectory {
  /// Contains audio files that should be treated as music.
  music,
  /// Contains audio files that should be treated as podcasts.
  podcasts,
  /// Contains audio files that should be treated as ringtones.
  ringtones,
  /// Contains audio files that should be treated as alarm sounds.
  alarms,
  /// Contains audio files that should be treated as notification sounds.
  notifications,
  /// Contains images.
  pictures,
  movies,
  /// Contains files of any type that have been downloaded by the user.
  downloads,
  /// Used to hold both pictures and videos when the device filesystem is
  /// treated like a camera's.
  dcim,
  /// Holds user-created documents.
  documents,
}

As can be seen from the above, this function has optional parameters, which can obtain the directory to access different contents. This function can only be used on Android, not on iOS platform, and an exception will be thrown.

  //Stored in / mnt/sdcard/Android/data/packagenmae/files /
  void createExternalStorageDirs() async{
   List<Directory>? dirs = await getExternalStorageDirectories();
   dirs!.forEach((element) {
      log("createExternalStorageDirs ${element.path}");
   });
   //[log] createExternalStorageDirs /storage/emulated/0/Android/data/com.example.flutter_widgets/files
   //[log] createExternalStorageDirs /storage/0DEB-3D0A/Android/data/com.example.flutter_widgets/files
  }

6. getApplicationDocumentsDirectory()

In Android, you get / data / data / packagename / APP_ Fluent / directory, which is used to store some data generated by users or that cannot be recreated by the application. It is equivalent to calling getDataDirectory(). If the data is visible to users, consider using getExternalStorageDirectory() method instead of this method. In iOS, this method is equivalent to calling the NSDocumentDirectory() method. If the data is not generated by the user, consider using getapplicationsupportdirectory().

  //getApplicationDocumentsDirectory is stored in / data / data / packagename / APP_ In the folder "fluent"
  void createDocumentDir() async {
    Directory dir = await  getApplicationDocumentsDirectory();
    log("createDocumentDir ${dir.path}");// createDocumentDir /data/user/0/com.example.flutter_widgets/app_flutter
    String filePath = "${dir.path}/document.txt";
    File file = File(filePath);
    if (!file.existsSync()){
      file.createSync();
    }
    //Write content to file
    file.writeAsStringSync("Happy Chinese New Year From Document");
    //Read the contents of the file
    String data = file.readAsStringSync();
    log("readData from document files: $data path ${file.absolute.path}");
    // /data/data/com.example.flutter_widgets/app_flutter/document.txt
  }

Summary:

From the above API, getApplicationSupport() directory is the most used directory, because it has good compatibility and can store users' privacy data and some other content data. Now Android's permission management is becoming more and more strict. Basically, programs can only access the directories they can manage. In fact, there is no need to obtain other directories, such as pictures and video albums, which can be completed by relying on third-party plug-ins.

reference resources:

Actual combat of Flutter - file system directory - brief book

Topics: Android Android Studio Flutter