Skip to content

Commit 5b753fe

Browse files
committed
feat(as): add ssh verb on the server resource to connect to a server
1 parent ee2e9bc commit 5b753fe

File tree

4 files changed

+125
-0
lines changed

4 files changed

+125
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
🎲🎲🎲 EXIT CODE: 0 🎲🎲🎲
2+
🟥🟥🟥 STDERR️️ 🟥🟥🟥️
3+
Connect to distant server via the SSH protocol.
4+
5+
USAGE:
6+
scw apple-silicon server ssh <server-id ...> [arg=value ...]
7+
8+
ARGS:
9+
server-id Server ID to SSH into
10+
[username=m1] Username used for the SSH connection
11+
[port=22] Port used for the SSH connection
12+
[command] Command to execute on the remote server
13+
[zone=fr-par-1] Zone to target. If none is passed will use default zone from the config
14+
15+
FLAGS:
16+
-h, --help help for ssh
17+
18+
GLOBAL FLAGS:
19+
-c, --config string The path to the config file
20+
-D, --debug Enable debug mode
21+
-o, --output string Output format: json or human, see 'scw help output' for more info (default "human")
22+
-p, --profile string The config profile to use

cmd/scw/testdata/test-all-usage-apple-silicon-server-usage.golden

+1
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ AVAILABLE COMMANDS:
1212
list List all servers
1313
reboot Reboot a server
1414
reinstall Reinstall a server
15+
ssh SSH into a server
1516
update Update a server
1617

1718
FLAGS:

internal/namespaces/applesilicon/v1alpha1/custom.go

+4
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,10 @@ import (
99
func GetCommands() *core.Commands {
1010
cmds := GetGeneratedCommands()
1111

12+
cmds.Merge(core.NewCommands(
13+
serverSSHCommand(),
14+
))
15+
1216
human.RegisterMarshalerFunc(applesilicon.ServerStatus(""), human.EnumMarshalFunc(serverStatusMarshalSpecs))
1317

1418
return cmds
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
package applesilicon
2+
3+
import (
4+
"context"
5+
"fmt"
6+
"os/exec"
7+
"reflect"
8+
9+
"github.com/scaleway/scaleway-cli/internal/core"
10+
applesilicon "github.com/scaleway/scaleway-sdk-go/api/applesilicon/v1alpha1"
11+
"github.com/scaleway/scaleway-sdk-go/scw"
12+
)
13+
14+
type serverSSHConnectRequest struct {
15+
Zone scw.Zone
16+
ServerID string
17+
Username string
18+
Port uint
19+
Command string
20+
}
21+
22+
func serverSSHCommand() *core.Command {
23+
return &core.Command{
24+
Short: `SSH into a server`,
25+
Long: `Connect to distant server via the SSH protocol.`,
26+
Namespace: "apple-silicon",
27+
Verb: "ssh",
28+
Resource: "server",
29+
ArgsType: reflect.TypeOf(serverSSHConnectRequest{}),
30+
ArgSpecs: core.ArgSpecs{
31+
{
32+
Name: "server-id",
33+
Short: "Server ID to SSH into",
34+
Required: true,
35+
Positional: true,
36+
},
37+
{
38+
Name: "username",
39+
Short: "Username used for the SSH connection",
40+
Default: core.DefaultValueSetter("m1"),
41+
},
42+
{
43+
Name: "port",
44+
Short: "Port used for the SSH connection",
45+
Default: core.DefaultValueSetter("22"),
46+
},
47+
{
48+
Name: "command",
49+
Short: "Command to execute on the remote server",
50+
},
51+
core.ZoneArgSpec(),
52+
},
53+
Run: serverSSHRun,
54+
}
55+
}
56+
57+
func serverSSHRun(ctx context.Context, argsI interface{}) (i interface{}, e error) {
58+
args := argsI.(*serverSSHConnectRequest)
59+
60+
client := core.ExtractClient(ctx)
61+
asAPI := applesilicon.NewAPI(client)
62+
serverResp, err := asAPI.GetServer(&applesilicon.GetServerRequest{
63+
Zone: args.Zone,
64+
ServerID: args.ServerID,
65+
})
66+
if err != nil {
67+
return nil, err
68+
}
69+
70+
if serverResp.Status != applesilicon.ServerStatusReady {
71+
return nil, &core.CliError{
72+
Err: fmt.Errorf("server is not ready"),
73+
Details: fmt.Sprintf("Server %s currently in %s", serverResp.Name, serverResp.Status),
74+
}
75+
}
76+
77+
sshArgs := []string{
78+
serverResp.IP.String(),
79+
"-p", fmt.Sprintf("%d", args.Port),
80+
"-l", args.Username,
81+
"-t",
82+
}
83+
if args.Command != "" {
84+
sshArgs = append(sshArgs, args.Command)
85+
}
86+
87+
sshCmd := exec.Command("ssh", sshArgs...)
88+
89+
exitCode, err := core.ExecCmd(ctx, sshCmd)
90+
if err != nil {
91+
return nil, err
92+
}
93+
if exitCode != 0 {
94+
return nil, &core.CliError{Empty: true, Code: exitCode}
95+
}
96+
97+
return &core.SuccessResult{Empty: true}, nil
98+
}

0 commit comments

Comments
 (0)