2 years ago
#58629
ChristianF
Listening for a camera capture using FileObserver: how to deal with temporary .pending files and get photo into byte array
I'm writing an Android Service to detect when an image is captured using the camera. Once it's captured I need to get the image contents into a byte array.
Here are the important parts of the onStartCommand
method of the Service:
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
String imgsPath = Environment.getExternalStorageDirectory().getAbsolutePath() + "/DCIM/Camera";
// fileObserver is an instance variable so that it doesn't get garbage collected after onStartCommand runs
this.fileObserver = new FileObserver(imgsPath, FileObserver.ALL_EVENTS) {
@Override
public void onEvent(int event, @Nullable String path) {
if (event != FileObserver.CREATE)
return;
byte[] bytes = new byte[0];
String filePath = imgsPath + "/" + path;
try {
bytes = org.apache.commons.io.FileUtils.readFileToByteArray(new File(filePath));
} catch (IOException e) {
e.printStackTrace();
}
// ... additional unimportant things for this question.
}
};
this.fileObserver.startWatching();
return START_STICKY; // If service gets killed, after returning from here then restart
}
onEvent
runs whenever I capture an image with the camera. However, when I attempt to read the file into a byte array (the LOC in the try
does this), I receive the following exception/stack trace:
W/System.err: java.io.IOException: File '/storage/emulated/0/DCIM/Camera/.pending-1642979007-20220116_150327.jpg' cannot be read
W/System.err: at org.apache.commons.io.FileUtils.openInputStream(FileUtils.java:294)
W/System.err: at org.apache.commons.io.FileUtils.readFileToByteArray(FileUtils.java:1851)
My hunch is that as the file is being written to the system (all the bytes aren't saved to the disk yet) that the .pending-1642979007-20220116_150327.jpg
file is used, and then renamed to 20220116_150327.jpg
. Is this the typical, or guaranteed behaviour of the Android OS? Stepping through the debugger I don't see another CREATE
event for the 20220116_150327.jpg
file.
If I want to only deal with the file once it's in a non-pending file state (everything has been written to disk) how should I do this? Is detecting the renaming of the .pending
file how it should be done?
java
android
android-11
file-watcher
0 Answers
Your Answer