@@ -21,11 +21,29 @@ public static class CqrsRouteMapper
2121
2222 private static readonly string [ ] GetAndHeadMethods = { "GET" , "HEAD" } ;
2323
24- private static readonly List < string > PostCommandPrefixes = new ( ) { "Create" , "Add" , "New" } ;
24+ private static readonly List < string > PostCommandPrefixes = new ( )
25+ {
26+ "Create" ,
27+ "Add" ,
28+ "New"
29+ } ;
2530
26- private static readonly List < string > PutCommandPrefixes = new ( ) { "Update" , "Modify" , "Replace" , "Alter" } ;
31+ private static readonly List < string > PutCommandPrefixes = new ( )
32+ {
33+ "Update" ,
34+ "Modify" ,
35+ "Replace" ,
36+ "Alter"
37+ } ;
2738
28- private static readonly List < string > DeleteCommandPrefixes = new ( ) { "Delete" , "Remove" , "Clean" , "Clear" , "Purge" } ;
39+ private static readonly List < string > DeleteCommandPrefixes = new ( )
40+ {
41+ "Delete" ,
42+ "Remove" ,
43+ "Clean" ,
44+ "Clear" ,
45+ "Purge"
46+ } ;
2947
3048 /// <summary>
3149 /// Map a query API, using GET method. <typeparamref name="T"/> would been constructed from route and query string.
@@ -96,14 +114,7 @@ public static IEndpointConventionBuilder MapQuery(
96114 string nullRouteParameterPattern = "-" ,
97115 bool enableHead = false )
98116 {
99- var isQuery = handler . Method . ReturnType . GetInterfaces ( ) . Where ( x => x . IsGenericType )
100- . Any ( x => QueryTypes . Contains ( x . GetGenericTypeDefinition ( ) ) ) ;
101- if ( isQuery == false )
102- {
103- throw new ArgumentException (
104- "delegate does not return a query, please make sure it returns object that implement IQuery<> or IListQuery<> or interface that inherit from them" ) ;
105- }
106-
117+ var returnType = EnsureReturnTypeIsQuery ( handler ) ;
107118 if ( mapNullableRouteParameters is MapNullableRouteParameter . Disable )
108119 {
109120 return MapRoutes ( route ) ;
@@ -118,7 +129,7 @@ public static IEndpointConventionBuilder MapQuery(
118129
119130 var parsedRoute = RoutePatternFactory . Parse ( route ) ;
120131 var context = new NullabilityInfoContext ( ) ;
121- var nullableRouteProperties = handler . Method . ReturnType . GetProperties ( )
132+ var nullableRouteProperties = returnType . GetProperties ( )
122133 . Where (
123134 p => p . GetMethod != null
124135 && p . SetMethod != null
@@ -209,8 +220,7 @@ public static IEndpointConventionBuilder MapCommand(
209220 [ StringSyntax ( "Route" ) ] string route ,
210221 Delegate handler )
211222 {
212- EnsureDelegateReturnTypeIsCommand ( handler ) ;
213- var commandTypeName = handler . Method . ReturnType . Name ;
223+ var commandTypeName = EnsureReturnTypeIsCommand ( handler ) . Name ;
214224 if ( PostCommandPrefixes . Any ( x => commandTypeName . StartsWith ( x ) ) )
215225 {
216226 return app . MapPostCommand ( route , handler ) ;
@@ -255,7 +265,7 @@ public static IEndpointConventionBuilder MapPostCommand(
255265 [ StringSyntax ( "Route" ) ] string route ,
256266 Delegate handler )
257267 {
258- EnsureDelegateReturnTypeIsCommand ( handler ) ;
268+ EnsureReturnTypeIsCommand ( handler ) ;
259269 return app . MapPost ( route , handler ) . AddEndpointFilter < CommandEndpointHandler > ( ) ;
260270 }
261271
@@ -285,7 +295,7 @@ public static IEndpointConventionBuilder MapPutCommand(
285295 [ StringSyntax ( "Route" ) ] string route ,
286296 Delegate handler )
287297 {
288- EnsureDelegateReturnTypeIsCommand ( handler ) ;
298+ EnsureReturnTypeIsCommand ( handler ) ;
289299 return app . MapPut ( route , handler ) . AddEndpointFilter < CommandEndpointHandler > ( ) ;
290300 }
291301
@@ -315,7 +325,7 @@ public static IEndpointConventionBuilder MapDeleteCommand(
315325 [ StringSyntax ( "Route" ) ] string route ,
316326 Delegate handler )
317327 {
318- EnsureDelegateReturnTypeIsCommand ( handler ) ;
328+ EnsureReturnTypeIsCommand ( handler ) ;
319329 return app . MapDelete ( route , handler ) . AddEndpointFilter < CommandEndpointHandler > ( ) ;
320330 }
321331
@@ -385,15 +395,42 @@ public static IEndpointRouteBuilder StopMappingPrefixToDelete(this IEndpointRout
385395 return app ;
386396 }
387397
388- private static void EnsureDelegateReturnTypeIsCommand ( Delegate handler )
398+ private static Type EnsureReturnTypeIsCommand ( Delegate handler )
389399 {
390- var isCommand = handler . Method . ReturnType . GetInterfaces ( ) . Where ( x => x . IsGenericType )
400+ var returnType = handler . Method . ReturnType ;
401+ if ( returnType . IsGenericType && returnType . GetGenericTypeDefinition ( ) == typeof ( Task < > ) )
402+ {
403+ returnType = returnType . GenericTypeArguments . First ( ) ;
404+ }
405+
406+ var isCommand = returnType . GetInterfaces ( ) . Where ( x => x . IsGenericType )
391407 . Any ( x => CommandTypes . Contains ( x . GetGenericTypeDefinition ( ) ) ) ;
392408 if ( isCommand == false )
393409 {
394410 throw new ArgumentException (
395411 "handler does not return command, check if delegate returns type that implements ICommand<> or ICommand<,>" ) ;
396412 }
413+
414+ return returnType ;
415+ }
416+
417+ private static Type EnsureReturnTypeIsQuery ( Delegate handler )
418+ {
419+ var returnType = handler . Method . ReturnType ;
420+ if ( returnType . IsGenericType && returnType . GetGenericTypeDefinition ( ) == typeof ( Task < > ) )
421+ {
422+ returnType = returnType . GenericTypeArguments . First ( ) ;
423+ }
424+
425+ var isCommand = returnType . GetInterfaces ( ) . Where ( x => x . IsGenericType )
426+ . Any ( x => QueryTypes . Contains ( x . GetGenericTypeDefinition ( ) ) ) ;
427+ if ( isCommand == false )
428+ {
429+ throw new ArgumentException (
430+ "handler does not return query, check if delegate returns type that implements IQuery<>" ) ;
431+ }
432+
433+ return returnType ;
397434 }
398435
399436 private static List < T [ ] > GetNotEmptySubsets < T > ( ICollection < T > items )
0 commit comments