ServiceComposer.AspNetCore

Custom HTTP status codes

The response status code can be set in composition handlers and it will be honored by the composition pipeline. To set a custom response status code the following snippet can be used:

public class SampleHandlerWithCustomStatusCode : ICompositionRequestsHandler
{
    [HttpGet("/sample/{id}")]
    public Task Handle(HttpRequest request)
    {
        var response = request.HttpContext.Response;
        response.StatusCode = (int)HttpStatusCode.Forbidden;

        return Task.CompletedTask;
    }
}

snippet source | anchor

[!WARNING] Composition handlers execute in parallel in a non-deterministic order. If more than one handler sets the response status code, the final code written to the response is unpredictable. Only one handler in a composition group should set the status code.

For error scenarios (validation failures, not found, forbidden), prefer using MVC Action results via request.SetActionResult(result). Action results are designed for exactly this case — ServiceComposer guarantees only the first handler to call SetActionResult takes effect, making the behavior deterministic:

public class SampleHandler : ICompositionRequestsHandler
{
    [HttpGet("/sample/{id}")]
    public Task Handle(HttpRequest request)
    {
        if (!IsValid(request))
        {
            request.SetActionResult(new BadRequestResult());
            return Task.CompletedTask;
        }

        var vm = request.GetComposedResponseModel();
        vm.Data = "...";
        return Task.CompletedTask;
    }

    bool IsValid(HttpRequest request) => request.RouteValues["id"] != null;
}

snippet source | anchor

Setting a status code directly on HttpContext.Response is appropriate only when a handler is the sole authority on the response code for its route, or when using a non-MVC endpoint where action results are not available.