Mercurial > hg > nginx-mail
comparison src/http/modules/ngx_http_ssi_filter_module.c @ 76:da9a3b14312d NGINX_0_1_38
nginx 0.1.38
*) Feature: the "limit_rate" directive is supported in in proxy and
FastCGI mode.
*) Feature: the "X-Accel-Limit-Rate" response header line is supported
in proxy and FastCGI mode.
*) Feature: the "break" directive.
*) Feature: the "log_not_found" directive.
*) Bugfix: the response status code was not changed when request was
redirected by the ""X-Accel-Redirect" header line.
*) Bugfix: the variables set by the "set" directive could not be used
in SSI.
*) Bugfix: the segmentation fault may occurred if the SSI page has more
than one remote subrequest.
*) Bugfix: nginx treated the backend response as invalid if the status
line in the header was transferred in two packets; bug appeared in
0.1.29.
*) Feature: the "ssi_types" directive.
*) Feature: the "autoindex_exact_size" directive.
*) Bugfix: the ngx_http_autoindex_module did not support the long file
names in UTF-8.
*) Feature: the IMAP/POP3 proxy.
author | Igor Sysoev <http://sysoev.ru> |
---|---|
date | Fri, 08 Jul 2005 00:00:00 +0400 |
parents | 0790a8599248 |
children | 9db7e0b5b27f |
comparison
equal
deleted
inserted
replaced
75:985847bb65f9 | 76:da9a3b14312d |
---|---|
21 | 21 |
22 typedef struct { | 22 typedef struct { |
23 ngx_flag_t enable; | 23 ngx_flag_t enable; |
24 ngx_flag_t silent_errors; | 24 ngx_flag_t silent_errors; |
25 ngx_flag_t ignore_recycled_buffers; | 25 ngx_flag_t ignore_recycled_buffers; |
26 | |
27 ngx_array_t *types; /* array of ngx_str_t */ | |
26 | 28 |
27 size_t min_file_chunk; | 29 size_t min_file_chunk; |
28 size_t value_len; | 30 size_t value_len; |
29 } ngx_http_ssi_conf_t; | 31 } ngx_http_ssi_conf_t; |
30 | 32 |
125 ngx_http_ssi_ctx_t *ctx, ngx_str_t **params); | 127 ngx_http_ssi_ctx_t *ctx, ngx_str_t **params); |
126 | 128 |
127 static ngx_http_variable_value_t * | 129 static ngx_http_variable_value_t * |
128 ngx_http_ssi_date_gmt_local_variable(ngx_http_request_t *r, uintptr_t gmt); | 130 ngx_http_ssi_date_gmt_local_variable(ngx_http_request_t *r, uintptr_t gmt); |
129 | 131 |
132 static char *ngx_http_ssi_types(ngx_conf_t *cf, ngx_command_t *cmd, void *conf); | |
133 | |
130 static ngx_int_t ngx_http_ssi_add_variables(ngx_conf_t *cf); | 134 static ngx_int_t ngx_http_ssi_add_variables(ngx_conf_t *cf); |
131 static void *ngx_http_ssi_create_conf(ngx_conf_t *cf); | 135 static void *ngx_http_ssi_create_conf(ngx_conf_t *cf); |
132 static char *ngx_http_ssi_merge_conf(ngx_conf_t *cf, | 136 static char *ngx_http_ssi_merge_conf(ngx_conf_t *cf, |
133 void *parent, void *child); | 137 void *parent, void *child); |
134 static ngx_int_t ngx_http_ssi_filter_init(ngx_cycle_t *cycle); | 138 static ngx_int_t ngx_http_ssi_filter_init(ngx_cycle_t *cycle); |
160 { ngx_string("ssi_min_file_chunk"), | 164 { ngx_string("ssi_min_file_chunk"), |
161 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_FLAG, | 165 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_FLAG, |
162 ngx_conf_set_size_slot, | 166 ngx_conf_set_size_slot, |
163 NGX_HTTP_LOC_CONF_OFFSET, | 167 NGX_HTTP_LOC_CONF_OFFSET, |
164 offsetof(ngx_http_ssi_conf_t, min_file_chunk), | 168 offsetof(ngx_http_ssi_conf_t, min_file_chunk), |
169 NULL }, | |
170 | |
171 { ngx_string("ssi_types"), | |
172 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_1MORE, | |
173 ngx_http_ssi_types, | |
174 NGX_HTTP_LOC_CONF_OFFSET, | |
175 0, | |
165 NULL }, | 176 NULL }, |
166 | 177 |
167 ngx_null_command | 178 ngx_null_command |
168 }; | 179 }; |
169 | 180 |
199 ngx_chain_t *in); | 210 ngx_chain_t *in); |
200 | 211 |
201 | 212 |
202 static u_char ngx_http_ssi_string[] = "<!--"; | 213 static u_char ngx_http_ssi_string[] = "<!--"; |
203 static u_char ngx_http_ssi_error_string[] = | 214 static u_char ngx_http_ssi_error_string[] = |
204 "[an error occurred while processing the directive]"; | 215 "[an error occurred while processing the directive]"; |
205 | 216 |
206 static ngx_str_t ngx_http_ssi_none = ngx_string("(none)"); | 217 static ngx_str_t ngx_http_ssi_none = ngx_string("(none)"); |
207 | 218 |
208 | 219 |
209 #define NGX_HTTP_SSI_ECHO_VAR 0 | 220 #define NGX_HTTP_SSI_ECHO_VAR 0 |
278 | 289 |
279 | 290 |
280 static ngx_int_t | 291 static ngx_int_t |
281 ngx_http_ssi_header_filter(ngx_http_request_t *r) | 292 ngx_http_ssi_header_filter(ngx_http_request_t *r) |
282 { | 293 { |
294 ngx_uint_t i; | |
295 ngx_str_t *type; | |
283 ngx_http_ssi_ctx_t *ctx; | 296 ngx_http_ssi_ctx_t *ctx; |
284 ngx_http_ssi_conf_t *conf; | 297 ngx_http_ssi_conf_t *conf; |
285 | 298 |
286 conf = ngx_http_get_module_loc_conf(r, ngx_http_ssi_filter_module); | 299 conf = ngx_http_get_module_loc_conf(r, ngx_http_ssi_filter_module); |
287 | 300 |
288 if (!conf->enable) { | 301 if (!conf->enable |
289 return ngx_http_next_header_filter(r); | 302 || r->headers_out.content_type.len == 0) |
290 } | |
291 | |
292 /* TODO: "text/html" -> custom types */ | |
293 | |
294 if (r->headers_out.content_type.len == 0 | |
295 || ngx_strncasecmp(r->headers_out.content_type.data, "text/html", 5) | |
296 != 0) | |
297 { | 303 { |
298 return ngx_http_next_header_filter(r); | 304 return ngx_http_next_header_filter(r); |
299 } | 305 } |
300 | 306 |
307 | |
308 type = conf->types->elts; | |
309 for (i = 0; i < conf->types->nelts; i++) { | |
310 if (r->headers_out.content_type.len >= type[i].len | |
311 && ngx_strncasecmp(r->headers_out.content_type.data, | |
312 type[i].data, type[i].len) == 0) | |
313 { | |
314 goto found; | |
315 } | |
316 } | |
317 | |
318 return ngx_http_next_header_filter(r); | |
319 | |
320 | |
321 found: | |
301 | 322 |
302 ctx = ngx_pcalloc(r->pool, sizeof(ngx_http_ssi_ctx_t)); | 323 ctx = ngx_pcalloc(r->pool, sizeof(ngx_http_ssi_ctx_t)); |
303 if (ctx == NULL) { | 324 if (ctx == NULL) { |
304 return NGX_ERROR; | 325 return NGX_ERROR; |
305 } | 326 } |
1630 | 1651 |
1631 return vv; | 1652 return vv; |
1632 } | 1653 } |
1633 | 1654 |
1634 | 1655 |
1656 static char * | |
1657 ngx_http_ssi_types(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) | |
1658 { | |
1659 ngx_http_ssi_conf_t *scf = conf; | |
1660 | |
1661 ngx_str_t *value, *type; | |
1662 ngx_uint_t i; | |
1663 | |
1664 if (scf->types == NULL) { | |
1665 scf->types = ngx_array_create(cf->pool, 4, sizeof(ngx_str_t)); | |
1666 if (scf->types == NULL) { | |
1667 return NGX_CONF_ERROR; | |
1668 } | |
1669 | |
1670 type = ngx_array_push(scf->types); | |
1671 if (type == NULL) { | |
1672 return NGX_CONF_ERROR; | |
1673 } | |
1674 | |
1675 type->len = sizeof("text/html") - 1; | |
1676 type->data = (u_char *) "text/html"; | |
1677 } | |
1678 | |
1679 value = cf->args->elts; | |
1680 | |
1681 for (i = 1; i < cf->args->nelts; i++) { | |
1682 | |
1683 if (ngx_strcmp(value[i].data, "text/html") == 0) { | |
1684 continue; | |
1685 } | |
1686 | |
1687 type = ngx_array_push(scf->types); | |
1688 if (type == NULL) { | |
1689 return NGX_CONF_ERROR; | |
1690 } | |
1691 | |
1692 type->len = value[i].len; | |
1693 | |
1694 type->data = ngx_palloc(cf->pool, type->len + 1); | |
1695 if (type->data == NULL) { | |
1696 return NGX_CONF_ERROR; | |
1697 } | |
1698 | |
1699 ngx_cpystrn(type->data, value[i].data, type->len + 1); | |
1700 } | |
1701 | |
1702 return NGX_CONF_OK; | |
1703 } | |
1704 | |
1705 | |
1635 static ngx_int_t | 1706 static ngx_int_t |
1636 ngx_http_ssi_add_variables(ngx_conf_t *cf) | 1707 ngx_http_ssi_add_variables(ngx_conf_t *cf) |
1637 { | 1708 { |
1638 ngx_http_variable_t *var, *v; | 1709 ngx_http_variable_t *var, *v; |
1639 | 1710 |
1658 | 1729 |
1659 conf = ngx_pcalloc(cf->pool, sizeof(ngx_http_ssi_conf_t)); | 1730 conf = ngx_pcalloc(cf->pool, sizeof(ngx_http_ssi_conf_t)); |
1660 if (conf == NULL) { | 1731 if (conf == NULL) { |
1661 return NGX_CONF_ERROR; | 1732 return NGX_CONF_ERROR; |
1662 } | 1733 } |
1734 | |
1735 /* | |
1736 * set by ngx_pcalloc(): | |
1737 * | |
1738 * conf->types = NULL; | |
1739 */ | |
1663 | 1740 |
1664 conf->enable = NGX_CONF_UNSET; | 1741 conf->enable = NGX_CONF_UNSET; |
1665 conf->silent_errors = NGX_CONF_UNSET; | 1742 conf->silent_errors = NGX_CONF_UNSET; |
1666 conf->ignore_recycled_buffers = NGX_CONF_UNSET; | 1743 conf->ignore_recycled_buffers = NGX_CONF_UNSET; |
1667 | 1744 |
1676 ngx_http_ssi_merge_conf(ngx_conf_t *cf, void *parent, void *child) | 1753 ngx_http_ssi_merge_conf(ngx_conf_t *cf, void *parent, void *child) |
1677 { | 1754 { |
1678 ngx_http_ssi_conf_t *prev = parent; | 1755 ngx_http_ssi_conf_t *prev = parent; |
1679 ngx_http_ssi_conf_t *conf = child; | 1756 ngx_http_ssi_conf_t *conf = child; |
1680 | 1757 |
1758 ngx_str_t *type; | |
1759 | |
1681 ngx_conf_merge_value(conf->enable, prev->enable, 0); | 1760 ngx_conf_merge_value(conf->enable, prev->enable, 0); |
1682 ngx_conf_merge_value(conf->silent_errors, prev->silent_errors, 0); | 1761 ngx_conf_merge_value(conf->silent_errors, prev->silent_errors, 0); |
1683 ngx_conf_merge_value(conf->ignore_recycled_buffers, | 1762 ngx_conf_merge_value(conf->ignore_recycled_buffers, |
1684 prev->ignore_recycled_buffers, 0); | 1763 prev->ignore_recycled_buffers, 0); |
1685 | 1764 |
1686 ngx_conf_merge_size_value(conf->min_file_chunk, prev->min_file_chunk, 1024); | 1765 ngx_conf_merge_size_value(conf->min_file_chunk, prev->min_file_chunk, 1024); |
1687 ngx_conf_merge_size_value(conf->value_len, prev->value_len, 256); | 1766 ngx_conf_merge_size_value(conf->value_len, prev->value_len, 256); |
1767 | |
1768 if (conf->types == NULL) { | |
1769 if (prev->types == NULL) { | |
1770 conf->types = ngx_array_create(cf->pool, 1, sizeof(ngx_str_t)); | |
1771 if (conf->types == NULL) { | |
1772 return NGX_CONF_ERROR; | |
1773 } | |
1774 | |
1775 type = ngx_array_push(conf->types); | |
1776 if (type == NULL) { | |
1777 return NGX_CONF_ERROR; | |
1778 } | |
1779 | |
1780 type->len = sizeof("text/html") - 1; | |
1781 type->data = (u_char *) "text/html"; | |
1782 | |
1783 } else { | |
1784 conf->types = prev->types; | |
1785 } | |
1786 } | |
1688 | 1787 |
1689 return NGX_CONF_OK; | 1788 return NGX_CONF_OK; |
1690 } | 1789 } |
1691 | 1790 |
1692 | 1791 |