Strophe.js не переподключается после отключения - PullRequest
0 голосов
/ 18 сентября 2018

Я работаю над проектом со сложным взаимодействием между бэкэндом WordPress (для хранения сообщений, сообщений), угловым интерфейсом (Angluar 6x) для взаимодействия с пользователем и сервером eJabber для общения в чате из веб-приложения.
Чтобы добиться этого, я пытаюсь интегрировать strophe.js в платформу Angular.
Метод аутентификации, который я использую, сложен.Когда новый пользователь регистрируется в бэкэнде WordPress с помощью подходящей (угловой) формы, я настраиваю хуки, которые также автоматически подписывают нового пользователя на мой локальный сервер eJabberd.Чтобы управлять аутентификацией, чтобы конечный пользователь не мог дважды вводить свои учетные данные, я установил в eJabberd собственный сценарий extauth (на основе this ), который работает параллельно с пользовательским API WordPress Rest.конечные точки (для этого я использую JWT).
Сценарий extauth работает нормально, и я могу успешно подключиться к своему локальному серверу eJabberd с различными клиентами чата (Adium, сообщения Apple и т. д.).Я могу подключиться (как уже говорилось, используя strophe) к eJabber из моего веб-приложения.

Вот фрагмент кода, который я использую для управления соединением (ChatPanel.Service.ts):

import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';

import { Strophe, $pres } from 'strophe.js';

import { EJABBERD } from 'app/api/api.module';

var chatPanelServiceInstance: any = null;

@Injectable()
export class ChatPanelService
{
    contacts: any[];
    chats: any[];
    user: any;
    client: any;

    // Private
    private _xmppConnectionsString: String = "ws://" + EJABBERD.host + ":5280/ws";
    private _xmppConnection: any = null;

    /**
     * Constructor
     */
    constructor(
    )
    {
        chatPanelServiceInstance = this;
        Strophe.log = (level: any, msg: string) => { console.log(level + ": " + msg); };
    }

    /**
     * Log into eJabberd
     *
     * @param {string} jid      user name
     * @param {string} password password (actually, the user token)
     */
    login(jid: string, password: string): void
    {
        if ( ! this._xmppConnection ) {
            this._xmppConnection = new Strophe.Connection( this._xmppConnectionsString , {'keepalive': true});
        }

        this._xmppConnection.connect(jid+'@'+EJABBERD.host, password, this._onConnect);
    }

    /**
     * Disconnect from eJabberd
     */
    logOut(): void
    {
        if ( this._xmppConnection ) {
            this._xmppConnection.options.sync = true;
            this._xmppConnection.flush();
            this._xmppConnection.disconnect("logout");
            this._xmppConnection = null;
        }
    }

    /**
     * eJabberd XMPP message Handler
     * @param {string} msg Message received
     */
    private _onMessage(msg: string): boolean
    {
        console.log("eJabber Msg: " + msg);

        return true;
    }

    /**
     * eJabberd connection Handler
     * @param {any} status connection result
     */
    private _onConnect(status: any): void
    {
        switch (status) {
            case Strophe.Status.CONNECTING:
                console.log("Connecting to eJabberd...");
                break;
            case Strophe.Status.CONNFAIL:
                console.log("eJabberd connection failed!");
                break;
            case Strophe.Status.DISCONNECTING:
                console.log("Disconnecting from eJabberd...");
                break;
            case Strophe.Status.DISCONNECTED:
                console.log("Disconnected from eJabberd");
                break;
            case Strophe.Status.CONNECTED:
                //handler function  [ onMessage() ]  will be called when the user recieves a new message
                chatPanelServiceInstance._xmppConnection.addHandler(chatPanelServiceInstance._onMessage, null, 'message');

                //Setting our presence in the server. so that everyone can know that we are online
                chatPanelServiceInstance._xmppConnection.send($pres().tree());

                console.log("eJabberd connected!");
                break;
            case Strophe.Status.AUTHENTICATING:
                console.log("eJabberd authenticating...");
                break;
            case Strophe.Status.AUTHFAIL:
                console.log("eJabberd authentication failed!");
                break;
            case Strophe.Status.ERROR:
                console.log("eJabberd generic connection error!");
                break;
            case Strophe.Status.ATTACHED:
                console.log("eJabberd connection attached!");
                break;
            case Strophe.Status.REDIRECT:
                console.log("eJabberd connection redirected!");
                break;
            case Strophe.Status.CONNTIMEOUT:
                console.log("eJabberd connection timeout!");
                break;
            default:
                console.log("eJabberd: Unknow connection status");
        }
    }

Проблема возникает, когда я пытаюсь повторно подключиться к серверу после выхода из системы.

Когда я выхожу из своего веб-приложения (то есть вызывается logout () из моего chatpanel.service), если я пытаюсь войти снова, я не получаю ответа от сервера ejabber.По-видимому, сервер перестает слушать любые дальнейшие запросы от strophe.
Я пробовал как с веб-сокетами, так и с BOSH.Окончательный результат тот же.

Вот снимок консоли браузера:

First, successfull, login (WebSocket)
[Log] Connecting to eJabberd... (main.js, line 8666)
[Log] 1: Websocket open (main.js, line 8626)
[Log] 1: _connect_cb was called (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] 1: SASL authentication succeeded. (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626, x4)
[Log] eJabberd connected! (main.js, line 8687)
[Log] 1: _dataRecv called (main.js, line 8626) 

Logout...
[Log] Disconnecting from eJabberd... (main.js, line 8672)
[Log] 1: Disconnect was called because: logout (main.js, line 8626)
[Log] 1: _doDisconnect was called (main.js, line 8626)
[Log] 1: WebSockets _doDisconnect was called (main.js, line 8626)
[Log] Disconnected from eJabberd (main.js, line 8675)
[Log] 1: Websocket closed (main.js, line 8626)

Second attempt (fails, WebSocket)
[Log] Connecting to eJabberd... (main.js, line 8666)
[Log] 1: Websocket open (main.js, line 8626)
[Log] 1: _connect_cb was called (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] eJabberd authentication failed! (main.js, line 8693)
[Log] 3: WebSocket stream error: connection-timeout - Idle connection (main.js, line 8626)
[Log] eJabberd generic connection error! (main.js, line 8696)
[Log] 1: _doDisconnect was called (main.js, line 8626)
[Log] 1: WebSockets _doDisconnect was called (main.js, line 8626)
[Log] Disconnected from eJabberd (main.js, line 8675)
[Log] 1: Websocket closed (main.js, line 8626)


Successful first login (BOSH)
[Log] Connecting to eJabberd... (main.js, line 8666)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: request id 1.0 posting (main.js, line 8626)
[Log] 0: request id 1.0 state changed to 1 (main.js, line 8626)
[Log] 0: request id 1.1 state changed to 2 (main.js, line 8626)
[Log] 0: request id 1.1 state changed to 3 (main.js, line 8626)
[Log] 0: request id 1.1 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: request id 1 should now be removed (main.js, line 8626)
[Log] 0: request id 1.1 got 200 (main.js, line 8626)
[Log] 1: _connect_cb was called (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: request id 2.0 posting (main.js, line 8626)
[Log] 0: request id 2.0 state changed to 1 (main.js, line 8626)
[Log] 0: request id 2.1 state changed to 2 (main.js, line 8626)
[Log] 0: request id 2.1 state changed to 3 (main.js, line 8626)
[Log] 0: request id 2.1 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: request id 2 should now be removed (main.js, line 8626)
[Log] 0: request id 2.1 got 200 (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] 1: SASL authentication succeeded. (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: request id 3.0 posting (main.js, line 8626)
[Log] 0: request id 3.0 state changed to 1 (main.js, line 8626)
[Log] 0: request id 3.1 state changed to 2 (main.js, line 8626)
[Log] 0: request id 3.1 state changed to 3 (main.js, line 8626)
[Log] 0: request id 3.1 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: request id 3 should now be removed (main.js, line 8626)
[Log] 0: request id 3.1 got 200 (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: request id 4.0 posting (main.js, line 8626)
[Log] 0: request id 4.0 state changed to 1 (main.js, line 8626)
[Log] 0: request id 4.1 state changed to 2 (main.js, line 8626)
[Log] 0: request id 4.1 state changed to 3 (main.js, line 8626)
[Log] 0: request id 4.1 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: request id 4 should now be removed (main.js, line 8626)
[Log] 0: request id 4.1 got 200 (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: request id 5.0 posting (main.js, line 8626)
[Log] 0: request id 5.0 state changed to 1 (main.js, line 8626)
[Log] 0: request id 5.1 state changed to 2 (main.js, line 8626)
[Log] 0: request id 5.1 state changed to 3 (main.js, line 8626)
[Log] 0: request id 5.1 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: request id 5 should now be removed (main.js, line 8626)
[Log] 0: request id 5.1 got 200 (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] eJabberd connected! (main.js, line 8687)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: request id 6.0 posting (main.js, line 8626)
[Log] 0: request id 6.0 state changed to 1 (main.js, line 8626)
[Log] 0: request id 6.1 state changed to 2 (main.js, line 8626)
[Log] 0: request id 6.1 state changed to 3 (main.js, line 8626)
[Log] 0: request id 6.1 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: request id 6 should now be removed (main.js, line 8626)
[Log] 0: request id 6.1 got 200 (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] 1: no requests during idle cycle, sending blank request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: request id 7.0 posting (main.js, line 8626)
[Log] 0: request id 7.0 state changed to 1 (main.js, line 8626)

Logout...
[Log] Disconnecting from eJabberd... (main.js, line 8672)
[Log] 1: Disconnect was called because: logout (main.js, line 8626)
[Log] 1: _sendTerminate was called (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 2 requests (main.js, line 8626)
[Log] 0: _processRequest: first request has readyState of 1 (main.js, line 8626)
[Log] 0: request id 17.0 posting (main.js, line 8626)
[Log] 0: request id 17.0 state changed to 1 (main.js, line 8626)
[Log] 0: request id 17.0 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: _processRequest: first request has readyState of 1 (main.js, line 8626)
[Log] 0: request id 17 should now be removed (main.js, line 8626)
[Log] 0: request id 17.0 got 200 (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] 0: request id 16.1 state changed to 2 (main.js, line 8626)
[Log] 0: request id 16.1 state changed to 3 (main.js, line 8626)
[Log] 0: request id 16.1 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: request id 16 should now be removed (main.js, line 8626)
[Log] 0: request id 16.1 got 200 (main.js, line 8626)
[Log] 1: _dataRecv called (main.js, line 8626)
[Log] 1: _doDisconnect was called (main.js, line 8626)
[Log] Disconnected from eJabberd (main.js, line 8675)

Second attempt (after logout, unsuccessful, BOSH)
[Log] Connecting to eJabberd... (main.js, line 8666)
[Log] 0: _throttledRequestHandler called with 1 requests (main.js, line 8626)
[Log] 0: request id 18.0 posting (main.js, line 8626)
[Log] 0: request id 18.0 state changed to 1 (main.js, line 8626)
[Error] Failed to load resource: the server responded with a status of 404 (Not Found) (b7e98bdb6711295ac7cd2c2d7a139415, line 0)
[Log] 0: request id 18.1 state changed to 2 (main.js, line 8626)
[Log] 0: request id 18.1 state changed to 3 (main.js, line 8626)
[Log] 0: request id 18.1 state changed to 4 (main.js, line 8626)
[Log] 0: removing request (main.js, line 8626)
[Log] 0: _throttledRequestHandler called with 0 requests (main.js, line 8626)
[Log] 0: request id 18 should now be removed (main.js, line 8626)
[Log] 0: request id 18.1 got 200 (main.js, line 8626)
[Log] 1: _connect_cb was called (main.js, line 8626)
[Log] 3: Server did not offer a supported authentication mechanism (main.js, line 8626)
[Log] eJabberd connection failed! (main.js, line 8669)
[Log] 1: _doDisconnect was called (main.js, line 8626)
[Log] Disconnected from eJabberd (main.js, line 8675) 

Как вы можете видеть, с помощью Bosh отладчик говорит мне, что сервер этого не делалпредложите любой подходящий метод аутентификации.
Судя по всему, сервер больше не прослушивает входящие запросы на соединение.Но, как ни странно, если я перезагружу сервер, переподключение пройдет успешно.Похоже, что strophe.js все еще держит что-то открытым даже после завершения процесса отключения, и единственный способ закрыть это - остановить сервер.

Я не уверен, что это проблема strophe.js или проблема конфигурации ejabberd, но я более склонен думать о проблеме клиента (или о том, чего мне не хватает в моем коде), поскольку внешние клиенты могутбезупречно подключаться к серверу.

Любая подсказка будет принята с благодарностью.

1 Ответ

0 голосов
/ 18 сентября 2018

Понял.
Я выкладываю здесь, в качестве ответа для тех, кто сталкивался с подобной проблемой.
Проблема была не в Strophe.js, а в конфигурации сервера jabber.Проблема была в кешировании.

Из документов eJabber ( здесь )

auth_use_cache: false | true: Начиная с ejabberd 17.06, кэширование получило полный пересмотр,Вместо extauth_cache набор новых переменных описывает поведение кэша, и значение по умолчанию теперь равно true.Обратите внимание, что кэширование мешает поддерживать несколько паролей для каждой учетной записи.Поэтому, если ваш механизм аутентификации поддерживает пароли для приложений, кэширование должно быть отключено.

eJabberd настроен на использование кэширования по умолчанию для всего, где оно применимо.
С тех пор, как я выхожу из своегоВ веб-приложении я аннулировал старый веб-токен JSON, используемый для аутентификации, ejabber проверяет новые учетные данные на соответствие кэшированному значению, обнаруживая, таким образом, несоответствие.
Решение состоит в том, чтобы отключить кэширование следующим образом (в ejabberd.yml) auth_use_cache: false

...