aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/src/protocol.c
diff options
context:
space:
mode:
authorEgor Tensin <Egor.Tensin@gmail.com>2023-07-17 23:03:59 +0200
committerEgor Tensin <Egor.Tensin@gmail.com>2023-07-18 00:38:50 +0200
commite05f02acd583797ceb449fc501d371d45a4293c1 (patch)
tree491322cf633b67918f0361c1ce986f6b690844bc /src/protocol.c
parentdocker: sanitize package dependencies (diff)
downloadcimple-e05f02acd583797ceb449fc501d371d45a4293c1.tar.gz
cimple-e05f02acd583797ceb449fc501d371d45a4293c1.zip
switch to JSON-RPC as message format
Instead of the weird `struct msg` I had, I switched to the JSON-RPC format. It's basically the same, but has a well-defined semantics in case of errors.
Diffstat (limited to '')
-rw-r--r--src/protocol.c163
1 files changed, 106 insertions, 57 deletions
diff --git a/src/protocol.c b/src/protocol.c
index 5d1903a..8ee57e1 100644
--- a/src/protocol.c
+++ b/src/protocol.c
@@ -7,132 +7,181 @@
#include "protocol.h"
#include "base64.h"
+#include "compiler.h"
#include "const.h"
-#include "log.h"
-#include "msg.h"
+#include "json_rpc.h"
#include "process.h"
#include "run_queue.h"
-#include "string.h"
#include <stddef.h>
-#include <stdio.h>
+#include <stdint.h>
#include <stdlib.h>
-static int check_msg_length(const struct msg *msg, size_t expected)
+static const char *const run_key_id = "id";
+static const char *const run_key_url = "url";
+static const char *const run_key_rev = "rev";
+
+int run_request_create(struct jsonrpc_request **request, const struct run *run)
{
- size_t actual = msg_get_length(msg);
+ int ret = 0;
- if (actual != expected) {
- log_err("Invalid number of arguments for a message: %zu\n", actual);
- msg_dump(msg);
- return -1;
- }
+ ret = jsonrpc_request_create(request, 1, CMD_RUN, NULL);
+ if (ret < 0)
+ return ret;
+ ret = jsonrpc_request_set_param_string(*request, run_key_url, run_get_url(run));
+ if (ret < 0)
+ goto free_request;
+ ret = jsonrpc_request_set_param_string(*request, run_key_rev, run_get_rev(run));
+ if (ret < 0)
+ goto free_request;
- return 0;
+ return ret;
+
+free_request:
+ jsonrpc_request_destroy(*request);
+
+ return ret;
}
-int msg_run_parse(const struct msg *msg, struct run **run)
+int run_request_parse(const struct jsonrpc_request *request, struct run **run)
{
- int ret = check_msg_length(msg, 3);
+ int ret = 0;
+
+ const char *url = NULL;
+ ret = jsonrpc_request_get_param_string(request, run_key_url, &url);
+ if (ret < 0)
+ return ret;
+ const char *rev = NULL;
+ ret = jsonrpc_request_get_param_string(request, run_key_rev, &rev);
if (ret < 0)
return ret;
- const char **argv = msg_get_strings(msg);
- /* We don't know the ID yet. */
- return run_create(run, 0, argv[1], argv[2]);
+ return run_create(run, 0, url, rev);
}
-int msg_new_worker_create(struct msg **msg)
+int new_worker_request_create(struct jsonrpc_request **request)
{
- static const char *argv[] = {CMD_NEW_WORKER, NULL};
- return msg_from_argv(msg, argv);
+ return jsonrpc_notification_create(request, CMD_NEW_WORKER, NULL);
}
-int msg_start_create(struct msg **msg, const struct run *run)
+int new_worker_request_parse(UNUSED const struct jsonrpc_request *request)
{
- char id[16];
- snprintf(id, sizeof(id), "%d", run_get_id(run));
-
- const char *argv[] = {CMD_START, id, run_get_url(run), run_get_rev(run), NULL};
-
- return msg_from_argv(msg, argv);
+ return 0;
}
-int msg_start_parse(const struct msg *msg, struct run **run)
+int start_request_create(struct jsonrpc_request **request, const struct run *run)
{
int ret = 0;
- ret = check_msg_length(msg, 4);
+ ret = jsonrpc_notification_create(request, CMD_START, NULL);
if (ret < 0)
return ret;
+ ret = jsonrpc_request_set_param_int(*request, run_key_id, run_get_id(run));
+ if (ret < 0)
+ goto free_request;
+ ret = jsonrpc_request_set_param_string(*request, run_key_url, run_get_url(run));
+ if (ret < 0)
+ goto free_request;
+ ret = jsonrpc_request_set_param_string(*request, run_key_rev, run_get_rev(run));
+ if (ret < 0)
+ goto free_request;
+
+ return ret;
- const char **argv = msg_get_strings(msg);
+free_request:
+ jsonrpc_request_destroy(*request);
+
+ return ret;
+}
- int id = 0;
+int start_request_parse(const struct jsonrpc_request *request, struct run **run)
+{
+ int ret = 0;
- ret = string_to_int(argv[1], &id);
+ int64_t id = 0;
+ ret = jsonrpc_request_get_param_int(request, run_key_id, &id);
+ if (ret < 0)
+ return ret;
+ const char *url = NULL;
+ ret = jsonrpc_request_get_param_string(request, run_key_url, &url);
+ if (ret < 0)
+ return ret;
+ const char *rev = NULL;
+ ret = jsonrpc_request_get_param_string(request, run_key_rev, &rev);
if (ret < 0)
return ret;
- return run_create(run, id, argv[2], argv[3]);
+ return run_create(run, (int)id, url, rev);
}
-int msg_finished_create(struct msg **msg, int run_id, const struct proc_output *output)
+static const char *const finished_key_run_id = "run_id";
+static const char *const finished_key_ec = "exit_code";
+static const char *const finished_key_data = "output";
+
+int finished_request_create(struct jsonrpc_request **request, int run_id,
+ const struct proc_output *output)
{
int ret = 0;
- char id[16];
- char ec[16];
-
- snprintf(id, sizeof(id), "%d", run_id);
- snprintf(ec, sizeof(ec), "%d", output->ec);
+ ret = jsonrpc_notification_create(request, CMD_FINISHED, NULL);
+ if (ret < 0)
+ return ret;
+ ret = jsonrpc_request_set_param_int(*request, finished_key_run_id, run_id);
+ if (ret < 0)
+ goto free_request;
+ ret = jsonrpc_request_set_param_int(*request, finished_key_ec, output->ec);
+ if (ret < 0)
+ goto free_request;
char *b64data = NULL;
-
ret = base64_encode(output->data, output->data_size, &b64data);
if (ret < 0)
- return ret;
-
- const char *argv[] = {CMD_FINISHED, id, ec, b64data, NULL};
+ goto free_request;
- ret = msg_from_argv(msg, argv);
+ ret = jsonrpc_request_set_param_string(*request, finished_key_data, b64data);
+ free(b64data);
if (ret < 0)
- goto free_b64data;
+ goto free_request;
-free_b64data:
- free(b64data);
+ return ret;
+
+free_request:
+ jsonrpc_request_destroy(*request);
return ret;
}
-int msg_finished_parse(const struct msg *msg, int *run_id, struct proc_output **_output)
+int finished_request_parse(const struct jsonrpc_request *request, int *_run_id,
+ struct proc_output **_output)
{
int ret = 0;
- ret = check_msg_length(msg, 4);
- if (ret < 0)
- return ret;
-
- const char **argv = msg_get_strings(msg);
-
struct proc_output *output = NULL;
ret = proc_output_create(&output);
if (ret < 0)
return ret;
- ret = string_to_int(argv[1], run_id);
+ int64_t run_id = 0;
+ ret = jsonrpc_request_get_param_int(request, finished_key_run_id, &run_id);
if (ret < 0)
goto free_output;
- ret = string_to_int(argv[2], &output->ec);
+
+ int64_t ec = -1;
+ ret = jsonrpc_request_get_param_int(request, finished_key_ec, &ec);
if (ret < 0)
goto free_output;
+ output->ec = (int)ec;
- const char *b64data = argv[3];
+ const char *b64data = NULL;
+ ret = jsonrpc_request_get_param_string(request, finished_key_data, &b64data);
+ if (ret < 0)
+ goto free_output;
ret = base64_decode(b64data, &output->data, &output->data_size);
if (ret < 0)
goto free_output;
+ *_run_id = (int)run_id;
*_output = output;
return ret;