Hướng dẫn dùng boto3 exceptions python
Tôi vừa chọn python làm ngôn ngữ kịch bản chuyển sang của mình và tôi đang cố gắng tìm cách xử lý lỗi thích hợp với boto3. Show
Tôi đang cố gắng tạo người dùng IAM:
Khi cuộc gọi đến created_user thành công, tôi nhận được một đối tượng gọn gàng chứa mã trạng thái http của lệnh gọi API và dữ liệu của người dùng mới được tạo. Thí dụ:
Điều này làm việc tuyệt vời. Nhưng khi điều này không thành công (như nếu người dùng đã tồn tại), tôi chỉ lấy một đối tượng thuộc kiểu botocore.exceptions.ClientError chỉ với văn bản để cho tôi biết điều gì đã xảy ra. Ví dụ: ClientError ('Xảy ra lỗi (EntityAlperedExists) khi gọi thao tác CreatUser: Người dùng có tên bị bỏ qua đã tồn tại.',) Điều này (AFAIK) khiến việc xử lý lỗi rất khó khăn vì tôi không thể bật mã trạng thái http kết quả (409 cho người dùng đã tồn tại theo tài liệu API AWS cho IAM). Điều này khiến tôi nghĩ rằng tôi phải làm điều gì đó sai cách. Cách tối ưu sẽ là boto3 không bao giờ ném ngoại lệ, nhưng juts luôn trả về một đối tượng phản ánh cách gọi API. Bất cứ ai có thể khai sáng cho tôi về vấn đề này hoặc chỉ cho tôi đi đúng hướng? Cảm ơn rất nhiều! 130 hữu ích 1 bình luận 92k xem chia sẻ Overview¶Boto3 provides many features to assist in navigating the errors and exceptions that you might encounter when interacting with AWS services. Specifically, this guide provides details on the following:
Why catch exceptions from AWS and Boto¶
Determining what exceptions to catch¶Exceptions that you might encounter when using Boto3 will come from one of two sources: botocore or the AWS services your client is interacting with. Botocore exceptions¶These exceptions are statically defined within the botocore package, a dependency of Boto3. The exceptions are related to issues with client-side behaviors, configurations, or validations. You can generate a list of the statically defined botocore exceptions using the following code: import botocore.exceptions for key, value in sorted(botocore.exceptions.__dict__.items()): if isinstance(value, type): print(key) Tip Click to see a full list of static exceptionsAliasConflictParameterError ApiVersionNotFoundError BaseEndpointResolverError BotoCoreError ChecksumError ClientError ConfigNotFound ConfigParseError ConnectTimeoutError ConnectionClosedError ConnectionError CredentialRetrievalError DataNotFoundError EndpointConnectionError EventStreamError HTTPClientError ImminentRemovalWarning IncompleteReadError InfiniteLoopConfigError InvalidConfigError InvalidDNSNameError InvalidExpressionError InvalidMaxRetryAttemptsError InvalidRetryConfigurationError InvalidS3AddressingStyleError InvalidS3UsEast1RegionalEndpointConfigError InvalidSTSRegionalEndpointsConfigError MD5UnavailableError MetadataRetrievalError MissingParametersError MissingServiceIdError NoCredentialsError NoRegionError OperationNotPageableError PaginationError ParamValidationError PartialCredentialsError ProfileNotFound ProxyConnectionError RangeError ReadTimeoutError RefreshWithMFAUnsupportedError SSLError ServiceNotInRegionError StubAssertionError StubResponseError UnStubbedResponseError UndefinedModelAttributeError UnknownClientMethodError UnknownCredentialError UnknownEndpointError UnknownKeyError UnknownParameterError UnknownServiceError UnknownServiceStyle UnknownSignatureVersionError UnseekableStreamError UnsupportedS3AccesspointConfigurationError UnsupportedS3ArnError UnsupportedSignatureVersionError UnsupportedTLSVersionWarning ValidationError WaiterConfigError WaiterError Note You can view available descriptions of the botocore static exceptions here. AWS service exceptions¶AWS service exceptions are caught with the underlying botocore exception, For a complete list of error responses from the services you’re using, consult the individual service’s AWS documentation, specifically the error response section of the AWS service’s API reference. These references also provide context around the exceptions and errors. Catching exceptions when using a low-level client¶Catching botocore exceptions¶Botocore
exceptions are statically defined in the botocore package. Any Boto3 clients you create will use these same statically defined exception classes. The most common botocore exception you’ll encounter is Additional client-side issues with SSL negotiation, client misconfiguration, or AWS service validation errors will also throw botocore exceptions. Here’s a generic example of how you might catch botocore exceptions. import botocore import boto3 client = boto3.client('aws_service_name') try: client.some_api_call(SomeParam='some_param') except botocore.exceptions.ClientError as error: # Put your error handling logic here raise error except botocore.exceptions.ParamValidationError as error: raise ValueError('The parameters you provided are incorrect: {}'.format(error)) Parsing error responses and catching exceptions from AWS services¶Unlike botocore exceptions, AWS service exceptions aren't statically defined in Boto3. This is due to errors and exceptions from AWS services varying widely and being subject to change. To properly catch an exception from an AWS service, you must parse the error response from the service. The error response provided to your client from the AWS service follows a common structure and is minimally processed and not obfuscated by Boto3. Using Boto3, the error response from an AWS service will look similar to a success response, except that an
{ 'Error': { 'Code': 'SomeServiceException', 'Message': 'Details/context around the exception or error' }, 'ResponseMetadata': { 'RequestId': '1234567890ABCDEF', 'HostId': 'host ID data will appear here as a hash', 'HTTPStatusCode': 400, 'HTTPHeaders': {'header metadata key/values will appear here'}, 'RetryAttempts': 0 } } Boto3 classifies all AWS service errors and exceptions as Using Amazon Kinesis as an example service, you can use Boto3 to catch the exception import botocore import boto3 import logging # Set up our logger logging.basicConfig(level=logging.INFO) logger = logging.getLogger() client = boto3.client('kinesis') try: logger.info('Calling DescribeStream API on myDataStream') client.describe_stream(StreamName='myDataStream') except botocore.exceptions.ClientError as error: if error.response['Error']['Code'] == 'LimitExceededException': logger.warn('API call limit exceeded; backing off and retrying...') else: raise error Note The Boto3 Additionally, you can also access some of the dynamic service-side exceptions from the client’s exception property. Using the previous example, you would need to modify only the except client.exceptions.LimitExceedException as error: logger.warn('API call limit exceeded; backing off and retrying...') Note Catching exceptions through Catching exceptions when using a resource client¶When
using Parsing for error responses uses the same exact methodology outlined in the low-level client section. Catching exceptions through the client’s client.meta.client.exceptions.SomeServiceException Using Amazon S3 as an example resource service, you can
use the client’s exception property to catch the import botocore import boto3 client = boto3.resource('s3') try: client.create_bucket(BucketName='myTestBucket') except client.meta.client.exceptions.BucketAlreadyExists as err: print("Bucket {} already exists!".format(err.response['Error']['BucketName'])) raise err Discerning useful information from error responses¶As stated previously in this guide, for details and context around specific AWS service exceptions, see the individual service’s AWS documentation, specifically the error response section of the AWS service’s API reference. Botocore exceptions will have detailed error messaging when those exceptions are thrown. These error messages provide details and context around the specific exception thrown. Descriptions of these exceptions can be viewed here. Outside of specific error or exception details and messaging, you might want to extract additional metadata from error responses:
Using a low-level Amazon SQS client, here’s an example of catching a generic or vague exception from the AWS service, and parsing out useful metadata from the error response. import botocore import boto3 client = boto3.client('sqs') queue_url = 'SQS_QUEUE_URL' try: client.send_message(QueueUrl=queue_url, MessageBody=('some_message')) except botocore.exceptions.ClientError as err: if err.response['Error']['Code'] == 'InternalError': # Generic error # We grab the message, request ID, and HTTP code to give to customer support print('Error Message: {}'.format(err.response['Error']['Message'])) print('Request ID: {}'.format(err.response['ResponseMetadata']['RequestId'])) print('Http code: {}'.format(err.response['ResponseMetadata']['HTTPStatusCode'])) else: raise err |