[sheepdog] [PATCH v2 1/3] sheep/http: implement HEAD operation for bucket

Robin Dong robin.k.dong at gmail.com
Thu Dec 26 07:11:02 CET 2013


I think we should add check in kv_delete_bucket() because users can't
delete a bucket which still contains objects.


2013/12/26 Liu Yuan <namei.unix at gmail.com>

> Signed-off-by: Liu Yuan <namei.unix at gmail.com>
> ---
>  sheep/http/http.h  |  3 +-
>  sheep/http/kv.c    | 80
> ++++++++++++++++++++++++++++++++++++++++++++++++++----
>  sheep/http/swift.c | 16 ++++++++++-
>  3 files changed, 92 insertions(+), 7 deletions(-)
>
> diff --git a/sheep/http/http.h b/sheep/http/http.h
> index dea34e0..40ff307 100644
> --- a/sheep/http/http.h
> +++ b/sheep/http/http.h
> @@ -126,7 +126,8 @@ int kv_list_accounts(struct http_request *req,
>
>  /* Bucket operations */
>  int kv_create_bucket(const char *account, const char *bucket);
> -int kv_read_bucket(const char *account, const char *bucket);
> +int kv_read_bucket(struct http_request *req, const char *account,
> +                  const char *bucket);
>  int kv_update_bucket(const char *account, const char *bucket);
>  int kv_delete_bucket(const char *account, const char *bucket);
>  int kv_iterate_bucket(const char *account,
> diff --git a/sheep/http/kv.c b/sheep/http/kv.c
> index 5fde277..a58310f 100644
> --- a/sheep/http/kv.c
> +++ b/sheep/http/kv.c
> @@ -18,7 +18,7 @@
>
>  struct kv_bnode {
>         char name[SD_MAX_BUCKET_NAME];
> -       uint64_t obj_count;
> +       uint64_t object_count;
>         uint64_t bytes_used;
>         uint64_t oid;
>  };
> @@ -320,7 +320,7 @@ static int bucket_create(const char *account, uint32_t
> account_vid,
>
>         pstrcpy(bnode.name, sizeof(bnode.name), bucket);
>         bnode.bytes_used = 0;
> -       bnode.obj_count = 0;
> +       bnode.object_count = 0;
>         ret = bnode_create(&bnode, account_vid);
>         if (ret != SD_RES_SUCCESS)
>                 goto err;
> @@ -355,6 +355,39 @@ out:
>         return ret;
>  }
>
> +static int bnode_update(const char *account, const char *bucket, uint64_t
> used,
> +                       bool create)
> +{
> +       uint32_t account_vid;
> +       struct kv_bnode bnode;
> +       int ret;
> +
> +       ret = sd_lookup_vdi(account, &account_vid);
> +       if (ret != SD_RES_SUCCESS) {
> +               sd_err("Failed to find account %s", account);
> +               return ret;
> +       }
> +
> +       ret = bnode_lookup(&bnode, account_vid, bucket);
> +       if (ret != SD_RES_SUCCESS)
> +               return ret;
> +
> +       if (create) {
> +               bnode.object_count++;
> +               bnode.bytes_used += used;
> +       } else {
> +               bnode.object_count--;
> +               bnode.bytes_used -= used;
> +       }
> +
> +       ret = sd_write_object(bnode.oid, (char *)&bnode, sizeof(bnode), 0,
> 0);
> +       if (ret != SD_RES_SUCCESS) {
> +               sd_err("failed to update bnode for %s", bucket);
> +               return ret;
> +       }
> +       return SD_RES_SUCCESS;
> +}
> +
>  static int bucket_delete(const char *account, uint32_t avid, const char
> *bucket)
>  {
>         struct kv_bnode bnode;
> @@ -470,10 +503,29 @@ out:
>         return ret;
>  }
>
> -int kv_read_bucket(const char *account, const char *bucket)
> +int kv_read_bucket(struct http_request *req, const char *account,
> +                  const char *bucket)
>  {
> -       /* TODO: read metadata of the bucket */
> -       return -1;
> +       uint32_t account_vid;
> +       struct kv_bnode bnode;
> +       int ret;
> +
> +       ret = sd_lookup_vdi(account, &account_vid);
> +       if (ret != SD_RES_SUCCESS) {
> +               sd_err("Failed to find account %s", account);
> +               return ret;
> +       }
> +
> +       ret = bnode_lookup(&bnode, account_vid, bucket);
> +       if (ret != SD_RES_SUCCESS)
> +               goto out;
> +       http_request_writef(req, "X-Container-Object-Count: %"PRIu64"\n",
> +                           bnode.object_count);
> +
> +       http_request_writef(req, "X-Container-Bytes-Used: %"PRIu64"\n",
> +                           bnode.bytes_used);
> +out:
> +       return ret;
>  }
>
>  int kv_update_bucket(const char *account, const char *bucket)
> @@ -948,6 +1000,13 @@ int kv_create_object(struct http_request *req, const
> char *account,
>         if (ret != SD_RES_SUCCESS) {
>                 sd_err("failed to create onode for %s", name);
>                 onode_free_data(onode);
> +               goto out;
> +       }
> +
> +       ret = bnode_update(account, bucket, req->data_length, true);
> +       if (ret != SD_RES_SUCCESS) {
> +               ret = onode_delete(onode);
> +               goto out;
>         }
>  out:
>         free(onode);
> @@ -1000,6 +1059,17 @@ int kv_delete_object(const char *account, const
> char *bucket, const char *name)
>                 goto out;
>
>         ret = onode_delete(onode);
> +       if (ret != SD_RES_SUCCESS)
> +               goto out;
> +
> +       /*
> +        * If bnode is deleted successfully, we consider it successful
> deletion
> +        * even if bnode_update() fails.
> +        *
> +        * FIXME: make bnode metadata consistent
> +        */
> +       if (bnode_update(account, bucket, onode->size, false) !=
> SD_RES_SUCCESS)
> +               sd_err("failed to update bnode for %s/%s", account,
> bucket);
>  out:
>         free(onode);
>         return ret;
> diff --git a/sheep/http/swift.c b/sheep/http/swift.c
> index 01e864a..c3985be 100644
> --- a/sheep/http/swift.c
> +++ b/sheep/http/swift.c
> @@ -95,7 +95,21 @@ static void swift_delete_account(struct http_request
> *req, const char *account)
>  static void swift_head_container(struct http_request *req, const char
> *account,
>                                  const char *container)
>  {
> -       http_response_header(req, NOT_IMPLEMENTED);
> +       int ret;
> +
> +       ret = kv_read_bucket(req, account, container);
> +       switch (ret) {
> +       case SD_RES_SUCCESS:
> +               http_response_header(req, NO_CONTENT);
> +               break;
> +       case SD_RES_NO_VDI:
> +       case SD_RES_NO_OBJ:
> +               http_response_header(req, NOT_FOUND);
> +               break;
> +       default:
> +               http_response_header(req, INTERNAL_SERVER_ERROR);
> +               break;
> +       }
>  }
>
>  static void swift_get_container_cb(const char *object, void *opaque)
> --
> 1.8.1.2
>
> --
> sheepdog mailing list
> sheepdog at lists.wpkg.org
> http://lists.wpkg.org/mailman/listinfo/sheepdog
>



-- 
--
Best Regard
Robin Dong
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.wpkg.org/pipermail/sheepdog/attachments/20131226/d5d5e8e2/attachment-0004.html>


More information about the sheepdog mailing list