@@ -29,6 +29,7 @@ type Plugin struct {
2929 AssumeRoleSessionName string
3030 Bucket string
3131 UserRoleArn string
32+ UserRoleExternalID string // New field for UserRoleArn ExternalID
3233
3334 // if not "", enable server-side encryption
3435 // valid values are:
@@ -99,7 +100,7 @@ type Plugin struct {
99100 // set externalID for assume role
100101 ExternalID string
101102
102- // set OIDC ID Token to retrieve temporary credentials
103+ // set OIDC ID Token to retrieve temporary credentials
103104 IdToken string
104105}
105106
@@ -434,60 +435,79 @@ func (p *Plugin) downloadS3Objects(client *s3.S3, sourceDir string) error {
434435
435436// createS3Client creates and returns an S3 client based on the plugin configuration
436437func (p * Plugin ) createS3Client () * s3.S3 {
437- conf := & aws.Config {
438- Region : aws .String (p .Region ),
439- Endpoint : & p .Endpoint ,
440- DisableSSL : aws .Bool (strings .HasPrefix (p .Endpoint , "http://" )),
441- S3ForcePathStyle : aws .Bool (p .PathStyle ),
442- }
443-
444- sess , err := session .NewSession (conf )
445- if err != nil {
446- log .Fatalf ("failed to create AWS session: %v" , err )
447- }
448-
449- if p .Key != "" && p .Secret != "" {
450- conf .Credentials = credentials .NewStaticCredentials (p .Key , p .Secret , "" )
451- } else if p .IdToken != "" && p .AssumeRole != "" {
452- creds , err := assumeRoleWithWebIdentity (sess , p .AssumeRole , p .AssumeRoleSessionName , p .IdToken )
453- if err != nil {
454- log .Fatalf ("failed to assume role with web identity: %v" , err )
455- }
456- conf .Credentials = creds
457- } else if p .AssumeRole != "" {
458- conf .Credentials = assumeRole (p .AssumeRole , p .AssumeRoleSessionName , p .ExternalID )
459- } else {
460- log .Warn ("AWS Key and/or Secret not provided (falling back to ec2 instance profile)" )
461- }
438+ conf := & aws.Config {
439+ Region : aws .String (p .Region ),
440+ Endpoint : & p .Endpoint ,
441+ DisableSSL : aws .Bool (strings .HasPrefix (p .Endpoint , "http://" )),
442+ S3ForcePathStyle : aws .Bool (p .PathStyle ),
443+ }
444+
445+ sess , err := session .NewSession (conf )
446+ if err != nil {
447+ log .Fatalf ("failed to create AWS session: %v" , err )
448+ }
449+
450+ if p .Key != "" && p .Secret != "" {
451+ conf .Credentials = credentials .NewStaticCredentials (p .Key , p .Secret , "" )
452+ } else if p .IdToken != "" && p .AssumeRole != "" {
453+ creds , err := assumeRoleWithWebIdentity (sess , p .AssumeRole , p .AssumeRoleSessionName , p .IdToken )
454+ if err != nil {
455+ log .Fatalf ("failed to assume role with web identity: %v" , err )
456+ }
457+ conf .Credentials = creds
458+ } else if p .AssumeRole != "" {
459+ conf .Credentials = assumeRole (p .AssumeRole , p .AssumeRoleSessionName , p .ExternalID )
460+ } else {
461+ log .Warn ("AWS Key and/or Secret not provided (falling back to ec2 instance profile)" )
462+ }
462463
463464 sess , err = session .NewSession (conf )
464- if err != nil {
465- log .Fatalf ("failed to create AWS session: %v" , err )
466- }
465+ if err != nil {
466+ log .Fatalf ("failed to create AWS session: %v" , err )
467+ }
468+
469+ client := s3 .New (sess , conf )
470+
471+ if len (p .UserRoleArn ) > 0 {
472+ log .WithFields (log.Fields {
473+ "UserRoleArn" : p .UserRoleArn ,
474+ }).Info ("Assuming user role ARN" )
467475
468- client := s3 .New (sess , conf )
476+ // Create new credentials by assuming the UserRoleArn with ExternalID
477+ creds := stscreds .NewCredentials (sess , p .UserRoleArn , func (provider * stscreds.AssumeRoleProvider ) {
478+ if p .UserRoleExternalID != "" {
479+ provider .ExternalID = aws .String (p .UserRoleExternalID )
480+ }
481+ })
469482
470- if len (p .UserRoleArn ) > 0 {
471- confRoleArn := aws.Config {
472- Region : aws .String (p .Region ),
473- Credentials : stscreds .NewCredentials (sess , p .UserRoleArn ),
474- }
475- client = s3 .New (sess , & confRoleArn )
476- }
483+ // Create a new session with the new credentials
484+ confWithUserRole := & aws.Config {
485+ Region : aws .String (p .Region ),
486+ Credentials : creds ,
487+ }
488+
489+ sessWithUserRole , err := session .NewSession (confWithUserRole )
490+ if err != nil {
491+ log .Fatalf ("failed to create AWS session with user role: %v" , err )
492+ }
493+
494+ client = s3 .New (sessWithUserRole )
495+ }
496+
497+ return client
477498
478- return client
479499}
480500
481501func assumeRoleWithWebIdentity (sess * session.Session , roleArn , roleSessionName , idToken string ) (* credentials.Credentials , error ) {
482- svc := sts .New (sess )
483- input := & sts.AssumeRoleWithWebIdentityInput {
484- RoleArn : aws .String (roleArn ),
485- RoleSessionName : aws .String (roleSessionName ),
486- WebIdentityToken : aws .String (idToken ),
487- }
488- result , err := svc .AssumeRoleWithWebIdentity (input )
489- if err != nil {
490- log .Fatalf ("failed to assume role with web identity: %v" , err )
491- }
492- return credentials .NewStaticCredentials (* result .Credentials .AccessKeyId , * result .Credentials .SecretAccessKey , * result .Credentials .SessionToken ), nil
493- }
502+ svc := sts .New (sess )
503+ input := & sts.AssumeRoleWithWebIdentityInput {
504+ RoleArn : aws .String (roleArn ),
505+ RoleSessionName : aws .String (roleSessionName ),
506+ WebIdentityToken : aws .String (idToken ),
507+ }
508+ result , err := svc .AssumeRoleWithWebIdentity (input )
509+ if err != nil {
510+ log .Fatalf ("failed to assume role with web identity: %v" , err )
511+ }
512+ return credentials .NewStaticCredentials (* result .Credentials .AccessKeyId , * result .Credentials .SecretAccessKey , * result .Credentials .SessionToken ), nil
513+ }
0 commit comments