/
client.go
101 lines (86 loc) · 1.99 KB
/
client.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
package service
import (
"bytes"
"crypto/rand"
"crypto/rsa"
"crypto/x509"
"encoding/base64"
"encoding/pem"
"time"
log "github.com/ckeyer/logrus"
"golang.org/x/crypto/ssh"
)
func GenerateSSHKey() (string, string, error) {
privateKey, err := rsa.GenerateKey(rand.Reader, 2048)
if err != nil {
log.Errorf("generate rsa key failed, %s", err)
return "", "", err
}
block := &pem.Block{
Type: "RSA PRIVATE KEY",
Bytes: x509.MarshalPKCS1PrivateKey(privateKey),
}
buf := &bytes.Buffer{}
err = pem.Encode(buf, block)
if err != nil {
return "", "", err
}
priKey := buf.String()
sg, err := ssh.ParsePrivateKey(buf.Bytes())
if err != nil {
return "", "", err
}
buf.Reset()
buf.WriteString(sg.PublicKey().Type())
buf.WriteString(" ")
buf.WriteString(base64.StdEncoding.EncodeToString(sg.PublicKey().Marshal()))
buf.WriteString(" ")
buf.WriteString("robot@nevis.io")
pubKey := buf.String()
return priKey, pubKey, nil
}
func RSAAuthMethod(priKey string) (ssh.AuthMethod, error) {
sg, err := ssh.ParsePrivateKey([]byte(priKey))
if err != nil {
log.Errorf("parse private key failed, %s", err)
return nil, err
}
return ssh.PublicKeys(sg), nil
}
type SSHClient struct {
*ssh.Client
*ssh.Session
WorkDir string
}
func NewSSHClient(user, endporint, priKey string) (*SSHClient, error) {
sg, err := RSAAuthMethod(priKey)
if err != nil {
log.Errorf("get rsa auth method failed, %s", err)
return nil, err
}
cfg := &ssh.ClientConfig{
User: user,
Auth: []ssh.AuthMethod{sg},
HostKeyCallback: ssh.InsecureIgnoreHostKey(),
Timeout: time.Second * 5,
}
cli, err := ssh.Dial("tcp", endporint, cfg)
if err != nil {
log.Errorf("dial ssh failed, %s", err)
return nil, err
}
ss, err := cli.NewSession()
if err != nil {
log.Errorf("get ssh session failed, %s", err)
return nil, err
}
return &SSHClient{cli, ss, ""}, nil
}
func (s *SSHClient) Close() {
if s.Session != nil {
s.Session.Close()
}
if s.Client != nil {
s.Client.Close()
}
}