Skip to content

Commit

Permalink
Merge pull request #3 from vstan02/rc2
Browse files Browse the repository at this point in the history
Realease 1.0.0
  • Loading branch information
vstan02 authored Jun 27, 2021
2 parents 5766d74 + d63bcd8 commit 0c3e378
Show file tree
Hide file tree
Showing 13 changed files with 141 additions and 120 deletions.
16 changes: 8 additions & 8 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,24 +20,24 @@
Here is an example of usage (for the full version see [demo/main.c](https://github.com/vstan02/conix/blob/master/demo/main.c) file):
```c
// Creating an new cli instance:
CnxApp app = { "my_app", "2.8.1" };
CnxCli* cli = cnx_cli_init(app);
cnx_cli_t* cli = cnx_cli_init((cnx_app_t) { "my_app", "2.8.1" });

// Adding some options for handling:
cnx_cli_add(cli, 4, (CnxOption[]) {
// CnxOption -> { name, description, handler, payload }.
{ "-a, --about", "Display something", about_option, (void*)app.name },
cnx_cli_add(cli, 5, (cnx_option_t[]) {
// cnx_option_t -> { name, description, handler, payload }.
{ "-a, --about", "Display something", about_option, NULL },
{ "-p, --print", "Display passed arguments", print_args_option, NULL },

// Handlers for "-v, --version" and "-h, --help" are added
// by default, but you can add your own handlers for them.
{ "-v, --version", "Display version", version_option, &app },
{ "-v, --version", "Display version", version_option, NULL },

// Handler for "--default" is called when are no arguments passed.
{ "--default", "Default option", index_option, (void*)app.name },
{ "--default", "Default option", index_option, NULL },

// Handler for "*" is called when is passed an unknown cli option.
// By default it has the same handler as the "-h, --help" option.
{ "*", NULL, not_found_option, (void*)app.name }
{ "*", NULL, not_found_option, NULL }
});

// Running for some command line arguments:
Expand Down
38 changes: 22 additions & 16 deletions demo/main.c
Original file line number Diff line number Diff line change
@@ -1,43 +1,49 @@
#include <stdio.h>
#include <conix.h>

void index_option(void* payload) {
printf("Welcome to %s!\n", (char*)payload);
void index_option(cnx_ctx_t* ctx, void* payload) {
printf("Welcome to %s!\n", ctx->app.name);
}

void about_option(void* payload) {
printf("%s is a simple app created with conix!\n", (char*)payload);
void about_option(cnx_ctx_t* ctx, void* payload) {
printf("%s is a simple app created with conix!\n", ctx->app.name);
}

void version_option(void* payload) {
CnxApp* app = (CnxApp*)payload;
printf("%s -> %s\n", app->name, app->version);
void version_option(cnx_ctx_t* ctx, void* payload) {
printf("%s -> %s\n", ctx->app.name, ctx->app.version);
}

void not_found_option(void* payload) {
printf("%s: Invalid option!\n", (char*)payload);
void print_args_option(cnx_ctx_t* ctx, void* payload) {
printf("Total arguments: %zu\n", ctx->argc - 1);
for (size_t i = 1; i < ctx->argc; ++i) {
printf("%zu -> %s\n", i, ctx->argv[i]);
}
}

void not_found_option(cnx_ctx_t* ctx, void* payload) {
printf("%s: Invalid option!\n", ctx->app.name);
}

int main(int argc, const char** argv) {
// Creating an new cli instance:
CnxApp app = { "my_app", "2.8.1" };
CnxCli* cli = cnx_cli_init(app);
cnx_cli_t* cli = cnx_cli_init((cnx_app_t) { "my_app", "2.8.1" });

// Adding some options for handling:
cnx_cli_add(cli, 4, (CnxOption[]) {
cnx_cli_add(cli, 5, (cnx_option_t[]) {
// CnxOption -> { name, description, handler, payload }.
{ "-a, --about", "Display something", about_option, (void*)app.name },
{ "-a, --about", "Display something", about_option, NULL },
{ "-p, --print", "Display passed arguments", print_args_option, NULL },

// Handlers for "-v, --version" and "-h, --help" are added
// by default, but you can add your own handlers for them.
{ "-v, --version", "Display version", version_option, &app },
{ "-v, --version", "Display version", version_option, NULL },

// Handler for "--default" is called when are no arguments passed
{ "--default", "Default option", index_option, (void*)app.name },
{ "--default", "Default option", index_option, NULL },

// Handler for "*" is called when is passed an unknown cli option.
// By default it has the same handler as the "-h, --help" option.
{ "*", NULL, not_found_option, (void*)app.name }
{ "*", NULL, not_found_option, NULL }
});

// Running for some command line arguments:
Expand Down
28 changes: 18 additions & 10 deletions include/conix.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,27 +22,35 @@

#include <stddef.h>

typedef struct t_CnxCli CnxCli;
typedef struct t_CnxApp CnxApp;
typedef struct t_CnxOption CnxOption;
typedef struct cnx_cli cnx_cli_t;
typedef struct cnx_app cnx_app_t;
typedef struct cnx_ctx cnx_ctx_t;
typedef struct cnx_option cnx_option_t;
typedef void(*cnx_handle_t)(cnx_ctx_t*, void*);

struct t_CnxApp {
struct cnx_app {
const char* name;
const char* version;
};

struct t_CnxOption {
struct cnx_ctx {
cnx_app_t app;
size_t argc;
const char** argv;
};

struct cnx_option {
const char* name;
const char* description;
void (*handle)(void*);
cnx_handle_t handle;
void* payload;
};

extern CnxCli* cnx_cli_init(CnxApp app);
extern void cnx_cli_free(CnxCli* cli);
extern cnx_cli_t* cnx_cli_init(cnx_app_t app);
extern void cnx_cli_free(cnx_cli_t* cli);

extern void cnx_cli_run(CnxCli* cli, size_t argc, const char* argv[]);
extern void cnx_cli_run(cnx_cli_t* cli, size_t argc, const char* argv[]);

extern void cnx_cli_add(CnxCli* cli, size_t count, CnxOption options[]);
extern void cnx_cli_add(cnx_cli_t* cli, size_t count, cnx_option_t options[]);

#endif // CONIX_CONIX_H
2 changes: 1 addition & 1 deletion src/common.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@
} \
} while (0)

typedef void (*handle_t)(void*);
typedef void (*handle_t)(void*, void*);

extern char* str_copy(const char* string);

Expand Down
48 changes: 26 additions & 22 deletions src/conix.c
Original file line number Diff line number Diff line change
Expand Up @@ -24,55 +24,59 @@

#define DEFAULT_OPTION "--default"

struct t_CnxCli {
CnxApp app;
Options options;
struct cnx_cli {
cnx_ctx_t ctx;
options_t options;
};

static void help(CnxCli*);
static void version(CnxCli*);
static void help(cnx_ctx_t*, cnx_cli_t*);
static void version(cnx_ctx_t*, void*);

extern CnxCli* cnx_cli_init(CnxApp app) {
CnxCli* cli = (CnxCli*) malloc(sizeof(CnxCli));
cli->app = app;
options_init(&cli->options);
extern cnx_cli_t* cnx_cli_init(cnx_app_t app) {
cnx_cli_t* cli = (cnx_cli_t*) malloc(sizeof(cnx_cli_t));
cli->ctx = (cnx_ctx_t) { app, 0, NULL };
options_init(&cli->options, &cli->ctx);

cnx_cli_add(cli, 3, (CnxOption[]) {
{ "-h, --help", "Display this information", (handle_t)help, cli },
{ "-v, --version", "Display version information", (handle_t)version, cli },
{ "*", NULL, (handle_t)help, cli }
cnx_cli_add(cli, 3, (cnx_option_t[]) {
{ "-h, --help", "Display this information", (cnx_handle_t)help, cli },
{ "-v, --version", "Display version information", (cnx_handle_t)version, NULL },
{ "*", NULL, (cnx_handle_t)help, cli }
});

return cli;
}

extern void cnx_cli_free(CnxCli* cli) {
extern void cnx_cli_free(cnx_cli_t* cli) {
if (cli != NULL) {
options_free(&cli->options);
free(cli);
}
}

extern void cnx_cli_run(CnxCli* cli, size_t argc, const char* argv[]) {
extern void cnx_cli_run(cnx_cli_t* cli, size_t argc, const char* argv[]) {
if (argc > 1) {
cli->ctx.argc = argc - 1;
cli->ctx.argv = argv + 1;
}
options_run(&cli->options, argc > 1 ? argv[1] : DEFAULT_OPTION);
}

extern void cnx_cli_add(CnxCli* cli, size_t count, CnxOption options[]) {
extern void cnx_cli_add(cnx_cli_t* cli, size_t count, cnx_option_t options[]) {
foreach(i, 0, count) {
options_add(&cli->options, (Option) {
options_add(&cli->options, (option_t) {
.name = options[i].name,
.description = options[i].description,
.payload = options[i].payload,
.handle = options[i].handle
.handle = (handle_t)options[i].handle
});
}
}

static void help(CnxCli* cli) {
printf("Usage: %s [options]\n\n", cli->app.name);
static void help(cnx_ctx_t* ctx, cnx_cli_t* cli) {
printf("Usage: %s [options]\n\n", ctx->app.name);
options_print(&cli->options);
}

static void version(CnxCli* cli) {
printf("%s v%s\n", cli->app.name, cli->app.version);
static void version(cnx_ctx_t* ctx, void* payload) {
printf("%s v%s\n", ctx->app.name, ctx->app.version);
}
22 changes: 11 additions & 11 deletions src/handlers.c
Original file line number Diff line number Diff line change
Expand Up @@ -22,41 +22,41 @@

#include "handlers.h"

struct t_HandlerStore {
Handler data;
HandlerStore* next;
struct handler_store {
handler_t data;
handler_store_t* next;
};

static size_t hash(const char*);

extern void handlers_init(Handlers* handlers) {
extern void handlers_init(handlers_t* handlers) {
foreach(i, 0, HANDLER_STORES) {
handlers->stores[i] = NULL;
}
}

extern void handlers_free(Handlers* handlers) {
extern void handlers_free(handlers_t* handlers) {
foreach(i, 0, HANDLER_STORES) {
HandlerStore* store = handlers->stores[i];
handler_store_t* store = handlers->stores[i];
while (store != NULL) {
HandlerStore* current = store;
handler_store_t* current = store;
store = store->next;
free(current);
}
}
}

extern void handlers_put(Handlers* handlers, Handler handler) {
HandlerStore* store = (HandlerStore*) malloc(sizeof(HandlerStore));
extern void handlers_put(handlers_t* handlers, handler_t handler) {
handler_store_t* store = (handler_store_t*) malloc(sizeof(handler_store_t));
store->data = handler;

size_t index = hash(handler.id);
store->next = handlers->stores[index];
handlers->stores[index] = store;
}

extern Handler* handlers_get(Handlers* handlers, const char* id) {
HandlerStore* store = handlers->stores[hash(id)];
extern handler_t* handlers_get(handlers_t* handlers, const char* id) {
handler_store_t* store = handlers->stores[hash(id)];
while (store != NULL) {
if (!strcmp(store->data.id, id)) {
return &store->data;
Expand Down
20 changes: 10 additions & 10 deletions src/handlers.h
Original file line number Diff line number Diff line change
Expand Up @@ -24,24 +24,24 @@

#define HANDLER_STORES 10

typedef struct t_Handler Handler;
typedef struct t_Handlers Handlers;
typedef struct t_HandlerStore HandlerStore;
typedef struct handler handler_t;
typedef struct handlers handlers_t;
typedef struct handler_store handler_store_t;

struct t_Handler {
struct handler {
const char* id;
void* payload;
handle_t handle;
};

struct t_Handlers {
HandlerStore* stores[HANDLER_STORES];
struct handlers {
handler_store_t* stores[HANDLER_STORES];
};

extern void handlers_init(Handlers* handlers);
extern void handlers_free(Handlers* handlers);
extern void handlers_init(handlers_t* handlers);
extern void handlers_free(handlers_t* handlers);

extern void handlers_put(Handlers* handlers, Handler handler);
extern Handler* handlers_get(Handlers* handlers, const char* id);
extern void handlers_put(handlers_t* handlers, handler_t handler);
extern handler_t* handlers_get(handlers_t* handlers, const char* id);

#endif // CONIX_HANDLERS_H
14 changes: 7 additions & 7 deletions src/info.c
Original file line number Diff line number Diff line change
Expand Up @@ -30,14 +30,14 @@
#define reallocate(type, array, size) \
(type*) realloc(array, size * sizeof(type))

static void push(Info*, size_t, InfoItem);
static void push(info_t*, size_t, info_item_t);

extern void info_init(Info* info) {
extern void info_init(info_t* info) {
info->length = info->size = 0;
info->values = NULL;
}

extern void info_free(Info* info) {
extern void info_free(info_t* info) {
if (info->values == NULL) return;
info_foreach(*info, item, {
free((char*) item.name);
Expand All @@ -46,7 +46,7 @@ extern void info_free(Info* info) {
free(info->values);
}

extern void info_put(Info* info, InfoItem value) {
extern void info_put(info_t* info, info_item_t value) {
if (info->values == NULL || strcmp(value.name, last_name(info)) > 0) {
return push(info, info->length, value);
}
Expand All @@ -62,10 +62,10 @@ extern void info_put(Info* info, InfoItem value) {
});
}

static void push(Info* info, size_t index, InfoItem value) {
static void push(info_t* info, size_t index, info_item_t value) {
if (info->length == info->size) {
info->size = info->size ? info->size * 2 : BASE_SIZE;
info->values = reallocate(InfoItem, info->values, info->size);
info->values = reallocate(info_item_t, info->values, info->size);
if (info->values == NULL) exit(EXIT_FAILURE);
}

Expand All @@ -74,7 +74,7 @@ static void push(Info* info, size_t index, InfoItem value) {
}

++info->length;
info->values[index] = (InfoItem) {
info->values[index] = (info_item_t) {
.name = str_copy(value.name),
.description = str_copy(value.description)
};
Expand Down
Loading

0 comments on commit 0c3e378

Please sign in to comment.