diff --git a/src/rgw/rgw_common.cc b/src/rgw/rgw_common.cc index 708e95b59cdc0..b6b38fbb46e99 100644 --- a/src/rgw/rgw_common.cc +++ b/src/rgw/rgw_common.cc @@ -61,6 +61,7 @@ rgw_http_errors rgw_http_s3_errors({ { ERR_INVALID_REQUEST, {400, "InvalidRequest" }}, { ERR_INVALID_DIGEST, {400, "InvalidDigest" }}, { ERR_BAD_DIGEST, {400, "BadDigest" }}, + { ERR_INVALID_LOCATION_CONSTRAINT, {400, "InvalidLocationConstraint" }}, { ERR_INVALID_BUCKET_NAME, {400, "InvalidBucketName" }}, { ERR_INVALID_OBJECT_NAME, {400, "InvalidObjectName" }}, { ERR_UNRESOLVABLE_EMAIL, {400, "UnresolvableGrantByEmailAddress" }}, diff --git a/src/rgw/rgw_common.h b/src/rgw/rgw_common.h index 6ed3a76c3f7cf..b9fdccc606b0f 100644 --- a/src/rgw/rgw_common.h +++ b/src/rgw/rgw_common.h @@ -205,6 +205,8 @@ using ceph::crypto::MD5; #define ERR_NO_ROLE_FOUND 2205 #define ERR_DELETE_CONFLICT 2206 #define ERR_NO_SUCH_BUCKET_POLICY 2207 +#define ERR_INVALID_LOCATION_CONSTRAINT 2208 + #define ERR_BUSY_RESHARDING 2300 #ifndef UINT32_MAX diff --git a/src/rgw/rgw_op.cc b/src/rgw/rgw_op.cc index 9f28b313c3a98..5b98e50fdb682 100644 --- a/src/rgw/rgw_op.cc +++ b/src/rgw/rgw_op.cc @@ -490,7 +490,7 @@ int rgw_build_bucket_policies(RGWRados* store, struct req_state* s) /* we now need to make sure that the operation actually requires copy source, that is * it's a copy operation */ - if (store->get_zonegroup().is_master && s->system_request) { + if (store->get_zonegroup().is_master_zonegroup() && s->system_request) { /*If this is the master, don't redirect*/ } else if (!s->local_source || (s->op != OP_PUT && s->op != OP_COPY) || @@ -2394,10 +2394,22 @@ void RGWCreateBucket::execute() if (op_ret < 0) return; - if (!store->get_zonegroup().is_master && + if (!location_constraint.empty() && + !store->has_zonegroup_api(location_constraint)) { + ldout(s->cct, 0) << "location constraint (" << location_constraint << ")" + << " can't be found." << dendl; + op_ret = -ERR_INVALID_LOCATION_CONSTRAINT; + s->err.message = "The specified location-constraint is not valid"; + return; + } + + if (!store->get_zonegroup().is_master_zonegroup() && store->get_zonegroup().api_name != location_constraint) { - ldout(s->cct, 0) << "location constraint (" << location_constraint << ") doesn't match zonegroup" << " (" << store->get_zonegroup().api_name << ")" << dendl; - op_ret = -EINVAL; + ldout(s->cct, 0) << "location constraint (" << location_constraint << ")" + << " doesn't match zonegroup" << " (" << store->get_zonegroup().api_name << ")" + << dendl; + op_ret = -ERR_INVALID_LOCATION_CONSTRAINT; + s->err.message = "The specified location-constraint is not valid"; return; } @@ -5537,7 +5549,7 @@ bool RGWBulkDelete::Deleter::delete_single(const acct_path_t& path) goto delop_fail; } - if (!store->get_zonegroup().is_master) { + if (!store->get_zonegroup().is_master_zonegroup()) { bufferlist in_data; ret = forward_request_to_master(s, &ot.read_version, store, in_data, nullptr); diff --git a/src/rgw/rgw_rados.cc b/src/rgw/rgw_rados.cc index 6dedd96b7cf34..fdf35ca82fe58 100644 --- a/src/rgw/rgw_rados.cc +++ b/src/rgw/rgw_rados.cc @@ -1852,7 +1852,7 @@ void RGWPeriodMap::decode(bufferlist::iterator& bl) { iter != zonegroups.end(); ++iter) { RGWZoneGroup& zonegroup = iter->second; zonegroups_by_api[zonegroup.api_name] = zonegroup; - if (zonegroup.is_master) { + if (zonegroup.is_master_zonegroup()) { master_zonegroup = zonegroup.get_id(); } } @@ -1873,7 +1873,7 @@ static uint32_t gen_short_zone_id(const std::string zone_id) int RGWPeriodMap::update(const RGWZoneGroup& zonegroup, CephContext *cct) { - if (zonegroup.is_master && (!master_zonegroup.empty() && zonegroup.get_id() != master_zonegroup)) { + if (zonegroup.is_master_zonegroup() && (!master_zonegroup.empty() && zonegroup.get_id() != master_zonegroup)) { ldout(cct,0) << "Error updating periodmap, multiple master zonegroups configured "<< dendl; ldout(cct,0) << "master zonegroup: " << master_zonegroup << " and " << zonegroup.get_id() <second; zonegroups_by_api[zonegroup.api_name] = zonegroup; - if (zonegroup.is_master) { + if (zonegroup.is_master_zonegroup()) { master_zonegroup = zonegroup.get_name(); } } @@ -3942,7 +3942,7 @@ int RGWRados::replace_region_with_zonegroup() ldout(cct, 0) << __func__ << " failed init region "<< *iter << ": " << cpp_strerror(-ret) << dendl; return ret; } - if (region.is_master) { + if (region.is_master_zonegroup()) { master_region = region.get_id(); master_zone = region.master_zone; } @@ -4234,7 +4234,7 @@ int RGWRados::init_zg_from_local(bool *creating_defaults) } } ldout(cct, 20) << "zonegroup " << zonegroup.get_name() << dendl; - if (zonegroup.is_master) { + if (zonegroup.is_master_zonegroup()) { // use endpoints from the zonegroup's master zone auto master = zonegroup.zones.find(zonegroup.master_zone); if (master == zonegroup.zones.end()) { @@ -8175,7 +8175,7 @@ int RGWRados::copy_obj_data(RGWObjectCtx& obj_ctx, bool RGWRados::is_meta_master() { - if (!get_zonegroup().is_master) { + if (!get_zonegroup().is_master_zonegroup()) { return false; } @@ -8196,7 +8196,7 @@ bool RGWRados::is_syncing_bucket_meta(const rgw_bucket& bucket) } /* zonegroup is not master zonegroup */ - if (!get_zonegroup().is_master) { + if (!get_zonegroup().is_master_zonegroup()) { return false; } diff --git a/src/rgw/rgw_rados.h b/src/rgw/rgw_rados.h index 24bb8bb3cb12e..4e81cbe4fcf36 100644 --- a/src/rgw/rgw_rados.h +++ b/src/rgw/rgw_rados.h @@ -2465,6 +2465,16 @@ class RGWRados const string& get_current_period_id() { return current_period.get_id(); } + + bool has_zonegroup_api(const std::string& api) const { + if (!current_period.get_id().empty()) { + const auto& zonegroups_by_api = current_period.get_map().zonegroups_by_api; + if (zonegroups_by_api.find(api) != zonegroups_by_api.end()) + return true; + } + return false; + } + // pulls missing periods for period_history std::unique_ptr period_puller; // maintains a connected history of periods