Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Routing Patterns

This section covers patterns for using feature flags to control route access and availability in your application.

Enabling routes

Feature flags are commonly used to enable or disable routes in your application. Instead of calling variation manually, you can encapsulate this pattern in decorators.

The following examples show route enabling implementations:

Python/Flask

Flask decorators allow you to wrap route handlers with additional logic. You can create a @require_flag decorator that evaluates a feature flag before allowing the route to execute. If the flag evaluates to the expected value, the request continues. Otherwise, it returns an error response.

Here is an example:

# See https://github.com/smohdarif/flask-ld-web-and-api/blob/main/launchdarkly/decorators.py#L18
@api_bp.get("/beta/experimental")
@require_flag("enable-experimental-api", default=False)
def experimental_feature():
    return jsonify({
        "message": "Welcome to the experimental API!",
        "status": "beta",
        "features": ["feature-1", "feature-2", "feature-3"]
    })

Express/Node.js

Express middleware functions can intercept requests before they reach route handlers. You can create a middleware factory that evaluates feature flags and either calls next() to continue or sends an error response. This middleware can also handle redirects for disabled routes.

Here is an example:

function requireFlag(flagKey, default=false, expectedValue=true, redirect_url) {
  return async (req, res, next) => {
    // implement context management to inject the context into the request
    const context = req.LD_CONTEXT
    const flag = await client.variation(flagKey, context, default);
    if (flag === expectedValue) {
      next();
    } else {
      if (redirect_url) {
        res.redirect(redirect_url);
      } else {
        res.status(404)
      }
    }
  };
}