private static void ThrowForUnboundResponseHandler(HttpOperationHandler handler, HttpParameter parameter, string operationName) { Fx.Assert(handler != null, "The 'handler' parameter should not be null."); Fx.Assert(parameter != null, "The 'parameter' parameter should not be null."); Fx.Assert(operationName != null, "The 'operationName' parameter should not be null."); string exceptionMessage = null; if (parameter.ValueConverter.CanConvertFromString) { exceptionMessage = SR.ResponseHandlerWithNoPossibleBindingForStringConvertableType( HttpOperationHandler.HttpOperationHandlerType.Name, handler.ToString(), operationName, parameter.Name, parameter.Type.Name, handler.GetType().Name); } else { exceptionMessage = SR.ResponseHandlerWithNoPossibleBindingForNonStringConvertableType( HttpOperationHandler.HttpOperationHandlerType.Name, handler.ToString(), operationName, parameter.Name, parameter.Type.Name, handler.GetType().Name); } Fx.Assert(exceptionMessage != null, "The 'exceptionMessage' variable should have been set."); throw Fx.Exception.AsError(new InvalidOperationException(exceptionMessage)); }
public void OutputParametersReturnsReflectedHttpParameters() { List <Type> types = new List <Type>(); TestDataAssert.Execute( TestData.RepresentativeValueAndRefTypeTestDataCollection, (type, obj) => { if (!types.Contains(type)) { types.Add(type); for (int i = 2; i <= 17; i++) { if (types.Count - i < 0) { break; } Type[] typeArray = types.Skip(types.Count - i).ToArray(); HttpOperationHandler genericHandler = GetGenericHandlerForTypes(typeArray); for (int j = 0; j < genericHandler.OutputParameters.Count; j++) { HttpParameter parameter = genericHandler.OutputParameters[j]; Assert.AreEqual("output", parameter.Name, "The HttpParameter.Name should have been 'input'."); Assert.AreEqual(typeArray.Last(), parameter.Type, "The HttpParameter.Type should have been the last type from the array."); } } } }); }
private static void ThrowForUnboundParameter(HttpOperationHandler handler, HttpParameter parameter, HandlerType handlerType, string operationName) { Fx.Assert(handler != null, "The 'handler' parameter should not be null."); Fx.Assert(parameter != null, "The 'parameter' parameter should not be null."); Fx.Assert(operationName != null, "The 'operationName' parameter should not be null."); if (handler == responseMessageSinkHandler) { throw Fx.Exception.AsError( new InvalidOperationException( SR.ResponseSinkHandlerWithNoHttpResponseMessageSource( HttpOperationHandler.HttpOperationHandlerType.Name, HttpTypeHelper.HttpResponseMessageType.Name, operationName))); } switch (handlerType) { case HandlerType.Request: ThrowForUnboundRequestHandler(handler, parameter, operationName); break; case HandlerType.ServiceOperation: ThrowForUnboundServiceOperation(parameter, operationName); break; case HandlerType.Response: ThrowForUnboundResponseHandler(handler, parameter, operationName); break; default: Fx.Assert("The handlerType should have been one of the above cases."); break; } }
public void Constructor() { HttpOperationHandler[] handlers = new HttpOperationHandler[0]; SHttpOperationDescription operation = new SHttpOperationDescription() { ReturnValue = HttpParameter.ResponseMessage }; OperationHandlerPipelineInfo pipelineInfo = new OperationHandlerPipelineInfo(handlers, handlers, operation); MOperationHandlerPipelineInfo molePipelineInfo = new MOperationHandlerPipelineInfo(pipelineInfo); HttpRequestMessage requestAtCall = null; object[] valuesAtCall = null; molePipelineInfo.GetEmptyPipelineValuesArray = () => new object[0]; molePipelineInfo.SetHttpRequestMessageHttpRequestMessageObjectArray = (req, values) => { requestAtCall = req; valuesAtCall = values; }; HttpRequestMessage request = new HttpRequestMessage(); OperationHandlerPipelineContext context = new OperationHandlerPipelineContext(pipelineInfo, request); Assert.IsNotNull(requestAtCall, "HttpRequestMessage was not set in pipeline info."); Assert.IsNotNull(valuesAtCall, "Values were not set in pipeline info."); HttpAssert.AreEqual(request, requestAtCall); }
public void GetHttpResponseMessageCallsPipelineInfo() { HttpRequestMessage request = new HttpRequestMessage(); HttpResponseMessage response = new HttpResponseMessage() { RequestMessage = request }; HttpOperationHandler[] handlers = new HttpOperationHandler[0]; SHttpOperationDescription operation = new SHttpOperationDescription() { ReturnValue = HttpParameter.ResponseMessage }; OperationHandlerPipelineInfo pipelineInfo = new OperationHandlerPipelineInfo(handlers, handlers, operation); MOperationHandlerPipelineInfo molePipelineInfo = new MOperationHandlerPipelineInfo(pipelineInfo); molePipelineInfo.GetEmptyPipelineValuesArray = () => new object[0]; molePipelineInfo.SetHttpRequestMessageHttpRequestMessageObjectArray = (req, values) => { }; molePipelineInfo.GetHttpResponseMessageObjectArray = (values) => response; OperationHandlerPipelineContext context = new OperationHandlerPipelineContext(pipelineInfo, request); HttpResponseMessage responseReturned = context.GetHttpResponseMessage(); Assert.IsNotNull(responseReturned, "HttpResponseMessage was not returned."); HttpAssert.AreEqual(response, responseReturned); }
internal OperationHandlerInfo(int offset, HttpOperationHandler handler) { Fx.Assert(handler != null, "The 'handler' parameter should not be null."); this.PipelineValuesOffset = offset; this.HandlerInputCount = handler.InputParameters.Count; this.OutputParameterInfo = new OutputParameterInfo[handler.OutputParameters.Count]; }
public void Constructor() { HttpOperationHandler[] handlers = new HttpOperationHandler[0]; SHttpOperationDescription operation = new SHttpOperationDescription() { ReturnValue = HttpParameter.ResponseMessage }; OperationHandlerPipeline pipeline = new OperationHandlerPipeline(handlers, handlers, operation); }
public void ConstructorThrowsWithNullResponseHandlers() { HttpOperationHandler[] handlers = new HttpOperationHandler[0]; SHttpOperationDescription operation = new SHttpOperationDescription() { ReturnValue = HttpParameter.ResponseMessage }; ExceptionAssert.ThrowsArgumentNull("responseHttpOperationHandlers", () => new OperationHandlerPipeline(handlers, null, operation)); }
public void ExecuteRequestPipeline() { HttpOperationHandler[] handlers = new HttpOperationHandler[0]; SHttpOperationDescription operation = new SHttpOperationDescription() { ReturnValue = HttpParameter.ResponseMessage }; OperationHandlerPipeline pipeline = new OperationHandlerPipeline(handlers, handlers, operation); HttpRequestMessage request = new HttpRequestMessage(); OperationHandlerPipelineContext context = pipeline.ExecuteRequestPipeline(request, new object[0]); Assert.IsNotNull(context, "Execute returned null context."); }
internal HttpResponseMessage ExecuteResponsePipeline(OperationHandlerPipelineContext pipelineContext, object[] parameters, object result) { Fx.Assert(pipelineContext != null, "The 'pipelineContext' parameter should not be null."); Fx.Assert(parameters != null, "The 'parameters' parameter should not be null."); object[] pipelineParameters = new object[parameters.Length + 1]; pipelineParameters[0] = result; Array.Copy(parameters, 0, pipelineParameters, 1, parameters.Length); pipelineContext.SetOutputValuesAndAdvance(pipelineParameters); for (int handlerIndex = 0; handlerIndex < this.responseHandlersCount; handlerIndex++) { HttpOperationHandler handler = this.responseHandlers[handlerIndex]; object[] inputValues = pipelineContext.GetInputValues(); object[] outputValues = handler.Handle(inputValues); pipelineContext.SetOutputValuesAndAdvance(outputValues); } return(pipelineContext.GetHttpResponseMessage()); }
public void InputParametersReturnsReflectedHttpParameters() { List <Type> types = new List <Type>(); TestDataAssert.Execute( TestData.RepresentativeValueAndRefTypeTestDataCollection, (type, obj) => { if (!types.Contains(type)) { types.Add(type); for (int i = 2; i <= 17; i++) { if (types.Count - i < 0) { break; } Type[] typeArray = types.Skip(types.Count - i).ToArray(); HttpOperationHandler genericHandler = GetGenericHandlerForTypes(typeArray); for (int j = 0; j < genericHandler.InputParameters.Count; j++) { HttpParameter parameter = genericHandler.InputParameters[j]; Assert.AreEqual(typeArray[j], parameter.Type, "The HttpParameter.Type should have been the same type as from the array."); if (i == 2) { Assert.AreEqual("input", parameter.Name, "The HttpParameter.Name should have been 'input'."); } else { string expectedName = "input" + (j + 1).ToString(); Assert.AreEqual(expectedName, parameter.Name, string.Format("The HttpParameter.Name should have been '{0}'.", expectedName)); } } } } }); }
public void ExecuteResponsePipeline() { HttpOperationHandler[] handlers = new HttpOperationHandler[0]; SHttpOperationDescription operation = new SHttpOperationDescription() { ReturnValue = HttpParameter.ResponseMessage }; OperationHandlerPipeline pipeline = new OperationHandlerPipeline(handlers, handlers, operation); HttpRequestMessage request = new HttpRequestMessage(); HttpResponseMessage response = new HttpResponseMessage() { RequestMessage = request }; OperationHandlerPipelineContext context = pipeline.ExecuteRequestPipeline(request, new object[0]); //// TODO: what is the convention for returning an HttpResponse from the operation? HttpResponseMessage actualResponse = pipeline.ExecuteResponsePipeline(context, new object[0], response); Assert.IsNotNull(actualResponse, "Execute returned null response."); }
internal OperationHandlerPipelineContext ExecuteRequestPipeline(HttpRequestMessage request, object[] parameters) { Fx.Assert(request != null, "The 'request' parameter should not be null."); Fx.Assert(parameters != null, "The 'parameters' parameter should not be null."); OperationHandlerPipelineContext pipelineContext = new OperationHandlerPipelineContext(this.pipelineContextInfo, request); for (int handlerIndex = 0; handlerIndex < this.requestHandlersCount; handlerIndex++) { HttpOperationHandler handler = this.requestHandlers[handlerIndex]; object[] inputValues = pipelineContext.GetInputValues(); object[] outputValues = handler.Handle(inputValues); pipelineContext.SetOutputValuesAndAdvance(outputValues); } object[] pipelineParameters = pipelineContext.GetInputValues(); Fx.Assert(pipelineParameters.Length == parameters.Length, "The two parameter object arrays should have the same length."); Array.Copy(pipelineParameters, parameters, parameters.Length); return(pipelineContext); }
public void SetOutputValuesAndAdvanceCallsPipelineInfo() { HttpRequestMessage request = new HttpRequestMessage(); HttpResponseMessage response = new HttpResponseMessage() { RequestMessage = request }; HttpOperationHandler[] handlers = new HttpOperationHandler[0]; SHttpOperationDescription operation = new SHttpOperationDescription() { ReturnValue = HttpParameter.ResponseMessage }; OperationHandlerPipelineInfo pipelineInfo = new OperationHandlerPipelineInfo(handlers, handlers, operation); int indexAtCall = -1; object[] valuesAtCall = null; object[] pipelineValuesAtCall = null; MOperationHandlerPipelineInfo molePipelineInfo = new MOperationHandlerPipelineInfo(pipelineInfo); molePipelineInfo.GetEmptyPipelineValuesArray = () => new object[0]; molePipelineInfo.SetHttpRequestMessageHttpRequestMessageObjectArray = (req, values) => { }; molePipelineInfo.SetOutputValuesFromHandlerInt32ObjectArrayObjectArray = (index, values, pipelineValues) => { indexAtCall = index; valuesAtCall = values; pipelineValuesAtCall = pipelineValues; }; OperationHandlerPipelineContext context = new OperationHandlerPipelineContext(pipelineInfo, request); context.SetOutputValuesAndAdvance(new object[0]); Assert.AreEqual(1, indexAtCall, "Handler index was not set."); Assert.IsNotNull(valuesAtCall, "Values were not set."); Assert.IsNotNull(pipelineValuesAtCall, "Pipeline values were not set."); }
private static OperationHandlerInfo[] GenerateHandlerInfo(List <HttpOperationHandler> handlers, List <HttpParameterBinding> bindings, string operationName, out int pipelineValuesArraySize) { Fx.Assert(handlers != null, "The 'handlers' parameter should not be null."); Fx.Assert(bindings != null, "The 'bindings' parameter should not be null."); Fx.Assert(operationName != null, "The 'bindings' parameter should not be null."); pipelineValuesArraySize = 0; OperationHandlerInfo[] handlerInfo = new OperationHandlerInfo[handlers.Count]; // First, construct the OperationHandlerInfo[] to determine each handlers's offset // in the pipelineValuesArray. for (int handlerIndex = 0; handlerIndex < handlers.Count; handlerIndex++) { HttpOperationHandler handler = handlers[handlerIndex]; OperationHandlerInfo info = new OperationHandlerInfo(pipelineValuesArraySize, handler); handlerInfo[handlerIndex] = info; pipelineValuesArraySize += info.HandlerInputCount; handlers[handlerIndex].OperationName = operationName; } // Second, map the HttpParameterBindings into the OutputParameterInfo array indices. for (int handlerIndex = 0; handlerIndex < handlers.Count; handlerIndex++) { HttpOperationHandler handler = handlers[handlerIndex]; for (int paramIndex = 0; paramIndex < handler.OutputParameters.Count; paramIndex++) { OperationHandlerInfo info = handlerInfo[handlerIndex]; info.OutputParameterInfo[paramIndex] = new OutputParameterInfo( bindings.Where(binding => binding.OutputHandlerIndex == handlerIndex && binding.OutputParameterIndex == paramIndex) .Select(binding => handlerInfo[binding.InputHandlerIndex].PipelineValuesOffset + binding.InputParameterIndex)); } } return(handlerInfo); }
public void GetInputValuesCallsPipelineInfo() { HttpOperationHandler[] handlers = new HttpOperationHandler[0]; SHttpOperationDescription operation = new SHttpOperationDescription() { ReturnValue = HttpParameter.ResponseMessage }; OperationHandlerPipelineInfo pipelineInfo = new OperationHandlerPipelineInfo(handlers, handlers, operation); MOperationHandlerPipelineInfo molePipelineInfo = new MOperationHandlerPipelineInfo(pipelineInfo); molePipelineInfo.GetEmptyPipelineValuesArray = () => new object[0]; molePipelineInfo.SetHttpRequestMessageHttpRequestMessageObjectArray = (req, values) => { }; bool calledForValues = false; int handlerIndexAtCall = -1; object[] valuesAtCall = null; molePipelineInfo.GetInputValuesForHandlerInt32ObjectArray = (index, values) => { calledForValues = true; handlerIndexAtCall = index; valuesAtCall = values; return(new object[0]); }; HttpRequestMessage request = new HttpRequestMessage(); OperationHandlerPipelineContext context = new OperationHandlerPipelineContext(pipelineInfo, request); object[] returnedValues = context.GetInputValues(); Assert.IsTrue(calledForValues, "PipelineInfo was not called for its values."); Assert.AreEqual(1, handlerIndexAtCall, "Handler index should have been 0."); Assert.IsNotNull(valuesAtCall, "Values at call should have not been null."); Assert.IsNotNull(returnedValues, "Returned values were null."); Assert.AreEqual(0, returnedValues.Length, "Returned values were incorrect length."); }
public void ConstructorThrowsWithNullOperation() { HttpOperationHandler[] handlers = new HttpOperationHandler[0]; ExceptionAssert.ThrowsArgumentNull("operation", () => new OperationHandlerPipeline(handlers, handlers, null)); }
private static List <HttpParameterBinding> BindHandlers(List <HttpOperationHandler> handlers, string operationName, int serviceOperationIndex) { Fx.Assert(handlers != null, "The 'handlers' parameter should not be null."); Fx.Assert(operationName != null, "The 'operationName' parameter should not be null."); List <HttpParameterBinding> pipelineBindings = new List <HttpParameterBinding>(); for (int inHandlerIndex = handlers.Count - 1; inHandlerIndex >= 1; inHandlerIndex--) { HttpOperationHandler inHandler = handlers[inHandlerIndex]; HandlerType inHandlerType = GetHandlerType(inHandlerIndex, serviceOperationIndex); for (int inParamIndex = 0; inParamIndex < inHandler.InputParameters.Count; inParamIndex++) { HttpParameter inParam = inHandler.InputParameters[inParamIndex]; List <HttpParameterBinding> bindings = new List <HttpParameterBinding>(); List <HttpParameterBinding> tentativeBindings = new List <HttpParameterBinding>(); for (int outHandlerIndex = inHandlerIndex - 1; outHandlerIndex >= 0; outHandlerIndex--) { HttpOperationHandler outHandler = handlers[outHandlerIndex]; HandlerType outHandlerType = GetHandlerType(outHandlerIndex, serviceOperationIndex); for (int outParamIndex = 0; outParamIndex < outHandler.OutputParameters.Count; outParamIndex++) { HttpParameter outParam = outHandler.OutputParameters[outParamIndex]; if (inParam.IsAssignableFromParameter(outParam.Type)) { HttpParameterBinding binding = new HttpParameterBinding(); binding.InputHandler = inHandler; binding.InputHandlerIndex = inHandlerIndex; binding.InputParameter = inParam; binding.InputParameterIndex = inParamIndex; binding.InputHandlerType = inHandlerType; binding.OutputHandler = outHandler; binding.OutputHandlerIndex = outHandlerIndex; binding.OutputParameter = outParam; binding.OutputParameterIndex = outParamIndex; binding.OutputHandlerType = outHandlerType; // If their names match or the input is either HttpRequesMessage, // HttpResponseMessage, or HttpContent, then go ahead and bind if (string.Equals(outParam.Name, inParam.Name, StringComparison.OrdinalIgnoreCase) || HttpTypeHelper.IsHttp(inParam.Type)) { bindings.Add(binding); } else { // Otherwise we will tentatively bind if this is // not a string conversion assignment if (outParam.Type != TypeHelper.StringType || !inParam.ValueConverter.CanConvertFromString) { tentativeBindings.Add(binding); } } } } } if (bindings.Count > 0) { pipelineBindings.AddRange(bindings); } else if (tentativeBindings.Count == 1) { pipelineBindings.AddRange(tentativeBindings); } else if (tentativeBindings.Count > 1) { ThrowForMulitpleTypeOnlyBindings(tentativeBindings, operationName); } else { ThrowForUnboundParameter(inHandler, inParam, inHandlerType, operationName); } } } return(pipelineBindings); }
private static void ThrowForMulitpleTypeOnlyBindings(List <HttpParameterBinding> tentativeBindings, string operationName) { Fx.Assert(tentativeBindings != null, "The 'tentativeBindings' parameter should not be null."); Fx.Assert(tentativeBindings.Count > 0, "The 'tentativeBindings' list should not be empty."); Fx.Assert(operationName != null, "The 'operationName' parameter should not be null."); string exceptionMessage = null; HandlerType inHandlerType = tentativeBindings[0].InputHandlerType; HttpOperationHandler inHandler = tentativeBindings[0].InputHandler; HttpParameter inParameter = tentativeBindings[0].InputParameter; switch (inHandlerType) { case HandlerType.Request: exceptionMessage = SR.RequestHandlerWithMultipleTypeOnlyBindings( HttpOperationHandler.HttpOperationHandlerType.Name, inHandler.ToString(), operationName, inParameter.Name, inParameter.Type.Name); break; case HandlerType.ServiceOperation: exceptionMessage = SR.ServiceOperationWithMultipleTypeOnlyBindings( operationName, inParameter.Name, inParameter.Type.Name, HttpOperationHandler.HttpOperationHandlerType.Name); break; case HandlerType.Response: exceptionMessage = SR.ResponseHandlerWithMultipleTypeOnlyBindings( HttpOperationHandler.HttpOperationHandlerType.Name, inHandler.ToString(), operationName, inParameter.Name, inParameter.Type.Name); break; default: Fx.Assert("The handlerType should have been one of the above cases."); break; } StringBuilder stringBuilder = new StringBuilder(exceptionMessage); foreach (HttpParameterBinding binding in tentativeBindings) { string parameterMessage = null; HandlerType outHandlerType = binding.OutputHandlerType; HttpOperationHandler outHandler = binding.OutputHandler; HttpParameter outParameter = binding.OutputParameter; switch (outHandlerType) { case HandlerType.Request: parameterMessage = SR.RequestHandlerTypeOnlyOutputParameter( HttpOperationHandler.HttpOperationHandlerType.Name, outHandler.ToString(), outParameter.Name, outParameter.Type.Name); break; case HandlerType.ServiceOperation: parameterMessage = SR.ServiceOperationTypeOnlyOutputParameter( outParameter.Name, outParameter.Type.Name); break; case HandlerType.Response: parameterMessage = SR.ResponseHandlerTypeOnlyOutputParameter( HttpOperationHandler.HttpOperationHandlerType.Name, outHandler.ToString(), outParameter.Name, outParameter.Type.Name); break; default: Fx.Assert("The handlerType should have been one of the above cases."); break; } stringBuilder.Append(Environment.NewLine); stringBuilder.Append(parameterMessage); } throw Fx.Exception.AsError(new InvalidOperationException(stringBuilder.ToString())); }