-2

我正在开发一个从服务器下载 sqlite3 文件并在以后随时使用它的应用程序,但下载后我无法读取它的数据

我使用此代码下载:

myConnection = [[NSURLConnection alloc] initWithRequest:request delegate:self];
[myConnection start];

我使用此代码获取数据:

- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data
{
    [myMutableData appendData:data];
}

我使用此代码保存文件:

- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{
    [myMutableData writeToFile:kPath atomically:YES]
}

保存文件后,我尝试通过以下代码使用它:

{
    const char *SQL = [@"SELECT * from table1" UTF8String];
    sqlite3 *database = NULL;
    NSString *file = kPath;
    if (sqlite3_open([file UTF8String], &database) == SQLITE_OK)
        sqlite3_exec(database, SQL, myCallback, (__bridge void*)myArray, NULL);
    sqlite3_close(database);
}

我的回调函数是:

static int myCallback(void *context, int count, char **values, char **columns) {
    // "count" is always zero !!

    return SQLITE_OK;
}

我的问题是:回调函数中的“计数”始终为零!

请帮我

4

2 回答 2

0

几个问题:

  1. 您的数据库路径应该:

    • 大概应该由NSSearchPathForDirectoriesInDomains;

    • connectionDidFinishLoading在as中应该是一样的sqlite3_open

    • 就编程风格而言,您可能希望使用与 不同的变量名kPath,这可能表明它是一个常量,而显然不是。

  2. 您应该检查调用的结果writeToFile以确保它被正确保存。

  3. 如果在模拟器上运行,您应该在下载后检查文件(手动在 Mac OS Finder 中,而不是通过您的应用程序......它应该在~/Library/Application Support/iPhone Simulator/...)导航到模拟器的文件夹并检查下载的文件。查看文件大小并查看您的服务器值是否与下载的值匹配。

  4. 更微妙的问题之一是,如果您的数据库 URL 使用的是 HTTP 协议并且未找到,您将不会didFailWithError从您NSURLConnection的 . 通过手动检查生成的文件确保下载成功。

    如果您NSURLConnection通过 HTTP 使用和下载并希望以编程方式确保您没有收到错误,您可以使用didReceiveResponse

    - (void)connection:(NSURLConnection*)connection didReceiveResponse:(NSURLResponse *)response
    {
        if ([response isKindOfClass:[NSHTTPURLResponse class]])
        {
            NSHTTPURLResponse *httpResponse = (id)response;
    
            NSInteger statusCode = [httpResponse statusCode];
    
            if (statusCode == 200)
            {
                // everything is ok
            }
            else if (statusCode >= 400)
            {
                // something went wrong, such as statusCode == 404 or something like that
            }
        }
    }
    
  5. 您没有向我们展示myMutableData. 我假设你已经做到了。您正在追加,但如果您忽略初始化该变量,它将继续进行而不会发生意外,但永远不会保存文件:

    myMutableData = [[NSMutableData alloc] init];
    
  6. sqlite3_open前面的问题很隐蔽,因为如果数据库不存在,执行过程将创建数据库。我在打开数据库时经常使用sqlite3_open_v2,所以如果数据库不存在,我会收到错误消息(或者,最好NSFileManager先用于检查文件是否存在)。您可能想要重置您的模拟器(或从您的设备中删除该应用程序),以便删除sqlite3_open为您创建的任何空白数据库。

  7. 与您的直接问题无关,但顺便说一句,您的NSURLConnection代码正在将整个数据库加载到 RAM 中。如果它不是太大,你可以摆脱它,但最好将它流式传输到持久存储,以最大限度地减少下载过程的内存占用。在设备(而不是模拟器)上运行您的应用程序时尤其如此。

于 2013-03-08T18:43:05.407 回答
0

我解决了!

我的错误是:我已经在本地更新了数据库文件,但我忘记在我的服务器愚蠢的错误中更新它!

感谢大家尝试提供帮助。

于 2013-03-09T06:46:59.743 回答