简体   繁体   English

在iphone上删除数据sqllite - 数据库已锁定

[英]Delete data sqllite on iphone - database is locked

my app crashed when I try to delete a data from my SqlLite db. 当我尝试从我的SqlLite数据库中删除数据时,我的应用程序崩溃了。

This is the error: Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Error while deleting. 'database is locked' 这是错误: Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Error while deleting. 'database is locked' Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Error while deleting. 'database is locked'

This is all my code on database: 这是我在数据库上的所有代码:

#import "Database.h"

static sqlite3 *database = nil;
static sqlite3_stmt *deleteStmt = nil;
static sqlite3_stmt *addStmt = nil;

@implementation Database

@synthesize id_poi, pathDb, arrPoi;

- (id) initWithData:(NSDictionary *) data {

    [super init];
    NSLog(@"%@",[data objectForKey:@"pathDb"]);
    NSLog(@"id_poi = %@",[data objectForKey:@"id_poi"]);
    //setto l'id nello stato dell'oggetto
    id_poi = [data objectForKey:@"id_poi"];
    pathDb = [data objectForKey:@"pathDb"];

    return self;
}

- (void) deletePoi {

    if (sqlite3_open([pathDb UTF8String], &database) == SQLITE_OK) {
        const char *sql = "delete from Poi where id_poi = ?";
        sqlite3_stmt *deleteStmt;
        if(sqlite3_prepare_v2(database, sql, -1, &deleteStmt, NULL) == SQLITE_OK) {
            //When binding parameters, index starts from 1 and not zero.
            sqlite3_bind_int(deleteStmt, 1, [id_poi integerValue]);

            if (SQLITE_DONE != sqlite3_step(deleteStmt)) {
                NSAssert1(0, @"Error while deleting. '%s'", sqlite3_errmsg(database));
                [[WPActivityIndicator sharedActivityIndicator] hide];
                return;
            }
        } else {
            NSAssert1(0, @"Error while creating delete statement. '%s'", sqlite3_errmsg(database));   
        }
        sqlite3_finalize(deleteStmt);
    } else {
        sqlite3_close(database); //Even though the open call failed, close the database connection to release all the memory.
    }


    [[WPActivityIndicator sharedActivityIndicator] hide];
}

- (BOOL) checkIdPoi {

    // lista temporanea
    NSMutableArray *listaTemp = [[NSMutableArray alloc] init];
    // Oggetto che contiene i vari elementi
    NSMutableDictionary *dictionary;

    NSMutableString *str_id_poi;//id della persona

    if (sqlite3_open([pathDb UTF8String], &database) == SQLITE_OK) {
        // query che ricava i valori
        const char *sql = "select id_poi from Poi where id_poi = ?";
        sqlite3_stmt *selectstmt;

        if(sqlite3_prepare_v2(database, sql, -1, &selectstmt, NULL) == SQLITE_OK) {

            sqlite3_bind_int(selectstmt, 1 , [id_poi integerValue]);
            while(sqlite3_step(selectstmt) == SQLITE_ROW) {
                // ricaviamo i valori letti dalla query
                str_id_poi = [NSMutableString stringWithUTF8String:(char *)sqlite3_column_text(selectstmt, 0)];

                // inseriamo tutti i valori letti in un unico oggetto
                dictionary = [[NSMutableDictionary alloc] initWithObjectsAndKeys:str_id_poi, @"id_poi", nil];
                //NSLog(@"str_id_poi = %@",str_id_poi);
                [listaTemp addObject:dictionary];
                [dictionary release];
                return TRUE;
            }
        } else {
            NSAssert1(0, @"Error while read data. '%s'", sqlite3_errmsg(database));
            return FALSE;
        }
    }
    else {
        sqlite3_close(database);
        return FALSE;
    }

    return FALSE;

}

- (void) addPoi {

    //NSLog(@"%@",pathDb);

    if (sqlite3_open([pathDb UTF8String], &database) == SQLITE_OK) {

        const char *sql = "insert into Poi(id_poi) Values(?)";
        sqlite3_stmt *addStmt;
        if(sqlite3_prepare_v2(database, sql, -1, &addStmt, NULL) == SQLITE_OK) {

            NSString *str_id_poi = [[NSString alloc] initWithFormat:@"%d", [id_poi integerValue]];
            sqlite3_bind_text(addStmt, 1, [str_id_poi UTF8String], -1, SQLITE_TRANSIENT);

            if(SQLITE_DONE != sqlite3_step(addStmt)) {
                NSAssert1(0, @"Error while inserting data. '%s'", sqlite3_errmsg(database));
                [[WPActivityIndicator sharedActivityIndicator] hide];
                return;
            } else {
                //SQLite provides a method to get the last primary key inserted by using sqlite3_last_insert_rowid
                //id_poi = sqlite3_last_insert_rowid(database);
            }

            //Reset the add statement.
            sqlite3_reset(addStmt);


        } else {
            NSAssert1(0, @"Error while creating add statement. '%s'", sqlite3_errmsg(database));            
        }
        sqlite3_finalize(addStmt); 

    } else {
        sqlite3_close(database); //Even though the open call failed, close the database connection to release all the memory.
    }

    sqlite3_close(database);

    [[WPActivityIndicator sharedActivityIndicator] hide];

}

// Carica i valori dal database passato come parametro
-(NSMutableArray*)getIdPOI {

    // lista temporanea
    NSMutableArray *listaTemp = [[NSMutableArray alloc] init];
    // Oggetto che contiene i vari elementi
    NSMutableDictionary *dictionary;

    NSMutableString *str_id_poi;//id della persona

    if (sqlite3_open([pathDb UTF8String], &database) == SQLITE_OK) {
        // query che ricava i valori
        const char *sql = "select id_poi from Poi";
        sqlite3_stmt *selectstmt;

        if(sqlite3_prepare_v2(database, sql, -1, &selectstmt, NULL) == SQLITE_OK) {

            while(sqlite3_step(selectstmt) == SQLITE_ROW) {
                // ricaviamo i valori letti dalla query
                str_id_poi = [NSMutableString stringWithUTF8String:(char *)sqlite3_column_text(selectstmt, 0)];

                // inseriamo tutti i valori letti in un unico oggetto
                dictionary = [[NSMutableDictionary alloc] initWithObjectsAndKeys:str_id_poi, @"id_poi", nil];
                //NSLog(@"str_id_poi = %@",str_id_poi);
                [listaTemp addObject:dictionary];
                [dictionary release];
            }

            //Reset the add statement.
            sqlite3_reset(selectstmt);

        } else {
            NSAssert1(0, @"Error while read data. '%s'", sqlite3_errmsg(database));
        }

        //ADD THIS LINE TO YOUR CODE
        sqlite3_finalize(selectstmt);
    }
    else
        sqlite3_close(database);

    sqlite3_close(database);

    return listaTemp;
}


+ (void) finalizeStatements {
    if(database) sqlite3_close(database);
    if(deleteStmt) sqlite3_finalize(deleteStmt);
    if(addStmt) sqlite3_finalize(addStmt);
}


-(void)dealloc {
    [pathDb release];
    [arrPoi release];

    [super dealloc];
}

@end

Any suggest? 有什么建议?

This type of error can occur when more then one query is fired for sqlite db. 当为sqlite db触发多个查询时,可能会发生此类错误。 When you are executing any query, you need to synchronize all calls to the database. 执行任何查询时,需要同步对数据库的所有调用。

Wrap all your database code in a @synchronized block like so: 将所有数据库代码包装在@synchronized块中,如下所示:

@synchronized(self)
{
   // database query code goes here
}

NB. NB。 this example assumes all database queries are executed from inside the 1 class. 此示例假定所有数据库查询都是从1类内部执行的。 If not, you should replace 'self' with a common object instance that is shared by all classes that interface with the database. 如果没有,则应将“self”替换为与数据库连接的所有类共享的公共对象实例。 Alternatively, you can run all database statements on the main thread. 或者,您可以在主线程上运行所有数据库语句。

This usually happens when the database was opened and then not closed properly. 这通常发生在数据库打开然后未正确关闭时。 It could be because you have the same instance of database opened from somewhere else.(Like a different class or SQLite manager). 这可能是因为您从其他地方打开了相同的数据库实例。(就像一个不同的类或SQLite管理器)。

It is usually advisable to create a singleton instance which communicates with your database rather opening and closing the database again and again.. hoping this helps. 通常建议创建一个与数据库通信的单例实例,而不是一次又一次地打开和关闭数据库..希望这会有所帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM