Re: проблемы с кодировкой nginx + ms exchange
Maxim Dounin
mdounin на mdounin.ru
Ср Янв 6 05:55:21 MSK 2010
Hello!
On Tue, Jan 05, 2010 at 11:42:20AM -0500, DigitalShaman wrote:
> Доброе время суток всем.
> nginx настроен в режиме прокси для MS Exchange 2003 Outlook Web
> Access
> в процессе работы выяснилась такая проблема: при попытке
> переслать любое письмо nginx выдает Bad Request (Invalid URL).
Всмысле, exchange выдаёт?
> После разбирательств с дебагом есть подозрение что nginx
> неправильно перекодирует имена папок при определенных запросах.
> Непонятным мне образом подменяя "Входящие" на "Черновики"
Судя по всему - exchange просто возвращает redirect на
"Черновики". А вот дальше уже случается Bad Request.
[...]
> location /exchange { proxy_pass https://frontendexch.kernel.local/exchange; }
Поскольку uri менять не нужно, можно попробовать вот так:
- location /exchange { proxy_pass https://frontendexch.kernel.local/exchange; }
+ location /exchange { proxy_pass https://frontendexch.kernel.local; }
В этом случае на бекенд будет передаваться оригинальный запрос в
том виде как он пришёл от клиента, точно также закодированный.
[...]
> 2010/01/05 16:00:44 4753#0: *377 write new buf t:1 f:0 0813A8F8, pos 0813A8F8, size: 544 file: 0, size: 0
> 2010/01/05 16:00:44 4753#0: *377 http write filter: l:0 f:0 s:544
> 2010/01/05 16:00:44 4753#0: *377 http cacheable: 0
> 2010/01/05 16:00:44 4753#0: *377 http upstream process upstream
> 2010/01/05 16:00:44 4753#0: *377 pipe read upstream: 1
> 2010/01/05 16:00:44 4753#0: *377 pipe preread: 0
> 2010/01/05 16:00:44 4753#0: *377 pipe recv chain: 0
> 2010/01/05 16:00:44 4753#0: *377 pipe buf free s:0 t:1 f:0 0813B858, pos 0813BA60, size: 0 file: 0, size: 0
> 2010/01/05 16:00:44 4753#0: *377 pipe write downstream: 1
> 2010/01/05 16:00:44 4753#0: *377 pipe write downstream done
> 2010/01/05 16:00:44 4753#0: *377 event timer: 12, old: 4274986183, new: 4274986434
> 2010/01/05 16:00:44 4753#0: *377 http upstream exit: 00000000
> 2010/01/05 16:00:44 4753#0: *377 finalize http upstream request: 0
> 2010/01/05 16:00:44 4753#0: *377 finalize http proxy request
> 2010/01/05 16:00:44 4753#0: *377 free rr peer 1 0
> 2010/01/05 16:00:44 4753#0: *377 SSL_shutdown: 1
> 2010/01/05 16:00:44 4753#0: *377 close http upstream connection: 12
> 2010/01/05 16:00:44 4753#0: *377 event timer del: 12: 4274986183
> 2010/01/05 16:00:44 4753#0: *377 delete posted event B782B10C
> 2010/01/05 16:00:44 4753#0: *377 http upstream temp fd: -1
> 2010/01/05 16:00:44 4753#0: *377 http output filter "/exchange/root/Входящие/фото НГ.EML/?Cmd=forward"
> 2010/01/05 16:00:44 4753#0: *377 http copy filter: "/exchange/root/Входящие/фото НГ.EML/?Cmd=forward"
> 2010/01/05 16:00:44 4753#0: *377 http postpone filter "/exchange/root/Входящие/фото НГ.EML/?Cmd=forward" BFD6B498
> 2010/01/05 16:00:44 4753#0: *377 write old buf t:1 f:0 0813A8F8, pos 0813A8F8, size: 544 file: 0, size: 0
> 2010/01/05 16:00:44 4753#0: *377 write new buf t:0 f:0 00000000, pos 00000000, size: 0 file: 0, size: 0
> 2010/01/05 16:00:44 4753#0: *377 http write filter: l:1 f:0 s:544
> 2010/01/05 16:00:44 4753#0: *377 http write filter limit 0
> 2010/01/05 16:00:44 4753#0: *377 malloc: 0815B400:16384
> 2010/01/05 16:00:44 4753#0: *377 SSL buf copy: 544
> 2010/01/05 16:00:44 4753#0: *377 SSL to write: 544
> 2010/01/05 16:00:44 4753#0: *377 SSL_write: 544
> 2010/01/05 16:00:44 4753#0: *377 http write filter 00000000
> 2010/01/05 16:00:44 4753#0: *377 http copy filter: 0 "/exchange/root/Входящие/фото НГ.EML/?Cmd=forward"
> 2010/01/05 16:00:44 4753#0: *377 http finalize request: 0, "/exchange/root/Входящие/фото НГ.EML/?Cmd=forward" a:1, c:1
> 2010/01/05 16:00:44 4753#0: *377 set http keepalive handler
> 2010/01/05 16:00:44 4753#0: *377 http close request
> 2010/01/05 16:00:44 4753#0: *377 http log handler
> 2010/01/05 16:00:44 4753#0: *377 free: 0813B858
> 2010/01/05 16:00:44 4753#0: *377 free: 081573F8
> 2010/01/05 16:00:44 4753#0: *377 free: 08139840, unused: 2576
> 2010/01/05 16:00:44 4753#0: *377 event timer add: 19: 75000:4274701434
> 2010/01/05 16:00:44 4753#0: *377 free: 08115EE0
> 2010/01/05 16:00:44 4753#0: *377 free: 080E29E8
> 2010/01/05 16:00:44 4753#0: *377 hc free: 00000000 0
> 2010/01/05 16:00:44 4753#0: *377 hc busy: 00000000 0
> 2010/01/05 16:00:44 4753#0: *377 free: 0815B400
> 2010/01/05 16:00:44 4753#0: *377 post event B782B654
> 2010/01/05 16:00:44 4753#0: *377 post event B775A654
> 2010/01/05 16:00:44 4753#0: *377 delete posted event B775A654
> 2010/01/05 16:00:44 4753#0: *377 http empty handler
> 2010/01/05 16:00:44 4753#0: *377 delete posted event B782B654
Вот тут закончился предыдущий запрос, и начался следующий.
> 2010/01/05 16:00:44 4753#0: *377 http keepalive handler
> 2010/01/05 16:00:44 4753#0: *377 malloc: 080E29E8:2048
> 2010/01/05 16:00:44 4753#0: *377 SSL_read: 801
> 2010/01/05 16:00:44 4753#0: *377 SSL_read: -1
> 2010/01/05 16:00:44 4753#0: *377 SSL_get_error: 2
> 2010/01/05 16:00:44 4753#0: *377 malloc: 08115EE0:656
> 2010/01/05 16:00:44 4753#0: *377 posix_memalign: 08139840:8192 @16
> 2010/01/05 16:00:44 4753#0: *377 http process request line
> 2010/01/05 16:00:44 4753#0: *377 s:0 in:'2F:/', out:'/'
> 2010/01/05 16:00:44 4753#0: *377 s:1 in:'65:e', out:'e'
[...]
> 2010/01/05 16:00:44 4753#0: *377 http request line: "GET /exchange/root/%D0%A7%D0%B5%D1%80%D0%BD%D0%BE%D0%B2%D0%B8%D0%BA%D0%B8/%3E%3E:%20%D1%84%D0%BE%D1%82%D0%BE%20%D0%9D%D0%93-13.EML?Cmd=forward&Create=0 HTTP/1.1"
> 2010/01/05 16:00:44 4753#0: *377 http uri: "/exchange/root/Черновики/>>: фото НГ-13.EML"
> 2010/01/05 16:00:44 4753#0: *377 http args: "Cmd=forward&Create=0"
> 2010/01/05 16:00:44 4753#0: *377 http exten: "EML"
> 2010/01/05 16:00:44 4753#0: *377 http process request header line
[...]
> 2010/01/05 16:00:44 4753#0: *377 http proxy header:
> "GET /exchange/root/%d0%a7%d0%b5%d1%80%d0%bd%d0%be%d0%b2%d0%b8%d0%ba%d0%b8/>>:%20%d1%84%d0%be%d1%82%d0%be%20%d0%9d%d0%93-13.EML?Cmd=forward&Create=0 HTTP/1.0
> Host: imap.site.com.ua
> X-Real-IP: 10.1.225.127
> X-Forwarded-For: 10.1.225.127
> Connection: close
> User-Agent: Mozilla/5.0 (X11; U; Linux i686; ru; rv:1.9.1.6) Gecko/20091215 Ubuntu/9.10 (karmic) Firefox/3.5.6
> Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
> Accept-Language: ru,en-us;q=0.7,en;q=0.3
> Accept-Encoding: gzip,deflate
> Accept-Charset: windows-1251,utf-8;q=0.7,*;q=0.7
> Referer: https://imap.site.com.ua/exchange/root/%D0%92%D1%85%D0%BE%D0%B4%D1%8F%D1%89%D0%B8%D0%B5/%D1%84%D0%BE%D1%82%D0%BE%20%D0%9D%D0%93.EML?Cmd=open
> Cookie: sessionid=2178fd18-050d-42ef-abad-161cd1669b93:0x419
А вот это - сформированный запрос на бекенд. Как видно, URL
несколько отличается от того что было исходно. Как использовать
оригинальный запрос от клиента написано выше, а не нравится
exchange'у скорее всего неэкранированный ">". Всё-таки RFC 2396
его запрещает использовать в URI неэкранированным, см. тут:
http://tools.ietf.org/html/rfc2396#section-2.4.3
Будет здорово если вы попробуете прилагающийся патч и сообщите о
результатах.
Maxim Dounin
p.s. Если пароль реальный - не забудте его поменять.
-------------- next part --------------
# HG changeset patch
# User Maxim Dounin <mdounin at mdounin.ru>
# Date 1262746160 -10800
# Node ID a7a3057e1539700d919701aff213b584380f6bfc
# Parent dd6dac3907850953f28375525d4a3c79fdc83588
Core: escape "<", ">", and """ in urls.
RFC 2396 requires it, and not escaping them seems to cause problems at
least with MS Exchange.
diff --git a/src/core/ngx_string.c b/src/core/ngx_string.c
--- a/src/core/ngx_string.c
+++ b/src/core/ngx_string.c
@@ -1258,13 +1258,13 @@ ngx_escape_uri(u_char *dst, u_char *src,
uint32_t *escape;
static u_char hex[] = "0123456789abcdef";
- /* " ", "#", "%", "?", %00-%1F, %7F-%FF */
+ /* " ", """, "#", "%", "<", ">", "?", %00-%1F, %7F-%FF */
static uint32_t uri[] = {
0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */
/* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */
- 0x80000029, /* 1000 0000 0000 0000 0000 0000 0010 1001 */
+ 0xd000002d, /* 1101 0000 0000 0000 0000 0000 0010 1101 */
/* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */
0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */
@@ -1278,13 +1278,13 @@ ngx_escape_uri(u_char *dst, u_char *src,
0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */
};
- /* " ", "#", "%", "+", "?", %00-%1F, %7F-%FF */
+ /* " ", """, "#", "%", "+", "<", ">", "?", %00-%1F, %7F-%FF */
static uint32_t args[] = {
0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */
/* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */
- 0x80000829, /* 1000 0000 0000 0000 0000 1000 0010 1001 */
+ 0xd000082d, /* 1101 0000 0000 0000 0000 1000 0010 1101 */
/* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */
0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */
@@ -1298,13 +1298,13 @@ ngx_escape_uri(u_char *dst, u_char *src,
0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */
};
- /* " ", "#", """, "%", "'", %00-%1F, %7F-%FF */
+ /* " ", """, "#", "%", "'", "<", ">", %00-%1F, %7F-%FF */
static uint32_t html[] = {
0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */
/* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */
- 0x000000ad, /* 0000 0000 0000 0000 0000 0000 1010 1101 */
+ 0x500000ad, /* 0101 0000 0000 0000 0000 0000 1010 1101 */
/* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */
0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */
@@ -1318,13 +1318,13 @@ ngx_escape_uri(u_char *dst, u_char *src,
0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */
};
- /* " ", """, "%", "'", %00-%1F, %7F-%FF */
+ /* " ", """, "%", "'", "<", ">", %00-%1F, %7F-%FF */
static uint32_t refresh[] = {
0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */
/* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */
- 0x00000085, /* 0000 0000 0000 0000 0000 0000 1000 0101 */
+ 0x50000085, /* 0101 0000 0000 0000 0000 0000 1000 0101 */
/* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */
0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */
Подробная информация о списке рассылки nginx-ru