2017-01-31 2 views
1

Я установил стандартную среду websocket/channel Phoenix, но я не использую предоставленный socket.js - у меня есть свой (очень простой) код, который соединяется с каналами и темами. Тем не менее, я не могу получить сокет, который будет продолжаться больше минуты или около того. Есть ли способ определить тайм-аут для сокетов? У меня нет каких-либо специальных конфигураций в Phoenix стороне (все стандартные согласно документации)Сброс в Websocket слишком скоро

Мой Javascript код выглядит следующим образом:

const ws = new WebSocket(sock_url); 
ws.onmessage = (msg) => { 
    const { payload, event } = JSON.parse(msg.data); 
    if (!event.startsWith("phx_")) { 
    onMessage(payload.body); 
    } 
}; 
ws.onclose = (code, reason) => { 
    onClose(code, reason); 
}; 
ws.onopen =() => { 
    ws.send(JSON.stringify({ 
    topic: `users_socket:${user_id}`, 
    event: "phx_join", 
    payload: {}, 
    ref: '1' 
    })); 
}; 

Update: Я закончил с использованием сокета. js-файл, который поставляется вместе с Phoenix, как и все предлагали - он просто делает все, что мне нужно. Спасибо всем, кто ответил :)

+0

Есть ли причина, по которой вы не просто используете предоставленный модуль феникс-сокета? –

+0

Это часть более крупной библиотеки, и запрос заключался в том, чтобы код был прост и свободен от «внешних» библиотек. Но если у меня возникнет слишком много проблем такого типа, я могу в конечном итоге использовать JS-код, который поставляется вместе с phoenix. – user1595077

ответ

1

Я разрабатываю проект с помощью Websockets (используя Go not Phoenix или Elixir), и у меня были те же проблемы с разъединением, которые мне удалось решить (по крайней мере, это не было время с тех пор) путем «пингования» веб-памяти, т.е. отправки сообщения в определенные интервалы времени.

Возможно, у вас может быть что-то подобное в вашем Javascript.

ws.onopen =() => { 
    ws.send(/** YOUR CODE */); 

    // Send a ping event every 10 seconds 
    setInterval(() => ws.send(JSON.stringify({ event: "ping" })), 10000); 
} 

И обрабатывать этот новый тип события соответственно на стороне сервера. Также вы можете попытаться контролировать событие onclose и в зависимости от причины повторно открыть соединение. Вы можете найти список таких кодов событий в Mozilla docs.

+0

Спасибо! Я думал о подобном решении, но задавался вопросом, есть ли что-то встроенное в реализацию сокета Phoenix. Я отмечу это как ответ, если этого не произойдет. – user1595077

+2

Phoenix делает именно то, что https://github.com/phoenixframework/phoenix/blob/v1.2/web/static/js/phoenix.js#L546 Я бы рекомендовал придерживаться стандартной реализации, он обрабатывает гораздо больше таких вещей, как резервное копирование для браузеров, не поддерживающих веб-порты, автоматическое повторное подключение при возникновении проблем с подключением, локальная буферизация сообщений, когда клиент находится в автономном режиме, обработка информации о присутствии и т. д. Тем не менее это всего около 500 LOC (считается с 'cloc'). Кроме того, вы не получите исправлений и обновлений для официального клиента. Очень рекомендую придерживаться стандартного решения. –

+0

@PatrickOscity Спасибо Патрику. Я никогда не работал с Phoenix или Elixir, поэтому я не знал деталей структуры. Просто дал общее решение. Я согласен с тем, что OP, если это возможно, должна использовать возможности структуры. –

1

phoenix backend ожидает пинг каждые 30 секунд. Вы можете повторно настроить его так:

defmodule UserSocket do 
    use Phoenix.Socket 

    ## Transports 
    transport :websocket, Phoenix.Transports.WebSocket, 
    timeout: 300_000, # 5 minutes 
    transport_log: :debug 
    ... 

end 

Если вы не заботитесь для тайм-аута вы можете установить его на очень высоком уровне. приведенный выше код устанавливает его в 5 минут.

В общем, phoenix.js реализует все это для вас. Это очень маленькая библиотека. Вы найдете в конце, что вы реализовали все, что есть в lib, с кучей вещей, которые вы получили не так :-)

Смежные вопросы