Add support for adding a prefix to a target when matching vhosts - quark - quar… | |
git clone git://git.suckless.org/quark | |
Log | |
Files | |
Refs | |
LICENSE | |
--- | |
commit 02d6ae5a5714ad24ea0d56a1d575c3dc72bb6949 | |
parent 4948053bee6d4883d988d104316d11ad9a0ca092 | |
Author: Laslo Hunhold <[email protected]> | |
Date: Tue, 27 Feb 2018 11:36:24 +0100 | |
Add support for adding a prefix to a target when matching vhosts | |
This makes quark's vhost-handling very powerful while still being | |
simple. | |
Imagine you have a website with a subdomain you really want | |
to move back to your main domain. | |
Say the subdomain is called "old.example.org" and you want to serve it | |
under "example.org" but in the subdirectory "old/", i.e. you want to | |
redirect a request "old.example.org/subdir/" to "example.org/old/subdir". | |
For a vhost-handler that only takes 4 arguments for each vhost this is | |
actually pretty powerful. | |
Diffstat: | |
M config.def.h | 6 ++++-- | |
M http.c | 14 ++++++++++++-- | |
2 files changed, 16 insertions(+), 4 deletions(-) | |
--- | |
diff --git a/config.def.h b/config.def.h | |
@@ -17,10 +17,12 @@ static struct { | |
const char *name; | |
const char *regex; | |
const char *dir; | |
+ const char *prefix; | |
regex_t re; | |
} vhost[] = { | |
- /* canonical host host regex directory */ | |
- { "example.org", "^(www\\.)?example\\.org$", "/example.org" }, | |
+ /* canonical host host regex directory … | |
+ { "example.org", "^(www\\.)?example\\.org$", "/example.org", … | |
+ { "example.org", "old\\.example\\.org", "/", … | |
}; | |
/* mime-types */ | |
diff --git a/http.c b/http.c | |
@@ -320,6 +320,9 @@ http_send_response(int fd, struct request *r) | |
char *p, *q, *mime; | |
const char *vhostmatch, *err; | |
+ /* make a working copy of the target */ | |
+ memcpy(realtarget, r->target, sizeof(realtarget)); | |
+ | |
/* match vhost */ | |
vhostmatch = NULL; | |
if (vhosts) { | |
@@ -338,10 +341,17 @@ http_send_response(int fd, struct request *r) | |
if (i == LEN(vhost)) { | |
return http_send_status(fd, S_NOT_FOUND); | |
} | |
+ | |
+ /* if we have a vhost prefix, prepend it to the target */ | |
+ if (vhost[i].prefix) { | |
+ if (snprintf(realtarget, sizeof(realtarget), "%s%s", | |
+ vhost[i].prefix, realtarget) >= sizeof(realtarget)… | |
+ return http_send_status(fd, S_REQUEST_TOO_LARG… | |
+ } | |
+ } | |
} | |
/* normalize target */ | |
- memcpy(realtarget, r->target, sizeof(realtarget)); | |
if (normabspath(realtarget)) { | |
return http_send_status(fd, S_BAD_REQUEST); | |
} | |
@@ -369,7 +379,7 @@ http_send_response(int fd, struct request *r) | |
} | |
} | |
- /* redirect if targets differ or host is non-canonical */ | |
+ /* redirect if targets differ, host is non-canonical or we prefixed */ | |
if (strcmp(r->target, realtarget) || (vhosts && vhostmatch && | |
strcmp(r->field[REQ_HOST], vhostmatch))) { | |
/* do we need to add a port to the Location? */ |