-
Notifications
You must be signed in to change notification settings - Fork 4
feat: Support keep-alive messages #3
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
Conversation
_examples/ssh-keepalive/keepalive.go
Outdated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is it possible to add a test for this case? Start up a server with a low timeout, validate that
- Without keepalives, connection times out
- With keepalives, connection stays up
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I managed to cover 2. with session stats, so we can ensure what was called and how many times.
Unfortunately, I can't address 1. easily as intercepting SSH connection on request level is not possible. Long story short, I don't know how to deny the SSH client from responding to keep-alive requests.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I tried out both ClientAliveInterval
and ServerAliveInterval
and they are working wonderfully.
One weird thing I noticed is that openssh's server actually seems to reply with SSH_MSG_REQUEST_FAILURE
(82) while we are now replying with SSH_MSG_REQUEST_SUCCESS
(81).
Similarly, the openssh client replies with SSH_MSG_CHANNEL_FAILURE
(100).
Seems like odd behavior on openssh
's part and the implementation here is better but I thought I would mention it in case there is some reason it is supposed to reply with failures (or maybe I am just doing something wrong).
I had a similar observation. I tried with some other existing SSH servers, and my Mac SSH client behaves the same way - it replies with a failure. TL;DR I added a comment paragraph describing the anomaly. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I tried it out and it appears to work fine.
Found a couple of data races though.
|
||
t.Run("Server terminates connection due to no keep-alive replies", func(t *testing.T) { | ||
t.Parallel() | ||
t.Skip("Go SSH client doesn't support disabling replies to keep-alive requests. We can't test it easily without mocking logic.") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
😢
This is a great finding, Cian. I forgot to run this with race flag and discovered a can of worms. It looks like using I'm afraid that I have to start it over 💀
|
Ok, I refactored the code by extracting the |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
All in all implementation logic seems solid, but some minor things came up.
I'm mainly concerned about us diverging from OpenSSH with the message types (see comment), why don't we mimic the behavior?
Related: coder/coder#7581
This PR enables SSH server support for keep-alive messages. It introduces 2 more configuration options:
ClientAliveInterval
andClientAliveCountMax
.This library is relatively old and not really covered with tests. I can add some if you find them beneficial.
How to test it (as CI doesn't start any tests):
Tab 1:
Tab 2: