change to tengine 2.0.3

This commit is contained in:
leon.li 2016-05-11 22:48:31 +08:00
parent 0ac5057cce
commit 0454877c32
628 changed files with 12456 additions and 142721 deletions

View file

@ -1,66 +1,5 @@
Changes with nginx 1.6.2 16 Sep 2014
*) Security: it was possible to reuse SSL sessions in unrelated contexts
if a shared SSL session cache or the same TLS session ticket key was
used for multiple "server" blocks (CVE-2014-3616).
Thanks to Antoine Delignat-Lavaud.
*) Bugfix: requests might hang if resolver was used and a DNS server
returned a malformed response; the bug had appeared in 1.5.8.
*) Bugfix: requests might hang if resolver was used and a timeout
occurred during a DNS request.
Changes with nginx 1.6.1 05 Aug 2014
*) Security: pipelined commands were not discarded after STARTTLS
command in SMTP proxy (CVE-2014-3556); the bug had appeared in 1.5.6.
Thanks to Chris Boulton.
*) Bugfix: the $uri variable might contain garbage when returning errors
with code 400.
Thanks to Sergey Bobrov.
*) Bugfix: in the "none" parameter in the "smtp_auth" directive; the bug
had appeared in 1.5.6.
Thanks to Svyatoslav Nikolsky.
Changes with nginx 1.6.0 24 Apr 2014
*) 1.6.x stable branch.
Changes with nginx 1.5.13 08 Apr 2014
*) Change: improved hash table handling; the default values of the
"variables_hash_max_size" and "types_hash_bucket_size" were changed
to 1024 and 64 respectively.
*) Feature: the ngx_http_mp4_module now supports the "end" argument.
*) Feature: byte ranges support in the ngx_http_mp4_module and while
saving responses to cache.
*) Bugfix: alerts "ngx_slab_alloc() failed: no memory" no longer logged
when using shared memory in the "ssl_session_cache" directive and in
the ngx_http_limit_req_module.
*) Bugfix: the "underscores_in_headers" directive did not allow
underscore as a first character of a header.
Thanks to Piotr Sikora.
*) Bugfix: cache manager might hog CPU on exit in nginx/Windows.
*) Bugfix: nginx/Windows terminated abnormally if the
"ssl_session_cache" directive was used with the "shared" parameter.
*) Bugfix: in the ngx_http_spdy_module.
Changes with nginx 1.5.12 18 Mar 2014
Changes with nginx 1.4.7 18 Mar 2014
*) Security: a heap memory buffer overflow might occur in a worker
process while handling a specially crafted request by
@ -69,23 +8,11 @@ Changes with nginx 1.5.12 18 Mar 2014
Thanks to Lucas Molas, researcher at Programa STIC, Fundación Dr.
Manuel Sadosky, Buenos Aires, Argentina.
*) Feature: the "proxy_protocol" parameters of the "listen" and
"real_ip_header" directives, the $proxy_protocol_addr variable.
*) Bugfix: in the "fastcgi_next_upstream" directive.
Thanks to Lucas Molas.
Changes with nginx 1.5.11 04 Mar 2014
*) Security: memory corruption might occur in a worker process on 32-bit
platforms while handling a specially crafted request by
ngx_http_spdy_module, potentially resulting in arbitrary code
execution (CVE-2014-0088); the bug had appeared in 1.5.10.
Thanks to Lucas Molas, researcher at Programa STIC, Fundación Dr.
Manuel Sadosky, Buenos Aires, Argentina.
*) Feature: the $ssl_session_reused variable.
Changes with nginx 1.4.6 04 Mar 2014
*) Bugfix: the "client_max_body_size" directive might not work when
reading a request body using chunked transfer encoding; the bug had
@ -95,71 +22,15 @@ Changes with nginx 1.5.11 04 Mar 2014
*) Bugfix: a segmentation fault might occur in a worker process when
proxying WebSocket connections.
*) Bugfix: a segmentation fault might occur in a worker process if the
ngx_http_spdy_module was used on 32-bit platforms; the bug had
appeared in 1.5.10.
*) Bugfix: the $upstream_status variable might contain wrong data if the
"proxy_cache_use_stale" or "proxy_cache_revalidate" directives were
used.
Thanks to Piotr Sikora.
*) Bugfix: a segmentation fault might occur in a worker process if
errors with code 400 were redirected to a named location using the
"error_page" directive.
*) Bugfix: nginx/Windows could not be built with Visual Studio 2013.
Changes with nginx 1.5.10 04 Feb 2014
*) Feature: the ngx_http_spdy_module now uses SPDY 3.1 protocol.
Thanks to Automattic and MaxCDN for sponsoring this work.
*) Feature: the ngx_http_mp4_module now skips tracks too short for a
seek requested.
*) Bugfix: a segmentation fault might occur in a worker process if the
$ssl_session_id variable was used in logs; the bug had appeared in
1.5.9.
*) Bugfix: the $date_local and $date_gmt variables used wrong format
outside of the ngx_http_ssi_filter_module.
*) Bugfix: client connections might be immediately closed if deferred
accept was used; the bug had appeared in 1.3.15.
*) Bugfix: alerts "getsockopt(TCP_FASTOPEN) ... failed" appeared in logs
during binary upgrade on Linux; the bug had appeared in 1.5.8.
Thanks to Piotr Sikora.
Changes with nginx 1.5.9 22 Jan 2014
*) Change: now nginx expects escaped URIs in "X-Accel-Redirect" headers.
*) Feature: the "ssl_buffer_size" directive.
*) Feature: the "limit_rate" directive can now be used to rate limit
responses sent in SPDY connections.
*) Feature: the "spdy_chunk_size" directive.
*) Feature: the "ssl_session_tickets" directive.
Thanks to Dirkjan Bussink.
Changes with nginx 1.4.5 11 Feb 2014
*) Bugfix: the $ssl_session_id variable contained full session
serialized instead of just a session id.
Thanks to Ivan Ristić.
*) Bugfix: nginx incorrectly handled escaped "?" character in the
"include" SSI command.
*) Bugfix: the ngx_http_dav_module did not unescape destination URI of
the COPY and MOVE methods.
*) Bugfix: resolver did not understand domain names with a trailing dot.
Thanks to Yichun Zhang.
*) Bugfix: client connections might be immediately closed if deferred
accept was used; the bug had appeared in 1.3.15.
*) Bugfix: alerts "zero size buf in output" might appear in logs while
proxying; the bug had appeared in 1.3.9.
@ -170,217 +41,53 @@ Changes with nginx 1.5.9 22 Jan 2014
*) Bugfix: proxied WebSocket connections might hang right after
handshake if the select, poll, or /dev/poll methods were used.
*) Bugfix: the "xclient" directive of the mail proxy module incorrectly
handled IPv6 client addresses.
Changes with nginx 1.5.8 17 Dec 2013
*) Feature: IPv6 support in resolver.
*) Feature: the "listen" directive supports the "fastopen" parameter.
Thanks to Mathew Rodley.
*) Feature: SSL support in the ngx_http_uwsgi_module.
Thanks to Roberto De Ioris.
*) Feature: vim syntax highlighting scripts were added to contrib.
Thanks to Evan Miller.
*) Bugfix: a timeout might occur while reading client request body in an
SSL connection using chunked transfer encoding.
*) Bugfix: the "master_process" directive did not work correctly in
nginx/Windows.
*) Bugfix: the "setfib" parameter of the "listen" directive might not
work.
*) Bugfix: in the ngx_http_spdy_module.
*) Bugfix: memory leak in nginx/Windows.
Changes with nginx 1.5.7 19 Nov 2013
Changes with nginx 1.4.4 19 Nov 2013
*) Security: a character following an unescaped space in a request line
was handled incorrectly (CVE-2013-4547); the bug had appeared in
0.8.41.
Thanks to Ivan Fratric of the Google Security Team.
*) Change: a logging level of auth_basic errors about no user/password
provided has been lowered from "error" to "info".
*) Feature: the "proxy_cache_revalidate", "fastcgi_cache_revalidate",
"scgi_cache_revalidate", and "uwsgi_cache_revalidate" directives.
*) Feature: the "ssl_session_ticket_key" directive.
Thanks to Piotr Sikora.
*) Bugfix: the directive "add_header Cache-Control ''" added a
"Cache-Control" response header line with an empty value.
*) Bugfix: the "satisfy any" directive might return 403 error instead of
401 if auth_request and auth_basic directives were used.
Thanks to Jan Marc Hoffmann.
*) Bugfix: the "accept_filter" and "deferred" parameters of the "listen"
directive were ignored for listen sockets created during binary
upgrade.
Thanks to Piotr Sikora.
*) Bugfix: some data received from a backend with unbufferred proxy
might not be sent to a client immediately if "gzip" or "gunzip"
directives were used.
Thanks to Yichun Zhang.
*) Bugfix: in error handling in ngx_http_gunzip_filter_module.
*) Bugfix: responses might hang if the ngx_http_spdy_module was used
with the "auth_request" directive.
*) Bugfix: memory leak in nginx/Windows.
Changes with nginx 1.5.6 01 Oct 2013
*) Feature: the "fastcgi_buffering" directive.
*) Feature: the "proxy_ssl_protocols" and "proxy_ssl_ciphers"
directives.
Thanks to Piotr Sikora.
*) Feature: optimization of SSL handshakes when using long certificate
chains.
*) Feature: the mail proxy supports SMTP pipelining.
*) Bugfix: in the ngx_http_auth_basic_module when using "$apr1$"
password encryption method.
Thanks to Markus Linnala.
*) Bugfix: in MacOSX, Cygwin, and nginx/Windows incorrect location might
be used to process a request if locations were given using characters
in different cases.
*) Bugfix: automatic redirect with appended trailing slash for proxied
locations might not work.
*) Bugfix: in the mail proxy server.
*) Bugfix: in the ngx_http_spdy_module.
Changes with nginx 1.5.5 17 Sep 2013
*) Change: now nginx assumes HTTP/1.0 by default if it is not able to
detect protocol reliably.
*) Feature: the "disable_symlinks" directive now uses O_PATH on Linux.
*) Feature: now nginx uses EPOLLRDHUP events to detect premature
connection close by clients if the "epoll" method is used.
*) Bugfix: in the "valid_referers" directive if the "server_names"
parameter was used.
*) Bugfix: the $request_time variable did not work in nginx/Windows.
*) Bugfix: in the "image_filter" directive.
Thanks to Lanshun Zhou.
*) Bugfix: OpenSSL 1.0.1f compatibility.
Thanks to Piotr Sikora.
Changes with nginx 1.5.4 27 Aug 2013
*) Change: the "js" extension MIME type has been changed to
"application/javascript"; default value of the "charset_types"
directive was changed accordingly.
*) Change: now the "image_filter" directive with the "size" parameter
returns responses with the "application/json" MIME type.
*) Feature: the ngx_http_auth_request_module.
*) Bugfix: a segmentation fault might occur on start or during
reconfiguration if the "try_files" directive was used with an empty
parameter.
*) Bugfix: memory leak if relative paths were specified using variables
in the "root" or "auth_basic_user_file" directives.
*) Bugfix: the "valid_referers" directive incorrectly executed regular
expressions if a "Referer" header started with "https://".
Thanks to Liangbin Li.
*) Bugfix: responses might hang if subrequests were used and an SSL
handshake error happened during subrequest processing.
Thanks to Aviram Cohen.
*) Bugfix: in the ngx_http_autoindex_module.
*) Bugfix: in the ngx_http_spdy_module.
Changes with nginx 1.5.3 30 Jul 2013
*) Change in internal API: now u->length defaults to -1 if working with
backends in unbuffered mode.
*) Change: now after receiving an incomplete response from a backend
server nginx tries to send an available part of the response to a
client, and then closes client connection.
Changes with nginx 1.4.3 08 Oct 2013
*) Bugfix: a segmentation fault might occur in a worker process if the
ngx_http_spdy_module was used with the "client_body_in_file_only"
directive.
*) Bugfix: the "so_keepalive" parameter of the "listen" directive might
be handled incorrectly on DragonFlyBSD.
Thanks to Sepherosa Ziehau.
*) Bugfix: a segmentation fault might occur on start or during
reconfiguration if the "try_files" directive was used with an empty
parameter.
*) Bugfix: in the ngx_http_xslt_filter_module.
*) Bugfix: the $request_time variable did not work in nginx/Windows.
*) Bugfix: in the ngx_http_sub_filter_module.
*) Bugfix: in the ngx_http_auth_basic_module when using "$apr1$"
password encryption method.
Thanks to Markus Linnala.
*) Bugfix: in the ngx_http_autoindex_module.
*) Bugfix: in the mail proxy server.
Changes with nginx 1.5.2 02 Jul 2013
*) Feature: now several "error_log" directives can be used.
Changes with nginx 1.4.2 17 Jul 2013
*) Bugfix: the $r->header_in() embedded perl method did not return value
of the "Cookie" and "X-Forwarded-For" request header lines; the bug
had appeared in 1.3.14.
*) Bugfix: in the ngx_http_spdy_module.
Thanks to Jim Radford.
*) Bugfix: nginx could not be built on Linux with x32 ABI.
Thanks to Serguei Ivantsov.
Changes with nginx 1.5.1 04 Jun 2013
*) Feature: the "ssi_last_modified", "sub_filter_last_modified", and
"xslt_last_modified" directives.
Thanks to Alexey Kolpakov.
*) Feature: the "http_403" parameter of the "proxy_next_upstream",
"fastcgi_next_upstream", "scgi_next_upstream", and
"uwsgi_next_upstream" directives.
*) Feature: the "allow" and "deny" directives now support unix domain
sockets.
*) Bugfix: nginx could not be built with the ngx_mail_ssl_module, but
without ngx_http_ssl_module; the bug had appeared in 1.3.14.
*) Bugfix: in the "proxy_set_body" directive.
Thanks to Lanshun Zhou.
*) Bugfix: in the "lingering_time" directive.
Thanks to Lanshun Zhou.
*) Bugfix: the "fail_timeout" parameter of the "server" directive in the
"upstream" context might not work if "max_fails" parameter was used;
the bug had appeared in 1.3.0.
@ -389,14 +96,11 @@ Changes with nginx 1.5.1 04 Jun 2013
"ssl_stapling" directive was used.
Thanks to Piotr Sikora.
*) Bugfix: in the mail proxy server.
Thanks to Filipe Da Silva.
*) Bugfix: nginx/Windows might stop accepting connections if several
worker processes were used.
Changes with nginx 1.5.0 07 May 2013
Changes with nginx 1.4.1 07 May 2013
*) Security: a stack-based buffer overflow might occur in a worker
process while handling a specially crafted request, potentially
@ -6393,7 +6097,7 @@ Changes with nginx 0.1.16 25 Jan 2005
*) Bugfix: the compressed response encrypted by SSL may not transferred
complete.
*) Bugfix: the TCP-specific TCP_NODELAY, TCP_NOPUSH, and TCP_CORK
*) Bugfix: the TCP-specific TCP_NODELAY, TCP_NOPSUH, and TCP_CORK
options, are not used for the unix domain sockets.
*) Feature: the rewrite directive supports the arguments rewriting.

View file

@ -1,40 +1,3 @@
Tengine 2.1.1 [2015-08-12]
* Feature: 支持动态upstream更新 [yzprofile]
* Feature: 增强ngx_http_reqstat_module模块 [cfsego]
* Feature: 增加ssl_verify_client_exception指令 [InfoHunter]
* Change: 降低解析配置的内存消耗 [ilexshen]
* Change: trim模块增加$trim_bytes和$trim_original_bytes [taoyuanyuan]
* Change: 升级debian二进制包的版本到2.1.0 [PeterDaveHello]
* Change: 将ngx_http_spdy_module模块集成到travis-ci自动编译 [chobits]
* Change: 更新SPDY/3.1 [chobits]
* Change: SPDY时关闭proxy_request_buffering指令 [chobits]
* Change: 增加编译选项支持设置linker [tanguofu]
* Bugfix: 修复SPDY的Backport bug [nginx official, ym]
* Bugfix: SPDY和SSL模块一起编译时报错 [ym]
* Bugfix: 修复打开reuseport的bug [monadbobo]
Tengine 2.1.0 [2014-12-19]
* Feature: 支持SO_REUSEPORT选项以提升CPU负载均衡性和性能 [monadbobo]
* Feature: 支持动态解析upstream中出现的域名 [InfoHunter]
* Feature: rewrite指令支持重定向到命名location [yzprofile]
* Feature: image_filter指令支持crop_keepx和crop_keepy参数 [Lax]
* Feature: consistent_hash模块和session_sticky模块支持SSL会话保持 [dinic]
* Feature: 支持travis-ci.org自动编译 [Jamyn]
* Feature: 健康检查模块支持FASTCGI检查 [yzprofile]
* Feature: 增强sysguard模块的功能 [InfoHunter]
* Feature: 新增变量$normalized_request得到规范化的请求 [yunkai]
* Feature: dso的include指令支持通配符 [monadbobo]
* Feature: 新增gzip_clear_etag指令 [taoyuanyuan]
* Feature: 为log_escape指令添加unprintable参数 [skoo87]
* Change: 合并nginx-1.6.2版本的修改 [cfsego, taoyuanyuan, chobits]
* Change: round robin负载均衡算法随机选择某个源站作为循环起点 [taoyuanyuan]
* Change: 对共享内存中的碎片进行优化 [chobits]
* Bugfix: SPDY/3关闭连接时去掉drop标志 [chobits]
* Bugfix: 修复SPDY/3出现连接泄漏的问题 [chobits]
* Bugfix: 修复limit_req模块将长度超过255个字符的key截断的问题 [chobits]
* Bugfix: 解析/etc/resolv.conf中的IPv6地址出错 [lifeibo]
* Bugfix: 通过红黑树查找到错误的upstream [taoyuanyuan]
Tengine 2.0.3 [2014-05-30]
* Feature: 支持按指定维度(域名url等)收集Tengine运行状态 [cfsego]
* Feature: 支持debian、ubuntu打包 [betetrpm, szepeviktor]

View file

@ -1,69 +1,5 @@
Изменения в nginx 1.6.2 16.09.2014
*) Безопасность: при использовании общего для нескольких блоков server
разделяемого кэша SSL-сессий или общего ключа для шифрования TLS
session tickets было возможно повторно использовать SSL-сессию в
контексте другого блока server (CVE-2014-3616).
Спасибо Antoine Delignat-Lavaud.
*) Исправление: запросы могли зависать, если использовался resolver и
DNS-сервер возвращал некорректный ответ; ошибка появилась в 1.5.8.
*) Исправление: запросы могли зависать, если использовался resolver и в
процессе обращения к DNS-серверу происходил таймаут.
Изменения в nginx 1.6.1 05.08.2014
*) Безопасность: pipelined-команды не отбрасывались после команды
STARTTLS в SMTP прокси-сервере (CVE-2014-3556); ошибка появилась в
1.5.6.
Спасибо Chris Boulton.
*) Исправление: переменная $uri могла содержать мусор при возврате
ошибок с кодом 400.
Спасибо Сергею Боброву.
*) Исправление: в работе параметра none директивы smtp_auth; ошибка
появилась в 1.5.6.
Спасибо Святославу Никольскому.
Изменения в nginx 1.6.0 24.04.2014
*) Стабильная ветка 1.6.x.
Изменения в nginx 1.5.13 08.04.2014
*) Изменение: улучшена обработка хэш-таблиц; в директивах
variables_hash_max_size и types_hash_bucket_size значения по
умолчанию изменены на 1024 и 64 соответственно.
*) Добавление: модуль ngx_http_mp4_module теперь понимает аргумент end.
*) Добавление: поддержка byte ranges модулем ngx_http_mp4_module и при
сохранении ответов в кэш.
*) Исправление: теперь nginx не пишет в лог сообщения "ngx_slab_alloc()
failed: no memory" при использовании разделяемой памяти в
ssl_session_cache и в модуле ngx_http_limit_req_module.
*) Исправление: директива underscores_in_headers не разрешала
подчёркивание в первом символе заголовка.
Спасибо Piotr Sikora.
*) Исправление: cache manager мог нагружать процессор при выходе в
nginx/Windows.
*) Исправление: при использовании ssl_session_cache с параметром shared
рабочий процесс nginx/Windows завершался аварийно.
*) Исправление: в модуле ngx_http_spdy_module.
Изменения в nginx 1.5.12 18.03.2014
Изменения в nginx 1.4.7 18.03.2014
*) Безопасность: при обработке специально созданного запроса модулем
ngx_http_spdy_module могло происходить переполнение буфера в рабочем
@ -72,24 +8,11 @@
Спасибо Lucas Molas из Programa STIC, Fundación Dr. Manuel Sadosky,
Buenos Aires, Argentina.
*) Добавление: параметр proxy_protocol в директивах listen и
real_ip_header, переменная $proxy_protocol_addr.
*) Исправление: в директиве fastcgi_next_upstream.
Спасибо Lucas Molas.
Изменения в nginx 1.5.11 04.03.2014
*) Безопасность: при обработке специально созданного запроса модулем
ngx_http_spdy_module на 32-битных платформах могла повреждаться
память рабочего процесса, что потенциально могло приводить к
выполнению произвольного кода (CVE-2014-0088); ошибка появилась в
1.5.10.
Спасибо Lucas Molas из Programa STIC, Fundación Dr. Manuel Sadosky,
Buenos Aires, Argentina.
*) Добавление: переменная $ssl_session_reused.
Изменения в nginx 1.4.6 04.03.2014
*) Исправление: директива client_max_body_size могла не работать при
чтении тела запроса с использованием chunked transfer encoding;
@ -99,74 +22,15 @@
*) Исправление: при проксировании WebSocket-соединений в рабочем
процессе мог произойти segmentation fault.
*) Исправление: в рабочем процессе мог произойти segmentation fault,
если использовался модуль ngx_http_spdy_module на 32-битных
платформах; ошибка появилась в 1.5.10.
*) Исправление: значение переменной $upstream_status могло быть
неверным, если использовались директивы proxy_cache_use_stale или
proxy_cache_revalidate.
Спасибо Piotr Sikora.
*) Исправление: в рабочем процессе мог произойти segmentation fault,
если ошибки с кодом 400 с помощью директивы error_page
перенаправлялись в именованный location.
*) Исправление: nginx/Windows не собирался с Visual Studio 2013.
Изменения в nginx 1.5.10 04.02.2014
*) Добавление: модуль ngx_http_spdy_module теперь использует протокол
SPDY 3.1.
Спасибо Automattic и MaxCDN за спонсирование разработки.
*) Добавление: модуль ngx_http_mp4_module теперь пропускает дорожки,
имеющие меньшую длину, чем запрошенная перемотка.
*) Исправление: в рабочем процессе мог произойти segmentation fault,
если переменная $ssl_session_id использовалась при логгировании;
ошибка появилась в 1.5.9.
*) Исправление: переменные $date_local и $date_gmt использовали неверный
формат вне модуля ngx_http_ssi_filter_module.
*) Исправление: клиентские соединения могли сразу закрываться, если
использовался отложенный accept; ошибка появилась в 1.3.15.
*) Исправление: сообщения "getsockopt(TCP_FASTOPEN) ... failed"
записывались в лог в процессе обновления исполняемого файла на Linux;
ошибка появилась в 1.5.8.
Спасибо Piotr Sikora.
Изменения в nginx 1.5.9 22.01.2014
*) Изменение: теперь в заголовке X-Accel-Redirect nginx ожидает
закодированный URI.
*) Добавление: директива ssl_buffer_size.
*) Добавление: директиву limit_rate теперь можно использовать для
ограничения скорости передачи ответов клиенту в SPDY-соединениях.
*) Добавление: директива spdy_chunk_size.
*) Добавление: директива ssl_session_tickets.
Спасибо Dirkjan Bussink.
Изменения в nginx 1.4.5 11.02.2014
*) Исправление: переменная $ssl_session_id содержала всю сессию в
сериализованном виде вместо её идентификатора.
Спасибо Ivan Ristić.
*) Исправление: nginx неправильно обрабатывал закодированный символ "?"
в команде SSI include.
*) Исправление: модуль ngx_http_dav_module не раскодировал целевой URI
при обработке методов COPY и MOVE.
*) Исправление: resolver не понимал доменные имена с точкой в конце.
Спасибо Yichun Zhang.
*) Исправление: клиентские соединения могли сразу закрываться, если
использовался отложенный accept; ошибка появилась в 1.3.15.
*) Исправление: при проксировании в логах могли появляться сообщения
"zero size buf in output"; ошибка появилась в 1.3.9.
@ -178,219 +42,53 @@
poll и /dev/poll проксируемые WebSocket-соединения могли зависать
сразу после открытия.
*) Исправление: директива xclient почтового прокси-сервера некорректно
передавала IPv6-адреса.
Изменения в nginx 1.5.8 17.12.2013
*) Добавление: теперь resolver поддерживает IPv6.
*) Добавление: директива listen поддерживает параметр fastopen.
Спасибо Mathew Rodley.
*) Добавление: поддержка SSL в модуле ngx_http_uwsgi_module.
Спасибо Roberto De Ioris.
*) Добавление: скрипты подсветки синтаксиса для vim добавлены в contrib.
Спасибо Evan Miller.
*) Исправление: при чтении тела запроса с использованием chunked
transfer encoding по SSL-соединению мог произойти таймаут.
*) Исправление: директива master_process работала неправильно в
nginx/Windows.
*) Исправление: параметр setfib директивы listen мог не работать.
*) Исправление: в модуле ngx_http_spdy_module.
*) Исправление: утечки памяти в nginx/Windows.
Изменения в nginx 1.5.7 19.11.2013
Изменения в nginx 1.4.4 19.11.2013
*) Безопасность: символ, следующий за незакодированным пробелом в строке
запроса, обрабатывался неправильно (CVE-2013-4547); ошибка появилась
в 0.8.41.
Спасибо Ivan Fratric из Google Security Team.
*) Изменение: уровень логгирования ошибок auth_basic об отсутствии
пароля понижен с уровня error до info.
*) Добавление: директивы proxy_cache_revalidate,
fastcgi_cache_revalidate, scgi_cache_revalidate и
uwsgi_cache_revalidate.
*) Добавление: директива ssl_session_ticket_key.
Спасибо Piotr Sikora.
*) Исправление: директива "add_header Cache-Control ''" добавляла строку
заголовка ответа "Cache-Control" с пустым значением.
*) Исправление: директива "satisfy any" могла вернуть ошибку 403 вместо
401 при использовании директив auth_request и auth_basic.
Спасибо Jan Marc Hoffmann.
*) Исправление: параметры accept_filter и deferred директивы listen
игнорировались для listen-сокетов, создаваемых в процессе обновления
исполняемого файла.
Спасибо Piotr Sikora.
*) Исправление: часть данных, полученных от бэкенда при
небуферизированном проксировании, могла не отправляться клиенту
сразу, если использовались директивы gzip или gunzip.
Спасибо Yichun Zhang.
*) Исправление: в обработке ошибок в модуле
ngx_http_gunzip_filter_module.
*) Исправление: ответы могли зависать, если использовался модуль
ngx_http_spdy_module и директива auth_request.
*) Исправление: утечки памяти в nginx/Windows.
Изменения в nginx 1.5.6 01.10.2013
*) Добавление: директива fastcgi_buffering.
*) Добавление: директивы proxy_ssl_protocols и proxy_ssl_ciphers.
Спасибо Piotr Sikora.
*) Добавление: оптимизация SSL handshake при использовании длинных
цепочек сертификатов.
*) Добавление: почтовый прокси-сервер поддерживает SMTP pipelining.
*) Исправление: в модуле ngx_http_auth_basic_module при использовании
метода шифрования паролей "$apr1$".
Спасибо Markus Linnala.
*) Исправление: на MacOSX, Cygwin и nginx/Windows для обработки запроса
мог использоваться неверный location, если для задания location'ов
использовались символы разных регистров.
*) Исправление: автоматическое перенаправление с добавлением
завершающего слэша для проксированных location'ов могло не работать.
*) Исправление: в почтовом прокси-сервере.
*) Исправление: в модуле ngx_http_spdy_module.
Изменения в nginx 1.5.5 17.09.2013
*) Изменение: теперь nginx по умолчанию использует HTTP/1.0, если точно
определить протокол не удалось.
*) Добавление: директива disable_symlinks теперь использует O_PATH на
Linux.
*) Добавление: для определения того, что клиент закрыл соединение, при
использовании метода epoll теперь используются события EPOLLRDHUP.
*) Исправление: в директиве valid_referers при использовании параметра
server_names.
*) Исправление: переменная $request_time не работала в nginx/Windows.
*) Исправление: в директиве image_filter.
Спасибо Lanshun Zhou.
*) Исправление: совместимость с OpenSSL 1.0.1f.
Спасибо Piotr Sikora.
Изменения в nginx 1.5.4 27.08.2013
*) Изменение: MIME-тип для расширения js изменён на
"application/javascript"; значение по умолчанию директивы
charset_types изменено соответственно.
*) Изменение: теперь директива image_filter с параметром size возвращает
ответ с MIME-типом "application/json".
*) Добавление: модуль ngx_http_auth_request_module.
*) Исправление: на старте или во время переконфигурации мог произойти
segmentation fault, если использовалась директива try_files с пустым
параметром.
*) Исправление: утечки памяти при использовании в директивах root и
auth_basic_user_file относительных путей, заданных с помощью
переменных.
*) Исправление: директива valid_referers неправильно выполняла
регулярные выражения, если заголовок Referer начинался с "https://".
Спасибо Liangbin Li.
*) Исправление: ответы могли зависать, если использовались подзапросы и
при обработке подзапроса происходила ошибка во время SSL handshake с
бэкендом.
Спасибо Aviram Cohen.
*) Исправление: в модуле ngx_http_autoindex_module.
*) Исправление: в модуле ngx_http_spdy_module.
Изменения в nginx 1.5.3 30.07.2013
*) Изменение во внутреннем API: теперь при небуферизированной работе с
бэкендами u->length по умолчанию устанавливается в -1.
*) Изменение: теперь при получении неполного ответа от бэкенда nginx
отправляет полученную часть ответа, после чего закрывает соединение с
клиентом.
Изменения в nginx 1.4.3 08.10.2013
*) Исправление: в рабочем процессе мог произойти segmentation fault,
если использовался модуль ngx_http_spdy_module и директива
client_body_in_file_only.
*) Исправление: параметр so_keepalive директивы listen мог работать
некорректно на DragonFlyBSD.
Спасибо Sepherosa Ziehau.
*) Исправление: на старте или во время переконфигурации мог произойти
segmentation fault, если использовалась директива try_files с пустым
параметром.
*) Исправление: в модуле ngx_http_xslt_filter_module.
*) Исправление: переменная $request_time не работала в nginx/Windows.
*) Исправление: в модуле ngx_http_sub_filter_module.
*) Исправление: в модуле ngx_http_auth_basic_module при использовании
метода шифрования паролей "$apr1$".
Спасибо Markus Linnala.
*) Исправление: в модуле ngx_http_autoindex_module.
*) Исправление: в почтовом прокси-сервере.
Изменения в nginx 1.5.2 02.07.2013
*) Добавление: теперь можно использовать несколько директив error_log.
Изменения в nginx 1.4.2 17.07.2013
*) Исправление: метод $r->header_in() встроенного перла не возвращал
значения строк "Cookie" и "X-Forwarded-For" из заголовка запроса;
ошибка появилась в 1.3.14.
*) Исправление: в модуле ngx_http_spdy_module.
Спасибо Jim Radford.
*) Исправление: nginx не собирался на Linux при использовании x32 ABI.
Спасибо Сергею Иванцову.
Изменения в nginx 1.5.1 04.06.2013
*) Добавление: директивы ssi_last_modified, sub_filter_last_modified и
xslt_last_modified.
Спасибо Алексею Колпакову.
*) Добавление: параметр http_403 в директивах proxy_next_upstream,
fastcgi_next_upstream, scgi_next_upstream и uwsgi_next_upstream.
*) Добавление: директивы allow и deny теперь поддерживают unix domain
сокеты.
*) Исправление: nginx не собирался с модулем ngx_mail_ssl_module, но без
модуля ngx_http_ssl_module; ошибка появилась в 1.3.14.
*) Исправление: в директиве proxy_set_body.
Спасибо Lanshun Zhou.
*) Исправление: в директиве lingering_time.
Спасибо Lanshun Zhou.
*) Исправление: параметр fail_timeout директивы server в блоке upstream
мог не работать, если использовался параметр max_fails; ошибка
появилась в 1.3.0.
@ -399,14 +97,11 @@
если использовалась директива ssl_stapling.
Спасибо Piotr Sikora.
*) Исправление: в почтовом прокси-сервере.
Спасибо Filipe Da Silva.
*) Исправление: nginx/Windows мог перестать принимать соединения, если
использовалось несколько рабочих процессов.
Изменения в nginx 1.5.0 07.05.2013
Изменения в nginx 1.4.1 07.05.2013
*) Безопасность: при обработке специально созданного запроса мог
перезаписываться стек рабочего процесса, что могло приводить к
@ -732,7 +427,7 @@
*) Изменение: параметр single директивы keepalive теперь игнорируется.
*) Изменение: сжатие SSL теперь отключено в том числе при использовании
OpenSSL старее 1.0.0.
OpenSSL cтарее 1.0.0.
*) Добавление: директиву "ip_hash" теперь можно использовать для
балансировки IPv6 клиентов.
@ -3009,7 +2704,7 @@
умолчанию; ошибка появилась в 0.7.18.
Спасибо Максиму Дунину.
*) Исправление: при проксировании SMTP nginx выдавал сообщение
*) Исправление: при проксировании SMPT nginx выдавал сообщение
"250 2.0.0 OK" вместо "235 2.0.0 OK"; ошибка появилась в 0.7.22.
Спасибо Максиму Дунину.
@ -6495,7 +6190,7 @@
*) Исправление: при использовании SSL сжатый ответ мог передаваться не
до конца.
*) Исправление: опции TCP_NODELAY, TCP_NOPUSH и TCP_CORK, специфичные
*) Исправление: опции TCP_NODELAY, TCP_NOPSUH и TCP_CORK, специфичные
для TCP сокетов, не используются для unix domain сокетов.
*) Добавление: директива rewrite поддерживает перезаписывание
@ -6559,7 +6254,7 @@
*) Изменение: если в URI встречался символ %3F, то он считался началом
строки аргументов.
*) Добавление: поддержка unix domain сокетов в модуле
*) Добавление: поддержка unix domain сoкетов в модуле
ngx_http_proxy_module.
*) Добавление: директивы ssl_engine и ssl_ciphers.

View file

@ -1,86 +1,3 @@
Changes with Tengine 2.1.1 12 Aug 2015
*) Feature: support for dynamic upstream update. (yzprofile)
*) Feature: enchanced ngx_http_reqstat_module. (cfsego)
*) Feature: added ssl_verify_client_exception directive. (InfoHunter)
*) Change: Reduced memory usage while parsing configuration. (ilexshen)
*) Change: added $trim_bytes and $trim_original_bytes. (taoyuanyuan)
*) Change: upgrade debian package to 2.1.0 (PeterDaveHello)
*) Change: support for auto compile for ngx_http_spdy_module. (chobits)
*) Change: updated SPDY/3.1. (chobits)
*) Change: disabled 'proxy_request_buffering' for SPDY. (chobits)
*) Change: added configue options to support set linker. (tanguofu)
*) Bugfix: fixed Backport bug of SPDY (nginx official, ym)
*) Bugfix: fixed compile error with SSL. (ym)
*) Bugfix: fixed bug of reuseport. (monadbobo)
Changes with Tengine 2.1.0 19 Dec 2014
*) Feature: support the SO_REUSEPORT option, to improve performance on
multicore systems. (monadbobo)
*) Feature: support for resolving upstream domain names on the fly.
(InfoHunter)
*) Feature: support for rewriting to named locations. (yzprofile)
*) Feature: added two parameters 'crop_keepx' and 'crop_keepy' to the
directive 'image_filter'. (Lax)
*) Feature: support for saving SSL sessions in consistent_hash module and
session_sticky module. (dinic)
*) Feature: support for compiling Tengine automatically in travis-ci.org.
(Jamyn)
*) Feature: support for FastCGI health check. (yzprofile)
*) Feature: enhanced sysguard module. (InfoHunter)
*) Feature: added a variable '$normalized_request', to get normalized
request URIs. (yunkai)
*) Feature: added wildcard support for 'include' directive in 'dso' block.
(monadbobo)
*) Feature: added the 'gzip_clear_etag' directive. (taoyuanyuan)
*) Feature: added the 'unprintable' parameter to the 'log_escape' directive.
(skoo87)
*) Change: merged changes from nginx-1.6.2. (cfsego, taoyuanyuan, chobits)
*) Change: now the order of servers in an upstream are random when
initialized. (taoyuanyuan)
*) Change: slab allocator free pages defragmentation. (chobits)
*) Bugfix: SPDY/3 dropped the "delayed" flag when finalizing connection.
(chobits)
*) Bugfix: fixed SPDY/3 connection leak. (chobits)
*) Bugfix: now don't truncate value of key to 255 bytes in limit_req module.
(chobits)
*) Bugfix: failed to parse /etc/resolv.conf with IPv6 addresses. (lifeibo)
*) Bugfix: upstream rbtree bugfix. (taoyuanyuan)
Changes with Tengine 2.0.3 30 May 2014
*) Feature: added support for collecting the running status of Tengine

View file

@ -1,7 +1,7 @@
/*
* Copyright (C) 2002-2013 Igor Sysoev
* Copyright (C) 2011,2013 Nginx, Inc.
* Copyright (C) 2010-2015 Alibaba Group Holding Limited
* Copyright (C) 2010-2014 Alibaba Group Holding Limited
* Copyright (C) 2011-2013 Xiaozhe "chaoslawful" Wang
* Copyright (C) 2011-2013 Zhang "agentzh" Yichun
* Copyright (C) 2011-2013 Weibin Yao

View file

@ -8,7 +8,7 @@ Tengine has been an open source project since December 2011. It is being activel
Features
--------
* All features of nginx-1.6.2 are inherited, i.e., it is 100% compatible with nginx.
* All features of nginx-1.4.4 are inherited, i.e., it is 100% compatible with nginx.
* Dynamic module loading support. You don't need to recompile Tengine when adding new modules to it.
* SPDY v3 support, and SPDY/HTTP servers can listen on the same port.
* Sends unbuffered upload directly to HTTP and FastCGI backend servers, which saves disk I/Os.

View file

@ -1,5 +1,5 @@
Introduction [![Build Status](https://travis-ci.org/alibaba/tengine.svg?branch=master)](https://travis-ci.org/alibaba/tengine)
Introduction
============
Tengine is a web server originated by [Taobao](http://en.wikipedia.org/wiki/Taobao), the largest e-commerce website in Asia. It is based on the [Nginx](http://nginx.org) HTTP server and has many advanced features. Tengine has proven to be very stable and efficient on some of the top 100 websites in the world, including [taobao.com](http://www.taobao.com) and [tmall.com](http://www.tmall.com).
@ -9,7 +9,7 @@ Tengine has been an open source project since December 2011. It is being activel
Features
========
* All features of nginx-1.6.2 are inherited, i.e., it is 100% compatible with nginx.
* All features of nginx-1.4.4 are inherited, i.e., it is 100% compatible with nginx.
* Dynamic module loading support. You don't need to recompile Tengine when adding new modules to it.
* SPDY v3 support, and SPDY/HTTP servers can listen on the same port.
* Sends unbuffered upload directly to HTTP and FastCGI backend servers, which saves disk I/Os.

View file

@ -5,8 +5,8 @@
# clang
NGX_CLANG_VER=`$CC -v 2>&1 | grep '\(clang\|LLVM\) version' 2>&1 \
| sed -e 's/^.* version \(.*\)/\1/'`
NGX_CLANG_VER=`$CC -v 2>&1 | grep 'clang version' 2>&1 \
| sed -e 's/^.*clang version \(.*\)/\1/'`
echo " + clang version: $NGX_CLANG_VER"
@ -82,14 +82,13 @@ fi
# warnings
CFLAGS="$CFLAGS $NGX_CLANG_OPT -Wall -Wextra -Wpointer-arith"
#CFLAGS="$CFLAGS -Wconditional-uninitialized"
#CFLAGS="$CFLAGS -Wmissing-prototypes"
# we have a lot of unused function arguments
CFLAGS="$CFLAGS -Wno-unused-parameter"
# stop on warning
CFLAGS="$CFLAGS -Werror"
#CFLAGS="$CFLAGS -Werror"
# debug
CFLAGS="$CFLAGS -g"

View file

@ -3,7 +3,7 @@
# Copyright (C) Nginx, Inc.
LINK=${LINK:-"\$(CC)"}
LINK="\$(CC)"
ngx_include_opt="-I "
ngx_compile_opt="-c"
@ -43,29 +43,6 @@ if test -n "$CFLAGS"; then
ngx_include_opt="-I"
;;
sunc)
case "$NGX_MACHINE" in
i86pc)
NGX_AUX=" src/os/unix/ngx_sunpro_x86.il"
;;
sun4u | sun4v)
NGX_AUX=" src/os/unix/ngx_sunpro_sparc64.il"
;;
esac
case $CPU in
amd64)
NGX_AUX=" src/os/unix/ngx_sunpro_amd64.il"
;;
esac
;;
esac
else

View file

@ -106,7 +106,6 @@ fi
# precompiled headers
CORE_DEPS="$CORE_DEPS $NGX_OBJS/ngx_config.pch"
CORE_LINK="$CORE_LINK $NGX_OBJS/ngx_pch.obj"
NGX_PCH="$NGX_OBJS/ngx_config.pch"
NGX_BUILD_PCH="-Ycngx_config.h -Fp$NGX_OBJS/ngx_config.pch"
NGX_USE_PCH="-Yungx_config.h -Fp$NGX_OBJS/ngx_config.pch"

View file

@ -67,7 +67,7 @@ elif `$CC -v 2>&1 | grep 'gcc version' >/dev/null 2>&1`; then
NGX_CC_NAME=gcc
echo " + using GNU C compiler"
elif `$CC -v 2>&1 | grep '\(clang\|LLVM\) version' >/dev/null 2>&1`; then
elif `$CC -v 2>&1 | grep 'clang version' >/dev/null 2>&1`; then
NGX_CC_NAME=clang
echo " + using Clang C compiler"

View file

@ -65,10 +65,10 @@ have=NGX_HAVE_C99_VARIADIC_MACROS . auto/have
# the precompiled headers
#CORE_DEPS="$CORE_DEPS $NGX_OBJS/ngx_config.pch"
#NGX_PCH="$NGX_OBJS/ngx_config.pch"
#NGX_BUILD_PCH="-fhq=$NGX_OBJS/ngx_config.pch"
#NGX_USE_PCH="-fh=$NGX_OBJS/ngx_config.pch"
CORE_DEPS="$CORE_DEPS $NGX_OBJS/ngx_config.pch"
NGX_PCH="$NGX_OBJS/ngx_config.pch"
NGX_BUILD_PCH="-fhq=$NGX_OBJS/ngx_config.pch"
NGX_USE_PCH="-fh=$NGX_OBJS/ngx_config.pch"
# the link flags, built target is NT GUI mode application

View file

@ -30,7 +30,7 @@ if [ -x $NGX_AUTOTEST ]; then
ngx_sunc_ver=`$NGX_AUTOTEST`
fi
rm -rf $NGX_AUTOTEST*
rm $NGX_AUTOTEST*
# 1424 == 0x590, Sun Studio 12

View file

@ -34,10 +34,10 @@ if [ -x $NGX_AUTOTEST ]; then
echo " big endian"
fi
rm -rf $NGX_AUTOTEST*
rm $NGX_AUTOTEST*
else
rm -rf $NGX_AUTOTEST*
rm $NGX_AUTOTEST*
echo
echo "$0: error: cannot detect system byte ordering"

View file

@ -120,4 +120,4 @@ else
echo "----------" >> $NGX_AUTOCONF_ERR
fi
rm -rf $NGX_AUTOTEST*
rm $NGX_AUTOTEST*

View file

@ -58,4 +58,4 @@ else
echo "----------" >> $NGX_AUTOCONF_ERR
fi
rm -rf $NGX_AUTOTEST*
rm $NGX_AUTOTEST*

View file

@ -20,7 +20,7 @@ mkdir -p $NGX_OBJS/src/core $NGX_OBJS/src/event $NGX_OBJS/src/event/modules \
$NGX_OBJS/src/os/unix $NGX_OBJS/src/os/win32 \
$NGX_OBJS/src/http $NGX_OBJS/src/http/modules \
$NGX_OBJS/src/http/modules/perl \
$NGX_OBJS/modules/ngx_http_lua_module/src \
$NGX_OBJS/src/http/modules/lua \
$NGX_OBJS/src/http/modules/tfs \
$NGX_OBJS/src/mail \
$NGX_OBJS/src/misc \
@ -628,7 +628,7 @@ END
cat << END > $NGX_DSO_COMPILE
#!/bin/sh
# Copyright (C) 2010-2015 Alibaba Group Holding Limited
# Copyright (C) 2010-2014 Alibaba Group Holding Limited
ngx_soext='$NGX_SOEXT'

View file

@ -1,3 +1,4 @@
# Copyright (C) Igor Sysoev
# Copyright (C) Nginx, Inc.
@ -41,7 +42,6 @@ fi
if [ $NGX_TEST_BUILD_EPOLL = YES ]; then
have=NGX_HAVE_EPOLL . auto/have
have=NGX_HAVE_EPOLLRDHUP . auto/have
have=NGX_HAVE_EVENTFD . auto/have
have=NGX_TEST_BUILD_EPOLL . auto/have
EVENT_MODULES="$EVENT_MODULES $EPOLL_MODULE"
@ -324,11 +324,6 @@ if [ $HTTP_CONCAT_SHARED = YES ]; then
NGX_SHARED_SRCS="$NGX_SHARED_SRCS|$HTTP_CONCAT_SRCS"
fi
if [ $HTTP_AUTH_REQUEST = YES ]; then
HTTP_MODULES="$HTTP_MODULES $HTTP_AUTH_REQUEST_MODULE"
HTTP_SRCS="$HTTP_SRCS $HTTP_AUTH_REQUEST_SRCS"
fi
if [ $HTTP_AUTH_BASIC = YES ]; then
USE_MD5=YES
USE_SHA1=YES
@ -504,13 +499,18 @@ if [ $HTTP_PERL = YES ]; then
fi
if [ $HTTP_LUA = YES ]; then
NGX_ADDONS="$NGX_ADDONS modules/ngx_http_lua_module"
USE_MD5=YES
USE_SHA1=YES
CORE_INCS="$CORE_INCS src/http/modules/lua/api"
HTTP_AUX_FILTER_MODULES="$HTTP_AUX_FILTER_MODULES $NGX_HTTP_LUA_MODULE"
HTTP_DEPS="$HTTP_DEPS $NGX_HTTP_LUA_MODULE_DEPS"
HTTP_SRCS="$HTTP_SRCS $NGX_HTTP_LUA_MODULE_SRCS"
fi
if [ $HTTP_LUA_SHARED = YES ]; then
USE_MD5=YES
USE_SHA1=YES
CORE_INCS="$CORE_INCS modules/ngx_http_lua_module/src/api"
CORE_INCS="$CORE_INCS src/http/modules/lua/api"
NGX_SHARED_MODULES="$NGX_SHARED_MODULES $NGX_HTTP_LUA_MODULE"
HTTP_DEPS="$HTTP_DEPS $NGX_HTTP_LUA_MODULE_DEPS"
NGX_SHARED_SRCS="$NGX_SHARED_SRCS|$NGX_HTTP_LUA_MODULE_SRCS"
@ -695,21 +695,6 @@ if [ $HTTP_UPSTREAM_KEEPALIVE = YES ]; then
HTTP_SRCS="$HTTP_SRCS $HTTP_UPSTREAM_KEEPALIVE_SRCS"
fi
if [ $HTTP_UPSTREAM_DYNAMIC = YES ]; then
HTTP_MODULES="$HTTP_MODULES $HTTP_UPSTREAM_DYNAMIC_MODULE"
HTTP_SRCS="$HTTP_SRCS $HTTP_UPSTREAM_DYNAMIC_SRCS"
fi
if [ $HTTP_DYNAMIC_UPSTREAM = YES ]; then
HTTP_MODULES="$HTTP_MODULES $HTTP_DYUPS_MODULE"
HTTP_SRCS="$HTTP_SRCS $HTTP_DYUPS_SRCS"
if [ $HTTP_DYNAMIC_UPSTREAM_LUA = YES ]; then
HTTP_SRCS="$HTTP_SRCS $HTTP_DYUPS_LUA_SRCS"
HTTP_DEPS="$HTTP_DEPS $HTTP_DYUPS_LUA_DEPS"
have=NGX_DYUPS_LUA . auto/have
fi
fi
if [ $HTTP_STUB_STATUS = YES ]; then
have=NGX_STAT_STUB . auto/have
NGX_DSO_ABI_COMPATIBILITY=$(($NGX_DSO_ABI_COMPATIBILITY|$NGX_DSO_STAT_STUB_TAG))
@ -828,8 +813,6 @@ if [ $MAIL = YES ]; then
modules="$modules $MAIL_PROXY_MODULE"
MAIL_SRCS="$MAIL_SRCS $MAIL_PROXY_SRCS"
NGX_ADDON_DEPS="$NGX_ADDON_DEPS \$(MAIL_DEPS)"
fi

View file

@ -112,7 +112,6 @@ NGX_ALL_MODULES="
ngx_http_upstream_ip_hash_module
ngx_http_upstream_least_conn_module
ngx_http_upstream_keepalive_module
ngx_http_upstream_dynamic_module
ngx_http_upstream_check_module
ngx_http_upstream_consistent_hash_module
ngx_http_stub_status_module
@ -220,7 +219,6 @@ HTTP_ADDITION=NO
HTTP_DAV=NO
HTTP_ACCESS=YES
HTTP_AUTH_BASIC=YES
HTTP_AUTH_REQUEST=NO
HTTP_USERID=YES
HTTP_CONCAT=NO
HTTP_AUTOINDEX=YES
@ -260,9 +258,6 @@ HTTP_UPSTREAM_CHECK=YES
HTTP_UPSTREAM_LEAST_CONN=YES
HTTP_UPSTREAM_SESSION_STICKY=YES
HTTP_UPSTREAM_KEEPALIVE=YES
HTTP_UPSTREAM_DYNAMIC=YES
HTTP_DYNAMIC_UPSTREAM=NO
HTTP_DYNAMIC_UPSTREAM_LUA=NO
HTTP_UPSTREAM_CONSISTENT_HASH=YES
HTTP_UPSTREAM_CONSISTENT_HASH_SHARED=NO
HTTP_UPSTREAM_RBTREE=YES
@ -466,7 +461,6 @@ do
HTTP_MP4_SHARED=NO ;;
--with-http_gunzip_module) HTTP_GUNZIP=YES ;;
--with-http_gzip_static_module) HTTP_GZIP_STATIC=YES ;;
--with-http_auth_request_module) HTTP_AUTH_REQUEST=YES ;;
--with-http_concat_module) HTTP_CONCAT=YES
HTTP_CONCAT_SHARED=NO ;;
--with-http_random_index_module) HTTP_RANDOM_INDEX=YES
@ -624,10 +618,6 @@ use the \"--without-http_limit_conn_module\" option instead"
HTTP_UPSTREAM_SESSION_STICKY=NO
HTTP_UPSTREAM_SESSION_STICKY_SHARED=NO ;;
--without-http_upstream_keepalive_module) HTTP_UPSTREAM_KEEPALIVE=NO ;;
--without-http_upstream_dynamic_module) HTTP_UPSTREAM_DYNAMIC=NO ;;
--with-http_dyups_module) HTTP_DYNAMIC_UPSTREAM=YES ;;
--with-http_dyups_lua_api) HTTP_DYNAMIC_UPSTREAM_LUA=YES ;;
--with-http_perl_module) HTTP_PERL=YES ;;
--with-perl_modules_path=*) NGX_PERL_MODULES="$value" ;;
@ -668,7 +658,6 @@ use the \"--without-http_limit_conn_module\" option instead"
--with-cc=*) CC="$value" ;;
--with-cpp=*) CPP="$value" ;;
--with-link=*) LINK="$value" ;;
--with-cc-opt=*) NGX_CC_OPT="$value" ;;
--with-ld-opt=*) NGX_LD_OPT="$value" ;;
--with-cpu-opt=*) CPU="$value" ;;
@ -775,7 +764,6 @@ cat << END
--with-http_mp4_module enable ngx_http_mp4_module
--with-http_gunzip_module enable ngx_http_gunzip_module
--with-http_gzip_static_module enable ngx_http_gzip_static_module
--with-http_auth_request_module enable ngx_http_auth_request_module
--with-http_concat_module enable ngx_http_concat_module
--with-http_random_index_module enable ngx_http_random_index_module
--with-http_secure_link_module enable ngx_http_secure_link_module
@ -869,8 +857,6 @@ cat << END
disable ngx_http_upstream_session_sticky_module
--without-http_upstream_keepalive_module
disable ngx_http_upstream_keepalive_module
--without-http_upstream_dynamic_module
disable ngx_http_upstream_dynamic_module
--without-http_upstream_ip_hash_module
disable ngx_http_upstream_ip_hash_module
--without-http_upstream_consistent_hash_module
@ -879,8 +865,6 @@ cat << END
--without-http_stub_status_module disable ngx_http_stub_status_module
--without-http_reqstat_module disable ngx_http_reqstat_module
--with-http_dyups_module enable ngx_http_dyups_module
--with-http_perl_module enable ngx_http_perl_module
--with-perl_modules_path=PATH set Perl modules path
--with-perl=PATH set perl binary pathname
@ -928,7 +912,6 @@ cat << END
--with-cc=PATH set C compiler pathname
--with-cpp=PATH set C preprocessor pathname
--with-link=LINK set C linker
--with-cc-opt=OPTIONS set additional C compiler options
--with-ld-opt=OPTIONS set additional linker options
--with-cpu-opt=CPU build for the specified CPU, valid values:
@ -1092,7 +1075,6 @@ elif [ $NGX_STATIC_ALL_MODULES = YES ]; then
HTTP_SLICE=YES
HTTP_MP4=YES
HTTP_GZIP_STATIC=YES
HTTP_GUNZIP=YES
HTTP_UPSTREAM_IP_HASH=YES
HTTP_FOOTER=YES
HTTP_TRIM=YES
@ -1101,11 +1083,7 @@ elif [ $NGX_STATIC_ALL_MODULES = YES ]; then
HTTP_UPSTREAM_LEAST_CONN=YES
HTTP_UPSTREAM_SESSION_STICKY=YES
HTTP_UPSTREAM_KEEPALIVE=YES
HTTP_UPSTREAM_DYNAMIC=YES
HTTP_DYNAMIC_UPSTREAM=YES
HTTP_REQ_STATUS=YES
HTTP_AUTH_REQUEST=YES
MAIL=YES
HTTP_XSLT_SHARED=NO
HTTP_IMAGE_FILTER_SHARED=NO

View file

@ -112,5 +112,5 @@ ngx_feature_incs="#include <libkern/OSAtomic.h>"
ngx_feature_path=
ngx_feature_libs=
ngx_feature_test="int32_t lock, n;
n = OSAtomicCompareAndSwap32Barrier(0, 1, &lock)"
n = OSAtomicCompareAndSwap32Barrier(0, 1, lock)"
. auto/feature

View file

@ -65,41 +65,9 @@ if [ $ngx_found = yes ]; then
CORE_SRCS="$CORE_SRCS $EPOLL_SRCS"
EVENT_MODULES="$EVENT_MODULES $EPOLL_MODULE"
EVENT_FOUND=YES
# EPOLLRDHUP appeared in Linux 2.6.17, glibc 2.8
ngx_feature="EPOLLRDHUP"
ngx_feature_name="NGX_HAVE_EPOLLRDHUP"
ngx_feature_run=no
ngx_feature_incs="#include <sys/epoll.h>"
ngx_feature_path=
ngx_feature_libs=
ngx_feature_test="int efd = 0, fd = 0;
struct epoll_event ee;
ee.events = EPOLLIN|EPOLLRDHUP|EPOLLET;
ee.data.ptr = NULL;
epoll_ctl(efd, EPOLL_CTL_ADD, fd, &ee)"
. auto/feature
fi
# O_PATH and AT_EMPTY_PATH were introduced in 2.6.39, glibc 2.14
ngx_feature="O_PATH"
ngx_feature_name="NGX_HAVE_O_PATH"
ngx_feature_run=no
ngx_feature_incs="#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>"
ngx_feature_path=
ngx_feature_libs=
ngx_feature_test="int fd; struct stat sb;
fd = openat(AT_FDCWD, \".\", O_PATH|O_DIRECTORY|O_NOFOLLOW);
if (fstatat(fd, \"\", &sb, AT_EMPTY_PATH) != 0) return 1"
. auto/feature
# sendfile()
CC_AUX_FLAGS="$cc_aux_flags -D_GNU_SOURCE"
@ -180,19 +148,6 @@ ngx_feature_test="struct crypt_data cd;
. auto/feature
# reuseport
ngx_feature="SO_REUSEPORT"
ngx_feature_name="NGX_HAVE_REUSEPORT"
ngx_feature_run=no
ngx_feature_incs="#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/tcp.h>"
ngx_feature_path=
ngx_feature_libs=
ngx_feature_test="setsockopt(0, SOL_SOCKET, SO_REUSEPORT, NULL, 0)"
. auto/feature
ngx_include="sys/vfs.h"; . auto/include

View file

@ -9,21 +9,10 @@ CORE_INCS="$WIN32_INCS"
CORE_DEPS="$WIN32_DEPS"
CORE_SRCS="$WIN32_SRCS $IOCP_SRCS"
OS_CONFIG="$WIN32_CONFIG"
CORE_LIBS="$CORE_LIBS advapi32.lib ws2_32.lib"
NGX_ICONS="$NGX_WIN32_ICONS"
SELECT_SRCS=$WIN32_SELECT_SRCS
case "$NGX_CC_NAME" in
gcc)
CORE_LIBS="$CORE_LIBS -ladvapi32 -lws2_32"
;;
*)
CORE_LIBS="$CORE_LIBS advapi32.lib ws2_32.lib"
;;
esac
EVENT_MODULES="$EVENT_MODULES $IOCP_MODULE"
EVENT_FOUND=YES

View file

@ -1,3 +1,4 @@
# Copyright (C) Igor Sysoev
# Copyright (C) Nginx, Inc.
@ -37,8 +38,7 @@ CORE_DEPS="src/core/nginx.h \
src/core/ngx_conf_file.h \
src/core/ngx_resolver.h \
src/core/ngx_open_file_cache.h \
src/core/ngx_crypt.h \
src/core/ngx_proxy_protocol.h"
src/core/ngx_crypt.h"
CORE_SRCS="src/core/nginx.c \
@ -71,8 +71,7 @@ CORE_SRCS="src/core/nginx.c \
src/core/ngx_conf_file.c \
src/core/ngx_resolver.c \
src/core/ngx_open_file_cache.c \
src/core/ngx_crypt.c \
src/core/ngx_proxy_protocol.c"
src/core/ngx_crypt.c"
REGEX_MODULE=ngx_regex_module
@ -357,7 +356,8 @@ HTTP_SPDY_DEPS="src/http/ngx_http_spdy.h \
src/http/ngx_http_spdy_module.h"
HTTP_SPDY_SRCS="src/http/ngx_http_spdy.c \
src/http/ngx_http_spdy_module.c \
src/http/ngx_http_spdy_filter_module.c"
src/http/ngx_http_spdy_filter_module.c \
src/http/ngx_http_spdy_v3.c"
HTTP_CHARSET_FILTER_MODULE=ngx_http_charset_filter_module
@ -422,10 +422,6 @@ HTTP_CONCAT_MODULE=ngx_http_concat_module
HTTP_CONCAT_SRCS=src/http/modules/ngx_http_concat_module.c
HTTP_AUTH_REQUEST_MODULE=ngx_http_auth_request_module
HTTP_AUTH_REQUEST_SRCS=src/http/modules/ngx_http_auth_request_module.c
HTTP_AUTOINDEX_MODULE=ngx_http_autoindex_module
HTTP_AUTOINDEX_SRCS=src/http/modules/ngx_http_autoindex_module.c
@ -566,16 +562,6 @@ HTTP_UPSTREAM_KEEPALIVE_MODULE=ngx_http_upstream_keepalive_module
HTTP_UPSTREAM_KEEPALIVE_SRCS=" \
src/http/modules/ngx_http_upstream_keepalive_module.c"
HTTP_UPSTREAM_DYNAMIC_MODULE=ngx_http_upstream_dynamic_module
HTTP_UPSTREAM_DYNAMIC_SRCS=" \
src/http/modules/ngx_http_upstream_dynamic_module.c"
HTTP_DYUPS_MODULE=ngx_http_dyups_module
HTTP_DYUPS_SRCS="src/http/modules/ngx_http_dyups_module.c"
HTTP_DYUPS_DEPS="src/http/modules/ngx_http_dyups.h"
HTTP_DYUPS_LUA_SRCS="src/http/modules/ngx_http_dyups_lua.c"
HTTP_DYUPS_LUA_DEPS="src/http/modules/ngx_http_dyups_lua.h"
HTTP_REQ_STATUS_MODULE=ngx_http_reqstat_module
HTTP_REQ_STATUS_SRCS=src/http/modules/ngx_http_reqstat_module.c
@ -627,106 +613,98 @@ NGX_BACKTRACE_MODULE=ngx_backtrace_module
NGX_BACKTRACE_SRCS=src/misc/ngx_backtrace_module.c
NGX_HTTP_LUA_MODULE=ngx_http_lua_module
NGX_HTTP_LUA_MODULE_SRCS="modules/ngx_http_lua_module/src/ngx_http_lua_script.c \
modules/ngx_http_lua_module/src/ngx_http_lua_log.c \
modules/ngx_http_lua_module/src/ngx_http_lua_subrequest.c \
modules/ngx_http_lua_module/src/ngx_http_lua_ndk.c \
modules/ngx_http_lua_module/src/ngx_http_lua_control.c \
modules/ngx_http_lua_module/src/ngx_http_lua_time.c \
modules/ngx_http_lua_module/src/ngx_http_lua_misc.c \
modules/ngx_http_lua_module/src/ngx_http_lua_variable.c \
modules/ngx_http_lua_module/src/ngx_http_lua_string.c \
modules/ngx_http_lua_module/src/ngx_http_lua_output.c \
modules/ngx_http_lua_module/src/ngx_http_lua_headers.c \
modules/ngx_http_lua_module/src/ngx_http_lua_req_body.c \
modules/ngx_http_lua_module/src/ngx_http_lua_uri.c \
modules/ngx_http_lua_module/src/ngx_http_lua_args.c \
modules/ngx_http_lua_module/src/ngx_http_lua_ctx.c \
modules/ngx_http_lua_module/src/ngx_http_lua_regex.c \
modules/ngx_http_lua_module/src/ngx_http_lua_module.c \
modules/ngx_http_lua_module/src/ngx_http_lua_headers_out.c \
modules/ngx_http_lua_module/src/ngx_http_lua_headers_in.c \
modules/ngx_http_lua_module/src/ngx_http_lua_directive.c \
modules/ngx_http_lua_module/src/ngx_http_lua_consts.c \
modules/ngx_http_lua_module/src/ngx_http_lua_exception.c \
modules/ngx_http_lua_module/src/ngx_http_lua_util.c \
modules/ngx_http_lua_module/src/ngx_http_lua_cache.c \
modules/ngx_http_lua_module/src/ngx_http_lua_contentby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_rewriteby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_accessby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_setby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_capturefilter.c \
modules/ngx_http_lua_module/src/ngx_http_lua_clfactory.c \
modules/ngx_http_lua_module/src/ngx_http_lua_pcrefix.c \
modules/ngx_http_lua_module/src/ngx_http_lua_headerfilterby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_shdict.c \
modules/ngx_http_lua_module/src/ngx_http_lua_socket_tcp.c \
modules/ngx_http_lua_module/src/ngx_http_lua_api.c \
modules/ngx_http_lua_module/src/ngx_http_lua_logby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_sleep.c \
modules/ngx_http_lua_module/src/ngx_http_lua_coroutine.c \
modules/ngx_http_lua_module/src/ngx_http_lua_bodyfilterby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_initby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_initworkerby.c \
modules/ngx_http_lua_module/src/ngx_http_lua_socket_udp.c \
modules/ngx_http_lua_module/src/ngx_http_lua_req_method.c \
modules/ngx_http_lua_module/src/ngx_http_lua_phase.c \
modules/ngx_http_lua_module/src/ngx_http_lua_uthread.c \
modules/ngx_http_lua_module/src/ngx_http_lua_timer.c \
modules/ngx_http_lua_module/src/ngx_http_lua_config.c \
modules/ngx_http_lua_module/src/ngx_http_lua_worker.c"
NGX_HTTP_LUA_MODULE_SRCS="src/http/modules/lua/ngx_http_lua_script.c \
src/http/modules/lua/ngx_http_lua_log.c \
src/http/modules/lua/ngx_http_lua_subrequest.c \
src/http/modules/lua/ngx_http_lua_ndk.c \
src/http/modules/lua/ngx_http_lua_control.c \
src/http/modules/lua/ngx_http_lua_time.c \
src/http/modules/lua/ngx_http_lua_misc.c \
src/http/modules/lua/ngx_http_lua_variable.c \
src/http/modules/lua/ngx_http_lua_string.c \
src/http/modules/lua/ngx_http_lua_output.c \
src/http/modules/lua/ngx_http_lua_headers.c \
src/http/modules/lua/ngx_http_lua_req_body.c \
src/http/modules/lua/ngx_http_lua_uri.c \
src/http/modules/lua/ngx_http_lua_args.c \
src/http/modules/lua/ngx_http_lua_ctx.c \
src/http/modules/lua/ngx_http_lua_regex.c \
src/http/modules/lua/ngx_http_lua_module.c \
src/http/modules/lua/ngx_http_lua_headers_out.c \
src/http/modules/lua/ngx_http_lua_headers_in.c \
src/http/modules/lua/ngx_http_lua_directive.c \
src/http/modules/lua/ngx_http_lua_consts.c \
src/http/modules/lua/ngx_http_lua_exception.c \
src/http/modules/lua/ngx_http_lua_util.c \
src/http/modules/lua/ngx_http_lua_cache.c \
src/http/modules/lua/ngx_http_lua_contentby.c \
src/http/modules/lua/ngx_http_lua_rewriteby.c \
src/http/modules/lua/ngx_http_lua_accessby.c \
src/http/modules/lua/ngx_http_lua_setby.c \
src/http/modules/lua/ngx_http_lua_capturefilter.c \
src/http/modules/lua/ngx_http_lua_clfactory.c \
src/http/modules/lua/ngx_http_lua_pcrefix.c \
src/http/modules/lua/ngx_http_lua_headerfilterby.c \
src/http/modules/lua/ngx_http_lua_shdict.c \
src/http/modules/lua/ngx_http_lua_socket_tcp.c \
src/http/modules/lua/ngx_http_lua_api.c \
src/http/modules/lua/ngx_http_lua_logby.c \
src/http/modules/lua/ngx_http_lua_sleep.c \
src/http/modules/lua/ngx_http_lua_coroutine.c \
src/http/modules/lua/ngx_http_lua_bodyfilterby.c \
src/http/modules/lua/ngx_http_lua_initby.c \
src/http/modules/lua/ngx_http_lua_socket_udp.c \
src/http/modules/lua/ngx_http_lua_req_method.c \
src/http/modules/lua/ngx_http_lua_phase.c \
src/http/modules/lua/ngx_http_lua_uthread.c"
NGX_HTTP_LUA_MODULE_DEPS="modules/ngx_http_lua_module/src/ddebug.h \
modules/ngx_http_lua_module/src/ngx_http_lua_script.h \
modules/ngx_http_lua_module/src/ngx_http_lua_log.h \
modules/ngx_http_lua_module/src/ngx_http_lua_subrequest.h \
modules/ngx_http_lua_module/src/ngx_http_lua_ndk.h \
modules/ngx_http_lua_module/src/ngx_http_lua_control.h \
modules/ngx_http_lua_module/src/ngx_http_lua_time.h \
modules/ngx_http_lua_module/src/ngx_http_lua_string.h \
modules/ngx_http_lua_module/src/ngx_http_lua_misc.h \
modules/ngx_http_lua_module/src/ngx_http_lua_variable.h \
modules/ngx_http_lua_module/src/ngx_http_lua_output.h \
modules/ngx_http_lua_module/src/ngx_http_lua_headers.h \
modules/ngx_http_lua_module/src/ngx_http_lua_uri.h \
modules/ngx_http_lua_module/src/ngx_http_lua_req_body.h \
modules/ngx_http_lua_module/src/ngx_http_lua_args.h \
modules/ngx_http_lua_module/src/ngx_http_lua_ctx.h \
modules/ngx_http_lua_module/src/ngx_http_lua_regex.h \
modules/ngx_http_lua_module/src/ngx_http_lua_common.h \
modules/ngx_http_lua_module/src/ngx_http_lua_directive.h \
modules/ngx_http_lua_module/src/ngx_http_lua_headers_out.h \
modules/ngx_http_lua_module/src/ngx_http_lua_headers_in.h \
modules/ngx_http_lua_module/src/ngx_http_lua_consts.h \
modules/ngx_http_lua_module/src/ngx_http_lua_exception.h \
modules/ngx_http_lua_module/src/ngx_http_lua_util.h \
modules/ngx_http_lua_module/src/ngx_http_lua_cache.h \
modules/ngx_http_lua_module/src/ngx_http_lua_contentby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_rewriteby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_accessby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_setby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_capturefilter.h \
modules/ngx_http_lua_module/src/ngx_http_lua_clfactory.h \
modules/ngx_http_lua_module/src/ngx_http_lua_pcrefix.h \
modules/ngx_http_lua_module/src/ngx_http_lua_headerfilterby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_shdict.h \
modules/ngx_http_lua_module/src/ngx_http_lua_socket_tcp.h \
modules/ngx_http_lua_module/src/api/ngx_http_lua_api.h \
modules/ngx_http_lua_module/src/ngx_http_lua_logby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_sleep.h \
modules/ngx_http_lua_module/src/ngx_http_lua_coroutine.h \
modules/ngx_http_lua_module/src/ngx_http_lua_bodyfilterby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_initby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_initworkerby.h \
modules/ngx_http_lua_module/src/ngx_http_lua_socket_udp.h \
modules/ngx_http_lua_module/src/ngx_http_lua_req_method.h \
modules/ngx_http_lua_module/src/ngx_http_lua_phase.h \
modules/ngx_http_lua_module/src/ngx_http_lua_probe.h \
modules/ngx_http_lua_module/src/ngx_http_lua_uthread.h \
modules/ngx_http_lua_module/src/ngx_http_lua_timer.h \
modules/ngx_http_lua_module/src/ngx_http_lua_config.h \
modules/ngx_http_lua_module/src/ngx_http_lua_worker.h"
NGX_HTTP_LUA_MODULE_DEPS="src/http/modules/lua/ddebug.h \
src/http/modules/lua/ngx_http_lua_script.h \
src/http/modules/lua/ngx_http_lua_log.h \
src/http/modules/lua/ngx_http_lua_subrequest.h \
src/http/modules/lua/ngx_http_lua_ndk.h \
src/http/modules/lua/ngx_http_lua_control.h \
src/http/modules/lua/ngx_http_lua_time.h \
src/http/modules/lua/ngx_http_lua_string.h \
src/http/modules/lua/ngx_http_lua_misc.h \
src/http/modules/lua/ngx_http_lua_variable.h \
src/http/modules/lua/ngx_http_lua_output.h \
src/http/modules/lua/ngx_http_lua_headers.h \
src/http/modules/lua/ngx_http_lua_uri.h \
src/http/modules/lua/ngx_http_lua_req_body.h \
src/http/modules/lua/ngx_http_lua_args.h \
src/http/modules/lua/ngx_http_lua_ctx.h \
src/http/modules/lua/ngx_http_lua_regex.h \
src/http/modules/lua/ngx_http_lua_common.h \
src/http/modules/lua/ngx_http_lua_directive.h \
src/http/modules/lua/ngx_http_lua_headers_out.h \
src/http/modules/lua/ngx_http_lua_headers_in.h \
src/http/modules/lua/ngx_http_lua_consts.h \
src/http/modules/lua/ngx_http_lua_exception.h \
src/http/modules/lua/ngx_http_lua_util.h \
src/http/modules/lua/ngx_http_lua_cache.h \
src/http/modules/lua/ngx_http_lua_contentby.h \
src/http/modules/lua/ngx_http_lua_rewriteby.h \
src/http/modules/lua/ngx_http_lua_accessby.h \
src/http/modules/lua/ngx_http_lua_setby.h \
src/http/modules/lua/ngx_http_lua_capturefilter.h \
src/http/modules/lua/ngx_http_lua_clfactory.h \
src/http/modules/lua/ngx_http_lua_pcrefix.h \
src/http/modules/lua/ngx_http_lua_headerfilterby.h \
src/http/modules/lua/ngx_http_lua_shdict.h \
src/http/modules/lua/ngx_http_lua_socket_tcp.h \
src/http/modules/lua/api/ngx_http_lua_api.h \
src/http/modules/lua/ngx_http_lua_logby.h \
src/http/modules/lua/ngx_http_lua_sleep.h \
src/http/modules/lua/ngx_http_lua_coroutine.h \
src/http/modules/lua/ngx_http_lua_bodyfilterby.h \
src/http/modules/lua/ngx_http_lua_initby.h \
src/http/modules/lua/ngx_http_lua_socket_udp.h \
src/http/modules/lua/ngx_http_lua_req_method.h \
src/http/modules/lua/ngx_http_lua_phase.h \
src/http/modules/lua/ngx_http_lua_probe.h \
src/http/modules/lua/ngx_http_lua_uthread.h"
NGX_HTTP_TFS_MODULE="ngx_http_tfs_module"
@ -778,3 +756,5 @@ NGX_HTTP_TFS_MODULE_SRCS="src/http/modules/tfs/ngx_tfs_common.c \
src/http/modules/tfs/ngx_http_tfs_meta_server_message.c \
src/http/modules/tfs/ngx_http_tfs_peer_connection.c \
src/http/modules/tfs/ngx_http_tfs_server_handler.c "

View file

@ -45,7 +45,7 @@ if [ -x $NGX_AUTOTEST ]; then
fi
rm -rf $NGX_AUTOTEST*
rm -f $NGX_AUTOTEST
case $ngx_size in

View file

@ -49,7 +49,7 @@ END
fi
fi
rm -rf $NGX_AUTOTEST*
rm -f $NGX_AUTOTEST
if [ $ngx_found = no ]; then
echo $ngx_n " $ngx_try not found$ngx_c"

View file

@ -33,7 +33,7 @@ else
echo $ngx_n " uintptr_t not found" $ngx_c
fi
rm -rf $NGX_AUTOTEST*
rm $NGX_AUTOTEST*
if [ $found = no ]; then

View file

@ -370,7 +370,7 @@ ngx_feature_test="setsockopt(0, IPPROTO_TCP, TCP_DEFER_ACCEPT, NULL, 0)"
. auto/feature
ngx_feature="TCP_KEEPIDLE"
ngx_feature="TCP_KEEPIDLE, TCP_KEEPINTVL, TCP_KEEPCNT"
ngx_feature_name="NGX_HAVE_KEEPALIVE_TUNABLE"
ngx_feature_run=no
ngx_feature_incs="#include <sys/socket.h>
@ -384,18 +384,6 @@ ngx_feature_test="setsockopt(0, IPPROTO_TCP, TCP_KEEPIDLE, NULL, 0);
. auto/feature
ngx_feature="TCP_FASTOPEN"
ngx_feature_name="NGX_HAVE_TCP_FASTOPEN"
ngx_feature_run=no
ngx_feature_incs="#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/tcp.h>"
ngx_feature_path=
ngx_feature_libs=
ngx_feature_test="setsockopt(0, IPPROTO_TCP, TCP_FASTOPEN, NULL, 0)"
. auto/feature
ngx_feature="TCP_INFO"
ngx_feature_name="NGX_HAVE_TCP_INFO"
ngx_feature_run=no

View file

@ -5,7 +5,7 @@ types {
text/xml xml;
image/gif gif;
image/jpeg jpeg jpg;
application/javascript js;
application/x-javascript js;
application/atom+xml atom;
application/rss+xml rss;
@ -24,17 +24,13 @@ types {
image/svg+xml svg svgz;
image/webp webp;
application/font-woff woff;
application/java-archive jar war ear;
application/json json;
application/mac-binhex40 hqx;
application/msword doc;
application/pdf pdf;
application/postscript ps eps ai;
application/rtf rtf;
application/vnd.apple.mpegurl m3u8;
application/vnd.ms-excel xls;
application/vnd.ms-fontobject eot;
application/vnd.ms-powerpoint ppt;
application/vnd.wap.wmlc wmlc;
application/vnd.google-earth.kml+xml kml;
@ -55,7 +51,6 @@ types {
application/x-x509-ca-cert der pem crt;
application/x-xpinstall xpi;
application/xhtml+xml xhtml;
application/xspf+xml xspf;
application/zip zip;
application/x-nokia-widget wgz;
application/vnd.android.package-archive apk;
@ -63,13 +58,10 @@ types {
application/octet-stream bin exe dll;
application/octet-stream deb;
application/octet-stream dmg;
application/octet-stream eot;
application/octet-stream iso img;
application/octet-stream msi msp msm;
application/vnd.openxmlformats-officedocument.wordprocessingml.document docx;
application/vnd.openxmlformats-officedocument.spreadsheetml.sheet xlsx;
application/vnd.openxmlformats-officedocument.presentationml.presentation pptx;
audio/midi mid midi kar;
audio/mpeg mp3;
audio/ogg ogg;
@ -77,7 +69,6 @@ types {
audio/x-realaudio ra;
video/3gpp 3gpp 3gp;
video/mp2t ts;
video/mp4 mp4;
video/mpeg mpeg mpg;
video/quicktime mov;

View file

@ -102,17 +102,18 @@ http {
# HTTPS server
#
#server {
# listen 443 ssl;
# listen 443;
# server_name localhost;
# ssl on;
# ssl_certificate cert.pem;
# ssl_certificate_key cert.key;
# ssl_session_cache shared:SSL:1m;
# ssl_session_timeout 5m;
# ssl_protocols SSLv2 SSLv3 TLSv1;
# ssl_ciphers HIGH:!aNULL:!MD5;
# ssl_prefer_server_ciphers on;
# ssl_prefer_server_ciphers on;
# location / {
# root html;

View file

@ -13,9 +13,3 @@ unicode2nginx by Maxim Dounin
configuration file format.
Two generated full maps for windows-1251 and koi8-r.
vim by Evan Miller
Syntax highlighting of nginx configuration for vim, to be
placed into ~/.vim/.

View file

@ -67,25 +67,5 @@ def walk_dir(dir):
for d in dirs:
walk_dir(d)
def usage():
print """
Usage: stylechecker.py file or dir
python stylechecker.py /path/to/the/c/code
or
python stylechecker.py /file/of/c/code """
sys.exit(1)
### main
if len(sys.argv) == 2:
PATH = sys.argv[1]
if os.path.isfile(PATH):
check_file(PATH)
elif os.path.isdir(PATH):
walk_dir(PATH)
else:
print RED + "Check the %s is file or dir" % PATH + ENDC
else:
usage()
walk_dir(sys.argv[1])

View file

@ -1,4 +0,0 @@
au BufRead,BufNewFile *.nginx set ft=nginx
au BufRead,BufNewFile */etc/nginx/* set ft=nginx
au BufRead,BufNewFile */usr/local/nginx/conf/* set ft=nginx
au BufRead,BufNewFile nginx.conf set ft=nginx

View file

@ -1,11 +0,0 @@
if exists("b:did_indent")
finish
endif
let b:did_indent = 1
setlocal indentexpr=
" cindent actually works for nginx' simple file structure
setlocal cindent
" Just make sure that the comments are not reset as defs would be.
setlocal cinkeys-=0#

View file

@ -1,703 +0,0 @@
" Vim syntax file
" Language: nginx.conf
if exists("b:current_syntax")
finish
end
setlocal iskeyword+=.
setlocal iskeyword+=/
setlocal iskeyword+=:
syn match ngxVariable '\$\(\w\+\|{\w\+}\)'
syn match ngxVariableBlock '\$\(\w\+\|{\w\+}\)' contained
syn match ngxVariableString '\$\(\w\+\|{\w\+}\)' contained
syn region ngxBlock start=+^+ end=+{+ skip=+\${+ contains=ngxComment,ngxDirectiveBlock,ngxVariableBlock,ngxString oneline
syn region ngxString start=+\z(["']\)+ end=+\z1+ skip=+\\\\\|\\\z1+ contains=ngxVariableString
syn match ngxComment ' *#.*$'
syn keyword ngxBoolean on
syn keyword ngxBoolean off
syn keyword ngxDirectiveBlock http contained
syn keyword ngxDirectiveBlock mail contained
syn keyword ngxDirectiveBlock events contained
syn keyword ngxDirectiveBlock server contained
syn keyword ngxDirectiveBlock types contained
syn keyword ngxDirectiveBlock location contained
syn keyword ngxDirectiveBlock upstream contained
syn keyword ngxDirectiveBlock charset_map contained
syn keyword ngxDirectiveBlock limit_except contained
syn keyword ngxDirectiveBlock if contained
syn keyword ngxDirectiveBlock geo contained
syn keyword ngxDirectiveBlock map contained
syn keyword ngxDirectiveImportant include
syn keyword ngxDirectiveImportant root
syn keyword ngxDirectiveImportant server
syn keyword ngxDirectiveImportant server_name
syn keyword ngxDirectiveImportant listen
syn keyword ngxDirectiveImportant internal
syn keyword ngxDirectiveImportant proxy_pass
syn keyword ngxDirectiveImportant memcached_pass
syn keyword ngxDirectiveImportant fastcgi_pass
syn keyword ngxDirectiveImportant try_files
syn keyword ngxDirectiveControl break
syn keyword ngxDirectiveControl return
syn keyword ngxDirectiveControl rewrite
syn keyword ngxDirectiveControl set
syn keyword ngxDirectiveError error_page
syn keyword ngxDirectiveError post_action
syn keyword ngxDirectiveDeprecated connections
syn keyword ngxDirectiveDeprecated imap
syn keyword ngxDirectiveDeprecated open_file_cache_retest
syn keyword ngxDirectiveDeprecated optimize_server_names
syn keyword ngxDirectiveDeprecated satisfy_any
syn keyword ngxDirective accept_mutex
syn keyword ngxDirective accept_mutex_delay
syn keyword ngxDirective access_log
syn keyword ngxDirective add_after_body
syn keyword ngxDirective add_before_body
syn keyword ngxDirective add_header
syn keyword ngxDirective addition_types
syn keyword ngxDirective aio
syn keyword ngxDirective alias
syn keyword ngxDirective allow
syn keyword ngxDirective ancient_browser
syn keyword ngxDirective ancient_browser_value
syn keyword ngxDirective auth_basic
syn keyword ngxDirective auth_basic_user_file
syn keyword ngxDirective auth_http
syn keyword ngxDirective auth_http_header
syn keyword ngxDirective auth_http_timeout
syn keyword ngxDirective autoindex
syn keyword ngxDirective autoindex_exact_size
syn keyword ngxDirective autoindex_localtime
syn keyword ngxDirective charset
syn keyword ngxDirective charset_types
syn keyword ngxDirective client_body_buffer_size
syn keyword ngxDirective client_body_in_file_only
syn keyword ngxDirective client_body_in_single_buffer
syn keyword ngxDirective client_body_temp_path
syn keyword ngxDirective client_body_timeout
syn keyword ngxDirective client_header_buffer_size
syn keyword ngxDirective client_header_timeout
syn keyword ngxDirective client_max_body_size
syn keyword ngxDirective connection_pool_size
syn keyword ngxDirective create_full_put_path
syn keyword ngxDirective daemon
syn keyword ngxDirective dav_access
syn keyword ngxDirective dav_methods
syn keyword ngxDirective debug_connection
syn keyword ngxDirective debug_points
syn keyword ngxDirective default_type
syn keyword ngxDirective degradation
syn keyword ngxDirective degrade
syn keyword ngxDirective deny
syn keyword ngxDirective devpoll_changes
syn keyword ngxDirective devpoll_events
syn keyword ngxDirective directio
syn keyword ngxDirective directio_alignment
syn keyword ngxDirective empty_gif
syn keyword ngxDirective env
syn keyword ngxDirective epoll_events
syn keyword ngxDirective error_log
syn keyword ngxDirective eventport_events
syn keyword ngxDirective expires
syn keyword ngxDirective fastcgi_bind
syn keyword ngxDirective fastcgi_buffer_size
syn keyword ngxDirective fastcgi_buffers
syn keyword ngxDirective fastcgi_busy_buffers_size
syn keyword ngxDirective fastcgi_cache
syn keyword ngxDirective fastcgi_cache_key
syn keyword ngxDirective fastcgi_cache_methods
syn keyword ngxDirective fastcgi_cache_min_uses
syn keyword ngxDirective fastcgi_cache_path
syn keyword ngxDirective fastcgi_cache_use_stale
syn keyword ngxDirective fastcgi_cache_valid
syn keyword ngxDirective fastcgi_catch_stderr
syn keyword ngxDirective fastcgi_connect_timeout
syn keyword ngxDirective fastcgi_hide_header
syn keyword ngxDirective fastcgi_ignore_client_abort
syn keyword ngxDirective fastcgi_ignore_headers
syn keyword ngxDirective fastcgi_index
syn keyword ngxDirective fastcgi_intercept_errors
syn keyword ngxDirective fastcgi_max_temp_file_size
syn keyword ngxDirective fastcgi_next_upstream
syn keyword ngxDirective fastcgi_param
syn keyword ngxDirective fastcgi_pass_header
syn keyword ngxDirective fastcgi_pass_request_body
syn keyword ngxDirective fastcgi_pass_request_headers
syn keyword ngxDirective fastcgi_read_timeout
syn keyword ngxDirective fastcgi_send_lowat
syn keyword ngxDirective fastcgi_send_timeout
syn keyword ngxDirective fastcgi_split_path_info
syn keyword ngxDirective fastcgi_store
syn keyword ngxDirective fastcgi_store_access
syn keyword ngxDirective fastcgi_temp_file_write_size
syn keyword ngxDirective fastcgi_temp_path
syn keyword ngxDirective fastcgi_upstream_fail_timeout
syn keyword ngxDirective fastcgi_upstream_max_fails
syn keyword ngxDirective flv
syn keyword ngxDirective geoip_city
syn keyword ngxDirective geoip_country
syn keyword ngxDirective google_perftools_profiles
syn keyword ngxDirective gzip
syn keyword ngxDirective gzip_buffers
syn keyword ngxDirective gzip_comp_level
syn keyword ngxDirective gzip_disable
syn keyword ngxDirective gzip_hash
syn keyword ngxDirective gzip_http_version
syn keyword ngxDirective gzip_min_length
syn keyword ngxDirective gzip_no_buffer
syn keyword ngxDirective gzip_proxied
syn keyword ngxDirective gzip_static
syn keyword ngxDirective gzip_types
syn keyword ngxDirective gzip_vary
syn keyword ngxDirective gzip_window
syn keyword ngxDirective if_modified_since
syn keyword ngxDirective ignore_invalid_headers
syn keyword ngxDirective image_filter
syn keyword ngxDirective image_filter_buffer
syn keyword ngxDirective image_filter_jpeg_quality
syn keyword ngxDirective image_filter_transparency
syn keyword ngxDirective imap_auth
syn keyword ngxDirective imap_capabilities
syn keyword ngxDirective imap_client_buffer
syn keyword ngxDirective index
syn keyword ngxDirective ip_hash
syn keyword ngxDirective keepalive_requests
syn keyword ngxDirective keepalive_timeout
syn keyword ngxDirective kqueue_changes
syn keyword ngxDirective kqueue_events
syn keyword ngxDirective large_client_header_buffers
syn keyword ngxDirective limit_conn
syn keyword ngxDirective limit_conn_log_level
syn keyword ngxDirective limit_rate
syn keyword ngxDirective limit_rate_after
syn keyword ngxDirective limit_req
syn keyword ngxDirective limit_req_log_level
syn keyword ngxDirective limit_req_zone
syn keyword ngxDirective limit_zone
syn keyword ngxDirective lingering_time
syn keyword ngxDirective lingering_timeout
syn keyword ngxDirective lock_file
syn keyword ngxDirective log_format
syn keyword ngxDirective log_not_found
syn keyword ngxDirective log_subrequest
syn keyword ngxDirective map_hash_bucket_size
syn keyword ngxDirective map_hash_max_size
syn keyword ngxDirective master_process
syn keyword ngxDirective memcached_bind
syn keyword ngxDirective memcached_buffer_size
syn keyword ngxDirective memcached_connect_timeout
syn keyword ngxDirective memcached_next_upstream
syn keyword ngxDirective memcached_read_timeout
syn keyword ngxDirective memcached_send_timeout
syn keyword ngxDirective memcached_upstream_fail_timeout
syn keyword ngxDirective memcached_upstream_max_fails
syn keyword ngxDirective merge_slashes
syn keyword ngxDirective min_delete_depth
syn keyword ngxDirective modern_browser
syn keyword ngxDirective modern_browser_value
syn keyword ngxDirective msie_padding
syn keyword ngxDirective msie_refresh
syn keyword ngxDirective multi_accept
syn keyword ngxDirective open_file_cache
syn keyword ngxDirective open_file_cache_errors
syn keyword ngxDirective open_file_cache_events
syn keyword ngxDirective open_file_cache_min_uses
syn keyword ngxDirective open_file_cache_valid
syn keyword ngxDirective open_log_file_cache
syn keyword ngxDirective output_buffers
syn keyword ngxDirective override_charset
syn keyword ngxDirective perl
syn keyword ngxDirective perl_modules
syn keyword ngxDirective perl_require
syn keyword ngxDirective perl_set
syn keyword ngxDirective pid
syn keyword ngxDirective pop3_auth
syn keyword ngxDirective pop3_capabilities
syn keyword ngxDirective port_in_redirect
syn keyword ngxDirective postpone_gzipping
syn keyword ngxDirective postpone_output
syn keyword ngxDirective protocol
syn keyword ngxDirective proxy
syn keyword ngxDirective proxy_bind
syn keyword ngxDirective proxy_buffer
syn keyword ngxDirective proxy_buffer_size
syn keyword ngxDirective proxy_buffering
syn keyword ngxDirective proxy_buffers
syn keyword ngxDirective proxy_busy_buffers_size
syn keyword ngxDirective proxy_cache
syn keyword ngxDirective proxy_cache_key
syn keyword ngxDirective proxy_cache_methods
syn keyword ngxDirective proxy_cache_min_uses
syn keyword ngxDirective proxy_cache_path
syn keyword ngxDirective proxy_cache_use_stale
syn keyword ngxDirective proxy_cache_valid
syn keyword ngxDirective proxy_connect_timeout
syn keyword ngxDirective proxy_headers_hash_bucket_size
syn keyword ngxDirective proxy_headers_hash_max_size
syn keyword ngxDirective proxy_hide_header
syn keyword ngxDirective proxy_ignore_client_abort
syn keyword ngxDirective proxy_ignore_headers
syn keyword ngxDirective proxy_intercept_errors
syn keyword ngxDirective proxy_max_temp_file_size
syn keyword ngxDirective proxy_method
syn keyword ngxDirective proxy_next_upstream
syn keyword ngxDirective proxy_pass_error_message
syn keyword ngxDirective proxy_pass_header
syn keyword ngxDirective proxy_pass_request_body
syn keyword ngxDirective proxy_pass_request_headers
syn keyword ngxDirective proxy_read_timeout
syn keyword ngxDirective proxy_redirect
syn keyword ngxDirective proxy_send_lowat
syn keyword ngxDirective proxy_send_timeout
syn keyword ngxDirective proxy_set_body
syn keyword ngxDirective proxy_set_header
syn keyword ngxDirective proxy_ssl_session_reuse
syn keyword ngxDirective proxy_store
syn keyword ngxDirective proxy_store_access
syn keyword ngxDirective proxy_temp_file_write_size
syn keyword ngxDirective proxy_temp_path
syn keyword ngxDirective proxy_timeout
syn keyword ngxDirective proxy_upstream_fail_timeout
syn keyword ngxDirective proxy_upstream_max_fails
syn keyword ngxDirective random_index
syn keyword ngxDirective read_ahead
syn keyword ngxDirective real_ip_header
syn keyword ngxDirective recursive_error_pages
syn keyword ngxDirective request_pool_size
syn keyword ngxDirective reset_timedout_connection
syn keyword ngxDirective resolver
syn keyword ngxDirective resolver_timeout
syn keyword ngxDirective rewrite_log
syn keyword ngxDirective rtsig_overflow_events
syn keyword ngxDirective rtsig_overflow_test
syn keyword ngxDirective rtsig_overflow_threshold
syn keyword ngxDirective rtsig_signo
syn keyword ngxDirective satisfy
syn keyword ngxDirective secure_link_secret
syn keyword ngxDirective send_lowat
syn keyword ngxDirective send_timeout
syn keyword ngxDirective sendfile
syn keyword ngxDirective sendfile_max_chunk
syn keyword ngxDirective server_name_in_redirect
syn keyword ngxDirective server_names_hash_bucket_size
syn keyword ngxDirective server_names_hash_max_size
syn keyword ngxDirective server_tokens
syn keyword ngxDirective set_real_ip_from
syn keyword ngxDirective smtp_auth
syn keyword ngxDirective smtp_capabilities
syn keyword ngxDirective smtp_client_buffer
syn keyword ngxDirective smtp_greeting_delay
syn keyword ngxDirective so_keepalive
syn keyword ngxDirective source_charset
syn keyword ngxDirective ssi
syn keyword ngxDirective ssi_ignore_recycled_buffers
syn keyword ngxDirective ssi_min_file_chunk
syn keyword ngxDirective ssi_silent_errors
syn keyword ngxDirective ssi_types
syn keyword ngxDirective ssi_value_length
syn keyword ngxDirective ssl
syn keyword ngxDirective ssl_certificate
syn keyword ngxDirective ssl_certificate_key
syn keyword ngxDirective ssl_ciphers
syn keyword ngxDirective ssl_client_certificate
syn keyword ngxDirective ssl_crl
syn keyword ngxDirective ssl_dhparam
syn keyword ngxDirective ssl_engine
syn keyword ngxDirective ssl_prefer_server_ciphers
syn keyword ngxDirective ssl_protocols
syn keyword ngxDirective ssl_session_cache
syn keyword ngxDirective ssl_session_timeout
syn keyword ngxDirective ssl_verify_client
syn keyword ngxDirective ssl_verify_depth
syn keyword ngxDirective starttls
syn keyword ngxDirective stub_status
syn keyword ngxDirective sub_filter
syn keyword ngxDirective sub_filter_once
syn keyword ngxDirective sub_filter_types
syn keyword ngxDirective tcp_nodelay
syn keyword ngxDirective tcp_nopush
syn keyword ngxDirective thread_stack_size
syn keyword ngxDirective timeout
syn keyword ngxDirective timer_resolution
syn keyword ngxDirective types_hash_bucket_size
syn keyword ngxDirective types_hash_max_size
syn keyword ngxDirective underscores_in_headers
syn keyword ngxDirective uninitialized_variable_warn
syn keyword ngxDirective use
syn keyword ngxDirective user
syn keyword ngxDirective userid
syn keyword ngxDirective userid_domain
syn keyword ngxDirective userid_expires
syn keyword ngxDirective userid_mark
syn keyword ngxDirective userid_name
syn keyword ngxDirective userid_p3p
syn keyword ngxDirective userid_path
syn keyword ngxDirective userid_service
syn keyword ngxDirective valid_referers
syn keyword ngxDirective variables_hash_bucket_size
syn keyword ngxDirective variables_hash_max_size
syn keyword ngxDirective worker_connections
syn keyword ngxDirective worker_cpu_affinity
syn keyword ngxDirective worker_priority
syn keyword ngxDirective worker_processes
syn keyword ngxDirective worker_rlimit_core
syn keyword ngxDirective worker_rlimit_nofile
syn keyword ngxDirective worker_rlimit_sigpending
syn keyword ngxDirective worker_threads
syn keyword ngxDirective working_directory
syn keyword ngxDirective xclient
syn keyword ngxDirective xml_entities
syn keyword ngxDirective xslt_stylesheet
syn keyword ngxDirective xslt_types
" 3rd party module list:
" http://wiki.nginx.org/Nginx3rdPartyModules
" Accept Language Module <http://wiki.nginx.org/NginxAcceptLanguageModule>
" Parses the Accept-Language header and gives the most suitable locale from a list of supported locales.
syn keyword ngxDirectiveThirdParty set_from_accept_language
" Access Key Module <http://wiki.nginx.org/NginxHttpAccessKeyModule>
" Denies access unless the request URL contains an access key.
syn keyword ngxDirectiveThirdParty accesskey
syn keyword ngxDirectiveThirdParty accesskey_arg
syn keyword ngxDirectiveThirdParty accesskey_hashmethod
syn keyword ngxDirectiveThirdParty accesskey_signature
" Auth PAM Module <http://web.iti.upv.es/~sto/nginx/>
" HTTP Basic Authentication using PAM.
syn keyword ngxDirectiveThirdParty auth_pam
syn keyword ngxDirectiveThirdParty auth_pam_service_name
" Cache Purge Module <http://labs.frickle.com/nginx_ngx_cache_purge/>
" Module adding ability to purge content from FastCGI and proxy caches.
syn keyword ngxDirectiveThirdParty fastcgi_cache_purge
syn keyword ngxDirectiveThirdParty proxy_cache_purge
" Chunkin Module <http://wiki.nginx.org/NginxHttpChunkinModule>
" HTTP 1.1 chunked-encoding request body support for Nginx.
syn keyword ngxDirectiveThirdParty chunkin
syn keyword ngxDirectiveThirdParty chunkin_keepalive
syn keyword ngxDirectiveThirdParty chunkin_max_chunks_per_buf
syn keyword ngxDirectiveThirdParty chunkin_resume
" Circle GIF Module <http://wiki.nginx.org/NginxHttpCircleGifModule>
" Generates simple circle images with the colors and size specified in the URL.
syn keyword ngxDirectiveThirdParty circle_gif
syn keyword ngxDirectiveThirdParty circle_gif_max_radius
syn keyword ngxDirectiveThirdParty circle_gif_min_radius
syn keyword ngxDirectiveThirdParty circle_gif_step_radius
" Drizzle Module <http://github.com/chaoslawful/drizzle-nginx-module>
" Make nginx talk directly to mysql, drizzle, and sqlite3 by libdrizzle.
syn keyword ngxDirectiveThirdParty drizzle_connect_timeout
syn keyword ngxDirectiveThirdParty drizzle_dbname
syn keyword ngxDirectiveThirdParty drizzle_keepalive
syn keyword ngxDirectiveThirdParty drizzle_module_header
syn keyword ngxDirectiveThirdParty drizzle_pass
syn keyword ngxDirectiveThirdParty drizzle_query
syn keyword ngxDirectiveThirdParty drizzle_recv_cols_timeout
syn keyword ngxDirectiveThirdParty drizzle_recv_rows_timeout
syn keyword ngxDirectiveThirdParty drizzle_send_query_timeout
syn keyword ngxDirectiveThirdParty drizzle_server
" Echo Module <http://wiki.nginx.org/NginxHttpEchoModule>
" Brings 'echo', 'sleep', 'time', 'exec' and more shell-style goodies to Nginx config file.
syn keyword ngxDirectiveThirdParty echo
syn keyword ngxDirectiveThirdParty echo_after_body
syn keyword ngxDirectiveThirdParty echo_before_body
syn keyword ngxDirectiveThirdParty echo_blocking_sleep
syn keyword ngxDirectiveThirdParty echo_duplicate
syn keyword ngxDirectiveThirdParty echo_end
syn keyword ngxDirectiveThirdParty echo_exec
syn keyword ngxDirectiveThirdParty echo_flush
syn keyword ngxDirectiveThirdParty echo_foreach_split
syn keyword ngxDirectiveThirdParty echo_location
syn keyword ngxDirectiveThirdParty echo_location_async
syn keyword ngxDirectiveThirdParty echo_read_request_body
syn keyword ngxDirectiveThirdParty echo_request_body
syn keyword ngxDirectiveThirdParty echo_reset_timer
syn keyword ngxDirectiveThirdParty echo_sleep
syn keyword ngxDirectiveThirdParty echo_subrequest
syn keyword ngxDirectiveThirdParty echo_subrequest_async
" Events Module <http://docs.dutov.org/nginx_modules_events_en.html>
" Privides options for start/stop events.
syn keyword ngxDirectiveThirdParty on_start
syn keyword ngxDirectiveThirdParty on_stop
" EY Balancer Module <http://github.com/ry/nginx-ey-balancer>
" Adds a request queue to Nginx that allows the limiting of concurrent requests passed to the upstream.
syn keyword ngxDirectiveThirdParty max_connections
syn keyword ngxDirectiveThirdParty max_connections_max_queue_length
syn keyword ngxDirectiveThirdParty max_connections_queue_timeout
" Fancy Indexes Module <https://connectical.com/projects/ngx-fancyindex/wiki>
" Like the built-in autoindex module, but fancier.
syn keyword ngxDirectiveThirdParty fancyindex
syn keyword ngxDirectiveThirdParty fancyindex_exact_size
syn keyword ngxDirectiveThirdParty fancyindex_footer
syn keyword ngxDirectiveThirdParty fancyindex_header
syn keyword ngxDirectiveThirdParty fancyindex_localtime
syn keyword ngxDirectiveThirdParty fancyindex_readme
syn keyword ngxDirectiveThirdParty fancyindex_readme_mode
" GeoIP Module (DEPRECATED) <http://wiki.nginx.org/NginxHttp3rdPartyGeoIPModule>
" Country code lookups via the MaxMind GeoIP API.
syn keyword ngxDirectiveThirdParty geoip_country_file
" Headers More Module <http://wiki.nginx.org/NginxHttpHeadersMoreModule>
" Set and clear input and output headers...more than "add"!
syn keyword ngxDirectiveThirdParty more_clear_headers
syn keyword ngxDirectiveThirdParty more_clear_input_headers
syn keyword ngxDirectiveThirdParty more_set_headers
syn keyword ngxDirectiveThirdParty more_set_input_headers
" HTTP Push Module <http://pushmodule.slact.net/>
" Turn Nginx into an adept long-polling HTTP Push (Comet) server.
syn keyword ngxDirectiveThirdParty push_buffer_size
syn keyword ngxDirectiveThirdParty push_listener
syn keyword ngxDirectiveThirdParty push_message_timeout
syn keyword ngxDirectiveThirdParty push_queue_messages
syn keyword ngxDirectiveThirdParty push_sender
" HTTP Redis Module <http://people.FreeBSD.ORG/~osa/ngx_http_redis-0.3.1.tar.gz>>
" Redis <http://code.google.com/p/redis/> support.>
syn keyword ngxDirectiveThirdParty redis_bind
syn keyword ngxDirectiveThirdParty redis_buffer_size
syn keyword ngxDirectiveThirdParty redis_connect_timeout
syn keyword ngxDirectiveThirdParty redis_next_upstream
syn keyword ngxDirectiveThirdParty redis_pass
syn keyword ngxDirectiveThirdParty redis_read_timeout
syn keyword ngxDirectiveThirdParty redis_send_timeout
" HTTP JavaScript Module <http://wiki.github.com/kung-fu-tzu/ngx_http_js_module>
" Embedding SpiderMonkey. Nearly full port on Perl module.
syn keyword ngxDirectiveThirdParty js
syn keyword ngxDirectiveThirdParty js_filter
syn keyword ngxDirectiveThirdParty js_filter_types
syn keyword ngxDirectiveThirdParty js_load
syn keyword ngxDirectiveThirdParty js_maxmem
syn keyword ngxDirectiveThirdParty js_require
syn keyword ngxDirectiveThirdParty js_set
syn keyword ngxDirectiveThirdParty js_utf8
" Log Request Speed <http://wiki.nginx.org/NginxHttpLogRequestSpeed>
" Log the time it took to process each request.
syn keyword ngxDirectiveThirdParty log_request_speed_filter
syn keyword ngxDirectiveThirdParty log_request_speed_filter_timeout
" Memc Module <http://wiki.nginx.org/NginxHttpMemcModule>
" An extended version of the standard memcached module that supports set, add, delete, and many more memcached commands.
syn keyword ngxDirectiveThirdParty memc_buffer_size
syn keyword ngxDirectiveThirdParty memc_cmds_allowed
syn keyword ngxDirectiveThirdParty memc_connect_timeout
syn keyword ngxDirectiveThirdParty memc_flags_to_last_modified
syn keyword ngxDirectiveThirdParty memc_next_upstream
syn keyword ngxDirectiveThirdParty memc_pass
syn keyword ngxDirectiveThirdParty memc_read_timeout
syn keyword ngxDirectiveThirdParty memc_send_timeout
syn keyword ngxDirectiveThirdParty memc_upstream_fail_timeout
syn keyword ngxDirectiveThirdParty memc_upstream_max_fails
" Mogilefs Module <http://www.grid.net.ru/nginx/mogilefs.en.html>
" Implements a MogileFS client, provides a replace to the Perlbal reverse proxy of the original MogileFS.
syn keyword ngxDirectiveThirdParty mogilefs_connect_timeout
syn keyword ngxDirectiveThirdParty mogilefs_domain
syn keyword ngxDirectiveThirdParty mogilefs_methods
syn keyword ngxDirectiveThirdParty mogilefs_noverify
syn keyword ngxDirectiveThirdParty mogilefs_pass
syn keyword ngxDirectiveThirdParty mogilefs_read_timeout
syn keyword ngxDirectiveThirdParty mogilefs_send_timeout
syn keyword ngxDirectiveThirdParty mogilefs_tracker
" MP4 Streaming Lite Module <http://wiki.nginx.org/NginxMP4StreamingLite>
" Will seek to a certain time within H.264/MP4 files when provided with a 'start' parameter in the URL.
syn keyword ngxDirectiveThirdParty mp4
" Nginx Notice Module <http://xph.us/software/nginx-notice/>
" Serve static file to POST requests.
syn keyword ngxDirectiveThirdParty notice
syn keyword ngxDirectiveThirdParty notice_type
" Phusion Passenger <http://www.modrails.com/documentation.html>
" Easy and robust deployment of Ruby on Rails application on Apache and Nginx webservers.
syn keyword ngxDirectiveThirdParty passenger_base_uri
syn keyword ngxDirectiveThirdParty passenger_default_user
syn keyword ngxDirectiveThirdParty passenger_enabled
syn keyword ngxDirectiveThirdParty passenger_log_level
syn keyword ngxDirectiveThirdParty passenger_max_instances_per_app
syn keyword ngxDirectiveThirdParty passenger_max_pool_size
syn keyword ngxDirectiveThirdParty passenger_pool_idle_time
syn keyword ngxDirectiveThirdParty passenger_root
syn keyword ngxDirectiveThirdParty passenger_ruby
syn keyword ngxDirectiveThirdParty passenger_use_global_queue
syn keyword ngxDirectiveThirdParty passenger_user_switching
syn keyword ngxDirectiveThirdParty rack_env
syn keyword ngxDirectiveThirdParty rails_app_spawner_idle_time
syn keyword ngxDirectiveThirdParty rails_env
syn keyword ngxDirectiveThirdParty rails_framework_spawner_idle_time
syn keyword ngxDirectiveThirdParty rails_spawn_method
" RDS JSON Module <http://github.com/agentzh/rds-json-nginx-module>
" Help ngx_drizzle and other DBD modules emit JSON data.
syn keyword ngxDirectiveThirdParty rds_json
syn keyword ngxDirectiveThirdParty rds_json_content_type
syn keyword ngxDirectiveThirdParty rds_json_format
syn keyword ngxDirectiveThirdParty rds_json_ret
" RRD Graph Module <http://wiki.nginx.org/NginxNgx_rrd_graph>
" This module provides an HTTP interface to RRDtool's graphing facilities.
syn keyword ngxDirectiveThirdParty rrd_graph
syn keyword ngxDirectiveThirdParty rrd_graph_root
" Secure Download <http://wiki.nginx.org/NginxHttpSecureDownload>
" Create expiring links.
syn keyword ngxDirectiveThirdParty secure_download
syn keyword ngxDirectiveThirdParty secure_download_fail_location
syn keyword ngxDirectiveThirdParty secure_download_path_mode
syn keyword ngxDirectiveThirdParty secure_download_secret
" SlowFS Cache Module <http://labs.frickle.com/nginx_ngx_slowfs_cache/>
" Module adding ability to cache static files.
syn keyword ngxDirectiveThirdParty slowfs_big_file_size
syn keyword ngxDirectiveThirdParty slowfs_cache
syn keyword ngxDirectiveThirdParty slowfs_cache_key
syn keyword ngxDirectiveThirdParty slowfs_cache_min_uses
syn keyword ngxDirectiveThirdParty slowfs_cache_path
syn keyword ngxDirectiveThirdParty slowfs_cache_purge
syn keyword ngxDirectiveThirdParty slowfs_cache_valid
syn keyword ngxDirectiveThirdParty slowfs_temp_path
" Strip Module <http://wiki.nginx.org/NginxHttpStripModule>
" Whitespace remover.
syn keyword ngxDirectiveThirdParty strip
" Substitutions Module <http://wiki.nginx.org/NginxHttpSubsModule>
" A filter module which can do both regular expression and fixed string substitutions on response bodies.
syn keyword ngxDirectiveThirdParty subs_filter
syn keyword ngxDirectiveThirdParty subs_filter_types
" Supervisord Module <http://labs.frickle.com/nginx_ngx_supervisord/>
" Module providing nginx with API to communicate with supervisord and manage (start/stop) backends on-demand.
syn keyword ngxDirectiveThirdParty supervisord
syn keyword ngxDirectiveThirdParty supervisord_inherit_backend_status
syn keyword ngxDirectiveThirdParty supervisord_name
syn keyword ngxDirectiveThirdParty supervisord_start
syn keyword ngxDirectiveThirdParty supervisord_stop
" Upload Module <http://www.grid.net.ru/nginx/upload.en.html>
" Parses multipart/form-data allowing arbitrary handling of uploaded files.
syn keyword ngxDirectiveThirdParty upload_aggregate_form_field
syn keyword ngxDirectiveThirdParty upload_buffer_size
syn keyword ngxDirectiveThirdParty upload_cleanup
syn keyword ngxDirectiveThirdParty upload_limit_rate
syn keyword ngxDirectiveThirdParty upload_max_file_size
syn keyword ngxDirectiveThirdParty upload_max_output_body_len
syn keyword ngxDirectiveThirdParty upload_max_part_header_len
syn keyword ngxDirectiveThirdParty upload_pass
syn keyword ngxDirectiveThirdParty upload_pass_args
syn keyword ngxDirectiveThirdParty upload_pass_form_field
syn keyword ngxDirectiveThirdParty upload_set_form_field
syn keyword ngxDirectiveThirdParty upload_store
syn keyword ngxDirectiveThirdParty upload_store_access
" Upload Progress Module <http://wiki.nginx.org/NginxHttpUploadProgressModule>
" Tracks and reports upload progress.
syn keyword ngxDirectiveThirdParty report_uploads
syn keyword ngxDirectiveThirdParty track_uploads
syn keyword ngxDirectiveThirdParty upload_progress
syn keyword ngxDirectiveThirdParty upload_progress_content_type
syn keyword ngxDirectiveThirdParty upload_progress_header
syn keyword ngxDirectiveThirdParty upload_progress_json_output
syn keyword ngxDirectiveThirdParty upload_progress_template
" Upstream Fair Balancer <http://wiki.nginx.org/NginxHttpUpstreamFairModule>
" Sends an incoming request to the least-busy backend server, rather than distributing requests round-robin.
syn keyword ngxDirectiveThirdParty fair
syn keyword ngxDirectiveThirdParty upstream_fair_shm_size
" Upstream Consistent Hash <http://wiki.nginx.org/NginxHttpUpstreamConsistentHash>
" Select backend based on Consistent hash ring.
syn keyword ngxDirectiveThirdParty consistent_hash
" Upstream Hash Module <http://wiki.nginx.org/NginxHttpUpstreamRequestHashModule>
" Provides simple upstream load distribution by hashing a configurable variable.
syn keyword ngxDirectiveThirdParty hash
syn keyword ngxDirectiveThirdParty hash_again
" XSS Module <http://github.com/agentzh/xss-nginx-module>
" Native support for cross-site scripting (XSS) in an nginx.
syn keyword ngxDirectiveThirdParty xss_callback_arg
syn keyword ngxDirectiveThirdParty xss_get
syn keyword ngxDirectiveThirdParty xss_input_types
syn keyword ngxDirectiveThirdParty xss_output_type
" uWSGI Module <http://wiki.nginx.org/HttpUwsgiModule>
" Allows Nginx to interact with uWSGI processes and control what parameters are passed to the process.
syn keyword ngxDirectiveThirdParty uwsgi_bind
syn keyword ngxDirectiveThirdParty uwsgi_buffer_size
syn keyword ngxDirectiveThirdParty uwsgi_buffering
syn keyword ngxDirectiveThirdParty uwsgi_buffers
syn keyword ngxDirectiveThirdParty uwsgi_busy_buffers_size
syn keyword ngxDirectiveThirdParty uwsgi_cache
syn keyword ngxDirectiveThirdParty uwsgi_cache_bypass
syn keyword ngxDirectiveThirdParty uwsgi_cache_key
syn keyword ngxDirectiveThirdParty uwsgi_cache_lock
syn keyword ngxDirectiveThirdParty uwsgi_cache_lock_timeout
syn keyword ngxDirectiveThirdParty uwsgi_cache_methods
syn keyword ngxDirectiveThirdParty uwsgi_cache_min_uses
syn keyword ngxDirectiveThirdParty uwsgi_cache_path
syn keyword ngxDirectiveThirdParty uwsgi_cache_use_stale
syn keyword ngxDirectiveThirdParty uwsgi_cache_valid
syn keyword ngxDirectiveThirdParty uwsgi_connect_timeout
syn keyword ngxDirectiveThirdParty uwsgi_hide_header
syn keyword ngxDirectiveThirdParty uwsgi_ignore_client_abort
syn keyword ngxDirectiveThirdParty uwsgi_ignore_headers
syn keyword ngxDirectiveThirdParty uwsgi_intercept_errors
syn keyword ngxDirectiveThirdParty uwsgi_max_temp_file_size
syn keyword ngxDirectiveThirdParty uwsgi_modifier1
syn keyword ngxDirectiveThirdParty uwsgi_modifier2
syn keyword ngxDirectiveThirdParty uwsgi_next_upstream
syn keyword ngxDirectiveThirdParty uwsgi_no_cache
syn keyword ngxDirectiveThirdParty uwsgi_param
syn keyword ngxDirectiveThirdParty uwsgi_pass
syn keyword ngxDirectiveThirdParty uwsgi_pass_header
syn keyword ngxDirectiveThirdParty uwsgi_pass_request_body
syn keyword ngxDirectiveThirdParty uwsgi_pass_request_headers
syn keyword ngxDirectiveThirdParty uwsgi_read_timeout
syn keyword ngxDirectiveThirdParty uwsgi_send_timeout
syn keyword ngxDirectiveThirdParty uwsgi_store
syn keyword ngxDirectiveThirdParty uwsgi_store_access
syn keyword ngxDirectiveThirdParty uwsgi_string
syn keyword ngxDirectiveThirdParty uwsgi_temp_file_write_size
syn keyword ngxDirectiveThirdParty uwsgi_temp_path
" highlight
hi link ngxComment Comment
hi link ngxVariable Identifier
hi link ngxVariableBlock Identifier
hi link ngxVariableString PreProc
hi link ngxBlock Normal
hi link ngxString String
hi link ngxBoolean Boolean
hi link ngxDirectiveBlock Statement
hi link ngxDirectiveImportant Type
hi link ngxDirectiveControl Keyword
hi link ngxDirectiveError Constant
hi link ngxDirectiveDeprecated Error
hi link ngxDirective Identifier
hi link ngxDirectiveThirdParty Special
let b:current_syntax = "nginx"

View file

@ -39,11 +39,11 @@
**concat_types** `MIME types`
**默认:** `concat_types: application/x-javascript text/css`
**默认:** `concat_types: text/css application/x-javascript`
**上下文:** `http, server, location`
定义配置的[MIME types](http://en.wikipedia.org/wiki/MIME_type)以及 "application/x-javascript" 是可以被接受
定义哪些[MIME types](http://en.wikipedia.org/wiki/MIME_type)是可以被接受
<br/>
<br/>

View file

@ -53,12 +53,3 @@ Context: `http, server, location`
The same as `proxy_request_buffering`.
## gzip\_clear\_etag ##
Syntax: **gzip\_clear\_etag** `on | off`
Default: `on`
Context: `http, server, location`
Determines whether gzip module should clear the “ETag” response header field.

View file

@ -53,13 +53,3 @@ Context: `http, server, location`
用法跟`proxy_request_buffering`指令一样。
## gzip\_clear\_etag ##
Syntax: **gzip\_clear\_etag** `on | off`
Default: `on`
Context: `http, server, location`
压缩的时候是否删除"ETag"响应头。

View file

@ -1,250 +0,0 @@
Name
====
* ngx_http_dyups_module
Description
===========
This module can be used to update your upstream-list without reloadding Nginx.
TODO:
It can not work with common `nginx_upstream_check_module`.
Compilation
===========
The module is not compiled into Tengine by default. It can be enabled with '--with-http_dyups_module'
configuration parameter, and enabled lua support with '--with-http_dyups_lua_api'.
But it can not be compiled as a '.so'.
Example
==========
file: conf/nginx.conf
daemon off;
error_log logs/error.log debug;
events {
}
http {
dyups_upstream_conf conf/upstream.conf;
include conf/upstream.conf;
server {
listen 8080;
location / {
proxy_pass http://$host;
}
}
server {
listen 8088;
location / {
echo 8088;
}
}
server {
listen 8089;
location / {
echo 8089;
}
}
server {
listen 8081;
location / {
dyups_interface;
}
}
}
file: conf/upstream.conf
upstream host1 {
server 127.0.0.1:8088;
}
upstream host2 {
server 127.0.0.1:8089;
}
Directives
===========
dyups_interface
--------------------------
**Syntax**: *dyups_interface*
**Default**: *none*
**Context**: *loc*
This directive set the interface location where you can add or delete the upstream list. See the section of Interface for detail.
dyups_read_msg_timeout
-----------------------------
**Syntax**: *dyups_read_msg_timeout time*
**Default**: *1s*
**Context**: *main*
This directive set the interval of workers readding the commands from share memory.
dyups_shm_zone_size
-----------------------------
**Syntax**: *dyups_shm_zone_size size*
**Default**: *2M*
**Context**: *main*
This directive set the size of share memory which used to store the commands.
dyups_upstream_conf
-----------------------------
**Syntax**: *dyups_upstream_conf path*
**Default**: *none*
**Context**: *main*
This directive set the path of file which you dumped all of upstreams' configs, it will be loaded in `init process` after process respwan to restore upstreams.
dyups_trylock
-----------------------------
**Syntax**: *dyups_trylock on | off*
**Default**: *off*
**Context**: *main*
You will get a better prefomance but it maybe not stable, and you will get a '409' when the update request conflicts with others.
restful interface
========================
GET
-------------------
* `/detail` get all upstreams and their servers
* `/list` get the list of upstreams
* `/upstream/name` find the upstream by it's name
POST
-------------------
* `/upstream/name` update one upstream
* `body` commands;
* `body` server ip:port;
DELETE
-------------------
* `/upstream/name` delete one upstream
Call the interface, when you get the return code is `HTTP_INTERNAL_SERVER_ERROR 500`, you need to reload nginx to make the Nginx work at a good state.
If you got `HTTP_CONFLICT 409`, you need resend the same commands again latter.
The /list and /detail interface will return `HTTP_NO_CONTENT 204` when there is no upstream.
Other code means you should modify your commands and call the interface again.
`ATTENEION`: You also need a `third-party` to generate the new config and dump it to Nginx'conf directory.
Sample
-------------------
```bash
» curl -H "host: dyhost" 127.0.0.1:8080
<html>
<head><title>502 Bad Gateway</title></head>
<body bgcolor="white">
<center><h1>502 Bad Gateway</h1></center>
<hr><center>nginx/1.3.13</center>
</body>
</html>
» curl -d "server 127.0.0.1:8089;server 127.0.0.1:8088;" 127.0.0.1:8081/upstream/dyhost
success
» curl -H "host: dyhost" 127.0.0.1:8080
8089
» curl -H "host: dyhost" 127.0.0.1:8080
8088
» curl 127.0.0.1:8081/detail
host1
server 127.0.0.1:8088
host2
server 127.0.0.1:8089
dyhost
server 127.0.0.1:8089
server 127.0.0.1:8088
» curl -i -X DELETE 127.0.0.1:8081/upstream/dyhost
success
» curl 127.0.0.1:8081/detail
host1
server 127.0.0.1:8088
host2
server 127.0.0.1:8089
```
API
========================
```c
extern ngx_flag_t ngx_http_dyups_api_enable;
ngx_int_t ngx_dyups_update_upstream(ngx_str_t *name, ngx_buf_t *buf,
ngx_str_t *rv);
ngx_int_t ngx_dyups_delete_upstream(ngx_str_t *name, ngx_str_t *rv);
```
## Lua API Example
NOTICE:
you should add the directive `dyups_interface` into your config file to active this feature
```lua
content_by_lua '
local dyups = require "ngx.dyups"
local status, rv = dyups.update("test", [[server 127.0.0.1:8088;]]);
ngx.print(status, rv)
if status ~= 200 then
ngx.print(status, rv)
return
end
ngx.print("update success")
status, rv = dyups.delete("test")
if status ~= 200 then
ngx.print(status, rv)
return
end
ngx.print("delete success")
';
```

View file

@ -13,14 +13,10 @@ This module will help monitor running status of Tengine.
* The information is divided into different zones, and each zone is independent.
* The status information is about connections, requests, response status codes, input and output flows,
rt, upstreams, and so on.
rt, and upstreams.
* It shows all the results by default, and can be set to show part of them by specifying zones.
* It support for user-defined status by using nginx variables. The maximum of all the status is 50.
* It recycles out-of-date running status information.
Compilation
===========
@ -51,9 +47,9 @@ Example
* Line format:
kv,bytes_in_total,bytes_out_total,conn_total,req_total,2xx,3xx,4xx,5xx,other,rt_total,upstream_req,upstream_rt,upstream_tries,200,206,302,304,403,404,416,499,500,502,503,504,508,detail_other,ups_4xx,ups_5xx
kv,bytes_in_total,bytes_out_total,conn_total,req_total,2xx,3xx,4xx,5xx,other,rt_total,upstream_req,upstream_rt,upstream_tries
* **kv** value of the variable defined by the directive 'req_status_zone'. The maximun key length is configurable, 104B by default, and overlength will be cut off
* **kv** value of the variable defined by the directive 'req_status_zone'
* **bytes_in_total** total number of bytes received from client
* **bytes_out_total** total number of bytes sent to client
* **conn_total** total number of accepted connections
@ -67,24 +63,6 @@ Example
* **upstream_req** total number of requests calling for upstream
* **upstream_rt** accumulation or upstream rt
* **upstream_tries** total number of times calling for upstream
* **200** total number of 200 requests
* **206** total number of 206 requests
* **302** total number of 302 requests
* **304** total number of 304 requests
* **403** total number of 403 requests
* **404** total number of 404 requests
* **416** total number of 416 requests
* **499** total number of 499 requests
* **500** total number of 500 requests
* **502** total number of 502 requests
* **503** total number of 503 requests
* **504** total number of 504 requests
* **508** total number of 508 requests
* **detail_other** total number of requests of other status codes
* **ups_4xx** total number of requests of upstream 4xx
* **ups_5xx** total number of requests of upstream 5xx
* some fields will be removed in future, because user-defined status has been supported.
* tsar can parse the result and monitor, see also https://github.com/alibaba/tsar
@ -134,41 +112,3 @@ req_status_show
**Context**: *loc*
Display the status information. You can specify zones to display.
req_status_zone_add_indicator
--------------------------------
**Syntax**: *req_status_zone_add_indecator zone_name $var1 [$var2 [...]]*
**Default**: *none*
**Context**: *main*
Add user-defined status by using nginx variables. The status will be appended at the end of each line on display.
req_status_zone_key_length
-------------------------------
**Syntax**: *req_status_zone_key_length zone_name length*
**Default**: *none*
**Context**: *main*
Define the maximun length of key for a zone. The default is 104.
req_status_zone_recycle
-------------------------------
**Syntax**: *req_status_zone_recycle zone_name times seconds*
**Default**: *none*
**Context**: *main*
Define the recycle threshold for a zone. Recycle will be switched on when the shared memory is exhausted, and will only take effect on imformation whose visit frequency is lower than the setting.
The setting frequency is defined by 'times' and 'seconds', and it is 10r/min by default.
req_status_zone_recycle demo_zone 10 60;

View file

@ -8,14 +8,10 @@
* 这个模块计算定义的变量根据变量值分别统计Tengine的运行状况。
* 可以监视的运行状况有连接数、请求数、各种响应码范围的请求数、输入输出流量、rt、upstream访问
* 可以监视的运行状况有连接数、请求数、各种响应码范围的请求数、输入输出流量、rt、upstream访问。
* 可以指定获取所有监控结果或者一部分监控结果。
* 利用变量添加自定义监控状态。总的监控状态最大个数为50个。
* 回收过期的监控数据。
编译
===========
@ -43,9 +39,9 @@
* 每行的格式
kv,bytes_in_total,bytes_out_total,conn_total,req_total,2xx,3xx,4xx,5xx,other,rt_total,upstream_req,upstream_rt,upstream_tries,200,206,302,304,403,404,416,499,500,502,503,504,508,detail_other,ups_4xx,ups_5xx
kv,bytes_in_total,bytes_out_total,conn_total,req_total,2xx,3xx,4xx,5xx,other,rt_total
* kv 计算得到的req_status_zone指令定义变量的值最大长度可配置默认104B超长的部分截断
* kv 计算得到的req_status_zone指令定义变量的值
* bytes_in_total 从客户端接收流量总和
* bytes_out_total 发送到客户端流量总和
* conn_total 处理过的连接总数
@ -59,24 +55,6 @@
* upstream_req 需要访问upstream的请求总数
* upstream_rt 访问upstream的总rt
* upstream_tries upstram总访问次数
* 200 200请求的总数
* 206 206请求的总数
* 302 302请求的总数
* 304 304请求的总数
* 403 403请求的总数
* 404 404请求的总数
* 416 416请求的总数
* 499 499请求的总数
* 500 500请求的总数
* 502 502请求的总数
* 503 503请求的总数
* 504 504请求的总数
* 508 508请求的总数
* detail_other 非以上13种status code的请求总数
* ups_4xx upstream返回4xx响应的请求总数
* ups_5xx upstream返回5xx响应的请求总数
* 注,后续会清理这些状态,因为已经支持了自定义状态。
* tsar可解析输出结果具体见https://github.com/alibaba/tsar
@ -125,41 +103,3 @@ req_status_show
**Context**: *loc*
按格式返回统计结果。可指定返回部分目标的统计结果。
req_status_zone_add_indicator
--------------------------------
**Syntax**: *req_status_zone_add_indecator zone_name $var1 [$var2 [...]]*
**Default**: *none*
**Context**: *main*
通过变量增加自定义字段,新增加的字段目前会展现在每行的末尾。
req_status_zone_key_length
-------------------------------
**Syntax**: *req_status_zone_key_length zone_name length*
**Default**: *none*
**Context**: *main*
定义某个共享内存块中key的最大长度默认值104。key中超出的部分会被截断。
req_status_zone_recycle
-------------------------------
**Syntax**: *req_status_zone_recycle zone_name times seconds*
**Default**: *none*
**Context**: *main*
定义某个共享内存块过期数据的回收。回收在共享内存耗尽时自动开启。只会回收访问频率低于设置值的监控数据。
频率定义为 times / seconds默认值为10r/min
req_status_zone_recycle demo_zone 10 60;

View file

@ -1,10 +1,5 @@
# Name #
**NOTE**
1. This module has been updated to official nginx SPDY/3.1 module, the document is available here:
http://nginx.org/en/docs/http/ngx_http_spdy_module.html
2. This document only applies to Tengine-2.1.0 and its old version. But the listen option `spdy_detect` can still be used with SPDY/3.1.
**ngx\_http\_spdy\_module**
Tengine added SPDY/3 support to this module. The new directives are listed below.

View file

@ -1,10 +1,5 @@
# Name #
**注意**
1. Tengine-2.1.0以上版本的SPDY模块已经与官方nginx同步只支持SPDY/3.1。
文档参考: http://nginx.org/en/docs/http/ngx_http_SPDY_module.html
2. 以下文档只适用于Tengine-2.1.0及以下版本只支持SPDY/2和SPDY/3。listen参数`spdy_detect`在SPDY/3.1下任然可以使用。
**ngx\_http\_spdy\_module**
Tengine对SPDY模块增加SPDY/3协议的支持。以下是新增的指令。

View file

@ -1,127 +0,0 @@
# ngx_http_sysguard_module
## Description
This module monitors memory usage (including the swap partition), load of CPUs and average response time of requests of the system. If any guideline that is monitored exceeds the threshold set by user, the current request will be redirected to a specific url. To be clarified, this module can only be full functional when the system supports sysinfo function and loadavg function. The sysguard module also need to read memory information from /proc file system.
## Configuration
server {
sysguard on;
sysguard_mode or;
sysguard_load load=10.5 action=/loadlimit;
sysguard_mem swapratio=20% action=/swaplimit;
sysguard_mem free=100M action=/freelimit;
sysguard_rt rt=0.01 period=5s action=/rtlimit;
location /loadlimit {
return 503;
}
location /swaplimit {
return 503;
}
location /freelimit {
return 503;
}
location /rtlimit {
return 503;
}
}
## Directives
**sysguard** `on` | `off`
**Default:** `sysguard off`
**Context:** `http, server, location`
Enable or disable the sysguard module.
<br/>
<br/>
**sysguard_load** `load=[ncpu*]number [action=/url]`
**Default:** `none`
**Context:** `http, server, location`
This directive tells the module to protect the system by monitoring the load of CPUs. If the system's loads reach the value that is specified by 'number' in one minute, the incoming request will be redirected to the url specified by 'action' parameter. If 'action' is not specified, tengine will respond with 503 error directly. It's also possible to use ncpu\* to make the configuration, in which case, ncpu stands for the number of the CPU cores. For instance, load = ncpu*1.5.
<br/>
<br/>
**sysguard_mem** `[swapratio=ratio%] [free=size] [action=/url]`
**Default:** `-`
**Context:** `http, server, location`
This directive is used to tell the module to protect the system by monitoring memroy usage. 'swapratio' is used to specify how many percent of the swap partition of the system, and 'free' is used to specify the miminum size of current memory. If any condition is fulfilled, the incoming request will be redirected to specified url, which is defined by parameter 'action'. If 'action' is not specified, the request will be responded with 503 error directly. Besides, if the user disables the swap partition in the system, this directive will not be functional. 'free' is calculated by /proc/meminfo, the algorithm is 'memfree = free + buffered + cached'.
<br/>
<br/>
**sysguard_rt** `[rt=seconds] [period=time] [action=/url]`
**Default:** `-`
**Context:** `http, server, location`
This directive is used to tell the module to protect the system by monitoring average response time of requests in a specified period. Parameter rt is used to set a threshold of the average response time, in second. Parameter period is used to specifiy the period of the statistics cycle. If the average response time of the system exceeds the threshold specified by the user, the incoming request will be redirected to a specified url which is defined by parameter 'action'. If no 'action' is presented, the request will be responded with 503 error directly.
<br/>
<br/>
**sysguard_mode** `and` | `or`
**Default:** 'sysguard_mode or'
**Context** 'http, server, location'
If there are more than one type of monitor, this directive is used to specified the relations among all the monitors which are: 'and' for all matching and 'or' for any matching.
<br/>
<br/>
**sysguard_interval** 'time'
**Default** 'sysguard_interval 1s'
**Context** 'http, server, location'
Specify the time interval to update your system information.
<br/>
<br/>
**sysguard_log_level** '[info | notice | warn | error]'
**Default** 'sysguard_log_level error'
**Context** 'http, server, location'
Specify the log level of sysguard.
## Installation
1. Compile sysguard module
configure [--with-http_sysguard_module | --with-http_sysguard_module=shared]
--with-http_sysguard_module, sysguard module will be compiled statically into tengine.
--with-http_sysguard_module=shared, sysguard module will be compiled dynamically into tengine.
2. Build and install
make&make install
3. Make sysguard configuration
4. Run

View file

@ -1,127 +0,0 @@
# sysguard 模块
## 介绍
该模块监控内存含swap分区、CPU和请求的响应时间当某些监控指标达到设定的阈值时跳转到指定的url。注意目前该模块仅对系统支持sysinfo函数时才支持基于load与内存信息的保护以及系统支持loadavg函数时支持基于load进行保护。模块需要从/proc文件系统中读取内存信息。
## 配置
server {
sysguard on;
sysguard_mode or;
sysguard_load load=10.5 action=/loadlimit;
sysguard_mem swapratio=20% action=/swaplimit;
sysguard_mem free=100M action=/freelimit;
sysguard_rt rt=0.01 period=5s action=/rtlimit;
location /loadlimit {
return 503;
}
location /swaplimit {
return 503;
}
location /freelimit {
return 503;
}
location /rtlimit {
return 503;
}
}
## 指令
**sysguard** `on` | `off`
**默认:** `sysguard off`
**上下文:** `http, server, location`
打开或者关闭这个模块
<br/>
<br/>
**sysguard_load** `load=[ncpu*]number [action=/url]`
**默认:** `none`
**上下文:** `http, server, location`
该指令用于配置根据系统的load来限制用户的请求以保护系统。当系统在一分钟内的load达到number时将进来的请求转到action所指定的url。如果action没有配置则直接返回503错误。load的数值还支持使用ncpu\*系数的方式来配置ncpu表示cpu核数乘以固定的系数得出期望限制的load值如: load=ncpu\*1.5。
<br/>
<br/>
**sysguard_mem** `[swapratio=ratio%] [free=size] [action=/url]`
**默认:** `-`
**上下文:** `http, server, location`
该指令用于配置根据系统的内存使用状态来限制用户请求以保护系统。swapratio用于配置当当前交换空间的已使用ratio%时或者剩下的内存少于size时就将进来的请求跳转到指定的url。如果action没有配置则直接返回503错误。另外如果用户自己禁用了交换区间则配置该指定是不起作用的。free是根据/proc/meminfo的内容来计算的计算公式是"memfree= free + buffered + cached"
<br/>
<br/>
**sysguard_rt** `[rt=seconds] [period=time] [action=/url]`
**默认:** `-`
**上下文:** `http, server, location`
该指令用于配置根据系统的请求平均响应时间来限制用户请求以保护系统。rt参数用于设置请求的平均响应时间的阈值单位为秒平均响应时间的统计周期使用period参数设置。当系统的请求平均响应时间大于阈值时将当前请求跳转到action参数配置的url如果action没有配置则直接返回503。
<br/>
<br/>
**sysguard_mode** `and` | `or`
**默认:** 'sysguard_mode or'
**上下文** 'http, server, location'
如果设置了多个监控指标此参数用于指定指标间的判断关系and为全部满足or为任一满足。
<br/>
<br/>
**sysguard_interval** 'time'
**默认** 'sysguard_interval 1s'
**上下文** 'http, server, location'
该指定用于配置获取系统信息时的缓存时间。默认为1s则表示在这1s内只调用一次系统函数来获取系统的当前状况。
<br/>
<br/>
**sysguard_log_level** '[info | notice | warn | error]'
**默认** 'sysguard_log_level error'
**上下文** 'http, server, location'
该指令用于配置,当保护系统的操作执行时,记录日志时的日志级别。
## 安装
1. 编译sysguard模块
configure [--with-http_sysguard_module | --with-http_sysguard_module=shared]
--with-http_sysguard_module选项sysguard模块将被静态编译到tengine中
--with-http_sysguard_module=shared, sysguard模块将被编译成动态文件采用动态模块的方式添加到tengine中
2. 编译,安装
make&make install
3. 配置sysguard的配置项
4. 运行

View file

@ -63,8 +63,6 @@ Context: `upstream`
Add health check for the upstream servers.
Passive health checking should not be enabled, as they may interfere. So do not use fail_timeout for the servers in the upstream context for which proactive health checking is enabled.
The parameters' meanings are:
* `interval`: the check request's interval time.
@ -109,7 +107,7 @@ In addition, in the case of "GET" method, size of the request uri should not be
Syntax: **check\_http\_expect\_alive** `[ http_2xx | http_3xx | http_4xx | http_5xx ]`
Default: `http_2xx http_3xx`
Default: `http_2xx | http_3xx`
Context: `upstream`
@ -172,7 +170,7 @@ Below it's the sample html page:
<tr>
<td>0</td>
<td>backend</td>
<td>192.168.0.1:80</td>
<td>106.187.48.116:80</td>
<td>up</td>
<td>39</td>
<td>0</td>
@ -185,7 +183,7 @@ Below it's the sample html page:
Below it's the sample of csv page:
0,backend,192.168.0.1:80,up,46,0,http,80
0,backend,106.187.48.116:80,up,46,0,http,80
Below it's the sample of json page:
@ -193,7 +191,7 @@ Below it's the sample of json page:
"total": 1,
"generation": 3,
"server": [
{"index": 0, "upstream": "backend", "name": "192.168.0.1:80", "status": "up", "rise": 58, "fall": 0, "type": "http", "port": 80}
{"index": 0, "upstream": "backend", "name": "106.187.48.116:80", "status": "up", "rise": 58, "fall": 0, "type": "http", "port": 80}
]
}}

View file

@ -74,7 +74,6 @@ Context: `upstream`
- `tcp`简单的tcp连接如果连接成功就说明后端正常。
- `ssl_hello`发送一个初始的SSL hello包并接受服务器的SSL hello包。
- `http`发送HTTP请求通过后端的回复包的状态来判断后端是否存活。
- `fastcgi`发送fsatcgi请求通过后端的回复包的状态来判断后端是否存活。
- `mysql`: 向mysql服务器连接通过接收服务器的greeting包来判断后端是否存活。
- `ajp`向后端发送AJP协议的Cping包通过接收Cpong包来判断后端是否存活。
* `port`: 指定后端服务器的检查端口。你可以指定不同于真实服务的后端服务器的端口比如后端提供的是443端口的应用你可以去检查80端口的状态来判断后端健康状况。默认是0表示跟后端server提供真实服务的端口一样。该选项出现于Tengine-1.4.0。
@ -105,18 +104,6 @@ Context: `upstream`
当采用长连接进行健康检查时需在该指令中添加keep-alive请求头`"HEAD / HTTP/1.1\r\nConnection: keep-alive\r\n\r\n"`。
同时,在采用`"GET"`方法的情况下请求uri的size不宜过大确保可以在1个`interval`内传输完成,否则会被健康检查模块视为后端服务器或网络异常。
## check\_fastcgi\_param ##
Syntax: **check\_fastcgi\_params** `parameter`:`value`
Default: `REQUEST_METHOD: GET`
`REQUEST_URI: /`
`SCRIPT_FILENAME: index.php'
Context: `upstream`
该指令可以配置fastcgi健康检查包发送的请求的header项。
## check\_http\_expect\_alive ##
Syntax: **check\_http\_expect\_alive** `[ http_2xx | http_3xx | http_4xx | http_5xx ]`
@ -186,7 +173,7 @@ Context: `location`
<tr>
<td>0</td>
<td>backend</td>
<td>192.168.0.1:80</td>
<td>106.187.48.116:80</td>
<td>up</td>
<td>39</td>
<td>0</td>
@ -199,7 +186,7 @@ Context: `location`
下面是csv格式页面的例子
0,backend,192.168.0.1:80,up,46,0,http,80
0,backend,106.187.48.116:80,up,46,0,http,80
下面是json格式页面的例子
@ -210,3 +197,4 @@ Context: `location`
{"index": 0, "upstream": "backend", "name": "106.187.48.116:80", "status": "up", "rise": 58, "fall": 0, "type": "http", "port": 80}
]
}}

View file

@ -1,47 +0,0 @@
Name
====
* ngx_http_upstream_dynamic_module
Description
===========
* This module provides the functionality to resolve domain names into IP addresses in an upstream at run-time.
Examples
========
upstream backend {
dynamic_resolve fallback=stale fail_timeout=30s;
server a.com;
server b.com;
}
server {
...
proxy_pass http://backend;
}
Directives
==========
dynamic_resolve
---------------
**Syntax**: *dynamic_resolve [fallback=stale|next|shutdown] [fail_timeout=time]*
**Default**: *-*
**Context**: *upstream*
Enable dynamic DNS resolving functionality in an upstream.
The 'fallback' parameter specifies what action to take if a domain name can not be resolved into an IP address:
* stale, use the original IP addresses resolved when tengine starts.
* next, go to next availiable server in the upstream.
* shutdown, finalize current request.
The 'fail_timeout' parameter specifies how long time tengine considers the DNS server as unavailiable if a DNS query fails for a server in the upstream. In this period of time, all requests comming will follow what 'fallback' specifies.

View file

@ -1,47 +0,0 @@
模块名
=====
* ngx_http_upstream_dynamic_module
介绍
===
* 此模块提供了在运行时动态解析upstream中server域名的功能
配置示例
=======
upstream backend {
dynamic_resolve fallback=stale fail_timeout=30s;
server a.com;
server b.com;
}
server {
...
proxy_pass http://backend;
}
指令
===
dynamic_resolve
---------------
**语法**: *dynamic_resolve [fallback=stale|next|shutdown] [fail_timeout=time]*
**默认值**: *-*
**上下文**: *upstream*
指定在某个upstream中启用动态域名解析功能。
fallback参数指定了当域名无法解析时采取的动作
* stale, 使用tengine启动的时候获取的旧地址
* next, 选择upstream中的下一个server
* shutdown, 结束当前请求
fail_timeout参数指定了一个时间在这个时间范围内DNS服务将被当作无法使用。具体来说就是当某次DNS请求失败后假定后续多长的时间内DNS服务依然不可用以减少对无效DNS的查询。

View file

@ -1,164 +0,0 @@
build/
work/
tags
cscope.*
*.mobi
genmobi.sh
.libs
*.swp
*.slo
*.la
*.swo
*.lo
*~
*.o
print.txt
.rsync
*.tar.gz
dist
build[789]
build
tags
update-readme
*.tmp
test/Makefile
test/blib
test.sh
t.sh
t/t.sh
test/t/servroot/
releng
reset
*.t_
src/handler.h
src/util.c
src/module.h
src/module.c
src/drizzle.c
src/processor.h
src/handler.c
src/util.h
src/drizzle.h
src/processor.c
src/output.c
src/output.h
libdrizzle
ctags
src/stream.h
nginx
keepalive
reindex
src/keepalive.c
src/keepalive.h
src/checker.h
src/checker.c
src/quoting.h
src/quoting.c
src/module.h
src/module.c
src/util.h
src/util.c
src/processor.h
src/processor.c
src/rds.h
src/utils.h
src/handler.c
src/handler.h
util/bench
*.html
trace.out*
try.sh
src/cache.c
src/cache.h
src/common.h
src/directive.c
src/directive.h
src/consts.[ch]
src/contentby.[ch]
src/pcrefix.[ch]
src/util.c
src/clfactory.c
src/directive.c
src/conf.h
src/setby.h
src/cache.h
src/hook.c
src/util.h
src/hook.h
src/common.h
src/directive.h
src/conf.c
src/setby.c
src/cache.c
src/module.c
src/clfactory.h
src/capturefilter.[ch]
src/contentby.c
pack
b.sh
src/in.[ch]
src/out.[ch]
go
all.sh
src/accessby.[ch]
src/rewriteby.[ch]
src/patch.[ch]
src/ndk.[ch]
src/control.[ch]
src/output.[ch]
src/variable.[ch]
src/string.[ch]
src/misc.[ch]
src/log.[ch]
src/exception.[ch]
src/subrequest.[ch]
src/time.[ch]
src/regex.[ch]
src/ctx.[ch]
src/args.[ch]
src/headers.[ch]
src/script.[ch]
src/filter.[ch]
src/shdict.[ch]
src/body.[ch]
src/uri.[ch]
src/api.[ch]
src/coroutine.[ch]
src/logby.[ch]
src/sleep.[ch]
a.patch
all
build1[0-9]
g
buildroot/
src/headerfilterby.[ch]
*.patch
analyze
tsock
a.c
test.lua
build12
ERRORS
src/bodyfilterby.[ch]
src/tcp.[ch]
src/initby.[ch]
src/initworkerby.[ch]
src/socket.[ch]
src/udp.[ch]
src/method.[ch]
tre
src/phase.[ch]
src/probe.h
src/uthread.[ch]
src/timer.[ch]
src/config.[ch]
src/worker.[ch]
*.plist
lua
ttimer
Makefile
tsubreq
tthread
addr2line
hup
theaders

View file

@ -1,3 +0,0 @@
[submodule "deps/ngx_devel_kit"]
path = deps/ngx_devel_kit
url = git://github.com/simpl/ngx_devel_kit.git

View file

@ -1,51 +0,0 @@
0.2.0 - 5 July 2011
* now we support ngx.var[1], ngx.var[2], and etc to refer to the nginx regex capturing variables \$1, \$2, and etc in Lua. this resolved github issue #43. thanks Tobia Conforto for reporting it.
* now we use the same value overriding mechanism as ngx_rewrite's set command for ngx.var.VAR = new_value. Assigning values to special variables like $limit_rate and $args should now work; also writing to built-in variables that are not changeable (like $arg_PARAMETER) will result in a 500 error page, as expected, now. thanks Richard Kearsley for reporting it.
* fixed the lua_code_cache off warning when the lua_code_cache is explicitly on. thanks Feng Xingguo.
* applied the patch from cyberty to add ngx.http_time() function to expose the nginx core function ngx_http_time to the Lua land.
* fixed an issue on i386: we now use off_t consistently. mixing it with size_t on 32-bit systems can cause Bad Things. this fixed github issue #42. thanks moodydeath.
* fixed an issue on i386: fixed a formatter mismatch issue in ngx_http_echo_adjust_subrequest. thanks Wang Bin. This caused incorrect subrequest Content-Length header when a body is specified.
* now in the subrequest capturing processor, we worked around an issue in ngx_http_static_module that when it issues 301 redirect for directory access w/o a trailing slash, it does not inject r->headers_out.location into the r->headers_out.headers list. thanks moodydeath for reporting it in the discussion of github issue #41.
* fixed a bug in ngx.location.capture() and ngx.location.capture_multi() that we could not capture locations with internal redirections in them. thanks moodydeath for reporting it in github issue #41.
* fixed redundant last chunk issue for ngx.exec() invocation at rewrite and access phases: we should quit the current core_run_phases cycle; this also fixed github issue #40: 2 Subrequest calls when using access_by_lua, ngx.exec and echo_location.
* fixed ngx.exit(status) where status >= 200 and status < 300 for access_by_lua* and rewrite_by_lua*: it should quit the whole request altegother and skip all those subsequent phase handlers (if any). thanks moodydeath for reporting it.
* fixed github issue #39: setting differnt response headers in Lua with common prefix might interfere with each other. thanks moodydeath.
* fixed GitHub issue #38: request headers did not forward to subrequests when the "method" or "body" option is explicitly specified by a non-nil value for ngx.location.capture(). thanks Richard Kearsley.
* fixed a bug in output header set; we should always set the header->hash to 1. thanks moodydeath for reporting it.
* fixed spots that trigger the "variable set but not used" warning issued by gcc 4.6.0.
* now we turn the ngx.req.header table into an ngx.req.get_headers() function; we also added ngx.req.set_header(name, value) and ngx.req.clear_header(name). thanks moodydeath.
* now we make ngx_devel_kit (NDK) optional. thanks Kirill A. Korinskiy.
* removed a duplicate definition of the ngx_str_set macro caught by ctags; also fixed a warning thrown by gcc -O3 on Mac OS X 10.6.
* added patch to use PCRE related Lua extensions in ngx_lua (chaoslawful)
* now we change the way we process HTTP 1.0 requests by automatically buffering all the user outputs generated by ngx.print()/ngx.say() calls, which is much more natural than the old broken way.
* fixed the "ngx.exec() after ngx.location.capture() hanging" bug for rewrite_by_lua* and access_by_lua* as well. thanks Wendal Chen.
* applied a patch from moodydeath to introduce the "ngx.is_subrequest" attribute.
* now we encourage use of the client_body_in_single_buffer directive instead of big client_body_buffer_size when lua_need_request_body is turned on.
* fixed the config script and added extra linking options needed by LuaJIT in 64-bit Mac OS X.
* fixed the zero size alert caused by ngx.print("") in Lua.
* now we always allocate r->request_body for subrequests when the method option is specified for ngx.location.capture*. this prevents accidental inheritance of parent request's request body when client_body_buffer_size < client_max_body_size.

File diff suppressed because it is too large Load diff

View file

@ -1,363 +0,0 @@
ngx_feature="Lua library"
ngx_feature_libs="-llua -lm"
ngx_feature_name=
ngx_feature_run=no
ngx_feature_incs="#include <lauxlib.h>"
ngx_feature_path=
ngx_feature_test="#if LUA_VERSION_NUM != 501
# error unsupported Lua language version
#endif
(void) luaL_newstate();"
if [ -n "$LUAJIT_INC" -o -n "$LUAJIT_LIB" ]; then
# explicitly set Lua lib path
ngx_feature="LuaJIT library in $LUAJIT_LIB and $LUAJIT_INC (specified by the LUAJIT_LIB and LUAJIT_INC env)"
ngx_feature_path="$LUAJIT_INC"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R$LUAJIT_LIB -L$LUAJIT_LIB -lluajit-5.1 -lm"
else
ngx_feature_libs="-L$LUAJIT_LIB -lluajit-5.1 -lm"
fi
. auto/feature
if [ $ngx_found = no ]; then
# retry with -ldl, static linking on Linux requires it.
ngx_feature="LuaJIT library in $LUAJIT_LIB and $LUAJIT_INC (specified by the LUAJIT_LIB and LUAJIT_INC env, with -ldl)"
ngx_feature_path="$LUAJIT_INC"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R$LUAJIT_LIB -L$LUAJIT_LIB -lluajit-5.1 -lm -ldl"
else
ngx_feature_libs="-L$LUAJIT_LIB -lluajit-5.1 -lm -ldl"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
cat << END
$0: error: ngx_http_lua_module requires the Lua or LuaJIT library and LUAJIT_LIB is defined as $LUAJIT_LIB and LUAJIT_INC (path for lua.h) $LUAJIT_INC, but we cannot find LuaJIT there.
END
exit 1
fi
case "$NGX_PLATFORM" in
Darwin:*)
case "$NGX_MACHINE" in
amd64 | x86_64 | i386)
echo "adding extra linking options needed by LuaJIT"
ngx_feature_libs="$ngx_feature_libs -pagezero_size 10000 -image_base 100000000"
;;
*)
;;
esac
;;
*)
;;
esac
else
if [ -n "$LUA_INC" -o -n "$LUA_LIB" ]; then
# explicitly set Lua lib path
ngx_feature="Lua library in $LUA_LIB and $LUA_INC (specified by the LUA_LIB and LUA_INC env)"
ngx_feature_path="$LUA_INC"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R$LUA_LIB -L$LUA_LIB -llua -lm"
else
ngx_feature_libs="-L$LUA_LIB -llua -lm"
fi
. auto/feature
if [ $ngx_found = no ]; then
cat << END
$0: error: ngx_http_lua_module requires the Lua or LuaJIT library and LUA_LIB is defined as $LUA_LIB and LUA_INC (path for lua.h) is $LUA_INC, but we cannot find standard Lua there.
END
exit 1
fi
else
# auto-discovery
ngx_feature="Lua library"
ngx_feature_libs="-llua -lm"
. auto/feature
if [ $ngx_found = no ]; then
# OpenBSD-5.2
ngx_feature="Lua library in /usr/local/"
ngx_feature_path="/usr/local/include/lua-5.1"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/usr/local/lib -L/usr/local/lib -llua -lm"
else
ngx_feature_libs="-L/usr/local/lib -llua5.1 -lm"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
# OpenBSD < 5.2
ngx_feature="Lua library in /usr/local/"
ngx_feature_path="/usr/local/include"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/usr/local/lib -L/usr/local/lib -llua -lm"
else
ngx_feature_libs="-L/usr/local/lib -llua -lm"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
# NetBSD
ngx_feature="Lua library in /usr/pkg/"
ngx_feature_path="/usr/pkg/include/"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/usr/pkg/lib -L/usr/pkg/lib -lm -llua"
else
ngx_feature_libs="-L/usr/pkg/lib -lm -llua"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
# MacPorts
ngx_feature="Lua library in /opt/local/"
ngx_feature_path="/opt/local/include"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/opt/local/lib -L/opt/local/lib -lm -llua"
else
ngx_feature_libs="-L/opt/local/lib -lm -llua"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
# FreeBSD
ngx_feature="Lua library in /usr/local/*/lua51/"
ngx_feature_path="/usr/local/include/lua51"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/usr/local/lib/lua51 -L/usr/local/lib/lua51 -llua -lm"
else
ngx_feature_libs="-L/usr/local/lib/lua51 -llua -lm"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
# Debian
ngx_feature="Lua library in /usr/"
ngx_feature_path="/usr/include/lua5.1"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/usr/lib -L/usr/lib -lm -llua5.1"
else
ngx_feature_libs="-L/usr/lib -lm -llua5.1"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
# FreeBSD with luajit-2.0 from ports collection
ngx_feature="LuaJIT library in /usr/local/"
ngx_feature_path="/usr/local/include/luajit-2.0"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/usr/local/lib -L/usr/local/lib -lluajit-5.1 -lm"
else
ngx_feature_libs="-L/usr/local/lib -lluajit-5.1 -lm"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
# Gentoo with LuaJIT-2.0
ngx_feature="LuaJIT library in /usr/"
ngx_feature_path="/usr/include/luajit-2.0"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/usr/lib -L/usr/lib -lm -lluajit-5.1"
else
ngx_feature_libs="-L/usr/lib -lm -lluajit-5.1"
fi
. auto/feature
fi
if [ $ngx_found = no ]; then
# Gentoo with LuaJIT-2.0, retry with -ldl
ngx_feature="LuaJIT library in /usr/"
ngx_feature_path="/usr/include/luajit-2.0"
if [ $NGX_RPATH = YES ]; then
ngx_feature_libs="-R/usr/lib -L/usr/lib -lm -lluajit-5.1 -ldl"
else
ngx_feature_libs="-L/usr/lib -lm -lluajit-5.1 -ldl"
fi
. auto/feature
fi
fi
fi
if [ $ngx_found = yes ]; then
CORE_INCS="$CORE_INCS $ngx_feature_path"
CORE_LIBS="$CORE_LIBS $ngx_feature_libs"
else
cat << END
$0: error: ngx_http_lua_module requires the Lua library.
END
exit 1
fi
ngx_addon_name=ngx_http_lua_module
HTTP_AUX_FILTER_MODULES="$HTTP_AUX_FILTER_MODULES ngx_http_lua_module"
NGX_ADDON_SRCS="$NGX_ADDON_SRCS \
$ngx_addon_dir/src/ngx_http_lua_script.c \
$ngx_addon_dir/src/ngx_http_lua_log.c \
$ngx_addon_dir/src/ngx_http_lua_subrequest.c \
$ngx_addon_dir/src/ngx_http_lua_ndk.c \
$ngx_addon_dir/src/ngx_http_lua_control.c \
$ngx_addon_dir/src/ngx_http_lua_time.c \
$ngx_addon_dir/src/ngx_http_lua_misc.c \
$ngx_addon_dir/src/ngx_http_lua_variable.c \
$ngx_addon_dir/src/ngx_http_lua_string.c \
$ngx_addon_dir/src/ngx_http_lua_output.c \
$ngx_addon_dir/src/ngx_http_lua_headers.c \
$ngx_addon_dir/src/ngx_http_lua_req_body.c \
$ngx_addon_dir/src/ngx_http_lua_uri.c \
$ngx_addon_dir/src/ngx_http_lua_args.c \
$ngx_addon_dir/src/ngx_http_lua_ctx.c \
$ngx_addon_dir/src/ngx_http_lua_regex.c \
$ngx_addon_dir/src/ngx_http_lua_module.c \
$ngx_addon_dir/src/ngx_http_lua_headers_out.c \
$ngx_addon_dir/src/ngx_http_lua_headers_in.c \
$ngx_addon_dir/src/ngx_http_lua_directive.c \
$ngx_addon_dir/src/ngx_http_lua_consts.c \
$ngx_addon_dir/src/ngx_http_lua_exception.c \
$ngx_addon_dir/src/ngx_http_lua_util.c \
$ngx_addon_dir/src/ngx_http_lua_cache.c \
$ngx_addon_dir/src/ngx_http_lua_contentby.c \
$ngx_addon_dir/src/ngx_http_lua_rewriteby.c \
$ngx_addon_dir/src/ngx_http_lua_accessby.c \
$ngx_addon_dir/src/ngx_http_lua_setby.c \
$ngx_addon_dir/src/ngx_http_lua_capturefilter.c \
$ngx_addon_dir/src/ngx_http_lua_clfactory.c \
$ngx_addon_dir/src/ngx_http_lua_pcrefix.c \
$ngx_addon_dir/src/ngx_http_lua_headerfilterby.c \
$ngx_addon_dir/src/ngx_http_lua_shdict.c \
$ngx_addon_dir/src/ngx_http_lua_socket_tcp.c \
$ngx_addon_dir/src/ngx_http_lua_api.c \
$ngx_addon_dir/src/ngx_http_lua_logby.c \
$ngx_addon_dir/src/ngx_http_lua_sleep.c \
$ngx_addon_dir/src/ngx_http_lua_coroutine.c \
$ngx_addon_dir/src/ngx_http_lua_bodyfilterby.c \
$ngx_addon_dir/src/ngx_http_lua_initby.c \
$ngx_addon_dir/src/ngx_http_lua_initworkerby.c \
$ngx_addon_dir/src/ngx_http_lua_socket_udp.c \
$ngx_addon_dir/src/ngx_http_lua_req_method.c \
$ngx_addon_dir/src/ngx_http_lua_phase.c \
$ngx_addon_dir/src/ngx_http_lua_uthread.c \
$ngx_addon_dir/src/ngx_http_lua_timer.c \
$ngx_addon_dir/src/ngx_http_lua_config.c \
$ngx_addon_dir/src/ngx_http_lua_worker.c \
"
NGX_ADDON_DEPS="$NGX_ADDON_DEPS \
$ngx_addon_dir/src/ddebug.h \
$ngx_addon_dir/src/ngx_http_lua_script.h \
$ngx_addon_dir/src/ngx_http_lua_log.h \
$ngx_addon_dir/src/ngx_http_lua_subrequest.h \
$ngx_addon_dir/src/ngx_http_lua_ndk.h \
$ngx_addon_dir/src/ngx_http_lua_control.h \
$ngx_addon_dir/src/ngx_http_lua_time.h \
$ngx_addon_dir/src/ngx_http_lua_string.h \
$ngx_addon_dir/src/ngx_http_lua_misc.h \
$ngx_addon_dir/src/ngx_http_lua_variable.h \
$ngx_addon_dir/src/ngx_http_lua_output.h \
$ngx_addon_dir/src/ngx_http_lua_headers.h \
$ngx_addon_dir/src/ngx_http_lua_uri.h \
$ngx_addon_dir/src/ngx_http_lua_req_body.h \
$ngx_addon_dir/src/ngx_http_lua_args.h \
$ngx_addon_dir/src/ngx_http_lua_ctx.h \
$ngx_addon_dir/src/ngx_http_lua_regex.h \
$ngx_addon_dir/src/ngx_http_lua_common.h \
$ngx_addon_dir/src/ngx_http_lua_directive.h \
$ngx_addon_dir/src/ngx_http_lua_headers_out.h \
$ngx_addon_dir/src/ngx_http_lua_headers_in.h \
$ngx_addon_dir/src/ngx_http_lua_consts.h \
$ngx_addon_dir/src/ngx_http_lua_exception.h \
$ngx_addon_dir/src/ngx_http_lua_util.h \
$ngx_addon_dir/src/ngx_http_lua_cache.h \
$ngx_addon_dir/src/ngx_http_lua_contentby.h \
$ngx_addon_dir/src/ngx_http_lua_rewriteby.h \
$ngx_addon_dir/src/ngx_http_lua_accessby.h \
$ngx_addon_dir/src/ngx_http_lua_setby.h \
$ngx_addon_dir/src/ngx_http_lua_capturefilter.h \
$ngx_addon_dir/src/ngx_http_lua_clfactory.h \
$ngx_addon_dir/src/ngx_http_lua_pcrefix.h \
$ngx_addon_dir/src/ngx_http_lua_headerfilterby.h \
$ngx_addon_dir/src/ngx_http_lua_shdict.h \
$ngx_addon_dir/src/ngx_http_lua_socket_tcp.h \
$ngx_addon_dir/src/api/ngx_http_lua_api.h \
$ngx_addon_dir/src/ngx_http_lua_logby.h \
$ngx_addon_dir/src/ngx_http_lua_sleep.h \
$ngx_addon_dir/src/ngx_http_lua_coroutine.h \
$ngx_addon_dir/src/ngx_http_lua_bodyfilterby.h \
$ngx_addon_dir/src/ngx_http_lua_initby.h \
$ngx_addon_dir/src/ngx_http_lua_initworkerby.h \
$ngx_addon_dir/src/ngx_http_lua_socket_udp.h \
$ngx_addon_dir/src/ngx_http_lua_req_method.h \
$ngx_addon_dir/src/ngx_http_lua_phase.h \
$ngx_addon_dir/src/ngx_http_lua_probe.h \
$ngx_addon_dir/src/ngx_http_lua_uthread.h \
$ngx_addon_dir/src/ngx_http_lua_timer.h \
$ngx_addon_dir/src/ngx_http_lua_config.h \
$ngx_addon_dir/src/ngx_http_lua_worker.h \
"
CFLAGS="$CFLAGS -DNDK_SET_VAR"
ngx_feature="export symbols by default (-E)"
ngx_feature_libs="-Wl,-E"
ngx_feature_name=
ngx_feature_run=no
ngx_feature_incs="#include <stdio.h>"
ngx_feature_path=
ngx_feature_test='printf("hello");'
. auto/feature
if [ $ngx_found = yes ]; then
CORE_LIBS="-Wl,-E $CORE_LIBS"
fi
# for Cygwin
ngx_feature="export symbols by default (--export-all-symbols)"
ngx_feature_libs="-Wl,--export-all-symbols"
ngx_feature_name=
ngx_feature_run=no
ngx_feature_incs="#include <stdio.h>"
ngx_feature_path=
ngx_feature_test='printf("hello");'
. auto/feature
if [ $ngx_found = yes ]; then
CORE_LIBS="-Wl,--export-all-symbols $CORE_LIBS"
fi
NGX_DTRACE_PROVIDERS="$NGX_DTRACE_PROVIDERS $ngx_addon_dir/dtrace/ngx_lua_provider.d"
NGX_TAPSET_SRCS="$NGX_TAPSET_SRCS $ngx_addon_dir/tapset/ngx_lua.stp"
USE_MD5=YES
USE_SHA1=YES
CORE_INCS="$CORE_INCS $ngx_addon_dir/src/api"
ngx_feature="SO_PASSCRED"
ngx_feature_libs=
ngx_feature_name="NGX_HTTP_LUA_HAVE_SO_PASSCRED"
ngx_feature_run=no
ngx_feature_incs="#include <sys/types.h>
#include <sys/socket.h>"
ngx_feature_path=
ngx_feature_test='setsockopt(1, SOL_SOCKET, SO_PASSCRED, NULL, 0);'
. auto/feature
#CFLAGS=$"$CFLAGS -DLUA_DEFAULT_PATH='\"/usr/local/openresty/lualib/?.lua\"'"
#CFLAGS=$"$CFLAGS -DLUA_DEFAULT_CPATH='\"/usr/local/openresty/lualib/?.so\"'"

View file

@ -1,61 +0,0 @@
provider nginx_lua {
probe http__lua__info(char *s);
/* lua_State *L */
probe http__lua__register__preload__package(void *L, u_char *pkg);
probe http__lua__req__socket__consume__preread(ngx_http_request_t *r,
u_char *data, size_t len);
/* lua_State *parent, lua_State *child */
probe http__lua__user__coroutine__create(ngx_http_request_t *r,
void *parent, void *child);
/* lua_State *parent, lua_State *child */
probe http__lua__user__coroutine__resume(ngx_http_request_t *r,
void *parent, void *child);
/* lua_State *parent, lua_State *child */
probe http__lua__user__coroutine__yield(ngx_http_request_t *r,
void *parent, void *child);
/* lua_State *L */
probe http__lua__thread__yield(ngx_http_request_t *r, void *L);
/* ngx_http_lua_socket_tcp_upstream_t *u */
probe http__lua__socket__tcp__send__start(ngx_http_request_t *r,
void *u, u_char *data, size_t len);
/* ngx_http_lua_socket_tcp_upstream_t *u */
probe http__lua__socket__tcp__receive__done(ngx_http_request_t *r,
void *u, u_char *data, size_t len);
/* ngx_http_lua_socket_tcp_upstream_t *u */
probe http__lua__socket__tcp__setkeepalive__buf__unread(
ngx_http_request_t *r, void *u, u_char *data, size_t len);
/* lua_State *creator, lua_State *newthread */
probe http__lua__user__thread__spawn(ngx_http_request_t *r,
void *creator, void *newthread);
/* lua_State *thread, ngx_http_lua_ctx_t *ctx */
probe http__lua__thread__delete(ngx_http_request_t *r, void *thread, void *ctx);
/* lua_State *thread */
probe http__lua__run__posted__thread(ngx_http_request_t *r, void *thread,
int status);
probe http__lua__coroutine__done(ngx_http_request_t *r, void *co,
int success);
/* lua_State *parent, lua_State *child */
probe http__lua__user__thread__wait(void *parent, void *child);
};
#pragma D attributes Evolving/Evolving/Common provider nginx_lua provider
#pragma D attributes Private/Private/Unknown provider nginx_lua module
#pragma D attributes Private/Private/Unknown provider nginx_lua function
#pragma D attributes Private/Private/Common provider nginx_lua name
#pragma D attributes Evolving/Evolving/Common provider nginx_lua args

View file

@ -1,140 +0,0 @@
# vi:ft=
use 5.10.1;
use Test::Base;
use RecvUntil;
plan tests => 1 * blocks();
run {
my $block = shift;
my $name = $block->name;
my $pat = $block->pat // die "$name: No --- pat found";
my $txt = $block->txt // die "$name: No --- txt found";
my $expected = $block->out // die "$name: No --- out found";
my $it = RecvUntil::recv_until($pat);
is $it->($txt), $expected, "$name: output ok";
};
__DATA__
=== TEST 1:
--- pat: abcabd
--- txt: abcabcabd
--- out: abc
=== TEST 2:
--- pat: aa
--- txt: abcabcaad
--- out: abcabc
=== TEST 3:
--- pat: ab
--- txt: bbcabcaad
--- out: bbc
=== TEST 4:
--- pat: aaa
--- txt: abaabcaaaef
--- out: abaabc
=== TEST 5:
--- pat: aaaaad
--- txt: baaaaaaaaeaaaaaaadf
--- out: baaaaaaaaeaa
=== TEST 6:
--- pat: abacadae
--- txt: a
--- out:
=== TEST 7:
--- pat: abacadae
--- txt: ababacadae
--- out: ab
=== TEST 8:
--- pat: abacadae
--- txt: abacabacadae
--- out: abac
=== TEST 9:
--- pat: abacadae
--- txt: abaabacadae
--- out: aba
=== TEST 10:
--- pat: abacadae
--- txt: abacadabacadae
--- out: abacad
=== TEST 11:
--- pat: abcabdabcabe
--- txt: abcabdabcabdabcabe
--- out: abcabd
=== TEST 12:
--- pat: abcabdabcabe
--- txt: abcabdabcabcabdabcabe
--- out: abcabdabc
=== TEST 13:
--- pat: abcabdabcabe
--- txt: abcabcabdabcabe
--- out: abc
=== TEST 14:
--- pat: abcabdabcabe
--- txt: ababcabdabcabe
--- out: ab
=== TEST 15:
--- pat: abcdef
--- txt: abcabcdef
--- out: abc
=== TEST 16:
--- pat: -- abc
--- txt: ---- abc
--- out: --
=== TEST 17:
--- pat: yz--ababyz
--- txt:
--- out: --
--- SKIP

View file

@ -1,20 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_ARGS_H_INCLUDED_
#define _NGX_HTTP_LUA_ARGS_H_INCLUDED_
#include "ngx_http_lua_common.h"
void ngx_http_lua_inject_req_args_api(lua_State *L);
int ngx_http_lua_parse_args(lua_State *L, u_char *buf, u_char *last, int max);
#endif /* _NGX_HTTP_LUA_ARGS_H_INCLUDED_ */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,296 +0,0 @@
/*
* Copyright (C) Xiaozhe Wang (chaoslawful)
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include <nginx.h>
#include <ngx_md5.h>
#include "ngx_http_lua_common.h"
#include "ngx_http_lua_cache.h"
#include "ngx_http_lua_clfactory.h"
#include "ngx_http_lua_util.h"
/**
* Find code chunk associated with the given key in code cache,
* and push it to the top of Lua stack if found.
*
* Stack layout before call:
* | ... | <- top
*
* Stack layout after call:
* | code chunk | <- top
* | ... |
*
* */
static ngx_int_t
ngx_http_lua_cache_load_code(ngx_http_request_t *r, lua_State *L,
const char *key)
{
int rc;
u_char *err;
/* get code cache table */
lua_pushlightuserdata(L, &ngx_http_lua_code_cache_key);
lua_rawget(L, LUA_REGISTRYINDEX); /* sp++ */
dd("Code cache table to load: %p", lua_topointer(L, -1));
if (!lua_istable(L, -1)) {
dd("Error: code cache table to load did not exist!!");
return NGX_ERROR;
}
lua_getfield(L, -1, key); /* sp++ */
if (lua_isfunction(L, -1)) {
/* call closure factory to gen new closure */
rc = lua_pcall(L, 0, 1, 0);
if (rc == 0) {
/* remove cache table from stack, leave code chunk at
* top of stack */
lua_remove(L, -2); /* sp-- */
return NGX_OK;
}
if (lua_isstring(L, -1)) {
err = (u_char *) lua_tostring(L, -1);
} else {
err = (u_char *) "unknown error";
}
ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
"lua: failed to run factory at key \"%s\": %s",
key, err);
lua_pop(L, 2);
return NGX_ERROR;
}
dd("Value associated with given key in code cache table is not code "
"chunk: stack top=%d, top value type=%s\n",
lua_gettop(L), lua_typename(L, -1));
/* remove cache table and value from stack */
lua_pop(L, 2); /* sp-=2 */
return NGX_DECLINED;
}
/**
* Store the closure factory at the top of Lua stack to code cache, and
* associate it with the given key. Then generate new closure.
*
* Stack layout before call:
* | code factory | <- top
* | ... |
*
* Stack layout after call:
* | code chunk | <- top
* | ... |
*
* */
static ngx_int_t
ngx_http_lua_cache_store_code(lua_State *L, const char *key)
{
int rc;
/* get code cache table */
lua_pushlightuserdata(L, &ngx_http_lua_code_cache_key);
lua_rawget(L, LUA_REGISTRYINDEX);
dd("Code cache table to store: %p", lua_topointer(L, -1));
if (!lua_istable(L, -1)) {
dd("Error: code cache table to load did not exist!!");
return NGX_ERROR;
}
lua_pushvalue(L, -2); /* closure cache closure */
lua_setfield(L, -2, key); /* closure cache */
/* remove cache table, leave closure factory at top of stack */
lua_pop(L, 1); /* closure */
/* call closure factory to generate new closure */
rc = lua_pcall(L, 0, 1, 0);
if (rc != 0) {
dd("Error: failed to call closure factory!!");
return NGX_ERROR;
}
return NGX_OK;
}
ngx_int_t
ngx_http_lua_cache_loadbuffer(ngx_http_request_t *r, lua_State *L,
const u_char *src, size_t src_len, const u_char *cache_key,
const char *name)
{
int n;
ngx_int_t rc;
const char *err = NULL;
n = lua_gettop(L);
dd("XXX cache key: [%s]", cache_key);
rc = ngx_http_lua_cache_load_code(r, L, (char *) cache_key);
if (rc == NGX_OK) {
/* code chunk loaded from cache, sp++ */
dd("Code cache hit! cache key='%s', stack top=%d, script='%.*s'",
cache_key, lua_gettop(L), (int) src_len, src);
return NGX_OK;
}
if (rc == NGX_ERROR) {
return NGX_ERROR;
}
/* rc == NGX_DECLINED */
dd("Code cache missed! cache key='%s', stack top=%d, script='%.*s'",
cache_key, lua_gettop(L), (int) src_len, src);
/* load closure factory of inline script to the top of lua stack, sp++ */
rc = ngx_http_lua_clfactory_loadbuffer(L, (char *) src, src_len, name);
if (rc != 0) {
/* Oops! error occured when loading Lua script */
if (rc == LUA_ERRMEM) {
err = "memory allocation error";
} else {
if (lua_isstring(L, -1)) {
err = lua_tostring(L, -1);
} else {
err = "unknown error";
}
}
goto error;
}
/* store closure factory and gen new closure at the top of lua stack to
* code cache */
rc = ngx_http_lua_cache_store_code(L, (char *) cache_key);
if (rc != NGX_OK) {
err = "fail to generate new closure from the closure factory";
goto error;
}
return NGX_OK;
error:
ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
"failed to load inlined Lua code: %s", err);
lua_settop(L, n);
return NGX_ERROR;
}
ngx_int_t
ngx_http_lua_cache_loadfile(ngx_http_request_t *r, lua_State *L,
const u_char *script, const u_char *cache_key)
{
int n;
ngx_int_t rc, errcode = NGX_ERROR;
u_char *p;
u_char buf[NGX_HTTP_LUA_FILE_KEY_LEN + 1];
const char *err = NULL;
n = lua_gettop(L);
/* calculate digest of script file path */
if (cache_key == NULL) {
dd("CACHE file key not pre-calculated...calculating");
p = ngx_copy(buf, NGX_HTTP_LUA_FILE_TAG, NGX_HTTP_LUA_FILE_TAG_LEN);
p = ngx_http_lua_digest_hex(p, script, ngx_strlen(script));
*p = '\0';
cache_key = buf;
} else {
dd("CACHE file key already pre-calculated");
}
dd("XXX cache key for file: [%s]", cache_key);
rc = ngx_http_lua_cache_load_code(r, L, (char *) cache_key);
if (rc == NGX_OK) {
/* code chunk loaded from cache, sp++ */
dd("Code cache hit! cache key='%s', stack top=%d, file path='%s'",
cache_key, lua_gettop(L), script);
return NGX_OK;
}
if (rc == NGX_ERROR) {
return NGX_ERROR;
}
/* rc == NGX_DECLINED */
dd("Code cache missed! cache key='%s', stack top=%d, file path='%s'",
cache_key, lua_gettop(L), script);
/* load closure factory of script file to the top of lua stack, sp++ */
rc = ngx_http_lua_clfactory_loadfile(L, (char *) script);
dd("loadfile returns %d (%d)", (int) rc, LUA_ERRFILE);
if (rc != 0) {
/* Oops! error occured when loading Lua script */
switch (rc) {
case LUA_ERRMEM:
err = "memory allocation error";
break;
case LUA_ERRFILE:
errcode = NGX_HTTP_NOT_FOUND;
/* fall through */
default:
if (lua_isstring(L, -1)) {
err = lua_tostring(L, -1);
} else {
err = "unknown error";
}
}
goto error;
}
/* store closure factory and gen new closure at the top of lua stack
* to code cache */
rc = ngx_http_lua_cache_store_code(L, (char *) cache_key);
if (rc != NGX_OK) {
err = "fail to generate new closure from the closure factory";
goto error;
}
return NGX_OK;
error:
ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
"failed to load external Lua file \"%s\": %s", script, err);
lua_settop(L, n);
return errcode;
}
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,24 +0,0 @@
/*
* Copyright (C) Xiaozhe Wang (chaoslawful)
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_CACHE_H_INCLUDED_
#define _NGX_HTTP_LUA_CACHE_H_INCLUDED_
#include "ngx_http_lua_common.h"
ngx_int_t ngx_http_lua_cache_loadbuffer(ngx_http_request_t *r, lua_State *L,
const u_char *src, size_t src_len, const u_char *cache_key,
const char *name);
ngx_int_t ngx_http_lua_cache_loadfile(ngx_http_request_t *r, lua_State *L,
const u_char *script, const u_char *cache_key);
#endif /* _NGX_HTTP_LUA_CACHE_H_INCLUDED_ */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,22 +0,0 @@
/*
* Copyright (C) Xiaozhe Wang (chaoslawful)
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_CLFACTORY_H_INCLUDED_
#define _NGX_HTTP_LUA_CLFACTORY_H_INCLUDED_
#include "ngx_http_lua_common.h"
ngx_int_t ngx_http_lua_clfactory_loadfile(lua_State *L, const char *filename);
ngx_int_t ngx_http_lua_clfactory_loadbuffer(lua_State *L, const char *buff,
size_t size, const char *name);
#endif /* _NGX_HTTP_LUA_CLFACTORY_H_INCLUDED_ */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,67 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include "ngx_http_lua_config.h"
#include "api/ngx_http_lua_api.h"
static int ngx_http_lua_config_prefix(lua_State *L);
static int ngx_http_lua_config_configure(lua_State *L);
void
ngx_http_lua_inject_config_api(lua_State *L)
{
/* ngx.config */
lua_createtable(L, 0, 5 /* nrec */); /* .config */
#if (NGX_DEBUG)
lua_pushboolean(L, 1);
#else
lua_pushboolean(L, 0);
#endif
lua_setfield(L, -2, "debug");
lua_pushcfunction(L, ngx_http_lua_config_prefix);
lua_setfield(L, -2, "prefix");
lua_pushinteger(L, nginx_version);
lua_setfield(L, -2, "nginx_version");
lua_pushinteger(L, ngx_http_lua_version);
lua_setfield(L, -2, "ngx_lua_version");
lua_pushcfunction(L, ngx_http_lua_config_configure);
lua_setfield(L, -2, "nginx_configure");
lua_setfield(L, -2, "config");
}
static int
ngx_http_lua_config_prefix(lua_State *L)
{
lua_pushlstring(L, (char *) ngx_cycle->prefix.data,
ngx_cycle->prefix.len);
return 1;
}
static int
ngx_http_lua_config_configure(lua_State *L)
{
lua_pushliteral(L, NGX_CONFIGURE);
return 1;
}
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,19 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_CONFIG_H_INCLUDED_
#define _NGX_HTTP_LUA_CONFIG_H_INCLUDED_
#include "ngx_http_lua_common.h"
void ngx_http_lua_inject_config_api(lua_State *L);
#endif /* _NGX_HTTP_LUA_CONFIG_H_INCLUDED_ */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,20 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_CONSTS_H_INCLUDED_
#define _NGX_HTTP_LUA_CONSTS_H_INCLUDED_
#include "ngx_http_lua_common.h"
void ngx_http_lua_inject_http_consts(lua_State *L);
void ngx_http_lua_inject_core_consts(lua_State *L);
#endif /* _NGX_HTTP_LUA_CONSTS_H_INCLUDED_ */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,216 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include "ngx_http_lua_util.h"
#include "ngx_http_lua_ctx.h"
typedef struct {
int ref;
lua_State *vm;
} ngx_http_lua_ngx_ctx_cleanup_data_t;
static ngx_int_t ngx_http_lua_ngx_ctx_add_cleanup(ngx_http_request_t *r,
int ref);
static void ngx_http_lua_ngx_ctx_cleanup(void *data);
int
ngx_http_lua_ngx_get_ctx(lua_State *L)
{
ngx_http_request_t *r;
ngx_http_lua_ctx_t *ctx;
r = ngx_http_lua_get_req(L);
if (r == NULL) {
return luaL_error(L, "no request found");
}
ctx = ngx_http_get_module_ctx(r, ngx_http_lua_module);
if (ctx == NULL) {
return luaL_error(L, "no request ctx found");
}
if (ctx->ctx_ref == LUA_NOREF) {
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"lua create ngx.ctx table for the current request");
lua_pushliteral(L, ngx_http_lua_ctx_tables_key);
lua_rawget(L, LUA_REGISTRYINDEX);
lua_createtable(L, 0 /* narr */, 4 /* nrec */);
lua_pushvalue(L, -1);
ctx->ctx_ref = luaL_ref(L, -3);
if (ngx_http_lua_ngx_ctx_add_cleanup(r, ctx->ctx_ref) != NGX_OK) {
return luaL_error(L, "no memory");
}
return 1;
}
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"lua fetching existing ngx.ctx table for the current "
"request");
lua_pushliteral(L, ngx_http_lua_ctx_tables_key);
lua_rawget(L, LUA_REGISTRYINDEX);
lua_rawgeti(L, -1, ctx->ctx_ref);
return 1;
}
int
ngx_http_lua_ngx_set_ctx(lua_State *L)
{
ngx_http_request_t *r;
ngx_http_lua_ctx_t *ctx;
r = ngx_http_lua_get_req(L);
if (r == NULL) {
return luaL_error(L, "no request found");
}
ctx = ngx_http_get_module_ctx(r, ngx_http_lua_module);
if (ctx == NULL) {
return luaL_error(L, "no request ctx found");
}
return ngx_http_lua_ngx_set_ctx_helper(L, r, ctx, 3);
}
int
ngx_http_lua_ngx_set_ctx_helper(lua_State *L, ngx_http_request_t *r,
ngx_http_lua_ctx_t *ctx, int index)
{
if (index < 0) {
index = lua_gettop(L) + index + 1;
}
if (ctx->ctx_ref == LUA_NOREF) {
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"lua create ngx.ctx table for the current request");
lua_pushliteral(L, ngx_http_lua_ctx_tables_key);
lua_rawget(L, LUA_REGISTRYINDEX);
lua_pushvalue(L, index);
ctx->ctx_ref = luaL_ref(L, -2);
lua_pop(L, 1);
if (ngx_http_lua_ngx_ctx_add_cleanup(r, ctx->ctx_ref) != NGX_OK) {
return luaL_error(L, "no memory");
}
return 0;
}
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"lua fetching existing ngx.ctx table for the current "
"request");
lua_pushliteral(L, ngx_http_lua_ctx_tables_key);
lua_rawget(L, LUA_REGISTRYINDEX);
luaL_unref(L, -1, ctx->ctx_ref);
lua_pushvalue(L, index);
ctx->ctx_ref = luaL_ref(L, -2);
lua_pop(L, 1);
return 0;
}
#ifndef NGX_LUA_NO_FFI_API
int
ngx_http_lua_ffi_get_ctx_ref(ngx_http_request_t *r)
{
ngx_http_lua_ctx_t *ctx;
ctx = ngx_http_get_module_ctx(r, ngx_http_lua_module);
if (ctx == NULL) {
return NGX_HTTP_LUA_FFI_NO_REQ_CTX;
}
return ctx->ctx_ref;
}
int
ngx_http_lua_ffi_set_ctx_ref(ngx_http_request_t *r, int ref)
{
ngx_http_lua_ctx_t *ctx;
ctx = ngx_http_get_module_ctx(r, ngx_http_lua_module);
if (ctx == NULL) {
return NGX_HTTP_LUA_FFI_NO_REQ_CTX;
}
ctx->ctx_ref = ref;
if (ngx_http_lua_ngx_ctx_add_cleanup(r, ref) != NGX_OK) {
return NGX_ERROR;
}
return NGX_OK;
}
#endif /* NGX_LUA_NO_FFI_API */
static ngx_int_t
ngx_http_lua_ngx_ctx_add_cleanup(ngx_http_request_t *r, int ref)
{
lua_State *L;
ngx_pool_cleanup_t *cln;
ngx_http_lua_ctx_t *ctx;
ngx_http_lua_ngx_ctx_cleanup_data_t *data;
ctx = ngx_http_get_module_ctx(r, ngx_http_lua_module);
L = ngx_http_lua_get_lua_vm(r, ctx);
cln = ngx_pool_cleanup_add(r->pool,
sizeof(ngx_http_lua_ngx_ctx_cleanup_data_t));
if (cln == NULL) {
return NGX_ERROR;
}
cln->handler = ngx_http_lua_ngx_ctx_cleanup;
data = cln->data;
data->vm = L;
data->ref = ref;
return NGX_OK;
}
static void
ngx_http_lua_ngx_ctx_cleanup(void *data)
{
lua_State *L;
ngx_http_lua_ngx_ctx_cleanup_data_t *clndata = data;
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, ngx_cycle->log, 0,
"lua release ngx.ctx at ref %d", clndata->ref);
L = clndata->vm;
lua_pushliteral(L, ngx_http_lua_ctx_tables_key);
lua_rawget(L, LUA_REGISTRYINDEX);
luaL_unref(L, -1, clndata->ref);
lua_pop(L, 1);
}
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,42 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include "ngx_http_lua_initby.h"
#include "ngx_http_lua_util.h"
ngx_int_t
ngx_http_lua_init_by_inline(ngx_log_t *log, ngx_http_lua_main_conf_t *lmcf,
lua_State *L)
{
int status;
status = luaL_loadbuffer(L, (char *) lmcf->init_src.data,
lmcf->init_src.len, "=init_by_lua")
|| ngx_http_lua_do_call(log, L);
return ngx_http_lua_report(log, L, status, "init_by_lua");
}
ngx_int_t
ngx_http_lua_init_by_file(ngx_log_t *log, ngx_http_lua_main_conf_t *lmcf,
lua_State *L)
{
int status;
status = luaL_loadfile(L, (char *) lmcf->init_src.data)
|| ngx_http_lua_do_call(log, L);
return ngx_http_lua_report(log, L, status, "init_by_lua_file");
}
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,315 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include "ngx_http_lua_initworkerby.h"
#include "ngx_http_lua_util.h"
static u_char * ngx_http_lua_log_init_worker_error(ngx_log_t *log,
u_char *buf, size_t len);
ngx_int_t
ngx_http_lua_init_worker(ngx_cycle_t *cycle)
{
char *rv;
void *cur, *prev;
ngx_uint_t i;
ngx_conf_t conf;
ngx_cycle_t *fake_cycle;
ngx_open_file_t *file, *ofile;
ngx_list_part_t *part;
ngx_connection_t *c = NULL;
ngx_http_module_t *module;
ngx_http_request_t *r = NULL;
ngx_http_lua_ctx_t *ctx;
ngx_http_conf_ctx_t *conf_ctx, http_ctx;
ngx_http_lua_loc_conf_t *llcf, *top_llcf;
ngx_http_lua_main_conf_t *lmcf;
ngx_http_core_loc_conf_t *clcf, *top_clcf;
lmcf = ngx_http_cycle_get_module_main_conf(cycle, ngx_http_lua_module);
if (lmcf == NULL
|| lmcf->init_worker_handler == NULL
|| lmcf->lua == NULL)
{
return NGX_OK;
}
conf_ctx = ((ngx_http_conf_ctx_t *) cycle->conf_ctx[ngx_http_module.index]);
http_ctx.main_conf = conf_ctx->main_conf;
top_clcf = conf_ctx->loc_conf[ngx_http_core_module.ctx_index];
top_llcf = conf_ctx->loc_conf[ngx_http_lua_module.ctx_index];
ngx_memzero(&conf, sizeof(ngx_conf_t));
conf.temp_pool = ngx_create_pool(NGX_CYCLE_POOL_SIZE, cycle->log);
if (conf.temp_pool == NULL) {
return NGX_ERROR;
}
conf.temp_pool->log = cycle->log;
/* we fake a temporary ngx_cycle_t here because some
* modules' merge conf handler may produce side effects in
* cf->cycle (like ngx_proxy vs cf->cycle->paths).
* also, we cannot allocate our temp cycle on the stack
* because some modules like ngx_http_core_module reference
* addresses within cf->cycle (i.e., via "&cf->cycle->new_log")
*/
fake_cycle = ngx_palloc(cycle->pool, sizeof(ngx_cycle_t));
if (fake_cycle == NULL) {
goto failed;
}
ngx_memcpy(fake_cycle, cycle, sizeof(ngx_cycle_t));
#if defined(nginx_version) && nginx_version >= 9007
ngx_queue_init(&fake_cycle->reusable_connections_queue);
#endif
if (ngx_array_init(&fake_cycle->listening, cycle->pool,
cycle->listening.nelts || 1,
sizeof(ngx_listening_t))
!= NGX_OK)
{
goto failed;
}
#if defined(nginx_version) && nginx_version >= 1003007
if (ngx_array_init(&fake_cycle->paths, cycle->pool, cycle->paths.nelts || 1,
sizeof(ngx_path_t *))
!= NGX_OK)
{
goto failed;
}
#endif
part = &cycle->open_files.part;
ofile = part->elts;
if (ngx_list_init(&fake_cycle->open_files, cycle->pool, part->nelts || 1,
sizeof(ngx_open_file_t))
!= NGX_OK)
{
goto failed;
}
for (i = 0; /* void */ ; i++) {
if (i >= part->nelts) {
if (part->next == NULL) {
break;
}
part = part->next;
ofile = part->elts;
i = 0;
}
file = ngx_list_push(&fake_cycle->open_files);
if (file == NULL) {
goto failed;
}
ngx_memcpy(file, ofile, sizeof(ngx_open_file_t));
}
if (ngx_list_init(&fake_cycle->shared_memory, cycle->pool, 1,
sizeof(ngx_shm_zone_t))
!= NGX_OK)
{
goto failed;
}
conf.ctx = &http_ctx;
conf.cycle = fake_cycle;
conf.pool = fake_cycle->pool;
conf.log = cycle->log;
http_ctx.loc_conf = ngx_pcalloc(conf.pool,
sizeof(void *) * ngx_http_max_module);
if (http_ctx.loc_conf == NULL) {
return NGX_ERROR;
}
http_ctx.srv_conf = ngx_pcalloc(conf.pool,
sizeof(void *) * ngx_http_max_module);
if (http_ctx.srv_conf == NULL) {
return NGX_ERROR;
}
for (i = 0; ngx_modules[i]; i++) {
if (ngx_modules[i]->type != NGX_HTTP_MODULE) {
continue;
}
module = ngx_modules[i]->ctx;
if (module->create_srv_conf) {
cur = module->create_srv_conf(&conf);
if (cur == NULL) {
return NGX_ERROR;
}
if (module->merge_srv_conf) {
prev = module->create_srv_conf(&conf);
if (prev == NULL) {
return NGX_ERROR;
}
rv = module->merge_srv_conf(&conf, prev, cur);
if (rv != NGX_CONF_OK) {
goto failed;
}
}
http_ctx.srv_conf[ngx_modules[i]->ctx_index] = cur;
}
if (module->create_loc_conf) {
cur = module->create_loc_conf(&conf);
if (cur == NULL) {
return NGX_ERROR;
}
if (module->merge_loc_conf) {
prev = module->create_loc_conf(&conf);
if (prev == NULL) {
return NGX_ERROR;
}
rv = module->merge_loc_conf(&conf, prev, cur);
if (rv != NGX_CONF_OK) {
goto failed;
}
}
http_ctx.loc_conf[ngx_modules[i]->ctx_index] = cur;
}
}
ngx_destroy_pool(conf.temp_pool);
conf.temp_pool = NULL;
c = ngx_http_lua_create_fake_connection();
if (c == NULL) {
goto failed;
}
c->log->handler = ngx_http_lua_log_init_worker_error;
r = ngx_http_lua_create_fake_request(c);
if (r == NULL) {
goto failed;
}
r->main_conf = http_ctx.main_conf;
r->srv_conf = http_ctx.srv_conf;
r->loc_conf = http_ctx.loc_conf;
clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
c->log->file = clcf->error_log->file;
if (!(c->log->log_level & NGX_LOG_DEBUG_CONNECTION)) {
c->log->log_level = clcf->error_log->log_level;
}
if (top_clcf->resolver) {
clcf->resolver = top_clcf->resolver;
}
ctx = ngx_http_lua_create_ctx(r);
if (ctx == NULL) {
goto failed;
}
ctx->context = NGX_HTTP_LUA_CONTEXT_INIT_WORKER;
ctx->cur_co_ctx = NULL;
r->read_event_handler = ngx_http_block_reading;
llcf = ngx_http_get_module_loc_conf(r, ngx_http_lua_module);
if (top_llcf->log_socket_errors != NGX_CONF_UNSET) {
llcf->log_socket_errors = top_llcf->log_socket_errors;
}
ngx_http_lua_set_req(lmcf->lua, r);
(void) lmcf->init_worker_handler(cycle->log, lmcf, lmcf->lua);
ngx_destroy_pool(r->pool);
ngx_destroy_pool(c->pool);
return NGX_OK;
failed:
if (conf.temp_pool) {
ngx_destroy_pool(conf.temp_pool);
}
if (r && r->pool) {
ngx_destroy_pool(r->pool);
}
if (c) {
ngx_http_lua_close_fake_connection(c);
}
return NGX_ERROR;
}
ngx_int_t
ngx_http_lua_init_worker_by_inline(ngx_log_t *log,
ngx_http_lua_main_conf_t *lmcf, lua_State *L)
{
int status;
status = luaL_loadbuffer(L, (char *) lmcf->init_worker_src.data,
lmcf->init_worker_src.len, "=init_worker_by_lua")
|| ngx_http_lua_do_call(log, L);
return ngx_http_lua_report(log, L, status, "init_worker_by_lua");
}
ngx_int_t
ngx_http_lua_init_worker_by_file(ngx_log_t *log, ngx_http_lua_main_conf_t *lmcf,
lua_State *L)
{
int status;
status = luaL_loadfile(L, (char *) lmcf->init_worker_src.data)
|| ngx_http_lua_do_call(log, L);
return ngx_http_lua_report(log, L, status, "init_worker_by_lua_file");
}
static u_char *
ngx_http_lua_log_init_worker_error(ngx_log_t *log, u_char *buf, size_t len)
{
u_char *p;
if (log->action) {
p = ngx_snprintf(buf, len, " while %s", log->action);
len -= p - buf;
buf = p;
}
return ngx_snprintf(buf, len, ", context: init_worker_by_lua*");
}

View file

@ -1,25 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_INITWORKERBY_H_INCLUDED_
#define _NGX_HTTP_LUA_INITWORKERBY_H_INCLUDED_
#include "ngx_http_lua_common.h"
ngx_int_t ngx_http_lua_init_worker_by_inline(ngx_log_t *log,
ngx_http_lua_main_conf_t *lmcf, lua_State *L);
ngx_int_t ngx_http_lua_init_worker_by_file(ngx_log_t *log,
ngx_http_lua_main_conf_t *lmcf, lua_State *L);
ngx_int_t ngx_http_lua_init_worker(ngx_cycle_t *cycle);
#endif /* _NGX_HTTP_LUA_INITWORKERBY_H_INCLUDED_ */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,252 +0,0 @@
/*
* Copyright (C) Xiaozhe Wang (chaoslawful)
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include "ngx_http_lua_misc.h"
#include "ngx_http_lua_ctx.h"
#include "ngx_http_lua_util.h"
static int ngx_http_lua_ngx_get(lua_State *L);
static int ngx_http_lua_ngx_set(lua_State *L);
void
ngx_http_lua_inject_misc_api(lua_State *L)
{
/* ngx. getter and setter */
lua_createtable(L, 0, 2); /* metatable for .ngx */
lua_pushcfunction(L, ngx_http_lua_ngx_get);
lua_setfield(L, -2, "__index");
lua_pushcfunction(L, ngx_http_lua_ngx_set);
lua_setfield(L, -2, "__newindex");
lua_setmetatable(L, -2);
}
static int
ngx_http_lua_ngx_get(lua_State *L)
{
int status;
ngx_http_request_t *r;
u_char *p;
size_t len;
r = ngx_http_lua_get_req(L);
if (r == NULL) {
return luaL_error(L, "no request object found");
}
p = (u_char *) luaL_checklstring(L, -1, &len);
dd("ngx get %s", p);
if (len == sizeof("status") - 1
&& ngx_strncmp(p, "status", sizeof("status") - 1) == 0)
{
ngx_http_lua_check_fake_request(L, r);
if (r->err_status) {
status = r->err_status;
} else if (r->headers_out.status) {
status = r->headers_out.status;
} else if (r->http_version == NGX_HTTP_VERSION_9) {
status = 9;
} else {
status = 0;
}
lua_pushinteger(L, status);
return 1;
}
if (len == sizeof("ctx") - 1
&& ngx_strncmp(p, "ctx", sizeof("ctx") - 1) == 0)
{
return ngx_http_lua_ngx_get_ctx(L);
}
if (len == sizeof("is_subrequest") - 1
&& ngx_strncmp(p, "is_subrequest", sizeof("is_subrequest") - 1) == 0)
{
lua_pushboolean(L, r != r->main);
return 1;
}
if (len == sizeof("headers_sent") - 1
&& ngx_strncmp(p, "headers_sent", sizeof("headers_sent") - 1) == 0)
{
ngx_http_lua_check_fake_request(L, r);
dd("headers sent: %d", r->header_sent);
lua_pushboolean(L, r->header_sent ? 1 : 0);
return 1;
}
dd("key %s not matched", p);
lua_pushnil(L);
return 1;
}
static int
ngx_http_lua_ngx_set(lua_State *L)
{
ngx_http_request_t *r;
u_char *p;
size_t len;
/* we skip the first argument that is the table */
p = (u_char *) luaL_checklstring(L, 2, &len);
if (len == sizeof("status") - 1
&& ngx_strncmp(p, "status", sizeof("status") - 1) == 0)
{
r = ngx_http_lua_get_req(L);
if (r == NULL) {
return luaL_error(L, "no request object found");
}
if (r->header_sent) {
ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
"attempt to set ngx.status after sending out "
"response headers");
return 0;
}
ngx_http_lua_check_fake_request(L, r);
/* get the value */
r->headers_out.status = (ngx_uint_t) luaL_checknumber(L, 3);
if (r->headers_out.status == 101) {
/*
* XXX work-around a bug in the Nginx core that 101 does
* not have a default status line
*/
ngx_str_set(&r->headers_out.status_line, "101 Switching Protocols");
} else {
r->headers_out.status_line.len = 0;
}
return 0;
}
if (len == sizeof("ctx") - 1
&& ngx_strncmp(p, "ctx", sizeof("ctx") - 1) == 0)
{
r = ngx_http_lua_get_req(L);
if (r == NULL) {
return luaL_error(L, "no request object found");
}
return ngx_http_lua_ngx_set_ctx(L);
}
lua_rawset(L, -3);
return 0;
}
#ifndef NGX_LUA_NO_FFI_API
int
ngx_http_lua_ffi_get_resp_status(ngx_http_request_t *r)
{
if (r->connection->fd == -1) {
return NGX_HTTP_LUA_FFI_BAD_CONTEXT;
}
if (r->err_status) {
return r->err_status;
} else if (r->headers_out.status) {
return r->headers_out.status;
} else if (r->http_version == NGX_HTTP_VERSION_9) {
return 9;
} else {
return 0;
}
}
int
ngx_http_lua_ffi_set_resp_status(ngx_http_request_t *r, int status)
{
if (r->connection->fd == -1) {
return NGX_HTTP_LUA_FFI_BAD_CONTEXT;
}
if (r->header_sent) {
ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
"attempt to set ngx.status after sending out "
"response headers");
return NGX_DECLINED;
}
r->headers_out.status = status;
if (status == 101) {
/*
* XXX work-around a bug in the Nginx core older than 1.5.5
* that 101 does not have a default status line
*/
ngx_str_set(&r->headers_out.status_line, "101 Switching Protocols");
} else {
r->headers_out.status_line.len = 0;
}
return NGX_OK;
}
int
ngx_http_lua_ffi_is_subrequest(ngx_http_request_t *r)
{
if (r->connection->fd == -1) {
return NGX_HTTP_LUA_FFI_BAD_CONTEXT;
}
return r != r->main;
}
int
ngx_http_lua_ffi_headers_sent(ngx_http_request_t *r)
{
ngx_http_lua_ctx_t *ctx;
ctx = ngx_http_get_module_ctx(r, ngx_http_lua_module);
if (ctx == NULL) {
return NGX_HTTP_LUA_FFI_NO_REQ_CTX;
}
if (r->connection->fd == -1) {
return NGX_HTTP_LUA_FFI_BAD_CONTEXT;
}
return r->header_sent ? 1 : 0;
}
#endif /* NGX_LUA_NO_FFI_API */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,252 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include "ngx_http_lua_req_method.h"
#include "ngx_http_lua_subrequest.h"
#include "ngx_http_lua_util.h"
static int ngx_http_lua_ngx_req_get_method(lua_State *L);
static int ngx_http_lua_ngx_req_set_method(lua_State *L);
void
ngx_http_lua_inject_req_method_api(lua_State *L)
{
lua_pushcfunction(L, ngx_http_lua_ngx_req_get_method);
lua_setfield(L, -2, "get_method");
lua_pushcfunction(L, ngx_http_lua_ngx_req_set_method);
lua_setfield(L, -2, "set_method");
}
static int
ngx_http_lua_ngx_req_get_method(lua_State *L)
{
int n;
ngx_http_request_t *r;
n = lua_gettop(L);
if (n != 0) {
return luaL_error(L, "only one argument expected but got %d", n);
}
r = ngx_http_lua_get_req(L);
if (r == NULL) {
return luaL_error(L, "request object not found");
}
ngx_http_lua_check_fake_request(L, r);
lua_pushlstring(L, (char *) r->method_name.data, r->method_name.len);
return 1;
}
static int
ngx_http_lua_ngx_req_set_method(lua_State *L)
{
int n;
int method;
ngx_http_request_t *r;
n = lua_gettop(L);
if (n != 1) {
return luaL_error(L, "only one argument expected but got %d", n);
}
method = luaL_checkint(L, 1);
r = ngx_http_lua_get_req(L);
if (r == NULL) {
return luaL_error(L, "request object not found");
}
ngx_http_lua_check_fake_request(L, r);
switch (method) {
case NGX_HTTP_GET:
r->method_name = ngx_http_lua_get_method;
break;
case NGX_HTTP_POST:
r->method_name = ngx_http_lua_post_method;
break;
case NGX_HTTP_PUT:
r->method_name = ngx_http_lua_put_method;
break;
case NGX_HTTP_HEAD:
r->method_name = ngx_http_lua_head_method;
break;
case NGX_HTTP_DELETE:
r->method_name = ngx_http_lua_delete_method;
break;
case NGX_HTTP_OPTIONS:
r->method_name = ngx_http_lua_options_method;
break;
case NGX_HTTP_MKCOL:
r->method_name = ngx_http_lua_mkcol_method;
break;
case NGX_HTTP_COPY:
r->method_name = ngx_http_lua_copy_method;
break;
case NGX_HTTP_MOVE:
r->method_name = ngx_http_lua_move_method;
break;
case NGX_HTTP_PROPFIND:
r->method_name = ngx_http_lua_propfind_method;
break;
case NGX_HTTP_PROPPATCH:
r->method_name = ngx_http_lua_proppatch_method;
break;
case NGX_HTTP_LOCK:
r->method_name = ngx_http_lua_lock_method;
break;
case NGX_HTTP_UNLOCK:
r->method_name = ngx_http_lua_unlock_method;
break;
case NGX_HTTP_PATCH:
r->method_name = ngx_http_lua_patch_method;
break;
case NGX_HTTP_TRACE:
r->method_name = ngx_http_lua_trace_method;
break;
default:
return luaL_error(L, "unsupported HTTP method: %d", method);
}
r->method = method;
return 0;
}
#ifndef NGX_LUA_NO_FFI_API
int
ngx_http_lua_ffi_req_get_method(ngx_http_request_t *r)
{
if (r->connection->fd == -1) {
return NGX_HTTP_LUA_FFI_BAD_CONTEXT;
}
return r->method;
}
int
ngx_http_lua_ffi_req_get_method_name(ngx_http_request_t *r, char *buf,
size_t *len)
{
if (r->connection->fd == -1) {
return NGX_HTTP_LUA_FFI_BAD_CONTEXT;
}
*len = ngx_min(r->method_name.len, *len);
ngx_memcpy(buf, r->method_name.data, *len);
return NGX_OK;
}
int
ngx_http_lua_ffi_req_set_method(ngx_http_request_t *r, int method)
{
if (r->connection->fd == -1) {
return NGX_HTTP_LUA_FFI_BAD_CONTEXT;
}
switch (method) {
case NGX_HTTP_GET:
r->method_name = ngx_http_lua_get_method;
break;
case NGX_HTTP_POST:
r->method_name = ngx_http_lua_post_method;
break;
case NGX_HTTP_PUT:
r->method_name = ngx_http_lua_put_method;
break;
case NGX_HTTP_HEAD:
r->method_name = ngx_http_lua_head_method;
break;
case NGX_HTTP_DELETE:
r->method_name = ngx_http_lua_delete_method;
break;
case NGX_HTTP_OPTIONS:
r->method_name = ngx_http_lua_options_method;
break;
case NGX_HTTP_MKCOL:
r->method_name = ngx_http_lua_mkcol_method;
break;
case NGX_HTTP_COPY:
r->method_name = ngx_http_lua_copy_method;
break;
case NGX_HTTP_MOVE:
r->method_name = ngx_http_lua_move_method;
break;
case NGX_HTTP_PROPFIND:
r->method_name = ngx_http_lua_propfind_method;
break;
case NGX_HTTP_PROPPATCH:
r->method_name = ngx_http_lua_proppatch_method;
break;
case NGX_HTTP_LOCK:
r->method_name = ngx_http_lua_lock_method;
break;
case NGX_HTTP_UNLOCK:
r->method_name = ngx_http_lua_unlock_method;
break;
case NGX_HTTP_PATCH:
r->method_name = ngx_http_lua_patch_method;
break;
case NGX_HTTP_TRACE:
r->method_name = ngx_http_lua_trace_method;
break;
default:
return NGX_DECLINED;
}
r->method = method;
return NGX_OK;
}
#endif
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,579 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include "ngx_http_lua_timer.h"
#include "ngx_http_lua_util.h"
#include "ngx_http_lua_contentby.h"
#include "ngx_http_lua_probe.h"
typedef struct {
unsigned premature; /* :1 */
int co_ref;
lua_State *co;
void **main_conf;
void **srv_conf;
void **loc_conf;
ngx_http_lua_main_conf_t *lmcf;
ngx_http_lua_vm_state_t *vm_state;
} ngx_http_lua_timer_ctx_t;
static int ngx_http_lua_ngx_timer_at(lua_State *L);
static void ngx_http_lua_timer_handler(ngx_event_t *ev);
static u_char * ngx_http_lua_log_timer_error(ngx_log_t *log, u_char *buf,
size_t len);
static void ngx_http_lua_abort_pending_timers(ngx_event_t *ev);
void
ngx_http_lua_inject_timer_api(lua_State *L)
{
lua_createtable(L, 0 /* narr */, 1 /* nrec */); /* ngx.timer. */
lua_pushcfunction(L, ngx_http_lua_ngx_timer_at);
lua_setfield(L, -2, "at");
lua_setfield(L, -2, "timer");
}
static int
ngx_http_lua_ngx_timer_at(lua_State *L)
{
int nargs, co_ref;
u_char *p;
lua_State *vm; /* the main thread */
lua_State *co;
ngx_msec_t delay;
ngx_event_t *ev;
ngx_http_request_t *r;
ngx_connection_t *saved_c = NULL;
ngx_http_lua_ctx_t *ctx;
#if 0
ngx_http_connection_t *hc;
#endif
ngx_http_lua_timer_ctx_t *tctx;
ngx_http_lua_main_conf_t *lmcf;
#if 0
ngx_http_core_main_conf_t *cmcf;
#endif
nargs = lua_gettop(L);
if (nargs < 2) {
return luaL_error(L, "expecting at least 2 arguments but got %d",
nargs);
}
delay = (ngx_msec_t) (luaL_checknumber(L, 1) * 1000);
luaL_argcheck(L, lua_isfunction(L, 2) && !lua_iscfunction(L, 2), 2,
"Lua function expected");
r = ngx_http_lua_get_req(L);
if (r == NULL) {
return luaL_error(L, "no request");
}
ctx = ngx_http_get_module_ctx(r, ngx_http_lua_module);
if (ngx_exiting && delay > 0) {
lua_pushnil(L);
lua_pushliteral(L, "process exiting");
return 2;
}
lmcf = ngx_http_get_module_main_conf(r, ngx_http_lua_module);
if (lmcf->pending_timers >= lmcf->max_pending_timers) {
lua_pushnil(L);
lua_pushliteral(L, "too many pending timers");
return 2;
}
if (lmcf->watcher == NULL) {
/* create the watcher fake connection */
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, ngx_cycle->log, 0,
"lua creating fake watcher connection");
if (ngx_cycle->files) {
saved_c = ngx_cycle->files[0];
}
lmcf->watcher = ngx_get_connection(0, ngx_cycle->log);
if (ngx_cycle->files) {
ngx_cycle->files[0] = saved_c;
}
if (lmcf->watcher == NULL) {
return luaL_error(L, "no memory");
}
/* to work around the -1 check in ngx_worker_process_cycle: */
lmcf->watcher->fd = (ngx_socket_t) -2;
lmcf->watcher->idle = 1;
lmcf->watcher->read->handler = ngx_http_lua_abort_pending_timers;
lmcf->watcher->data = lmcf;
}
vm = ngx_http_lua_get_lua_vm(r, ctx);
co = lua_newthread(vm);
/* L stack: time func [args] thread */
ngx_http_lua_probe_user_coroutine_create(r, L, co);
lua_createtable(co, 0, 0); /* the new globals table */
/* co stack: global_tb */
lua_createtable(co, 0, 1); /* the metatable */
ngx_http_lua_get_globals_table(co);
lua_setfield(co, -2, "__index");
lua_setmetatable(co, -2);
/* co stack: global_tb */
ngx_http_lua_set_globals_table(co);
/* co stack: <empty> */
dd("stack top: %d", lua_gettop(L));
lua_xmove(vm, L, 1); /* move coroutine from main thread to L */
/* L stack: time func [args] thread */
/* vm stack: empty */
lua_pushvalue(L, 2); /* copy entry function to top of L*/
/* L stack: time func [args] thread func */
lua_xmove(L, co, 1); /* move entry function from L to co */
/* L stack: time func [args] thread */
/* co stack: func */
ngx_http_lua_get_globals_table(co);
lua_setfenv(co, -2);
/* co stack: func */
lua_pushlightuserdata(L, &ngx_http_lua_coroutines_key);
lua_rawget(L, LUA_REGISTRYINDEX);
/* L stack: time func [args] thread corountines */
lua_pushvalue(L, -2);
/* L stack: time func [args] thread coroutines thread */
co_ref = luaL_ref(L, -2);
lua_pop(L, 1);
/* L stack: time func [args] thread */
if (nargs > 2) {
lua_pop(L, 1); /* L stack: time func [args] */
lua_xmove(L, co, nargs - 2); /* L stack: time func */
/* co stack: func [args] */
}
p = ngx_alloc(sizeof(ngx_event_t) + sizeof(ngx_http_lua_timer_ctx_t),
r->connection->log);
if (p == NULL) {
lua_pushlightuserdata(L, &ngx_http_lua_coroutines_key);
lua_rawget(L, LUA_REGISTRYINDEX);
luaL_unref(L, -1, co_ref);
return luaL_error(L, "no memory");
}
ev = (ngx_event_t *) p;
ngx_memzero(ev, sizeof(ngx_event_t));
p += sizeof(ngx_event_t);
tctx = (ngx_http_lua_timer_ctx_t *) p;
tctx->premature = 0;
tctx->co_ref = co_ref;
tctx->co = co;
tctx->main_conf = r->main_conf;
tctx->srv_conf = r->srv_conf;
tctx->loc_conf = r->loc_conf;
tctx->lmcf = lmcf;
if (ctx && ctx->vm_state) {
tctx->vm_state = ctx->vm_state;
tctx->vm_state->count++;
} else {
tctx->vm_state = NULL;
}
ev->handler = ngx_http_lua_timer_handler;
ev->data = tctx;
ev->log = ngx_cycle->log;
lmcf->pending_timers++;
ngx_add_timer(ev, delay);
lua_pushinteger(L, 1);
return 1;
}
static void
ngx_http_lua_timer_handler(ngx_event_t *ev)
{
int n;
lua_State *L;
ngx_int_t rc;
ngx_connection_t *c = NULL;
ngx_http_request_t *r = NULL;
ngx_http_lua_ctx_t *ctx;
ngx_http_cleanup_t *cln;
ngx_pool_cleanup_t *pcln;
ngx_http_lua_timer_ctx_t tctx;
ngx_http_lua_main_conf_t *lmcf;
ngx_http_core_loc_conf_t *clcf;
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, ngx_cycle->log, 0,
"lua ngx.timer expired");
ngx_memcpy(&tctx, ev->data, sizeof(ngx_http_lua_timer_ctx_t));
ngx_free(ev);
ev = NULL;
lmcf = tctx.lmcf;
lmcf->pending_timers--;
if (lmcf->running_timers >= lmcf->max_running_timers) {
ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, 0,
"%i lua_max_running_timers are not enough",
lmcf->max_running_timers);
goto failed;
}
c = ngx_http_lua_create_fake_connection();
if (c == NULL) {
goto failed;
}
c->log->handler = ngx_http_lua_log_timer_error;
r = ngx_http_lua_create_fake_request(c);
if (r == NULL) {
goto failed;
}
r->main_conf = tctx.main_conf;
r->srv_conf = tctx.srv_conf;
r->loc_conf = tctx.loc_conf;
clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
c->log->file = clcf->error_log->file;
if (!(c->log->log_level & NGX_LOG_DEBUG_CONNECTION)) {
c->log->log_level = clcf->error_log->log_level;
}
dd("lmcf: %p", lmcf);
ctx = ngx_http_lua_create_ctx(r);
if (ctx == NULL) {
goto failed;
}
if (tctx.vm_state) {
ctx->vm_state = tctx.vm_state;
pcln = ngx_pool_cleanup_add(r->pool, 0);
if (pcln == NULL) {
goto failed;
}
pcln->handler = ngx_http_lua_cleanup_vm;
pcln->data = tctx.vm_state;
}
ctx->cur_co_ctx = &ctx->entry_co_ctx;
L = ngx_http_lua_get_lua_vm(r, ctx);
cln = ngx_http_cleanup_add(r, 0);
if (cln == NULL) {
goto failed;
}
cln->handler = ngx_http_lua_request_cleanup_handler;
cln->data = ctx;
ctx->cleanup = &cln->handler;
ctx->entered_content_phase = 1;
ctx->context = NGX_HTTP_LUA_CONTEXT_TIMER;
r->read_event_handler = ngx_http_block_reading;
ctx->cur_co_ctx->co_ref = tctx.co_ref;
ctx->cur_co_ctx->co = tctx.co;
ctx->cur_co_ctx->co_status = NGX_HTTP_LUA_CO_RUNNING;
dd("r connection: %p, log %p", r->connection, r->connection->log);
/* save the request in coroutine globals table */
ngx_http_lua_set_req(tctx.co, r);
lmcf->running_timers++;
lua_pushboolean(tctx.co, tctx.premature);
n = lua_gettop(tctx.co);
if (n > 2) {
lua_insert(tctx.co, 2);
}
#ifdef NGX_LUA_USE_ASSERT
ctx->cur_co_ctx->co_top = 1;
#endif
rc = ngx_http_lua_run_thread(L, r, ctx, n - 1);
dd("timer lua run thread: %d", (int) rc);
if (rc == NGX_ERROR || rc >= NGX_OK) {
/* do nothing */
} else if (rc == NGX_AGAIN) {
rc = ngx_http_lua_content_run_posted_threads(L, r, ctx, 0);
} else if (rc == NGX_DONE) {
rc = ngx_http_lua_content_run_posted_threads(L, r, ctx, 1);
} else {
rc = NGX_OK;
}
ngx_http_lua_finalize_request(r, rc);
return;
failed:
if (tctx.co_ref && tctx.co) {
lua_pushlightuserdata(tctx.co, &ngx_http_lua_coroutines_key);
lua_rawget(tctx.co, LUA_REGISTRYINDEX);
luaL_unref(tctx.co, -1, tctx.co_ref);
lua_settop(tctx.co, 0);
}
if (tctx.vm_state) {
ngx_http_lua_cleanup_vm(tctx.vm_state);
}
if (r && r->pool) {
ngx_destroy_pool(r->pool);
}
if (c) {
ngx_http_lua_close_fake_connection(c);
}
}
static u_char *
ngx_http_lua_log_timer_error(ngx_log_t *log, u_char *buf, size_t len)
{
u_char *p;
if (log->action) {
p = ngx_snprintf(buf, len, " while %s", log->action);
len -= p - buf;
buf = p;
}
return ngx_snprintf(buf, len, ", context: ngx.timer");
}
static void
ngx_http_lua_abort_pending_timers(ngx_event_t *ev)
{
ngx_int_t i, n;
ngx_event_t **events;
ngx_connection_t *c, *saved_c = NULL;
ngx_rbtree_node_t *cur, *prev, *next, *sentinel, *temp;
ngx_http_lua_timer_ctx_t *tctx;
ngx_http_lua_main_conf_t *lmcf;
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, ngx_cycle->log, 0,
"lua abort pending timers");
c = ev->data;
lmcf = c->data;
dd("lua connection fd: %d", (int) c->fd);
if (!c->close) {
return;
}
c->read->closed = 1;
c->write->closed = 1;
/* we temporarily use a valid fd (0) to make ngx_free_connection happy */
c->fd = 0;
if (ngx_cycle->files) {
saved_c = ngx_cycle->files[0];
}
ngx_free_connection(c);
c->fd = (ngx_socket_t) -1;
if (ngx_cycle->files) {
ngx_cycle->files[0] = saved_c;
}
if (lmcf->pending_timers == 0) {
return;
}
/* expire pending timers immediately */
sentinel = ngx_event_timer_rbtree.sentinel;
cur = ngx_event_timer_rbtree.root;
/* XXX nginx does not guarentee the parent of root is meaningful,
* so we temporarily override it to simplify tree traversal. */
temp = cur->parent;
cur->parent = NULL;
prev = NULL;
events = ngx_pcalloc(ngx_cycle->pool,
lmcf->pending_timers * sizeof(ngx_event_t));
if (events == NULL) {
return;
}
n = 0;
dd("root: %p, root parent: %p, sentinel: %p", cur, cur->parent, sentinel);
while (n < lmcf->pending_timers) {
if (cur == sentinel || cur == NULL) {
ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, 0,
"lua pending timer counter got out of sync: %i",
lmcf->pending_timers);
break;
}
dd("prev: %p, cur: %p, cur parent: %p, cur left: %p, cur right: %p",
prev, cur, cur->parent, cur->left, cur->right);
if (prev == cur->parent) {
/* neither of the children has been accessed yet */
next = cur->left;
if (next == sentinel) {
ev = (ngx_event_t *)
((char *) cur - offsetof(ngx_event_t, timer));
if (ev->handler == ngx_http_lua_timer_handler) {
dd("found node: %p", cur);
events[n++] = ev;
}
next = (cur->right != sentinel) ? cur->right : cur->parent;
}
} else if (prev == cur->left) {
/* just accessed the left child */
ev = (ngx_event_t *)
((char *) cur - offsetof(ngx_event_t, timer));
if (ev->handler == ngx_http_lua_timer_handler) {
dd("found node 2: %p", cur);
events[n++] = ev;
}
next = (cur->right != sentinel) ? cur->right : cur->parent;
} else if (prev == cur->right) {
/* already accessed both children */
next = cur->parent;
} else {
/* not reacheable */
next = NULL;
}
prev = cur;
cur = next;
}
/* restore the old tree root's parent */
ngx_event_timer_rbtree.root->parent = temp;
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, ngx_cycle->log, 0,
"lua found %i pending timers to be aborted prematurely",
n);
for (i = 0; i < n; i++) {
ev = events[i];
ngx_rbtree_delete(&ngx_event_timer_rbtree, &ev->timer);
#if (NGX_DEBUG)
ev->timer.left = NULL;
ev->timer.right = NULL;
ev->timer.parent = NULL;
#endif
ev->timer_set = 0;
ev->timedout = 1;
tctx = ev->data;
tctx->premature = 1;
dd("calling timer handler prematurely");
ev->handler(ev);
}
#if 0
if (pending_timers) {
ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, 0,
"lua pending timer counter got out of sync: %i",
pending_timers);
}
#endif
}
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,20 +0,0 @@
/*
* Copyright (C) Xiaozhe Wang (chaoslawful)
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_TIMER_H_INCLUDED_
#define _NGX_HTTP_LUA_TIMER_H_INCLUDED_
#include "ngx_http_lua_common.h"
void ngx_http_lua_inject_timer_api(lua_State *L);
#endif /* _NGX_HTTP_LUA_TIMER_H_INCLUDED_ */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,405 +0,0 @@
/*
* Copyright (C) Xiaozhe Wang (chaoslawful)
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_UTIL_H_INCLUDED_
#define _NGX_HTTP_LUA_UTIL_H_INCLUDED_
#include "ngx_http_lua_common.h"
#ifndef NGX_UNESCAPE_URI_COMPONENT
#define NGX_UNESCAPE_URI_COMPONENT 0
#endif
#ifndef NGX_LUA_NO_FFI_API
typedef struct {
int len;
u_char *data;
} ngx_http_lua_ffi_str_t;
typedef struct {
ngx_http_lua_ffi_str_t key;
ngx_http_lua_ffi_str_t value;
} ngx_http_lua_ffi_table_elt_t;
#endif /* NGX_LUA_NO_FFI_API */
/* char whose address we use as the key in Lua vm registry for
* user code cache table */
extern char ngx_http_lua_code_cache_key;
/* key in Lua vm registry for all the "ngx.ctx" tables */
#define ngx_http_lua_ctx_tables_key "ngx_lua_ctx_tables"
/* char whose address we use as the key in Lua vm registry for
* regex cache table */
extern char ngx_http_lua_regex_cache_key;
/* char whose address we use as the key in Lua vm registry for
* socket connection pool table */
extern char ngx_http_lua_socket_pool_key;
/* char whose address we use as the key for the coroutine parent relationship */
extern char ngx_http_lua_coroutine_parents_key;
/* coroutine anchoring table key in Lua VM registry */
extern char ngx_http_lua_coroutines_key;
/* key to the metatable for ngx.req.get_headers() and ngx.resp.get_headers() */
extern char ngx_http_lua_headers_metatable_key;
#ifndef ngx_str_set
#define ngx_str_set(str, text) \
(str)->len = sizeof(text) - 1; (str)->data = (u_char *) text
#endif
#ifndef NGX_HTTP_SWITCHING_PROTOCOLS
#define NGX_HTTP_SWITCHING_PROTOCOLS 101
#endif
#if defined(nginx_version) && nginx_version < 1000000
#define ngx_memmove(dst, src, n) (void) memmove(dst, src, n)
#endif
#define ngx_http_lua_context_name(c) \
((c) == NGX_HTTP_LUA_CONTEXT_SET ? "set_by_lua*" \
: (c) == NGX_HTTP_LUA_CONTEXT_REWRITE ? "rewrite_by_lua*" \
: (c) == NGX_HTTP_LUA_CONTEXT_ACCESS ? "access_by_lua*" \
: (c) == NGX_HTTP_LUA_CONTEXT_CONTENT ? "content_by_lua*" \
: (c) == NGX_HTTP_LUA_CONTEXT_LOG ? "log_by_lua*" \
: (c) == NGX_HTTP_LUA_CONTEXT_HEADER_FILTER ? "header_filter_by_lua*" \
: (c) == NGX_HTTP_LUA_CONTEXT_TIMER ? "ngx.timer" \
: (c) == NGX_HTTP_LUA_CONTEXT_INIT_WORKER ? "init_worker_by_lua*" \
: "(unknown)")
#define ngx_http_lua_check_context(L, ctx, flags) \
if (!((ctx)->context & (flags))) { \
return luaL_error(L, "API disabled in the context of %s", \
ngx_http_lua_context_name((ctx)->context)); \
}
#ifndef NGX_LUA_NO_FFI_API
static ngx_inline ngx_int_t
ngx_http_lua_ffi_check_context(ngx_http_lua_ctx_t *ctx, unsigned flags,
u_char *err, size_t *errlen)
{
if (!(ctx->context & flags)) {
*errlen = ngx_snprintf(err, *errlen,
"API disabled in the context of %s",
ngx_http_lua_context_name((ctx)->context))
- err;
return NGX_DECLINED;
}
return NGX_OK;
}
#endif
#define ngx_http_lua_check_fake_request(L, r) \
if ((r)->connection->fd == -1) { \
return luaL_error(L, "API disabled in the current context"); \
}
#define ngx_http_lua_check_fake_request2(L, r, ctx) \
if ((r)->connection->fd == -1) { \
return luaL_error(L, "API disabled in the context of %s", \
ngx_http_lua_context_name((ctx)->context)); \
}
lua_State * ngx_http_lua_init_vm(lua_State *parent_vm, ngx_cycle_t *cycle,
ngx_pool_t *pool, ngx_http_lua_main_conf_t *lmcf, ngx_log_t *log,
ngx_pool_cleanup_t **pcln);
lua_State * ngx_http_lua_new_thread(ngx_http_request_t *r, lua_State *l,
int *ref);
u_char * ngx_http_lua_rebase_path(ngx_pool_t *pool, u_char *src, size_t len);
ngx_int_t ngx_http_lua_send_header_if_needed(ngx_http_request_t *r,
ngx_http_lua_ctx_t *ctx);
ngx_int_t ngx_http_lua_send_chain_link(ngx_http_request_t *r,
ngx_http_lua_ctx_t *ctx, ngx_chain_t *cl);
void ngx_http_lua_discard_bufs(ngx_pool_t *pool, ngx_chain_t *in);
ngx_int_t ngx_http_lua_add_copy_chain(ngx_http_request_t *r,
ngx_http_lua_ctx_t *ctx, ngx_chain_t ***plast, ngx_chain_t *in,
ngx_int_t *eof);
void ngx_http_lua_reset_ctx(ngx_http_request_t *r, lua_State *L,
ngx_http_lua_ctx_t *ctx);
void ngx_http_lua_generic_phase_post_read(ngx_http_request_t *r);
void ngx_http_lua_request_cleanup(ngx_http_lua_ctx_t *ctx, int foricible);
void ngx_http_lua_request_cleanup_handler(void *data);
ngx_int_t ngx_http_lua_run_thread(lua_State *L, ngx_http_request_t *r,
ngx_http_lua_ctx_t *ctx, volatile int nret);
ngx_int_t ngx_http_lua_wev_handler(ngx_http_request_t *r);
u_char * ngx_http_lua_digest_hex(u_char *dest, const u_char *buf,
int buf_len);
void ngx_http_lua_set_multi_value_table(lua_State *L, int index);
void ngx_http_lua_unescape_uri(u_char **dst, u_char **src, size_t size,
ngx_uint_t type);
uintptr_t ngx_http_lua_escape_uri(u_char *dst, u_char *src,
size_t size, ngx_uint_t type);
void ngx_http_lua_inject_req_api(ngx_log_t *log, lua_State *L);
void ngx_http_lua_process_args_option(ngx_http_request_t *r,
lua_State *L, int table, ngx_str_t *args);
ngx_int_t ngx_http_lua_open_and_stat_file(u_char *name,
ngx_open_file_info_t *of, ngx_log_t *log);
ngx_chain_t * ngx_http_lua_chain_get_free_buf(ngx_log_t *log, ngx_pool_t *p,
ngx_chain_t **free, size_t len);
void ngx_http_lua_create_new_globals_table(lua_State *L, int narr, int nrec);
int ngx_http_lua_traceback(lua_State *L);
ngx_http_lua_co_ctx_t * ngx_http_lua_get_co_ctx(lua_State *L,
ngx_http_lua_ctx_t *ctx);
ngx_http_lua_co_ctx_t * ngx_http_lua_create_co_ctx(ngx_http_request_t *r,
ngx_http_lua_ctx_t *ctx);
ngx_int_t ngx_http_lua_run_posted_threads(ngx_connection_t *c, lua_State *L,
ngx_http_request_t *r, ngx_http_lua_ctx_t *ctx);
ngx_int_t ngx_http_lua_post_thread(ngx_http_request_t *r,
ngx_http_lua_ctx_t *ctx, ngx_http_lua_co_ctx_t *coctx);
void ngx_http_lua_del_thread(ngx_http_request_t *r, lua_State *L,
ngx_http_lua_ctx_t *ctx, ngx_http_lua_co_ctx_t *coctx);
void ngx_http_lua_rd_check_broken_connection(ngx_http_request_t *r);
ngx_int_t ngx_http_lua_test_expect(ngx_http_request_t *r);
ngx_int_t ngx_http_lua_check_broken_connection(ngx_http_request_t *r,
ngx_event_t *ev);
void ngx_http_lua_finalize_request(ngx_http_request_t *r, ngx_int_t rc);
void ngx_http_lua_finalize_fake_request(ngx_http_request_t *r,
ngx_int_t rc);
void ngx_http_lua_close_fake_connection(ngx_connection_t *c);
void ngx_http_lua_release_ngx_ctx_table(ngx_log_t *log, lua_State *L,
ngx_http_lua_ctx_t *ctx);
void ngx_http_lua_cleanup_vm(void *data);
ngx_connection_t * ngx_http_lua_create_fake_connection(void);
ngx_http_request_t * ngx_http_lua_create_fake_request(ngx_connection_t *c);
ngx_int_t ngx_http_lua_report(ngx_log_t *log, lua_State *L, int status,
const char *prefix);
int ngx_http_lua_do_call(ngx_log_t *log, lua_State *L);
#define ngx_http_lua_check_if_abortable(L, ctx) \
if ((ctx)->no_abort) { \
return luaL_error(L, "attempt to abort with pending subrequests"); \
}
static ngx_inline void
ngx_http_lua_init_ctx(ngx_http_request_t *r, ngx_http_lua_ctx_t *ctx)
{
ngx_memzero(ctx, sizeof(ngx_http_lua_ctx_t));
ctx->ctx_ref = LUA_NOREF;
ctx->entry_co_ctx.co_ref = LUA_NOREF;
ctx->resume_handler = ngx_http_lua_wev_handler;
ctx->request = r;
}
static ngx_inline ngx_http_lua_ctx_t *
ngx_http_lua_create_ctx(ngx_http_request_t *r)
{
lua_State *L;
ngx_http_lua_ctx_t *ctx;
ngx_pool_cleanup_t *cln;
ngx_http_lua_loc_conf_t *llcf;
ngx_http_lua_main_conf_t *lmcf;
ctx = ngx_palloc(r->pool, sizeof(ngx_http_lua_ctx_t));
if (ctx == NULL) {
return NULL;
}
ngx_http_lua_init_ctx(r, ctx);
ngx_http_set_ctx(r, ctx, ngx_http_lua_module);
llcf = ngx_http_get_module_loc_conf(r, ngx_http_lua_module);
if (!llcf->enable_code_cache && r->connection->fd != -1) {
lmcf = ngx_http_get_module_main_conf(r, ngx_http_lua_module);
dd("lmcf: %p", lmcf);
L = ngx_http_lua_init_vm(lmcf->lua, lmcf->cycle, r->pool, lmcf,
r->connection->log, &cln);
if (L == NULL) {
ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
"failed to initialize Lua VM");
return NULL;
}
if (lmcf->init_handler) {
if (lmcf->init_handler(r->connection->log, lmcf, L) != NGX_OK) {
/* an error happened */
return NULL;
}
}
ctx->vm_state = cln->data;
} else {
ctx->vm_state = NULL;
}
return ctx;
}
static ngx_inline lua_State *
ngx_http_lua_get_lua_vm(ngx_http_request_t *r, ngx_http_lua_ctx_t *ctx)
{
ngx_http_lua_main_conf_t *lmcf;
if (ctx == NULL) {
ctx = ngx_http_get_module_ctx(r, ngx_http_lua_module);
}
if (ctx && ctx->vm_state) {
return ctx->vm_state->vm;
}
lmcf = ngx_http_get_module_main_conf(r, ngx_http_lua_module);
dd("lmcf->lua: %p", lmcf->lua);
return lmcf->lua;
}
#define ngx_http_lua_req_key "__ngx_req"
static ngx_inline ngx_http_request_t *
ngx_http_lua_get_req(lua_State *L)
{
ngx_http_request_t *r;
lua_getglobal(L, ngx_http_lua_req_key);
r = lua_touserdata(L, -1);
lua_pop(L, 1);
return r;
}
static ngx_inline void
ngx_http_lua_set_req(lua_State *L, ngx_http_request_t *r)
{
lua_pushlightuserdata(L, r);
lua_setglobal(L, ngx_http_lua_req_key);
}
static ngx_inline void
ngx_http_lua_get_globals_table(lua_State *L)
{
lua_pushvalue(L, LUA_GLOBALSINDEX);
}
static ngx_inline void
ngx_http_lua_set_globals_table(lua_State *L)
{
lua_replace(L, LUA_GLOBALSINDEX);
}
#define ngx_http_lua_hash_literal(s) \
ngx_http_lua_hash_str((u_char *) s, sizeof(s) - 1)
static ngx_inline ngx_uint_t
ngx_http_lua_hash_str(u_char *src, size_t n)
{
ngx_uint_t key;
key = 0;
while (n--) {
key = ngx_hash(key, *src);
src++;
}
return key;
}
static ngx_inline ngx_int_t
ngx_http_lua_set_content_type(ngx_http_request_t *r)
{
ngx_http_lua_loc_conf_t *llcf;
llcf = ngx_http_get_module_loc_conf(r, ngx_http_lua_module);
if (llcf->use_default_type) {
return ngx_http_set_content_type(r);
}
return NGX_OK;
}
static ngx_inline void
ngx_http_lua_cleanup_pending_operation(ngx_http_lua_co_ctx_t *coctx)
{
if (coctx->cleanup) {
coctx->cleanup(coctx);
coctx->cleanup = NULL;
}
}
extern ngx_uint_t ngx_http_lua_location_hash;
extern ngx_uint_t ngx_http_lua_content_length_hash;
#endif /* _NGX_HTTP_LUA_UTIL_H_INCLUDED_ */
/* vi:set ft=c ts=4 sw=4 et fdm=marker: */

View file

@ -1,64 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef DDEBUG
#define DDEBUG 0
#endif
#include "ddebug.h"
#include "ngx_http_lua_worker.h"
static int ngx_http_lua_ngx_worker_exiting(lua_State *L);
static int ngx_http_lua_ngx_worker_pid(lua_State *L);
void
ngx_http_lua_inject_worker_api(lua_State *L)
{
lua_createtable(L, 0 /* narr */, 2 /* nrec */); /* ngx.worker. */
lua_pushcfunction(L, ngx_http_lua_ngx_worker_exiting);
lua_setfield(L, -2, "exiting");
lua_pushcfunction(L, ngx_http_lua_ngx_worker_pid);
lua_setfield(L, -2, "pid");
lua_setfield(L, -2, "worker");
}
static int
ngx_http_lua_ngx_worker_exiting(lua_State *L)
{
lua_pushboolean(L, ngx_exiting);
return 1;
}
static int
ngx_http_lua_ngx_worker_pid(lua_State *L)
{
lua_pushinteger(L, (lua_Integer) ngx_pid);
return 1;
}
#ifndef NGX_LUA_NO_FFI_API
int
ngx_http_lua_ffi_worker_pid(void)
{
return (int) ngx_pid;
}
int
ngx_http_lua_ffi_worker_exiting(void)
{
return (int) ngx_exiting;
}
#endif

View file

@ -1,17 +0,0 @@
/*
* Copyright (C) Yichun Zhang (agentzh)
*/
#ifndef _NGX_HTTP_LUA_WORKER_H_INCLUDED_
#define _NGX_HTTP_LUA_WORKER_H_INCLUDED_
#include "ngx_http_lua_common.h"
void ngx_http_lua_inject_worker_api(lua_State *L);
#endif /* _NGX_HTTP_LUA_WORKER_H_INCLUDED_ */

View file

@ -1,2 +0,0 @@
servroot

View file

@ -1,88 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
repeat_each(1);
plan tests => repeat_each() * (blocks() * 2 + 1);
$ENV{TEST_NGINX_MEMCACHED_PORT} ||= 11211;
$ENV{TEST_NGINX_MYSQL_PORT} ||= 3306;
our $http_config = <<'_EOC_';
upstream database {
drizzle_server 127.0.0.1:$TEST_NGINX_MYSQL_PORT protocol=mysql
dbname=ngx_test user=ngx_test password=ngx_test;
}
_EOC_
no_shuffle();
run_tests();
__DATA__
=== TEST 1: conv_uid - drop table
--- http_config eval: $::http_config
--- config
location = /init {
drizzle_pass database;
drizzle_query "DROP TABLE IF EXISTS conv_uid";
}
--- request
GET /init
--- error_code: 200
--- timeout: 10
--- no_error_log
[error]
=== TEST 2: conv_uid - create table
--- http_config eval: $::http_config
--- config
location = /init {
drizzle_pass database;
drizzle_query "CREATE TABLE conv_uid(id serial primary key, new_uid integer, old_uid integer)";
}
--- request
GET /init
--- error_code: 200
--- timeout: 10
--- no_error_log
[error]
=== TEST 3: conv_uid - insert value
--- http_config eval: $::http_config
--- config
location = /init {
drizzle_pass database;
drizzle_query "INSERT INTO conv_uid(old_uid,new_uid) VALUES(32,56),(35,78)";
}
--- request
GET /init
--- error_code: 200
--- timeout: 10
--- no_error_log
[error]
=== TEST 4: flush data from memcached
--- config
location /flush {
set $memc_cmd flush_all;
memc_pass 127.0.0.1:$TEST_NGINX_MEMCACHED_PORT;
}
--- request
GET /flush
--- error_code: 200
--- response_body eval
"OK\r
"
--- timeout: 10
--- no_error_log
[error]

View file

@ -1,35 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
repeat_each(2);
plan tests => blocks() * repeat_each() * 2;
run_tests();
__DATA__
=== TEST 1: sanity (integer)
--- config
location /lua {
echo 2;
}
--- request
GET /lua
--- response_body
2
=== TEST 2: sanity (string)
--- config
location /lua {
echo "helloworld";
}
--- request
GET /lua
--- response_body
helloworld

View file

@ -1,799 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
repeat_each(2);
plan tests => repeat_each() * (blocks() * 3 + 4);
#log_level("warn");
no_long_string();
run_tests();
__DATA__
=== TEST 1: simple set (integer)
--- config
location /lua {
set_by_lua $res "return 1+1";
echo $res;
}
--- request
GET /lua
--- response_body
2
--- no_error_log
[error]
=== TEST 2: simple set (string)
--- config
location /lua {
set_by_lua $res "return 'hello' .. 'world'";
echo $res;
}
--- request
GET /lua
--- response_body
helloworld
--- no_error_log
[error]
=== TEST 3: internal only
--- config
location /lua {
set_by_lua $res "function fib(n) if n > 2 then return fib(n-1)+fib(n-2) else return 1 end end return fib(10)";
echo $res;
}
--- request
GET /lua
--- response_body
55
--- no_error_log
[error]
=== TEST 4: inlined script with arguments
--- config
location /lua {
set_by_lua $res "return ngx.arg[1] + ngx.arg[2]" $arg_a $arg_b;
echo $res;
}
--- request
GET /lua?a=1&b=2
--- response_body
3
--- no_error_log
[error]
=== TEST 5: fib by arg
--- config
location /fib {
set_by_lua $res "function fib(n) if n > 2 then return fib(n-1)+fib(n-2) else return 1 end end return fib(tonumber(ngx.arg[1]))" $arg_n;
echo $res;
}
--- request
GET /fib?n=10
--- response_body
55
--- no_error_log
[error]
=== TEST 6: adder
--- config
location = /adder {
set_by_lua $res
"local a = tonumber(ngx.arg[1])
local b = tonumber(ngx.arg[2])
return a + b" $arg_a $arg_b;
echo $res;
}
--- request
GET /adder?a=25&b=75
--- response_body
100
--- no_error_log
[error]
=== TEST 7: read nginx variables directly from within Lua
--- config
location = /set-both {
set $b 32;
set_by_lua $a "return tonumber(ngx.var.b) + 1";
echo "a = $a";
}
--- request
GET /set-both
--- response_body
a = 33
--- no_error_log
[error]
=== TEST 8: set nginx variables directly from within Lua
--- config
location = /set-both {
set $b "";
set_by_lua $a "ngx.var.b = 32; return 7";
echo "a = $a";
echo "b = $b";
}
--- request
GET /set-both
--- response_body
a = 7
b = 32
--- no_error_log
[error]
=== TEST 9: set non-existent nginx variables
--- config
location = /set-both {
#set $b "";
set_by_lua $a "ngx.var.b = 32; return 7";
echo "a = $a";
}
--- request
GET /set-both
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
variable "b" not found for writing; maybe it is a built-in variable that is not changeable or you forgot to use "set $b '';" in the config file to define it first
=== TEST 10: set quote sql str
--- config
location = /set {
set $a "";
set_by_lua $a "return ngx.quote_sql_str(ngx.var.a)";
echo $a;
}
--- request
GET /set
--- response_body
''
--- no_error_log
[error]
=== TEST 11: set md5
--- config
location = /md5 {
set_by_lua $a 'return ngx.md5("hello")';
echo $a;
}
--- request
GET /md5
--- response_body
5d41402abc4b2a76b9719d911017c592
--- no_error_log
[error]
=== TEST 12: no ngx.print
--- config
location /lua {
set_by_lua $res "ngx.print(32) return 1";
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 13: no ngx.say
--- config
location /lua {
set_by_lua $res "ngx.say(32) return 1";
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 14: no ngx.flush
--- config
location /lua {
set_by_lua $res "ngx.flush()";
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 15: no ngx.eof
--- config
location /lua {
set_by_lua $res "ngx.eof()";
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 16: no ngx.send_headers
--- config
location /lua {
set_by_lua $res "ngx.send_headers()";
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 17: no ngx.location.capture
--- config
location /lua {
set_by_lua $res 'ngx.location.capture("/sub")';
echo $res;
}
location /sub {
echo sub;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 18: no ngx.location.capture_multi
--- config
location /lua {
set_by_lua $res 'ngx.location.capture_multi{{"/sub"}}';
echo $res;
}
location /sub {
echo sub;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 19: no ngx.exit
--- config
location /lua {
set_by_lua $res 'ngx.exit(0)';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 20: no ngx.redirect
--- config
location /lua {
set_by_lua $res 'ngx.redirect("/blah")';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 21: no ngx.exec
--- config
location /lua {
set_by_lua $res 'ngx.exec("/blah")';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 22: no ngx.req.set_uri(uri, true)
--- config
location /lua {
set_by_lua $res 'ngx.req.set_uri("/blah", true)';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 23: ngx.req.set_uri(uri) exists
--- config
location /lua {
set_by_lua $res 'ngx.req.set_uri("/blah") return 1';
echo $uri;
}
--- request
GET /lua
--- response_body
/blah
--- no_error_log
[error]
=== TEST 24: no ngx.req.read_body()
--- config
location /lua {
set_by_lua $res 'ngx.req.read_body()';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 25: no ngx.req.socket()
--- config
location /lua {
set_by_lua $res 'return ngx.req.socket()';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 26: no ngx.socket.tcp()
--- config
location /lua {
set_by_lua $res 'return ngx.socket.tcp()';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 27: no ngx.socket.connect()
--- config
location /lua {
set_by_lua $res 'return ngx.socket.connect("127.0.0.1", 80)';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
API disabled in the context of set_by_lua*
=== TEST 28: set $limit_rate (variables with set_handler)
--- config
location /lua {
set $limit_rate 1000;
rewrite_by_lua '
ngx.var.limit_rate = 180;
';
echo "limit rate = $limit_rate";
}
--- request
GET /lua
--- response_body
limit rate = 180
--- no_error_log
[error]
=== TEST 29: set $args and read $query_string
--- config
location /lua {
set $args 'hello';
rewrite_by_lua '
ngx.var.args = "world";
';
echo $query_string;
}
--- request
GET /lua
--- response_body
world
--- no_error_log
[error]
=== TEST 30: set $arg_xxx
--- config
location /lua {
rewrite_by_lua '
ngx.var.arg_foo = "world";
';
echo $arg_foo;
}
--- request
GET /lua?foo=3
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
variable "arg_foo" not found for writing; maybe it is a built-in variable that is not changeable or you forgot to use "set $arg_foo '';" in the config file to define it first
=== TEST 31: symbol $ in lua code of set_by_lua
--- config
location /lua {
set_by_lua $res 'return "$unknown"';
echo $res;
}
--- request
GET /lua
--- response_body
$unknown
--- no_error_log
[error]
=== TEST 32: symbol $ in lua code of set_by_lua_file
--- config
location /lua {
set_by_lua_file $res html/a.lua;
echo $res;
}
--- user_files
>>> a.lua
return "$unknown"
--- request
GET /lua
--- response_body
$unknown
--- no_error_log
[error]
=== TEST 33: external script files with arguments
--- config
location /lua {
set_by_lua_file $res html/a.lua $arg_a $arg_b;
echo $res;
}
--- user_files
>>> a.lua
return ngx.arg[1] + ngx.arg[2]
--- request
GET /lua?a=5&b=2
--- response_body
7
--- no_error_log
[error]
=== TEST 34: variables in set_by_lua_file's file path
--- config
location /lua {
set $path "html/a.lua";
set_by_lua_file $res $path $arg_a $arg_b;
echo $res;
}
--- user_files
>>> a.lua
return ngx.arg[1] + ngx.arg[2]
--- request
GET /lua?a=5&b=2
--- response_body
7
--- no_error_log
[error]
=== TEST 35: lua error (string)
--- config
location /lua {
set_by_lua $res 'error("Bad")';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
failed to run set_by_lua*: set_by_lua:1: Bad
=== TEST 36: lua error (nil)
--- config
location /lua {
set_by_lua $res 'error(nil)';
echo $res;
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
failed to run set_by_lua*: unknown reason
=== TEST 37: globals get cleared for every single request
--- config
location /lua {
set_by_lua $res '
if not foo then
foo = 1
else
foo = foo + 1
end
return foo
';
echo $res;
}
--- request
GET /lua
--- response_body
1
--- no_error_log
[error]
=== TEST 38: user modules using ngx.arg
--- http_config
lua_package_path "$prefix/html/?.lua;;";
--- config
location /lua {
set_by_lua $res 'local foo = require "foo" return foo.go()' $arg_a $arg_b;
echo $res;
}
--- user_files
>>> foo.lua
module("foo", package.seeall)
function go()
return ngx.arg[1] + ngx.arg[2]
end
--- request
GET /lua?a=1&b=2
--- response_body
3
--- no_error_log
[error]
=== TEST 39: server scope (inline)
--- config
location /lua {
set $a "[$res]";
echo $a;
}
set_by_lua $res "return 1+1";
--- request
GET /lua
--- response_body
[2]
--- no_error_log
[error]
=== TEST 40: server if scope (inline)
--- config
location /lua {
set $a "[$res]";
echo $a;
}
if ($arg_name = "jim") {
set_by_lua $res "return 1+1";
}
--- request
GET /lua?name=jim
--- response_body
[2]
--- no_error_log
[error]
=== TEST 41: location if scope (inline)
--- config
location /lua {
if ($arg_name = "jim") {
set_by_lua $res "return 1+1";
set $a "[$res]";
echo $a;
}
}
--- request
GET /lua?name=jim
--- response_body
[2]
--- no_error_log
[error]
=== TEST 42: server scope (file)
--- config
location /lua {
set $a "[$res]";
echo $a;
}
set_by_lua_file $res html/a.lua;
--- user_files
>>> a.lua
return 1+1
--- request
GET /lua
--- response_body
[2]
--- no_error_log
[error]
=== TEST 43: server if scope (file)
--- config
location /lua {
set $a "[$res]";
echo $a;
}
if ($arg_name = "jim") {
set_by_lua_file $res html/a.lua;
}
--- request
GET /lua?name=jim
--- user_files
>>> a.lua
return 1+1
--- response_body
[2]
--- no_error_log
[error]
=== TEST 44: location if scope (file)
--- config
location /lua {
if ($arg_name = "jim") {
set_by_lua_file $res html/a.lua;
set $a "[$res]";
echo $a;
}
}
--- user_files
>>> a.lua
return 1+1
--- request
GET /lua?name=jim
--- response_body
[2]
--- no_error_log
[error]
=== TEST 45: backtrace
--- config
location /t {
set_by_lua $a '
function foo()
bar()
end
function bar()
error("something bad happened")
end
foo()
';
echo ok;
}
--- request
GET /t
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
something bad happened
stack traceback:
in function 'error'
in function 'bar'
in function 'foo'
=== TEST 46: Lua file does not exist
--- config
location /lua {
set_by_lua_file $a html/test2.lua;
}
--- user_files
>>> test.lua
v = ngx.var["request_uri"]
ngx.print("request_uri: ", v, "\n")
--- request
GET /lua?a=1&b=2
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log eval
qr/failed to load external Lua file ".*?test2\.lua": cannot open .*? No such file or directory/

View file

@ -1,837 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_on();
#workers(2);
#log_level('warn');
repeat_each(2);
#repeat_each(1);
plan tests => repeat_each() * (blocks() * 2 + 18);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: basic print
--- config
location /lua {
# NOTE: the newline escape sequence must be double-escaped, as nginx config
# parser will unescape first!
content_by_lua '
local ok, err = ngx.print("Hello, Lua!\\n")
if not ok then
ngx.log(ngx.ERR, "print failed: ", err)
end
';
}
--- request
GET /lua
--- response_body
Hello, Lua!
--- no_error_log
[error]
=== TEST 2: basic say
--- config
location /say {
# NOTE: the newline escape sequence must be double-escaped, as nginx config
# parser will unescape first!
content_by_lua '
local ok, err = ngx.say("Hello, Lua!")
if not ok then
ngx.log(ngx.ERR, "say failed: ", err)
return
end
local ok, err = ngx.say("Yay! ", 123)
if not ok then
ngx.log(ngx.ERR, "say failed: ", err)
return
end
';
}
--- request
GET /say
--- response_body
Hello, Lua!
Yay! 123
--- no_error_log
[error]
=== TEST 3: no ngx.echo
--- config
location /lua {
content_by_lua 'ngx.echo("Hello, Lua!\\n")';
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 4: variable
--- config
location /lua {
# NOTE: the newline escape sequence must be double-escaped, as nginx config
# parser will unescape first!
content_by_lua 'v = ngx.var["request_uri"] ngx.print("request_uri: ", v, "\\n")';
}
--- request
GET /lua?a=1&b=2
--- response_body
request_uri: /lua?a=1&b=2
=== TEST 5: variable (file)
--- config
location /lua {
content_by_lua_file html/test.lua;
}
--- user_files
>>> test.lua
v = ngx.var["request_uri"]
ngx.print("request_uri: ", v, "\n")
--- request
GET /lua?a=1&b=2
--- response_body
request_uri: /lua?a=1&b=2
=== TEST 6: calc expression
--- config
location /lua {
content_by_lua_file html/calc.lua;
}
--- user_files
>>> calc.lua
local function uri_unescape(uri)
local function convert(hex)
return string.char(tonumber("0x"..hex))
end
local s = string.gsub(uri, "%%([0-9a-fA-F][0-9a-fA-F])", convert)
return s
end
local function eval_exp(str)
return loadstring("return "..str)()
end
local exp_str = ngx.var["arg_exp"]
-- print("exp: '", exp_str, "'\n")
local status, res
status, res = pcall(uri_unescape, exp_str)
if not status then
ngx.print("error: ", res, "\n")
return
end
status, res = pcall(eval_exp, res)
if status then
ngx.print("result: ", res, "\n")
else
ngx.print("error: ", res, "\n")
end
--- request
GET /lua?exp=1%2B2*math.sin(3)%2Fmath.exp(4)-math.sqrt(2)
--- response_body
result: -0.4090441561579
=== TEST 7: read $arg_xxx
--- config
location = /lua {
content_by_lua 'who = ngx.var.arg_who
ngx.print("Hello, ", who, "!")';
}
--- request
GET /lua?who=agentzh
--- response_body chomp
Hello, agentzh!
=== TEST 8: capture location
--- config
location /other {
echo "hello, world";
}
location /lua {
content_by_lua 'res = ngx.location.capture("/other"); ngx.print("status=", res.status, " "); ngx.print("body=", res.body)';
}
--- request
GET /lua
--- response_body
status=200 body=hello, world
ei= TEST 9: capture non-existed location
--- config
location /lua {
content_by_lua 'res = ngx.location.capture("/other"); ngx.print("status=", res.status)';
}
--- request
GET /lua
--- response_body: status=404
=== TEST 9: invalid capture location (not as expected...)
--- config
location /lua {
content_by_lua 'res = ngx.location.capture("*(#*"); ngx.say("res=", res.status)';
}
--- request
GET /lua
--- response_body
res=404
=== TEST 10: nil is "nil"
--- config
location /lua {
content_by_lua 'ngx.say(nil)';
}
--- request
GET /lua
--- response_body
nil
=== TEST 11: write boolean
--- config
location /lua {
content_by_lua 'ngx.say(true, " ", false)';
}
--- request
GET /lua
--- response_body
true false
=== TEST 12: bad argument type to ngx.location.capture
--- config
location /lua {
content_by_lua 'ngx.location.capture(nil)';
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 13: capture location (default 0);
--- config
location /recur {
content_by_lua '
local num = tonumber(ngx.var.arg_num) or 0;
ngx.print("num is: ", num, "\\n");
if (num > 0) then
res = ngx.location.capture("/recur?num="..tostring(num - 1));
ngx.print("status=", res.status, " ");
ngx.print("body=", res.body, "\\n");
else
ngx.print("end\\n");
end
';
}
--- request
GET /recur
--- response_body
num is: 0
end
=== TEST 14: capture location
--- config
location /recur {
content_by_lua '
local num = tonumber(ngx.var.arg_num) or 0;
ngx.print("num is: ", num, "\\n");
if (num > 0) then
res = ngx.location.capture("/recur?num="..tostring(num - 1));
ngx.print("status=", res.status, " ");
ngx.print("body=", res.body);
else
ngx.print("end\\n");
end
';
}
--- request
GET /recur?num=3
--- response_body
num is: 3
status=200 body=num is: 2
status=200 body=num is: 1
status=200 body=num is: 0
end
=== TEST 15: setting nginx variables from within Lua
--- config
location /set {
set $a "";
content_by_lua 'ngx.var.a = 32; ngx.say(ngx.var.a)';
add_header Foo $a;
}
--- request
GET /set
--- response_headers
Foo: 32
--- response_body
32
=== TEST 16: nginx quote sql string 1
--- config
location /set {
set $a 'hello\n\r\'"\\';
content_by_lua 'ngx.say(ngx.quote_sql_str(ngx.var.a))';
}
--- request
GET /set
--- response_body
'hello\n\r\'\"\\'
=== TEST 17: nginx quote sql string 2
--- config
location /set {
set $a "hello\n\r'\"\\";
content_by_lua 'ngx.say(ngx.quote_sql_str(ngx.var.a))';
}
--- request
GET /set
--- response_body
'hello\n\r\'\"\\'
=== TEST 18: use dollar
--- config
location /set {
content_by_lua '
local s = "hello 112";
ngx.say(string.find(s, "%d+$"))';
}
--- request
GET /set
--- response_body
79
=== TEST 19: subrequests do not share variables of main requests by default
--- config
location /sub {
echo $a;
}
location /parent {
set $a 12;
content_by_lua 'res = ngx.location.capture("/sub"); ngx.print(res.body)';
}
--- request
GET /parent
--- response_body eval: "\n"
=== TEST 20: subrequests can share variables of main requests
--- config
location /sub {
echo $a;
}
location /parent {
set $a 12;
content_by_lua '
res = ngx.location.capture(
"/sub",
{ share_all_vars = true }
);
ngx.print(res.body)
';
}
--- request
GET /parent
--- response_body
12
=== TEST 21: main requests use subrequests' variables
--- config
location /sub {
set $a 12;
}
location /parent {
content_by_lua '
res = ngx.location.capture("/sub", { share_all_vars = true });
ngx.say(ngx.var.a)
';
}
--- request
GET /parent
--- response_body
12
=== TEST 22: main requests do NOT use subrequests' variables
--- config
location /sub {
set $a 12;
}
location /parent {
content_by_lua '
res = ngx.location.capture("/sub", { share_all_vars = false });
ngx.say(ngx.var.a)
';
}
--- request
GET /parent
--- response_body_like eval: "\n"
=== TEST 23: capture location headers
--- config
location /other {
default_type 'foo/bar';
echo "hello, world";
}
location /lua {
content_by_lua '
res = ngx.location.capture("/other");
ngx.say("type: ", res.header["Content-Type"]);
';
}
--- request
GET /lua
--- response_body
type: foo/bar
=== TEST 24: capture location multi-value headers
--- config
location /other {
#echo "hello, world";
content_by_lua '
ngx.header["Set-Cookie"] = {"a", "hello, world", "foo"}
local ok, err = ngx.eof()
if not ok then
ngx.log(ngx.ERR, "eof failed: ", err)
return
end
';
}
location /lua {
content_by_lua '
res = ngx.location.capture("/other");
ngx.say("type: ", type(res.header["Set-Cookie"]));
ngx.say("len: ", #res.header["Set-Cookie"]);
ngx.say("value: ", table.concat(res.header["Set-Cookie"], "|"))
';
}
--- request
GET /lua
--- response_body
type: table
len: 3
value: a|hello, world|foo
--- no_error_log
[error]
=== TEST 25: capture location headers
--- config
location /other {
default_type 'foo/bar';
content_by_lua '
ngx.header.Bar = "Bah";
';
}
location /lua {
content_by_lua '
res = ngx.location.capture("/other");
ngx.say("type: ", res.header["Content-Type"]);
ngx.say("Bar: ", res.header["Bar"]);
';
}
--- request
GET /lua
--- response_body
type: foo/bar
Bar: Bah
=== TEST 26: capture location headers
--- config
location /other {
default_type 'foo/bar';
content_by_lua '
ngx.header.Bar = "Bah";
ngx.header.Bar = nil;
';
}
location /lua {
content_by_lua '
res = ngx.location.capture("/other");
ngx.say("type: ", res.header["Content-Type"]);
ngx.say("Bar: ", res.header["Bar"] or "nil");
';
}
--- request
GET /lua
--- response_body
type: foo/bar
Bar: nil
=== TEST 27: HTTP 1.0 response
--- config
location /lua {
content_by_lua '
data = "hello, world"
-- ngx.header["Content-Length"] = #data
-- ngx.header.content_length = #data
ngx.print(data)
';
}
location /main {
proxy_pass http://127.0.0.1:$server_port/lua;
}
--- request
GET /main
--- response_headers
Content-Length: 12
--- response_body chop
hello, world
=== TEST 28: multiple eof
--- config
location /lua {
content_by_lua '
ngx.say("Hi")
local ok, err = ngx.eof()
if not ok then
ngx.log(ngx.WARN, "eof failed: ", err)
return
end
ok, err = ngx.eof()
if not ok then
ngx.log(ngx.WARN, "eof failed: ", err)
return
end
';
}
--- request
GET /lua
--- response_body
Hi
--- no_error_log
[error]
--- error_log
eof failed: seen eof
=== TEST 29: nginx vars in script path
--- config
location ~ ^/lua/(.+)$ {
content_by_lua_file html/$1.lua;
}
--- user_files
>>> calc.lua
local a,b = ngx.var.arg_a, ngx.var.arg_b
ngx.say(a+b)
--- request
GET /lua/calc?a=19&b=81
--- response_body
100
=== TEST 30: nginx vars in script path
--- config
location ~ ^/lua/(.+)$ {
content_by_lua_file html/$1.lua;
}
location /main {
echo_location /lua/sum a=3&b=2;
echo_location /lua/diff a=3&b=2;
}
--- user_files
>>> sum.lua
local a,b = ngx.var.arg_a, ngx.var.arg_b
ngx.say(a+b)
>>> diff.lua
local a,b = ngx.var.arg_a, ngx.var.arg_b
ngx.say(a-b)
--- request
GET /main
--- response_body
5
1
=== TEST 31: basic print (HEAD + HTTP 1.1)
--- config
location /lua {
# NOTE: the newline escape sequence must be double-escaped, as nginx config
# parser will unescape first!
content_by_lua 'ngx.print("Hello, Lua!\\n")';
}
--- request
HEAD /lua
--- response_body
=== TEST 32: basic print (HEAD + HTTP 1.0)
--- config
location /lua {
# NOTE: the newline escape sequence must be double-escaped, as nginx config
# parser will unescape first!
content_by_lua '
ngx.print("Hello, Lua!\\n")
';
}
--- request
HEAD /lua HTTP/1.0
--- response_headers
!Content-Length
--- response_body
=== TEST 33: headers_sent & HEAD
--- config
location /lua {
content_by_lua '
ngx.say(ngx.headers_sent)
local ok, err = ngx.flush()
if not ok then
ngx.log(ngx.WARN, "failed to flush: ", err)
return
end
ngx.say(ngx.headers_sent)
';
}
--- request
HEAD /lua
--- response_body
--- no_error_log
[error]
--- error_log
failed to flush: header only
=== TEST 34: HEAD & ngx.say
--- config
location /lua {
content_by_lua '
ngx.send_headers()
local ok, err = ngx.say(ngx.headers_sent)
if not ok then
ngx.log(ngx.WARN, "failed to say: ", err)
return
end
';
}
--- request
HEAD /lua
--- response_body
--- no_error_log
[error]
--- error_log
failed to say: header only
=== TEST 35: ngx.eof before ngx.say
--- config
location /lua {
content_by_lua '
local ok, err = ngx.eof()
if not ok then
ngx.log(ngx.ERR, "eof failed: ", err)
return
end
ok, err = ngx.say(ngx.headers_sent)
if not ok then
ngx.log(ngx.WARN, "failed to say: ", err)
return
end
';
}
--- request
GET /lua
--- response_body
--- no_error_log
[error]
--- error_log
failed to say: seen eof
=== TEST 36: headers_sent + GET
--- config
location /lua {
content_by_lua '
-- print("headers sent: ", ngx.headers_sent)
ngx.say(ngx.headers_sent)
ngx.say(ngx.headers_sent)
-- ngx.flush()
ngx.say(ngx.headers_sent)
';
}
--- request
GET /lua
--- response_body
false
true
true
=== TEST 37: HTTP 1.0 response with Content-Length
--- config
location /lua {
content_by_lua '
data = "hello,\\nworld\\n"
ngx.header["Content-Length"] = #data
ngx.say("hello,")
ngx.flush()
-- ngx.location.capture("/sleep")
ngx.say("world")
';
}
location /sleep {
echo_sleep 2;
}
location /main {
proxy_pass http://127.0.0.1:$server_port/lua;
}
--- request
GET /main
--- response_headers
Content-Length: 13
--- response_body
hello,
world
--- timeout: 5
=== TEST 38: ngx.print table arguments (github issue #54)
--- config
location /t {
content_by_lua 'ngx.print({10, {0, 5}, 15}, 32)';
}
--- request
GET /t
--- response_body chop
10051532
=== TEST 39: ngx.say table arguments (github issue #54)
--- config
location /t {
content_by_lua 'ngx.say({10, {0, "5"}, 15}, 32)';
}
--- request
GET /t
--- response_body
10051532
=== TEST 40: Lua file does not exist
--- config
location /lua {
content_by_lua_file html/test2.lua;
}
--- user_files
>>> test.lua
v = ngx.var["request_uri"]
ngx.print("request_uri: ", v, "\n")
--- request
GET /lua?a=1&b=2
--- response_body_like: 404 Not Found
--- error_code: 404
--- error_log eval
qr/failed to load external Lua file ".*?test2\.lua": cannot open .*? No such file or directory/
=== TEST 41: .lua file with shebang
--- config
location /lua {
content_by_lua_file html/test.lua;
}
--- user_files
>>> test.lua
#!/bin/lua
ngx.say("line ", debug.getinfo(1).currentline)
--- request
GET /lua?a=1&b=2
--- response_body
line 3
--- no_error_log
[error]
=== TEST 42: syntax error in inlined Lua code
--- config
location /lua {
content_by_lua 'for end';
}
--- request
GET /lua
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log eval
qr/failed to load inlined Lua code: /

View file

@ -1,130 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
repeat_each(1);
plan tests => blocks() * repeat_each() * 2;
#$ENV{LUA_PATH} = $ENV{HOME} . '/work/JSON4Lua-0.9.30/json/?.lua';
no_long_string();
run_tests();
__DATA__
=== TEST 1: syntax error in lua code chunk
--- config
location /lua {
set_by_lua $res "local a
a = a+;
return a";
echo $res;
}
--- request
GET /lua
--- error_code: 500
--- response_body_like: 500 Internal Server Error
=== TEST 2: syntax error in lua file
--- config
location /lua {
set_by_lua_file $res 'html/test.lua';
echo $res;
}
--- user_files
>>> test.lua
local a
a = 3 +;
return a
--- request
GET /lua
--- error_code: 500
--- response_body_like: 500 Internal Server Error
=== TEST 3: syntax error in lua file (from Guang Feng)
--- config
location /lua {
set $res '[{"a":32},{"b":64}]';
#set $res '[{"friend_userid":1750146},{"friend_userid":1750150},{"friend_userid":1750153},{"friend_userid":1750166},{"friend_userid":1750181},{"friend_userid":1750186},{"friend_userid":1750195},{"friend_userid":1750232}]';
set_by_lua_file $list 'html/test.lua' $res;
#set_by_lua_file $list 'html/feed.lua' $res;
echo $list;
}
--- user_files
>>> test.lua
-- local j = require('json')
local p = ngx.arg[1]
return p
>>> feed.lua
local s = require("json")
local function explode(d,p)
local t, ll
t={}
ll=0
if(#p == 1) then return p end
while true do
l=string.find(p,d,ll+1,true)
if l~=nil then
table.insert(t, string.sub(p,ll,l-1))
ll=l+1
else
table.insert(t, string.sub(p,ll))
break
end
end
return t
end
local a = explode(',', string.sub(ngx.arg[1], 2, -1))
local x = {}
for i,v in ipairs(a) do table.insert(x,s.decode(v).friend_userid) end
return table.concat(x,',')
--- request
GET /lua
--- response_body
[{"a":32},{"b":64}]
=== TEST 4: 500 in subrequest
--- config
location /main {
content_by_lua '
local res = ngx.location.capture("/err")
ngx.say(res.status);
';
}
location /err {
return 500;
}
--- request
GET /main
--- response_body
500
=== TEST 5: drizzle_pass 500 in subrequest
--- config
location /main {
content_by_lua '
local res = ngx.location.capture("/err")
ngx.say(res.status);
';
}
location /err {
set $back 'blah-blah';
drizzle_pass $back;
}
--- request
GET /main
--- response_body
500

View file

@ -1,211 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#log_level('warn');
#master_on();
#repeat_each(120);
repeat_each(2);
plan tests => blocks() * repeat_each() * 2;
our $HtmlDir = html_dir;
#warn $html_dir;
#$ENV{LUA_PATH} = "$html_dir/?.lua";
#no_diff();
no_long_string();
run_tests();
__DATA__
=== TEST 1: sanity
--- http_config eval
"lua_package_path '$::HtmlDir/?.lua;./?.lua';"
--- config
location /main {
echo_location /load;
echo_location /check;
echo_location /check;
}
location /load {
content_by_lua '
package.loaded.foo = nil;
local foo = require "foo";
foo.hi()
';
}
location /check {
content_by_lua '
local foo = package.loaded.foo
if foo then
ngx.say("found")
foo.hi()
else
ngx.say("not found")
end
';
}
--- request
GET /main
--- user_files
>>> foo.lua
module(..., package.seeall);
ngx.say("loading");
function hi ()
ngx.say("hello, foo")
end;
--- response_body
loading
hello, foo
found
hello, foo
found
hello, foo
=== TEST 2: sanity
--- http_config eval
"lua_package_cpath '$::HtmlDir/?.so';"
--- config
location /main {
content_by_lua '
ngx.print(package.cpath);
';
}
--- request
GET /main
--- user_files
--- response_body_like: ^[^;]+/servroot/html/\?.so$
=== TEST 3: expand default path (after)
--- http_config eval
"lua_package_path '$::HtmlDir/?.lua;;';"
--- config
location /main {
content_by_lua '
ngx.print(package.path);
';
}
--- request
GET /main
--- response_body_like: ^[^;]+/servroot/html/\?.lua;.+\.lua;$
=== TEST 4: expand default cpath (after)
--- http_config eval
"lua_package_cpath '$::HtmlDir/?.so;;';"
--- config
location /main {
content_by_lua '
ngx.print(package.cpath);
';
}
--- request
GET /main
--- response_body_like: ^[^;]+/servroot/html/\?.so;.+\.so;$
=== TEST 5: expand default path (before)
--- http_config eval
"lua_package_path ';;$::HtmlDir/?.lua';"
--- config
location /main {
content_by_lua '
ngx.print(package.path);
';
}
--- request
GET /main
--- response_body_like: ^.+\.lua;[^;]+/servroot/html/\?.lua$
=== TEST 6: expand default cpath (before)
--- http_config eval
"lua_package_cpath ';;$::HtmlDir/?.so';"
--- config
location /main {
content_by_lua '
ngx.print(package.cpath);
';
}
--- request
GET /main
--- response_body_like: ^.+\.so;[^;]+/servroot/html/\?.so$
=== TEST 7: require "ngx" (content_by_lua)
--- config
location /ngx {
content_by_lua '
local ngx = require "ngx"
ngx.say("hello, world")
';
}
--- request
GET /ngx
--- response_body
hello, world
=== TEST 8: require "ngx" (set_by_lua)
--- config
location /ngx {
set_by_lua $res '
local ngx = require "ngx"
return ngx.escape_uri(" ")
';
echo $res;
}
--- request
GET /ngx
--- response_body
%20
=== TEST 9: require "ndk" (content_by_lua)
--- config
location /ndk {
content_by_lua '
local ndk = require "ndk"
local res = ndk.set_var.set_escape_uri(" ")
ngx.say(res)
';
}
--- request
GET /ndk
--- response_body
%20
=== TEST 10: require "ndk" (set_by_lua)
--- config
location /ndk {
set_by_lua $res '
local ndk = require "ndk"
return ndk.set_var.set_escape_uri(" ")
';
echo $res;
}
--- request
GET /ndk
--- response_body
%20

View file

@ -1,727 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#repeat_each(20000);
repeat_each(2);
#master_on();
#workers(1);
#log_level('debug');
#log_level('warn');
#worker_connections(1024);
plan tests => repeat_each() * (blocks() * 3 + 2);
$ENV{TEST_NGINX_MEMCACHED_PORT} ||= 11211;
$ENV{TEST_NGINX_MYSQL_PORT} ||= 3306;
our $LuaCpath = $ENV{LUA_CPATH} ||
'/usr/local/openresty-debug/lualib/?.so;/usr/local/openresty/lualib/?.so;;';
#$ENV{LUA_PATH} = $ENV{HOME} . '/work/JSON4Lua-0.9.30/json/?.lua';
no_long_string();
run_tests();
__DATA__
=== TEST 1: throw 403
--- config
location /lua {
content_by_lua "ngx.exit(403);ngx.say('hi')";
}
--- request
GET /lua
--- error_code: 403
--- response_body_like: 403 Forbidden
--- no_error_log
[error]
=== TEST 2: throw 404
--- config
location /lua {
content_by_lua "ngx.exit(404);ngx.say('hi');";
}
--- request
GET /lua
--- error_code: 404
--- response_body_like: 404 Not Found
--- no_error_log
[error]
=== TEST 3: throw 404 after sending the header and partial body
--- config
location /lua {
content_by_lua "ngx.say('hi');ngx.exit(404);ngx.say(', you')";
}
--- request
GET /lua
--- error_log
attempt to set status 404 via ngx.exit after sending out the response status 200
--- no_error_log
alert
--- response_body
hi
=== TEST 4: working with ngx_auth_request (succeeded)
--- config
location /auth {
content_by_lua "
if ngx.var.user == 'agentzh' then
ngx.eof();
else
ngx.exit(403)
end";
}
location /api {
set $user $arg_user;
auth_request /auth;
echo "Logged in";
}
--- request
GET /api?user=agentzh
--- error_code: 200
--- response_body
Logged in
--- no_error_log
[error]
=== TEST 5: working with ngx_auth_request (failed)
--- config
location /auth {
content_by_lua "
if ngx.var.user == 'agentzh' then
ngx.eof();
else
ngx.exit(403)
end";
}
location /api {
set $user $arg_user;
auth_request /auth;
echo "Logged in";
}
--- request
GET /api?user=agentz
--- error_code: 403
--- response_body_like: 403 Forbidden
--- no_error_log
[error]
=== TEST 6: working with ngx_auth_request (simplest form, w/o ngx_memc)
--- http_config eval
"
lua_package_cpath '$::LuaCpath';
upstream backend {
drizzle_server 127.0.0.1:\$TEST_NGINX_MYSQL_PORT protocol=mysql
dbname=ngx_test user=ngx_test password=ngx_test;
drizzle_keepalive max=300 mode=single overflow=ignore;
}
"
--- config
location /memc {
internal;
set $memc_key $arg_key;
set $memc_exptime $arg_exptime;
memc_pass 127.0.0.1:$TEST_NGINX_MEMCACHED_PORT;
}
location /conv-uid-mysql {
internal;
set $key "conv-uid-$arg_uid";
#srcache_fetch GET /memc key=$key;
#srcache_store PUT /memc key=$key;
default_type 'application/json';
drizzle_query "select new_uid as uid from conv_uid where old_uid=$arg_uid";
drizzle_pass backend;
rds_json on;
}
location /conv-uid {
internal;
content_by_lua_file 'html/foo.lua';
}
location /api {
set $uid $arg_uid;
auth_request /conv-uid;
echo "Logged in $uid";
}
--- user_files
>>> foo.lua
local cjson = require('cjson');
local old_uid = ngx.var.uid
-- print('about to run sr')
local res = ngx.location.capture('/conv-uid-mysql?uid=' .. old_uid)
if (res.status ~= ngx.HTTP_OK) then
ngx.exit(res.status)
end
-- print('just have run sr: ' .. res.body)
res = cjson.decode(res.body)
if (not res or not res[1] or not res[1].uid or
not string.match(res[1].uid, '^%d+$')) then
ngx.exit(ngx.HTTP_INTERNAL_SERVER_ERROR)
end
ngx.var.uid = res[1].uid;
-- print('done')
--- request
GET /api?uid=32
--- response_body
Logged in 56
--- no_error_log
[error]
=== TEST 7: working with ngx_auth_request (simplest form)
--- http_config eval
"
lua_package_cpath '$::LuaCpath';
upstream backend {
drizzle_server 127.0.0.1:\$TEST_NGINX_MYSQL_PORT protocol=mysql
dbname=ngx_test user=ngx_test password=ngx_test;
drizzle_keepalive max=300 mode=single overflow=ignore;
}
"
--- config
location /memc {
internal;
set $memc_key $arg_key;
set $memc_exptime $arg_exptime;
memc_pass 127.0.0.1:$TEST_NGINX_MEMCACHED_PORT;
}
location /conv-uid-mysql {
internal;
set $key "conv-uid-$arg_uid";
#srcache_fetch GET /memc key=$key;
#srcache_store PUT /memc key=$key;
default_type 'application/json';
drizzle_query "select new_uid as uid from conv_uid where old_uid=$arg_uid";
drizzle_pass backend;
rds_json on;
}
location /conv-uid {
internal;
content_by_lua_file 'html/foo.lua';
}
location /api {
set $uid $arg_uid;
auth_request /conv-uid;
echo "Logged in $uid";
}
--- user_files
>>> foo.lua
local cjson = require('cjson');
local old_uid = ngx.var.uid
-- print('about to run sr')
local res = ngx.location.capture('/conv-uid-mysql?uid=' .. old_uid)
-- print('just have run sr' .. res.body)
if (res.status ~= ngx.HTTP_OK) then
ngx.exit(res.status)
end
res = cjson.decode(res.body)
if (not res or not res[1] or not res[1].uid or
not string.match(res[1].uid, '^%d+$')) then
ngx.exit(ngx.HTTP_INTERNAL_SERVER_ERROR)
end
ngx.var.uid = res[1].uid;
-- print('done')
--- request
GET /api?uid=32
--- response_body
Logged in 56
--- no_error_log
[error]
=== TEST 8: working with ngx_auth_request
--- http_config eval
"
lua_package_cpath '$::LuaCpath';
upstream backend {
drizzle_server 127.0.0.1:\$TEST_NGINX_MYSQL_PORT protocol=mysql
dbname=ngx_test user=ngx_test password=ngx_test;
drizzle_keepalive max=300 mode=single overflow=ignore;
}
upstream memc_a {
server 127.0.0.1:\$TEST_NGINX_MEMCACHED_PORT;
}
upstream memc_b {
server 127.0.0.1:\$TEST_NGINX_MEMCACHED_PORT;
}
upstream_list memc_cluster memc_a memc_b;
"
--- config
location /memc {
internal;
set $memc_key $arg_key;
set $memc_exptime $arg_exptime;
set_hashed_upstream $backend memc_cluster $arg_key;
memc_pass $backend;
}
location /conv-uid-mysql {
internal;
set $key "conv-uid-$arg_uid";
#srcache_fetch GET /memc key=$key;
#srcache_store PUT /memc key=$key;
default_type 'application/json';
drizzle_query "select new_uid as uid from conv_uid where old_uid=$arg_uid";
drizzle_pass backend;
rds_json on;
}
location /conv-uid {
internal;
content_by_lua_file 'html/foo.lua';
}
location /api {
set $uid $arg_uid;
auth_request /conv-uid;
echo "Logged in $uid";
}
--- user_files
>>> foo.lua
local cjson = require('cjson');
local old_uid = ngx.var.uid
-- print('about to run sr')
local res = ngx.location.capture('/conv-uid-mysql?uid=' .. old_uid)
-- print('just have run sr' .. res.body)
if (res.status ~= ngx.HTTP_OK) then
ngx.exit(res.status)
end
res = cjson.decode(res.body)
if (not res or not res[1] or not res[1].uid or
not string.match(res[1].uid, '^%d+$')) then
ngx.exit(ngx.HTTP_INTERNAL_SERVER_ERROR)
end
ngx.var.uid = res[1].uid;
-- print('done')
--- request
GET /api?uid=32
--- response_body
Logged in 56
--- no_error_log
[error]
--- timeout: 5
=== TEST 9: working with ngx_auth_request
--- http_config
upstream backend {
drizzle_server 127.0.0.1:$TEST_NGINX_MYSQL_PORT protocol=mysql
dbname=ngx_test user=ngx_test password=ngx_test;
drizzle_keepalive max=300 mode=single overflow=ignore;
}
upstream memc_a {
server 127.0.0.1:$TEST_NGINX_MEMCACHED_PORT;
keepalive 300;
}
#upstream_list memc_cluster memc_a memc_b;
--- config
location /memc {
internal;
set $memc_key $arg_key;
set $memc_exptime $arg_exptime;
#set_hashed_upstream $backend memc_cluster $arg_key;
memc_pass memc_a;
}
location /conv-mysql {
internal;
set $key "conv-uri-$query_string";
#srcache_fetch GET /memc key=$key;
#srcache_store PUT /memc key=$key;
default_type 'application/json';
set_quote_sql_str $seo_uri $query_string;
drizzle_query "select url from my_url_map where seo_url=$seo_uri";
drizzle_pass backend;
rds_json on;
}
location /conv-uid {
internal;
content_by_lua_file 'html/foo.lua';
}
location /baz {
set $my_uri $uri;
auth_request /conv-uid;
echo_exec /jump $my_uri;
}
location /jump {
internal;
rewrite ^ $query_string? redirect;
}
--- user_files
>>> foo.lua
local cjson = require('cjson');
local seo_uri = ngx.var.my_uri
-- print('about to run sr')
local res = ngx.location.capture('/conv-mysql?' .. seo_uri)
if (res.status ~= ngx.HTTP_OK) then
ngx.exit(res.status)
end
res = cjson.decode(res.body)
if (not res or not res[1] or not res[1].url) then
ngx.exit(ngx.HTTP_INTERNAL_SERVER_ERROR)
end
ngx.var.my_uri = res[1].url;
-- print('done')
--- request
GET /baz
--- response_body_like: 302
--- error_code: 302
--- response_headers
Location: http://localhost:$ServerPort/foo/bar
--- SKIP
=== TEST 10: throw 0
--- config
location /lua {
content_by_lua "ngx.say('Hi'); ngx.eof(); ngx.exit(0);ngx.say('world')";
}
--- request
GET /lua
--- error_code: 200
--- response_body
Hi
--- no_error_log
[error]
=== TEST 11: pcall safe
--- config
location /lua {
content_by_lua '
function f ()
ngx.say("hello")
ngx.exit(200)
end
pcall(f)
ngx.say("world")
';
}
--- request
GET /lua
--- error_code: 200
--- response_body
hello
--- no_error_log
[error]
=== TEST 12: 501 Method Not Implemented
--- config
location /lua {
content_by_lua '
ngx.exit(501)
';
}
--- request
GET /lua
--- error_code: 501
--- response_body_like: 501 (?:Method )?Not Implemented
--- no_error_log
[error]
=== TEST 13: 501 Method Not Implemented
--- config
location /lua {
content_by_lua '
ngx.exit(ngx.HTTP_METHOD_NOT_IMPLEMENTED)
';
}
--- request
GET /lua
--- error_code: 501
--- response_body_like: 501 (?:Method )?Not Implemented
--- no_error_log
[error]
=== TEST 14: throw 403 after sending out headers with 200
--- config
location /lua {
rewrite_by_lua '
ngx.send_headers()
ngx.say("Hello World")
ngx.exit(403)
';
}
--- request
GET /lua
--- response_body
Hello World
--- error_log
attempt to set status 403 via ngx.exit after sending out the response status 200
--- no_error_log
[alert]
=== TEST 15: throw 403 after sending out headers with 403
--- config
location /lua {
rewrite_by_lua '
ngx.status = 403
ngx.send_headers()
ngx.say("Hello World")
ngx.exit(403)
';
}
--- request
GET /lua
--- response_body
Hello World
--- error_code: 403
--- no_error_log
[error]
[alert]
=== TEST 16: throw 403 after sending out headers with 403 (HTTP 1.0 buffering)
--- config
location /t {
rewrite_by_lua '
ngx.status = 403
ngx.say("Hello World")
ngx.exit(403)
';
}
--- request
GET /t HTTP/1.0
--- response_body
Hello World
--- error_code: 403
--- no_error_log
[error]
[alert]
=== TEST 17: throw 444 after sending out responses (HTTP 1.0)
--- config
location /lua {
content_by_lua "
ngx.say('ok');
return ngx.exit(444)
";
}
--- request
GET /lua HTTP/1.0
--- ignore_response
--- log_level: debug
--- no_error_log
lua sending HTTP 1.0 response headers
[error]
=== TEST 18: throw 499 after sending out responses (HTTP 1.0)
--- config
location /lua {
content_by_lua "
ngx.say('ok');
return ngx.exit(499)
";
}
--- request
GET /lua HTTP/1.0
--- ignore_response
--- log_level: debug
--- no_error_log
lua sending HTTP 1.0 response headers
[error]
=== TEST 19: throw 408 after sending out responses (HTTP 1.0)
--- config
location /lua {
content_by_lua "
ngx.say('ok');
return ngx.exit(408)
";
}
--- request
GET /lua HTTP/1.0
--- ignore_response
--- log_level: debug
--- no_error_log
lua sending HTTP 1.0 response headers
[error]
=== TEST 20: exit(201) with custom response body
--- config
location = /t {
content_by_lua "
ngx.status = 201
ngx.say('ok');
return ngx.exit(201)
";
}
--- request
GET /t
--- ignore_response
--- log_level: debug
--- no_error_log
lua sending HTTP 1.0 response headers
[error]
[alert]
=== TEST 21: exit 403 in header filter
--- config
location = /t {
content_by_lua "ngx.say('hi');";
header_filter_by_lua '
return ngx.exit(403)
';
}
--- request
GET /t
--- error_code: 403
--- response_body_like: 403 Forbidden
--- no_error_log
[error]
=== TEST 22: exit 201 in header filter
--- config
lingering_close always;
location = /t {
content_by_lua "ngx.say('hi');";
header_filter_by_lua '
return ngx.exit(201)
';
}
--- request
GET /t
--- error_code: 201
--- response_body
--- no_error_log
[error]
=== TEST 23: exit both in header filter and content handler
--- config
location = /t {
content_by_lua "ngx.status = 201 ngx.say('hi') ngx.exit(201)";
header_filter_by_lua '
return ngx.exit(201)
';
}
--- request
GET /t
--- error_code: 201
--- stap2
/*
F(ngx_http_send_header) {
printf("=== %d\n", $r->headers_out->status)
print_ubacktrace()
}
*/
F(ngx_http_lua_header_filter_inline) {
printf("=== %d\n", $r->headers_out->status)
print_ubacktrace()
}
F(ngx_http_lua_header_filter_by_chunk).return {
if ($return == -1) {
printf("====== header filter by chunk\n")
print_ubacktrace()
}
}
--- stap_out
--- response_body
--- no_error_log
[error]
[alert]
=== TEST 24: exit 444 in header filter
--- config
location = /t {
content_by_lua "ngx.say('hello world');";
header_filter_by_lua '
return ngx.exit(444)
';
}
--- request
GET /t
--- error_code: 444
--- response_body
--- no_error_log
[error]

View file

@ -1,184 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
repeat_each(2);
#repeat_each(1);
plan tests => repeat_each() * (blocks() * 2 + 1);
no_long_string();
run_tests();
__DATA__
=== TEST 1: escape uri in set_by_lua
--- config
location /escape {
set_by_lua $res "return ngx.escape_uri('a 你')";
echo $res;
}
--- request
GET /escape
--- response_body
a%20%E4%BD%A0
=== TEST 2: unescape uri in set_by_lua
--- config
location /unescape {
set_by_lua $res "return ngx.unescape_uri('a%20%e4%bd%a0')";
echo $res;
}
--- request
GET /unescape
--- response_body
a
=== TEST 3: escape uri in content_by_lua
--- config
location /escape {
content_by_lua "ngx.say(ngx.escape_uri('a 你'))";
}
--- request
GET /escape
--- response_body
a%20%E4%BD%A0
=== TEST 4: unescape uri in content_by_lua
--- config
location /unescape {
content_by_lua "ngx.say(ngx.unescape_uri('a%20%e4%bd%a0'))";
}
--- request
GET /unescape
--- response_body
a
=== TEST 5: escape uri in set_by_lua
--- config
location /escape {
set_by_lua $res "return ngx.escape_uri('a+b')";
echo $res;
}
--- request
GET /escape
--- response_body
a%2Bb
=== TEST 6: escape uri in set_by_lua
--- config
location /escape {
set_by_lua $res "return ngx.escape_uri('\"a/b={}:<>;&[]\\\\^')";
echo $res;
}
--- request
GET /escape
--- response_body
%22a%2Fb%3D%7B%7D%3A%3C%3E%3B%26%5B%5D%5C%5E
=== TEST 7: escape uri in set_by_lua
--- config
location /escape {
echo hello;
header_filter_by_lua '
ngx.header.baz = ngx.escape_uri(" ")
';
}
--- request
GET /escape
--- response_headers
baz: %20
--- response_body
hello
=== TEST 8: escape a string that cannot be escaped
--- config
location /escape {
set_by_lua $res "return ngx.escape_uri('abc')";
echo $res;
}
--- request
GET /escape
--- response_body
abc
=== TEST 9: escape an empty string that cannot be escaped
--- config
location /escape {
set_by_lua $res "return ngx.escape_uri('')";
echo $res;
}
--- request
GET /escape
--- response_body eval: "\n"
=== TEST 10: escape nil
--- config
location /escape {
set_by_lua $res "return ngx.escape_uri(nil)";
echo "[$res]";
}
--- request
GET /escape
--- response_body
[]
=== TEST 11: escape numbers
--- config
location /escape {
set_by_lua $res "return ngx.escape_uri(32)";
echo "[$res]";
}
--- request
GET /escape
--- response_body
[32]
=== TEST 12: unescape nil
--- config
location = /t {
set_by_lua $res "return ngx.unescape_uri(nil)";
echo "[$res]";
}
--- request
GET /t
--- response_body
[]
=== TEST 13: unescape numbers
--- config
location = /t {
set_by_lua $res "return ngx.unescape_uri(32)";
echo "[$res]";
}
--- request
GET /t
--- response_body
[32]

View file

@ -1,103 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('warn');
repeat_each(2);
plan tests => repeat_each() * (blocks() * 2);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: set md5 hello
--- config
location = /md5 {
content_by_lua 'ngx.say(ngx.md5("hello"))';
}
--- request
GET /md5
--- response_body
5d41402abc4b2a76b9719d911017c592
=== TEST 2: nil string to ngx.md5
--- config
location = /md5 {
content_by_lua 'ngx.say(ngx.md5(nil))';
}
--- request
GET /md5
--- response_body
d41d8cd98f00b204e9800998ecf8427e
=== TEST 3: null string to ngx.md5
--- config
location /md5 {
content_by_lua 'ngx.say(ngx.md5(""))';
}
--- request
GET /md5
--- response_body
d41d8cd98f00b204e9800998ecf8427e
=== TEST 4: use ngx.md5 in set_by_lua
--- config
location = /md5 {
set_by_lua $a 'return ngx.md5("hello")';
echo $a;
}
--- request
GET /md5
--- response_body
5d41402abc4b2a76b9719d911017c592
=== TEST 5: use ngx.md5 in set_by_lua (nil)
--- config
location = /md5 {
set_by_lua $a 'return ngx.md5(nil)';
echo $a;
}
--- request
GET /md5
--- response_body
d41d8cd98f00b204e9800998ecf8427e
=== TEST 6: use ngx.md5 in set_by_lua (null string)
--- config
location /md5 {
set_by_lua $a 'return ngx.md5("")';
echo $a;
}
--- request
GET /md5
--- response_body
d41d8cd98f00b204e9800998ecf8427e
=== TEST 7: md5(number)
--- config
location = /md5 {
content_by_lua 'ngx.say(ngx.md5(45))';
}
--- request
GET /md5
--- response_body
6c8349cc7260ae62e3b1396831a8398f

View file

@ -1,39 +0,0 @@
# vim:set ft=perl ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('warn');
repeat_each(1);
plan tests => repeat_each() * (blocks() * 2);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: use ngx.today in content_by_lua
--- config
location = /today {
content_by_lua 'ngx.say(ngx.today())';
}
--- request
GET /today
--- response_body_like: ^\d{4}-\d{2}-\d{2}$
=== TEST 2: use ngx.today in set_by_lua
--- config
location = /today {
set_by_lua $a 'return ngx.today()';
echo $a;
}
--- request
GET /today
--- response_body_like: ^\d{4}-\d{2}-\d{2}$

View file

@ -1,456 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('debug'); # to ensure any log-level can be outputed
repeat_each(2);
plan tests => repeat_each() * (blocks() * 3 + 4);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: test log-level STDERR
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.STDERR, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 2: test log-level EMERG
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.EMERG, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[emerg\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 3: test log-level ALERT
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.ALERT, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[alert\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 4: test log-level CRIT
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.CRIT, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[crit\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 5: test log-level ERR
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.ERR, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[error\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 6: test log-level WARN
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.WARN, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[warn\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 7: test log-level NOTICE
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.NOTICE, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[notice\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 8: test log-level INFO
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.INFO, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[info\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 9: test log-level DEBUG
--- config
location /log {
content_by_lua '
ngx.say("before log")
ngx.log(ngx.DEBUG, "hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[debug\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 10: regression test print()
--- config
location /log {
content_by_lua '
ngx.say("before log")
print("hello, log", 1234, 3.14159)
ngx.say("after log")
';
}
--- request
GET /log
--- response_body
before log
after log
--- error_log eval
qr/\[notice\] \S+: \S+ \[lua\] content_by_lua:3: hello, log12343.14159/
=== TEST 11: print(nil)
--- config
location /log {
content_by_lua '
print()
print(nil)
print("nil: ", nil)
ngx.say("hi");
';
}
--- request
GET /log
--- response_body
hi
--- error_log eval
[
'[lua] content_by_lua:2: ,',
'[lua] content_by_lua:3: nil,',
'[lua] content_by_lua:4: nil: nil,',
]
=== TEST 12: ngx.log in set_by_lua
--- config
location /log {
set_by_lua $a '
ngx.log(ngx.ERR, "HELLO")
return 32;
';
echo $a;
}
--- request
GET /log
--- response_body
32
--- error_log eval
qr/\[error\] \S+: \S+ \[lua\] set_by_lua:2: HELLO,/
=== TEST 13: test booleans and nil
--- config
location /log {
set_by_lua $a '
ngx.log(ngx.ERR, true, false, nil)
return 32;
';
echo $a;
}
--- request
GET /log
--- response_body
32
--- error_log eval
qr/\[error\] \S+: \S+ \[lua\] set_by_lua:2: truefalsenil,/
=== TEST 14: print() in header filter
--- config
location /log {
header_filter_by_lua '
print("hello world")
ngx.header.foo = 32
';
echo hi;
}
--- request
GET /log
--- response_headers
foo: 32
--- error_log eval
qr/\[notice\] .*? \[lua\] header_filter_by_lua:2: hello world/
--- response_body
hi
=== TEST 15: ngx.log() in header filter
--- config
location /log {
header_filter_by_lua '
ngx.log(ngx.ERR, "howdy, lua!")
ngx.header.foo = 32
';
echo hi;
}
--- request
GET /log
--- response_headers
foo: 32
--- response_body
hi
--- error_log eval
qr/\[error\] .*? \[lua\] header_filter_by_lua:2: howdy, lua!/
=== TEST 16: ngx.log() big data
--- config
location /log {
content_by_lua '
ngx.log(ngx.ERR, "a" .. string.rep("h", 1970) .. "b")
ngx.say("hi")
';
}
--- request
GET /log
--- response_headers
--- error_log eval
[qr/ah{1970}b/]
=== TEST 17: ngx.log in Lua function calls & inlined lua
--- config
location /log {
content_by_lua '
function foo()
bar()
end
function bar()
ngx.log(ngx.ERR, "hello, log", 1234, 3.14159)
end
foo()
ngx.say("done")
';
}
--- request
GET /log
--- response_body
done
--- error_log eval
qr/\[error\] \S+: \S+ \[lua\] content_by_lua:7: bar\(\): hello, log12343.14159/
=== TEST 18: ngx.log in Lua function tail-calls & inlined lua
--- config
location /log {
content_by_lua '
function foo()
return bar(5)
end
function bar(n)
if n < 1 then
ngx.log(ngx.ERR, "hello, log", 1234, 3.14159)
return n
end
return bar(n - 1)
end
foo()
ngx.say("done")
';
}
--- request
GET /log
--- response_body
done
--- error_log eval
qr/\[error\] \S+: \S+ \[lua\] content_by_lua:8:(?: foo\(\):)? hello, log12343.14159/
=== TEST 19: ngx.log in Lua files
--- config
location /log {
content_by_lua_file 'html/test.lua';
}
--- user_files
>>> test.lua
function foo()
bar()
end
function bar()
ngx.log(ngx.ERR, "hello, log", 1234, 3.14159)
end
foo()
ngx.say("done")
--- request
GET /log
--- response_body
done
--- error_log eval
qr/\[error\] \S+: \S+ \[lua\] test.lua:6: bar\(\): hello, log12343.14159/
=== TEST 20: ngx.log with bad levels (ngx.ERROR, -1)
--- config
location /log {
content_by_lua '
ngx.log(ngx.ERROR, "hello lua")
ngx.say("done")
';
}
--- request
GET /log
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
bad log level: -1
=== TEST 21: ngx.log with bad levels (9)
--- config
location /log {
content_by_lua '
ngx.log(9, "hello lua")
ngx.say("done")
';
}
--- request
GET /log
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
bad log level: 9
=== TEST 22: \0 in the log message
--- config
location = /t {
content_by_lua '
ngx.log(ngx.WARN, "hello\\0world")
ngx.say("ok")
';
}
--- request
GET /t
--- response_body
ok
--- no_error_log
[error]
--- error_log eval
"2: hello\0world, client: "

View file

@ -1,273 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('debug'); # to ensure any log-level can be outputed
repeat_each(2);
plan tests => repeat_each() * (blocks() * 2 + 2);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: test reading request body
--- config
location /echo_body {
lua_need_request_body on;
content_by_lua '
ngx.print(ngx.var.request_body or "nil")
';
}
--- request eval
"POST /echo_body
hello\x00\x01\x02
world\x03\x04\xff"
--- response_body eval
"hello\x00\x01\x02
world\x03\x04\xff"
=== TEST 2: test not reading request body
--- config
location /echo_body {
lua_need_request_body off;
content_by_lua '
ngx.print(ngx.var.request_body or "nil")
';
}
--- request eval
"POST /echo_body
hello\x00\x01\x02
world\x03\x04\xff"
--- response_body eval
"nil"
=== TEST 3: test default setting (not reading request body)
--- config
location /echo_body {
content_by_lua '
ngx.print(ngx.var.request_body or "nil")
';
}
--- request eval
"POST /echo_body
hello\x00\x01\x02
world\x03\x04\xff"
--- response_body eval
"nil"
=== TEST 4: test main conf
--- http_config
lua_need_request_body on;
--- config
location /echo_body {
content_by_lua '
ngx.print(ngx.var.request_body or "nil")
';
}
--- request eval
"POST /echo_body
hello\x00\x01\x02
world\x03\x04\xff"
--- response_body eval
"hello\x00\x01\x02
world\x03\x04\xff"
=== TEST 5: test server conf
--- config
lua_need_request_body on;
location /echo_body {
content_by_lua '
ngx.print(ngx.var.request_body or "nil")
';
}
--- request eval
"POST /echo_body
hello\x00\x01\x02
world\x03\x04\xff"
--- response_body eval
"hello\x00\x01\x02
world\x03\x04\xff"
=== TEST 6: test override main conf
--- http_config
lua_need_request_body on;
--- config
location /echo_body {
lua_need_request_body off;
content_by_lua '
ngx.print(ngx.var.request_body or "nil")
';
}
--- request eval
"POST /echo_body
hello\x00\x01\x02
world\x03\x04\xff"
--- response_body eval
"nil"
=== TEST 7: test override server conf
--- config
lua_need_request_body on;
location /echo_body {
lua_need_request_body off;
content_by_lua '
ngx.print(ngx.var.request_body or "nil")
';
}
--- request eval
"POST /echo_body
hello\x00\x01\x02
world\x03\x04\xff"
--- response_body eval
"nil"
=== TEST 8: test override server conf
--- config
location /proxy {
proxy_pass http://127.0.0.1:$server_port/hi;
}
location /hi {
echo_request_body;
}
location /echo_body {
lua_need_request_body off;
content_by_lua '
ngx.say(ngx.var.request_body or "nil")
local res = ngx.location.capture(
"/proxy",
{ method = ngx.HTTP_POST,
body = ngx.var.request_body })
ngx.say(res.status)
';
}
--- request eval
"POST /echo_body
"
--- response_body
nil
200
=== TEST 9: empty POST body
--- config
location /proxy {
proxy_pass http://127.0.0.1:$server_port/hi;
}
location /hi {
echo_request_body;
}
location /echo_body {
lua_need_request_body on;
content_by_lua '
ngx.say(ngx.var.request_body or "nil")
local res = ngx.location.capture(
"/proxy",
{ method = ngx.HTTP_POST,
body = ngx.var.request_body })
ngx.say(res.status)
';
}
--- request eval
"POST /echo_body
"
--- response_body
nil
200
=== TEST 10: on disk request body
--- config
location /proxy {
proxy_pass http://127.0.0.1:$server_port/hi;
}
location /hi {
echo_request_body;
}
location /echo_body {
lua_need_request_body on;
client_max_body_size 100k;
client_body_buffer_size 1;
sendfile on;
content_by_lua '
local res = ngx.location.capture(
"/proxy",
{ method = ngx.HTTP_POST,
body = ngx.var.request_body })
ngx.print(res.body)
';
}
--- request eval
"POST /echo_body
" . ('a' x 1024)
--- response_body chomp
=== TEST 11: no modify main request content-length
--- config
location /foo {
content_by_lua '
ngx.location.capture("/other", {body = "hello"})
ngx.say(ngx.req.get_headers()["Content-Length"] or "nil")
';
}
location /other {
echo hi;
}
--- request
POST /foo
hi
--- response_body
2
=== TEST 12: Expect: 100-Continue
--- config
location /echo_body {
lua_need_request_body on;
content_by_lua '
ngx.print(ngx.var.request_body or "nil")
';
}
--- request
POST /echo_body
hello world
--- more_headers
Expect: 100-Continue
--- ignore_response
--- no_error_log
[error]
[alert]
http finalize request: 500, "/echo_body?" a:1, c:2
http finalize request: 500, "/echo_body?" a:1, c:0
--- log_level: debug

View file

@ -1,171 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('warn');
repeat_each(2);
plan tests => repeat_each() * (blocks() * 2);
#no_diff();
#no_long_string();
run_tests();
#md5_bin_bin is hard to test, so convert it to hex mode
__DATA__
=== TEST 1: set md5_bin hello ????xxoo
--- config
location = /md5_bin {
content_by_lua 'local a = string.gsub(ngx.md5_bin("hello"), ".", function (c)
return string.format("%02x", string.byte(c))
end); ngx.say(a)';
}
--- request
GET /md5_bin
--- response_body
5d41402abc4b2a76b9719d911017c592
=== TEST 2: set md5_bin hello ????xxoo
--- config
location = /md5_bin {
content_by_lua 'ngx.say(string.len(ngx.md5_bin("hello")))';
}
--- request
GET /md5_bin
--- response_body
16
=== TEST 3: set md5_bin hello
--- config
location = /md5_bin {
content_by_lua '
local s = ngx.md5_bin("hello")
s = string.gsub(s, ".", function (c)
return string.format("%02x", string.byte(c))
end)
ngx.say(s)
';
}
--- request
GET /md5_bin
--- response_body
5d41402abc4b2a76b9719d911017c592
=== TEST 4: nil string to ngx.md5_bin
--- config
location = /md5_bin {
content_by_lua '
local s = ngx.md5_bin(nil)
s = string.gsub(s, ".", function (c)
return string.format("%02x", string.byte(c))
end)
ngx.say(s)
';
}
--- request
GET /md5_bin
--- response_body
d41d8cd98f00b204e9800998ecf8427e
=== TEST 5: null string to ngx.md5_bin
--- config
location /md5_bin {
content_by_lua '
local s = ngx.md5_bin("")
s = string.gsub(s, ".", function (c)
return string.format("%02x", string.byte(c))
end)
ngx.say(s)
';
}
--- request
GET /md5_bin
--- response_body
d41d8cd98f00b204e9800998ecf8427e
=== TEST 6: use ngx.md5_bin in set_by_lua
--- config
location = /md5_bin {
set_by_lua $a 'return string.gsub(ngx.md5_bin("hello"), ".", function (c)
return string.format("%02x", string.byte(c))
end)';
echo $a;
}
--- request
GET /md5_bin
--- response_body
5d41402abc4b2a76b9719d911017c592
=== TEST 7: use ngx.md5_bin in set_by_lua (nil)
--- config
location = /md5_bin {
set_by_lua $a '
local s = ngx.md5_bin(nil)
s = string.gsub(s, ".", function (c)
return string.format("%02x", string.byte(c))
end)
return s
';
echo $a;
}
--- request
GET /md5_bin
--- response_body
d41d8cd98f00b204e9800998ecf8427e
=== TEST 8: use ngx.md5_bin in set_by_lua (null string)
--- config
location /md5_bin {
set_by_lua $a '
local s = ngx.md5_bin("")
s = string.gsub(s, ".", function (c)
return string.format("%02x", string.byte(c))
end)
return s
';
echo $a;
}
--- request
GET /md5_bin
--- response_body
d41d8cd98f00b204e9800998ecf8427e
=== TEST 9: md5_bin(number)
--- config
location = /t {
content_by_lua '
s = ngx.md5_bin(45)
s = string.gsub(s, ".", function (c)
return string.format("%02x", string.byte(c))
end)
return s
';
}
--- request
GET /t
--- response_body

View file

@ -1,119 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('warn');
repeat_each(1);
plan tests => repeat_each() * (blocks() * 2);
#no_diff();
no_long_string();
run_tests();
__DATA__
=== TEST 1: use ngx.localtime in content_by_lua
--- config
location = /now {
content_by_lua 'ngx.say(ngx.localtime())';
}
--- request
GET /now
--- response_body_like: ^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}$
=== TEST 2: use ngx.localtime in set_by_lua
--- config
location = /now {
set_by_lua $a 'return ngx.localtime()';
echo $a;
}
--- request
GET /now
--- response_body_like: ^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}$
=== TEST 3: use ngx.time in set_by_lua
--- config
location = /time {
set_by_lua $a 'return ngx.time()';
echo $a;
}
--- request
GET /time
--- response_body_like: ^\d{10,}$
=== TEST 4: use ngx.time in content_by_lua
--- config
location = /time {
content_by_lua 'ngx.say(ngx.time())';
}
--- request
GET /time
--- response_body_like: ^\d{10,}$
=== TEST 5: use ngx.time in content_by_lua
--- config
location = /time {
content_by_lua '
ngx.say(ngx.time())
ngx.say(ngx.localtime())
ngx.say(ngx.utctime())
ngx.say(ngx.cookie_time(ngx.time()))
';
}
--- request
GET /time
--- response_body_like chomp
^\d{10,}
\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}
\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}
\w+, .*? GMT$
=== TEST 6: use ngx.now in set_by_lua
--- config
location = /time {
set_by_lua $a 'return ngx.now()';
echo $a;
}
--- request
GET /time
--- response_body_like: ^\d{10,}(\.\d{1,3})?$
=== TEST 7: use ngx.now in content_by_lua
--- config
location = /time {
content_by_lua 'ngx.say(ngx.now())';
}
--- request
GET /time
--- response_body_like: ^\d{10,}(\.\d{1,3})?$
=== TEST 8: use ngx.update_time & ngx.now in content_by_lua
--- config
location = /time {
content_by_lua '
ngx.update_time()
ngx.say(ngx.now())
';
}
--- request
GET /time
--- response_body_like: ^\d{10,}(\.\d{1,3})?$

View file

@ -1,198 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('warn');
repeat_each(2);
plan tests => repeat_each() * (blocks() * 2 + 3);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: base64 encode hello
--- config
location = /encode_base64 {
content_by_lua 'ngx.say(ngx.encode_base64("hello"))';
}
--- request
GET /encode_base64
--- response_body
aGVsbG8=
=== TEST 2: nil string to ngx.encode_base64
--- config
location = /encode_base64 {
content_by_lua 'ngx.say("left" .. ngx.encode_base64(nil) .. "right")';
}
--- request
GET /encode_base64
--- response_body
leftright
=== TEST 3: null string to ngx.encode_base64
--- config
location = /encode_base64 {
content_by_lua 'ngx.say("left" .. ngx.encode_base64("") .. "right")';
}
--- request
GET /encode_base64
--- response_body
leftright
=== TEST 4: use ngx.encode_base64 in set_by_lua
--- config
location = /encode_base64 {
set_by_lua $a 'return ngx.encode_base64("hello")';
echo $a;
}
--- request
GET /encode_base64
--- response_body
aGVsbG8=
=== TEST 5: use ngx.encode_base64 in set_by_lua (nil)
--- config
location = /encode_base64 {
set_by_lua $a 'return "left" .. ngx.encode_base64(nil) .. "right"';
echo $a;
}
--- request
GET /encode_base64
--- response_body
leftright
=== TEST 6: use ngx.encode_base64 in set_by_lua (null string)
--- config
location /encode_base64 {
set_by_lua $a 'return "left" .. ngx.encode_base64("") .. "right"';
echo $a;
}
--- request
GET /encode_base64
--- response_body
leftright
=== TEST 7: base64 encode hello
--- config
location = /decode_base64 {
content_by_lua 'ngx.say(ngx.decode_base64("aGVsbG8="))';
}
--- request
GET /decode_base64
--- response_body
hello
=== TEST 8: null string to ngx.decode_base64
--- config
location = /decode_base64 {
content_by_lua 'ngx.say("left" .. ngx.decode_base64("") .. "right")';
}
--- request
GET /decode_base64
--- response_body
leftright
=== TEST 9: use ngx.decode_base64 in set_by_lua
--- config
location = /decode_base64 {
set_by_lua $a 'return ngx.decode_base64("aGVsbG8=")';
echo $a;
}
--- request
GET /decode_base64
--- response_body
hello
=== TEST 10: use ngx.decode_base64 in set_by_lua (nil)
--- config
location = /decode_base64 {
set_by_lua $a 'return "left" .. ngx.decode_base64(nil) .. "right"';
echo $a;
}
--- request
GET /decode_base64
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
string argument only
=== TEST 11: use ngx.decode_base64 in set_by_lua (null string)
--- config
location /decode_base64 {
set_by_lua $a 'return "left" .. ngx.decode_base64("") .. "right"';
echo $a;
}
--- request
GET /decode_base64
--- response_body
leftright
=== TEST 12: base64 encode number
--- config
location = /t {
content_by_lua 'ngx.say(ngx.encode_base64(32))';
}
--- request
GET /t
--- response_body
MzI=
=== TEST 13: base64 decode number
--- config
location = /t {
content_by_lua 'ngx.say(ngx.decode_base64(32))';
}
--- request
GET /t
--- response_body_like: 500 Internal Server Error
--- error_code: 500
--- error_log
string argument only
=== TEST 14: base64 decode error
--- config
location = /t {
content_by_lua 'ngx.say(ngx.decode_base64("^*~"))';
}
--- request
GET /t
--- response_body
nil
--- no_error_log
[error]

File diff suppressed because it is too large Load diff

View file

@ -1,273 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('warn');
#repeat_each(120);
repeat_each(2);
plan tests => repeat_each() * (blocks() * 2 + 7);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: no key found
--- config
location /nil {
content_by_lua '
ngx.say(ngx.blah_blah == nil and "nil" or "not nil")
';
}
--- request
GET /nil
--- response_body
nil
=== TEST 2: .status found
--- config
location /nil {
content_by_lua '
ngx.say(ngx.status == nil and "nil" or "not nil")
';
}
--- request
GET /nil
--- response_body
not nil
=== TEST 3: default to 0
--- config
location /nil {
content_by_lua '
ngx.say(ngx.status);
';
}
--- request
GET /nil
--- response_body
0
=== TEST 4: default to 0
--- config
location /nil {
content_by_lua '
ngx.say("blah");
ngx.say(ngx.status);
';
}
--- request
GET /nil
--- response_body
blah
200
=== TEST 5: set 201
--- config
location /201 {
content_by_lua '
ngx.status = 201;
ngx.say("created");
';
}
--- request
GET /201
--- response_body
created
--- error_code: 201
=== TEST 6: set "201"
--- config
location /201 {
content_by_lua '
ngx.status = "201";
ngx.say("created");
';
}
--- request
GET /201
--- response_body
created
--- error_code: 201
=== TEST 7: set "201.7"
--- config
location /201 {
content_by_lua '
ngx.status = "201.7";
ngx.say("created");
';
}
--- request
GET /201
--- response_body
created
--- error_code: 201
=== TEST 8: set "abc"
--- config
location /201 {
content_by_lua '
ngx.status = "abc";
ngx.say("created");
';
}
--- request
GET /201
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 9: set blah
--- config
location /201 {
content_by_lua '
ngx.blah = 201;
ngx.say("created");
';
}
--- request
GET /201
--- response_body
created
--- no_error_log
[error]
=== TEST 10: set ngx.status before headers are sent
--- config
location /t {
content_by_lua '
ngx.say("ok")
ngx.status = 201
';
}
--- request
GET /t
--- response_body
ok
--- error_code: 200
--- error_log eval
qr/\[error\] .*? attempt to set ngx\.status after sending out response headers/
=== TEST 11: http 1.0 and ngx.status
--- config
location /nil {
content_by_lua '
ngx.status = ngx.HTTP_UNAUTHORIZED
ngx.say("invalid request")
ngx.exit(ngx.HTTP_OK)
';
}
--- request
GET /nil HTTP/1.0
--- response_body
invalid request
--- error_code: 401
--- no_error_log
[error]
=== TEST 12: github issue #221: cannot modify ngx.status for responses from ngx_proxy
--- config
location = /t {
proxy_pass http://127.0.0.1:$server_port/;
header_filter_by_lua '
if ngx.status == 206 then
ngx.status = ngx.HTTP_OK
end
';
}
--- request
GET /t
--- more_headers
Range: bytes=0-4
--- response_body chop
<html
--- error_code: 200
--- no_error_log
[error]
=== TEST 13: 101 response has a complete status line
--- config
location /t {
content_by_lua '
ngx.status = 101
ngx.send_headers()
';
}
--- request
GET /t
--- raw_response_headers_like: ^HTTP/1.1 101 Switching Protocols\r\n
--- error_code: 101
--- no_error_log
[error]
=== TEST 14: reading error status code
--- config
location = /t {
content_by_lua 'ngx.say("status = ", ngx.status)';
}
--- raw_request eval
"GET /t\r\n"
--- http09
--- response_body
status = 9
=== TEST 15: err status
--- config
location /nil {
content_by_lua '
ngx.exit(502)
';
body_filter_by_lua '
if ngx.arg[2] then
ngx.log(ngx.WARN, "ngx.status = ", ngx.status)
end
';
}
--- request
GET /nil
--- response_body_like: 502 Bad Gateway
--- error_code: 502
--- error_log
ngx.status = 502
--- no_error_log
[error]

File diff suppressed because it is too large Load diff

View file

@ -1,576 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
repeat_each(2);
plan tests => repeat_each() * (blocks() * 2 + 4);
$ENV{TEST_NGINX_MEMCACHED_PORT} ||= 11211;
#no_diff();
#no_shuffle();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: sanity
--- config
location /read {
content_by_lua '
ngx.exec("/hi");
ngx.say("Hi");
';
}
location /hi {
echo "Hello";
}
--- request
GET /read
--- response_body
Hello
=== TEST 2: empty uri arg
--- config
location /read {
content_by_lua '
ngx.exec("");
ngx.say("Hi");
';
}
location /hi {
echo "Hello";
}
--- request
GET /read
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 3: no arg
--- config
location /read {
content_by_lua '
ngx.exec();
ngx.say("Hi");
';
}
location /hi {
echo "Hello";
}
--- request
GET /read
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 4: too many args
--- config
location /read {
content_by_lua '
ngx.exec(1, 2, 3, 4);
ngx.say("Hi");
';
}
location /hi {
echo "Hello";
}
--- request
GET /read
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 5: null uri
--- config
location /read {
content_by_lua '
ngx.exec(nil)
ngx.say("Hi")
';
}
location /hi {
echo "Hello";
}
--- request
GET /read
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 6: user args
--- config
location /read {
content_by_lua '
ngx.exec("/hi", "Yichun Zhang")
ngx.say("Hi")
';
}
location /hi {
echo Hello $query_string;
}
--- request
GET /read
--- response_body
Hello Yichun Zhang
=== TEST 7: args in uri
--- config
location /read {
content_by_lua '
ngx.exec("/hi?agentzh")
ngx.say("Hi")
';
}
location /hi {
echo Hello $query_string;
}
--- request
GET /read
--- response_body
Hello agentzh
=== TEST 8: args in uri and user args
--- config
location /read {
content_by_lua '
ngx.exec("/hi?a=Yichun", "b=Zhang")
ngx.say("Hi")
';
}
location /hi {
echo Hello $query_string;
}
--- request
GET /read
--- response_body
Hello a=Yichun&b=Zhang
=== TEST 9: args in uri and user args
--- config
location /read {
content_by_lua '
ngx.exec("@hi?a=Yichun", "b=Zhang")
ngx.say("Hi")
';
}
location @hi {
echo Hello $query_string;
}
--- request
GET /read
--- response_body
Hello
=== TEST 10: exec after location capture (simple echo)
--- config
location /test {
content_by_lua_file 'html/test.lua';
}
location /a {
echo "hello";
}
location /b {
echo "hello";
}
--- user_files
>>> test.lua
ngx.location.capture('/a')
ngx.exec('/b')
--- request
GET /test
--- response_body
hello
=== TEST 11: exec after location capture (memc)
--- config
location /test {
content_by_lua_file 'html/test.lua';
}
location /a {
set $memc_key 'hello world';
set $memc_value 'hello hello hello world world world';
set $memc_cmd set;
memc_pass 127.0.0.1:$TEST_NGINX_MEMCACHED_PORT;
}
location /b {
set $memc_key 'hello world';
set $memc_cmd get;
memc_pass 127.0.0.1:$TEST_NGINX_MEMCACHED_PORT;
}
--- user_files
>>> test.lua
ngx.location.capture('/a')
ngx.exec('/b')
--- request
GET /test
--- response_body: hello hello hello world world world
=== TEST 12: exec after named location capture (simple echo)
--- config
location /test {
content_by_lua_file 'html/test.lua';
}
location /a {
echo "hello";
}
location @b {
echo "hello";
}
--- user_files
>>> test.lua
ngx.location.capture('/a')
ngx.exec('@b')
--- request
GET /test
--- response_body
hello
=== TEST 13: exec after named location capture (memc)
--- config
location /test {
content_by_lua_file 'html/test.lua';
}
location /a {
set $memc_key 'hello world';
set $memc_value 'hello hello hello world world world';
set $memc_cmd set;
memc_pass 127.0.0.1:$TEST_NGINX_MEMCACHED_PORT;
}
location @b {
set $memc_key 'hello world';
set $memc_cmd get;
memc_pass 127.0.0.1:$TEST_NGINX_MEMCACHED_PORT;
}
--- user_files
>>> test.lua
ngx.location.capture('/a')
ngx.exec('@b')
--- request
GET /test
--- response_body: hello hello hello world world world
=== TEST 14: github issue #40: 2 Subrequest calls when using access_by_lua, ngx.exec and echo_location (content)
--- config
location = /hi {
echo hello;
}
location /sub {
proxy_pass http://127.0.0.1:$server_port/hi;
#echo hello;
}
location /p{
#content_by_lua '
#local res = ngx.location.capture("/sub")
#ngx.print(res.body)
#';
echo_location /sub;
}
location /lua {
content_by_lua '
ngx.exec("/p")
';
}
--- request
GET /lua
--- response_body
hello
=== TEST 15: github issue #40: 2 Subrequest calls when using access_by_lua, ngx.exec and echo_location (content + named location)
--- config
location = /hi {
echo hello;
}
location /sub {
proxy_pass http://127.0.0.1:$server_port/hi;
#echo hello;
}
location @p {
#content_by_lua '
#local res = ngx.location.capture("/sub")
#ngx.print(res.body)
#';
echo_location /sub;
}
location /lua {
content_by_lua '
ngx.exec("@p")
';
}
--- request
GET /lua
--- response_body
hello
=== TEST 16: github issue #40: 2 Subrequest calls when using access_by_lua, ngx.exec and echo_location (content + post subrequest)
--- config
location = /hi {
echo hello;
}
location /sub {
proxy_pass http://127.0.0.1:$server_port/hi;
#echo hello;
}
location /p{
#content_by_lua '
#local res = ngx.location.capture("/sub")
#ngx.print(res.body)
#';
echo_location /sub;
}
location blah {
echo blah;
}
location /lua {
content_by_lua '
ngx.location.capture("/blah")
ngx.exec("/p")
';
}
--- request
GET /lua
--- response_body
hello
=== TEST 17: pcall safe
--- config
location /lua {
content_by_lua '
function f ()
ngx.exec("/hi")
end
pcall(f)
ngx.say("hello")
';
}
location /hi {
echo hi;
}
--- request
GET /lua
--- error_code: 200
--- response_body
hi
=== TEST 18: lua table as "args" parameter
--- config
location /lua {
content_by_lua '
local args = { foo = 3, bar = 4 }
ngx.exec("/hi", args)
';
}
location /hi {
echo "foo = $arg_foo";
echo "bar = $arg_bar";
}
--- request
GET /lua
--- error_code: 200
--- response_body
foo = 3
bar = 4
=== TEST 19: jump to internal locations requires ctx cleared
--- config
location @proxy {
rewrite_by_lua return;
echo hello;
}
location /main {
content_by_lua '
ngx.exec("@proxy")
';
}
--- request
GET /main
--- response_body
hello
=== TEST 20: exec + rewrite + named locations
--- config
location @proxy {
rewrite_by_lua return;
echo hello;
}
location /main {
rewrite_by_lua '
ngx.exec("@proxy")
';
}
--- request
GET /main
--- response_body
hello
=== TEST 21: exec(named location) in subrequests
--- config
location /entry {
echo_location /foo;
echo_location /foo2;
}
location /foo {
content_by_lua '
ngx.exec("@bar")
';
}
location /foo2 {
content_by_lua '
ngx.exec("@bar")
';
}
location @bar {
proxy_pass http://127.0.0.1:$server_port/bar;
}
location /bar {
echo hello;
}
--- request
GET /entry
--- response_body
hello
hello
=== TEST 22: exec(normal location) in subrequests
--- config
location /entry {
echo_location /foo;
echo_location /foo2;
}
location /foo {
content_by_lua '
ngx.exec("/baz")
';
}
location /foo2 {
content_by_lua '
ngx.exec("/baz")
';
}
location /baz {
proxy_pass http://127.0.0.1:$server_port/bar;
}
location /bar {
echo hello;
}
--- request
GET /entry
--- response_body
hello
hello
=== TEST 23: content_by_lua + ngx.exec + subrequest capture
--- config
location /main {
rewrite_by_lua '
res = ngx.location.capture("/test_loc");
ngx.print("hello, ", res.body)
';
content_by_lua return;
}
location /test_loc {
content_by_lua '
ngx.exec("@proxy")
';
}
location @proxy {
#echo proxy;
proxy_pass http://127.0.0.1:$server_port/foo;
}
location /foo {
#echo_status 201;
echo bah;
}
--- request
GET /main
--- response_body
hello, bah
=== TEST 24: jump to an internal location
--- config
location /t {
content_by_lua '
return ngx.exec("/proxy", ngx.var.args)
';
}
location /proxy {
internal;
proxy_pass http://127.0.0.1:$server_port/dummy;
}
location = /dummy {
echo -n dummy;
}
--- pipelined_requests eval
["GET /t", "GET /t?foo"]
--- response_body eval
["dummy", "dummy"]
--- no_error_log
[error]

View file

@ -1,175 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
repeat_each(2);
plan tests => repeat_each() * (blocks() * 2 + 4);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: sanity
--- config
location /read {
content_by_lua '
local s = ndk.set_var.set_escape_uri(" :")
local r = ndk.set_var.set_unescape_uri("a%20b")
ngx.say(s)
ngx.say(r)
';
}
--- request
GET /read
--- response_body
%20%3A
a b
=== TEST 2: directive not found
--- config
location /read {
content_by_lua '
local s = ndk.set_var.set_escape_uri_blah_blah(" :")
ngx.say(s)
';
}
--- request
GET /read
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 3: directive not found
--- config
location /read {
content_by_lua '
local s = ndk.set_var.content_by_lua(" :")
ngx.say(s)
';
}
--- request
GET /read
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 4: directive not found
--- config
location /read {
header_filter_by_lua '
ngx.header.Foo = ndk.set_var.set_escape_uri(" %")
';
echo hi;
}
--- request
GET /read
--- response_headers
Foo: %20%25
--- response_body
hi
=== TEST 5: bug: ndk.set_var not initialize ngx_http_variable_value_t variable properly
--- config
location /luaset {
content_by_lua "
local version = '2011.10.13+0000'
local e_version = ndk.set_var.set_encode_base32(version)
local s_version= ndk.set_var.set_quote_sql_str(version)
ngx.say(e_version)
ngx.say(s_version)
";
}
--- request
GET /luaset
--- response_body
68o32c9e64o2sc9j5co30c1g
'2011.10.13+0000'
=== TEST 6: set_by_lua
--- config
location /read {
set_by_lua $r '
return ndk.set_var.set_unescape_uri("a%20b")
';
echo $r;
}
--- request
GET /read
--- response_body
a b
=== TEST 7: header_filter_by_lua
--- config
location /read {
set $foo '';
content_by_lua '
ngx.send_headers()
ngx.say(ngx.var.foo)
';
header_filter_by_lua '
ngx.var.foo = ndk.set_var.set_unescape_uri("a%20b")
';
}
--- request
GET /read
--- response_body
a b
=== TEST 8: log_by_lua
--- config
location /read {
echo ok;
log_by_lua '
local foo = ndk.set_var.set_unescape_uri("a%20b")
ngx.log(ngx.WARN, "foo = ", foo)
';
}
--- request
GET /read
--- response_body
ok
--- wait: 0.1
--- error_log
foo = a b
=== TEST 9: ngx.timer.*
--- config
location /read {
echo ok;
log_by_lua '
ngx.timer.at(0, function ()
local foo = ndk.set_var.set_unescape_uri("a%20b")
ngx.log(ngx.WARN, "foo = ", foo)
end)
';
}
--- request
GET /read
--- response_body
ok
--- wait: 0.1
--- error_log
foo = a b
--- no_error_log
[error]

View file

@ -1,48 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
repeat_each(2);
plan tests => blocks() * repeat_each() * 2;
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: sanity
--- config
location /read {
content_by_lua '
ngx.say(ngx.OK)
ngx.say(ngx.AGAIN)
ngx.say(ngx.DONE)
ngx.say(ngx.ERROR)
';
}
--- request
GET /read
--- response_body
0
-2
-4
-1
=== TEST 2: http constants
--- config
location /read {
content_by_lua '
ngx.say(ngx.HTTP_GATEWAY_TIMEOUT)
';
}
--- request
GET /read
--- response_body
504

File diff suppressed because it is too large Load diff

View file

@ -1,46 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
log_level('warn');
repeat_each(2);
#repeat_each(1);
plan tests => repeat_each() * (blocks() * 2);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: cookie_time
--- config
location /lua {
content_by_lua '
ngx.say(ngx.cookie_time(1290079655))
';
}
--- request
GET /lua
--- response_body
Thu, 18-Nov-10 11:27:35 GMT
=== TEST 2: cookie_time in set_by_lua
--- config
location /lua {
set_by_lua $a '
return ngx.cookie_time(1290079655)
';
echo $a;
}
--- request
GET /lua
--- response_body
Thu, 18-Nov-10 11:27:35 GMT

View file

@ -1,169 +0,0 @@
# vim:set ft= ts=4 sw=4 et fdm=marker:
use lib 'lib';
use Test::Nginx::Socket::Lua;
#worker_connections(1014);
#master_process_enabled(1);
#log_level('warn');
repeat_each(2);
#repeat_each(1);
plan tests => repeat_each() * (blocks() * 3 + 1);
#no_diff();
#no_long_string();
run_tests();
__DATA__
=== TEST 1: default 302
--- config
location /read {
content_by_lua '
ngx.redirect("http://agentzh.org/foo");
ngx.say("hi")
';
}
--- request
GET /read
--- response_headers
Location: http://agentzh.org/foo
--- response_body_like: 302 Found
--- error_code: 302
=== TEST 2: explicit 302
--- config
location /read {
content_by_lua '
ngx.redirect("http://agentzh.org/foo", ngx.HTTP_MOVED_TEMPORARILY);
ngx.say("hi")
';
}
--- request
GET /read
--- response_headers
Location: http://agentzh.org/foo
--- response_body_like: 302 Found
--- error_code: 302
=== TEST 3: explicit 301
--- config
location /read {
content_by_lua '
ngx.redirect("http://agentzh.org/foo", ngx.HTTP_MOVED_PERMANENTLY);
ngx.say("hi")
';
}
--- request
GET /read
--- response_headers
Location: http://agentzh.org/foo
--- response_body_like: 301 Moved Permanently
--- error_code: 301
=== TEST 4: bad rc
--- config
location /read {
content_by_lua '
ngx.redirect("http://agentzh.org/foo", 404);
ngx.say("hi")
';
}
--- request
GET /read
--- response_headers
!Location
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 5: no args
--- config
location /read {
content_by_lua '
ngx.redirect()
ngx.say("hi")
';
}
--- request
GET /read
--- response_headers
!Location
--- response_body_like: 500 Internal Server Error
--- error_code: 500
=== TEST 6: relative uri
--- config
location /echo {
echo hello, world;
}
location /proxy {
proxy_pass http://127.0.0.1:$TEST_NGINX_SERVER_PORT/echo;
}
location /read {
content_by_lua '
ngx.location.capture("/proxy")
ngx.redirect("/echo")
ngx.say("hi")
';
}
--- request
GET /read
--- raw_response_headers_like: Location: http://localhost(?::\d+)?/echo\r\n
--- response_body_like: 302 Found
--- error_code: 302
=== TEST 7: default 302 (with uri args)
--- config
location /read {
content_by_lua '
ngx.redirect("http://agentzh.org/foo?bar=3");
ngx.say("hi")
';
}
--- request
GET /read
--- response_headers
Location: http://agentzh.org/foo?bar=3
--- response_body_like: 302 Found
--- error_code: 302
=== TEST 8: location.capture + ngx.redirect
--- config
location /echo {
echo hello, world;
}
location /proxy {
proxy_pass http://127.0.0.1:$TEST_NGINX_SERVER_PORT/echo;
}
location /read {
content_by_lua '
ngx.location.capture("/proxy")
ngx.location.capture("/proxy")
ngx.redirect("/echo")
ngx.exit(403)
';
}
--- pipelined_requests eval
["GET /read/1", "GET /read/2"]
--- error_code eval
[302, 302]
--- response_body eval
[qr/302 Found/, qr/302 Found/]

Some files were not shown because too many files have changed in this diff Show more