Skip to content

Commit 1b8f1b1

Browse files
author
Mike Morris
committed
lookup mfa_serial in source_profile section if not found in specified profile
Attempt to look up the mfa_serial in source_profile if not found in the provided profile. Allows us to simplify the config file a bit at the expense of full compatibility with awscli (AWS SDKs in general?) Updated README with example on how this works
1 parent cf9dc33 commit 1b8f1b1

File tree

3 files changed

+46
-13
lines changed

3 files changed

+46
-13
lines changed

AWSConfigParser.go

Lines changed: 29 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -17,9 +17,26 @@ type AWSConfigParser struct {
1717
Logger *logo.Logger
1818
}
1919

20+
func (p *AWSConfigParser) lookupProfile(profile *string, cfg *ini.File) (*AWSProfile, error) {
21+
p.Logger.Debug("In lookupProfile()")
22+
section := "default"
23+
24+
if *profile != "default" {
25+
section = "profile " + *profile
26+
}
27+
28+
p.Logger.Debugf("Looking for profile data in section: '%s'", section)
29+
profile_t := &AWSProfile{SourceProfile: *profile}
30+
err := cfg.Section(section).MapTo(profile_t)
31+
if err != nil {
32+
return nil, err
33+
}
34+
35+
return profile_t, nil
36+
}
37+
2038
func (p *AWSConfigParser) GetProfile(profile *string) (*AWSProfile, error) {
2139
p.Logger.Debug("In GetProfile()")
22-
section := "default"
2340

2441
cfg, err := p._readConfig()
2542
if err != nil {
@@ -28,17 +45,21 @@ func (p *AWSConfigParser) GetProfile(profile *string) (*AWSProfile, error) {
2845

2946
cfg.BlockMode = false
3047

31-
if *profile != "default" {
32-
section = "profile " + *profile
33-
}
34-
35-
p.Logger.Debugf("Looking for profile data in section: '%s'", section)
36-
profile_t := &AWSProfile{SourceProfile: *profile}
37-
err = cfg.Section(section).MapTo(profile_t)
48+
profile_t, err := p.lookupProfile(profile, cfg)
3849
if err != nil {
3950
return nil, err
4051
}
4152

53+
if len(profile_t.MfaSerial) < 1 && *profile != profile_t.SourceProfile {
54+
p.Logger.Debug("No mfa_serial config found in profile, checking source_profile")
55+
src_profile_t, err := p.lookupProfile(&profile_t.SourceProfile, cfg)
56+
if err == nil {
57+
profile_t.MfaSerial = src_profile_t.MfaSerial
58+
} else {
59+
p.Logger.Debugf("Ignoring error while looking up source_profile info: %+v", err)
60+
}
61+
}
62+
4263
p.Logger.Debugf("PROFILE: %+v", *profile_t)
4364
return profile_t, nil
4465
}

README.md

Lines changed: 16 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -45,19 +45,31 @@ Pre-compiled binaries for various platforms can be downloaded [here](https://git
4545
## Configuration
4646

4747
To configure a profile in the .aws/config file for using AssumeRole, make sure the `source_profile` and `role_arn` attributes are
48-
set for the profile. The `role_arn` attribute will determine which role will be assumed for that profile. The `source_profile`
49-
attribute specifies the name of the profile which will be used to perform the GetSessionToken operation.
48+
set for the desired profile. The `role_arn` attribute will determine which role to assume for that profile. The `source_profile`
49+
attribute specifies the name of the profile which will be used to perform the GetSessionToken operation. If you wish to supply an MFA
50+
code when doing the GetSessionToken call, you **MUST** specify the `mfa_serial` attribute in the profile referenced by `source_profile`
5051

5152
If the `mfa_serial` attribute is present in the profile configuration, That MFA device will be used when requesting or refreshing
52-
the session token.
53+
the session token. If the attribute is not found in the profile configuration, the program will attempt to find it in the section
54+
referenced by `source_profile`, in an attempt to simplify the config file. (NOTE: this is a non-standard configuration, and may break
55+
other tools which require the mfa_serial attribute inside the profile config to make the AssumeRole API call, [ex: awscli])
5356

54-
Example:
57+
Example (compatible with awscli `--profile` option):
5558

5659
[profile admin]
5760
source_profile = default
5861
role_arn = arn:aws:iam::987654321098:role/admin_role
5962
mfa_serial = arn:aws:iam::123456789098:mfa/iam_user
6063

64+
Example (NOT compatible with awscli `--profile` option, if MFA requred for AssumeRole):
65+
66+
[default]
67+
mfa_serial = arn:aws:iam::123456789098:mfa/iam_user
68+
69+
[profile admin]
70+
source_profile = default
71+
role_arn = arn:aws:iam::987654321098:role/admin_role
72+
6173
### Required AWS permissions
6274

6375
The user's credentials used by this program will need access to call the following AWS APIs to function:

RoleGetter.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ package main
33
import (
44
"encoding/json"
55
"github.com/aws/aws-sdk-go/service/iam"
6-
"net/url"
76
"github.com/mbndr/logo"
7+
"net/url"
88
)
99

1010
type RoleGetter interface {

0 commit comments

Comments
 (0)