Dados principais de localização do arquivo Sqlite

91

Normalmente, o arquivo de armazenamento sqlite para aplicativos de dados principais está localizado em

Biblioteca> Suporte de aplicativo> Simulador de iPhone> 7.1 (ou qualquer versão que você esteja usando)> Aplicativos> (qualquer pasta que contenha seu aplicativo)> Documentos

pasta, mas não consigo encontrar no IOS 8. Eu presumiria que eles simplesmente adicionariam uma pasta 8.0 dentro da pasta iPhone Simulator, mas ela não está lá. Alguém conseguiu localizá-lo?

enlyte
fonte
2
Tenho quase certeza de que sua pergunta é uma duplicata, considerando que perguntei mais de uma semana antes de a sua ser feita. Agradeceríamos se você me deixasse receber o crédito por esta pergunta, considerando que é a primeira pergunta que fiz, e parece que você já tem uma reputação @HenryGlendening
enlyte
Veja como verificar dbpath stackoverflow.com/a/27358291/3840428
Nagarjun
Siga este ... stackoverflow.com/questions/24290989/…
Tunvir Rahman Tusher
2
Alguém sabe como obter os arquivos CoreData do dispositivo real? Eu costumava fazer isso via iTunes em versões mais antigas do Xcode, mas desde o Xcode 8 / iOS10 não acho que os arquivos CoreData sejam armazenados no diretório de documentos do aplicativo, portanto, não visíveis no iTunes. Existe uma maneira de obter os arquivos CoreDate do dispositivo em seu computador?
Bocaxica
1
Não sei por que eles continuam a mover isso. Eles deveriam colocá-lo em algum lugar e apenas deixá-lo.
RegularExpression

Respostas:

135

Consegui localizar o arquivo sqlite, e agora está neste caminho:

Biblioteca / Desenvolvedor / CoreSimulator / Dispositivos / (números e letras) / dados / Containers / Dados / Aplicativo / (números e letras) / Documentos /

(números e letras) representa uma pasta que seria exclusiva do seu aplicativo / computador, mas seria assim: 779AE2245-F8W2-57A9-8C6D-98643B1CF01A

Consegui encontrá-lo acessando appDelegate.m, rolando para baixo até o

- (NSURL *)applicationDocumentsDirectory 

método e NSLogging o caminho de retorno, como este:

// 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];
 }

Isso lhe dará seu caminho exclusivo, tornando-o mais fácil para você, porque é complicado localizá-lo com as 2 pastas / sequências de letras e números sem nome.

Swift 4.2:

let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
print(paths[0])
enlyte
fonte
4
Use xcrun simctl listpara obter a lista de nomes de simuladores e seus UUIDs.
Sandy Chapman,
1
Observe que se você usar um banco de dados compartilhado para um grupo de aplicativos (por exemplo, quando estiver usando uma extensão), o caminho é Biblioteca / Desenvolvedor / CoreSimulator / Dispositivos / $ número / dados / Containers / Compartilhado / Grupo de aplicativos / $ número / Nome.sqlite
andreacipriani
6
Observe que, em 2019 , Library/Developer/CoreSimulator/Devices/(numbers and letters)/data/Containers/Data/Application/(numbers and letters)/Documents/não é mais verdade. Agora você encontra o .sqlite e dois arquivos relacionados emLibrary/Developer/CoreSimulator/Devices/(numbers and letters)/data/Containers/Data/Application/(numbers and letters)/Library/Application Support/
Gang Fang
@GangFang Estou tentando converter meu código Objective C que é construído no Xcode 7 para a última versão swift e criar um novo projeto, então como posso migrar esses dois arquivos .sqlite diferentes para um único lugar.
Sanjay Shah
84

Nenhuma das respostas mencionou a maneira mais simples de realmente obter a localização do arquivo DB.

Ele nem mesmo exige que você modifique seu código-fonte, já que é uma chave de tempo de execução simples no XCode.

  1. Escolha Editar esquema ... próximo ao botão Executar.

    editar esquema

  2. Selecione Executar / Argumentos e adicione as duas opções a seguir:

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

    opção

  3. Execute o aplicativo e você verá nos registros:

    Histórico

hyperknot
fonte
2
Esta é realmente a melhor e mais simples solução. Obrigado!
Omid Ariyan
Pra mim o log não aparece, você pode me ajudar?
Augusto
@Augusto Não posso te ajudar aqui, mas se você fizer uma nova pergunta sobre isso, as pessoas provavelmente poderão responder e te ajudar.
hyperknot
Ótima resposta! Esta deve ser a resposta aceita. Além disso, existe alguma maneira que você conheça de alterar a cor dessa saída no console, além das preferências do Xcode? Seria bom se ele se
destacasse
Obrigado pela dica! O caminho muda constantemente, para mim agora (iOS 13.3.1) o caminho é / Users / *** / Library / Developer / CoreSimulator / Devices / A91CEB1C-B15D-46B5-9B83-DB22056DEFD1 / data / Containers / Shared / AppGroup / B835599A- CA36-432F-871A-17EDA181CC54 / Portanto, é melhor obtê-lo das informações de depuração do CoreData em vez de tentar adivinhar você mesmo.
AlKir
52

Experimente esta Etapa Simples de 3

  1. Copie o código a seguir em didFinishLaunchingWithOptionsseu appdelegate.me adicione um ponto de interrupção antes doNSLog()

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

Ou em Swift:

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

insira a descrição da imagem aqui

2. Abra o Finder-> Go -> Vá para a pasta e cole o caminho copiado da etapa 1

insira a descrição da imagem aqui

3. Yah !!! Você está em seu destino.

Tunvir Rahman Tusher
fonte
2
Para swift3, use: NSSearchPathForDirectoriesInDomains (.applicationSupportDirectory, .userDomainMask, true)
Yohst
38

Se seu aplicativo estiver usando Core Data, é apenas uma questão de pesquisar o arquivo sqlite no Terminal:

find ~ -name app_db_file_name.sqlite

Os resultados listarão o caminho completo para as pastas do simulador que contêm seu aplicativo.

DiscDev
fonte
2
@AlexWei Eu gostaria que a Apple adicionasse um botão no menu Arquivo para "Revelar a pasta de documentos do Simulador no localizador" ou algo semelhante. Parece ridículo que ainda não esteja lá, considerando que eles sempre mudam onde estão armazenando os arquivos ...
DiscDev
1
No caso de outros estão interessados, eu adicionei este comando como um alias para o meu profile: alias myapp_simulator_db="find ~/Library/Developer/CoreSimulator/Devices -name MyApp.sqlite". É útil quando você precisa executar este comando repetidamente.
brinde em
sudo find ~ -name app_db_file_name.sqlite me ajudou
Qadir Hussain
21

Eu hackeei este 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'" \;

Isso imprime:

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

Atualizar:

Como alguém apontou aqui , também é possível executar xcrun simctl list devicespara obter um resultado semelhante:

== 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)
Alexandre
fonte
18

Se você estiver usando o Swift , isso retornará o caminho absoluto do diretório do documento:

func applicationDirectoryPath() -> String {
    return NSSearchPathForDirectoriesInDomains(.DocumentDirectory, .UserDomainMask, true).last! as String
}
Mike Rapadas
fonte
1
Deve ser nomeado "func documentDirectoryPath ()" o que é para onde você está indo ...
Yohst
13

Eu escrevi um script bash para encontrar a localização da pasta do aplicativo e da pasta de dados do aplicativo dentro de um simulador, você pode baixá-lo aqui . Depois de descompactar o script, você pode navegar até a pasta em que o script está e usá-lo. Se você chamá-lo sem opções, ele fornecerá uma lista de simuladores iOS instalados. Você pode então usar as opções para localizar seu programa. Escrevendo:

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

encontrará a pasta do aplicativo e a pasta da área inicial do seu aplicativo no simulador do iPad Air iOS 8. Aqui está um exemplo:

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

Atualizar

Há uma atualização do script original que permite pesquisar com base no tipo de dispositivo usando uma opção -d. Também escrevi outro script que cria uma série de pastas com nomes sensatos para que você possa encontrar seu aplicativo e seus documentos. Este script criará uma pasta chamada iOS_SIMULATORS em sua área inicial e você poderá navegar facilmente até seu aplicativo a partir daí.

James Snook
fonte
Perfeito, editei seu script para fazer outro que reinicia todos os dados do simulador de um determinado aplicativo. Muito obrigado James!
Martin
Obrigado! Ótima solução para um PITA comum.
David Hersey
6

Consegui localizar a pasta de simuladores com a próxima saída do console:

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

no meu caso foi (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/
vírus
fonte
6

Com base nas respostas de Michaels, isso é para Swift 3

    func applicationDirectoryPath() -> String {
        return NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true).last! as String
    }
Jochen Bedersdorfer
fonte
A única solução aqui!
Fattie
5

Para Swift 3.0

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

você pode obter a localização de Coredata no Xcode 8.2

Tecnologia
fonte
5

Após novas atualizações do Xcode, descobri que os arquivos sql agora estão armazenados em uma nova pasta, /Library/Application Supportesta pode ser uma situação única, mas se você não encontrou os arquivos sql na pasta de documentos, procure-os aqui:

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

antes de ser armazenado na Documentspasta:

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

Nazir
fonte
4

Para SWIFT 3:

Copie e cole este código em didFinishLaunchingWithOptions

 print(NSSearchPathForDirectoriesInDomains(.applicationSupportDirectory, .userDomainMask, true).last! as String)
Sandu
fonte
Isso me ajudou. mas quando tento ir para esse caminho via terminal ele diz: Não existe esse arquivo ou diretório, mas quando tento ir para a opção de pasta, ele realmente existe.
Qadir Hussain
Isso funcionou para mim no OSX. Eu precisava ir mais 1 diretório dentro do diretório "Application Support" chamado <my app name> para corrigir o arquivo .sqlite.
Jacksonsox
3

Para Swift 3

print(NSSearchPathForDirectoriesInDomains(.applicationSupportDirectory, .userDomainMask, true).last! as String)
Andrew Shon
fonte
2

Como James Snook , criei meu próprio script para fornecer acesso mais fácil aos aplicativos do simulador. Acho que pode ser útil para muitas pessoas que chegam aqui, além de mim.

Ao contrário de seu script, o meu não é uma ferramenta de pesquisa, ele cria uma estrutura de pastas completa (e legível por humanos) com todos os dispositivos / tempos de execução e coloca links virtuais para os aplicativos neles.

Você pode obtê-lo neste Gist .

Execute-o sempre que instalar um aplicativo no simulador ou apenas execute-o toda vez que for buscar um aplicativo por qualquer motivo (ele será atualizado e abrirá a pasta de dispositivos no Finder).

fbeeper
fonte
Você pode adaptar este script para automatizar algumas coisas. Mas devo dizer que este aplicativo GUI que acabei de encontrar soa como uma alternativa realmente útil se você quiser apenas acessar as pastas do aplicativo :)
fbeeper
Isso também é muito bom, mas eu prefiro o segundo script postado por James Snook, pois também cria links virtuais para os diretórios de dados.
David Hersey
2

Se você não especificou nenhum diretório, você pode usar o código abaixo para imprimir o diretório padrão:

imprimir (NSPersistentContainer.defaultDirectoryURL ())

Ashutosh Shukla
fonte
1

Para iOS 10.0+você pode usar persistentContainer.persistentStoreCoordinator.persistentStores.first?.url

Criei a função Utilitário que copia o arquivo sqlite para o local desejado (funciona apenas para simulador).

Você pode usar como

import CoreData


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

Se você já tiver acesso aos arquivos sqlite, shm e wal, execute os comandos no terminal para mesclar o arquivo WAL no arquivo sqlite.

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

Depois de executar os comandos acima, você pode ver os dados em seu arquivo sqlite.


Aqui está a definição do método de utilidade para

/**
 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")      
}

Para

/**
 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");
}
Inder Kumar Rathore
fonte
0

Swift 3.x

Localize a função didFinishLaunchingWithOptions em seu arquivo AppDelegate e cole este código lá.

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

Swift 4.x

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

Swift 4.2

let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
        print(paths[0])
Divesh Singh
fonte
-1

Você pode usar o código a seguir.

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

Irá imprimir a localização do armazenamento persistente dos dados principais, ou seja, sqlite

Piyush
fonte