2014-12-25 10 views
8

Desidero sapere se l'utente ha lanciato la nostra applicazione basata su Java da un file system di sola lettura come da un dmg, quindi funzioni come auto- l'aggiornamento sarà in grado di mostrare informazioni significative invece di abortire con un errore. Prima pensavo che controllare il percorso di .app sarebbe stato sufficiente (quando lanciato da un file .dmg è qualcosa come /Volumes/MyApp 1.2.3/MyApp.app, ma questo non funzionerà, perché l'utente potrebbe aver installato l'applicazione su una partizione diversa. ?Rilevare se un'applicazione è stata avviata da un file system di sola lettura su OS X

+0

Che cosa è esattamente la tua definizione di sola lettura? Cosa succede se il filesystem è scrivibile, ma l'utente non ha le autorizzazioni per modificare il pacchetto dell'app? Questo si qualificherebbe? – NPE

+0

No, perché l'applicazione può richiedere le autorizzazioni. –

risposta

1

È anche possibile controllare direttamente da Java se un certo percorso punti a qualcosa all'interno di una directory di sola lettura interrogando il FileStore associato al tuo percorso:

File classpathRoot = new File(MyClass.class.getClassLoader().getResource("").getPath()); 
/* getPath() actually returns a String instead of a Path object, 
    * so we need to take this little detour */ 
Path yourAppPath = classpathRoot.toPath(); 
boolean isReadOnly = Files.getFileStore(yourAppPath).isReadOnly(); 
3

Se OSX è conforme a POSIX, per determinare se il filesystem è montato R/o, è possibile utilizzare statvfs() o fstatvfs(), tornato struct statvfs campo f_flag dovrebbe avere ST_RDONLY bit impostato per R/o del file system.

Come era indicato nei commenti, controllare se questa informazione è correttamente fornita dal sistema operativo

JNA e this possono essere utili per Java.

Un paio di idee, che possono essere utile here (access(), open(), utime()).

È possibile utilizzare anche lo specifico OS X statfs(), ma questa funzione non è portabile (Linux e * BSD hanno funzioni statfs() leggermente diverse).

+0

In realtà, essendo conforme a POSIX ** non ** significa che si può usare 'statvfs()' per sapere se un file system è di sola lettura. La [man page] (https://developer.apple.com/library/mac/documentation/Darwin/Reference/ManPages/man3/statvfs.3.html) dice che POSIX in realtà non richiede che queste funzioni facciano * qualsiasi cosa * e che non dovrebbero essere utilizzati da app portatili. Dato che la domanda era specifica per OS X, si potrebbe usarli in questo caso, ma la tua implicazione sul fatto che si possa usarli su qualsiasi sistema operativo conforme a POSIX non è corretta. –

+0

@KenThomases, http://pubs.opengroup.org/onlinepubs/9699919799/functions/statvfs.html dice "Problema 7" queste funzioni vengono spostate in ** Base ** da ** XSI **, quindi come capire che non sono più opzionali per il sistema conformat POSIX. – kestasx

+0

Dal tuo link "Non è specificato se tutti i membri della struttura statvfs abbiano valori significativi su tutti i file system". Le funzioni fanno parte dello standard Base, ma non sono obbligate a ** fare nulla **. –

5

È possibile utilizzare -[NSURL getResourceValue:forKey:error:] con la chiave NSURLVolumeIsReadOnlyKey. Lo applicheresti all'URL del pacchetto dell'app restituito da [[NSBundle mainBundle] bundleURL]. Quindi:

NSBundle* bundle = [NSBundle mainBundle]; 
NSURL* bundleURL = bundle.bundleURL; 
NSNumber* readOnly; 
NSError* error; 
if ([bundleURL getResourceValue:&readOnly forKey:NSURLVolumeIsReadOnlyKey error:&error]) 
{ 
    BOOL isReadOnly = [readOnly boolValue]; 
    // act on isReadOnly value 
} 
else 
{ 
    // Handle error 
} 
+0

Potresti suddividere le chiamate in metodi separati, quindi è più facile per me replicare da Java usando SWT? Grazie in anticipo. –

+0

Ho modificato la mia risposta. E 'questo che intendevi? –

Problemi correlati