Android 앱에서 사용할 WebSocket 라이브러리는 무엇입니까? [닫은]


131

WebSocket 연결을 유지하면서 (몇 시간 또는 며칠 이상) 백그라운드에서 실행 되며 정기적으로 서버에 일부 데이터를 보내는 내 Android 앱에 서비스 를 추가하고 싶습니다 .

이제 Java 용 WebSocket 라이브러리가 많이있는 것 같습니다. 어떤 라이브러리를 사용해야하는지 잘 모르겠습니다.

또한 Android 용 기본 socket.io 클라이언트 라이브러리가 있습니다.

  • nkzawa / socket.io-client.java GitHub의 설명 : Socket.IO v1.0 이상과 호환되는 Java 용 전 기능 Socket.IO 클라이언트 라이브러리.

어쨌든 웹 프론트 엔드에 nodejs / socket.io를 사용할 계획이기 때문에 socket.io Android 클라이언트를 사용하는 것이 편리합니다. 그러나 네이티브 클라이언트는 상당히 어리고 몇 가지 공개 된 문제가 있습니다. 또한 WebSocket 지원이 클라이언트 측에서 보장 될 수 있기 때문에 안드로이드 앱이 socket.io 클라이언트 라이브러리 (socket.io 1.0 서버와 호환되는 것을 제외하고)를 사용하는 이점이 없다는 것을 이해합니다. .

내 요구 사항은 다음과 같습니다.

  • Android API 9 이상과의 호환성
  • SSL을 통한 연결 가능성
  • 영구적 인 깨우기 잠금을 유지하지 않고도 오랫동안 연결 유지
  • 사용 가능한 nodejs websocket 서버 구현 또는 socket.io와의 호환성

이러한 요구 사항에 적합한 라이브러리 중 어떤 것이 있습니까?


아마도 분위기 . 이 질문을 참조하십시오 .
Basil Bourque

2
WebSocket이나 Atmosphere의 전문가가 아닙니다. Atmosphere는 WebSocket 지원을 포함하여 Push 기능을 위해 많은 프로젝트에서 사용되는 것으로 잘 알려져 있습니다. 내 유일한 경험은 Vaadin 웹 앱 을 빌드하는 데 간접적 입니다. Vaadin은 자동 푸시 기능을 위해 Atmosphere를 사용합니다. 그러나 WebSocket은 간단한 역사 동안 정의, 사양 및 다양한 구현에 대한 많은 변경 사항으로 인해 여전히 비교적 새롭습니다. 따라서 어떻게 든 "문제"를 기대하십시오.
Basil Bourque

2
참고로, 아우토반은 거기에 있으며 화려한 웹 사이트가 있습니다. 그러나 설치 및 실행에 시간을 할애 할 때까지 "보안 웹 소켓이 구현되지 않음"에 유의하십시오. 다음.
cloudsurfin

1
귀하의 질문에 언급 한 것과 동일한 요구 사항을 겪었으므로 okhttp로 모든 요구 사항을 충족시키는 데 도움이되었습니다. 버전 3.5의 도입 이후 웹 소켓을 지원하므로 okHttp (웹 서비스 호출 + 웹 소켓 지원)를 사용하는 이점이 있습니다. 시작하는 링크는 다음과 같습니다. < medium.com/@ssaurel/… >
Kaleem Patel

7
이와 같은 질문은 종결되어서는 안됩니다.
Martin Berger

답변:


123

몇 가지 메모.

  • koush / AndroidAsyncRFC 6455에 필요한 닫기 핸드 셰이크 를 수행하지 않습니다 . 자세한 내용은 이것을 참조 하십시오.

  • Project Tyrus 는 Android에서 작동하지만 라이센스 ( CDL이 포함 된 CDDL 1.1 및 GPL 2 ) 및 크기 ( ProGuard로 WebSocket 클라이언트 jar 크기 줄이기 )가 요구 사항을 충족하는지 확인하십시오. 또한 텍스트 크기가 크면 Tyrus에서 예외가 발생할 수 있습니다 (버그 일 수 있음). 자세한 내용은 이것을 참조 하십시오.

  • Jetty : 부두 사용자 메일 링리스트 의 2 년 전 이메일 스레드"현재 Android 호환 Jetty 9 WebSocket 클라이언트가 없습니다. Android 용 Jetty WebSocket 클라이언트를 JDK 7에서 JDK 5/6으로 백 포트 할 계획이 있습니다. JSR-356 Java WebSocket API (javax.websocket) 구현을 완료하는 것보다 우선 순위가 낮습니다. " WebSocket Client API에 대한 Jetty의 현재 문서 에는 Android에 대한 언급이 없습니다.

  • codebutler / android-websocketRFC 6455에 필요한 닫기 핸드 셰이크 를 수행하지 않으며 닫기시 예외를 throw 할 수 있습니다. 참조 .

  • Atmosphere / wasyncAsyncHttpClient / async-http-client 를 WebSocket 구현으로 사용합니다. 대신 AsyncHttpClient / async-http-client를 대신 언급해야합니다.

  • firebase / TubeSock 이 확인하지 않습니다 Sec-WebSocket-Accept. 이것은 RFC 6455 에 대한 위반 입니다. 또한 TubeSock은 문자 메시지 작성에 버그가 있습니다. 문자 메시지에 멀티 바이트 UTF-8 문자를 사용하면 조만간 버그가 발생합니다. TubeSock 문제에 대한 자세한 목록은 delight-im / Android-DDP의 이슈 3 을 참조하십시오 .

고려 사항

Java로 작성된 WebSocket 클라이언트 구현을 선택할 때 고려해야 할 사항 :

  1. 준수 . RFC 6455에 필요한 클로징 핸드 셰이크를 구현하는 것은 소수의 구현이 아닙니다 . (닫는 악수를 구현하지 않을 경우 어떻게됩니까?를 참조하십시오 .)
  2. 필수 Java 버전 . Java SE 5, 6, 7, 8 또는 Java EE? 안드로이드에서도 작동합니까?
  3. 크기 . 일부 구현에는 많은 종속성이 있습니다.
  4. wss 지원.
  5. HTTP 프록시 지원
  6. HTTP 프록시 지원을 통한 WSSS . HTTP 프록시를 통한 wss를 지원하기 위해 WebSocket 클라이언트 라이브러리가 수행해야하는 작업에 대해서는 HTML5 웹 소켓이 프록시 서버와 상호 작용하는 방법의 그림 2를 참조하십시오 .
  7. SSL 구성에 대한 유연성 . SSLSocketFactorySSLContext불필요한 제한없이 활용 될 수 있어야한다.
  8. 기본 인증을 포함 하여 오프닝 핸드 셰이크 의 사용자 정의 HTTP 헤더
  9. 프록시 서버에서의 인증을 포함하여 HTTP 프록시 협상의 사용자 정의 HTTP 헤더
  10. 모든 프레임 유형 (연속, 이진, 텍스트, 닫기, 핑 및 탁구) 을 보낼 수 있습니다 . 대부분의 구현은 개발자에게 조각난 프레임요청하지 않은 퐁 프레임을 수동으로 보내는 수단을 제공하지 않습니다 .
  11. 다양한 WebSocket 이벤트를 수신하기위한 리스너 인터페이스 . 인터페이스가 열악하면 개발자가 좌절합니다. 풍부한 인터페이스를 통해 개발자는 강력한 응용 프로그램을 작성할 수 있습니다.
  12. WebSocket 상태를 조회 할 수 있습니다. RFC 6455 는 CONNECTING, OPEN, CLOSING 및 CLOSED 상태를 정의하지만 정의 된 방식으로 내부 상태 전이를 유지하는 구현은 거의 없습니다.
  13. 소켓 연결에 대한 시간 초과 값을 설정할 수 있습니다 . ( 방법 의 두 번째 인수와 동일 )Socket.connect(SocketAddress endpoint, int timeout)
  14. 기본 원시 소켓에 액세스 할 수 있습니다 .
  15. 사용하기 쉬운 직관적 API .
  16. 문서화 여부
  17. RFC 7692 (WebSocket 용 압축 확장) 지원 (일명 permessage-deflate).
  18. 리디렉션 (3xx) 지원
  19. 다이제스트 인증 지원.

nv-websocket-client 는 마지막 두 개를 제외한 위의 모든 것을 다룹니다. 또한 작지만 편리한 기능 중 하나는 핑 / 퐁 프레임을 주기적으로 보내는 것입니다. setPingInterval/setPongInterval메소드를 호출하여 수행 할 수 있습니다( JavaDoc 참조).

면책 조항 : Takahiko Kawasaki는 nv-websocket-client의 저자입니다.


1
nv-websocket-client 라이브러리가 아직 개발 중입니까? 오류 1006으로 TooTallNate / Java-WebSocket에서 자동 연결 끊김 문제가 발생했으며 이유가 없습니다.이 nv-websocket도 문제를 해결합니까?
Ankit Bansal

1
1006의 경우, 사양 (RFC 6455)은 코드 가 엔드 포인트에 의해 닫기 제어 프레임에서 상태 코드로 설정되어서는 안된다고 명시하고 있습니다 . 이것은 코드가 클라이언트 측에서 생성되었음을 의미합니다. WebSocketListener의onDisconnected 메소드와 onError메소드를 통해 연결 해제에 대한 자세한 정보를 얻을 수 있습니다 . 메소드는 인스턴스를 제공합니다 . 문제가 무엇인지 보려면 메소드를 호출 하십시오. onErrorWebSocketExceptiongetError()
Takahiko Kawasaki

7
wss의 경우 okhttp와 autobahn을 시도했습니다 (이 답변의 자체 홍보도 의심됩니다). 아우토반은 쉽지만 SSL이 없습니다. OkHttp는 거의 통합되지 않은 문서를 가지고있다 (2016 년 2 월). 코드 예제와 예외 사항을 읽는 데 많은 시간을 낭비했습니다. 시간 제한을 0으로 설정하거나 들어오는 메시지를 닫는 등의 해결 방법을 익히지 않아 뼈대 예제가 작동합니다. 그 두 가지 (그리고 나의 좌절감)를 버리고, 나는 nv (새롭게) 잘 문서화되어 있음을 발견했다. 그것은 소란없이 일했다.
cloudsurfin

1
Square / okhttp의 새로운 웹 소켓 지원에 대한 의견이 있으십니까? medium.com/square-corner-blog/…
scorpiodawg

2
OkHttp에 대한 세부 정보를 모릅니다. Authlete, Inc. ( " API 보안 스타트 업 Authlete가 시드 펀딩에서 120 만 달러를 모금했습니다 ") 로 너무 바빠서 죄송합니다 . OkHttp 를 검토하고 고려 사항 목록을 업데이트 할 시간을 할애 할 수 없습니다. 내 대답 이후의 변경 사항에 대해서는 CHANGES.md를 참조하십시오 . OkHttp는 138 명의 공헌자를 가진 큰 프로젝트 인 것 같지만 nv-websocket-client는 나의 취미입니다.
Takahiko Kawasaki

4

다른 고려 사항 :

Tyrus는 Android에서 작동합니다. 그러나 Android 5.0에서 사용하는 SSL 라이브러리는 버그가 있으며 SSL 핸드 셰이크에 실패합니다 . 이것은 최신 버전의 Android에서 수정되어야하지만 Android가 많은 기기에서 업데이트되지 않는 방식으로 인해 문제가 될 수 있습니다.

다른 웹 소켓 구현에 SSL이 구현되는 방식에 따라 문제가 될 수도 있습니다.

AndroidAsync에는이 SSL 문제가 없습니다. 시간 초과를 설정할 수없는 것과 같은 다른 문제가 있습니다 .


3

a)이 파일을 gradle 파일에 추가하십시오

compile 'com.github.nkzawa:socket.io-client:0.3.0'

b) 응용 프로그램 활동에 다음 행을 추가하십시오.

    public class MyApplication extends Application {
     private Socket mSocket;
        {
            try {
               mSocket = IO.socket(Config.getBaseURL());

            } catch (URISyntaxException e) {
                throw new RuntimeException(e);
            }
        }

        public Socket getSocket() {
            return mSocket;
        }
}

c) WebSocket을 호출 한 활동에이 기능을 추가하십시오.

     private void websocketConnection() {
            //Get websocket from application
            MyApplication app = (MyApplication ) getApplication();
            mSocket = app.getSocket();
            mSocket.on(Socket.EVENT_CONNECT, onConnect);
            mSocket.on(Socket.EVENT_DISCONNECT, onDisconnect);
            mSocket.on(Socket.EVENT_CONNECT_ERROR, onConnectError);
            mSocket.on(Socket.EVENT_CONNECT_TIMEOUT, onConnectError);
            mSocket.on("messageFromServer", onNewLocation);
            mSocket.connect();
        } 


    private Emitter.Listener onConnect = new Emitter.Listener() {
        @Override
        public void call(Object... args) {
            runOnUiThread(() -> {
                if (!isConnected) {

                    RequestSocket mRequestSocket = new RequestSocket();

                    mRequestSocket.setToken("anil_singhania");
                   /* your parameter */
                    mSocket.emit("messageFromClient", new Gson().toJson(mRequestSocket));
                    Log.i("Socket Data", new Gson().toJson(mRequestSocket));
                    isConnected = true;
                }
            });
        }
    };

    private Emitter.Listener onDisconnect = args -> runOnUiThread(() -> {
        isConnected = false;
       /* Toast.makeText(getApplicationContext(),
                R.string.disconnect, Toast.LENGTH_LONG).show();*/
    });

    private Emitter.Listener onConnectError = args -> runOnUiThread(() -> {
         /*   Toast.makeText(getApplicationContext(),
            R.string.error_connect, Toast.LENGTH_LONG).show()*/
    });

    private Emitter.Listener onNewLocation = new Emitter.Listener() {
        @Override
        public void call(final Object... args) {
            runOnUiThread(() -> {


            });
        }
    };

이것은 ws : // 프로토콜을 지원하지 않습니다.
Girish Bhutiya
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.