From b5d5c55b5440fef27a63f43ea1e431ff2a4393d7 Mon Sep 17 00:00:00 2001 From: Casey Bodley Date: Tue, 12 Mar 2024 19:05:13 -0400 Subject: [PATCH] rgw/pubsub: add ERR_AUTHORIZATION -> AuthorizationError sns docs specify AuthorizationError as the 403 error code rather than s3's AccessDenied: https://docs.aws.amazon.com/sns/latest/api/API_CreateTopic.html#API_CreateTopic_Errors boto3 sns clients can catch this as AuthorizationErrorException Signed-off-by: Casey Bodley --- src/rgw/rgw_common.cc | 1 + src/rgw/rgw_common.h | 1 + src/rgw/rgw_rest_pubsub.cc | 16 ++++----- src/test/rgw/bucket_notification/test_bn.py | 36 ++++++++++----------- 4 files changed, 28 insertions(+), 26 deletions(-) diff --git a/src/rgw/rgw_common.cc b/src/rgw/rgw_common.cc index 79c1fe4c0a9..6b560d8f6e6 100644 --- a/src/rgw/rgw_common.cc +++ b/src/rgw/rgw_common.cc @@ -86,6 +86,7 @@ rgw_http_errors rgw_http_s3_errors({ { ERR_LENGTH_REQUIRED, {411, "MissingContentLength" }}, { EACCES, {403, "AccessDenied" }}, { EPERM, {403, "AccessDenied" }}, + { ERR_AUTHORIZATION, {403, "AuthorizationError" }}, { ERR_SIGNATURE_NO_MATCH, {403, "SignatureDoesNotMatch" }}, { ERR_INVALID_ACCESS_KEY, {403, "InvalidAccessKeyId" }}, { ERR_USER_SUSPENDED, {403, "UserSuspended" }}, diff --git a/src/rgw/rgw_common.h b/src/rgw/rgw_common.h index 56f51d08d74..5e44eeed89b 100644 --- a/src/rgw/rgw_common.h +++ b/src/rgw/rgw_common.h @@ -325,6 +325,7 @@ inline constexpr const char* RGW_REST_STS_XMLNS = #define ERR_INVALID_OBJECT_STATE 2222 #define ERR_PRESIGNED_URL_EXPIRED 2223 #define ERR_PRESIGNED_URL_DISABLED 2224 +#define ERR_AUTHORIZATION 2225 // SNS 403 AuthorizationError #define ERR_BUSY_RESHARDING 2300 #define ERR_NO_SUCH_ENTITY 2301 diff --git a/src/rgw/rgw_rest_pubsub.cc b/src/rgw/rgw_rest_pubsub.cc index 7db88ceddda..7914f813a20 100644 --- a/src/rgw/rgw_rest_pubsub.cc +++ b/src/rgw/rgw_rest_pubsub.cc @@ -318,14 +318,14 @@ class RGWPSCreateTopicOp : public RGWOp { // account users don't consult the existing owner/policy if (!verify_user_permission(this, s, topic_arn, rgw::IAM::snsCreateTopic)) { - return -EACCES; + return -ERR_AUTHORIZATION; } return 0; } if (topic && !verify_topic_permission(this, s, *topic, topic_arn, rgw::IAM::snsCreateTopic)) { - return -EACCES; + return -ERR_AUTHORIZATION; } return 0; } @@ -407,7 +407,7 @@ public: // check account permissions up front if (s->auth.identity->get_account() && !verify_user_permission(this, s, {}, rgw::IAM::snsListTopics)) { - return -EACCES; + return -ERR_AUTHORIZATION; } return 0; @@ -528,7 +528,7 @@ class RGWPSGetTopicOp : public RGWOp { int verify_permission(optional_yield y) override { if (!verify_topic_permission(this, s, result, topic_arn, rgw::IAM::snsGetTopicAttributes)) { - return -EACCES; + return -ERR_AUTHORIZATION; } return 0; } @@ -614,7 +614,7 @@ class RGWPSGetTopicAttributesOp : public RGWOp { int verify_permission(optional_yield y) override { if (!verify_topic_permission(this, s, result, topic_arn, rgw::IAM::snsGetTopicAttributes)) { - return -EACCES; + return -ERR_AUTHORIZATION; } return 0; } @@ -782,7 +782,7 @@ class RGWPSSetTopicAttributesOp : public RGWOp { int verify_permission(optional_yield y) override { if (!verify_topic_permission(this, s, result, topic_arn, rgw::IAM::snsSetTopicAttributes)) { - return -EACCES; + return -ERR_AUTHORIZATION; } return 0; } @@ -906,14 +906,14 @@ class RGWPSDeleteTopicOp : public RGWOp { if (s->auth.identity->get_account()) { if (!verify_user_permission(this, s, topic_arn, rgw::IAM::snsDeleteTopic)) { - return -EACCES; + return -ERR_AUTHORIZATION; } return 0; } if (topic && !verify_topic_permission(this, s, *topic, topic_arn, rgw::IAM::snsDeleteTopic)) { - return -EACCES; + return -ERR_AUTHORIZATION; } return 0; } diff --git a/src/test/rgw/bucket_notification/test_bn.py b/src/test/rgw/bucket_notification/test_bn.py index df69fbaf059..e3ebea7236e 100644 --- a/src/test/rgw/bucket_notification/test_bn.py +++ b/src/test/rgw/bucket_notification/test_bn.py @@ -4344,12 +4344,12 @@ def test_ps_s3_topic_permissions(): try: # 2nd user tries to override the topic topic_arn = topic_conf2.set_config() - assert False, "'AccessDenied' error is expected" + assert False, "'AuthorizationError' error is expected" except ClientError as err: if 'Error' in err.response: - assert_equal(err.response['Error']['Code'], 'AccessDenied') + assert_equal(err.response['Error']['Code'], 'AuthorizationError') else: - assert_equal(err.response['Code'], 'AccessDenied') + assert_equal(err.response['Code'], 'AuthorizationError') except Exception as err: print('unexpected error type: '+type(err).__name__) @@ -4360,12 +4360,12 @@ def test_ps_s3_topic_permissions(): try: # 2nd user tries to set the attribute status = topic_conf2.set_attributes(attribute_name="persistent", attribute_val="false", topic_arn=topic_arn) - assert False, "'AccessDenied' error is expected" + assert False, "'AuthorizationError' error is expected" except ClientError as err: if 'Error' in err.response: - assert_equal(err.response['Error']['Code'], 'AccessDenied') + assert_equal(err.response['Error']['Code'], 'AuthorizationError') else: - assert_equal(err.response['Code'], 'AccessDenied') + assert_equal(err.response['Code'], 'AuthorizationError') except Exception as err: print('unexpected error type: '+type(err).__name__) @@ -4390,12 +4390,12 @@ def test_ps_s3_topic_permissions(): try: # 2nd user tries to delete the topic status = topic_conf2.del_config(topic_arn=topic_arn) - assert False, "'AccessDenied' error is expected" + assert False, "'AuthorizationError' error is expected" except ClientError as err: if 'Error' in err.response: - assert_equal(err.response['Error']['Code'], 'AccessDenied') + assert_equal(err.response['Error']['Code'], 'AuthorizationError') else: - assert_equal(err.response['Code'], 'AccessDenied') + assert_equal(err.response['Code'], 'AuthorizationError') except Exception as err: print('unexpected error type: '+type(err).__name__) @@ -4442,12 +4442,12 @@ def test_ps_s3_topic_no_permissions(): try: # 2nd user tries to override the topic topic_arn = topic_conf2.set_config() - assert False, "'AccessDenied' error is expected" + assert False, "'AuthorizationError' error is expected" except ClientError as err: if 'Error' in err.response: - assert_equal(err.response['Error']['Code'], 'AccessDenied') + assert_equal(err.response['Error']['Code'], 'AuthorizationError') else: - assert_equal(err.response['Code'], 'AccessDenied') + assert_equal(err.response['Code'], 'AuthorizationError') except Exception as err: print('unexpected error type: '+type(err).__name__) @@ -4458,12 +4458,12 @@ def test_ps_s3_topic_no_permissions(): try: # 2nd user tries to set the attribute status = topic_conf2.set_attributes(attribute_name="persistent", attribute_val="false", topic_arn=topic_arn) - assert False, "'AccessDenied' error is expected" + assert False, "'AuthorizationError' error is expected" except ClientError as err: if 'Error' in err.response: - assert_equal(err.response['Error']['Code'], 'AccessDenied') + assert_equal(err.response['Error']['Code'], 'AuthorizationError') else: - assert_equal(err.response['Code'], 'AccessDenied') + assert_equal(err.response['Code'], 'AuthorizationError') except Exception as err: print('unexpected error type: '+type(err).__name__) @@ -4481,12 +4481,12 @@ def test_ps_s3_topic_no_permissions(): try: # 2nd user tries to delete the topic status = topic_conf2.del_config(topic_arn=topic_arn) - assert False, "'AccessDenied' error is expected" + assert False, "'AuthorizationError' error is expected" except ClientError as err: if 'Error' in err.response: - assert_equal(err.response['Error']['Code'], 'AccessDenied') + assert_equal(err.response['Error']['Code'], 'AuthorizationError') else: - assert_equal(err.response['Code'], 'AccessDenied') + assert_equal(err.response['Code'], 'AuthorizationError') except Exception as err: print('unexpected error type: '+type(err).__name__) -- 2.39.5