Skip to content

Is it possible to connect to a server that does not have the websocket transport? #660

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
MathiasDrapier opened this issue Apr 19, 2021 · 2 comments
Labels
Milestone

Comments

@MathiasDrapier
Copy link

MathiasDrapier commented Apr 19, 2021

Hello,
I have a Socket.io server that works very well, I can connect with different libraries (python, js etc ...).
But with this library I can't connect. The special thing about my server is that it does not implement the WebSocket transport.

I can connect and exchange messages for about 5 seconds, then I am disconnected.

Here is the error I am getting:

io.socket.engineio.client.EngineIOException: xhr poll error
        at io.socket.engineio.client.Transport.onError(Transport.java:65)
        at io.socket.engineio.client.transports.PollingXHR.access$100(PollingXHR.java:26)
        at io.socket.engineio.client.transports.PollingXHR$6$1.run(PollingXHR.java:129)
        at io.socket.thread.EventThread$2.run(EventThread.java:80)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
        at java.lang.Thread.run(Thread.java:761)
     Caused by: java.net.SocketTimeoutException: timeout
        at okio.Okio$4.newTimeoutException(Okio.java:232)
        at okio.AsyncTimeout.exit(AsyncTimeout.java:285)
        at okio.AsyncTimeout$2.read(AsyncTimeout.java:241)
        at okio.RealBufferedSource.indexOf(RealBufferedSource.java:354)
        at okio.RealBufferedSource.readUtf8LineStrict(RealBufferedSource.java:226)
        at okhttp3.internal.http1.Http1Codec.readHeaderLine(Http1Codec.java:215)
        at okhttp3.internal.http1.Http1Codec.readResponseHeaders(Http1Codec.java:189)
        at okhttp3.internal.http.CallServerInterceptor.intercept(CallServerInterceptor.java:88)
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
        at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:45)
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
        at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:93)
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
        at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:93)
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
        at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:127)
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
        at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:257)
        at okhttp3.RealCall$AsyncCall.execute(RealCall.java:201)
        at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133) 
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607) 
        at java.lang.Thread.run(Thread.java:761) 
     Caused by: java.net.SocketException: Socket operation on non-socket
        at java.net.SocketInputStream.socketRead0(Native Method)
        at java.net.SocketInputStream.read(SocketInputStream.java:151)
        at java.net.SocketInputStream.read(SocketInputStream.java:120)
        at okio.Okio$2.read(Okio.java:140)
        at okio.AsyncTimeout$2.read(AsyncTimeout.java:237)
        at okio.RealBufferedSource.indexOf(RealBufferedSource.java:354) 
        at okio.RealBufferedSource.readUtf8LineStrict(RealBufferedSource.java:226) 
        at okhttp3.internal.http1.Http1Codec.readHeaderLine(Http1Codec.java:215) 
        at okhttp3.internal.http1.Http1Codec.readResponseHeaders(Http1Codec.java:189) 
        at okhttp3.internal.http.CallServerInterceptor.intercept(CallServerInterceptor.java:88) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:45) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:93) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:93) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:127) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:257) 
        at okhttp3.RealCall$AsyncCall.execute(RealCall.java:201) 
        at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32) 
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133) 
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607) 
        at java.lang.Thread.run(Thread.java:761) 

The last part of the stack trace is not always the same, sometimes I have:

Caused by: java.net.SocketException: Socket closed
        at java.net.SocketInputStream.socketRead0(Native Method)
        at java.net.SocketInputStream.read(SocketInputStream.java:151)
        at java.net.SocketInputStream.read(SocketInputStream.java:120)
        at okio.Okio$2.read(Okio.java:140)
        at okio.AsyncTimeout$2.read(AsyncTimeout.java:237)
        at okio.RealBufferedSource.indexOf(RealBufferedSource.java:354) 
        at okio.RealBufferedSource.readUtf8LineStrict(RealBufferedSource.java:226) 
        at okhttp3.internal.http1.Http1Codec.readHeaderLine(Http1Codec.java:215) 
        at okhttp3.internal.http1.Http1Codec.readResponseHeaders(Http1Codec.java:189) 
        at okhttp3.internal.http.CallServerInterceptor.intercept(CallServerInterceptor.java:88) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:45) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:93) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:93) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:127) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:257) 
        at okhttp3.RealCall$AsyncCall.execute(RealCall.java:201) 
        at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32) 
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133) 
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607) 
        at java.lang.Thread.run(Thread.java:761) 

or

Caused by: java.net.SocketTimeoutException: Software caused connection abort
        at java.net.SocketInputStream.socketRead0(Native Method)
        at java.net.SocketInputStream.read(SocketInputStream.java:151)
        at java.net.SocketInputStream.read(SocketInputStream.java:120)
        at okio.Okio$2.read(Okio.java:140)
        at okio.AsyncTimeout$2.read(AsyncTimeout.java:237)
        at okio.RealBufferedSource.indexOf(RealBufferedSource.java:354) 
        at okio.RealBufferedSource.readUtf8LineStrict(RealBufferedSource.java:226) 
        at okhttp3.internal.http1.Http1Codec.readHeaderLine(Http1Codec.java:215) 
        at okhttp3.internal.http1.Http1Codec.readResponseHeaders(Http1Codec.java:189) 
        at okhttp3.internal.http.CallServerInterceptor.intercept(CallServerInterceptor.java:88) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:45) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:93) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:93) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:127) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147) 
        at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121) 
        at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:257) 
        at okhttp3.RealCall$AsyncCall.execute(RealCall.java:201) 
        at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32) 
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133) 
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607) 
        at java.lang.Thread.run(Thread.java:761) 
@darrachequesne
Copy link
Member

Thanks, I could indeed reproduce the behavior.

I guess this is a bug, because a failure to upgrade to WebSocket should not close the connection.

darrachequesne added a commit to socketio/engine.io-client-java that referenced this issue Jul 3, 2022
With the previous value (10 seconds by default), a connection
established with HTTP long-polling was closed if the server did not
send any packet for 10 seconds (the HTTP request would timeout from the
client side).

It will now default to 1 minute, which is above the
`pingInterval + pingTimeout` value from the server.

Note: the connectTimeout and writeTimeout options are left as is (10
seconds), but you may need to increase them depending on your use case:

```
OkHttpClient client = new OkHttpClient.Builder()
	.connectTimeout(20, TimeUnit.SECONDS)
	.readTimeout(1, TimeUnit.MINUTES)
	.writeTimeout(1, TimeUnit.MINUTES)
        .build();
```

Related:

- socketio/socket.io-client-java#491
- socketio/socket.io-client-java#660
darrachequesne added a commit to socketio/engine.io-client-java that referenced this issue Jul 10, 2022
With the previous value (10 seconds by default), a connection
established with HTTP long-polling was closed if the server did not
send any packet for 10 seconds (the HTTP request would timeout from the
client side).

It will now default to 1 minute, which is above the
`pingInterval + pingTimeout` value from the server.

Note: the connectTimeout and writeTimeout options are left as is (10
seconds), but you may need to increase them depending on your use case:

```
OkHttpClient client = new OkHttpClient.Builder()
	.connectTimeout(20, TimeUnit.SECONDS)
	.readTimeout(1, TimeUnit.MINUTES)
	.writeTimeout(1, TimeUnit.MINUTES)
        .build();
```

Related:

- socketio/socket.io-client-java#491
- socketio/socket.io-client-java#660

Backported from fb531fa
@darrachequesne
Copy link
Member

For future readers:

I think this was due to the default readTimeout value of the OkHttp client (10 seconds). It must be increased:

OkHttpClient okHttpClient = new OkHttpClient.Builder()
        .readTimeout(1, TimeUnit.MINUTES) // important for HTTP long-polling
        .build();

IO.Options options = new IO.Options();
options.callFactory = okHttpClient;
options.webSocketFactory = okHttpClient;

Socket socket = IO.socket(URI.create("https://example.com"), options);

See also: socketio/engine.io-client-java@fb531fa

Please reopen if needed.

@darrachequesne darrachequesne added this to the 2.1.0 milestone Jul 10, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants