Add vsock-backed SSH session reminders
Remind users when a VM is still running after hanger vm ssh exits instead of silently dropping them back to the host shell.\n\nAttach a Firecracker vsock device to each VM, persist the host vsock path/CID,\nadd a new guest-side banger-vsock-pingd responder to the runtime bundle and both\nimage-build paths, and expose a vm.ping RPC that the CLI and TUI call after SSH\nreturns. Doctor and start/build preflight now validate the helper plus\n/dev/vhost-vsock so the feature fails early and clearly.\n\nValidated with go mod tidy, bash -n customize.sh, git diff --check, make build,\nand GOCACHE=/tmp/banger-gocache go test ./... outside the sandbox because the\ndaemon tests need real Unix/UDP sockets. Rebuild the image/rootfs used for new\nVMs so the guest ping service is present.
This commit is contained in:
parent
4930d82cb9
commit
08ef706e3f
31 changed files with 912 additions and 75 deletions
|
|
@ -4,7 +4,9 @@ import (
|
|||
"bytes"
|
||||
"context"
|
||||
"errors"
|
||||
"io"
|
||||
"os"
|
||||
"os/exec"
|
||||
"path/filepath"
|
||||
"reflect"
|
||||
"strings"
|
||||
|
|
@ -209,6 +211,56 @@ func TestVMSetParamsFromFlagsRejectsNonPositiveCPUAndMemory(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestRunSSHSessionPrintsReminderWhenPingAlive(t *testing.T) {
|
||||
origSSHExec := sshExecFunc
|
||||
origPing := vmPingFunc
|
||||
t.Cleanup(func() {
|
||||
sshExecFunc = origSSHExec
|
||||
vmPingFunc = origPing
|
||||
})
|
||||
|
||||
sshExecFunc = func(ctx context.Context, stdin io.Reader, stdout, stderr io.Writer, args []string) error {
|
||||
return nil
|
||||
}
|
||||
vmPingFunc = func(ctx context.Context, socketPath, idOrName string) (api.VMPingResult, error) {
|
||||
return api.VMPingResult{Name: "devbox", Alive: true}, nil
|
||||
}
|
||||
|
||||
var stderr bytes.Buffer
|
||||
if err := runSSHSession(context.Background(), "/tmp/bangerd.sock", "devbox", strings.NewReader(""), &bytes.Buffer{}, &stderr, []string{"root@127.0.0.1"}); err != nil {
|
||||
t.Fatalf("runSSHSession: %v", err)
|
||||
}
|
||||
if !strings.Contains(stderr.String(), "devbox is still running") {
|
||||
t.Fatalf("stderr = %q, want reminder", stderr.String())
|
||||
}
|
||||
}
|
||||
|
||||
func TestRunSSHSessionPreservesSSHExitStatusOnPingWarning(t *testing.T) {
|
||||
origSSHExec := sshExecFunc
|
||||
origPing := vmPingFunc
|
||||
t.Cleanup(func() {
|
||||
sshExecFunc = origSSHExec
|
||||
vmPingFunc = origPing
|
||||
})
|
||||
|
||||
sshExecFunc = func(ctx context.Context, stdin io.Reader, stdout, stderr io.Writer, args []string) error {
|
||||
return &exec.ExitError{}
|
||||
}
|
||||
vmPingFunc = func(ctx context.Context, socketPath, idOrName string) (api.VMPingResult, error) {
|
||||
return api.VMPingResult{}, errors.New("dial failed")
|
||||
}
|
||||
|
||||
var stderr bytes.Buffer
|
||||
err := runSSHSession(context.Background(), "/tmp/bangerd.sock", "devbox", strings.NewReader(""), &bytes.Buffer{}, &stderr, []string{"root@127.0.0.1"})
|
||||
var exitErr *exec.ExitError
|
||||
if !errors.As(err, &exitErr) {
|
||||
t.Fatalf("runSSHSession error = %v, want exit error", err)
|
||||
}
|
||||
if !strings.Contains(stderr.String(), "failed to check whether devbox is still running") {
|
||||
t.Fatalf("stderr = %q, want warning", stderr.String())
|
||||
}
|
||||
}
|
||||
|
||||
func TestResolveVMTargetsDeduplicatesAndReportsErrors(t *testing.T) {
|
||||
vms := []model.VMRecord{
|
||||
testCLIResolvedVM("alpha-id", "alpha"),
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue