DDD layers and CQRSEndpoints and feature flags
No narration yet
Module 9 · Lesson 312 min

Endpoints and feature flags

Fusion uses minimal APIs: an endpoint is app.MapPost(route, async (body, useCase) => ...), with the use case injected straight into the handler. The handler is thin: validate input, call the use case, and map the Result to an HTTP status. It branches on the Result type (Module 5), guard-clauses first, happy path last (conventions E1, E2).

Guard-clause-first minimal API (real shape)
app.MapPost("/api/v1/flights/{key}:revertDecision",
    async (string key, RevertDisruptionDecision useCase) =>
    {
        var result = await useCase.Execute(new RevertDisruptionDecisionRequest(key));
        if (!result.IsSuccess)
        {
            return result.Errors[0] switch
            {
                EntityNotFound e => Results.NotFound(e.Message),
                DecisionNotFound e => Results.NotFound(e.Message),
                _ => Results.BadRequest(result.Errors),
            };
        }
        return Results.Ok(result.Value);   // happy path, last line
    });

New user-facing behaviour ships behind a feature flag (anti-pattern #29, convention FF1), because Fusion deploys trunk-based and every merge reaches the shared environment. The backend calls await _featureClient.GetBooleanValueAsync("FUS-{ticket}-{slug}", false, cancellationToken: cancellationToken); the flag defaults OFF so an unconfigured environment does not accidentally expose an unfinished feature, and each environment turns it ON explicitly once approved (dev on, test/prod off until the PM signs off). The key format is FUS-{ticket}-{slug} in kebab-case.

Practice

Try it yourself

Do

Read an endpoint's guard-first flow

Confirm the shape: validate, call, map by type, ok last.

Tick every step to confirm you did it.