feat: routes now specify a method
							parent
							
								
									9b66223a57
								
							
						
					
					
						commit
						18d67fb69f
					
				|  | @ -5,3 +5,4 @@ compile_commands.json | |||
| lander.data* | ||||
| pastes/ | ||||
| .cache/ | ||||
| vgcore.* | ||||
|  |  | |||
|  | @ -11,11 +11,11 @@ | |||
| extern const char *http_response_type_names[5][32]; | ||||
| 
 | ||||
| typedef enum http_request_method { | ||||
|   http_request_method_get = 0, | ||||
|   http_request_method_post = 1, | ||||
|   http_request_method_put = 2, | ||||
|   http_request_method_patch = 3, | ||||
|   http_request_method_delete = 4 | ||||
|   http_get = 0, | ||||
|   http_post = 1, | ||||
|   http_put = 2, | ||||
|   http_patch = 3, | ||||
|   http_delete = 4 | ||||
| } http_request_method; | ||||
| 
 | ||||
| extern const char *request_method_names[]; | ||||
|  |  | |||
|  | @ -14,6 +14,7 @@ typedef enum http_route_type { | |||
| 
 | ||||
| typedef struct http_route { | ||||
|   http_route_type type; | ||||
|   http_request_method method; | ||||
|   char *path; | ||||
|   regex_t *regex; | ||||
|   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 | ||||
|  * 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 | ||||
|  |  | |||
|  | @ -3,6 +3,7 @@ | |||
| // clang-format off
 | ||||
| 
 | ||||
| const char *http_response_type_names[5][32] = { | ||||
|   // 1xx
 | ||||
|   { | ||||
|     "Continue", // 100
 | ||||
|     "Switching Protocols", // 101,
 | ||||
|  |  | |||
|  | @ -35,6 +35,7 @@ void http_loop_ctx_reset(http_loop_ctx *ctx) { | |||
| 
 | ||||
|   ctx->res.body = NULL; | ||||
| 
 | ||||
|   ctx->res.type = 0; | ||||
|   ctx->res.head_len = 0; | ||||
|   ctx->res.head_written = 0; | ||||
|   ctx->res.body_len = 0; | ||||
|  |  | |||
|  | @ -79,6 +79,7 @@ void http_loop_route_request(event_loop_conn *conn) { | |||
|        ctx->req.path); | ||||
| 
 | ||||
|   http_route *route; | ||||
|   bool path_matched = false; | ||||
| 
 | ||||
|   for (size_t i = 0; i < gctx->route_count; i++) { | ||||
|     route = &gctx->routes[i]; | ||||
|  | @ -86,16 +87,21 @@ void http_loop_route_request(event_loop_conn *conn) { | |||
|     switch (route->type) { | ||||
|     case http_route_literal: | ||||
|       if (strncmp(route->path, ctx->req.path, ctx->req.path_len) == 0) { | ||||
|         ctx->route = route; | ||||
|         return; | ||||
|         path_matched = true; | ||||
| 
 | ||||
|         if (ctx->req.method == route->method) { | ||||
|           ctx->route = route; | ||||
|           return; | ||||
|         } | ||||
|       } | ||||
|       break; | ||||
|     // TODO
 | ||||
|     case http_route_regex:; | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|   // Fallthrough is to write a 404
 | ||||
|   ctx->res.type = http_not_found; | ||||
|   // Fallthrough case
 | ||||
|   ctx->res.type = path_matched ? http_method_not_allowed : http_not_found; | ||||
|   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"; | ||||
| 
 | ||||
| void http_loop_init_header(http_response *res) { | ||||
|   if (res->type == 0) { | ||||
|     res->type = http_ok; | ||||
|   } | ||||
| 
 | ||||
|   const char *response_type_name = | ||||
|       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; | ||||
|   } | ||||
| } | ||||
| 
 | ||||
| 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" | ||||
|     "</html>\n"; | ||||
| 
 | ||||
| bool http_write_404(event_loop_conn *conn) { | ||||
| bool lander_get_index(event_loop_conn *conn) { | ||||
|   http_loop_ctx *ctx = conn->ctx; | ||||
|   ctx->res.type = 200; | ||||
|   ctx->res.body = index_page; | ||||
|   ctx->res.body_len = sizeof(index_page) - 1; | ||||
|   ctx->res.owns_body = false; | ||||
| 
 | ||||
|   http_loop_res_set_body(ctx, index_page, sizeof(index_page) - 1, false); | ||||
| 
 | ||||
|   conn->state = event_loop_conn_state_res; | ||||
| 
 | ||||
|   return true; | ||||
| } | ||||
| 
 | ||||
| http_route routes[] = { | ||||
|     {.type = http_route_literal, .path = "/", .steps = {http_write_404, NULL}}}; | ||||
| http_route routes[] = {{.type = http_route_literal, | ||||
|                         .method = http_get, | ||||
|                         .path = "/", | ||||
|                         .steps = {lander_get_index, NULL}}}; | ||||
| 
 | ||||
| int main() { | ||||
|   setvbuf(stdout, NULL, _IONBF, 0); | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue