-
Notifications
You must be signed in to change notification settings - Fork 283
/
defaults.go
145 lines (117 loc) Β· 4.16 KB
/
defaults.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
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
package snow
import (
"context"
"fmt"
"github.com/google/uuid"
"github.com/aws/eks-anywhere/pkg/api/v1alpha1"
"github.com/aws/eks-anywhere/pkg/aws"
"github.com/aws/eks-anywhere/pkg/cluster"
"github.com/aws/eks-anywhere/pkg/filewriter"
"github.com/aws/eks-anywhere/pkg/logger"
"github.com/aws/eks-anywhere/pkg/providers/common"
)
type Defaulters struct {
clientRegistry ClientRegistry
writer filewriter.FileWriter
keyGenerator SshKeyGenerator
uuid uuid.UUID
}
type SshKeyGenerator interface {
GenerateSSHAuthKey(filewriter.FileWriter) (string, error)
}
type DefaultersOpt func(defaulters *Defaulters)
func NewDefaulters(clientRegistry ClientRegistry, writer filewriter.FileWriter, opts ...DefaultersOpt) *Defaulters {
defaulters := &Defaulters{
clientRegistry: clientRegistry,
writer: writer,
keyGenerator: common.SshAuthKeyGenerator{},
uuid: uuid.New(), // In the future if we need a cluster wide uuid that is shared, we should move this call to the dependency factory for reuse.
}
for _, opt := range opts {
opt(defaulters)
}
return defaulters
}
func WithKeyGenerator(generator SshKeyGenerator) DefaultersOpt {
return func(defaulters *Defaulters) {
defaulters.keyGenerator = generator
}
}
// WithUUID will set uuid generated outside of constructor.
func WithUUID(uuid uuid.UUID) DefaultersOpt {
return func(defaulters *Defaulters) {
defaulters.uuid = uuid
}
}
// GenerateDefaultSSHKeys generates ssh key if it doesn't exist already.
func (d *Defaulters) GenerateDefaultSSHKeys(ctx context.Context, machineConfigs map[string]*v1alpha1.SnowMachineConfig, clusterName string) error {
md := NewMachineConfigDefaulters(d)
for _, m := range machineConfigs {
if m.Spec.SshKeyName == "" {
if err := md.SetupDefaultSSHKey(ctx, m, clusterName); err != nil {
return err
}
}
}
return nil
}
type MachineConfigDefaulters struct {
sshKey string
defaulters *Defaulters
}
func NewMachineConfigDefaulters(d *Defaulters) *MachineConfigDefaulters {
return &MachineConfigDefaulters{
defaulters: d,
}
}
// SetupDefaultSSHKey creates and imports a default ssh key to snow devices listed in the snow machine config.
// If not exist, a ssh auth key is generated locally first. Then we loop through the devices in the machine config,
// and import the key to any device that does not have the key. In the end the default ssh key name is assigned to
// the snow machine config.
func (md *MachineConfigDefaulters) SetupDefaultSSHKey(ctx context.Context, m *v1alpha1.SnowMachineConfig, clusterName string) error {
defaultSSHKeyName := md.defaultSSHKeyName(clusterName)
clientMap, err := md.defaulters.clientRegistry.Get(ctx)
if err != nil {
return err
}
if len(md.sshKey) <= 0 {
logger.V(1).Info("SnowMachineConfig SshKey is empty. Creating default key pair", "default key name", defaultSSHKeyName)
md.sshKey, err = md.defaulters.keyGenerator.GenerateSSHAuthKey(md.defaulters.writer)
if err != nil {
return err
}
}
for _, ip := range m.Spec.Devices {
client, ok := clientMap[ip]
if !ok {
return fmt.Errorf("credentials not found for device [%s]", ip)
}
keyExists, err := client.EC2KeyNameExists(ctx, defaultSSHKeyName)
if err != nil {
return fmt.Errorf("describing key pair on snow device [%s]: %v", ip, err)
}
if keyExists {
continue
}
if err = client.EC2ImportKeyPair(ctx, defaultSSHKeyName, []byte(md.sshKey)); err != nil {
return fmt.Errorf("importing key pair on snow device [deviceIP=%s]: %v", ip, err)
}
}
m.Spec.SshKeyName = defaultSSHKeyName
return nil
}
func (md *MachineConfigDefaulters) defaultSSHKeyName(clusterName string) string {
return fmt.Sprintf("%s-%s-%s", defaultAwsSshKeyName, clusterName, md.defaulters.uuid.String())
}
func SetupEksaCredentialsSecret(c *cluster.Config) error {
creds, err := aws.EncodeFileFromEnv(eksaSnowCredentialsFileKey)
if err != nil {
return fmt.Errorf("setting up snow credentials: %v", err)
}
certs, err := aws.EncodeFileFromEnv(eksaSnowCABundlesFileKey)
if err != nil {
return fmt.Errorf("setting up snow certificates: %v", err)
}
c.SnowCredentialsSecret = EksaCredentialsSecret(c.SnowDatacenter, []byte(creds), []byte(certs))
return nil
}