react-native-fs
react-native-fs copied to clipboard
RNFS.writeFile() -> ENOENT: open failed: EEXIST (File exists) - if file is deleted manually
On a real Android device, RNFS.writeFile()
fails saying ENOENT: open failed: EEXIST (File exists)
, while RNFS.exists()
returns false
. This occurs after the file was created by the app, and then deleted manually from the file system. This problem does NOT occur on an Android emulator.
Scenario to reproduce: ON A REAL DEVICE:
- Use RNFS.writeFile() to create a file
- Using a file access software, e.g. Google Files, delete the created file (above).
- Try to re-create the file again using RNFS.writeFile()
- You get an error
ENOENT: open failed: EEXIST (File exists)
, while it has been deleted, and the result ofRNFS.exists()
confirms that it is not there?!
Device Infomation:
Samsung Galaxy S10+
Android Version: 11
One UI Version: 3.1
Google Play system update: 1 August 2021
Kernel version: 4.14.113.22340597
#1 Wed Dec 1 11:14:06 KST 2021
Code:
try {
const fileExists = await RNFS.exists(fullPath);
console.log("fileExists:", fileExists, "fullPath:", fullPath, ); // fileExists: false - fullPath: /storage/emulated/0/Download/myFileName.csv
if (fileExists) {
// Execution never reaches this point
console.log("inside if statement", );
await RNFS.unlink(fullPath);
console.log("file deleted");
}
// The following statement triggers the catch (below)
await RNFS.writeFile(fullPath, fileContents, "utf8");
// execution never reaches this point
console.log("file Written");
}
catch (err) {
console.error("err:", err ); // err: [Error: ENOENT: open failed: EEXIST (File exists), open '/storage/emulated/0/Download/myFileName.csv']
}
Versions:
"react-native": "0.66.4",
"react-native-fs": "^2.18.0",
I'm seeing this issue as well. Not only with RNFS writes in my case, it is also seen with file writes from the backend so may not be fixable in react-native-fs. It does appear to happen when files have been manually deleted.
If I change the file name to a previously unused one, it works normally, so it definitely is related to a deleted file.
I have tried deleting the whole folder containing the files, and also subsequently emptying the recycle bin, but the errors still occur unless I change to a new filename. My versions are the same as above:
"react-native": "0.66.4",
"react-native-fs": "^2.18.0",
it happens with appendFile
as well...
Any updates?
Fixed by this way:
- add to the AndroidManifest.xml
<application android:requestLegacyExternalStorage="true"`
- request permission:
const requestWritePermission = async () => {
try {
const granted = await PermissionsAndroid.request(
PermissionsAndroid.PERMISSIONS.WRITE_EXTERNAL_STORAGE,
);
if (granted === PermissionsAndroid.RESULTS.GRANTED) {
console.log('You can use the write');
return true;
} else {
console.log('write denied');
return false;
}
} catch (err) {
Alert.alert(err.message);
return false;
}
};
Instead of deleting the previous file and creating a new one, create a new named file each time. like adding random numbers at the end of the file name. You can do that with using libraries such as nanoid.
const uri = RNFS.ExternalStorageDirectoryPath + `/filename-${nanoid()}.txt`;
Of course, this can turn the user storage space into a garbage, depending on how often you use it.
Having the same issue with RNFS.copyFile()
. Here is some extra information that may help someone:
Device Infomation:
Samsung Galaxy A50
Android Version: 11
One UI Version: 3.1
Google Play system update: October 1, 2022
Kernel version: 4.14.113-113-21578199
#1 Fri Sep 16 15:21:34 KST 2022
Code
try {
RNFS.copyFile(src, dest); // Where dest is a file that has been deleted manually via My Files app.
} catch (error)
console.error(error.message); // ENOENT: open failed: EEXIST (File exists), open `/storage/emulated/... (dest location)`.
}
Versions
"react-native": "0.64.4",
"react-native-fs": "2.20.0",
I believe that android caches the filenames even after you delete them. I have Android File Manager and when I delete a file through there and close the app I am able to save the file with the same name successfully. If I delete the file from the file manager on the device and try to resave with the same name then it throws the "already exists" error.
I came across this using cordova-plugin-file-transfer
- and the same behavior. The file downloaded fine, then I manually deleted from phone using File Manager
app. After that I couldn't download the file again. My app has all the permissions and has <application android:requestLegacyExternalStorage="true">
Drove me nuts trying to understand the issue until I found this thread.
What I don't understand is why Android cares if the file already exists...why not just over write it? Seems a bug that if a user deletes a file and Android caches the name to never be used again. Makes no sense.
@NathanNovak - whats the difference between Android File Manager
and some other device app File Manager
? Seems if we can figure out what the Android
one is doing we could replicate that in our code. Like, how do we delete the file name from (what appears to be) Android's cached list?
Another thing to note. After the user manually deletes the file, my app reading the device directory path shows the file does not exist. But when trying to write the file with the same name again, it shows it as existing
Just hit the manually deleted file issue. In my case it seems that if i have "Trash folder" enabled, after clearing it the file is writable again. You could also turn off using a trash folder altogether (maybe not available depending on the Android OS variant You use). This without adding any permission requests, nor legacy flags.
Is there any solution? I have the same problem. If I delete the file manually, this error appears.
the file still exists in recycle bin which causes the error. Delete the file from there and try downloading it again it should work fine.
the file still exists in recycle bin which causes the error. Delete the file from there and try downloading it again it should work fine.
As noted above (Feb 18 2022), deleting from the recycling bin does not clear this. The system still retains 'memory' of the file somewhere
the file still exists in recycle bin which causes the error. Delete the file from there and try downloading it again it should work fine.
As noted above (Feb 18 2022), deleting from the recycling bin does not clear this. The system still retains 'memory' of the file somewhere
Idk, I was getting this last week tried deleting the file from recycle bin and it worked. I did test this again and again and every time after deleting the file from recycle bin it allowed me to download with the same name. my project contains following versions. "react-native": "0.73.1", "react-native-fs": "^2.20.0", // this is same i see Samsung A33
maybe this issue varies from device to device.