Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow for multiple parameters on an endpoint #199

Open
rikrak opened this issue Aug 8, 2023 · 1 comment
Open

Allow for multiple parameters on an endpoint #199

rikrak opened this issue Aug 8, 2023 · 1 comment

Comments

@rikrak
Copy link

rikrak commented Aug 8, 2023

Not sure if this is currently possible, but I've been trying to create a POST endpoint where part of the parameters come from the route. I can't get it to work with a single request parameter as the entire class is bound to the requets body.

For example, I'd like to be able to support scenarios like:

    [Route("/Country/{id}/Rename")]
    [HttpPost]
    public override async Task<ActionResult> HandleAsync(CountryIdentifier id, CountryRenameRequest request, CancellationToken cancellationToken = new CancellationToken())
    {
    }

This doen't seem to be currently possible if I use the EndpointBasAsync.WithRequest<T>.WithResponse mechanism for declaring the endpoint.

I've worked around it by re-creating the EndpointBaseAsync structure and adapting it. Is this an appropriate thing to do, or is there a better way to achieve the same thing?

    public static class EndpointAsync
    {
         public static class WithRequest<TParam, TRequest>
        {
            public abstract class WithResult<TResponse> : EndpointBase
            {
                public abstract Task<TResponse> HandleAsync(
                    TParam param,
                    TRequest request,
                    CancellationToken cancellationToken = default(CancellationToken)
                    );
            }

            public abstract class WithoutResult : EndpointBase
            {
                public abstract Task HandleAsync(
                    TParam param, 
                    TRequest request, 
                    CancellationToken cancellationToken = default(CancellationToken));
            }

            public abstract class WithActionResult<TResponse> : EndpointBase
            {
                public abstract Task<ActionResult<TResponse>> HandleAsync(
                    TParam param,
                    TRequest request,
                    CancellationToken cancellationToken = default(CancellationToken));
            }

            public abstract class WithActionResult : EndpointBase
            {
                public abstract Task<ActionResult> HandleAsync(
                    TParam param,
                    TRequest request,
                    CancellationToken cancellationToken = default(CancellationToken));
            }

            public abstract class WithAsyncEnumerableResult<T> : EndpointBase
            {
                public abstract IAsyncEnumerable<T> HandleAsync(
                    TParam param,
                    TRequest request,
                    CancellationToken cancellationToken = default(CancellationToken));
            }
        }
        // ... other code (truncated for clarity)
}

happy to submit a PR for this sort of thing :-)

@rikrak
Copy link
Author

rikrak commented Aug 8, 2023

Actually, having just reviewed this again in my codebase, I'm not sure I like the idea of multiple parameters. It makes the route intuitive, but it marginally complicates the construction of the command.

    public override async Task<ActionResult> HandleAsync(CountryIdentifier id, CountryRenameRequest request, CancellationToken cancellationToken = new CancellationToken())
    {
        var cmd = _mapper.Map<CountryRenameCommand>(request);
        cmd = cmd with {Id = id};
        RunCommand(cmd);
        // ...
    }

instead of

    public override async Task<ActionResult> HandleAsync(CountryRenameRequest request, CancellationToken cancellationToken = new CancellationToken())
    {
        var cmd = _mapper.Map<CountryRenameCommand>(request);
        RunCommand(cmd);
        // ...
    }

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant