I'm having trouble updating my database. I believe it's due to it possibly being read only, however I am unsure. I created my database in my console, and the code below adds the database to the project folder rather than referencing it externally. Here is the code to transfer the file to the project folder
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
databaseName = #"databasenew.sql";
/* copy over to phone code */
NSString *documentDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask,YES) objectAtIndex:0];
NSString *sqlFile =[documentDirectory stringByAppendingPathComponent:#"databasenew.sql"];
if (![[NSFileManager defaultManager] fileExistsAtPath:sqlFile]) {
NSString *bundleSql = [[NSBundle mainBundle] pathForResource:#"databasenew" ofType:#"sql"];
NSError *error = nil;
[[NSFileManager defaultManager] copyItemAtPath:bundleSql toPath:sqlFile error:&error];
if (error) {
NSLog(#"Could not copy json file: %#", error);
}
else{
NSLog(#"yea");
}
}
else{
NSLog(#"transfer complete");
}
NSString *bundleSql = [[NSBundle mainBundle] pathForResource:#"databasenew" ofType:#"sql"];
databasePath = bundleSql;
self.window.rootViewController = self.viewController;
[self.window makeKeyAndVisible];
return YES;
}
Here is the code where I try to update
-(void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *) namespaceURI qualifiedName:(NSString *)qName
attributes: (NSDictionary *)attributeDict
{
if ([elementName isEqualToString:#"Message"])
{
NSLog(soapResults);
NSString *convertString = soapResults;
check = [convertString intValue];
NSLog(#"user is");
NSLog(user);
if(check > 0){
databaseName = #"databasenew.sql";
NSString *bundleSql = [[NSBundle mainBundle] pathForResource:#"databasenew" ofType:#"sql"];
databasePath = bundleSql;
sqlite3 *database;
if(sqlite3_open([databasePath UTF8String], &database) == SQLITE_OK) {
const char *sqlStatement = "UPDATE people set user = 'munch'";
sqlite3_stmt *compiledStatement;
if(sqlite3_prepare_v2(database, sqlStatement, -1, &compiledStatement, NULL) == SQLITE_OK) {
NSLog(#"success");
NSLog(soapResults);
BOOL success = sqlite3_step(compiledStatement);
if (success != SQLITE_DONE) {
BOOL myBool=YES;
NSLog([NSString stringWithFormat:#"My Bool value : %d",success]);
}
}else{
NSLog(#"the fail ispreparing something");
NSAssert1(0, #"Error while creating update statement. '%s'", sqlite3_errmsg(database));
}
sqlite3_finalize(compiledStatement);
}else{
NSLog(#"fail");
}
sqlite3_close(database);
NSString *string = [NSString stringWithFormat:#"%d", check];
NSLog(string);
NSLog(#"lolololol");
check = 0;
[self Bootup];
}else{
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:#"Problem!" message:#"Incorrect Username or Password"
delegate:self cancelButtonTitle:#"Ok" otherButtonTitles:#"Yes", nil];
[alert show];
[alert release];
}
// gotoContent = checkConfirm;
}
if( [elementName isEqualToString:#"ValidateUserResponse"])
{
if(!soapResults)
{
soapResults = [[NSMutableString alloc] init];
NSLog(soapResults);
NSLog(#"above is soap validate user");
}
recordResults = TRUE;
}
}
I've done my NDlog debugging and it says "success" as it should if the code for updating is successful, however the database itself does not update. What is the reason for this?
You are forgeting some code for update statement
//the binding part is missing in your code , you need to write after Prepare statement.
sqlite3_bind_text(compiledStatement, 1, [string UTF8String], -1, SQLITE_TRANSIENT);
if(SQLITE_DONE != sqlite3_step(compiledStatement))
NSAssert1(0, #"Error while updating. '%s'", sqlite3_errmsg(database));
sqlite3_reset(compiledStatement);
Via iphonesdkarticles.com.
This will resolve your error.
-(BOOL) someUpdateFunction {
BOOL updatedSuccessfully = NO;
// Open the database.
if(sqlite3_open([databasePath UTF8String], &database) == SQLITE_OK) {
NSString *updateQuery = [[NSString alloc] initWithFormat:#"UPDATE people SET user = 'terror' WHERE user = 'greg'"];
const char *query = [updateQuery UTF8String];
[updateQuery release];
sqlite3_stmt *statement;
int res = (sqlite3_prepare_v2( database, query, -1, &statement, NULL));
if(res == SQLITE_OK) {
int result = sqlite3_step(statement);
if(result == SQLITE_DONE) {
updatedSuccessfully = YES;
sqlite3_finalize(statement);
}else {
NSLog(#"Failed with error code: %d", result);
}
}else {
NSLog(#"Failed to prepare the update query with error code: %d", res);
}
}else {
NSLog(#"Failed to open the database");
}
sqlite3_close(database);
//NSLog(updatedSuccessfully);
//NSLog(#"The value of the bool is %#\n", updatedSuccessfully);
return updatedSuccessfully;
}
I was supplied this in the chat room. Thanks lads.
Remember to copy the DB over to the device else. You can find the DB path with this code:
- (NSString *) dataFilePath:(NSString *) dbName {
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *dbPath = [documentsDirectory stringByAppendingPathComponent:dbName];
return dbPath;
}
-(BOOL)buildtheDB{
BOOL updatedSuccessfully = NO;
NSString *documentDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask,YES) objectAtIndex:0];
NSString *sqlFile =[documentDirectory stringByAppendingPathComponent:kDatabaseFileName];
if ([[NSFileManager defaultManager] fileExistsAtPath:sqlFile] == NO) {
NSString *bundleSql = [[NSBundle mainBundle] pathForResource:#"database" ofType:#"sqlite"];
NSError *error = nil;
BOOL databaseCopied = [[NSFileManager defaultManager] copyItemAtPath:bundleSql toPath:sqlFile error:&error];
if (databaseCopied == NO) {
if (error) {
NSLog(#"Could not copy database file with error: %#", [error localizedDescription]);
}
}else {
NSLog(#"Database copied successfully");
}
}
else{
NSLog(#"Database already copied");
}
return updatedSuccessfully;
}
Related
I have following code (modified code from this tutorial):
-(NSMutableArray *) getChampionDatabase
{
NSMutableArray *championsArray = [[NSMutableArray alloc] init];
#try {
NSFileManager *fileManager = [NSFileManager defaultManager];
NSString *databasePath = [[NSBundle mainBundle]pathForResource: #"Champions Database" ofType:#"sqlite"];
BOOL success = [fileManager fileExistsAtPath:databasePath];
if (!success)
{
NSLog(#"cannot connect to Database! at filepath %#",databasePath);
}
if(sqlite3_open([databasePath UTF8String], &database) == SQLITE_OK)
{
const char *sql = "SELECT CHAMPION_ID,CHAMPION_NAME,CHAMPION_IMG FROM CHAMPIONS";
sqlite3_stmt *sqlStatement;
if(sqlite3_prepare(database, sql, -1, &sqlStatement, NULL) == SQLITE_OK)
{
while (sqlite3_step(sqlStatement)==SQLITE_ROW) {
championList *ChampionList = [[championList alloc]init];
ChampionList.championId = [NSString stringWithUTF8String:(char *) sqlite3_column_text(sqlStatement,0)];
ChampionList.championName = [NSString stringWithUTF8String:(char *) sqlite3_column_text(sqlStatement,1)];
ChampionList.championImage = [NSString stringWithUTF8String:(char *) sqlite3_column_text(sqlStatement, 2)];
[championsArray addObject:ChampionList];
}
}
else
{
NSLog(#"problem with database prepare");
}
}
else
{
NSLog(#"problem with database openning");
}
}
#catch (NSException *exception)
{
NSLog(#"An exception occured: %#", [exception reason]);
}
#finally
{
return championsArray;
}
}
After running this code i always have output : "problem with database prepare"
Then i tried to check error number of sqlite3_prepare by following code:
int ret = sqlite3_prepare(database, sql, -1, &sqlStatement, NULL);
if (ret != SQLITE_OK) {
NSLog(#"Error calling sqlite3_prepare: %d", ret);
}
output: "Error calling sqlite3_prepare: 26"
error 26 - /*File opened that is not a database file */
File have sqlite 3 version
how is this possible? file extension is .sqlite and i can modify it in sqlite manager
Make sure you added your DB to the ressource bundle of your project and don't put any space in your name of your DB. For example use a name like champion_db.sqlite.
Am using SQLite3. and am updating row which is already present by using following code
- (BOOL)updateTableData :(NSString *) num
{
AppDelegate *appDelegate = (AppDelegate *)[UIApplication sharedApplication].delegate;
dbPath = [self getDBPath:#"studentslist.sqlite"];
if(sqlite3_open([dbPath UTF8String], &database) == SQLITE_OK)
{
sqlite3_stmt *updateStmt;
const char *sql = "update studentInfo set sAge=?, sAddrs1=?, sAddrs2=?, sMobile =?, sClass =? where sRollNumber=?;";
if(sqlite3_prepare_v2(database, sql, -1, &updateStmt, NULL) != SQLITE_OK)
{
NSLog(#"updateTableData: Error while creating delete statement. '%s'", sqlite3_errmsg(database));
return;
}
NSLog(#"appDelegate.updateArray %#",appDelegate.updateArray);
sqlite3_bind_int(updateStmt, 1,[[appDelegate.updateArray objectAtIndex:0] intValue]);
sqlite3_bind_text(updateStmt, 2,[[appDelegate.updateArray objectAtIndex:1] UTF8String], -1,SQLITE_TRANSIENT);
sqlite3_bind_text(updateStmt, 3,[[appDelegate.updateArray objectAtIndex:2] UTF8String], -1,SQLITE_TRANSIENT);
sqlite3_bind_text(updateStmt, 4,[[appDelegate.updateArray objectAtIndex:3] UTF8String], -1,SQLITE_TRANSIENT);
sqlite3_bind_text(updateStmt, 5,[[appDelegate.updateArray objectAtIndex:4] UTF8String], -1,SQLITE_TRANSIENT);
if (SQLITE_DONE != sqlite3_step(updateStmt))
{
NSLog(#"updateTableData: Error while updating. '%s'", sqlite3_errmsg(database));
sqlite3_finalize(updateStmt);
sqlite3_reset(updateStmt);
sqlite3_close(database);
return NO;
}
else
{
NSLog(#"updateTableData: Updated");
sqlite3_finalize(updateStmt);
sqlite3_close(database);
return YES;
}
}
else
{
NSLog(#"updateTableData :Database Not Opened");
sqlite3_close(database);
return NO;
}
in main class am calling this method as follows
-(IBAction)updateButtonAction:(id)sender
{
AppDelegate *appDelegate = (AppDelegate *)[UIApplication sharedApplication].delegate;
db = [[Database alloc]init];
if ([ageTxtFld.text length]>0 && [address1TxtFld.text length]>0 && [address2TxtFld.text length]>0 && [mobileTxtFld.text length]>0 && [classTxtFld.text length]>0)
{
[appDelegate.updateArray addObject:ageTxtFld.text];
[appDelegate.updateArray addObject:address1TxtFld.text];
[appDelegate.updateArray addObject:address2TxtFld.text];
[appDelegate.updateArray addObject:mobileTxtFld.text];
[appDelegate.updateArray addObject:classTxtFld.text];
NSLog(#"appDelegate.updateArray %#",appDelegate.updateArray);
NSString *num = rollNumberTxtFld.text;
BOOL is = [db updateTableData:num];
if (is == YES)
{
updateAlert = [[UIAlertView alloc] initWithTitle:#"Success" message:#"Updated" delegate:self cancelButtonTitle:#"Ok" otherButtonTitles:nil, nil];
[updateAlert show];
}
else
{
updateAlert = [[UIAlertView alloc] initWithTitle:#"Fail" message:#"Not Updated" delegate:self cancelButtonTitle:#"Ok" otherButtonTitles:nil, nil];
[updateAlert show];
}
}
else
{
UIAlertView *errorAlert = [[UIAlertView alloc] initWithTitle:#"Error" message:#"Enter all values" delegate:self cancelButtonTitle:#"Ok" otherButtonTitles:nil, nil];
[errorAlert show];
}
}
But it always printing NSLog(#"updateTableData: Updated"); but not updating
Any one can suggest me or help with code.
Thanks in Advance
- (void)createEditableCopyOfDatabaseIfNeeded {
BOOL success;
NSFileManager *fileManager = [NSFileManager defaultManager];
NSError *error;
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *writableDBPath = [documentsDirectory stringByAppendingPathComponent:#"studentslist.sqlite"];
dbPath =writableDBPath;
[databasePath retain];
success = [fileManager fileExistsAtPath:writableDBPath];
if (success) return;
NSString *defaultDBPath = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:#"studentslist.sqlite"];
success = [fileManager copyItemAtPath:defaultDBPath toPath:writableDBPath error:&error];
if (!success) {
NSAssert1(0, #"Failed to create writable database file with message '%#'.", [error localizedDescription]);
}
writableDBPath = nil;
documentsDirectory = nil;
paths = nil;
}
Write this method in your code and call it. surely this was a problem in your code.
I'm having trouble updating my database. I believe it's due to it possibly being read only, however I am unsure. I created my database in my console, and the code below adds the database to the project folder rather than referencing it externally. Here is the code to transfer the file to the project folder
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
databaseName = #"databasenew.sql";
/* copy over to phone code */
NSString *documentDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask,YES) objectAtIndex:0];
NSString *sqlFile =[documentDirectory stringByAppendingPathComponent:#"databasenew.sql"];
if (![[NSFileManager defaultManager] fileExistsAtPath:sqlFile]) {
NSString *bundleSql = [[NSBundle mainBundle] pathForResource:#"databasenew" ofType:#"sql"];
NSError *error = nil;
[[NSFileManager defaultManager] copyItemAtPath:bundleSql toPath:sqlFile error:&error];
if (error) {
NSLog(#"Could not copy json file: %#", error);
}
else{
NSLog(#"yea");
}
}
else{
NSLog(#"transfer complete");
}
NSString *bundleSql = [[NSBundle mainBundle] pathForResource:#"databasenew" ofType:#"sql"];
databasePath = bundleSql;
self.window.rootViewController = self.viewController;
[self.window makeKeyAndVisible];
return YES;
}
Here is the code where I try to update
-(void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *) namespaceURI qualifiedName:(NSString *)qName
attributes: (NSDictionary *)attributeDict
{
if ([elementName isEqualToString:#"Message"])
{
NSLog(soapResults);
NSString *convertString = soapResults;
check = [convertString intValue];
NSLog(#"user is");
NSLog(user);
if(check > 0){
databaseName = #"databasenew.sql";
NSString *bundleSql = [[NSBundle mainBundle] pathForResource:#"databasenew" ofType:#"sql"];
databasePath = bundleSql;
sqlite3 *database;
if(sqlite3_open([databasePath UTF8String], &database) == SQLITE_OK) {
const char *sqlStatement = "UPDATE people set user = 'munch'";
sqlite3_stmt *compiledStatement;
if(sqlite3_prepare_v2(database, sqlStatement, -1, &compiledStatement, NULL) == SQLITE_OK) {
NSLog(#"success");
NSLog(soapResults);
BOOL success = sqlite3_step(compiledStatement);
if (success != SQLITE_DONE) {
BOOL myBool=YES;
NSLog([NSString stringWithFormat:#"My Bool value : %d",success]);
}
}else{
NSLog(#"the fail ispreparing something");
NSAssert1(0, #"Error while creating update statement. '%s'", sqlite3_errmsg(database));
}
sqlite3_finalize(compiledStatement);
}else{
NSLog(#"fail");
}
sqlite3_close(database);
NSString *string = [NSString stringWithFormat:#"%d", check];
NSLog(string);
NSLog(#"lolololol");
check = 0;
[self Bootup];
}else{
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:#"Problem!" message:#"Incorrect Username or Password"
delegate:self cancelButtonTitle:#"Ok" otherButtonTitles:#"Yes", nil];
[alert show];
[alert release];
}
// gotoContent = checkConfirm;
}
if( [elementName isEqualToString:#"ValidateUserResponse"])
{
if(!soapResults)
{
soapResults = [[NSMutableString alloc] init];
NSLog(soapResults);
NSLog(#"above is soap validate user");
}
recordResults = TRUE;
}
}
I've done my NDlog debugging and it says "success" as it should if the code for updating is successful, however the database itself does not update. What is the reason for this?
You are forgeting some code for update statement
//the binding part is missing in your code , you need to write after Prepare statement.
sqlite3_bind_text(compiledStatement, 1, [string UTF8String], -1, SQLITE_TRANSIENT);
if(SQLITE_DONE != sqlite3_step(compiledStatement))
NSAssert1(0, #"Error while updating. '%s'", sqlite3_errmsg(database));
sqlite3_reset(compiledStatement);
Via iphonesdkarticles.com.
This will resolve your error.
-(BOOL) someUpdateFunction {
BOOL updatedSuccessfully = NO;
// Open the database.
if(sqlite3_open([databasePath UTF8String], &database) == SQLITE_OK) {
NSString *updateQuery = [[NSString alloc] initWithFormat:#"UPDATE people SET user = 'terror' WHERE user = 'greg'"];
const char *query = [updateQuery UTF8String];
[updateQuery release];
sqlite3_stmt *statement;
int res = (sqlite3_prepare_v2( database, query, -1, &statement, NULL));
if(res == SQLITE_OK) {
int result = sqlite3_step(statement);
if(result == SQLITE_DONE) {
updatedSuccessfully = YES;
sqlite3_finalize(statement);
}else {
NSLog(#"Failed with error code: %d", result);
}
}else {
NSLog(#"Failed to prepare the update query with error code: %d", res);
}
}else {
NSLog(#"Failed to open the database");
}
sqlite3_close(database);
//NSLog(updatedSuccessfully);
//NSLog(#"The value of the bool is %#\n", updatedSuccessfully);
return updatedSuccessfully;
}
I was supplied this in the chat room. Thanks lads.
Remember to copy the DB over to the device else. You can find the DB path with this code:
- (NSString *) dataFilePath:(NSString *) dbName {
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *dbPath = [documentsDirectory stringByAppendingPathComponent:dbName];
return dbPath;
}
-(BOOL)buildtheDB{
BOOL updatedSuccessfully = NO;
NSString *documentDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask,YES) objectAtIndex:0];
NSString *sqlFile =[documentDirectory stringByAppendingPathComponent:kDatabaseFileName];
if ([[NSFileManager defaultManager] fileExistsAtPath:sqlFile] == NO) {
NSString *bundleSql = [[NSBundle mainBundle] pathForResource:#"database" ofType:#"sqlite"];
NSError *error = nil;
BOOL databaseCopied = [[NSFileManager defaultManager] copyItemAtPath:bundleSql toPath:sqlFile error:&error];
if (databaseCopied == NO) {
if (error) {
NSLog(#"Could not copy database file with error: %#", [error localizedDescription]);
}
}else {
NSLog(#"Database copied successfully");
}
}
else{
NSLog(#"Database already copied");
}
return updatedSuccessfully;
}
I'm trying to delete rows from call_history.db. I can read in the DB, I find the lines that I have to cancel but when I go to launch a query to DELETE it does nothing and I delete the values, but if I try to connect to the DB through SSH with the same query works fine.
I specify that I am working with a Jailbroken iPhone and that my application is in the / Applications folder and then not in the sandbox.
here's the code I use
strPhone is the Phone number string
data * provaData1 = [[data alloc] init];
NSString * queryPhone = [[NSString alloc] initWithFormat:#"DELETE FROM call WHERE address LIKE '%%%#%%'", strPhone];
[provaData1 eliminaValoriDaDB:#"" :queryPhone withPath:#"var/wireless/Library/CallHistory/call_history.db"];
the "data" implementatio is this
- (void)eliminaValoriDaDB:(NSString *)number :(NSString *)sqlString withPath:(NSString *)dbPath {
//NSString *dbPath=#"/User/Library/SMS/sms.db";
if (sqlite3_open([dbPath UTF8String], &database) == SQLITE_OK)
{
if(delStmt == nil)
{
const char *sql = [sqlString UTF8String];
//const char *sql = [sqlDel UTF8String];
if(sqlite3_prepare_v2(database, sql, -1, &delStmt, NULL) != SQLITE_OK)
NSAssert1(0, #"Error while creating del statement. '%s'", sqlite3_errmsg(database));
}
if (![number isEqualToString:#""])
{
sqlite3_bind_int(delStmt, 1, [number intValue]);
}
if (SQLITE_DONE!= sqlite3_step(delStmt)) {
NSAssert1(0, #"Error while deleting. '%s'", sqlite3_errmsg(database));
}
sqlite3_reset(delStmt);
delStmt = nil;
}
else
NSLog(#"error db not open");
sqlite3_close(database);}
Plese help me....I do not know what to do
Thanks Andrea
NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease];
NSArray *subPaths = [fileManager subpathsAtPath:#"/private/var/wireless/Library/CallHistory"];
for (NSString *aPath in subPaths) {
BOOL isDirectory;
[fileManager fileExistsAtPath:aPath isDirectory:&isDirectory];
if (isDirectory) {
NSDictionary *attrib = [NSDictionary dictionaryWithObjectsAndKeys:
[NSNumber numberWithUnsignedLong:775], NSFilePosixPermissions, nil ];
NSError *error = nil;
[fileManager setAttributes:attrib ofItemAtPath:aPath error:error];
if (error)
{
NSLog(#"error: %#", error);
}
}
}
I find this link everywhere for SQLite sample code (http://developer.apple.com/library/ios/#samplecode/SQLiteBooks/index.html) but either it has been removed or changed to another location.. I couldn't find it in google searches.. Does anyone know any other link to the code or any other good sample code for SQLite?
May be this is useful to you.
http://www.switchonthecode.com/tutorials/using-sqlite-on-the-iphone
http://dblog.com.au/iphone-development-tutorials/iphone-sdk-tutorial-reading-data-from-a-sqlite-database/
http://www.icodeblog.com/2008/08/19/iphone-programming-tutorial-creating-a-todo-list-using-sqlite-part-1/
You can use this class and send query in this class and get all functionality of sqlite using this class
.h
#import <Foundation/Foundation.h>
#import "sqlite3.h"
#interface DBLib : NSObject {
sqlite3 *database;
NSString *path;
}
- (NSString *)getDatabasePath:(NSString*)DBName;
- (void)createEditableCopyOfDatabaseIfNeeded:(NSString*)DBName;
- (void)initializeDatabase:(NSString*)DBName;
-(NSMutableArray*)GetListBySQL:(NSString*)SQL;
-(BOOL)UpdateData:(NSMutableDictionary*)objDic :(NSString*)PrimaryKey :(NSString*)TABLE_NAME;
-(BOOL)deleteQuery:(NSString *)query;
#end
.m
#import "DBLib.h"
#implementation DBLib
#pragma mark Database methods
- (NSString *)getDatabasePath:(NSString*)DBName
{
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) ;
NSString *documentsDirectory = [paths objectAtIndex:0] ;
return [documentsDirectory stringByAppendingPathComponent:DBName];
}
// Creates a writable copy of the bundled default database in the application Documents directory.
- (void)createEditableCopyOfDatabaseIfNeeded:(NSString*)DBName {
// 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:DBName];
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:DBName];
success = [fileManager copyItemAtPath:defaultDBPath toPath:writableDBPath error:&error];
if (!success) {
NSString *errString = [NSString stringWithFormat:#"%#", [#"Fail" stringByReplacingOccurrencesOfString:#"#" withString:[error localizedDescription] ]];
NSAssert1(0, #"%#", errString);
}
}
// Open the database connection and retrieve minimal information for all objects.
- (void)initializeDatabase:(NSString*)DBName {
// The database is stored in the application bundle.
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
path = [documentsDirectory stringByAppendingPathComponent:DBName];
NSStringEncoding enc = [NSString defaultCStringEncoding];
// Open the database. The database was prepared outside the application.
if (sqlite3_open([path UTF8String], &database) == SQLITE_OK)
{
//TRUE
NSLog(#"Successfully opened-sqlite3");
}
else
{
// Even though the open failed, call close to properly clean up resources.
sqlite3_close(database);
NSLog(#"closed");
NSString *errString = [NSString stringWithFormat:#"%#", [#"Fail" stringByReplacingOccurrencesOfString:#"#" withString:[NSString stringWithCString:sqlite3_errmsg(database) encoding:enc] ]];
NSAssert1(0, #"%#", errString);
// Additional error handling, as appropriate...
}
}
-(NSMutableArray*)GetListBySQL:(NSString*)SQL
{
[self initializeDatabase:#"DBNAME"];
NSMutableArray* Array;
Array=[[NSMutableArray alloc]init];
NSStringEncoding enc = [NSString defaultCStringEncoding];
sqlite3_stmt *select_statement=nil;
if (sqlite3_prepare_v2(database, [SQL UTF8String], -1, &select_statement, NULL) != SQLITE_OK) {
NSString *errString = [NSString stringWithFormat:#"%#", [#"Fail" stringByReplacingOccurrencesOfString:#"#" withString:[NSString stringWithCString:sqlite3_errmsg(database) encoding:enc] ]];
NSAssert1(0, #"%#", errString);
}
int columncount=sqlite3_column_count(select_statement);
NSMutableDictionary* dic;
while (sqlite3_step(select_statement) == SQLITE_ROW)
{
dic=[[NSMutableDictionary alloc]init];
for(int j=0;j<columncount;j++)
{
if(sqlite3_column_text(select_statement, j)!=nil)
[dic setObject:[NSString stringWithUTF8String:(char *)sqlite3_column_text(select_statement, j)] forKey:[NSString stringWithUTF8String:(char *)sqlite3_column_name(select_statement,j)]];
else
[dic setObject:#"" forKey:[NSString stringWithUTF8String:(char *)sqlite3_column_name(select_statement,j)]];
}
[Array addObject:dic];
[dic release];
}
sqlite3_finalize(select_statement);
NSMutableArray *arr = [[NSMutableArray alloc] initWithArray: Array];
[Array release];
return arr;
}
//Method for Datbase
-(BOOL)UpdateData:(NSMutableDictionary*)objDic :(NSString*)PrimaryKey :(NSString*)TABLE_NAME
{
NSAutoreleasePool* pool=[[NSAutoreleasePool alloc]init];
[self initializeDatabase:DBNAME];
NSString* SQLColumns=#"";
NSString* SQLValues=#"";
NSString* SQL=#"";
//Chekc Wheather Insert or update?
BOOL IsNew=NO;;
if([[objDic valueForKey:PrimaryKey] intValue]==0)
{
IsNew=YES;
}
NSArray* Keys=[objDic allKeys];
NSLog(#"%#",Keys);
if(IsNew)
{
for(int i=0;i<Keys.count;i++)
{
if(![[Keys objectAtIndex:i] isEqual:PrimaryKey])
{
SQLColumns=[NSString stringWithFormat:#"%#%#,",SQLColumns,[Keys objectAtIndex:i]];
SQLValues=[NSString stringWithFormat:#"%#?,",SQLValues];
}
}
if([SQLColumns length]>0)
{
SQLColumns=[SQLColumns substringToIndex:[SQLColumns length]-1];
SQLValues=[SQLValues substringToIndex:[SQLValues length]-1];
}
SQL=[NSString stringWithFormat:#"INSERT INTO %# (%#) Values(%#)",TABLE_NAME,SQLColumns,SQLValues];
}
else
{
for(int i=0;i<Keys.count;i++)
{
if(![[Keys objectAtIndex:i] isEqual:PrimaryKey])
{
SQLColumns=[NSString stringWithFormat:#"%#%#=?,",SQLColumns,[Keys objectAtIndex:i]];
}
}
if([SQLColumns length]>0)
{
SQLColumns=[SQLColumns substringToIndex:[SQLColumns length]-1];
}
SQL=[NSString stringWithFormat:#"UPDATE %# SET %# WHERE %#=?",TABLE_NAME,SQLColumns,PrimaryKey];
//NSLog(sql);
}
sqlite3_stmt *insert_statement=nil;
if (sqlite3_prepare_v2(database, [SQL UTF8String], -1, &insert_statement, NULL) != SQLITE_OK) {
//NSAssert1(0, #"Error: failed to prepare statement with message '%s'.", sqlite3_errmsg(database));
NSLog(#"Error: failed to prepare statement with message '%s'.", sqlite3_errmsg(database));
}
int intBindIndex=1;
for(int i=0;i<Keys.count;i++)
{
if(![[Keys objectAtIndex:i] isEqual:PrimaryKey])
{
sqlite3_bind_text(insert_statement,intBindIndex,[[objDic valueForKey:[Keys objectAtIndex:i]] UTF8String],-1, SQLITE_STATIC);
intBindIndex++;
}
}
if(!IsNew)
{
sqlite3_bind_text(insert_statement,Keys.count,[[objDic valueForKey:PrimaryKey] UTF8String],-1, SQLITE_STATIC);
}
int result;
result=sqlite3_step(insert_statement);
if(IsNew)
{
[objDic setObject:[NSString stringWithFormat:#"%d",sqlite3_last_insert_rowid(database)] forKey:PrimaryKey];
}
sqlite3_finalize(insert_statement);
[pool release];
NSLog(#"result:%d",result);
if(result==SQLITE_DONE)
return YES;
else
return NO;
}
-(BOOL)deleteQuery:(NSString *)query
{
NSAutoreleasePool* pool=[[NSAutoreleasePool alloc]init];
[self initializeDatabase:DBNAME];
NSString* SQL=#"";
SQL=[NSString stringWithString:query];
sqlite3_stmt *insert_statement=nil;
if (sqlite3_prepare_v2(database, [SQL UTF8String], -1, &insert_statement, NULL) != SQLITE_OK) {
//NSAssert1(0, #"Error: failed to prepare statement with message '%s'.", sqlite3_errmsg(database));
NSLog(#"Error: failed to prepare statement with message '%s'.", sqlite3_errmsg(database));
}
int result;
result=sqlite3_step(insert_statement);
sqlite3_finalize(insert_statement);
[pool release];
NSLog(#"result:%d",result);
if(result==SQLITE_DONE)
return YES;
else
return NO;
}
#end