2016-07-01 13 views
0

Я изо всех сил пытаюсь выяснить, что происходит с моим кодом. Этот фрагмент кода работает на КАЖДЫЙ (видимо) телефона, кроме Моторола (Moto G, и т.д. ...):Невозможно создать папки на определенных устройствах

private void createFolder(String folderPath) throws CantCreateFolderPathException { 
    File folder = new File(folderPath); 
    if (folder.mkdirs() || folder.isDirectory()) 
     return; //Everything ok! 

    throw new CantCreateFolderPathException(folderPath); 
} 

И я генерировать путь к папке с этим:

public String getFolderPath(Courseware courseware) { 
    String path = getBestPath() + courseware.getSubject().getName() + File.separator; 
    UnisantaApplication.Log_i("SAVE PATH:" + path); 
    return path; 
    //Result example: sd/unisantaapp/material/SUBJECT NAME/ 
} 

private String getBestPath() { 
    if (isExternalStorageWritable()) 
     return getExternalPath(); 
    return getInternalPath(); 
} 

private String getExternalPath() { 
    return Environment.getExternalStorageDirectory() 
      .getAbsolutePath() + File.separator + 
      "unisantaapp" + File.separator + 
      "material" + File.separator; 
} 

private String getInternalPath() { 
    return UnisantaApplication.getInstance().getApplicationContext() 
      .getFilesDir().getAbsolutePath() + File.separator + 
      "material" + File.separator; 
} 

folder.mkdirs держит возвращает false, что вызывает выброс CantCreateFolderPathException. СНОВА, он работает на всех других телефонах, которые я проверил, так что, вероятно, это не разрешение манифеста отсутствует:

<manifest xmlns:android="http://schemas.android.com/apk/res/android" 
package="si.unisanta.tcc.unisantaapp" > 

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

<application 
     [...] 

Я попросил помощи у моего друга, так как я не» У меня есть мотор. Я создал APK с некоторыми диалогами, чтобы помочь мне понять ошибку, мои шаги были:

  1. Узнайте, какой путь является «лучшим вариантом» генерируется из моего кода: getBestPath возвращает ExternalStorageDirectory, но mkdirs постоянно возвращается ложные

  2. Пробовал менять getBestPath к всегда возвращает внутренний путь, то mkdirs вернулся истинный! На этом пути:

    Internal path returned (Примечание: Caminho: означает Path:)

    Но мой друг утверждает, что он не может открыть файл и не найти его с другой третьей стороной файлового проводника. Когда он пытается открыть PDF, он говорит: «Невозможно просматривать PDF» и файл исследователь говорит: «суперпользователя не доступен».

  3. Разочарованный без подсказки о том, что происходит, я сделал шаг назад ВОЗВРАТ мой метод getBestPath работать, как ожидалось, и изменил призыв folder.mkdirs() к Files.createParentDirs(folder) надеясь на более описательное ошибки, но вместо этого я только что получил простой :

    createParentDirs result

Ну, почему я не могу создать папку/файл и откройте это JUST IN MOTOROLA PHONES? Кто-нибудь здесь уже столкнулся с этим? Какие-нибудь подсказки о том, что я делаю неправильно?

+1

«Но мой друг утверждает, что он не может открыть файл и не найти его с другой третьей стороной файлового проводника» - то есть, как [внутренняя хранилище] (https://commonsware.com/blog/2014/04/07/storage-situation-internal-storage.html). «Когда он пытается открыть PDF-файл, он говорит:« Невозможно просмотреть PDF »- сторонние приложения не имеют прямого доступа к файловой системе для внутреннего хранилища вашего приложения. «Какие-нибудь подсказки о том, что я делаю неправильно?» - вы вставляете изображения диалогов, а не трассировки стека Java для тех исключений, с которыми вы сталкиваетесь. – CommonsWare

+1

Кроме того, возможно, ваше отказоустойчивое устройство является единственным устройством Android 6.0, которое вы тестируете, и в этом случае вам необходимо просмотреть разрешения во время выполнения: https://stackoverflow.com/questions/32635704/android-permission-doesnt-work- even-if-i-have-announce-it – CommonsWare

+0

@CommonsWare, я не могу заставить его телефон отлаживать локально, извините за это:/Поэтому 'mkdirs' не генерирует исключение, он просто возвращает false. – Latrova

ответ

0

Как @CommonsWare указал, это не проблема MOTOROLA, а Android 6.0. Я просто добавил поддержку для запроса разрешений (runtime), а также прочитал предложенный article (замечательная статья, действительно стоит того).

Я просто добавил следующее в своей деятельности:

private boolean hasPermissionToDownload() { 
    int permissionResult = ContextCompat.checkSelfPermission(this, 
      Manifest.permission.WRITE_EXTERNAL_STORAGE); 
    return permissionResult == PackageManager.PERMISSION_GRANTED; 
} 

private void explainOrAskPermission() { 
    if (ActivityCompat.shouldShowRequestPermissionRationale(this, Manifest.permission.WRITE_EXTERNAL_STORAGE)) { 
     new AlertDialog.Builder(this) 
      .setTitle(R.string.download_permission_explain_title) 
      .setMessage(getString(R.string.download_permission_explain_message)) 
      .setNeutralButton(R.string.ok, new DialogInterface.OnClickListener() { 
       @Override 
       public void onClick(DialogInterface dialogInterface, int i) { 
        askPermission(); 
       } 
      }) 
      .show(); 
    } 
    else { 
     askPermission(); 
    } 
} 

private void askPermission() { 
    ActivityCompat.requestPermissions(this, 
      new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, 
      PERMISSION_SAVE_DOWNLOAD_REQUEST); 
} 

@Override 
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) { 
    if (requestCode == PERMISSION_SAVE_DOWNLOAD_REQUEST) { 
     if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) { 
      downloadCourseware(lastCoursewareClicked); 
     } 
     else { 
      new AlertDialog.Builder(this) 
       .setTitle(R.string.download_permission_denied_title) 
       .setMessage(R.string.download_permission_denied_message) 
       .setNeutralButton(R.string.ok, null) 
       .show(); 
     } 
    } 
}