summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYehuda Sadeh <yehuda@inktank.com>2013-06-24 23:43:50 -0700
committerYehuda Sadeh <yehuda@inktank.com>2013-06-24 23:43:50 -0700
commit63e81afeb80481ea8ca6987744dce03b0005c7cc (patch)
treea71b07364cf5783dc4b59a41bb4d2caeccdde550
parent7e41c1036de061e0d73cee8a6707d22bc16fb09f (diff)
downloadceph-63e81afeb80481ea8ca6987744dce03b0005c7cc.tar.gz
rgw: multiple fixes related to metadata, bucket creation
Signed-off-by: Yehuda Sadeh <yehuda@inktank.com>
-rw-r--r--src/rgw/rgw_bucket.cc47
-rw-r--r--src/rgw/rgw_bucket.h2
-rw-r--r--src/rgw/rgw_common.h8
-rw-r--r--src/rgw/rgw_json_enc.cc4
-rw-r--r--src/rgw/rgw_metadata.cc30
-rw-r--r--src/rgw/rgw_metadata.h3
-rw-r--r--src/rgw/rgw_rados.cc38
-rw-r--r--src/rgw/rgw_rados.h1
8 files changed, 81 insertions, 52 deletions
diff --git a/src/rgw/rgw_bucket.cc b/src/rgw/rgw_bucket.cc
index 419f40b5c2d..05a15d26760 100644
--- a/src/rgw/rgw_bucket.cc
+++ b/src/rgw/rgw_bucket.cc
@@ -127,10 +127,14 @@ int rgw_bucket_store_info(RGWRados *store, string& bucket_name, bufferlist& bl,
return store->meta_mgr->put_entry(bucket_meta_handler, bucket_name, bl, exclusive, objv_tracker, mtime, pattrs);
}
-int rgw_bucket_instance_store_info(RGWRados *store, string& oid, bufferlist& bl, bool exclusive,
+int rgw_bucket_instance_store_info(RGWRados *store, string& entry, bufferlist& bl, bool exclusive,
map<string, bufferlist> *pattrs, RGWObjVersionTracker *objv_tracker,
time_t mtime) {
- return store->meta_mgr->put_entry(bucket_instance_meta_handler, oid, bl, exclusive, objv_tracker, mtime, pattrs);
+ return store->meta_mgr->put_entry(bucket_instance_meta_handler, entry, bl, exclusive, objv_tracker, mtime, pattrs);
+}
+
+int rgw_bucket_instance_remove_entry(RGWRados *store, string& entry, RGWObjVersionTracker *objv_tracker) {
+ return store->meta_mgr->remove_entry(bucket_instance_meta_handler, entry, objv_tracker);
}
#warning removed RGWBucket::create_bucket(), clean this up when ready
@@ -1363,20 +1367,16 @@ public:
time_t orig_mtime;
- int ret = store->get_bucket_entrypoint_info(NULL, entry, be, &objv_tracker, &orig_mtime);
+ int ret = store->get_bucket_entrypoint_info(NULL, entry, old_be, &objv_tracker, &orig_mtime);
if (ret < 0 && ret != -ENOENT)
return ret;
- ret = store->put_bucket_entrypoint_info(entry, old_be, false, mtime);
+ ret = store->put_bucket_entrypoint_info(entry, be, false, mtime);
if (ret < 0)
return ret;
-#warning need to link bucket here
-#if 0
- ret = rgw_add_bucket(store, bci.info.owner, bci.info.bucket, bci.info.creation_time);
- if (ret < 0)
- return ret;
-#endif
+ /* link bucket */
+ ret = rgw_add_bucket(store, be.owner, be.bucket, be.creation_time);
return 0;
}
@@ -1465,12 +1465,12 @@ class RGWBucketInstanceMetadataHandler : public RGWMetadataHandler {
public:
string get_type() { return "bucket.instance"; }
- int get(RGWRados *store, string& entry, RGWMetadataObject **obj) {
+ int get(RGWRados *store, string& oid, RGWMetadataObject **obj) {
RGWBucketCompleteInfo bci;
time_t mtime;
- int ret = store->get_bucket_instance_info(NULL, entry, bci.info, &mtime, &bci.attrs);
+ int ret = store->get_bucket_instance_info(NULL, oid, bci.info, &mtime, &bci.attrs);
if (ret < 0)
return ret;
@@ -1481,7 +1481,7 @@ public:
return 0;
}
- int put(RGWRados *store, string& entry, RGWObjVersionTracker& objv_tracker, time_t mtime, JSONObj *obj) {
+ int put(RGWRados *store, string& oid, RGWObjVersionTracker& objv_tracker, time_t mtime, JSONObj *obj) {
RGWBucketCompleteInfo bci, old_bci;
decode_json_obj(bci, obj);
@@ -1489,14 +1489,14 @@ public:
old_bci.info.objv_tracker = objv_tracker;
- int ret = store->get_bucket_instance_info(NULL, entry, old_bci.info, &orig_mtime, &old_bci.attrs);
+ int ret = store->get_bucket_instance_info(NULL, oid, old_bci.info, &orig_mtime, &old_bci.attrs);
if (ret < 0 && ret != -ENOENT)
return ret;
if (ret == -ENOENT || old_bci.info.bucket.bucket_id != bci.info.bucket.bucket_id) {
/* a new bucket, we need to select a new bucket placement for it */
rgw_bucket bucket;
- ret = store->set_bucket_location_by_rule(bci.info.placement_rule, entry, bucket);
+ ret = store->set_bucket_location_by_rule(bci.info.placement_rule, oid, bucket);
if (ret < 0) {
ldout(store->ctx(), 0) << "ERROR: select_bucket_placement() returned " << ret << dendl;
return ret;
@@ -1510,7 +1510,7 @@ public:
bci.info.objv_tracker = old_bci.info.objv_tracker;
}
- ret = store->put_bucket_instance_info(entry, bci.info, false, mtime, &bci.attrs);
+ ret = store->put_bucket_instance_info(oid, bci.info, false, mtime, &bci.attrs);
if (ret < 0)
return ret;
@@ -1529,18 +1529,17 @@ public:
};
int remove(RGWRados *store, string& entry, RGWObjVersionTracker& objv_tracker) {
- rgw_bucket bucket;
- int r = init_bucket(store, entry, bucket, &objv_tracker);
- if (r < 0) {
- cerr << "could not init bucket=" << entry << std::endl;
- return r;
- }
+ RGWBucketInfo info;
- return store->delete_bucket(bucket, objv_tracker);
+ int ret = store->get_bucket_instance_info(NULL, entry, info, NULL, NULL);
+ if (ret < 0 && ret != -ENOENT)
+ return ret;
+
+ return rgw_bucket_instance_remove_entry(store, entry, &info.objv_tracker);
}
void get_pool_and_oid(RGWRados *store, string& key, rgw_bucket& bucket, string& oid) {
- oid = key;
+ oid = RGW_BUCKET_INSTANCE_MD_PREFIX + key;
bucket = store->zone.domain_root;
}
diff --git a/src/rgw/rgw_bucket.h b/src/rgw/rgw_bucket.h
index 3d8ea265396..2a87e9b097b 100644
--- a/src/rgw/rgw_bucket.h
+++ b/src/rgw/rgw_bucket.h
@@ -29,6 +29,8 @@ extern int rgw_bucket_instance_store_info(RGWRados *store, string& oid, bufferli
map<string, bufferlist> *pattrs, RGWObjVersionTracker *objv_tracker,
time_t mtime);
+extern int rgw_bucket_instance_remove_entry(RGWRados *store, string& entry, RGWObjVersionTracker *objv_tracker);
+
extern int rgw_bucket_delete_bucket_obj(RGWRados *store, string& bucket_name, RGWObjVersionTracker& objv_tracker);
/**
diff --git a/src/rgw/rgw_common.h b/src/rgw/rgw_common.h
index 179c4fe70c6..0fc35e00292 100644
--- a/src/rgw/rgw_common.h
+++ b/src/rgw/rgw_common.h
@@ -684,16 +684,19 @@ struct RGWBucketEntryPoint
{
rgw_bucket bucket;
string owner;
+ time_t creation_time;
bool has_bucket_info;
RGWBucketInfo old_bucket_info;
- RGWBucketEntryPoint() : has_bucket_info(false) {}
+ RGWBucketEntryPoint() : creation_time(0), has_bucket_info(false) {}
void encode(bufferlist& bl) const {
ENCODE_START(8, 8, bl);
::encode(bucket, bl);
::encode(owner, bl);
+ uint64_t ctime = (uint64_t)creation_time;
+ ::encode(ctime, bl);
ENCODE_FINISH(bl);
}
void decode(bufferlist::iterator& bl) {
@@ -708,6 +711,9 @@ struct RGWBucketEntryPoint
has_bucket_info = false;
::decode(bucket, bl);
::decode(owner, bl);
+ uint64_t ctime;
+ ::decode(ctime, bl);
+ creation_time = (uint64_t)ctime;
DECODE_FINISH(bl);
}
diff --git a/src/rgw/rgw_json_enc.cc b/src/rgw/rgw_json_enc.cc
index 8ab6ff530e6..1be85d43607 100644
--- a/src/rgw/rgw_json_enc.cc
+++ b/src/rgw/rgw_json_enc.cc
@@ -439,6 +439,8 @@ void rgw_bucket::decode_json(JSONObj *obj) {
void RGWBucketEntryPoint::dump(Formatter *f) const
{
encode_json("bucket", bucket, f);
+ encode_json("owner", owner, f);
+ encode_json("creation_time", creation_time, f);
encode_json("has_bucket_info", has_bucket_info, f);
if (has_bucket_info) {
encode_json("old_bucket_info", old_bucket_info, f);
@@ -447,6 +449,8 @@ void RGWBucketEntryPoint::dump(Formatter *f) const
void RGWBucketEntryPoint::decode_json(JSONObj *obj) {
JSONDecoder::decode_json("bucket", bucket, obj);
+ JSONDecoder::decode_json("owner", owner, obj);
+ JSONDecoder::decode_json("creation_time", creation_time, obj);
JSONDecoder::decode_json("has_bucket_info", has_bucket_info, obj);
if (has_bucket_info) {
JSONDecoder::decode_json("old_bucket_info", old_bucket_info, obj);
diff --git a/src/rgw/rgw_metadata.cc b/src/rgw/rgw_metadata.cc
index 6242806ef4d..99d06fda5c4 100644
--- a/src/rgw/rgw_metadata.cc
+++ b/src/rgw/rgw_metadata.cc
@@ -28,6 +28,9 @@ struct LogStatusDump {
case MDLOG_STATUS_COMPLETE:
s = "complete";
break;
+ case MDLOG_STATUS_ABORT:
+ s = "abort";
+ break;
default:
s = "unknown";
break;
@@ -499,17 +502,23 @@ int RGWMetadataManager::pre_modify(RGWMetadataHandler *handler, string& section,
}
int RGWMetadataManager::post_modify(string& section, string& key, RGWMetadataLogData& log_data,
- RGWObjVersionTracker *objv_tracker)
+ RGWObjVersionTracker *objv_tracker, int ret)
{
- log_data.status = MDLOG_STATUS_COMPLETE;
+ if (ret >= 0)
+ log_data.status = MDLOG_STATUS_COMPLETE;
+ else
+ log_data.status = MDLOG_STATUS_ABORT;
bufferlist logbl;
::encode(log_data, logbl);
- int ret = md_log->add_entry(store, section, key, logbl);
+ int r = md_log->add_entry(store, section, key, logbl);
if (ret < 0)
return ret;
+ if (r < 0)
+ return r;
+
return 0;
}
@@ -530,10 +539,9 @@ int RGWMetadataManager::put_entry(RGWMetadataHandler *handler, string& key, buff
ret = rgw_put_system_obj(store, bucket, oid,
bl.c_str(), bl.length(), exclusive,
objv_tracker, mtime, pattrs);
- if (ret < 0)
- return ret;
+ /* cascading ret into post_modify() */
- ret = post_modify(section, key, log_data, objv_tracker);
+ ret = post_modify(section, key, log_data, objv_tracker, ret);
if (ret < 0)
return ret;
@@ -556,10 +564,9 @@ int RGWMetadataManager::remove_entry(RGWMetadataHandler *handler, string& key, R
rgw_obj obj(bucket, oid);
ret = store->delete_obj(NULL, obj);
- if (ret < 0)
- return ret;
+ /* cascading ret into post_modify() */
- ret = post_modify(section, key, log_data, objv_tracker);
+ ret = post_modify(section, key, log_data, objv_tracker, ret);
if (ret < 0)
return ret;
@@ -578,10 +585,9 @@ int RGWMetadataManager::set_attrs(RGWMetadataHandler *handler, string& key,
return ret;
ret = store->set_attrs(NULL, obj, attrs, rmattrs, objv_tracker);
- if (ret < 0)
- return ret;
+ /* cascading ret into post_modify() */
- ret = post_modify(section, key, log_data, objv_tracker);
+ ret = post_modify(section, key, log_data, objv_tracker, ret);
if (ret < 0)
return ret;
diff --git a/src/rgw/rgw_metadata.h b/src/rgw/rgw_metadata.h
index ba12decdd41..6dd21d10a21 100644
--- a/src/rgw/rgw_metadata.h
+++ b/src/rgw/rgw_metadata.h
@@ -22,6 +22,7 @@ enum RGWMDLogStatus {
MDLOG_STATUS_SETATTRS,
MDLOG_STATUS_REMOVE,
MDLOG_STATUS_COMPLETE,
+ MDLOG_STATUS_ABORT,
};
class RGWMetadataObject {
@@ -117,7 +118,7 @@ class RGWMetadataManager {
RGWMetadataLogData& log_data, RGWObjVersionTracker *objv_tracker,
RGWMDLogStatus op_type);
int post_modify(string& section, string& key, RGWMetadataLogData& log_data,
- RGWObjVersionTracker *objv_tracker);
+ RGWObjVersionTracker *objv_tracker, int ret);
public:
RGWMetadataManager(CephContext *_cct, RGWRados *_store);
diff --git a/src/rgw/rgw_rados.cc b/src/rgw/rgw_rados.cc
index e5cb6c8ecd4..e8638a8173a 100644
--- a/src/rgw/rgw_rados.cc
+++ b/src/rgw/rgw_rados.cc
@@ -1807,6 +1807,14 @@ int RGWRados::create_bucket(RGWUserInfo& owner, rgw_bucket& bucket,
info.creation_time = creation_time;
ret = put_bucket_info(bucket.name, info, exclusive, 0, &attrs, true);
if (ret == -EEXIST) {
+ /* remove bucket meta instance */
+ string entry;
+ get_bucket_instance_entry(bucket, entry);
+ r = rgw_bucket_instance_remove_entry(this, entry, &info.objv_tracker);
+ if (r < 0)
+ return r;
+
+ /* remove bucket index */
librados::IoCtx index_ctx; // context for new bucket
int r = open_bucket_index_ctx(bucket, index_ctx);
if (r < 0)
@@ -4460,9 +4468,16 @@ int RGWRados::get_bucket_stats(rgw_bucket& bucket, uint64_t *bucket_ver, uint64_
return 0;
}
+void RGWRados::get_bucket_instance_entry(rgw_bucket& bucket, string& entry)
+{
+ entry = bucket.name + ":" + bucket.bucket_id;
+}
+
void RGWRados::get_bucket_meta_oid(rgw_bucket& bucket, string& oid)
{
- oid = RGW_BUCKET_INSTANCE_MD_PREFIX + bucket.name + ":" + bucket.bucket_id;
+ string entry;
+ get_bucket_instance_entry(bucket, entry);
+ oid = RGW_BUCKET_INSTANCE_MD_PREFIX + entry;
}
int RGWRados::get_bucket_instance_info(void *ctx, string& entry, RGWBucketInfo& info,
@@ -4564,6 +4579,7 @@ int RGWRados::put_bucket_entrypoint_info(string& bucket_name, RGWBucketEntryPoin
bufferlist epbl;
::encode(entry_point, epbl);
RGWObjVersionTracker ot;
+ ot.generate_new_write_ver(cct);
return rgw_bucket_store_info(this, bucket_name, epbl, exclusive, NULL, &ot, mtime);
}
@@ -4575,9 +4591,9 @@ int RGWRados::put_bucket_instance_info(string& bucket_name, RGWBucketInfo& info,
::encode(info, bl);
- string oid;
- get_bucket_meta_oid(info.bucket, oid);
- return rgw_bucket_instance_store_info(this, oid, bl, exclusive, pattrs, &info.objv_tracker, mtime);
+ string key;
+ get_bucket_instance_entry(info.bucket, key); /* when we go through meta api, we don't use oid directly */
+ return rgw_bucket_instance_store_info(this, key, bl, exclusive, pattrs, &info.objv_tracker, mtime);
}
int RGWRados::put_bucket_info(string& bucket_name, RGWBucketInfo& info, bool exclusive,
@@ -4598,18 +4614,12 @@ int RGWRados::put_bucket_info(string& bucket_name, RGWBucketInfo& info, bool exc
RGWBucketEntryPoint entry_point;
entry_point.bucket = info.bucket;
entry_point.owner = info.owner;
+ entry_point.creation_time = info.creation_time;
ret = put_bucket_entrypoint_info(info.bucket.name, entry_point, exclusive, mtime);
- if (exclusive && ret == -EEXIST) {
- string oid;
- get_bucket_meta_oid(info.bucket, oid);
- rgw_obj obj(zone.domain_root, oid);
- int r = delete_obj(NULL, obj);
- if (r < 0) {
- ldout(cct, 0) << "ERROR: failed removing object " << obj << " when trying to clean up" << dendl;
- }
- }
+ if (ret < 0)
+ return ret;
- return ret;
+ return 0;
}
int RGWRados::omap_get_vals(rgw_obj& obj, bufferlist& header, const string& marker, uint64_t count, std::map<string, bufferlist>& m)
diff --git a/src/rgw/rgw_rados.h b/src/rgw/rgw_rados.h
index e6298e73353..1e6f1de862f 100644
--- a/src/rgw/rgw_rados.h
+++ b/src/rgw/rgw_rados.h
@@ -1269,6 +1269,7 @@ public:
int decode_policy(bufferlist& bl, ACLOwner *owner);
int get_bucket_stats(rgw_bucket& bucket, uint64_t *bucket_ver, uint64_t *master_ver, map<RGWObjCategory, RGWBucketStats>& stats);
+ void get_bucket_instance_entry(rgw_bucket& bucket, string& entry);
void get_bucket_meta_oid(rgw_bucket& bucket, string& oid);
int put_bucket_entrypoint_info(string& bucket_name, RGWBucketEntryPoint& entry_point, bool exclusive, time_t mtime);