2016-01-19 11 views
9

Con Swift ora alcune funzioni sono contrassegnate con throws e questo costringe gli sviluppatori a chiamare la funzione all'interno di un blocco do - try catch. Ma come lo sviluppatore può conoscere l'elenco delle diverse eccezioni generate da tale funzione?Come ottenere l'elenco degli errori generati da una funzione?

come riferimento, qui è una linea di codice Java:

static void employeeAge(int age) throws MyExceptionA,MyExceptionB 

Qui è chiaro che le eccezioni sono 2 MyExceptionA e MyExceptionB e lo sviluppatore può decidere di agire in modo diverso dipende dell'errore.

Possiamo ottenere lo stesso su Swift?

+0

Unfortanely, è necessario controllare la Documentazione (API). Fai attenzione, non c'è eccezione che si lanci, ma lancio di errori. Se stai cercando un modo per organizzare il flusso del tuo codice, usa invece il controllo corretto. L'errore di lancio di cattura è la tua ultima possibilità di recuperare da esso, non sei in grado di recuperare dall'eccezione. – user3441734

+0

[Vedi anche questa domanda correlata e la risposta accettata.] (Http://stackoverflow.com/questions/31977738/how-to-find-the-kind-of-errors-a-method-may-throw-and- catch-them-in-swift) – Suragch

risposta

4

Quando il docs Swift dice una funzione throws, significano che viene generata ErrorType (nel cacao API di solito un NSError), non è un'eccezione.

Si consideri il seguente do-try-catch flusso per NSFileManager s' createDirectoryAtPath:

let documentsPath = NSSearchPathForDirectoriesInDomains(.DocumentDirectory, .UserDomainMask, true)[0] 

do { 
    try NSFileManager.defaultManager().createDirectoryAtPath(documentsPath, withIntermediateDirectories: false, attributes: nil) 
} catch { 
    // 'error' variable automatically populated 
    print(error) 
    print(error.dynamicType) 
} 

createDirectoryAtPath non riuscirà perché la directory documenti esiste già. Registrazione della dynamicType del error mostra che è in realtà un oggetto NSError:

Error Domain=NSCocoaErrorDomain Code=516 "The file “Documents” couldn’t be saved in the folder “35B0B3BF-D502-4BA0-A991-D07568AB87C6” because a file with the same name already exists." UserInfo={NSFilePath=/Users/jal/Library/Developer/CoreSimulator/Devices/E8A35774-C9B7-42F0-93F1-8103FBBC7118/data/Containers/Data/Application/35B0B3BF-D502-4BA0-A991-D07568AB87C6/Documents, NSUnderlyingError=0x7fa88bd14410 {Error Domain=NSPOSIXErrorDomain Code=17 "File exists"}} 

NSError 

Per vedere i diversi tipi di errori di una funzione può throw, si dovrebbe esaminare la error per informazioni per determinare il tipo di errore generato e come gestire ciascun errore. Nel caso di NSError questo sarebbe il suo dominio, codice e descrizione.

In questo caso particolare, esiste già una directory in quel percorso, quindi il file manager non può creare una nuova directory. Un esempio di un altro motivo per cui questa operazione potrebbe fallire sarebbe se il file manager non avesse accesso in scrittura. Quello sarebbe il codice di errore 256.

+1

Tranne che c'è l'errore "puro" di swift ... L'unico requisito è che l'errore di lancio sia conforme al protokol ErrorType. Non significa che sia un oggetto NSError. – user3441734

+0

@ user3441734 Non vedo errori "puri" generati nelle API o nei documenti Cocoa Touch, questo era solo un esempio utilizzando un metodo fornito da Apple. Puoi fornirmi un esempio nei documenti di un errore "puro" Swift? Inoltre, '' ErrorType' 'viene adottato da 'NSError'.] (Https://developer.apple.com/library/ios/documentation/Swift/Reference/Swift_ErrorType_Protocol/index.html) – JAL

+0

In entrambi i casi, non ci sono differenze tipi di errori che vengono lanciati. Tutti gli errori sarebbero di tipo 'NSError' o conformi al protocollo' ErrorType'. Dovresti esaminare la descrizione specifica dell'errore o il codice di errore per capire cosa è andato storto. – JAL

-1

Si scrive una sequenza dopo la cattura per indicare gli errori che tale clausola può gestire.

do { 
    try expression 
    statements 
} catch pattern 1 { 
    statements 
} catch pattern 2 where condition { 
    statements 
} 

vedere Errori sezione di utilizzo Utilizzo Do-Catch of Swift Programming Language

+4

la domanda è come posso ottenere l'elenco di tutti gli errori possibili lanciati da una funzione. Se non conosco la lista, non posso specificare quali conosco come trattare. – IgnazioC

0

Ho avuto la stessa identica domanda dell'OP. Dal momento che nessuno ha risposto alla domanda come ha chiesto (e anche io), ecco il mio contributo.

In Swift 3 e Xcode 8.3.3 si farebbe quanto segue per trattare le singole eccezioni. Di seguito vi fornirò un esempio con FileManager.

Per prima cosa si dispone solo di un blocco di cattura per rilevare l'errore che il metodo genera. Quindi trasmetti quell'errore come un NSError. Contrariamente al protocollo Error in Swift, NSError è una vera classe di errore. Quindi puoi estrarre il codice di quell'errore in un'istruzione switch. Dovrai sapere da quale dominio il metodo genera l'errore e trovare i codici di errore nel file di intestazione appropriato.

Nell'esempio seguente, gli errori relativi ai file vengono generati in NSCocoaErrorDomain e questi codici di errore sono definiti/elencati in Foundation/FoundationErrors.h.Nel mio computer, si trovano a

/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/System/Library/Frameworks/Foundation.framework/Versions/C/Headers/FoundationErrors.h 

per le applicazioni MacOS e al

/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk/System/Library/Frameworks/Foundation.framework/Headers/ 

per le applicazioni iPhone.

Quindi, ecco un esempio:

let home = FileManager.default.homeDirectoryForCurrentUser 
let file = home.appendingPathComponent("file") 
do { 
    let loadedString = try String(contentsOf: file) 
} 
catch { 
    let realError = error as NSError // As weird as it looks, Xcode actually wants this forced conversion 
    print(realError.localizedDescription) 
    switch realError.code { 
    case 257: // No permission 
     handleNoPermission() 
    case 260: // File not found 
     handleFileNotFound() 
    default: 
     handleUndefinedError() 
    } 
} 

Il .localizedDescription contiene un utente messaggio amichevole nel linguaggio del vostro utente su tale errore. Se il file non viene trovato sopra, stampa: The file “file” couldn’t be opened because there is no such file. in inglese. È pensato per essere utilizzato direttamente nelle finestre di dialogo degli errori che si presentano all'utente.

È inoltre possibile trovare ulteriori informazioni su ciò che errore viene generato da ogni dominio qui: https://developer.apple.com/library/content/documentation/Cocoa/Conceptual/ErrorHandlingCocoa/ErrorObjectsDomains/ErrorObjectsDomains.html