#include "../../include/database.h" #include "../../include/package.h" #include "../../include/error.h" #include "../../include/util.h" #include #include #include #include char *queries[] = { // QUERY_CREATE_PACKAGE_TABLE "CREATE TABLE IF NOT EXISTS packages (" \ " name TEXT PRIMARY KEY NOT NULL," \ " version TEXT NOT NULL," \ " desc TEXT NOT NULL," \ " size INT NOT NULL," \ " depends TEXT NOT NULL);", // QUERY_INSERT_PACKAGE_SINGLE "INSERT INTO packages VALUES (?, ?, ?, ?, ?)", // QUERY_SELECT_PACKAGE_SINGLE_1 "SELECT * FROM packages WHERE name = ?", // QUERY_SELECT_PACKAGE_SINGLE_2 "SELECT * FROM packages WHERE name = ? AND version = ?", // QUERY_DELETE_PACKAGE_SINGLE "DELETE FROM packages WHERE name = ?", // QUERY_SELECT_PACKAGE_ALL "SELECT * FROM packages", // QUERY_CREATE_FILE_TABLE "CREATE TABLE IF NOT EXISTS files (" \ " path TEXT PRIMARY KEY NOT NULL," \ " hash TEXT NOT NULL," \ " keep INT NOT NULL," \ " package TEXT NOT NULL);", // QUERY_INSERT_FILE_SINGLE "INSERT INTO files VALUES (?, ?, ?, ?)", // QUERY_DELETE_FILE_ALL "DELETE FROM files WHERE package = ? AND keep = 0", // QUERY_DELETE_FILE_SINGLE "DELETE FROM files WHERE path = ?", // QUERY_SELECT_FILE_ALL "SELECT * FROM files WHERE package = ?", // QUERY_SELECT_FILE_SINGLE "SELECT * FROM files WHERE path = ?", // QUERY_UPDATE_FILE_1 "UPDATE files SET keep = 1 WHERE path = ?", // QUERY_UPDATE_FILE_2 "UPDATE files SET keep = 0 WHERE path = ?", }; lm_database_t *lm_database_new(char *path){ lm_database_t *db = malloc(sizeof(lm_database_t)); char *err = NULL; bzero(db, sizeof(lm_database_t)); if(exists(path, NULL) && (is_file(path) || !can_read(path) || !can_write(path))){ lm_error_set(LM_ERR_DbCantAccess); return NULL; } if(!exists(path, NULL) && !mkdir_ifnot(path)){ lm_error_set(LM_ERR_DbCantAccess); return NULL; } size_t pathlen = strlen(path); char packagesdb[pathlen+20], filesdb[pathlen+20]; join(packagesdb, path, "packages.db"); join(filesdb, path, "files.db"); if(sqlite3_open(packagesdb, &db->entries_db)){ pdebug(__func__, "(%s) failed to open databse: %s", packagesdb, sqlite3_errmsg(db->entries_db)); lm_error_set(LM_ERR_DbSqlOpenFail); return NULL; } if(sqlite3_open(filesdb, &db->files_db)){ pdebug(__func__, "(%s) failed to open databse: %s", filesdb, sqlite3_errmsg(db->files_db)); lm_error_set(LM_ERR_DbSqlOpenFail); return NULL; } if(sqlite3_exec(db->entries_db, queries[QUERY_CREATE_ENTRY_TABLE], NULL, 0, &err) != SQLITE_OK){ pdebug(__func__, "(%s) failed to create packages table: %s", packagesdb, err); lm_error_set(LM_ERR_DbSqlCreateFail); sqlite3_free(err); db->entries_db = NULL; } if(sqlite3_exec(db->files_db, queries[QUERY_CREATE_FILE_TABLE], NULL, 0, &err) != SQLITE_OK){ pdebug(__func__, "(%s) failed to create files table: %s", filesdb, err); lm_error_set(LM_ERR_DbSqlCreateFail); sqlite3_free(err); db->files_db = NULL; } db->dir = strdup(path); return db; } void lm_database_free(lm_database_t *db){ if(NULL != db->entries_st) sqlite3_finalize(db->entries_st); if(NULL != db->files_st) sqlite3_finalize(db->files_st); sqlite3_close(db->entries_db); sqlite3_close(db->files_db); free(db->dir); free(db); } bool lm_database_step_all(sqlite3_stmt *st){ int rc = 0; while((rc = sqlite3_step(st)) == SQLITE_ROW) continue; return rc == SQLITE_DONE; }