将更新的数据库复制到ios sdk中的设备中

时间:2013-05-02 08:52:03

标签: iphone ios objective-c database xcode

在我的应用程序中,我使用了sqlite DB。我将应用程序的1.0版本提交到了应用程序商店。但之后我对DB进行了一些更改,比如插入一些新行。

然后提交了1.1版本的应用程序。 But i will not able to get updated DB because the old DB already exists in device.

我该如何解决这个问题?

如果我删除该应用&然后安装新版本的应用程序,然后我得到了更新的数据库。

//My code for copy of DB is as follow:

- (void)createEditableCopyOfDatabaseIfNeeded
{
    // First, test for existence.
    BOOL success;
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSError *error;
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentsDirectory = [paths objectAtIndex:0];
    NSString *writableDBPath = [documentsDirectory stringByAppendingPathComponent:@"xxx.sqlite"];
    success = [fileManager fileExistsAtPath:writableDBPath];
    if (success) return;

    // The writable database does not exist, so copy the default to the appropriate location.

    NSString *defaultDBPath = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"xxx.sqlite"];
    success = [fileManager copyItemAtPath:defaultDBPath toPath:writableDBPath error:&error];
    if (!success) {
        NSAssert1(0, @"Failed to create writable database file with message '%@'.", [error localizedDescription]);
    }
}

我在appDidFinishLaunching方法中调用了这个方法。

如何在新版本可用的情况下更新数据库而不删除应用

3 个答案:

答案 0 :(得分:5)

您可以使用NSUserDefaults执行此操作。

在新版本中添加以下代码:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
  if(![[NSUserDefaults standardUserDefaults] boolForKey:@"1.1"]])
  {
     [self removeDatabase];
     [self createEditableCopyOfDatabaseIfNeeded];
     [[NSUserDefaults standardUserDefaults] setBool:YES forKey:@"1.1"];
  }
  //Other stuffs
}

删除旧数据库文件的方法:

- (void)removeDatabase
{
    BOOL success;
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSError *error;
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentsDirectory = [paths objectAtIndex:0];
    NSString *removeDBPath = [documentsDirectory stringByAppendingPathComponent:@"xxx.sqlite"];
    success = [fileManager fileExistsAtPath:writableDBPath];
    if(success)
    {
       [fileManager removeItemAtPath:writableDBPath error:&error]
    }
}

答案 1 :(得分:0)

您需要执行数据库迁移,以便应用的旧用户不会丢失数据。

这意味着检查已存在的数据库版本,并执行必要的SQL语句以更新架构和数据。

MTMigration框架(MIT许可证)可以帮助您为每个应用版本执行一次代码,例如:

[MTMigration migrateToVersion:@"1.1" block:^{
    // migrate the SQL database here
}];

但您可能希望以不同方式检测数据库的版本。

为此过程编写一些单元测试是个好主意。搞砸用户数据是你想做的最后一件事。

答案 2 :(得分:0)

您必须编写数据迁移脚本: -

如果您需要对包含某些数据的现有表进行更改,则需要执行以下步骤:

1)重命名现有表

Say TableName是'TestTable',所以将表重命名为'TestTableOld'

2)创建一个名为“TestTable”的新表,其中包含您想要的新列以及其他争议。

3)使用以下查询将数据从'TestTableOld'复制到'TestTable':

插入TestTable('col1',col2'...'coln')值选择col1,col2,col3,...'coln'来自TestTableOld;

并且新添加的列设置值为空白,因为新条目将使用这样。

4)删除表'TestTableOld'

遵循上述四步程序,因为它可以作为alter语句使用,也可以保留原始表中的所有数据。

如果您正在使用User_Version,那么将有助于识别具有新数据库的旧数据库