Say that you’re working on building an image editor app. In this case, you would let the user perform the following steps:
- In the app, access the user’s camera to take photos
- If the user snaps a photo, import this file to another module that lets them edit the image
- When the user is done modifying the picture, the app should upload this to social media
Sure, this might work. But there is a minor flaw: what if the client wants to edit an existing image? To make this possible, this means that the program should have access to the user’s file system.
This is where react-native-fs
comes in. It is an easy-to-use library that lets developers read and write files and folders to the host device. In this guide, you will learn the fundamentals of the react-native-fs
library and work through some advanced use cases.
This will be the outcome of this article:
Here are the steps we’ll take:
Getting started
As a first step, we have to initialize a React Native project using react-native-cli
like so:
react-native init fileSystemLearn
When that’s done, install the react-native-fs
module:
npm install react-native-fs react-native link react-native-fs #link this library with our app's native code
Basic usage
Getting file paths
RNFS includes a set of constants that informs the user about the list of file paths configured on their device. Some of them include:
MainBundleDirectory
: The app’s data folderDownloadDirectoryPath
: Points toward the user’sDownloads
directoryExternalStorageDirectory
: Contains the path of the device’s external storage
Here’s a brief example of these constants in action:
import {useState, useEffect} from 'react'; import RNFS from 'react-native-fs'; function App() { const [downloadsFolder, setDownloadsFolder] = useState(''); const [documentsFolder, setDocumentsFolder] = useState(''); const [externalDirectory, setExternalDirectory] = useState(''); useEffect(() => { //get user's file paths from react-native-fs setDownloadsFolder(RNFS.DownloadDirectoryPath); setDocumentsFolder(RNFS.DocumentDirectoryPath); //alternative to MainBundleDirectory. setExternalDirectory(RNFS.ExternalStorageDirectoryPath); }, []); return ( <SafeAreaView> <Text> Downloads Folder: {downloadsFolder}</Text> <Text>Documents folder: {documentsFolder}</Text> <Text>External storage: {externalDirectory}</Text> </SafeAreaView> ); }
In this code sample, we procured the user’s file paths from the react-native-fs
library. Later on, we then stored these values into the downloadsFolder
, documentsFolder
, and externalFolder
Hooks. In the end, the program rendered the Hooks onto the screen.
Reading directories
To get files and folder content, RNFS bundles a readDir
method. As the name suggests, this function allows developers to get statistics of a certain folder:
function App() { const [files, setFiles] = useState([]); const getFileContent = async (path) => { const reader = await RNFS.readDir(path); setFiles(reader); }; useEffect(() => { getFileContent(RNFS.DocumentDirectoryPath); //run the function on the first render. }, []); //this component will render our list item to the UI const Item = ({ name, isFile }) => { return ( <View> <Text style={styles.name}>Name: {name}</Text> <Text> {isFile ? "It is a file" : "It's a folder"}</Text> </View> ); }; const renderItem = ({ item, index }) => { return ( <View> <Text style={styles.title}>{index}</Text> {/* The isFile method indicates whether the scanned content is a file or a folder*/} <Item name={item.name} isFile={item.isFile()} /> </View> ); }; return ( <SafeAreaView> <FlatList data={files} renderItem={renderItem} keyExtractor={(item) => item.name} /> </SafeAreaView> ); }
Here’s a breakdown of this code piece by piece:
- In the beginning, we declared an asynchronous function called
getFileContent
- The
getFileContent
method executes thereadDir
method with the argument set topath
. This means that the project will read thepath
directory and return all the available content as an array - Later on, we stored the value of the response into the
files
Hook - Furthermore, the program executed the
getFileContent
function and passed in theRNFS.DocumentDirectoryPath
constant as an argument. This means that React Native will now try to read the contents of our app’s data folder - In the end, we used the
FlatList
module to render the value of thefiles
in a list view
Advanced usage
Creating folders
Directories are crucial for organizational purposes. For example, all images should go into the assets
folder, and the user data should stay in the appdata
directory.
To materialize a folder, RNFS includes a function called mkdir
. Here’s a brief example of this method in action:
const folderPath = RNFS.DocumentDirectoryPath + "/assets"; const makeDirectory = async (folderPath) => { await RNFS.mkdir(folderPath); //create a new folder on folderPath }; useEffect(() => { makeDirectory(folderPath); //execute this function on first mount getFileContent(RNFS.DocumentDirectoryPath); //this function was defined in the previous example }, []); return ( <SafeAreaView> {/*FlatList code to render file paths.*/} {/*renderItem function was defined earlier in this article*/} <FlatList data={files} renderItem={renderItem} keyExtractor={(item) => item.name} /> </SafeAreaView> );
In this piece of code, our makeDirectory
method accepts a parameter called folderPath
. When invoked, the app runs the mkdir
function, which then creates a new folder at the specified path.
Creating files
To write content to a file, RNFS includes a writeFile
method. This is critical for use cases where the app has to store sensitive user data on the user’s device:
const filePath = RNFS.DocumentDirectoryPath + "/joke.txt"; //absolute path of our file const fileContent = "Why do programmers wear glasses? \n They can't C#!"; const makeFile = async (filePath, content) => { try { //create a file at filePath. Write the content data to it await RNFS.writeFile(filePath, content, "utf8"); console.log("written to file"); } catch (error) { //if the function throws an error, log it out. console.log(error); } }; //extra code removed for brevity.. useEffect(() => { makeFile(filePath, fileContent); getFileContent(RNFS.DocumentDirectoryPath); }, []); return { /* Code to render FlatList with files Hook as our dataset...*/ };
In this snippet, we first coded a custom function called makeFile
, which takes in two parameters: filePath
and content
. Within this function, we are invoking the RNFS.writeFile
method, which tells React to create a file at filePath
and write the value of content
to this desired entity.
Reading files
RNFS’s readFile
function allows developers to procure data from a chosen file. This is important for note-taking apps, where the app has to read plain text files from the disk and display them to the user:
const filePath = RNFS.DocumentDirectoryPath + "/joke.txt"; const [fileData, setFileData] = useState(); const readFile = async (path) => { const response = await RNFS.readFile(path); setFileData(response); //set the value of response to the fileData Hook. }; useEffect(() => { readFile(filePath); }, []); return ( <SafeAreaView> {/* Display the value*/} <Text style={styles.name}>{fileData}</Text> </SafeAreaView> );
When invoked, the RNFS.readFile
function will attempt to get the contents of the file located in our chosen directory. If the attempt fails, the program will crash and throw an error.
File deletion
In order to remove a file, you can use the unlink
function like so:
const folderPath = RNFS.DocumentDirectoryPath + "/assets"; //path of folder to delete const filePath = RNFS.DocumentDirectoryPath + "/joke.txt"; //file to delete const [files, setFiles] = useState([]); const deleteFile = async (path) => { try { await RNFS.unlink(path); //delete the item present at 'path' console.log("file deleted"); } catch (error) { console.log(error); } }; useEffect(() => { //delete both the joke.txt file and the assets folder deleteFile(filePath); deleteFile(folderPath); //when the files and folders are deleted, get available files and folders: getFileContent(RNFS.DocumentDirectoryPath); }, []); return <SafeAreaView>{/*Code to render FlatList..*/}</SafeAreaView>;
In this block of code, we used the unlink
method to delete a file and a folder from the document directory.
Conclusion
Here is the source code for the article.
In this article, you learned how to create files and directories and write to them via the react-native-fs
library. Other than file modification, we can use this library for other situations, for example:
- Online storage apps: Cloud storage services like Google Drive and Tresorit upload the clients’ files located on their mobile devices
- Email: When it comes to sending attachments to a receiver, email clients allow the user to select and send files using a file manager
If you encountered any difficulty, I encourage you to play with and deconstruct the code so that you can fully understand its inner workings.
Thank you so much for making it to the end! Happy coding!
The post How to access file systems with React Native appeared first on LogRocket Blog.
from LogRocket Blog https://ift.tt/PXnivqh
via Read more