@@ -15,8 +15,9 @@ import (
15
15
"gopkg.in/yaml.v2"
16
16
17
17
"github.com/aws/aws-sdk-go/aws/credentials"
18
- pb "github.com/otm/ims /proto"
18
+ pb "github.com/otm/limes /proto"
19
19
"google.golang.org/grpc"
20
+ "google.golang.org/grpc/codes"
20
21
"google.golang.org/grpc/grpclog"
21
22
)
22
23
@@ -46,15 +47,15 @@ func newCliClient(address string) *cliClient {
46
47
}
47
48
48
49
// StartService bootstraps the metadata service
49
- func StartService (args * Start ) {
50
+ func StartService (configFile , adress , profileName , MFA string , fake bool ) {
50
51
log := & ConsoleLogger {}
51
52
config := Config {}
52
53
53
54
// TODO: Move to function and use a default configuration file
54
- if args . ConfigFile != "" {
55
+ if configFile != "" {
55
56
// Parse in options from the given config file.
56
- log .Debug ("Loading configuration from %s\n " , args . ConfigFile )
57
- configContents , configErr := ioutil .ReadFile (args . ConfigFile )
57
+ log .Debug ("Loading configuration from %s\n " , configFile )
58
+ configContents , configErr := ioutil .ReadFile (configFile )
58
59
if configErr != nil {
59
60
log .Fatalf ("Could not read from config file. The error was: %s\n " , configErr .Error ())
60
61
}
@@ -69,7 +70,7 @@ func StartService(args *Start) {
69
70
70
71
defer func () {
71
72
log .Debug ("Removing UNIX socket.\n " )
72
- os .Remove (args . Adress )
73
+ os .Remove (adress )
73
74
}()
74
75
75
76
// Startup the HTTP server and respond to requests.
@@ -81,11 +82,16 @@ func StartService(args *Start) {
81
82
log .Fatalf ("Could not startup the metadata interface: %s\n " , err )
82
83
}
83
84
84
- if args . MFA == "" {
85
- args . MFA = checkMFA (config )
85
+ if MFA == "" {
86
+ MFA = checkMFA (config )
86
87
}
87
88
88
- credsManager := NewCredentialsExpirationManager (config , args .MFA )
89
+ var credsManager CredentialsManager
90
+ if fake {
91
+ credsManager = & FakeCredentialsManager {}
92
+ } else {
93
+ credsManager = NewCredentialsExpirationManager (profileName , config , MFA )
94
+ }
89
95
90
96
mds , metadataError := NewMetadataService (listener , credsManager )
91
97
if metadataError != nil {
@@ -94,7 +100,7 @@ func StartService(args *Start) {
94
100
mds .Start ()
95
101
96
102
stop := make (chan struct {})
97
- agentServer := NewCliHandler (args . Adress , credsManager , stop , config )
103
+ agentServer := NewCliHandler (adress , credsManager , stop , config )
98
104
err = agentServer .Start ()
99
105
if err != nil {
100
106
log .Fatalf ("Could not start agentServer: %s\n " , err .Error ())
@@ -139,8 +145,9 @@ func (c *cliClient) stop(args *Stop) error {
139
145
}
140
146
141
147
func (c * cliClient ) status (args * Status ) error {
142
- status := "up"
148
+ status := true
143
149
150
+ service := "up"
144
151
r , err := c .srv .Status (context .Background (), & pb.Void {})
145
152
if err != nil {
146
153
r = & pb.StatusReply {
@@ -150,41 +157,68 @@ func (c *cliClient) status(args *Status) error {
150
157
SessionToken : "n/a" ,
151
158
Expiration : "n/a" ,
152
159
}
153
- status = "down"
154
- defer fmt .Fprintf (os .Stderr , "\n communication error: %v\n " , err )
160
+ service = "down"
161
+ status = false
162
+
163
+ showCorrectionAndExit (err )
164
+ defer fmt .Fprintf (errout , "\n error communicating with daemon: %v\n " , err )
155
165
}
156
166
157
167
if r .Error != "" {
158
- status = "error"
159
- defer fmt .Fprintf (os .Stderr , "\n error retrieving status: %v\n " , r .Error )
168
+ service = "error"
169
+ status = false
170
+ defer fmt .Fprintf (errout , "\n error communication with daemon: %v\n " , r .Error )
160
171
}
161
172
162
173
env := "ok"
163
174
errConf := checkActiveAWSConfig ()
164
175
if errConf != nil {
165
176
env = "nok"
166
- defer fmt .Fprintf (os .Stderr , "\n warning: %v\n " , errConf )
177
+ status = false
178
+ defer fmt .Fprintf (errout , "run 'limes fix' to automaticly resolv the problem\n " )
179
+ defer fmt .Fprintf (errout , "\n warning: %v\n " , errConf )
167
180
}
168
181
169
- fmt .Printf ("Server: %v\n " , status )
170
- fmt .Printf ("AWS Config: %v\n " , env )
171
- fmt .Printf ("Role: %v\n " , r .Role )
182
+ if ! status {
183
+ fmt .Fprintf (out , "Status: %v\n " , "nok" )
184
+ } else {
185
+ fmt .Fprintf (out , "Status: %v\n " , "ok" )
186
+ }
187
+ fmt .Fprintf (out , "Role: %v\n " , r .Role )
172
188
173
189
if args .Verbose == false {
174
190
return err
175
191
}
176
192
177
- fmt .Printf ("AccessKeyId: %v\n " , r .AccessKeyId )
178
- fmt .Printf ("SecretAccessKey: %v\n " , r .SecretAccessKey )
179
- fmt .Printf ("SessionToken: %v\n " , r .SessionToken )
180
- fmt .Printf ("Expiration: %v\n " , r .Expiration )
193
+ fmt .Fprintf (out , "Server: %v\n " , service )
194
+ fmt .Fprintf (out , "AWS Config: %v\n " , env )
195
+ fmt .Fprintf (out , "AccessKeyId: %v\n " , r .AccessKeyId )
196
+ fmt .Fprintf (out , "SecretAccessKey: %v\n " , r .SecretAccessKey )
197
+ fmt .Fprintf (out , "SessionToken: %v\n " , r .SessionToken )
198
+ fmt .Fprintf (out , "Expiration: %v\n " , r .Expiration )
181
199
182
200
return err
183
201
}
184
202
185
- func (c * cliClient ) assumeRole (role string , args * SwitchProfile ) error {
186
- r , err := c .srv .AssumeRole (context .Background (), & pb.AssumeRoleRequest {Name : role })
203
+ func (c * cliClient ) assumeRole (role string , MFA string ) error {
204
+ r , err := c .srv .AssumeRole (context .Background (), & pb.AssumeRoleRequest {Name : role , Mfa : MFA })
205
+ if err != nil {
206
+ if grpc .Code (err ) == codes .FailedPrecondition && grpc .ErrorDesc (err ) == errMFANeeded .Error () {
207
+ return c .assumeRole (role , askMFA ())
208
+ }
209
+
210
+ fmt .Fprintf (os .Stderr , "error: %v\n " , err )
211
+ return err
212
+ }
213
+
214
+ fmt .Fprintf (out , "Assumed: %v\n " , r .Role )
215
+ return nil
216
+ }
217
+
218
+ func (c * cliClient ) setSourceProfile (role , MFA string ) error {
219
+ r , err := c .srv .SetCredentials (context .Background (), & pb.AssumeRoleRequest {Name : role , Mfa : MFA })
187
220
if err != nil {
221
+ showCorrectionAndExit (err )
188
222
fmt .Fprintf (os .Stderr , "communication error: %v\n " , err )
189
223
return err
190
224
}
@@ -201,6 +235,7 @@ func (c *cliClient) assumeRole(role string, args *SwitchProfile) error {
201
235
func (c * cliClient ) retreiveRole (role string ) (* credentials.Credentials , error ) {
202
236
r , err := c .srv .RetrieveRole (context .Background (), & pb.AssumeRoleRequest {Name : role })
203
237
if err != nil {
238
+ showCorrectionAndExit (err )
204
239
fmt .Fprintf (os .Stderr , "communication error: %v\n " , err )
205
240
return nil , err
206
241
}
@@ -219,6 +254,23 @@ func (c *cliClient) retreiveRole(role string) (*credentials.Credentials, error)
219
254
return creds , nil
220
255
}
221
256
257
+ // Config(ctx context.Context, in *Void, opts ...grpc.CallOption) (*ConfigReply, error)
258
+ func (c * cliClient ) listRoles () ([]string , error ) {
259
+ r , err := c .srv .Config (context .Background (), & pb.Void {})
260
+ if err != nil {
261
+ showCorrectionAndExit (err )
262
+ fmt .Fprintf (os .Stderr , "communication error: %v\n " , err )
263
+ return nil , err
264
+ }
265
+
266
+ roles := make ([]string , 0 , len (r .Profiles ))
267
+ for role := range r .Profiles {
268
+ roles = append (roles , role )
269
+ }
270
+
271
+ return roles , nil
272
+ }
273
+
222
274
func checkMFA (config Config ) string {
223
275
var MFA string
224
276
@@ -235,3 +287,30 @@ func checkMFA(config Config) string {
235
287
236
288
return MFA
237
289
}
290
+
291
+ // ask the user for an MFA token
292
+ func askMFA () string {
293
+ var MFA string
294
+
295
+ fmt .Printf ("Enter MFA: " )
296
+ _ , err := fmt .Scanf ("%s" , & MFA )
297
+ if err != nil {
298
+ log .Fatalf ("err: %v\n " , err )
299
+ }
300
+
301
+ return MFA
302
+ }
303
+
304
+ func showCorrectionAndExit (err error ) {
305
+ if grpc .Code (err ) == codes .FailedPrecondition {
306
+ if grpc .ErrorDesc (err ) == errMFANeeded .Error () {
307
+ fmt .Fprintf (errout , "%v: run 'limes credentials --mfa <serial>'\n " , grpc .ErrorDesc (err ))
308
+ os .Exit (1 )
309
+ }
310
+
311
+ if grpc .ErrorDesc (err ) == errUnknownProfile .Error () {
312
+ fmt .Fprintf (errout , "%v: run 'limes --profile <name> credentials [--mfa <serial>]'\n " , grpc .ErrorDesc (err ))
313
+ os .Exit (1 )
314
+ }
315
+ }
316
+ }
0 commit comments