You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
85 lines
2.7 KiB
85 lines
2.7 KiB
This patch makes it possible to serve static content from Nix store paths, by
|
|
using the hash of the store path for the ETag header.
|
|
|
|
diff --git a/src/http/ngx_http_core_module.c b/src/http/ngx_http_core_module.c
|
|
index cb49ef74..7b456993 100644
|
|
--- a/src/http/ngx_http_core_module.c
|
|
+++ b/src/http/ngx_http_core_module.c
|
|
@@ -1583,6 +1583,8 @@ ngx_http_set_etag(ngx_http_request_t *r)
|
|
{
|
|
ngx_table_elt_t *etag;
|
|
ngx_http_core_loc_conf_t *clcf;
|
|
+ u_char *real, *ptr1, *ptr2;
|
|
+ ngx_err_t err;
|
|
|
|
clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
|
|
|
|
@@ -1598,16 +1600,60 @@ ngx_http_set_etag(ngx_http_request_t *r)
|
|
etag->hash = 1;
|
|
ngx_str_set(&etag->key, "ETag");
|
|
|
|
- etag->value.data = ngx_pnalloc(r->pool, NGX_OFF_T_LEN + NGX_TIME_T_LEN + 3);
|
|
- if (etag->value.data == NULL) {
|
|
- etag->hash = 0;
|
|
- return NGX_ERROR;
|
|
+ err = ngx_errno;
|
|
+ real = ngx_realpath(clcf->root.data, NULL);
|
|
+ ngx_set_errno(err);
|
|
+
|
|
+ #define NIX_STORE_DIR "@nixStoreDir@"
|
|
+ #define NIX_STORE_LEN @nixStoreDirLen@
|
|
+
|
|
+ if (r->headers_out.last_modified_time == 1
|
|
+ && real != NULL
|
|
+ && !ngx_strncmp(real, NIX_STORE_DIR, NIX_STORE_LEN)
|
|
+ && real[NIX_STORE_LEN] == '/'
|
|
+ && real[NIX_STORE_LEN + 1] != '\0')
|
|
+ {
|
|
+ ptr1 = real + NIX_STORE_LEN;
|
|
+ *ptr1 = '"';
|
|
+
|
|
+ ptr2 = (u_char *) ngx_strchr(ptr1, '-');
|
|
+
|
|
+ if (ptr2 == NULL) {
|
|
+ ngx_free(real);
|
|
+ etag->hash = 0;
|
|
+ return NGX_ERROR;
|
|
+ }
|
|
+
|
|
+ *ptr2++ = '"';
|
|
+ *ptr2 = '\0';
|
|
+
|
|
+ etag->value.len = ngx_strlen(ptr1);
|
|
+ etag->value.data = ngx_pnalloc(r->pool, etag->value.len);
|
|
+
|
|
+ if (etag->value.data == NULL) {
|
|
+ ngx_free(real);
|
|
+ etag->hash = 0;
|
|
+ return NGX_ERROR;
|
|
+ }
|
|
+
|
|
+ ngx_memcpy(etag->value.data, ptr1, etag->value.len);
|
|
+ ngx_http_clear_last_modified(r);
|
|
+ } else {
|
|
+ etag->value.data = ngx_pnalloc(r->pool, NGX_OFF_T_LEN + NGX_TIME_T_LEN + 3);
|
|
+
|
|
+ if (etag->value.data == NULL) {
|
|
+ ngx_free(real);
|
|
+ etag->hash = 0;
|
|
+ return NGX_ERROR;
|
|
+ }
|
|
+
|
|
+ etag->value.len = ngx_sprintf(etag->value.data, "\"%xT-%xO\"",
|
|
+ r->headers_out.last_modified_time,
|
|
+ r->headers_out.content_length_n)
|
|
+ - etag->value.data;
|
|
}
|
|
|
|
- etag->value.len = ngx_sprintf(etag->value.data, "\"%xT-%xO\"",
|
|
- r->headers_out.last_modified_time,
|
|
- r->headers_out.content_length_n)
|
|
- - etag->value.data;
|
|
+ ngx_free(real);
|
|
|
|
r->headers_out.etag = etag;
|
|
|
|
|