]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
rgw: copy obj does versioning too
authorYehuda Sadeh <yehuda@redhat.com>
Wed, 10 Dec 2014 22:39:27 +0000 (14:39 -0800)
committerYehuda Sadeh <yehuda@redhat.com>
Mon, 19 Jan 2015 23:57:55 +0000 (15:57 -0800)
Signed-off-by: Yehuda Sadeh <yehuda@redhat.com>
src/rgw/rgw_op.cc
src/rgw/rgw_rados.cc
src/rgw/rgw_rados.h

index 2e54987ec57ef1e98038bc30a73672eeda474b85..30b8b0debd86e048e7732bc9b2b8dda06a97cd10 100644 (file)
@@ -2363,6 +2363,8 @@ void RGWCopyObj::execute()
                         if_nomatch,
                         replace_attrs,
                         attrs, RGW_OBJ_CATEGORY_MAIN,
+                        olh_epoch,
+                        (version_id.empty() ? NULL : &version_id),
                         &s->req_id, /* use req_id as tag */
                         &etag,
                         &s->err,
index 9591d2821dfad7b4abeef7a277f779912f4ade33..f9e27ffa89ab3e1a92f87c30792e0af95a6e1e49 100644 (file)
@@ -2934,6 +2934,14 @@ int RGWRados::Object::Write::write_meta(uint64_t size,
   epoch = ref.ioctx.get_last_version();
   poolid = ref.ioctx.get_id();
 
+  /* successfully modified object, update internal object state */
+  state->exists = true;
+  state->mtime = meta.set_mtime;
+  state->size = size;
+  state->has_attrs = true;
+  state->epoch = epoch;
+  state->attrset = attrs;
+
   r = target->complete_atomic_modification();
   if (r < 0) {
     ldout(store->ctx(), 0) << "ERROR: complete_atomic_modification returned r=" << r << dendl;
@@ -3243,7 +3251,7 @@ int RGWRados::rewrite_obj(RGWBucketInfo& dest_bucket_info, rgw_obj& obj)
     return ret;
   }
 
-  return copy_obj_data(rctx, dest_bucket_info, read_op, end, obj, obj, max_chunk_size, NULL, mtime, attrset, RGW_OBJ_CATEGORY_MAIN, NULL, NULL, NULL);
+  return copy_obj_data(rctx, dest_bucket_info, read_op, end, obj, obj, max_chunk_size, NULL, mtime, attrset, RGW_OBJ_CATEGORY_MAIN, 0, NULL, NULL, NULL, NULL);
 }
 
 int RGWRados::fetch_remote_obj(RGWObjectCtx& obj_ctx,
@@ -3264,6 +3272,8 @@ int RGWRados::fetch_remote_obj(RGWObjectCtx& obj_ctx,
                bool replace_attrs,
                map<string, bufferlist>& attrs,
                RGWObjCategory category,
+               uint64_t olh_epoch,
+               string *version_id,
                string *ptag,
                string *petag,
                struct rgw_err *err,
@@ -3424,6 +3434,8 @@ int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
                bool replace_attrs,
                map<string, bufferlist>& attrs,
                RGWObjCategory category,
+               uint64_t olh_epoch,
+               string *version_id,
                string *ptag,
                string *petag,
                struct rgw_err *err,
@@ -3455,8 +3467,8 @@ int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
   if (remote_src || !source_zone.empty()) {
     return fetch_remote_obj(obj_ctx, user_id, client_id, op_id, info, source_zone,
                dest_obj, src_obj, dest_bucket_info, src_bucket_info, mtime, mod_ptr,
-               unmod_ptr, if_match, if_nomatch, replace_attrs, attrs,
-               category, ptag, petag, err, progress_cb, progress_data);
+               unmod_ptr, if_match, if_nomatch, replace_attrs, attrs, category,
+               olh_epoch, version_id, ptag, petag, err, progress_cb, progress_data);
   }
 
   map<string, bufferlist> src_attrs;
@@ -3530,7 +3542,8 @@ int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
 
   if (copy_data) { /* refcounting tail wouldn't work here, just copy the data */
     return copy_obj_data(obj_ctx, dest_bucket_info, read_op, end, dest_obj, src_obj,
-                         max_chunk_size, mtime, 0, src_attrs, category, ptag, petag, err);
+                         max_chunk_size, mtime, 0, src_attrs, category, olh_epoch,
+                         version_id, ptag, petag, err);
   }
 
   RGWObjManifest::obj_iterator miter = astate->manifest.obj_begin();
@@ -3545,6 +3558,15 @@ int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
     return ret;
   }
 
+  bool versioned_dest = dest_bucket_info.versioning_enabled();
+
+  if (version_id && !version_id->empty()) {
+    versioned_dest = true;
+    dest_obj.set_instance(*version_id);
+  } else if (versioned_dest) {
+    gen_rand_obj_instance_name(&dest_obj);
+  }
+
   bufferlist first_chunk;
 
   bool copy_itself = (dest_obj == src_obj);
@@ -3554,6 +3576,11 @@ int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
   RGWRados::Object dest_op_target(this, obj_ctx, dest_obj);
   RGWRados::Object::Write write_op(&dest_op_target);
 
+  RGWObjState *dest_state = NULL;
+  ret = get_obj_state(&obj_ctx, dest_obj, &dest_state, NULL);
+  if (ret < 0)
+    return ret;
+
   string tag;
 
   if (ptag)
@@ -3607,11 +3634,19 @@ int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
   write_op.meta.mtime = mtime;
   write_op.meta.flags = PUT_OBJ_CREATE;
   write_op.meta.category = category;
+  write_op.meta.olh_epoch = olh_epoch;
 
   ret = write_op.write_meta(end + 1, attrs);
   if (ret < 0)
     goto done_ret;
 
+  if (versioned_dest || dest_state->is_olh) {
+    ret = set_olh(obj_ctx, dest_bucket_info.owner, dest_obj, false, NULL, olh_epoch);
+    if (ret < 0) {
+      goto done_ret;
+    }
+  }
+
   return 0;
 
 done_ret:
@@ -3648,6 +3683,8 @@ int RGWRados::copy_obj_data(RGWObjectCtx& obj_ctx,
               time_t set_mtime,
                map<string, bufferlist>& attrs,
                RGWObjCategory category,
+               uint64_t olh_epoch,
+               string *version_id,
                string *ptag,
                string *petag,
                struct rgw_err *err)
@@ -3661,6 +3698,10 @@ int RGWRados::copy_obj_data(RGWObjectCtx& obj_ctx,
   RGWPutObjProcessor_Atomic processor(obj_ctx,
                                       dest_bucket_info.owner, dest_obj.bucket, dest_obj.get_object(),
                                       cct->_conf->rgw_obj_stripe_size, tag, dest_bucket_info.versioning_enabled());
+  if (version_id) {
+    processor.set_version_id(*version_id);
+  }
+  processor.set_olh_epoch(olh_epoch);
   int ret = processor.prepare(this, NULL);
   if (ret < 0)
     return ret;
@@ -5573,9 +5614,10 @@ int RGWRados::olh_init_modification(RGWObjState& state, rgw_obj& obj, string *op
 {
   int ret;
 
-  do {
-    ret = olh_init_modification_impl(state, obj, op_tag);
-  } while (ret == -EEXIST);
+  ret = olh_init_modification_impl(state, obj, op_tag);
+  if (ret == -EEXIST) {
+    ret = -ECANCELED;
+  }
 
   return ret;
 }
index 10c2c09710016a31e4191e6bedbe0a5cc43f87ac..0a44d37bf925ba7583c7c3f08c2a8a7998c635e3 100644 (file)
@@ -1458,10 +1458,11 @@ public:
         int flags;
         const char *if_match;
         const char *if_nomatch;
+        uint64_t olh_epoch;
 
         MetaParams() : mtime(NULL), rmattrs(NULL), data(NULL), manifest(NULL), ptag(NULL),
                  remove_objs(NULL), set_mtime(0), category(RGW_OBJ_CATEGORY_MAIN), flags(0),
-                 if_match(NULL), if_nomatch(NULL) {}
+                 if_match(NULL), if_nomatch(NULL), olh_epoch(0) {}
       } meta;
 
       Write(RGWRados::Object *_target) : target(_target) {}
@@ -1595,6 +1596,8 @@ public:
                        bool replace_attrs,
                        map<string, bufferlist>& attrs,
                        RGWObjCategory category,
+                       uint64_t olh_epoch,
+                       string *version_id,
                        string *ptag,
                        string *petag,
                        struct rgw_err *err,
@@ -1632,6 +1635,8 @@ public:
                bool replace_attrs,
                map<std::string, bufferlist>& attrs,
                RGWObjCategory category,
+               uint64_t olh_epoch,
+               string *version_id,
                string *ptag,
                string *petag,
                struct rgw_err *err,
@@ -1648,6 +1653,8 @@ public:
               time_t set_mtime,
                map<string, bufferlist>& attrs,
                RGWObjCategory category,
+               uint64_t olh_epoch,
+               string *version_id,
                string *ptag,
                string *petag,
                struct rgw_err *err);