java.io.filenotfoundexception open failed eacces (

2020-02-03 06:44发布

问题:

The following code which consists of downloading a file from a server and save it in the storage works fine when the device has an internal storage.
But when I tried it with a device with no internal storage, only with external storage I get the following exception.

java.io.filenotfoundexception open failed eacces (permission denied)

public void downloadFile(String dlUrl, String dlName) {
    int count;

    HttpURLConnection con = null;
    InputStream is = null;
    FileOutputStream fos = null;

    try {
        URL url = new URL( dlUrl );
        con = (HttpURLConnection) url.openConnection();
        con.setDoInput(true);
        con.connect();

        is = url.openStream();
        String dir = Environment.getExternalStorageDirectory() + Util.DL_DIRECTORY;
        File file = new File( dir );
        if( !file.exists() ){
            file.mkdir();
        }

        Util.LOG_W(TAG, "Downloading: " + dlName + " ...");

        fos = new FileOutputStream(file + "/" +  dlName);
        byte data[] = new byte[1024];

        while( (count = is.read(data)) != -1 ){
            fos.write(data, 0, count);
        }

        Util.LOG_D(TAG, dlName + " Download Complete!");


    } catch (Exception e) {
        Util.LOG_E(TAG, "DOWNLOAD ERROR = " + e.toString() );
        bServiceDownloading = false;
    }
    finally{
        try {
            if( is != null)
                is.close();
            if( fos != null)
                fos.close();
            if( con != null)
                con.disconnect();
        } catch (Exception e) {
            Util.LOG_E(TAG, "CLOSE ERROR = " + e.toString() );
        }
    }
}

And in manifest file I has the following:

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>

Any suggestions what maybe the cause? By the way Environment.getExternalStorageDirectory() returns /mnt/sdcard/ and file.mkdir() return false.

回答1:

This problem seems to be caused by several factors.

Check#1
First add this permission in your manifest file and check if it is working:

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<application>
    ...

</application>

  .....

Check#2:

If you are running on an emulator, check the properties to see if it has an SD card.

Check#3:

Disable file transfer from device to computer. If Enabled, the app wont be able to access the SD card.

Check#4:
If still not working, try the following:

 String dir = Environment.getExternalStorageDirectory().getAbsolutePath()

For me the following worked:
The problem is that getExternalStorageDirectory returns /mnt/sdcard whereas I need the actual path of external storage which is /mnt/sdcard-ext and there is no API in android that can get me the absolute path of removable sdcard.
My solution was to hard code the directory as follows:

String dir = "/mnt/sdcard-ext" ;

Since the application is intended to work only on one device, the above did the job.
If you encounter the same problem, use an file explorer application to find out the name of the external directory and hard code it.



回答2:

Use READ_EXTERNAL_STORAGE permission to read data from the device.



回答3:

Did you try it on emulator? Check the properties if it has an SD card. I had the same problem, and it was because the emulator did not have an SD card. Check if yours has or not.



回答4:

I had the same problem, and i solved it by disabling file transfer from device to computer. Because if u enable file transfer, sd card is not accessible to debugging application.



回答5:

try
Environment.getExternalStorageDirectory().getAbsolutePath()

and don't forget to add

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />


回答6:

This attribute is "false" by default on apps targeting Android 10 or higher.

<application android:requestLegacyExternalStorage="true" ... > ... </application>



回答7:

I suspect you are running Android 6.0 Marshmallow (API 23) or later. If this is the case, you must implement runtime permissions before you try to read/write external storage. https://developer.android.com/training/permissions/requesting.html



回答8:

Try using mkdirs instead of mkdir. If you are creating a directory path and parent doesn't exist then you should use mkdirs.



回答9:

I had the same problem. I used the write and read permission in the manifest correctly , yet it didn't work! The solution was very silly: unplug your phone from the PC before running the application. It seems when your phone is connected as "Mass storage" to the PC, the application cannot access the external storage.



回答10:

i have done very silly mistake. I have already put in AndroidManifest.xml

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

and also add permission in java file,as get permission pragmatically. But there is mistake of Manifest.permission.READ_EXTERNAL_STORAGE. Please use Manifest.permission.WRITE_EXTERNAL_STORAGE.

ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, requestCode);


回答11:

It is possible that the device requires that you manually give the permissions to the cell phone, check your equipment and check that the write permission is activated on your device.