Support parse url

Signed-off-by: Jianhui Zhao <zhaojh329@gmail.com>
main
Jianhui Zhao 2020-03-14 14:03:48 +08:00
parent 5f4f6e0d97
commit 040763a64a
4 changed files with 41 additions and 17 deletions

View File

@ -36,7 +36,8 @@ static void on_request(struct uh_connection *conn)
conn->send_head(conn, 200, -1, NULL);
conn->chunk_printf(conn, "I'm Libuhttpd: %s\n", UHTTPD_VERSION_STRING);
conn->chunk_printf(conn, "Url: %s\n", conn->get_url(conn));
conn->chunk_printf(conn, "Path: %s\n", conn->get_path(conn));
conn->chunk_printf(conn, "Query: %s\n", conn->get_query(conn));
conn->chunk_printf(conn, "User-Agent: %s\n", conn->get_header(conn, "User-Agent"));
conn->chunk_printf(conn, "Body: %.*s\n", body_len, body);
conn->chunk_end(conn);

View File

@ -150,13 +150,28 @@ static void conn_redirect(struct uh_connection *conn, int code, const char *loca
/* data of the request field */
#define O2D(c, o) ((const char *)c->rb.data + o)
static const char *conn_get_url(struct uh_connection *conn)
static const char *conn_get_path(struct uh_connection *conn)
{
struct http_parser_url *u = &conn->url_parser;
struct uh_request *req = &conn->req;
if (!req->url)
req->url = strndup(O2D(conn, req->url_info.offset), req->url_info.len);
return req->url;
if (!req->url.path)
req->url.path = strndup(O2D(conn, u->field_data[UF_PATH].off) + req->url.offset, u->field_data[UF_PATH].len);
return req->url.path;
}
static const char *conn_get_query(struct uh_connection *conn)
{
struct http_parser_url *u = &conn->url_parser;
struct uh_request *req = &conn->req;
if (!(u->field_set & (1 << UF_QUERY)))
return "";
if (!req->url.query)
req->url.query = strndup(O2D(conn, u->field_data[UF_QUERY].off) + req->url.offset, u->field_data[UF_QUERY].len);
return req->url.query;
}
static const char *conn_get_header(struct uh_connection *conn, const char *name)
@ -204,10 +219,11 @@ static int on_url_cb(struct http_parser *parser, const char *at, size_t length)
struct uh_connection *conn = (struct uh_connection *)parser->data;
struct uh_request *req = &conn->req;
req->url_info.offset = ROF(conn, at);
req->url_info.len = length;
req->url.offset = ROF(conn, at);
return 0;
http_parser_url_init(&conn->url_parser);
return http_parser_parse_url(at, length, false, &conn->url_parser);
}
static int on_header_field_cb(struct http_parser *parser, const char *at, size_t length)
@ -257,7 +273,7 @@ static bool run_plugins(struct uh_connection *conn)
struct uh_plugin *p = conn->srv->plugins;
while (p) {
if (!strcmp(conn->get_url(conn), p->path)) {
if (!strcmp(conn->get_path(conn), p->path)) {
p->handler(conn);
return true;
}
@ -281,8 +297,11 @@ static int on_message_complete_cb(struct http_parser *parser)
buffer_pull(&conn->rb, NULL, buffer_length(&conn->rb));
if (req->url)
free(req->url);
if (req->url.path)
free(req->url.path);
if (req->url.query)
free(req->url.query);
for (i = 0; i < UHTTPD_MAX_HEADER_NUM; i++) {
if (req->headers[i].name)
@ -513,7 +532,8 @@ struct uh_connection *uh_new_connection(struct uh_server *srv, int sock, struct
conn->chunk_vprintf = conn_chunk_vprintf;
conn->chunk_end = conn_chunk_end;
conn->get_url = conn_get_url;
conn->get_path = conn_get_path;
conn->get_query = conn_get_query;
conn->get_header = conn_get_header;
conn->get_body = conn_get_body;

View File

@ -44,9 +44,10 @@ struct uh_server;
struct uh_request {
struct {
int offset;
int len;
} url_info;
char *url;
char *path;
char *query;
} url;
struct {
int name_offset;
int name_len;
@ -80,6 +81,7 @@ struct uh_connection {
struct uh_server *srv;
struct sockaddr_in addr;
struct http_parser parser;
struct http_parser_url url_parser;
struct uh_connection *prev;
struct uh_connection *next;
void (*free)(struct uh_connection *conn);
@ -94,7 +96,8 @@ struct uh_connection {
void (*chunk_printf)(struct uh_connection *conn, const char *format, ...);
void (*chunk_vprintf)(struct uh_connection *conn, const char *format, va_list arg);
void (*chunk_end)(struct uh_connection *conn);
const char *(*get_url)(struct uh_connection *conn);
const char *(*get_path)(struct uh_connection *conn);
const char *(*get_query)(struct uh_connection *conn);
const char *(*get_header)(struct uh_connection *conn, const char *name);
const char *(*get_body)(struct uh_connection *conn, int *len);
};

View File

@ -27,7 +27,7 @@
static void test_handler(struct uh_connection *conn)
{
conn->send_head(conn, 200, -1, NULL);
conn->chunk_printf(conn, "Url: %s\n", conn->get_url(conn));
conn->chunk_printf(conn, "Path: %s\n", conn->get_path(conn));
conn->chunk_end(conn);
}