Как разрешить MVC ActionFilter видеть, что такое недопустимые исходные данные JSON?

У меня есть следующий метод действия с пользовательским [JsonFilter], и этот ActionFilterAttribute не вызывается, когда структура JSON для CustomClass, отправленная клиентом, недействительна:

  [JsonFilter(Param = "myCustomClass", JsonDataType = typeof(CustomClass)]
  [ValidateInput(false)]
  public ActionResult MyFunction(CustomClass myCustomClass) 
  {
     //Do something ground-breaking here
  }

Код [Json] ActionFilterAttribute будет вызываться только в том случае, если структура JSON, переданная клиентом, действительна. Если структура JSON, отправленная клиентом, недействительна, кажется, что конвейер среды MVC выдает следующее исключение, и моя логика ActionFilter никогда не вызывается (хотел бы отправить обратно специальный код ошибки для типа класса в ошибке). Вот исключение, которое я получаю и хотел бы, чтобы эти классы/события не пытались просматривать данные JSON при вызове моего метода действия:

Invalid JSON primitive: <reports the first character that resulting in invalid JSON format here> 
enter code here
Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code. 

Exception Details: System.ArgumentException: Invalid JSON primitive: .

Source Error: 
An unhandled exception was generated during the execution of the current web request. Information regarding the origin and location of the exception can be identified using the exception stack trace below. 

Stack Trace: 

[ArgumentException: Invalid JSON primitive: .]
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializePrimitiveObject() +762458
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializeInternal(Int32 depth) +360
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializeDictionary(Int32 depth) +542
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializeInternal(Int32 depth) +222
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializeList(Int32 depth) +379
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializeInternal(Int32 depth) +325
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializeDictionary(Int32 depth) +542
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializeInternal(Int32 depth) +222
   System.Web.Script.Serialization.JavaScriptObjectDeserializer.BasicDeserialize(String input, Int32 depthLimit, JavaScriptSerializer serializer) +115
   System.Web.Script.Serialization.JavaScriptSerializer.Deserialize(JavaScriptSerializer serializer, String input, Type type, Int32 depthLimit) +57
   System.Web.Mvc.JsonValueProviderFactory.GetValueProvider(ControllerContext controllerContext) +239
   System.Web.Mvc.ValueProviderFactoryCollection.GetValueProvider(ControllerContext controllerContext) +211
   System.Web.Mvc.ControllerBase.get_ValueProvider() +66
   System.Web.Mvc.ControllerActionInvoker.GetParameterValue(ControllerContext controllerContext, ParameterDescriptor parameterDescriptor) +78
   System.Web.Mvc.ControllerActionInvoker.GetParameterValues(ControllerContext controllerContext, ActionDescriptor actionDescriptor) +153
   System.Web.Mvc.Async.<>c__DisplayClass21.<BeginInvokeAction>b__19(AsyncCallback asyncCallback, Object asyncState) +1449
   System.Web.Mvc.Async.WrappedAsyncResultBase`1.Begin(AsyncCallback callback, Object state, Int32 timeout) +150
   System.Web.Mvc.Async.AsyncResultWrapper.Begin(AsyncCallback callback, Object state, BeginInvokeDelegate beginDelegate, EndInvokeDelegate`1 endDelegate, Object tag, Int32 timeout) +96
   System.Web.Mvc.Async.AsyncControllerActionInvoker.BeginInvokeAction(ControllerContext controllerContext, String actionName, AsyncCallback callback, Object state) +487
   System.Web.Mvc.Controller.<BeginExecuteCore>b__1c(AsyncCallback asyncCallback, Object asyncState, ExecuteCoreState innerState) +45
   System.Web.Mvc.Async.WrappedAsyncVoid`1.CallBeginDelegate(AsyncCallback callback, Object callbackState) +111
   System.Web.Mvc.Async.WrappedAsyncResultBase`1.Begin(AsyncCallback callback, Object state, Int32 timeout) +150
   System.Web.Mvc.Async.AsyncResultWrapper.Begin(AsyncCallback callback, Object callbackState, BeginInvokeDelegate`1 beginDelegate, EndInvokeVoidDelegate`1 endDelegate, TState invokeState, Object tag, Int32 timeout, SynchronizationContext callbackSyncContext) +203
   System.Web.Mvc.Controller.BeginExecuteCore(AsyncCallback callback, Object state) +879
   System.Web.Mvc.Async.WrappedAsyncResultBase`1.Begin(AsyncCallback callback, Object state, Int32 timeout) +150
   System.Web.Mvc.Async.AsyncResultWrapper.Begin(AsyncCallback callback, Object callbackState, BeginInvokeDelegate`1 beginDelegate, EndInvokeVoidDelegate`1 endDelegate, TState invokeState, Object tag, Int32 timeout, SynchronizationContext callbackSyncContext) +154
   System.Web.Mvc.Controller.BeginExecute(RequestContext requestContext, AsyncCallback callback, Object state) +527
   System.Web.Mvc.MvcHandler.<BeginProcessRequest>b__4(AsyncCallback asyncCallback, Object asyncState, ProcessRequestState innerState) +108
   System.Web.Mvc.Async.WrappedAsyncVoid`1.CallBeginDelegate(AsyncCallback callback, Object callbackState) +111
   System.Web.Mvc.Async.WrappedAsyncResultBase`1.Begin(AsyncCallback callback, Object state, Int32 timeout) +150
   System.Web.Mvc.Async.AsyncResultWrapper.Begin(AsyncCallback callback, Object callbackState, BeginInvokeDelegate`1 beginDelegate, EndInvokeVoidDelegate`1 endDelegate, TState invokeState, Object tag, Int32 timeout, SynchronizationContext callbackSyncContext) +203
   System.Web.Mvc.MvcHandler.BeginProcessRequest(HttpContextBase httpContext, AsyncCallback callback, Object state) +665
   System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +12289467
   System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +288

________________________________________
Version Information: Microsoft .NET Framework Version:4.0.30319; ASP.NET Version:4.0.30319.34280

Я также попытался добавить следующее в класс/свойства:

[ScriptIgnore]

Но это тоже не сработало. Если я удалю параметр из своего метода действия, тогда мой метод получит возможность просмотреть переданные данные, но мне нужно затем получить доступ к объекту запроса для JSON, когда у меня есть выделенный фильтр действий JSON для преобразования JSON в C # класс. Есть какие-либо предложения относительно того, как предотвратить попытку Framework проанализировать этот JSON до того, как мой ActionFilter приступит к работе?


person Moe Howard    schedule 23.01.2016    source источник
comment
Попробуйте реализовать собственный фильтр исключений.   -  person Hamlet Hakobyan    schedule 23.01.2016
comment
Рассмотрю это. Но при первоначальном осмотре оказалось, что это глобальный фильтр, и мы надеялись, что его можно будет применить на уровне метода с атрибутами, указывающими, какой тип кода ошибки выдавать. Еще раз спасибо, опубликую свои обновления, как только у меня будут некоторые подробности.   -  person Moe Howard    schedule 25.01.2016
comment
Гамлет, вы были правы в своем ответе. Бесконечно благодарен. Я использовал этот пост для получения более подробной информации о реализации такого фильтра, и его можно применять на уровне метода действия: stackoverflow.com/questions/2073925/   -  person Moe Howard    schedule 26.01.2016


Ответы (1)


Гамлет, вы были правы в своем ответе. Бесконечно благодарен. Я использовал этот пост для более подробной информации о реализации такого фильтра, и его можно применять на уровне метода действия: Пользовательский фильтр исключений не срабатывает в asp.net MVC

person Moe Howard    schedule 25.01.2016