diff lib/db.c @ 20:f98ea578b1ef

misc: revamp database
author David Demelier <markand@malikania.fr>
date Tue, 19 Jul 2022 21:52:42 +0200
parents de4bf839b565
children dd078aea5d02
line wrap: on
line diff
--- a/lib/db.c	Fri Jul 15 11:11:48 2022 +0200
+++ b/lib/db.c	Tue Jul 19 21:52:42 2022 +0200
@@ -47,69 +47,42 @@
 
 static sqlite3 *db;
 
-typedef void (*unpacker)(sqlite3_stmt *, struct db_ctx *, void *);
-
-struct str {
-	char *str;
-	struct str *next;
-};
-
 struct list {
-	unpacker unpack;
+	void (*unpack)(sqlite3_stmt *, void *);
 	void *data;
 	size_t datasz;
 	size_t elemwidth;
-	struct db_ctx *ctx;
 };
 
-static const char *
-strlist_add(struct db_ctx *ctx, const char *text)
+static void
+project_unpacker(sqlite3_stmt *stmt, void *data)
 {
-	struct str *s, *list = ctx->handle;
+	struct project *project = data;
 
-	s = util_calloc(1, sizeof (*s));
-	s->str = util_strdup(text);
-	LL_APPEND(list, s);
-
-	return s->str;
+	project->id = sqlite3_column_int(stmt, 0);
+	project->name = util_strdup(CHAR(sqlite3_column_text(stmt, 1)));
+	project->desc = util_strdup(CHAR(sqlite3_column_text(stmt, 2)));
+	project->url = util_strdup(CHAR(sqlite3_column_text(stmt, 3)));
+	project->script = util_strdup(CHAR(sqlite3_column_text(stmt, 4)));
 }
 
 static void
-strlist_free(struct db_ctx *ctx)
+worker_unpacker(sqlite3_stmt *stmt, void *data)
 {
-	struct str *s, *tmp, *list = ctx->handle;
+	struct worker *w = data;
 
-	LL_FOREACH_SAFE(list, s, tmp) {
-		free(s->str);
-		free(s);
-	}
-
-	ctx->handle = NULL;
+	w->id = sqlite3_column_int(stmt, 0);
+	w->name = util_strdup(CHAR(sqlite3_column_text(stmt, 1)));
+	w->desc = util_strdup(CHAR(sqlite3_column_text(stmt, 2)));
 }
 
 static void
-project_unpacker(sqlite3_stmt *stmt, struct db_ctx *ctx, struct project *project)
+job_unpacker(sqlite3_stmt *stmt, void *data)
 {
-	project->id = sqlite3_column_int(stmt, 0);
-	project->name = strlist_add(ctx, CHAR(sqlite3_column_text(stmt, 1)));
-	project->desc = strlist_add(ctx, CHAR(sqlite3_column_text(stmt, 2)));
-	project->url = strlist_add(ctx, CHAR(sqlite3_column_text(stmt, 3)));
-	project->script = strlist_add(ctx, CHAR(sqlite3_column_text(stmt, 4)));
-}
+	struct job *job = data;
 
-static void
-worker_unpacker(sqlite3_stmt *stmt, struct db_ctx *ctx, struct worker *w)
-{
-	w->id = sqlite3_column_int(stmt, 0);
-	w->name = strlist_add(ctx, CHAR(sqlite3_column_text(stmt, 1)));
-	w->desc = strlist_add(ctx, CHAR(sqlite3_column_text(stmt, 2)));
-}
-
-static void
-job_unpacker(sqlite3_stmt *stmt, struct db_ctx *ctx, struct job *job)
-{
 	job->id = sqlite3_column_int(stmt, 0);
-	job->tag = strlist_add(ctx, CHAR(sqlite3_column_text(stmt, 1)));
+	job->tag = util_strdup(CHAR(sqlite3_column_text(stmt, 1)));
 	job->project_id = sqlite3_column_int(stmt, 2);
 }
 
@@ -121,6 +94,9 @@
 		case 'i':
 			sqlite3_bind_int(stmt, index++, va_arg(ap, int));
 			break;
+		case 'j':
+			sqlite3_bind_int64(stmt, index++, va_arg(ap, intmax_t));
+			break;
 		case 's':
 			sqlite3_bind_text(stmt, index++, va_arg(ap, const char *), -1, SQLITE_STATIC);
 			break;
@@ -197,8 +173,6 @@
 	ssize_t ret = -1;
 	size_t tot = 0;
 
-	sel->ctx->handle = NULL;
-
 	if (sqlite3_prepare(db, sql, -1, &stmt, NULL) != SQLITE_OK)
 		return log_warn("db: %s", sqlite3_errmsg(db)), -1;
 
@@ -207,15 +181,12 @@
 	va_end(ap);
 
 	while (tot < sel->datasz && (step = sqlite3_step(stmt)) == SQLITE_ROW)
-		sel->unpack(stmt, sel->ctx, (unsigned char *)sel->data + (tot++ * sel->elemwidth));
+		sel->unpack(stmt, (unsigned char *)sel->data + (tot++ * sel->elemwidth));
 
 	if (step == SQLITE_OK || step == SQLITE_DONE || step == SQLITE_ROW)
 		ret = tot;
-	else {
+	else
 		memset(sel->data, 0, sel->datasz * sel->elemwidth);
-		strlist_free(sel->ctx->handle);
-		sel->ctx->handle = NULL;
-	}
 
 	sqlite3_finalize(stmt);
 
@@ -256,45 +227,42 @@
 }
 
 ssize_t
-db_project_list(struct db_ctx *ctx, struct project *projects, size_t projectsz)
+db_project_list(struct project *projects, size_t projectsz)
 {
 	struct list sel = {
-		.unpack = (unpacker)project_unpacker,
+		.unpack = project_unpacker,
 		.data = projects,
 		.datasz = projectsz,
 		.elemwidth = sizeof (*projects),
-		.ctx = ctx
 	};
 
 	return list(&sel, CHAR(sql_project_list), "z", projectsz);
 }
 
 int
-db_project_find(struct db_ctx *ctx, struct project *project)
+db_project_find(struct project *project, const char *name)
 {
 	struct list sel = {
-		.unpack = (unpacker)project_unpacker,
+		.unpack = project_unpacker,
 		.data = project,
 		.datasz = 1,
 		.elemwidth = sizeof (*project),
-		.ctx = ctx
 	};
 
-	return list(&sel, CHAR(sql_project_find), "s", project->name) == 1 ? 0 : -1;
+	return list(&sel, CHAR(sql_project_find), "s", name) == 1 ? 0 : -1;
 }
 
 int
-db_project_find_id(struct db_ctx *ctx, struct project *project)
+db_project_find_id(struct project *project, intmax_t id)
 {
 	struct list sel = {
-		.unpack = (unpacker)project_unpacker,
+		.unpack = project_unpacker,
 		.data = project,
 		.datasz = 1,
 		.elemwidth = sizeof (*project),
-		.ctx = ctx
 	};
 
-	return list(&sel, CHAR(sql_project_find_id), "i", project->id) == 1 ? 0 : -1;
+	return list(&sel, CHAR(sql_project_find_id), "i", id) == 1 ? 0 : -1;
 }
 
 int
@@ -306,48 +274,44 @@
 }
 
 ssize_t
-db_worker_list(struct db_ctx *ctx, struct worker *wk, size_t wksz)
+db_worker_list(struct worker *wk, size_t wksz)
 {
-	assert(ctx);
 	assert(wk);
 
 	struct list sel = {
-		.unpack = (unpacker)worker_unpacker,
+		.unpack = worker_unpacker,
 		.data = wk,
 		.datasz = wksz,
 		.elemwidth = sizeof (*wk),
-		.ctx = ctx
 	};
 
 	return list(&sel, CHAR(sql_worker_list), "z", wksz);
 }
 
 int
-db_worker_find(struct db_ctx *ctx, struct worker *wk)
+db_worker_find(struct worker *wk, const char *name)
 {
 	struct list sel = {
-		.unpack = (unpacker)worker_unpacker,
+		.unpack = worker_unpacker,
 		.data = wk,
 		.datasz = 1,
 		.elemwidth = sizeof (*wk),
-		.ctx = ctx
 	};
 
-	return list(&sel, CHAR(sql_worker_find), "s", wk->name) == 1 ? 0 : -1;
+	return list(&sel, CHAR(sql_worker_find), "s", name) == 1 ? 0 : -1;
 }
 
 int
-db_worker_find_id(struct db_ctx *ctx, struct worker *wk)
+db_worker_find_id(struct worker *wk, intmax_t id)
 {
 	struct list sel = {
-		.unpack = (unpacker)worker_unpacker,
+		.unpack = worker_unpacker,
 		.data = wk,
 		.datasz = 1,
 		.elemwidth = sizeof (*wk),
-		.ctx = ctx
 	};
 
-	return list(&sel, CHAR(sql_worker_find_id), "i", wk->id) == 1 ? 0 : -1;
+	return list(&sel, CHAR(sql_worker_find_id), "i", id) == 1 ? 0 : -1;
 }
 
 int
@@ -360,17 +324,15 @@
 }
 
 ssize_t
-db_job_todo(struct db_ctx *ctx, struct job *jobs, size_t jobsz, int worker_id)
+db_job_todo(struct job *jobs, size_t jobsz, int worker_id)
 {
-	assert(ctx);
 	assert(jobs);
 
 	struct list sel = {
-		.unpack = (unpacker)job_unpacker,
+		.unpack = job_unpacker,
 		.data = jobs,
 		.datasz = jobsz,
 		.elemwidth = sizeof (*jobs),
-		.ctx = ctx
 	};
 
 	return list(&sel, CHAR(sql_job_todo), "iiz", worker_id, worker_id, jobsz);
@@ -393,12 +355,3 @@
 		db = NULL;
 	}
 }
-
-void
-db_ctx_finish(struct db_ctx *ctx)
-{
-	if (ctx->handle) {
-		strlist_free(ctx->handle);
-		ctx->handle = NULL;
-	}
-}