mainBundle にあるデータベースを更新する必要があるプロジェクトで、データベースの更新に取り組んでいます。mainbundle のファイルが読み取り専用であることは既にわかっているので、更新のために mainBundle のデータベースをドキュメント ディレクトリにコピーしました。更新後、ドキュメントディレクトリのそのファイルをmainBundleのファイルに置き換えたいです。誰でもこの問題を解決する方法を教えてください。前もって感謝します
2 に答える
それはできません。バンドルファイルは更新できないため。どういうわけか、そうすると、ビルドは次回の実行時に無効なバイナリメッセージを表示します。
ちなみに、なぜメインバンドルからDBを更新する必要があるのですか?メインバンドルデータベースファイルは元のデータベースのコピーであり、変更するにはドキュメントディレクトリにコピーする必要があります。
アップデート
アプリを再起動した後も記録を保持したい場合は、データベースを使用します。問題を解決するには、次のようにします。
NSString *docDirPath = [(NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)) objectAtIndex:0];
これにより、ドキュメントディレクトリのパスが返されます。その後、次のようにデータベースをこのパスにコピーします。
NSString *dbPath = [strDocPath stringByAppendingPathComponent:@"myDb.sqlite"];
if (![[NSFileManager defaultManager] fileExistsAtPath:dbPath]) {
[[NSFileManager defaultManager] copyItemAtPath:[[NSBundle mainBundle] pathForResource:@"mydb" ofType:@"sqlite"] toPath:dbPath error:nil];
}
これにより、データベースがパスにすでに存在するかどうかがチェックされ、空のデータベースに置き換えられません。データベースが存在しない場合(つまり、アプリの最初の実行)、データベースがコピーされます。
dbPath
これで、ドキュメントディレクトリにあり、アプリを再起動した後も保持されるデータベースにアクセスするためにアクセスできます。
データベースの存在を確認することを忘れないでください。if (![[NSFileManager defaultManager] fileExistsAtPath:dbPath]) {
そうしないと、実行のたびにアプリがドキュメントディレクトリのデータベースを元の(空のデータベース)に置き換えます。
この助けを願っています。
バンドルは署名されたコピーです。バンドルからリソースのいずれかを変更しようとすると、その署名は無効になります。したがって、更新されたデータベースをドキュメントディレクトリからバンドルにコピーすることはできません。コードは、ドキュメントディレクトリから更新されたコピーを参照する必要があります。
これを実現するには、更新が必要であることがわかったら、以下の手順に従います。
- 既存のドキュメントディレクトリデータベースの名前を変更します。
- バンドルデータベースをドキュメントディレクトリにコピーします。
- いずれか1つのコピーを更新してください。
- 古いコピーを解放します。
- 例外として、新しいコピーを削除し、古いコピーの名前を元の名前に変更します。
- アプリが正常に更新されたことをブールフラグにマークしないでください。次回は同じ演習を実行できます。
それが役に立てば幸い。