java.io.FileNotFoundException (Permission denied) When trying to write to the Android sdcard

懵懂的女人 提交于 2019-12-04 22:46:26

This is how your manifest file should look like

<application android:icon="@drawable/icon" android:label="@string/app_name">
    <activity android:name=".WriteCBTextToFileActivity"
              android:label="@string/app_name">
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />
            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>
</application>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

I had this issue and the answers here didn't fix it, because I had made a pretty silly mistake.

Make sure you give your Android emulator an SD card...I had left the size of the SD card blank and so of course it couldn't find anything. On top of that, I was specifying a directory inside said SD card which had not yet been created so be sure to consider that case as well.

(You can change an AVD's SD card settings by going to the Android Virtual Device Manager, editing your emulator of choice, and entering some value for the SD card size)

You must also make sure that the External Storage subsystem is in the correct state; use Environment.getExternalStorageState() and look for Environment.MEDIA_MOUNTED that is the only safe state.

It's also a good idea to narrow exception handling to IOException around those sections, so you don't over-recover from IO-specific issues, e.g. media unmounted.

If you need events, there are broadcast intents (Intent.ACTION_MEDIA_xxx) with the same information you can register for with IntentListener.

Also note that external storage may be disabled when you are using USB for debugging!

There is also an extended period during device startup, where External Storage is not available. If you do stuff in services on startup, this is an issue.

In general, your application must be aware of the External Storage state when accessing it, and handle cases where it is unavailable, or becomes unavailable while accessing it.

If you have the correct permissions set in the manifest, make sure your device is not in "Disk Drive" mode when connect to a PC. Change it to "Charge only" mode and it should work.

Nitay

Notice that in addition to Saurabh answer, since API 23 you need to request permissions at run-time.

See here: https://developer.android.com/training/permissions/requesting.html

And Justin Fiedler's answer here: https://stackoverflow.com/a/33288986/328059

Also, I've had several cases when after changing permission and re-running the app using Instant Run the permissions were not updated. So, as a best practice, after changing the manifest I uninstall the app from the target device, and rebuild.

Dinh Nguu Nguyen

You can try with:

String myPath=Environment.getExternalStorageDirectory()+"/Image"+ imageGroup + "_" + imageNumber + ".png";

File myFile = new File();      
input = new FileInputStream(myFile);

Try to use openFileOutput("filename") to return a FileOutputStream instead of specifying the location by yourself.

Check the doc here

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!