Как настроить long-polling на nginx?

Пытаюсь организовать примитивный обмен сообщениями через long-polling с помощью nginx.
В качестве примера взял эту статью: habrahabr.ru/post/252349
Проблема: не получается добавить подписчика в /sub/ - браузер ругается:
GET localhost/sub/subscriber1 404 (Not Found)
Хотя, как я понял, этот путь должен быть обработан nginx'ом.
Конфиг nginx:
http {
     server {
           listen 80 default;
           location ~ /\.ht {
               deny  all;
           }
           location / {
            proxy_pass http://127.0.0.1:8080;
           }
           location /channels-stats {
                # activate channels statistics mode for this location
                push_stream_channels_statistics;

                # query string based channel id
                push_stream_channels_path               $arg_id;
            }
            location /pub {
               # activate publisher (admin) mode for this location
               push_stream_publisher admin;

                # query string based channel id
                push_stream_channels_path               $arg_id;
            }
            location ~ /sub/(.*) {
                # activate subscriber (streaming) mode for this location
                push_stream_subscriber;

                # positional channel path
                push_stream_channels_path                   $1;
                push_stream_longpolling_connection_ttl    30s;
                push_stream_last_received_message_time  $arg_time; 
                push_stream_last_received_message_tag     $arg_tag;
            }
        }
    push_stream_shared_memory_size 32M;
    ...


Код JS подключения к каналу:
var channelId = 'subscriber1'; 
var  last_etag=0; 
var  last_time=null;

function new_message() {
$.ajax({
        url: '/sub/' + channelId,
        type: "GET",
        dataType: 'json',
        beforeSend: function(xhr){xhr.setRequestHeader('Etag', last_etag);xhr.setRequestHeader('Last-Modified', last_time);},
        success: function(data, status, xhr) {
        last_etag =xhr.getResponseHeader('Etag'); 
        last_time =xhr.getResponseHeader('Last-Modified');
        console.log(data);
        setTimeout(new_message, 50);
        }
    })
}
new_message();


При выполнении в терминале можно увидеть, что запрос к localhost/sub отправляется к apache, который, соответственно, отдает 404:
$ curl -s -v --no-buffer 'http://localhost/sub/my_channel_1'
* Hostname was NOT found in DNS cache
*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 80 (#0)
> GET /sub/my_channel_1 HTTP/1.1
> User-Agent: curl/7.35.0
> Host: localhost
> Accept: */*
> 
< HTTP/1.1 404 Not Found
* Server nginx/1.2.6 is not blacklisted
< Server: nginx/1.2.6
< Date: Tue, 19 May 2015 13:35:12 GMT
< Content-Type: text/html; charset=iso-8859-1
< Content-Length: 288
< Connection: keep-alive
< 
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>404 Not Found</title>
</head><body>
<h1>Not Found</h1>
<p>The requested URL /sub/my_channel_1 was not found on this server.</p>
<hr>
<address>Apache/2.4.7 (Ubuntu) Server at localhost Port 80</address>
</body></html>
* Connection #0 to host localhost left intact
  • Вопрос задан
  • 1446 просмотров
Решения вопроса 1
AMar4enko
@AMar4enko
Цитата из руководства
To find location matching a given request, nginx first checks locations defined using the prefix strings (prefix locations). Among them, the location with the longest matching prefix is selected and remembered. Then regular expressions are checked, in the order of their appearance in the configuration file.

Сначала ищутся совпадения в префиксных location, и только если среди них ничего не нашлось, то regexp.
Таким образом, у вас срабатывает location /, вместо location ~ /sub/(.*).
Напишите так
location / {
            location ~ /sub/(.*) {
                # activate subscriber (streaming) mode for this location
                push_stream_subscriber;

                # positional channel path
                push_stream_channels_path                   $1;
                push_stream_longpolling_connection_ttl    30s;
                push_stream_last_received_message_time  $arg_time; 
                push_stream_last_received_message_tag     $arg_tag;
            }

            proxy_pass http://127.0.0.1:8080;
}
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы