- Added evaluation variables in docroot

This commit is contained in:
Alexey Berezhok
2026-06-24 02:08:54 +03:00
parent c74ae3bec6
commit 2cb396b1d0
2 changed files with 89 additions and 11 deletions

View File

@@ -109,6 +109,7 @@ def main(nginx_src_dir="."):
# Добавляем наш модуль в конец
args_list.append("--add-dynamic-module=../modules/mod_rewrite")
args_list.append("--with-debug")
print(f"Added --add-dynamic-module=../modules/mod_rewrite", file=sys.stderr)

View File

@@ -775,6 +775,9 @@ ngx_htaccess_search_upward(ngx_http_request_t *r, u_char *docroot, size_t docroo
u_char *path_buf = (u_char *)ngx_palloc(r->pool, current_path->len + 1 + htaccess_name_len);
size_t current_pos;
ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: try to find .htaccess %s, uri=\"%V\"", path_buf, &r->uri);
if (!path_buf) {
return NGX_ERROR;
}
@@ -792,6 +795,8 @@ ngx_htaccess_search_upward(ngx_http_request_t *r, u_char *docroot, size_t docroo
/* Iterate upward from current directory up to docroot */
while (1) {
/* Check if file exists at this level */
ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: try to find(1) .htaccess %s, uri=\"%V\"", path_buf, &r->uri);
struct stat st;
if (stat((char *)path_buf, &st) == 0 && ngx_is_file(&st)) {
/* Found .htaccess! */
@@ -812,6 +817,8 @@ ngx_htaccess_search_upward(ngx_http_request_t *r, u_char *docroot, size_t docroo
if (last_slash == NULL) {
/* Reached DocRoot without finding htaccess */
ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: try to find .htaccess %s, uri=\"%V\" error(1)", path_buf, &r->uri);
return NGX_ERROR;
}
@@ -820,6 +827,8 @@ ngx_htaccess_search_upward(ngx_http_request_t *r, u_char *docroot, size_t docroo
if (current_pos < docroot_len) {
/* Reached or passed DocRoot - no htaccess found */
ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: try to find .htaccess %s, uri=\"%V\" error(2)", path_buf, &r->uri);
return NGX_ERROR;
}
@@ -1496,8 +1505,13 @@ ngx_http_apache_rewrite_location_handler(ngx_http_request_t *r)
return NGX_DECLINED;
}
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: location handler engine enabled in location, uri=\"%V\"", &r->uri);
/* Check htaccess parsing enable */
if (!sconf->htaccess_enable_set || sconf->htaccess_enable != 1) {
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: location handler htaccess disabled, uri=\"%V\"", &r->uri);
/* Use only location rules */
if (lcf->rules->nelts == 0) {
return NGX_DECLINED;
@@ -1533,20 +1547,56 @@ ngx_http_apache_rewrite_location_handler(ngx_http_request_t *r)
u_char *htaccess_name = sconf->htaccess_name.data ? (u_char *)sconf->htaccess_name.data : (u_char *)".htaccess";
size_t htaccess_name_len = sconf->htaccess_name.data ? sconf->htaccess_name.len : 9;
/* Build initial path: docroot + r->uri */
ngx_str_t current_path;
rc = ngx_htaccess_build_path(r, clcf->root.data, clcf->root.len, &current_path, htaccess_name, htaccess_name_len);
ngx_str_t evaluated_root = {0, NULL};
size_t evaluated_root_len = 0;
/* Check if root contains variables and evaluate them */
if (clcf->root_lengths != NULL) {
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: root has script variables, evaluating");
/* Run the script to evaluate variables in clcf->root */
if (ngx_http_script_run(r, &evaluated_root,
clcf->root_lengths->elts, 0,
clcf->root_values->elts) == NULL) {
ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
"mod_rewrite: failed to evaluate root path script");
return NGX_ERROR;
}
evaluated_root_len = evaluated_root.len > 0 ? evaluated_root.len : 0;
/* LOG: Show evaluated root */
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: evaluated root path len=%uz", evaluated_root_len);
} else {
/* LOG: No script variables in root */
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: root has no script variables, using clcf->root directly");
}
/* Build initial path: docroot + r->uri using evaluated or original root */
rc = ngx_htaccess_build_path(r,
evaluated_root.data ? evaluated_root.data : clcf->root.data,
evaluated_root.len > 0 ? evaluated_root.len : clcf->root.len,
&current_path, htaccess_name, htaccess_name_len);
ngx_str_t htaccess_docroot = ngx_null_string;
/* Remove last component (filename) to search from parent directory */
if (rc == NGX_OK && current_path.len > 0) {
/* Search upward for .htaccess file */
rc = ngx_htaccess_search_upward(r, clcf->root.data, clcf->root.len, &current_path,
htaccess_name, htaccess_name_len, &htaccess_path);
/* Search upward for .htaccess file - use evaluated root here too! */
rc = ngx_htaccess_search_upward(r,
evaluated_root.data ? evaluated_root.data : clcf->root.data,
evaluated_root.len > 0 ? evaluated_root.len : clcf->root.len,
&current_path, htaccess_name, htaccess_name_len,
&htaccess_path);
if (rc == NGX_ERROR) {
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: location handler .htaccess not found, uri=\"%V\"", &r->uri);
/* File not found — use only location rules */
ctx = ngx_http_get_module_ctx(r, ngx_http_apache_rewrite_module);
if (ctx && ctx->end) {
@@ -1558,18 +1608,35 @@ ngx_http_apache_rewrite_location_handler(ngx_http_request_t *r)
return ngx_process_rules_result(rc, ctx, r, 0);
}
htaccess_docroot.data = ngx_pcalloc(r->pool, htaccess_path.len);
size_t htaccess_docroot_vlen = htaccess_path.len - (clcf->root.len + 1) - htaccess_name_len;
if ((long)htaccess_docroot_vlen < 0) htaccess_docroot_vlen = 0;
ngx_memcpy(htaccess_docroot.data, htaccess_path.data + clcf->root.len + 1, htaccess_docroot_vlen);
/* LOG: Show found htaccess path */
if (rc == NGX_OK && htaccess_path.data) {
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: found .htaccess at: %V", &htaccess_path);
} else {
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: .htaccess not found, uri=%V", &r->uri);
}
htaccess_docroot.len = htaccess_path.len - (clcf->root.len + 1) - htaccess_name_len;
/* Extract htaccess_docroot path - now correctly works with evaluated root */
size_t used_root_len = (evaluated_root.len > 0) ? evaluated_root.len : clcf->root.len;
htaccess_docroot.data = ngx_pcalloc(r->pool, htaccess_path.len);
size_t htaccess_docroot_vlen = htaccess_path.len - (used_root_len + 1) - htaccess_name_len;
if ((long)htaccess_docroot_vlen < 0) htaccess_docroot_vlen = 0;
ngx_memcpy(htaccess_docroot.data, htaccess_path.data + used_root_len + 1, htaccess_docroot_vlen);
htaccess_docroot.len = htaccess_path.len - (used_root_len + 1) - htaccess_name_len;
} else {
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: failed to build current path for .htaccess search");
}
/* Check if htaccess file exists */
struct stat st;
if (!htaccess_path.data || stat((char *)htaccess_path.data, &st) == -1) {
/* File does not exist — use only location rules */
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: location handler .htaccess nto found by stat, uri=\"%V\"", &r->uri);
if (lcf->rules->nelts == 0) {
return NGX_DECLINED;
}
@@ -1641,6 +1708,9 @@ ngx_http_apache_rewrite_location_handler(ngx_http_request_t *r)
/* If no cached rules, parse .htaccess file */
if (combined_rules == NULL) {
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: location handler rules from .htaccess not in cache reread, .htaccess=\"%V\"", &htaccess_path);
parsed_rules = ngx_htaccess_parse_file_from_ha(r, &htaccess_path);
if (!parsed_rules){
@@ -1660,11 +1730,17 @@ ngx_http_apache_rewrite_location_handler(ngx_http_request_t *r)
/* Store in cache — add/update entry in linked list */
ngx_htaccess_update_cache(r, htaccess_path, st.st_mtime, parsed_rules);
} else {
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: location handler get rules from cache .htaccess, .htaccess=\"%V\"", &htaccess_path);
}
if (state_htaccess == ENGINE_DISABLED)
return NGX_DECLINED;
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: location handler engine enabled in .htaccess, .htaccess=\"%V\"", &htaccess_path);
/* Ensure ctx exists */
if (ctx == NULL) {
ctx = ngx_pcalloc(r->pool, sizeof(ngx_rewrite_ctx_t));
@@ -1685,7 +1761,8 @@ ngx_http_apache_rewrite_location_handler(ngx_http_request_t *r)
/* Combine location rules with .htaccess rules (.htaccess has priority - added first) */
ngx_int_t final_rc;
ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"mod_rewrite: location handler rules from .htaccess found %d, .htaccess=\"%V\"", combined_rules->nelts, &htaccess_path);
if (combined_rules->nelts > 0 && lcf->rules->nelts > 0) {
/* Create combined array: htaccess rules first, then location rules */
ngx_array_t *final_rules = ngx_array_create(r->pool,