feat: routes now specify a method
parent
9b66223a57
commit
18d67fb69f
|
@ -5,3 +5,4 @@ compile_commands.json
|
||||||
lander.data*
|
lander.data*
|
||||||
pastes/
|
pastes/
|
||||||
.cache/
|
.cache/
|
||||||
|
vgcore.*
|
||||||
|
|
|
@ -11,11 +11,11 @@
|
||||||
extern const char *http_response_type_names[5][32];
|
extern const char *http_response_type_names[5][32];
|
||||||
|
|
||||||
typedef enum http_request_method {
|
typedef enum http_request_method {
|
||||||
http_request_method_get = 0,
|
http_get = 0,
|
||||||
http_request_method_post = 1,
|
http_post = 1,
|
||||||
http_request_method_put = 2,
|
http_put = 2,
|
||||||
http_request_method_patch = 3,
|
http_patch = 3,
|
||||||
http_request_method_delete = 4
|
http_delete = 4
|
||||||
} http_request_method;
|
} http_request_method;
|
||||||
|
|
||||||
extern const char *request_method_names[];
|
extern const char *request_method_names[];
|
||||||
|
|
|
@ -14,6 +14,7 @@ typedef enum http_route_type {
|
||||||
|
|
||||||
typedef struct http_route {
|
typedef struct http_route {
|
||||||
http_route_type type;
|
http_route_type type;
|
||||||
|
http_request_method method;
|
||||||
char *path;
|
char *path;
|
||||||
regex_t *regex;
|
regex_t *regex;
|
||||||
bool (*steps[5])(event_loop_conn *);
|
bool (*steps[5])(event_loop_conn *);
|
||||||
|
@ -93,7 +94,8 @@ void http_loop_process_request(event_loop_conn *conn);
|
||||||
* Set the request body to the given buffer. If owned is set to true, the body
|
* Set the request body to the given buffer. If owned is set to true, the body
|
||||||
* buffer will be free'd after the request has finished.
|
* buffer will be free'd after the request has finished.
|
||||||
*/
|
*/
|
||||||
void http_loop_res_set_body(const char *body, size_t body_len, bool owned);
|
void http_loop_res_set_body(http_loop_ctx *ctx, const char *body,
|
||||||
|
size_t body_len, bool owned);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Initialize a new http loop
|
* Initialize a new http loop
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
// clang-format off
|
// clang-format off
|
||||||
|
|
||||||
const char *http_response_type_names[5][32] = {
|
const char *http_response_type_names[5][32] = {
|
||||||
|
// 1xx
|
||||||
{
|
{
|
||||||
"Continue", // 100
|
"Continue", // 100
|
||||||
"Switching Protocols", // 101,
|
"Switching Protocols", // 101,
|
||||||
|
|
|
@ -35,6 +35,7 @@ void http_loop_ctx_reset(http_loop_ctx *ctx) {
|
||||||
|
|
||||||
ctx->res.body = NULL;
|
ctx->res.body = NULL;
|
||||||
|
|
||||||
|
ctx->res.type = 0;
|
||||||
ctx->res.head_len = 0;
|
ctx->res.head_len = 0;
|
||||||
ctx->res.head_written = 0;
|
ctx->res.head_written = 0;
|
||||||
ctx->res.body_len = 0;
|
ctx->res.body_len = 0;
|
||||||
|
|
|
@ -79,6 +79,7 @@ void http_loop_route_request(event_loop_conn *conn) {
|
||||||
ctx->req.path);
|
ctx->req.path);
|
||||||
|
|
||||||
http_route *route;
|
http_route *route;
|
||||||
|
bool path_matched = false;
|
||||||
|
|
||||||
for (size_t i = 0; i < gctx->route_count; i++) {
|
for (size_t i = 0; i < gctx->route_count; i++) {
|
||||||
route = &gctx->routes[i];
|
route = &gctx->routes[i];
|
||||||
|
@ -86,16 +87,21 @@ void http_loop_route_request(event_loop_conn *conn) {
|
||||||
switch (route->type) {
|
switch (route->type) {
|
||||||
case http_route_literal:
|
case http_route_literal:
|
||||||
if (strncmp(route->path, ctx->req.path, ctx->req.path_len) == 0) {
|
if (strncmp(route->path, ctx->req.path, ctx->req.path_len) == 0) {
|
||||||
|
path_matched = true;
|
||||||
|
|
||||||
|
if (ctx->req.method == route->method) {
|
||||||
ctx->route = route;
|
ctx->route = route;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
// TODO
|
// TODO
|
||||||
case http_route_regex:;
|
case http_route_regex:;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Fallthrough is to write a 404
|
// Fallthrough case
|
||||||
ctx->res.type = http_not_found;
|
ctx->res.type = path_matched ? http_method_not_allowed : http_not_found;
|
||||||
conn->state = event_loop_conn_state_res;
|
conn->state = event_loop_conn_state_res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -9,6 +9,10 @@ static const char *http_response_format = "HTTP/1.1 %i %s\n"
|
||||||
"Content-Length: %lu\n\n";
|
"Content-Length: %lu\n\n";
|
||||||
|
|
||||||
void http_loop_init_header(http_response *res) {
|
void http_loop_init_header(http_response *res) {
|
||||||
|
if (res->type == 0) {
|
||||||
|
res->type = http_ok;
|
||||||
|
}
|
||||||
|
|
||||||
const char *response_type_name =
|
const char *response_type_name =
|
||||||
http_response_type_names[res->type / 100 - 1][res->type % 100];
|
http_response_type_names[res->type / 100 - 1][res->type % 100];
|
||||||
|
|
||||||
|
@ -61,3 +65,10 @@ void http_loop_write_response(event_loop_conn *conn) {
|
||||||
res->body_written += bytes_to_write;
|
res->body_written += bytes_to_write;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void http_loop_res_set_body(http_loop_ctx *ctx, const char *body,
|
||||||
|
size_t body_len, bool owned) {
|
||||||
|
ctx->res.body = body;
|
||||||
|
ctx->res.body_len = body_len;
|
||||||
|
ctx->res.owns_body = owned;
|
||||||
|
}
|
||||||
|
|
15
src/main.c
15
src/main.c
|
@ -14,19 +14,20 @@ const char index_page[] =
|
||||||
" </body>\n"
|
" </body>\n"
|
||||||
"</html>\n";
|
"</html>\n";
|
||||||
|
|
||||||
bool http_write_404(event_loop_conn *conn) {
|
bool lander_get_index(event_loop_conn *conn) {
|
||||||
http_loop_ctx *ctx = conn->ctx;
|
http_loop_ctx *ctx = conn->ctx;
|
||||||
ctx->res.type = 200;
|
|
||||||
ctx->res.body = index_page;
|
http_loop_res_set_body(ctx, index_page, sizeof(index_page) - 1, false);
|
||||||
ctx->res.body_len = sizeof(index_page) - 1;
|
|
||||||
ctx->res.owns_body = false;
|
|
||||||
conn->state = event_loop_conn_state_res;
|
conn->state = event_loop_conn_state_res;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
http_route routes[] = {
|
http_route routes[] = {{.type = http_route_literal,
|
||||||
{.type = http_route_literal, .path = "/", .steps = {http_write_404, NULL}}};
|
.method = http_get,
|
||||||
|
.path = "/",
|
||||||
|
.steps = {lander_get_index, NULL}}};
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
setvbuf(stdout, NULL, _IONBF, 0);
|
setvbuf(stdout, NULL, _IONBF, 0);
|
||||||
|
|
Loading…
Reference in New Issue