@@ -123,6 +123,35 @@ def add_traits(base, names, trait_type=None):
123123 return base
124124
125125
126+ def _get_head_bucket (s3_resource , bucket_name ):
127+ """ Try to get the header info of a bucket, in order to
128+ check if it exists and its permissions
129+ """
130+
131+ import botocore
132+
133+ # Try fetch the bucket with the name argument
134+ try :
135+ s3_resource .meta .client .head_bucket (Bucket = bucket_name )
136+ except botocore .exceptions .ClientError as exc :
137+ error_code = int (exc .response ['Error' ]['Code' ])
138+ if error_code == 403 :
139+ err_msg = 'Access to bucket: %s is denied; check credentials' \
140+ % bucket_name
141+ raise Exception (err_msg )
142+ elif error_code == 404 :
143+ err_msg = 'Bucket: %s does not exist; check spelling and try ' \
144+ 'again' % bucket_name
145+ raise Exception (err_msg )
146+ else :
147+ err_msg = 'Unable to connect to bucket: %s. Error message:\n %s' \
148+ % (bucket_name , exc )
149+ except Exception as exc :
150+ err_msg = 'Unable to connect to bucket: %s. Error message:\n %s' \
151+ % (bucket_name , exc )
152+ raise Exception (err_msg )
153+
154+
126155class IOBase (BaseInterface ):
127156 def _run_interface (self , runtime ):
128157 return runtime
@@ -535,43 +564,35 @@ def _fetch_bucket(self, bucket_name):
535564 session = boto3 .session .Session (
536565 aws_access_key_id = aws_access_key_id ,
537566 aws_secret_access_key = aws_secret_access_key )
538- s3_resource = session .resource ('s3' , use_ssl = True )
539567
540- # Otherwise, connect anonymously
541568 else :
542- iflogger .info ('Connecting to AWS: %s anonymously...' , bucket_name )
569+ iflogger .info ('Connecting to S3 bucket: %s with IAM role...' ,
570+ bucket_name )
571+
572+ # Lean on AWS environment / IAM role authentication and authorization
543573 session = boto3 .session .Session ()
544- s3_resource = session .resource ('s3' , use_ssl = True )
545- s3_resource .meta .client .meta .events .register (
546- 'choose-signer.s3.*' , botocore .handlers .disable_signing )
547574
548- # Explicitly declare a secure SSL connection for bucket object
549- bucket = s3_resource .Bucket (bucket_name )
575+ s3_resource = session .resource ('s3' , use_ssl = True )
550576
551577 # And try fetch the bucket with the name argument
552578 try :
553- s3_resource .meta .client .head_bucket (Bucket = bucket_name )
554- except botocore .exceptions .ClientError as exc :
555- error_code = int (exc .response ['Error' ]['Code' ])
556- if error_code == 403 :
557- err_msg = 'Access to bucket: %s is denied; check credentials' \
558- % bucket_name
559- raise Exception (err_msg )
560- elif error_code == 404 :
561- err_msg = 'Bucket: %s does not exist; check spelling and try ' \
562- 'again' % bucket_name
563- raise Exception (err_msg )
564- else :
565- err_msg = 'Unable to connect to bucket: %s. Error message:\n %s' \
566- % (bucket_name , exc )
579+ _get_head_bucket (s3_resource , bucket_name )
567580 except Exception as exc :
568- err_msg = 'Unable to connect to bucket: %s. Error message:\n %s' \
569- % (bucket_name , exc )
570- raise Exception (err_msg )
581+
582+ # Try to connect anonymously
583+ s3_resource .meta .client .meta .events .register (
584+ 'choose-signer.s3.*' , botocore .handlers .disable_signing )
585+
586+ iflogger .info ('Connecting to AWS: %s anonymously...' , bucket_name )
587+ _get_head_bucket (s3_resource , bucket_name )
588+
589+ # Explicitly declare a secure SSL connection for bucket object
590+ bucket = s3_resource .Bucket (bucket_name )
571591
572592 # Return the bucket
573593 return bucket
574594
595+
575596 # Send up to S3 method
576597 def _upload_to_s3 (self , bucket , src , dst ):
577598 '''
@@ -590,10 +611,8 @@ def _upload_to_s3(self, bucket, src, dst):
590611 s3_prefix = s3_str + bucket .name
591612
592613 # Explicitly lower-case the "s3"
593- if dst .lower ().startswith (s3_str ):
594- dst_sp = dst .split ('/' )
595- dst_sp [0 ] = dst_sp [0 ].lower ()
596- dst = '/' .join (dst_sp )
614+ if dst [:len (s3_str )].lower () == s3_str :
615+ dst = s3_str + dst [len (s3_str ):]
597616
598617 # If src is a directory, collect files (this assumes dst is a dir too)
599618 if os .path .isdir (src ):
0 commit comments