Update in couchbase

2019-08-24 04:33发布

问题:

I need some help in update using couchbase. I have a task in my page. If the user clicks the like then the likes count should be updated in my couchbase bucket. I have tried my own update handler code but that has some time latency. I have included my update code too below.

This is my code for liking a task...

public ResponseVO LikeTask(LikeVO likeVO)
        {
            ResponseVO response = new ResponseVO();

            try
            {
                if (!isLiked(likeVO.TaskID, likeVO.UserID))
                {

                    UpdateTaskDB likeUpdate = new UpdateTaskDB();

                    UpdateTaskVO updatetaskvo = new UpdateTaskVO();
                    updatetaskvo.FieldName = "Likes";
                    LikeVO tempvo = new LikeVO();
                    tempvo.LikedOn = DateTime.Now.ToString();
                    tempvo.UserID = likeVO.UserID;
                    tempvo.UserName = likeVO.UserName;
                    tempvo.TaskID = likeVO.TaskID;
                    updatetaskvo.ObjectValue = tempvo;
                    updatetaskvo.TaskID = likeVO.TaskID;
                    likeUpdate.UpdateDocument(updatetaskvo);
              }
                response.StatusMessage = "Liked Successfully";
            }
            catch (Exception ex)
            {
                response.StatusCode = "0";
                response.StatusMessage = ex.Message;
            }

            return response;
        }

My own update handler code:

 public class UpdateTaskDB
    {
        CouchbaseClient oCouchbase;
        public UpdateTaskDB()
        {
            oCouchbase = new CouchbaseClient("vwspace", "");
        }
        public TaskVO GetTaskByID(string task_id)
        {

            TaskVO results = null;
            try
            {
                String str1;

                str1 = (String)oCouchbase.Get(task_id);

                results = JsonConvert.DeserializeObject<TaskVO>(str1);
            }
            catch (Exception ex)
            {

            }
            return results;
        }

        public void UpdateDocument(UpdateTaskVO inputParams)
        {
            try
            {
                var client = new CouchbaseClient("vwspace", "");
                TaskVO taskDoc = GetTaskByID(inputParams.TaskID);

                switch (inputParams.FieldName)
                {
                    case "Likes":
                        List<LikeVO> docLikes = taskDoc.likes;
                        docLikes.Add((LikeVO)inputParams.ObjectValue);
                        taskDoc.likes = docLikes;
                        break;
                    case "UnLike":
                        LikeVO unlikevo = (LikeVO)inputParams.ObjectValue;
                        for (int count = 0; count < taskDoc.likes.Count; count++)
                        {
                            if (taskDoc.likes[count].UserID.Equals(unlikevo.UserID))
                            {
                                unlikevo = taskDoc.likes[count];
                                break;
                            }
                        }
                        taskDoc.likes.Remove(unlikevo);
                        break;

                    default:
                        break;
                }

                String json = JsonConvert.SerializeObject(taskDoc);
                client.Store(StoreMode.Set, inputParams.TaskID, json);

            }
            catch (Exception ex)
            {
                Console.Write("Exception :" + ex.Message);
            }
        }
    }

Is ther any other way to handle this update in couchbase? Kindly help me out..

回答1:

The latency you're seeing is likely due to the fact that you're creating two instances of the CouchbaseClient for each click. Creating an instance of a CouchbaseClient is an expensive operation, because of the bootstrapping and configuration setup that takes place.

There are a couple of different approaches you can take to minimize how frequently you create CouchbaseClient instances. One would be to create a static client that is reused by your data access classes. Another approach for web apps is to associate instances with HttpApplication instances. For an example of the Web approach, see my (incomplete) sample project on GitHub below.

https://github.com/jzablocki/couchbase-beer.net/blob/master/src/CouchbaseBeersWeb/Models/WebRepositoryBase%271.cs

Also, I would suggest using CAS operations when updating a document's like count. You want to make sure that a "like" vote doesn't cause the entire document to be update from a stale read.

For example:

public TaskVO GetTaskByID(string task_id)
{
    var getResult = oCouchbase.ExecuteGet<string>(task_id);   
    var results = JsonConvert.DeserializeObject<TaskVO>(str1.Value);
    results.Cas = getResult.Cas; //Here I'm suggesting adding a Cas property to your TaskVO
    return results;
}

Then on your update:

public void UpdateDocument(UpdateTaskVO inputParams)
{
    try
    {
        TaskVO taskDoc = GetTaskByID(inputParams.TaskID);

        switch (inputParams.FieldName)
        {
            ...
        }        

        String json = JsonConvert.SerializeObject(taskDoc);
        client.ExecuteStore(StoreMode.Set, inputParams.TaskID, json, taskDoc.Cas); 
        //this will fail if the document has been updated by another user.  You could use a retry strategy    
    }
    catch (Exception ex)
    {
        Console.Write("Exception :" + ex.Message);
    }
}