Почему Flash Media Server не вызывает обработчик application.onDisconnect?

У меня возникла странная проблема в моем приложении Flex/Flashcom. Если клиентское приложение неожиданно отключается от сервера, последний не вызывает функцию обработчика application.onDisconnect. В направлении ведьмы я должен смотреть? Спасибо.

Обновление Я не использую серверные компоненты, но я размещаю это в Linux.

Ответ 1

Как упоминалось Артем Тихомиров (автор вопроса) в своем собственном ответе, мой ответ (я держу там ниже как wiki, для архива).

Настоящий ответ был дано Риком Токио относительно ошибки в Linux и задокументирован в этот поток.

Единственная причина, по которой мой ответ "выбран", состоит в том, что Артем не выбирал другого ответа (или своего ответа) до 7-дневных ограничений, предоставляя мне (первый и самый верхний ответ) половину пунктов награды (75 из 150) автоматически, как описано в этой записи в блоге SO.


Первое свинец:

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

Когда вы разрабатываете приложения, имейте в виду, что использование компонентов вводит явные события onConnectAccept и onConnectReject.

Вам нужно включить код для обработки этих событий.
Когда вы используете компоненты, вы должны изменить оператор application.onConnect в своем серверном коде, чтобы включить обработчики событий application.onConnectAccept и application.onConnectReject.
Последняя строка (в порядке выполнения) вашего обработчика onConnect должна быть либо application.acceptConnection(), либо application.rejectConnection().

Если вашему приложению требуется дополнительный код, следуя явным методам acceptConnection() или rejectConnection(), таким как сообщение о том, что пользователю предоставлено или запрещено разрешение на приложение, вы должны поместить этот код в application.onConnectAccept или application.onConnectReject.

СОВЕТ. Если вы не используете медиакомпоненты, вы не можете использовать application.onConnectAccept и application.onConnectReject.


Затем вы можете проверить любое сообщение об ошибке на панели вывода Flash, например:

Error #2044: NetStatusEvent non pris en charge : level=error, code=NetStream.Play.Failed
    at MethodInfo-1()
Error #2044: NetStatusEvent non pris en charge : level=error, code=NetStream.Record.NoAccess
    at MethodInfo-1()

Это означало бы исключение сервера, не принимаемое во внимание клиентом, заставляя неожиданный выход.

Если клиент считывает поток с сервера, он должен убедиться:

  • NetConnection преуспел
  • NetStreams (вход и выход) прослушивает NET_STATUS

Хороший код понравится:

var status:Function = function( e:NetStatusEvent ):void
{
    trace( "status : " + e.info.code ) ;
    if ( e.info.code == "NetConnection.Connect.Success" )
    {
        streamOut = new NetStream( nc ) ;
        streamOut.addEventListener( NetStatusEvent.NET_STATUS , status ) ;

        streamIn  = new NetStream( nc ) ;
        streamIn.addEventListener( NetStatusEvent.NET_STATUS , status ) ;

        streamOut.attachCamera( cam ) ;
        video.attachNetStream( streamIn ) ;

        streamOut.publish( "private" ) ;
        streamIn.play( "private" ) ;       
    }
}

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

Ответ 2

Если это так, он задокументировал и здесь интересный форум для последующего... в основном на Linux он может работать немного сумасшедшим, например:)

Ответ 3

Возможно, клиент отключен, прежде чем сервер (Flash Media-) "знает" об этом. Таким образом, функция 'onDisconnect' не вызывается (она никогда не вызывается клиентом), пока очень, очень поздно.

Если вы хотите обнаружить (и действовать) "затяжные" разъединения раньше, используйте метод client.getStats().

У меня есть пример примера действий на стороне сервера:

// add method to standard class
Client.prototype.isAlive = function() {
        var stats = this.getStats();
        var timeout_value = 3 * 1000;  // in ms.
        //trace('Measured timeout: ' + stats['ping_rtt']);
        if (stats)
                return (stats['ping_rtt'] < timeout_value);
}

// use this in an interval which traverses the application.clients list
if (! client.isAlive())
    application.disconnect(client);

Вы можете запустить и протестировать это поведение "отсутствует onDisconnect", удалив сетевой кабель из подключенного клиента Flash.