@@ -19,6 +19,7 @@ namespace Asp.Versioning.Conventions;
1919using Microsoft . OData . ModelBuilder ;
2020using Microsoft . OData . ModelBuilder . Config ;
2121using System . Reflection ;
22+ using Xunit ;
2223using static Microsoft . AspNetCore . Http . StatusCodes ;
2324using static Microsoft . AspNetCore . Mvc . ModelBinding . BindingSource ;
2425using static Microsoft . AspNetCore . OData . Query . AllowedArithmeticOperators ;
@@ -469,6 +470,50 @@ public void apply_to_should_use_model_bound_query_attributes()
469470 options => options . ExcludingMissingMembers ( ) ) ;
470471 }
471472
473+ [ Fact ]
474+ public void apply_should_override_model_bound_settings_with_enable_query_attribute ( )
475+ {
476+ // arrange
477+ var builder = new ODataConventionModelBuilder ( ) . EnableLowerCamelCase ( ) ;
478+
479+ builder . EntitySet < Customer > ( "Customers" ) ;
480+
481+ var validationSettings = new ODataValidationSettings ( )
482+ {
483+ AllowedQueryOptions = AllowedQueryOptions . None ,
484+ AllowedArithmeticOperators = AllowedArithmeticOperators . None ,
485+ AllowedLogicalOperators = AllowedLogicalOperators . None ,
486+ AllowedFunctions = AllowedFunctions . None ,
487+ } ;
488+ var settings = new TestODataQueryOptionSettings ( typeof ( Customer ) ) ;
489+ var convention = new ODataValidationSettingsConvention ( validationSettings , settings ) ;
490+ var model = builder . GetEdmModel ( ) ;
491+ var description = NewApiDescription ( typeof ( CustomersController ) , typeof ( IEnumerable < Customer > ) , model ) ;
492+
493+ // act
494+ convention . ApplyTo ( description ) ;
495+
496+ // assert
497+ var parameter = description . ParameterDescriptions . Single ( ) ;
498+
499+ parameter . Should ( ) . BeEquivalentTo (
500+ new
501+ {
502+ Name = "$filter" ,
503+ Source = Query ,
504+ Type = typeof ( string ) ,
505+ DefaultValue = default ( object ) ,
506+ IsRequired = false ,
507+ ModelMetadata = new { Description = "Test" } ,
508+ ParameterDescriptor = new
509+ {
510+ Name = "$filter" ,
511+ ParameterType = typeof ( string ) ,
512+ } ,
513+ } ,
514+ options => options . ExcludingMissingMembers ( ) ) ;
515+ }
516+
472517 [ Fact ]
473518 public void apply_to_should_process_odataX2Dlike_api_description ( )
474519 {
@@ -678,6 +723,13 @@ public class OrdersController : ODataController
678723 public IActionResult Get ( ODataQueryOptions < Order > options ) => Ok ( ) ;
679724 }
680725
726+ public class CustomersController : ODataController
727+ {
728+ [ EnableQuery ( AllowedQueryOptions = Filter ) ]
729+ [ ProducesResponseType ( typeof ( IEnumerable < Customer > ) , Status200OK ) ]
730+ public IActionResult Get ( ODataQueryOptions < Customer > options ) => Ok ( ) ;
731+ }
732+
681733 [ Select ]
682734 [ Filter ]
683735 [ Count ]
@@ -693,6 +745,12 @@ public class Order
693745 public int Quantity { get ; set ; }
694746 }
695747
748+ [ Page ( MaxTop = 25 , PageSize = 25 ) ]
749+ public class Customer
750+ {
751+ public int CustomerId { get ; set ; }
752+ }
753+
696754 private sealed class TestODataQueryOptionSettings : ODataQueryOptionSettings
697755 {
698756 internal TestODataQueryOptionSettings ( Type type , bool dollarPrefix = true ) :
0 commit comments