Esempio n. 1
0
 public ClientErrorResultFilter(
     ApiBehaviorOptions apiBehaviorOptions,
     ILogger <ClientErrorResultFilter> logger)
 {
     _clientErrorFactory = apiBehaviorOptions?.ClientErrorFactory ?? throw new ArgumentNullException(nameof(apiBehaviorOptions));
     _logger             = logger ?? throw new ArgumentNullException(nameof(logger));
 }
Esempio n. 2
0
 public DefaultProblemDetailsFactory(
     IOptions <ApiBehaviorOptions> options,
     IOptions <ProblemDetailsOptions>?problemDetailsOptions = null)
 {
     _options   = options?.Value ?? throw new ArgumentNullException(nameof(options));
     _configure = problemDetailsOptions?.Value?.CustomizeProblemDetails;
 }
Esempio n. 3
0
            public void When_CreatingValidationProblemDetailsWithClientErrorMapping_Expect_ValidationProblemDetailsWithClientErrorNotMapped()
            {
                // Arrange
                ApiBehaviorOptions apiBehaviorOptions = new ApiBehaviorOptions();

                int status = new Random().Next(int.MaxValue);

                apiBehaviorOptions.ClientErrorMapping[status] = new ClientErrorData
                {
                    Title = Guid.NewGuid().ToString(),
                    Link  = Guid.NewGuid().ToString(),
                };

                IOptions <ApiBehaviorOptions> options = Options.Create(apiBehaviorOptions);
                ProblemDetailsFactory         factory = new CustomProblemDetailsFactory(options);

                string title = Guid.NewGuid().ToString();
                string type  = Guid.NewGuid().ToString();

                // Act
                ValidationProblemDetails result =
                    factory.CreateValidationProblemDetails(new DefaultHttpContext(), new ModelStateDictionary(), status, title, type);

                // Assert
                Assert.NotEqual(apiBehaviorOptions.ClientErrorMapping[status].Title, title);
                Assert.NotEqual(apiBehaviorOptions.ClientErrorMapping[status].Link, type);
                Assert.Equal(status, result.Status);
                Assert.Equal(title, result.Title);
                Assert.Equal(type, result.Type);
            }
        private static ServiceCollection MockMvcServices()
        {
            var services = new ServiceCollection();

            services.TryAddSingleton <IFileProvider, InMemoryFileProvider>();
            services.AddSingleton(Mock.Of <IWebHostEnvironment>());
            services.AddSingleton(Mock.Of <ILoggerFactory>());
            services.AddTransient(typeof(IActionInvokerFactory), (s) => Mock.Of <IActionInvokerFactory>());
            services.AddTransient(typeof(IActionSelector), (s) => Mock.Of <IActionSelector>());
            services.AddTransient(typeof(DiagnosticSource), (s) => Mock.Of <DiagnosticSource>());

            services.TryAddSingleton <IOptions <ApiBehaviorOptions> >(x =>
            {
                var options = new ApiBehaviorOptions();
                options.InvalidModelStateResponseFactory = (a) => null;
                return(new OptionsWrapper <ApiBehaviorOptions>(options));
            });

            var roMock = new Mock <IOptions <RouteOptions> >();

            roMock.SetupGet(x => x.Value).Returns(new RouteOptions()
            {
                AppendTrailingSlash = true,
                ConstraintMap       = new Dictionary <string, Type>()
            });
            services.AddTransient(typeof(IOptions <RouteOptions>), (s) => roMock.Object);
            var optsMock = new Mock <IOptions <MvcOptions> >();

            optsMock.SetupGet(x => x.Value).Returns(Mock.Of <MvcOptions>());
            services.AddTransient(typeof(IOptions <MvcOptions>), (s) => optsMock.Object);

            services.AddMvcCore();
            services.AddOneScript();
            return(services);
        }
 public ConvertViewResultToObjectResultAttributeImpl(OutputFormatterSelector formatterSelector, ILoggerFactory loggerFactory, IOptions <MvcOptions> mvcOptions, IOptions <ApiBehaviorOptions> apiBehaviorOptions, bool enabled)
 {
     _logger             = loggerFactory.CreateLogger <ConvertViewResultToObjectResultAttribute>();
     _mvcOptions         = mvcOptions.Value;
     _apiBehaviorOptions = apiBehaviorOptions.Value;
     _enabled            = enabled;
 }
Esempio n. 6
0
        public ApiBehaviorApplicationModelProvider(
            IOptions <ApiBehaviorOptions> apiBehaviorOptions,
            IModelMetadataProvider modelMetadataProvider,
            IClientErrorFactory clientErrorFactory,
            ILoggerFactory loggerFactory)
        {
            _apiBehaviorOptions    = apiBehaviorOptions.Value;
            _modelMetadataProvider = modelMetadataProvider;
            _logger = loggerFactory.CreateLogger <ApiBehaviorApplicationModelProvider>();

            if (!_apiBehaviorOptions.SuppressModelStateInvalidFilter && _apiBehaviorOptions.InvalidModelStateResponseFactory == null)
            {
                throw new ArgumentException(Resources.FormatPropertyOfTypeCannotBeNull(
                                                typeof(ApiBehaviorOptions),
                                                nameof(ApiBehaviorOptions.InvalidModelStateResponseFactory)));
            }

            _modelStateInvalidFilter = new ModelStateInvalidFilter(
                apiBehaviorOptions.Value,
                loggerFactory.CreateLogger <ModelStateInvalidFilter>());

            _clientErrorResultFilter = new ClientErrorResultFilter(
                clientErrorFactory,
                loggerFactory.CreateLogger <ClientErrorResultFilter>());
        }
Esempio n. 7
0
        public void OnProvidersExecuting_SkipsAddingFilterToActionIfFeatureIsDisabledUsingOptions()
        {
            // Arrange
            var context = GetContext(typeof(SimpleController));
            var options = new ApiBehaviorOptions
            {
                SuppressModelStateInvalidFilter = true,
            };

            var provider = GetProvider(options);

            // Act
            provider.OnProvidersExecuting(context);

            // Assert
            Assert.Collection(
                Assert.Single(context.Result.Controllers).Actions.OrderBy(a => a.ActionName),
                action =>
            {
                Assert.DoesNotContain(typeof(ModelStateInvalidFilter), action.Filters.Select(f => f.GetType()));
            },
                action =>
            {
                Assert.DoesNotContain(typeof(ModelStateInvalidFilter), action.Filters.Select(f => f.GetType()));
            });
        }
Esempio n. 8
0
        private static ApiBehaviorOptions GetOptions()
        {
            var apiBehaviorOptions = new ApiBehaviorOptions();

            apiBehaviorOptions.ClientErrorFactory[404] = _ => Result;
            return(apiBehaviorOptions);
        }
Esempio n. 9
0
        private static ClientErrorResultFilter GetFilter(ApiBehaviorOptions options = null)
        {
            var apiBehaviorOptions = options ?? GetOptions();
            var filter             = new ClientErrorResultFilter(apiBehaviorOptions, NullLogger <ClientErrorResultFilter> .Instance);

            return(filter);
        }
        private static ProblemDetailsFactory GetProblemDetails()
        {
            var options = new ApiBehaviorOptions();

            new ApiBehaviorOptionsSetup().Configure(options);
            return(new DefaultProblemDetailsFactory(Options.Create(options)));
        }
        public static void UseCustomInvalidModelUnprocessableEntityResponse(this ApiBehaviorOptions options)
        {
            options.InvalidModelStateResponseFactory = (actionContext) =>
            {
                ProblemDetailsFactory problemFactory = actionContext.HttpContext.RequestServices.GetRequiredService <ProblemDetailsFactory>();
                ProblemDetails        problemDetails = problemFactory.CreateValidationProblemDetails(actionContext.HttpContext, actionContext.ModelState);

                problemDetails.Instance = actionContext.HttpContext.Request.Path;
                problemDetails.Detail   = "See errors property for additional details.";

                var actionExecutingContext = actionContext as ActionExecutingContext;
                if (actionContext.ModelState.ErrorCount != 0 &&
                    (actionContext is ControllerContext || actionContext.ActionDescriptor.Parameters.Count == actionExecutingContext.ActionArguments.Count))
                {
                    problemDetails.Title    = "One or more validation errors occured.";
                    problemDetails.Status   = StatusCodes.Status422UnprocessableEntity;
                    problemDetails.Instance = $"{actionContext.HttpContext.Request.PathBase}/modelvalidationerror";

                    return(new UnprocessableEntityObjectResult(problemDetails)
                    {
                        ContentTypes = { "application/problem+json" }
                    });
                }

                problemDetails.Title  = "One or more errors occured on the input";
                problemDetails.Status = StatusCodes.Status400BadRequest;

                return(new BadRequestObjectResult(problemDetails)
                {
                    ContentTypes = { "application/problem+json" }
                });
            };
        }
        public void BlogApiBehavior_OK()
        {
            var target = new ApiBehaviorOptions();

            ConfigureApiBehavior.BlogApiBehavior(target);

            Assert.IsNotNull(target.InvalidModelStateResponseFactory);
        }
 public static void UseVirgoApiOptions(this ApiBehaviorOptions options)
 {
     options.SuppressModelStateInvalidFilter  = true;
     options.InvalidModelStateResponseFactory = (a) =>
     {
         return(new BadRequestObjectResult(a.ModelState.GetErrorJson()));
     };
 }
Esempio n. 14
0
 public ProblemDetailsSetup(
     IHostingEnvironment environment,
     IHttpContextAccessor httpContextAccessor,
     IOptions <ApiBehaviorOptions> apiOptions)
 {
     Environment         = environment;
     HttpContextAccessor = httpContextAccessor;
     ApiOptions          = apiOptions.Value;
 }
        private static void ConfigureApiBehaviorOptions(ApiBehaviorOptions options)
        {
            options.SuppressMapClientErrors         = true;
            options.SuppressModelStateInvalidFilter = false;
#if NETSTANDARD2_0
            options.SuppressUseValidationProblemDetailsForInvalidModelStateResponses = true;
#endif
            options.InvalidModelStateResponseFactory = (actionContext) => HandleInvalidModelStateResponse(actionContext);
        }
Esempio n. 16
0
        public static void ConfigureApiBehaviour(ApiBehaviorOptions apiBehaviorOptions)
        {
            apiBehaviorOptions.InvalidModelStateResponseFactory = context =>
            {
                var payload = Common.ProcessInvalidModelState(context.ModelState);

                return(new BadRequestObjectResult(payload));
            };
        }
        /// <summary>
        /// Instantiates a new <see cref="WebHookFilterProvider"/> instance with the given
        /// <paramref name="behaviorOptions"/> and <paramref name="loggerFactory"/>.
        /// </summary>
        /// <param name="behaviorOptions">The <see cref="ApiBehaviorOptions"/> accessor.</param>
        /// <param name="loggerFactory">The <see cref="ILoggerFactory"/>.</param>
        public WebHookFilterProvider(IOptions <ApiBehaviorOptions> behaviorOptions, ILoggerFactory loggerFactory)
        {
            _behaviorOptions = behaviorOptions.Value;
            _loggerFactory   = loggerFactory;

            var logger = loggerFactory.CreateLogger <ModelStateInvalidFilter>();

            _modelStateInvalidFilter = new ModelStateInvalidFilter(_behaviorOptions, logger);
        }
Esempio n. 18
0
 public static ApiBehaviorOptions UseFailureProblemDetailResponseFactory(this ApiBehaviorOptions options)
 {
     options.InvalidModelStateResponseFactory = context =>
     {
         var detail = FailureProblemDetail.FromHttpContext(context.HttpContext)
                      .WithFailures(context.ModelState.ToSerializable());
         return(new BadRequestObjectResult(detail));
     };
     return(options);
 }
Esempio n. 19
0
 public static void ControllerConfiguration(ApiBehaviorOptions options) =>
 options.InvalidModelStateResponseFactory = context =>
 {
     //var dict = context.ModelState;
     //var errors = new List<string>();
     //foreach (var key in dict.Keys)
     //    errors.AddRange(dict[key].Errors.Select(x => x.ErrorMessage));
     //return new BadRequestObjectResult(ApiResponse.ModelStateErrors(errors));
     return(new BadRequestObjectResult(context.ModelState));
 };
        public void Configure_AssignsInvalidModelStateResponseFactory()
        {
            // Arrange
            var optionsSetup = new ApiBehaviorOptionsSetup();
            var options      = new ApiBehaviorOptions();

            // Act
            optionsSetup.Configure(options);

            // Assert
            Assert.Same(ApiBehaviorOptionsSetup.DefaultFactory, options.InvalidModelStateResponseFactory);
        }
Esempio n. 21
0
    public ModelStateInvalidFilter(ApiBehaviorOptions apiBehaviorOptions, ILogger logger)
    {
        _apiBehaviorOptions = apiBehaviorOptions ?? throw new ArgumentNullException(nameof(apiBehaviorOptions));
        if (!_apiBehaviorOptions.SuppressModelStateInvalidFilter && _apiBehaviorOptions.InvalidModelStateResponseFactory == null)
        {
            throw new ArgumentException(Resources.FormatPropertyOfTypeCannotBeNull(
                                            typeof(ApiBehaviorOptions),
                                            nameof(ApiBehaviorOptions.InvalidModelStateResponseFactory)));
        }

        _logger = logger ?? throw new ArgumentNullException(nameof(logger));
    }
        //Needs to be after AddMvc or use ConfigureApiBehaviourOptions
        public static void ConfigureProblemDetailsInvalidModelStateFactory(this ApiBehaviorOptions options, ProblemDetailsInvalidModelStateFactoryOptions problemDetailsInvalidModelStateFactoryOptions)
        {
            //.Net Core 2.2
            //400
            //401
            //403
            //404
            //406
            //409
            //415
            //422

            //.Net Core 3.0
            //400
            //401
            //403
            //404
            //406
            //409
            //415
            //422
            //500

            options.ClientErrorMapping[StatusCodes.Status422UnprocessableEntity] = new ClientErrorData
            {
                Link  = "https://tools.ietf.org/html/rfc4918#section-11.2",
                Title = "One or more validation errors occurred.", //Unprocessable Entity
            };

            options.ClientErrorMapping[499] = new ClientErrorData
            {
                Link  = "about:blank",
                Title = "The request was cancelled.",
            };

            options.ClientErrorMapping[StatusCodes.Status500InternalServerError] = new ClientErrorData
            {
                Link  = "https://tools.ietf.org/html/rfc7231#section-6.6.1",
                Title = "An error occurred while processing your request.",
            };

            options.ClientErrorMapping[StatusCodes.Status504GatewayTimeout] = new ClientErrorData
            {
                Link  = "about:blank",
                Title = "The request timed out.",
            };

#if NETCOREAPP3_0
            options.InvalidModelStateResponseFactory = problemDetailsInvalidModelStateFactoryOptions.InvalidModelStateResponseAbstractFactory();
#else
            options.InvalidModelStateResponseFactory = problemDetailsInvalidModelStateFactoryOptions.InvalidModelStateResponseAbstractFactory(problemDetailsInvalidModelStateFactoryOptions.EnableAngularErrors);
#endif
        }
        public void PostConfigure_SetProblemDetailsModelStateResponseFactory()
        {
            // Arrange
            var optionsSetup = new ApiBehaviorOptionsSetup();
            var options      = new ApiBehaviorOptions();

            // Act
            optionsSetup.Configure(options);
            optionsSetup.PostConfigure(string.Empty, options);

            // Assert
            Assert.Same(ApiBehaviorOptionsSetup.ProblemDetailsFactory, options.InvalidModelStateResponseFactory);
        }
Esempio n. 24
0
 /// <summary>
 /// Adds the invalid model state exception.
 /// </summary>
 /// <param name="options">Options.</param>
 public static void UseInvalidModelStateException(this ApiBehaviorOptions options)
 {
     options.InvalidModelStateResponseFactory += (ActionContext arg) => {
         var state = arg.ModelState;
         var ie    = state as IEnumerable <KeyValuePair <string, ModelStateEntry> >;
         var sb    = new StringBuilder();
         foreach (var item in ie)
         {
             sb.Append($"{item.Key}:{item.Value.Errors[0].ErrorMessage};");
         }
         throw new ParameterException(sb.ToString());
     };
 }
Esempio n. 25
0
    public void Configure_AddsClientErrorMappings()
    {
        // Arrange
        var expected     = new[] { 400, 401, 403, 404, 405, 406, 409, 415, 422, 500, };
        var optionsSetup = new ApiBehaviorOptionsSetup();
        var options      = new ApiBehaviorOptions();

        // Act
        optionsSetup.Configure(options);

        // Assert
        Assert.Equal(expected, options.ClientErrorMapping.Keys);
    }
Esempio n. 26
0
        public static void UseInvalidModelStateToError(this ApiBehaviorOptions options)
        {
            options.InvalidModelStateResponseFactory = context =>
            {
                var errorsWithMessage = context.ModelState
                                        .Where(x => x.Value.ValidationState == ModelValidationState.Invalid).ToDictionary(
                    x => string.Join('.', x.Key.Split('.').Select(StringExtensions.ToCamelCase)),
                    x => x.Value.Errors.First().ErrorMessage);

                var fieldValidationError = new FieldValidationError(errorsWithMessage);
                return(new BadRequestObjectResult(fieldValidationError));
            };
        }
Esempio n. 27
0
    private static ProblemDetailsFactory GetProblemDetailsFactory(Action <ApiBehaviorOptions> configure = null)
    {
        var options = new ApiBehaviorOptions();
        var setup   = new ApiBehaviorOptionsSetup();

        setup.Configure(options);
        if (configure != null)
        {
            configure(options);
        }

        return(new DefaultProblemDetailsFactory(Options.Options.Create(options)));
    }
Esempio n. 28
0
        public static void CustomInvalidModelStateResponse(this ApiBehaviorOptions apiBehaviorOptions)
        {
            apiBehaviorOptions.InvalidModelStateResponseFactory = actionContext =>
            {
                OperationResult result = new OperationResult(false, new List <string>());

                foreach (var modelState in actionContext.ModelState)
                {
                    result.Messages.AddRange(modelState.Value.Errors.Select(error => error.ErrorMessage).ToList());
                }

                return(new BadRequestObjectResult(result));
            };
        }
Esempio n. 29
0
        public ApiBehaviorApplicationModelProvider(IOptions <ApiBehaviorOptions> apiBehaviorOptions, ILoggerFactory loggerFactory)
        {
            _apiBehaviorOptions = apiBehaviorOptions.Value;
            if (_apiBehaviorOptions.EnableModelStateInvalidFilter && _apiBehaviorOptions.InvalidModelStateResponseFactory == null)
            {
                throw new ArgumentException(Resources.FormatPropertyOfTypeCannotBeNull(
                                                typeof(ApiBehaviorOptions),
                                                nameof(ApiBehaviorOptions.InvalidModelStateResponseFactory)));
            }

            _modelStateInvalidFilter = new ModelStateInvalidFilter(
                apiBehaviorOptions.Value,
                loggerFactory.CreateLogger <ModelStateInvalidFilter>());
        }
        public void Configure_AssignsInvalidModelStateResponseFactory()
        {
            // Arrange
            var optionsSetup = new ApiBehaviorOptionsSetup(
                NullLoggerFactory.Instance,
                Options.Options.Create(new MvcCompatibilityOptions()));
            var options = new ApiBehaviorOptions();

            // Act
            optionsSetup.Configure(options);

            // Assert
            Assert.Same(ApiBehaviorOptionsSetup.DefaultFactory, options.InvalidModelStateResponseFactory);
        }