Joetjah
Joetjah

Reputation: 6132

SQLite sqlite3_prepare_v2 no error but not ok neither

Hey guys, I'm just playing around with SQLite so this is new for me. I've got a view in which persons data can be both saved and found. The save-function and find-function work perfectly. Now, I've got a new view with a tableView in it. I want to get all the persons in the contacts-table and fill the list with it.

Untill now, I've got:

-(void)viewWillAppear:(BOOL)animated {
    const char *dbpath = [databasePath UTF8String];
    sqlite3_stmt *statement;

    if (sqlite3_open(dbpath, &contactDB) == SQLITE_OK)
    {
        NSLog(@"Opened DB");
        NSString *querySQL = [NSString stringWithFormat:@"SELECT name FROM contacts"];

        const char *query_stmt = [querySQL UTF8String];
        NSLog(@"could not prepare statement: %s\n", sqlite3_errmsg(contactDB));

        if (sqlite3_prepare_v2(contactDB, query_stmt, -1, &statement, NULL) == SQLITE_OK)
        //if (sqlite3_step(query_stmt) == SQLITE_DONE)
        {
            //NSLog(@"SQLite OK");
            NSLog(@"SQLite ok");
            //if (sqlite3_step(statement) == SQLITE_ROW)
            //{
                while(sqlite3_step(statement) == SQLITE_ROW) {
                    NSLog(@"SQLite ROW");
                    NSString *person = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 0)];
                    [personsList addObject:person];
                }
            //} else {
            //    NSLog(@"Emtpy list");
            //}
            sqlite3_finalize(statement);
        }
        sqlite3_close(contactDB);
    }
    NSLog(@"Calling reload");
    NSLog(@"%@", personsList);
    [tabelView reloadData];
}

This is all in viewWillAppear. When the view is loaded and done, the log says: 2011-05-06 10:45:26.976 database[1412:207] Opened DB

2011-05-06 10:45:26.978 database[1412:207] could not prepare statement: not an error

2011-05-06 10:45:26.979 database[1412:207] Calling reload

2011-05-06 10:45:26.979 database[1412:207] (

)

So it seems the statement isn't an error, but sqlite3_prepare_v2 isn't SQL_OK after all. Any help?

EDIT: In the previous view, the statement for creating a person is: @"INSERT INTO CONTACTS (name, address, phone) VALUES (\"%@\", \"%@\", \"%@\")", name.text, address.text, phone.text];

The statement for finding someone is: @"SELECT address, phone FROM contacts WHERE name=\"%@\"", name.text];

These two statements work and the data is displayed.

Upvotes: 0

Views: 12278

Answers (4)

Haider Malik
Haider Malik

Reputation: 1771

This worked for me:

create the table in your didload functions and then add this in (assuming you have declared the other table view functions):

public func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell{
    let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! TableViewCell        

    var selectStatement: OpaquePointer? = nil
    let selectSql = "select * from Inventory where ID = \((indexPath.row + 1))"
    if sqlite3_prepare_v2(Database.database.sqliteDB, selectSql, -1, &selectStatement, nil) == SQLITE_OK{
        if sqlite3_step(selectStatement) == SQLITE_ROW {

            let nameItem = sqlite3_column_text(selectStatement, 1)
            let price = sqlite3_column_double(selectStatement, 2)
            let quantity = sqlite3_column_int(selectStatement, 3)

            let nameString = String(cString: nameItem!)
            let priceString = String(format: "%.1f",price)
            let quantityString = String(quantity)

            cell.itemName.text = nameString
            cell.itemPrice.text = priceString
            cell.itemQuantity.text = quantityString

        }
    }

    return cell
}

Upvotes: 0

Joetjah
Joetjah

Reputation: 6132

I used const char *dbpath = [databasePath UTF8String];, but I forgot to put the following code above it:

// Get the documents directory
    NSString *docsDir;
    NSArray *dirPaths;
    dirPaths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);

    docsDir = [dirPaths objectAtIndex:0];
    databasePath = [[NSString alloc] initWithString: [docsDir stringByAppendingPathComponent: @"contacts.db"]];
    const char *dbpath = [databasePath UTF8String];

Upvotes: 0

Chetan Bhalara
Chetan Bhalara

Reputation: 10344

Try this,

-(void)viewWillAppear:(BOOL)animated {

    // Override point for customization after app launch.
    // Setup some globals
    // Get the path to the documents directory and append the databaseName
    NSArray *documentPaths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentsDir = [documentPaths objectAtIndex:0];
    databasePath = [documentsDir stringByAppendingPathComponent:@"contacts.db"];

    const char *dbpath = [databasePath UTF8String];
    sqlite3_stmt *statement;

    if (sqlite3_open(dbpath, &contactDB) == SQLITE_OK)
    {
        NSLog(@"Opened DB");
        NSString *querySQL = [NSString stringWithFormat:@"SELECT name FROM CONTACTS"];
        const char *query_stmt = [querySQL UTF8String];

        NSLog(@"could not prepare statement: %s\n", sqlite3_errmsg(contactDB));

        if (sqlite3_prepare_v2(contactDB, query_stmt, -1, &statement, NULL) == SQLITE_OK)
        {
            NSLog(@"SQLite ok");
                while(sqlite3_step(statement) == SQLITE_ROW) {
                    NSLog(@"SQLite ROW");
                    NSString *person = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 0)];
                    [personsList addObject:person];
                }
            sqlite3_finalize(statement);
        }
        else
        {
            //NSLog(@"could not prepare statement: %s\n", sqlite3_errmsg(statement));
        }
        sqlite3_close(contactDB);
    }
    NSLog(@"Calling reload");
    NSLog(@"%@", personsList);
    [tabelView reloadData];
}

Upvotes: 1

Rahul Sharma
Rahul Sharma

Reputation: 3013

@joetjah I used your code to fetch the results and it worked fine

2011-05-06 16:03:00.076 SQLiteDemo[6454:207] Opened DB
2011-05-06 16:03:09.550 SQLiteDemo[6454:207] could not prepare statement: not an error
2011-05-06 16:03:24.685 SQLiteDemo[6454:207] SQLite ok
2011-05-06 16:03:26.229 SQLiteDemo[6454:207] SQLite ROW
2011-05-06 16:03:28.254 SQLiteDemo[6454:207] SQLite ROW
2011-05-06 16:03:34.461 SQLiteDemo[6454:207] Calling reload
2011-05-06 16:03:35.009 SQLiteDemo[6454:207] (
    rahul,
    sqlite
)


-(void)testFunction{
    const char *dbpath = [databasePath UTF8String];
    sqlite3_stmt *statement;
    sqlite3 *contactDB;
    NSMutableArray *personsList = [[NSMutableArray alloc ] initWithCapacity:0];
    if (sqlite3_open(dbpath, &contactDB) == SQLITE_OK)
    {
        NSLog(@"Opened DB");
        NSString *querySQL = [NSString stringWithFormat:@"SELECT name FROM contacts"];

        const char *query_stmt = [querySQL UTF8String];
        NSLog(@"could not prepare statement: %s\n", sqlite3_errmsg(contactDB));

        if (sqlite3_prepare_v2(contactDB, query_stmt, -1, &statement, NULL) == SQLITE_OK)
            //if (sqlite3_step(query_stmt) == SQLITE_DONE)
        {
            //NSLog(@"SQLite OK");
            NSLog(@"SQLite ok");
            //if (sqlite3_step(statement) == SQLITE_ROW)
            //{
            while(sqlite3_step(statement) == SQLITE_ROW) {
                NSLog(@"SQLite ROW");
                NSString *person = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 0)];
                [personsList addObject:person];
            }
            //} else {
            //    NSLog(@"Emtpy list");
            //}
            sqlite3_finalize(statement);
        }
        sqlite3_close(contactDB);
    }
    NSLog(@"Calling reload");
    NSLog(@"%@", personsList);
    //[tabelView reloadData];
}

You can compare the code, The probable point of failure might be 1] data not being saved properly and hence nothing is fetched. 2] databasePath being set to blank (which I doubt as you get Open Db log)

The table contact is created using "CREATE TABLE contacts (name text, age integer)" try this once and let me know if it works.

Upvotes: 3

Related Questions