Пример #1
0
        protected override IOperationResult ProcessResponse(BinaryResponse response)
        {
            var result = new BinaryOperationResult();
            var status = response.StatusCode;

            this.StatusCode = status;

            if (status == 0)
            {
                var data = response.Data;
                if (data.Count != 8)
                {
                    return(result.Fail("Result must be 8 bytes long, received: " + data.Count, new InvalidOperationException()));
                }

                this.result = BinaryConverter.DecodeUInt64(data.Array, data.Offset);

                return(result.Pass());
            }

            var message = ResultHelper.ProcessResponseData(response.Data);

            return(result.Fail(message));
        }
Пример #2
0
        private IOperationResult ExecuteWithRedirect(IMemcachedNode startNode, ISingleItemOperation op)
        {
            var result = new BinaryOperationResult();

            var opResult = startNode.Execute(op);

            if (opResult.Success)
            {
                return(result.Pass());
            }

            var iows = op as IOperationWithState;

            // different op factory, we do not know how to retry
            if (iows == null)
            {
                result.InnerResult = opResult.InnerResult;
                return(result.Fail("Operation state was invalid"));
            }

#if HAS_FORWARD_MAP
            // node responded with invalid vbucket
            // this should happen only when a node is in a transitioning state
            if (iows.State == OpState.InvalidVBucket)
            {
                // check if we have a forward-locator
                // (whihc supposedly reflects the state of the cluster when all vbuckets have been migrated succesfully)
                IMemcachedNodeLocator fl = this.nsPool.ForwardLocator;
                if (fl != null)
                {
                    var nextNode = fl.Locate(op.Key);
                    if (nextNode != null)
                    {
                        // the node accepted the requesta
                        if (nextNode.Execute(op))
                        {
                            return(true);
                        }
                    }
                }
            }
#endif
            // still invalid vbucket, try all nodes in sequence
            if (iows.State == OperationState.InvalidVBucket)
            {
                var nodes = this.Pool.GetWorkingNodes();

                foreach (var node in nodes)
                {
                    opResult = node.Execute(op);
                    if (opResult.Success)
                    {
                        return(result.Pass());
                    }

                    // the node accepted our request so quit
                    if (iows.State != OperationState.InvalidVBucket)
                    {
                        break;
                    }
                }
            }

            //TODO: why would this happen?
            return(result.Fail("Failed to execute operation"));
        }
Пример #3
0
        public IOperationResult Execute(IOperation op)
        {
            IOperationResult result = new BinaryOperationResult();
            IPooledSocket    socket = null;

            try
            {
                socket = _pool.Acquire();
                if (Log.IsDebugEnabled)
                {
                    Log.DebugFormat("Start execute {0} with {1}", op.Key, socket.InstanceId);
                }
                var buffers = op.GetBuffer();
                socket.Write(buffers);

                result = op.ReadResponse(socket);
                if (result.Success)
                {
                    result.Pass();
                }
            }
            catch (NodeShutdownException e)
            {
                string msg = String.Format("Node Shutdown - {0}.", EndPoint);
                Log.DebugFormat("m:{0} i:{1}\n{2}", msg, op.Key, e);
                result.Fail(msg, e);
                result.StatusCode = StatusCode.NodeShutdown.ToInt();
            }
            catch (QueueTimeoutException e)
            {
                string msg = String.Format("Queue Timeout - {0}.", EndPoint);
                Log.ErrorFormat("m:{0} i:{1}\n{2}", msg, op.Key, e);
                result.Fail(msg, e);
                result.StatusCode = StatusCode.SocketPoolTimeout.ToInt();
            }
            catch (IOException e)
            {
                string msg = String.Format("Exception reading response - {0}", EndPoint);
                Log.ErrorFormat("m:{0} s:{1} i:{2}\n{3}", msg, op.Key,
                                socket == null ? Guid.Empty : socket.InstanceId, e);
                result.Fail(msg, e);
                if (result.StatusCode == null ||
                    result.StatusCode == StatusCode.Success.ToInt())
                {
                    result.StatusCode = StatusCode.InternalError.ToInt();
                }
            }
            catch (Exception e)
            {
                string msg = String.Format("Operation failed - {0}", EndPoint);
                Log.ErrorFormat("m:{0} s:{1} i:{2}\n{3}", msg, op.Key,
                                socket == null ? Guid.Empty : socket.InstanceId, e);
                result.Fail(msg, e);
                if (result.StatusCode == null ||
                    result.StatusCode == StatusCode.Success.ToInt())
                {
                    result.StatusCode = StatusCode.InternalError.ToInt();
                }
            }
            finally
            {
                if (socket != null)
                {
                    if (Log.IsDebugEnabled)
                    {
                        Log.DebugFormat("End execute {0} with {1}", op.Key, socket.InstanceId);
                    }
                    _pool.Release(socket);
                }
            }
            if (Log.IsDebugEnabled)
            {
                const string msg = "Operation {0} :i {1} n: {2} t: {3} m: {4} sc: {5} r: {6}";
                Log.DebugFormat(msg, result.Success ?
                                op.RetryAttempts > 0 ? "succeeded*" : "succeeded" :
                                op.RetryAttempts > 0 ? "failed*" : "failed",
                                op.Key,
                                _endpoint, Thread.CurrentThread.Name,
                                result.Message,
                                Enum.GetName(typeof(StatusCode), result.StatusCode ?? 0),
                                op.RetryAttempts);
            }
            return(result);
        }