Dati di base della posizione del file SQLite


91

In genere, il file di archivio sqlite per le app di dati principali si trova in

Libreria> Supporto applicazioni> Simulatore iPhone> 7.1 (o qualsiasi versione tu stia utilizzando)> Applicazioni> (Qualunque cartella contenga la tua app)> Documenti

cartella, ma non riesco a trovarlo in IOS 8. Presumo che aggiungerebbero semplicemente una cartella 8.0 all'interno della cartella iPhone Simulator, ma non è lì. Qualcuno è riuscito a localizzarlo?


2
Sono abbastanza sicuro che la tua domanda sia il duplicato, considerando che l'ho fatta più di una settimana prima che la tua fosse posta. Sarebbe apprezzato se mi permettessi di ottenere il merito di questa domanda, considerando che è la prima domanda che ho mai fatto e sembra che tu abbia già una reputazione @HenryGlendening
enlyte

Dai un'occhiata a questo come controllare DBPATH stackoverflow.com/a/27358291/3840428
Nagarjun


2
Qualcuno sa come ottenere i file CoreData dal dispositivo reale? Lo facevo tramite iTunes nelle versioni precedenti di Xcode, ma poiché Xcode 8 / iOS10 non credo che i file CoreData siano archiviati nella directory dei documenti dell'app, quindi non visibili in iTunes. C'è un modo per ottenere i file CoreDate dal dispositivo sul tuo computer?
Bocaxica

1
Non so perché continuano a spostare questo. Dovrebbero metterlo da qualche parte e lasciarlo.
RegularExpression

Risposte:


135

Sono riuscito a individuare il file sqlite e ora si trova in questo percorso:

Libreria / Sviluppatore / CoreSimulator / Dispositivi / (numeri e lettere) / dati / Contenitori / Dati / Applicazione / (numeri e lettere) / Documenti /

(numeri e lettere) sta per una cartella che sarebbe univoca per la tua app / computer, ma sarebbe simile a questa: 779AE2245-F8W2-57A9-8C6D-98643B1CF01A

Sono stato in grado di trovarlo andando in appDelegate.m, scorrendo verso il basso fino al file

- (NSURL *)applicationDocumentsDirectory 

metodo e NSLogging il percorso di ritorno, in questo modo:

// Returns the URL to the application's Documents directory.
- (NSURL *)applicationDocumentsDirectory
{
    NSLog(@"%@",[[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory  inDomains:NSUserDomainMask] lastObject]);

    return [[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] lastObject];
 }

Questo ti darà il tuo percorso unico, rendendolo più facile per te, perché è difficile individuarlo con le 2 cartelle / stringhe di lettere e numeri senza nome.

Swift 4.2:

let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
print(paths[0])

4
Utilizzare xcrun simctl listper ottenere l'elenco dei nomi dei simulatori e i relativi UUID.
Sandy Chapman

1
Tieni presente che se utilizzi un database condiviso per un gruppo di app (ad esempio quando utilizzi un'estensione) il percorso è Library / Developer / CoreSimulator / Devices / $ number / data / Containers / Shared / AppGroup / $ number / Name.sqlite
andreacipriani

7
Si noti che, nel 2019 , Library/Developer/CoreSimulator/Devices/(numbers and letters)/data/Containers/Data/Application/(numbers and letters)/Documents/non è più vero. Ora trovi il .sqlite e i relativi due file inLibrary/Developer/CoreSimulator/Devices/(numbers and letters)/data/Containers/Data/Application/(numbers and letters)/Library/Application Support/
Gang Fang

@GangFang Sto provando a convertire il mio codice Objective C che è compilato in Xcode 7 all'ultima versione swift e creare un nuovo progetto, così come posso migrare questi due diversi file .sqlite in una sola posizione.
Sanjay Shah,

85

Nessuna delle risposte ha menzionato il modo più semplice per ottenere effettivamente la posizione del file DB.

Non richiede nemmeno di modificare il codice sorgente, poiché è un semplice interruttore di runtime in XCode.

  1. Scegli Modifica schema ... accanto al pulsante Esegui.

    modifica schema

  2. Seleziona Esegui / Argomenti e aggiungi le seguenti due opzioni:

    -com.apple.CoreData.SQLDebug 1
    -com.apple.CoreData.Logging.stderr 1

    opzione

  3. Esegui l'app e vedrai nei log:

    registri


2
Questa è davvero la soluzione più semplice e migliore. Grazie!
Omid Ariyan

Per me il log non compare, mi puoi aiutare?
Augusto

@Augusto Non posso aiutarti qui, ma se fai una nuova domanda a riguardo le persone possono probabilmente rispondere e aiutarti.
hyperknot

Bella risposta! Questa dovrebbe essere la risposta accettata. Inoltre, esiste un modo per modificare il colore di questo output nella console, oltre che tramite le preferenze di Xcode? Sarebbe bello se
risalisse

Grazie per il suggerimento! Il percorso cambia costantemente, per me ora (iOS 13.3.1) il percorso è / Users / *** / Library / Developer / CoreSimulator / Devices / A91CEB1C-B15D-46B5-9B83-DB22056DEFD1 / data / Containers / Shared / AppGroup / B835599A- CA36-432F-871A-17EDA181CC54 / Quindi è meglio ottenerlo dalle informazioni di debug di CoreData piuttosto che cercare di indovinare te stesso.
AlKir

52

Prova questo semplice 3 passaggio

  1. Copia il codice seguente nel didFinishLaunchingWithOptionstuo appdelegate.me aggiungi un punto di interruzione prima del fileNSLog()

    (BOOL)application:(UIApplication *)application  
    
    didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
    
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSLog(@"%@",[paths objectAtIndex:0]);
     }

O in Swift:

let paths = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.UserDomainMask, true)
print(paths[0])

inserisci qui la descrizione dell'immagine

2.Apri Finder-> Vai -> Vai alla cartella e incolla il percorso copiato dal passaggio 1

inserisci qui la descrizione dell'immagine

3. Yah !!! Sei nella tua destinazione.


2
Per swift3 utilizzare: NSSearchPathForDirectoriesInDomains (.applicationSupportDirectory, .userDomainMask, true)
Yohst

38

Se la tua app utilizza Core Data, è solo questione di cercare il file sqlite in Terminal:

find ~ -name app_db_file_name.sqlite

I risultati elencheranno il percorso completo delle cartelle del simulatore che contengono la tua app.


2
@AlexWei Vorrei che Apple aggiungesse un pulsante nel menu File a "Rivela la cartella dei documenti di Simulator nel Finder" o qualcosa di simile. Sembra ridicolo che non sia ancora lì, considerando che continuano a cambiare la posizione in cui archiviano i file ...
DiscDev

1
Nel caso in cui gli altri sono interessati, ho aggiunto questo comando come un alias al mio .profile: alias myapp_simulator_db="find ~/Library/Developer/CoreSimulator/Devices -name MyApp.sqlite". È utile quando è necessario eseguire ripetutamente questo comando.
brindisi

sudo find ~ -name app_db_file_name.sqlite mi ha aiutato
Qadir Hussain

21

Ho violato questo one-liner ( Gist ): find ~/Library/Developer/CoreSimulator/Devices/ -name device.plist -exec sh -c "/usr/libexec/PlistBuddy -c \"print UDID\" '{}' | tr '\n' ' '" \; -exec sh -c "/usr/libexec/PlistBuddy -c \"print name\" '{}' | tr '\n' ' '" \; -exec sh -c "/usr/libexec/PlistBuddy -c \"print runtime\" '{}' | sed -n 's/com\.apple\.CoreSimulator.SimRuntime\.\(.*\)/\1/p'" \;

Questo stampa:

14F313C8-3813-4E38-903E-2010C136B77B iPad Retina iOS-8-0
1F6B82A2-C467-479A-8CAF-074BE507AC8E iPad Air iOS-8-0
2DA83944-BE5D-4342-B330-08F67A932D8C iPad 2 iOS-7-1
48703432-A5C5-4606-9369-0D21B53EB1E8 iPhone 4s iOS-7-1
4AFB71CC-6752-4F9A-A239-4DC9CA53A8B8 iPhone 5s iOS-8-0
53A65771-DF50-4A5C-A8D2-4D1C3A5D0F60 iPhone 5 iOS-7-1
6B97C174-5914-4E89-8D17-943F0E2703BA iPhone 5 iOS-8-0
6C2DF3E9-FA26-4391-8B66-72E1467D6297 iPad 2 iOS-8-0
7F85E299-A3C2-4704-8B44-2984F6F995F5 iPad Retina iOS-7-1
8B9EDFFD-2240-476B-88AD-06ABE8F9FF51 iPhone 6 Plus iOS-8-0
97691E5D-5C38-4875-8AA7-C2B1E4ABCBB5 Resizable iPhone iOS-8-0
9BBF3408-6CA4-4CE0-BD4E-B02001F1262B iPhone 5s iOS-7-1
C9237847-F0AA-44BC-A74E-C08C2E0F7A6C Resizable iPad iOS-8-0
CC44C1BA-F39C-4410-AE34-4ABBD7806D45 iPad Air iOS-7-1
CDF4D811-5011-4464-8291-5CDA378375EA iPhone 6 iOS-8-0
E77DE00C-E244-4F25-A5E2-E6581614D5A2 iPhone 4s iOS-8-0

Aggiornare:

Come qualcuno ha sottolineato qui , è anche possibile correre xcrun simctl list devicesper ottenere un risultato simile:

== Devices ==
-- iOS 7.0 --
-- iOS 7.1 --
    iPhone 4s (48703432-A5C5-4606-9369-0D21B53EB1E8) (Shutdown)
    iPhone 5 (53A65771-DF50-4A5C-A8D2-4D1C3A5D0F60) (Shutdown)
    iPhone 5s (9BBF3408-6CA4-4CE0-BD4E-B02001F1262B) (Shutdown)
    iPad 2 (2DA83944-BE5D-4342-B330-08F67A932D8C) (Shutdown)
    iPad Retina (7F85E299-A3C2-4704-8B44-2984F6F995F5) (Shutdown)
    iPad Air (CC44C1BA-F39C-4410-AE34-4ABBD7806D45) (Shutdown)
-- iOS 8.1 --
    iPhone 4s (0763EF65-DD0D-4FAD-84C7-2DE63D416526) (Shutdown)
    iPhone 5 (868ED444-8440-4115-AF37-F419CC682D2F) (Shutdown)
    iPhone 5s (E0455E5D-7315-4EC8-B05E-76284728244C) (Shutdown)
    iPhone 6 Plus (72554908-FF99-4B8F-9B87-65255ED08CFC) (Shutdown)
    iPhone 6 (32AA8133-53A4-4BE0-8CE5-0C7A87E81CAF) (Shutdown)
    iPad 2 (4AF84DE8-CBA2-47AE-A92A-0C0CEF9F41F8) (Booted)
    iPad Retina (69238B44-AAFD-4CD5-AAEA-C182D0BC300D) (Shutdown)
    iPad Air (E580AD99-0040-4EC1-B704-0C85567E6747) (Shutdown)
    Resizable iPhone (32E872FC-6513-41AB-A5B9-B23EB7D10DC8) (Shutdown)
    Resizable iPad (99997922-4A9F-4574-9E3E-EF45F893F4A2) (Shutdown)

18

Se stai usando Swift , questo restituirà il percorso assoluto della directory dei documenti:

func applicationDirectoryPath() -> String {
    return NSSearchPathForDirectoriesInDomains(.DocumentDirectory, .UserDomainMask, true).last! as String
}

1
Dovrebbe essere chiamato "func documentDirectoryPath ()" come stai andando ...
Yohst

13

Ho scritto uno script bash per trovare la posizione della cartella dell'applicazione e della cartella dei dati dell'applicazione all'interno di un simulatore, puoi scaricarlo qui . Dopo aver decompresso lo script, è possibile accedere alla cartella in cui si trova lo script e utilizzarlo. Se lo chiami senza opzioni, ti darà un elenco di simulatori iOS installati. È quindi possibile utilizzare le opzioni per trovare il programma. Scrittura:

./simulatorAppFolders -s "iPad Air" -i iOS-8-0 -a <MyApp>

troverà la cartella dell'applicazione e la cartella dell'area home della tua app sul simulatore di iPad Air iOS 8. Ecco un esempio:

MacBook-Air:_posts user$ ./simulatorAppFolders -s "iPad Air" -i iOS-8-0 -a MyApp
App folder = /Users/james/Library/Developer/CoreSimulator/Devices/6A9DEE93-FAEF-4BF4-9989-BC14CD38AEA0/data/Containers/Bundle/Application/8F64CD7F-A227-43D6-98AC-41D3919827CB
dataFolder = /Users/james/Library/Developer/CoreSimulator/Devices/6A9DEE93-FAEF-4BF4-9989-BC14CD38AEA0/data/Containers/Data/Application/96C40A21-5A5C-4399-839C-B155B8A72932

Aggiornare

C'è un aggiornamento allo script originale che ti consente di cercare in base al tipo di dispositivo utilizzando un'opzione -d. Ho anche scritto un altro script che crea una serie di cartelle con nomi ragionevoli in modo che tu possa trovare la tua domanda ei documenti dell'applicazione. Questo script creerà una cartella chiamata iOS_SIMULATORS nella tua area home e da lì potrai facilmente navigare alla tua applicazione.


Perfetto, ho modificato il tuo script per crearne un altro che reintegrasse tutti i dati del simulatore di una determinata app. Grazie mille James!
Martin,

Grazie! Ottima soluzione per una PITA comune.
David Hersey

6

Sono stato in grado di individuare la cartella dei simulatori con il prossimo output della console:

NSLog(@"app dir: %@",[[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] lastObject]);

nel mio caso era (Xcode 6 beta)

app dir: file:///Users/user/Library/Developer/CoreSimulator/Devices/D00C56D4-DDA3-47B0-9951-27D3B9EC68E8/data/Applications/6ABF3E54-37F5-4AD1-A223-F7467F601FB6/Documents/

6

Sulla base delle risposte di Michaels, questo è per Swift 3

    func applicationDirectoryPath() -> String {
        return NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true).last! as String
    }

L'unica soluzione qui!
Fattie

5

Per Swift 3.0

let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
print(paths[0])

puoi ottenere la posizione di Coredata in Xcode 8.2


5

Dopo i nuovi aggiornamenti di Xcode ho scoperto che i file sql sono ora archiviati in una nuova cartella /Library/Application Supportquesta potrebbe essere una situazione unica, ma se non hai trovato i file sql nella cartella dei documenti cercali qui:

~/Library/Developer/CoreSimulator/Devices/[@device_id@]/data/Containers/Data/Application/[@application_id@]/Library/Application Support/

prima che fosse memorizzato nella Documentscartella:

~/Library/Developer/CoreSimulator/Devices/[@device_id@]/data/Containers/Data/Application/[@application_id@]/Documents/


4

Per SWIFT 3:

Copia incolla questo codice in didFinishLaunchingWithOptions

 print(NSSearchPathForDirectoriesInDomains(.applicationSupportDirectory, .userDomainMask, true).last! as String)

Questo mi ha aiutato. ma quando provo ad andare a quel percorso tramite terminale, dice: Nessun file o directory di questo tipo, ma quando provo ad andare all'opzione cartella esiste effettivamente.
Qadir Hussain

Questo ha funzionato per me su OSX. Dovevo andare in un'altra directory nella directory "Application Support" denominata <nome app> per correggere il file .sqlite.
Jacksonsox

3

Per swift 3

print(NSSearchPathForDirectoriesInDomains(.applicationSupportDirectory, .userDomainMask, true).last! as String)

2

Come James Snook ho creato il mio script per fornire un accesso più facile alle app del simulatore. Penso che possa essere utile per molte persone che arrivano qui, oltre a me.

A differenza del suo script, il mio non è uno strumento di ricerca, crea una struttura di cartelle completa (e leggibile dall'uomo) con tutti i dispositivi / runtime e inserisce collegamenti software alle app al loro interno.

Puoi ottenerlo in questo Gist .

Eseguilo ogni volta che installi un'app nel simulatore, o semplicemente eseguilo ogni volta che stai andando a recuperare un'app per qualsiasi motivo (si aggiornerà e aprirà la cartella dei dispositivi nel Finder).


Puoi adattare questo script per automatizzare alcune cose. Ma devo dire che questa app GUI che ho appena trovato suona come un'alternativa davvero utile se vuoi solo accedere alle cartelle dell'app :)
fbeeper

Anche questo è abbastanza carino, ma preferisco il secondo script pubblicato da James Snook in quanto crea anche collegamenti morbidi alle directory dei dati.
David Hersey

2

Se non hai specificato alcuna directory, puoi utilizzare il codice seguente per stampare la directory predefinita:

print (NSPersistentContainer.defaultDirectoryURL ())


1

Perché iOS 10.0+puoi usare persistentContainer.persistentStoreCoordinator.persistentStores.first?.url

Ho creato la funzione Utility che copia il file sqlite nella posizione desiderata (funziona solo per il simulatore).

Puoi usarlo come

import CoreData


let appDelegate = UIApplication.shared.delegate as! AppDelegate
UTility.getSqliteTo(destinationPath: "/Users/inderkumarrathore/Desktop", persistentContainer: appDelegate.persistentContainer)

Se hai già accesso ai file sqlite, shm e wal, esegui i comandi nel terminale per unire il file WAL nel file sqlite.

$ sqlite3 persistentStore
sqlite> PRAGMA wal_checkpoint;
Press control + d

Dopo aver eseguito i comandi precedenti puoi vedere i dati nel tuo file sqlite.


Ecco la definizione del metodo di utilità per

/**
 Copies the sqlite, wal and shm file to the destination folder. Don't forget to merge the wal file using the commands printed int the console.
 @param destinationPath Path where sqlite files has to be copied
 @param persistentContainer NSPersistentContainer
*/
public static func getSqliteTo(destinationPath: String, persistentContainer: NSPersistentContainer) {
  let storeUrl = persistentContainer.persistentStoreCoordinator.persistentStores.first?.url

  let sqliteFileName = storeUrl!.lastPathComponent
  let walFileName = sqliteFileName + "-wal"
  let shmFileName = sqliteFileName + "-shm"
  //Add all file names in array
  let fileArray = [sqliteFileName, walFileName, shmFileName]

  let storeDir = storeUrl!.deletingLastPathComponent()

  // Destination dir url, make sure file don't exists in that folder
  let destDir = URL(fileURLWithPath: destinationPath, isDirectory: true)

  do {
    for fileName in fileArray {
      let sourceUrl = storeDir.appendingPathComponent(fileName, isDirectory: false)
      let destUrl = destDir.appendingPathComponent(fileName, isDirectory: false)
      try FileManager.default.copyItem(at: sourceUrl, to: destUrl)
      print("File: \(fileName) copied to path: \(destUrl.path)")
    }
  }
  catch {
    print("\(error)")
  }
  print("\n\n\n ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ NOTE ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~\n")
  print("In your terminal run the following commands to merge wal file. Otherwise you may see partial or no data in \(sqliteFileName) file")
  print("\n-------------------------------------------------")
  print("$ cd \(destDir.path)")
  print("$ sqlite3 \(sqliteFileName)")
  print("sqlite> PRAGMA wal_checkpoint;")
  print("-------------------------------------------------\n")
  print("Press control + d")      
}

Per

/**
 Copies the sqlite, wal and shm file to the destination folder. Don't forget to merge the wal file using the commands printed int the console.
 @param destinationPath Path where sqlite files has to be copied
 @param persistentContainer NSPersistentContainer
 */
+ (void)copySqliteFileToDestination:(NSString *)destinationPath persistentContainer:(NSPersistentContainer *)persistentContainer {
  NSError *error = nil;
  NSURL *storeUrl = persistentContainer.persistentStoreCoordinator.persistentStores.firstObject.URL;
  NSString * sqliteFileName = [storeUrl lastPathComponent];
  NSString *walFileName = [sqliteFileName stringByAppendingString:@"-wal"];
  NSString *shmFileName = [sqliteFileName stringByAppendingString:@"-shm"];
  //Add all file names in array
  NSArray *fileArray = @[sqliteFileName, walFileName, shmFileName];

  // Store Directory
  NSURL *storeDir = storeUrl.URLByDeletingLastPathComponent;

  // Destination dir url, make sure file don't exists in that folder
  NSURL *destDir = [NSURL fileURLWithPath:destinationPath isDirectory:YES];

  for (NSString *fileName in fileArray) {
    NSURL *sourceUrl = [storeDir URLByAppendingPathComponent:fileName isDirectory:NO];
    NSURL *destUrl = [destDir URLByAppendingPathComponent:fileName isDirectory:NO];
    [[NSFileManager defaultManager] copyItemAtURL:sourceUrl toURL:destUrl error:&error];
    if (!error) {
      RLog(@"File: %@ copied to path: %@", fileName, [destUrl path]);
    }
  }


  NSLog(@"\n\n\n ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ NOTE ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~\n");
  NSLog(@"In your terminal run the following commands to merge wal file. Otherwise you may see partial or no data in %@ file", sqliteFileName);
  NSLog(@"\n-------------------------------------------------");
  NSLog(@"$ cd %@", destDir.path);
  NSLog(@"$ sqlite3 %@", sqliteFileName);
  NSLog(@"sqlite> PRAGMA wal_checkpoint;");
  NSLog(@"-------------------------------------------------\n");
  NSLog(@"Press control + d");
}

0

Swift 3.x

Individua la funzione didFinishLaunchingWithOptions nel tuo file AppDelegate e incolla questo codice lì.

let path = NSSearchPathForDirectoriesInDomains(.applicationSupportDirectory, .userDomainMask, true)
print("\(path)")

0

Swift 4.x

    let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
    print(paths[0])

0

Swift 4.2

let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
        print(paths[0])

-1

Puoi usare il seguente codice.

   func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
    // Override point for customization after application launch.
    **print(persistentContainer.persistentStoreDescriptions)**
    return true
}

Stamperà la posizione della memoria persistente dei dati di base, ad esempio sqlite

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.