2016-07-13 59 views
7

Ho un problema con le autorizzazioni su Android 6.0 e versioni successive.Permessi Android 6.0 e montaggio OBB

Il gioco su cui sto lavorando utilizzava il permesso WRITE_EXTERNAL_STORAGE. Su Android 6.0 e versioni successive l'avviso che chiede all'utente di consentire che venga visualizzato.

Ho ricevuto una richiesta per sbarazzarsi di questo avviso, il che significa che il gioco non può più utilizzare WRITE_EXTERNAL_STORAGE.

Tecnicamente il gioco non sta scrivendo e sta leggendo la memoria esterna da nessuna parte in questo momento. Tutti i file salvati e memorizzati nella cache sono memorizzati nella directory specifica dell'applicazione (/storage/emulated/0/Android/data/com.company.productname) Ma il gioco deve leggere (e talvolta scaricare) il file OBB, che è memorizzato nella directory /storage/emulated/0/Android/obb/com.company.productname.

Il gioco ha un accesso a questa directory, anche senza WRITE_EXTERNAL_STORAGE o READ_EXTERNAL_STORAGE su dispositivi:

  • Motorola Nexus 6
  • LG Nexus 5

ma sembra che non ha na accesso a questa directory su:

  • Samsung Galaxy S5, S6 e S7
  • Nvidia Shield tablet

Ho controllato anche utilizzando i test Alpha in modo da simulare il download del gioco dal negozio.

Quando viene concessa l'autorizzazione all'archiviazione (tramite Impostazioni app), tutto funziona correttamente.

Come viene montato l'OBB?

L'Unreal Engine 4, che io uso, utilizza la funzione C open() per gestire il file OBB:

int32 Handle = open(LocalPath, O_RDONLY); 

Dove LocalPath è un percorso completo del file OBB:/stoccaggio/emulato/0/Android/OBB/com.company.productname/main.10003.com.company.productname.obb

le domande sono:

  1. il gioco ha bisogno di un/WRITE _EXTERNAL_STOR LEGGI ETÀ per leggere e scaricare il file OBB?
  2. Se sì, allora come posso eliminare l'avviso che chiede all'utente le autorizzazioni.
  3. Se no, allora perché la serie Samsung Galaxy S è così problematica?
+0

'ricevuto una richiesta per sbarazzarsi di questo avviso'. Richiesta sciocca. Diglielo! Lasciali andare su Impostazioni della tua app su cui autorizzare l'autorizzazione. – greenapps

+0

Come stai montando su OBB e cosa stai passando a UE4 come 'LocalPath'? –

+0

Inoltre, quale versione (s) di Android sono in esecuzione su questi dispositivi diversi? –

risposta

8

Ok, sembra che il problema è stato elencato da qualche altra parte, ma non ho potuto trovare, perché non sapevo che fosse il problema esatto ...

https://code.google.com/p/android/issues/detail?id=197287

L'API23 per qualche ragione di set l'utente dell'OBB per il root, non l'utente corretto e per questo l'app non ha accesso ad esso.

Dopo aver riavviato il dispositivo, tutto funziona correttamente.

A questo punto non esiste una soluzione chiara per questo.

Grazie @Larry per fornire tutte le informazioni necessarie e disponibile :)

+0

Sembra che non ci sia ancora soluzione alternativa fino ad oggi? – derFunk

0

Fornire una risposta in base alla discussione del commento sopra. Il problema è il modo in cui viene fornito LocalPath. In Android, i percorsi del filesystem non sono coerenti tra produttori diversi e non dovresti fare ipotesi sui percorsi di archiviazione.

Quindi, piuttosto che avere questa (solo codice di esempio):

public class MyActivity extends Activity { 
    static final String LocalPath = "/storage/emulated/0/Android/obb/com.company.productname/main.10003.com.company.p‌​roductname.obb "; 
    ... 
} 

Hai bisogno di fare qualcosa di simile:

public class MyActivity extends Activity { 
    File mObb; 
    ... 

    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(); 
     ... 

     mObb = new File(getObbDir(), getPackageName() + ".obb"); 

     // Get the path for passing to UE4 later 
     String LocalPath = mObb.getAbsolutePath(); 
    } 

Questo farà in modo che il codice ottiene la posizione corretta OBB per la vostra app sull'archiviazione esterna primaria per il dispositivo specificato. È quindi possibile salvare l'OBB lì e in seguito quando l'app avvia UE4 può puntare direttamente al file.

La posizione di un'app su una memoria esterna primaria per OBB (e altri file) non richiede autorizzazioni per leggere e scrivere per quell'app. Se il percorso sull'archiviazione esterna non è uno generato dai metodi precedenti, è necessaria l'autorizzazione WRITE_EXTERNAL_STORAGE per scrivere i dati.

+0

Grazie per un suggerimento, ma ancora ... Ho preso l'indirizzo usando getObbDir() e getAbsolutePath() e restituito ... /storage/emulated/0/Android/obb/com.company .productname;) Ho anche controllato l'errno dal metodo aperto ed è 'EACCES 13/* Autorizzazione negata * /' C'è anche una cosa ... Installa il gioco inserendo apk e obb nella directory creata in Android/OBB e installare APK. Quando inserisco Obb nella directory di archiviazione e poi lo copio tramite Android File Manager nella directory corretta e poi installo ... quindi funziona e ha accesso ... – zompi

+0

Il motore UE4 è in esecuzione nel processo della tua app o è un componente/pacchetto separato? –

+0

OK, sembra molto strano cosa stai facendo per installare l'app e il file obb. L'installazione dell'app deve essere eseguita tramite 'adb' o il Play Store, quindi non è necessaria alcuna posizione di archiviazione speciale. In genere i tuoi file obb vengono scaricati dall'app e inseriti nella directory obb * o * puoi ospitarli su Google Play e trascinarli in quel modo. Il framework deve essere la cosa che crea la directory obb, quindi l'APK deve essere installato prima in modo che le autorizzazioni ottengano l'installazione corretta. Se stai creando manualmente la directory (adb shell?) Provando ad usarla, ciò causerà problemi. –

1

Grazie a @Larry per punta a soluzione giusta.

Per coloro, che sta chiedendo, perché AOSP APK di espansione Supporto libray non funziona senza permesso, qui è la modifica APKExpansionSupport.java

package com.android.vending.expansion.zipfile; 
/* 
* Copyright (C) 2012 The Android Open Source Project 
* 
* Licensed under the Apache License, Version 2.0 (the "License"); 
* you may not use this file except in compliance with the License. 
* You may obtain a copy of the License at 
* 
*  http://www.apache.org/licenses/LICENSE-2.0 
* 
* Unless required by applicable law or agreed to in writing, software 
* distributed under the License is distributed on an "AS IS" BASIS, 
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
* See the License for the specific language governing permissions and 
* limitations under the License. 
*/ 
import java.io.File; 
import java.io.IOException; 
import java.util.Vector; 

import android.content.Context; 

public class APKExpansionSupport { 
    public static String[] getAPKExpansionFiles(Context ctx, int mainVersion, int patchVersion) { 
     String packageName = ctx.getPackageName(); 
     Vector<String> ret = new Vector<>(2); 
     File expPath = ctx.getObbDir(); 
     // Check that expansion file path exists 
     if (expPath.exists()) { 
      if (mainVersion > 0) { 
       String strMainPath = expPath + File.separator + "main." + mainVersion + "." + packageName + ".obb"; 
       File main = new File(strMainPath); 
       if (main.isFile()) { 
        ret.add(strMainPath); 
       } 
      } 
      if (patchVersion > 0) { 
       String strPatchPath = expPath + File.separator + "patch." + mainVersion + "." + packageName + ".obb"; 
       File main = new File(strPatchPath); 
       if (main.isFile()) { 
        ret.add(strPatchPath); 
       } 
      } 
     } 
     String[] retArray = new String[ret.size()]; 
     ret.toArray(retArray); 
     return retArray; 
    } 

    public static ZipResourceFile getResourceZipFile(String[] expansionFiles) throws IOException { 
     ZipResourceFile apkExpansionFile = null; 
     for (String expansionFilePath : expansionFiles) { 
      if (null == apkExpansionFile) { 
       apkExpansionFile = new ZipResourceFile(expansionFilePath); 
      } else { 
       apkExpansionFile.addPatchFile(expansionFilePath); 
      } 
     } 
     return apkExpansionFile; 
    } 

    public static ZipResourceFile getAPKExpansionZipFile(Context ctx, int mainVersion, int patchVersion) throws IOException{ 
     String[] expansionFiles = getAPKExpansionFiles(ctx, mainVersion, patchVersion); 
     return getResourceZipFile(expansionFiles); 
    } 
} 
2

Siete invitati di verificare se l'applicazione dal negozio è scrittura permesso.