private void ProcessRequest(IRingMasterRequest request, Action<RequestResponse, Exception> onCompletion) { if (request == null) { throw new ArgumentNullException(nameof(request)); } switch (request.RequestType) { case RingMasterRequestType.Init: { var initRequest = (RequestInit)request; this.requestHandler = this.onInitSession(initRequest); var initResponse = new RequestResponse { ResultCode = (int)RingMasterException.Code.Ok, Content = new string[] { initRequest.SessionId.ToString(), Guid.NewGuid().ToString() }, }; this.requestOrdering.Release(); RingMasterServerEventSource.Log.ProcessSessionInit(this.Id, initResponse.ResultCode); onCompletion?.Invoke(initResponse, null); return; } case RingMasterRequestType.GetData: { var getDataRequest = (RequestGetData)request; getDataRequest.Watcher = this.MakeWatcher(getDataRequest.Watcher); break; } case RingMasterRequestType.GetChildren: { var getChildrenRequest = (RequestGetChildren)request; getChildrenRequest.Watcher = this.MakeWatcher(getChildrenRequest.Watcher); break; } case RingMasterRequestType.Exists: { var existsRequest = (RequestExists)request; existsRequest.Watcher = this.MakeWatcher(existsRequest.Watcher); break; } } if (this.server.Redirect != null) { RedirectSuggested redirect = this.server.Redirect(); this.requestOrdering.Release(); RingMasterServerEventSource.Log.RedirectionSuggested(this.Id, redirect?.SuggestedConnectionString); onCompletion?.Invoke( new RequestResponse() { ResponsePath = request.Path, ResultCode = (int)RingMasterException.Code.Sessionmoved, Stat = default(Stat), Content = redirect, }, null); return; } if (this.requestHandler != null) { QueuedWorkItemPool.Default.Queue( () => { // Give a signal that the next request can be started. For read requests in the same session, // they may be processed concurrently. For write requests, they will be ordered by locking. this.requestOrdering.Release(); this.requestHandler.RequestOverlapped(request, onCompletion); }); return; } throw new InvalidOperationException("Session has not been initialized"); }
private RequestResponse ProcessRequest(IRingMasterRequest request, IZooKeeperRequest zkprRequest) { if (request == null) { throw new ArgumentNullException(nameof(request)); } if (zkprRequest == null) { throw new ArgumentNullException(nameof(zkprRequest)); } switch (request.RequestType) { case RingMasterRequestType.Init: { var initRequest = (Requests.RequestInit)request; RequestResponse initResponse = null; if (this.requestHandler == null) { this.requestHandler = this.onInitSession(initRequest); if (((zkprRequest as ZkprProtocolMessages.CreateSession).SessionId != 0) || (zkprRequest as ZkprProtocolMessages.CreateSession).IsNullPassword == false) { initResponse = new RequestResponse { ResultCode = (int)RingMasterException.Code.Authfailed, Content = new string[] { "0", string.Empty }, }; } } if (initResponse == null) { initResponse = (this.requestHandler as CoreRequestHandler).InitResponse; } ZooKeeperServerEventSource.Log.ProcessSessionInit(this.Id, initResponse.ResultCode); return(initResponse); } case RingMasterRequestType.GetData: { var getDataRequest = (Requests.RequestGetData)request; getDataRequest.Watcher = this.MakeWatcher(getDataRequest.Watcher); break; } case RingMasterRequestType.GetChildren: { var getChildrenRequest = (Requests.RequestGetChildren)request; getChildrenRequest.Watcher = this.MakeWatcher(getChildrenRequest.Watcher); break; } case RingMasterRequestType.Exists: { var existsRequest = (Requests.RequestExists)request; existsRequest.Watcher = this.MakeWatcher(existsRequest.Watcher); break; } } if (this.server.Redirect != null) { RedirectSuggested redirect = this.server.Redirect(); ZooKeeperServerEventSource.Log.RedirectionSuggested(this.Id, redirect?.SuggestedConnectionString); return(new RequestResponse() { ResponsePath = request.Path, ResultCode = (int)RingMasterException.Code.Sessionmoved, Stat = default(Stat), Content = redirect, }); } if (this.requestHandler != null) { using (var completed = new AutoResetEvent(false)) { RequestResponse response = null; this.requestHandler.RequestOverlapped(request, (r, e) => { response = r; completed.Set(); }); completed.WaitOne(); return(response); } } throw new InvalidOperationException("Session has not been initialized"); }