如何在Android平台> = 23中检查并请求SD卡的读写权限 [英] How to check and request read, write permission for sd card in platform >= 23 of Android

查看:83
本文介绍了如何在Android平台> = 23中检查并请求SD卡的读写权限的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有以下代码来请求对称为模拟的外部(共享)存储的读写权限.现在我也想读写SD卡.但是我在日志中收到错误权限被拒绝".

I have the following code to request read,write permission for external(shared) storage known as emulated. Now I also want to read and write to SD Card. But i am getting the error "permission denied" in logs.

//We are calling this method to check the read permission status
public boolean isReadWriteStorageAllowed() {
    //Getting the permission status
    int resultRead   = ContextCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE);
    int resultWrite  = ContextCompat.checkSelfPermission(this, Manifest.permission.WRITE_EXTERNAL_STORAGE);

    //If permission is granted returning true
    if (resultRead == PackageManager.PERMISSION_GRANTED && resultWrite == PackageManager.PERMISSION_GRANTED)
        return true;

    //If permission is not granted returning false
    return false;
}

public void requestStoragePermission(int code){

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

该错误的日志如下

The logs for the error are as below

    10-12 14:23:03.998 8550-8550/com.free W/System.err: java.io.FileNotFoundException: /storage/8E14-3919/database.db (Permission denied)
10-12 14:23:03.998 8550-8550/com.free W/System.err:     at java.io.FileOutputStream.open(Native Method)
10-12 14:23:03.998 8550-8550/com.free W/System.err:     at java.io.FileOutputStream.<init>(FileOutputStream.java:221)
10-12 14:23:03.998 8550-8550/com. free W/System.err:     at java.io.FileOutputStream.<init>(FileOutputStream.java:108)
10-12 14:23:03.998 8550-8550/com.free W/System.err:     at com. DatabaseManage.exportDatabase(DatabaseManage.java:140)
10-12 14:23:03.998 8550-8550/com.free W/System.err:     at com. DatabaseManage.access$000(DatabaseManage.java:50)
10-12 14:23:03.998 8550-8550/com.free W/System.err:     at com. DatabaseManage$1.onClick(DatabaseManage.java:106)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at com.android.internal.app.AlertController$AlertParams$3.onItemClick(AlertController.java:1244)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at android.widget.AdapterView.performItemClick(AdapterView.java:339)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at android.widget.AbsListView.performItemClick(AbsListView.java:1695)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at android.widget.AbsListView$PerformClick.run(AbsListView.java:4171)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at android.widget.AbsListView$13.run(AbsListView.java:6772)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at android.os.Handler.handleCallback(Handler.java:751)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at android.os.Handler.dispatchMessage(Handler.java:95)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at android.os.Looper.loop(Looper.java:154)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at android.app.ActivityThread.main(ActivityThread.java:6692)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at java.lang.reflect.Method.invoke(Native Method)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1468)
10-12 14:23:03.999 8550-8550/com.free W/System.err:     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1358)

我的问题是如果询问外部存储的存储权限"还会授予"sd卡"的权限吗?如果不是,那么我的代码有什么问题或我缺少什么?我需要解决方案!

My question is 'if asking the storage permissions for external storage' will also grant the permissions for 'sd card'? If not then whats wrong in my code or what am i missing? I need a solution!

代码如下

public void exportDB(){
    int size, pathSize = 0;
    String[] storageLocations = null;

    final File dbFile = context.getDatabasePath(DATABASE_NAME);//existing database file path

    File device = Environment.getExternalStorageDirectory();//device storage
    String[] sdCard = getExternalStorageDirectories();//sd cards

    size = sdCard.length;

    if(size == 0)
        pathSize = 0;
    else if(size > 0)
        pathSize = size + 1;

    pathForExports   = new String[pathSize];
    storageLocations = new String[pathSize];

    if(sdCard.length == 0){
        pathForExports[0]   = device.getAbsolutePath() + "/" + DATABASE_NAME;
        storageLocations[0] = "1) Device Storage";
    }
    else if(sdCard.length > 0) {
        pathForExports[0] = device.getAbsolutePath() + "/" + DATABASE_NAME;
        storageLocations[0] = "1) Device Storage";

        for (int i=0;i<sdCard.length; i++) {
            File file = new File(sdCard[i]);
            pathForExports[i+1] = file.getAbsolutePath() + "/" + DATABASE_NAME;
            if(sdCard.length > 1) {
                storageLocations[i+1] = (i+2) + ") Sd Card - " + (i+1);
            }
            else
                storageLocations[i+1] = (i+2) + ") Sd Card";
        }
    }
    //File file = new File(Environment.getExternalStorageDirectory() + File.separator + SAMPLE_DB_NAME);

    AlertDialog.Builder builder = new AlertDialog.Builder(context);
    builder.setTitle("Choose Export Location");
    builder.setItems(pathForExports, new DialogInterface.OnClickListener() {
        @Override
        public void onClick(DialogInterface dialog, int which) {
            exportDatabase(dbFile, which);
        }
    });
    AlertDialog alertDialog = builder.create();
    alertDialog.show();
}

private void exportDatabase(File dbFile, int whichButton) {

    FileChannel source = null;
    FileChannel destination = null;

    try {
        source = new FileInputStream(dbFile).getChannel();
        destination = new FileOutputStream(pathForExports[whichButton]).getChannel();
        destination.transferFrom(source, 0, source.size());
        source.close();
        destination.close();

        if(whichButton == 0)
            alert("Database is exported to device storage");
        else
            alert("Database is exported to sd Card");
    } catch(IOException e) {
        e.printStackTrace();
        if(whichButton == 0)
            alert("Failed to export database to device storage");
        else
            alert("Failed to export database to sd card");
    }
}

推荐答案

    /storage/8E14-3919/database.db .

即使您具有外部存储的所有权限,也仍然无法在该位置的micro SD卡上进行写操作.

Even if you have all the permissions for external storage then still you will not be able to write on the micro SD card on that place.

您只能在卡上的应用程序特定目录中写入.

You can only write in the app specific directory on the card.

要找到该路径,请使用getExternalFilesDirs().如果幸运的话,这是返回的条目之一.

To find that path use getExternalFilesDirs(). If you are lucky it is one of the entries returned.

对您来说,路径看起来像

For you the path would look like

 /storage/8E14-3919/Android/data/<packagename>/files

使用文件浏览器应用程序进行查看.它可能已经在那里.

Have a look with a file explorer app. It is probably already there.

如果要在卡上的任何地方写,请使用存储访问框架.

If you want to write everywhere on the card use the storage access framework.

这篇关于如何在Android平台&gt; = 23中检查并请求SD卡的读写权限的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆