C# 使用委托包装异常处理时Web API调用不起作用

C# 使用委托包装异常处理时Web API调用不起作用,c#,asp.net-web-api,owin,self-hosting,C#,Asp.net Web Api,Owin,Self Hosting,我有一个带有自托管OWIN的.NET4.5.2应用程序来支持内部WebAPI。为了进行常规异常处理,我尝试将所有调用封装在一个方法“TryOk”中,并将委托作为参数。TryOk将关心异常并处理它们 我尝试在没有委托的情况下调用web api,它成功了。只有在使用委托时,才会出现错误 我将代码缩减到最大值,并删除了所有类似async的代码平衡 [HttpPost,路由(“echo”)] 公共IHttpActionResult MyEchoApi([FromBody]字符串回显) { //这是工作:

我有一个带有自托管OWIN的.NET4.5.2应用程序来支持内部WebAPI。为了进行常规异常处理,我尝试将所有调用封装在一个方法“TryOk”中,并将委托作为参数。TryOk将关心异常并处理它们

我尝试在没有委托的情况下调用web api,它成功了。只有在使用委托时,才会出现错误

我将代码缩减到最大值,并删除了所有类似async的代码平衡

[HttpPost,路由(“echo”)]
公共IHttpActionResult MyEchoApi([FromBody]字符串回显)
{
//这是工作:直接返回
//返回Ok(“你说“+echo?”“没什么”);
//这也是可行的:带异常处理的直接返回
//尝试{返回Ok(call());}
//catch(异常ex){return BadRequest(ex.Message);}
//这不起作用:正在包装委托
return TryOk(()=>{return Ok(“你说“+echo?”“nothing”);});
}
专用IHttpActionResult TryOk(函数调用)
{
尝试{返回Ok(call());}
catch(异常ex){return BadRequest(ex.Message);}
}
我在“Microsoft.Owin.Host.HttpListener.RequestProcessing.HttpListenerStreamWrapper.”上收到异常“从“长度”获取值时出错”,内部异常为“此流不支持搜索操作”

例外情况详情:

"ExceptionMessage": "Error getting value from 'Length' on 'Microsoft.Owin.Host.HttpListener.RequestProcessing.HttpListenerStreamWrapper'.",
"ExceptionType": "Newtonsoft.Json.JsonSerializationException",
"StackTrace": "   bei Newtonsoft.Json.Serialization.DynamicValueProvider.GetValue(Object target)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.CalculatePropertyValues(JsonWriter writer, Object value, JsonContainerContract contract, JsonProperty member, JsonProperty property, JsonContract& memberContract, Object& memberValue)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeObject(JsonWriter writer, Object value, JsonObjectContract contract, JsonProperty member, JsonContainerContract collectionContract, JsonProperty containerProperty)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeDictionary(JsonWriter writer, IDictionary values, JsonDictionaryContract contract, JsonProperty member, JsonContainerContract collectionContract, JsonProperty containerProperty)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeObject(JsonWriter writer, Object value, JsonObjectContract contract, JsonProperty member, JsonContainerContract collectionContract, JsonProperty containerProperty)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeObject(JsonWriter writer, Object value, JsonObjectContract contract, JsonProperty member, JsonContainerContract collectionContract, JsonProperty containerProperty)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeDictionary(JsonWriter writer, IDictionary values, JsonDictionaryContract contract, JsonProperty member, JsonContainerContract collectionContract, JsonProperty containerProperty)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeObject(JsonWriter writer, Object value, JsonObjectContract contract, JsonProperty member, JsonContainerContract collectionContract, JsonProperty containerProperty)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeObject(JsonWriter writer, Object value, JsonObjectContract contract, JsonProperty member, JsonContainerContract collectionContract, JsonProperty containerProperty)
   bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.Serialize(JsonWriter jsonWriter, Object value, Type objectType)
   bei Newtonsoft.Json.JsonSerializer.SerializeInternal(JsonWriter jsonWriter, Object value, Type objectType)
   bei System.Net.Http.Formatting.BaseJsonMediaTypeFormatter.WriteToStream(Type type, Object value, Stream writeStream, Encoding effectiveEncoding)
   bei System.Net.Http.Formatting.JsonMediaTypeFormatter.WriteToStream(Type type, Object value, Stream writeStream, Encoding effectiveEncoding)
   bei System.Net.Http.Formatting.BaseJsonMediaTypeFormatter.WriteToStreamAsync(Type type, Object value, Stream writeStream, HttpContent content, TransportContext transportContext, CancellationToken cancellationToken)
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
   bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   bei System.Web.Http.Owin.HttpMessageHandlerAdapter.<BufferResponseContentAsync>d__27.MoveNext()",
"InnerException": {
    "Message": "An error has occurred.",
    "ExceptionMessage": "This stream does not support seek operations.",
    "ExceptionType": "System.NotSupportedException",
    "StackTrace": "   bei System.Net.HttpResponseStream.get_Length()
    bei GetLength(Object )
    bei Newtonsoft.Json.Serialization.DynamicValueProvider.GetValue(Object target)"
}
“ExceptionMessage”:“从“Microsoft.Owin.Host.HttpListener.RequestProcessing.HttpListenerStreamWrapper”上的“Length”获取值时出错。”,
“ExceptionType”:“Newtonsoft.Json.JsonSerializationException”,
“StackTrace”:“bei Newtonsoft.Json.Serialization.DynamicValueProvider.GetValue(对象目标)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.CalculatePropertyValues(JsonWriter编写器、对象值、JsonContainerContract、JsonProperty成员、JsonProperty属性、JsonContract和memberContract、对象和成员值)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializationObject(JsonWriter编写器、对象值、JSONObject合同、JsonProperty成员、JsonContainerContract集合合同、JsonProperty容器属性)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializationDictionary(JsonWriter编写器、IDictionary值、JSONDictionary合同、JsonProperty成员、JsonContainerContract集合合同、JsonProperty容器属性)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializationObject(JsonWriter编写器、对象值、JSONObject合同、JsonProperty成员、JsonContainerContract集合合同、JsonProperty容器属性)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializationObject(JsonWriter编写器、对象值、JSONObject合同、JsonProperty成员、JsonContainerContract集合合同、JsonProperty容器属性)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializationDictionary(JsonWriter编写器、IDictionary值、JSONDictionary合同、JsonProperty成员、JsonContainerContract集合合同、JsonProperty容器属性)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializationObject(JsonWriter编写器、对象值、JSONObject合同、JsonProperty成员、JsonContainerContract集合合同、JsonProperty容器属性)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializationObject(JsonWriter编写器、对象值、JSONObject合同、JsonProperty成员、JsonContainerContract集合合同、JsonProperty容器属性)
bei Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.serializate(JsonWriter JsonWriter,对象值,类型objectType)
bei Newtonsoft.Json.JsonSerializer.SerializeInternal(JsonWriter JsonWriter,对象值,类型objectType)
bei System.Net.Http.Formatting.BaseJsonMediaTypeFormatter.WriteToStream(类型类型、对象值、流writeStream、编码有效编码)
bei System.Net.Http.Formatting.JsonMediaTypeFormatter.WriteToStream(类型类型、对象值、流writeStream、编码有效编码)
bei System.Net.Http.Formatting.BaseJsonMediaTypeFormatter.WriteToStreamAsync(类型类型、对象值、流writeStream、HttpContent内容、TransportContext TransportContext、CancellationToken CancellationToken)
---这是一个非常有趣的故事---
bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
bei System.Runtime.CompilerServices.TaskWaiter.HandleNonSuccessAndDebuggerNotification(任务)
bei System.Web.Http.Owin.HttpMessageHandlerAdapter.d_u27.MoveNext()“,
“内部异常”:{
“消息”:“发生错误。”,
“ExceptionMessage”:“此流不支持查找操作。”,
“异常类型”:“System.NotSupportedException”,
“StackTrace”:“bei System.Net.HttpResponseStream.get_Length()
bei GetLength(对象)
bei Newtonsoft.Json.Serialization.DynamicValueProvider.GetValue(对象目标)”
}
我做错了什么

谢谢你的回答或想法

--jaz

你是,这就是为什么它会导致你的错误

在这一行中,您在回调函数中返回了IHttpActionResult:

 return TryOk(() => { return Ok("you say " + echo ?? "nothing"); });
您不需要调用
Ok(call())
,只需调用
returncall()


我还有一个建议,我建议你使用一个全球定位系统。

哦,天哪,我犯了一个多么愚蠢的错误!我应该自己发现的。谢谢你的快速回答。感谢您推荐ex过滤器-jaz@jaz错误总是会发生的,所以不要担心。
private IHttpActionResult TryOk<T>(Func<T> call)
{
    // call itself returns an Ok http action result, you are returning a reposnse on another response! just change to call();
    try { return Ok(call()); }
    catch (Exception ex) { return BadRequest(ex.Message); }
}
try
{
    var returnValue = call();

    if(returnValue is IHttpActionResult)
        return returnValue;

    return Ok(returnValue);
}
catch(Exception ex)
{
    return BadRequest(ex.Message);
}