VeryGoodOpenSource / dart_frog

A fast, minimalistic backend framework for Dart 🎯
https://dartfrog.vgv.dev
MIT License
1.87k stars 150 forks source link

feat: Allow routing parameters in `middleware` #773

Open rubenferreira97 opened 1 year ago

rubenferreira97 commented 1 year ago

Description Currently is not possible to access routing parameters on middlewares. Would be nice in cases where we have nested routing parameters and have different logic dependent on that parameter (e.g. /[userId]/tasks/[taskId], middleware on /[userId]/_middleware.dart that checks if we have permissions for that [userId) .

My current workaround relies on private implementations 😕:

Middleware /[test]/_middleware.dart:

import 'package:dart_frog/dart_frog.dart';
import 'package:dart_frog/src/_internal.dart' show toShelfHandler;

Handler middleware(Handler handler /* String test */) { // `String test` does not work
  return fromShelfHandler((request) async {
    print((request.context['shelf_router/params'] as Map<String, String>?)?['test']);
    return toShelfHandler(handler)(request);
  });
}

Index /[test]/index.dart:

Future<Response> onRequest(RequestContext context, String test) async {
  return Response(body: '$test');
}
felangel commented 1 year ago

Hi @rubenferreira97 👋 This is already possible:


Handler middleware(Handler handler) {
  return (context) {
    final request = context.request;
    // Do something with the request
    return handler(context);
  };
}
rubenferreira97 commented 1 year ago

@felangel Thanks for you answer!

Sorry if I am missing something but first I guess you meant context.request instead of request.context, second neither request or context expose routing params as far as I know.

Middleware /[test]/_middleware.dart:

Handler middleware(Handler handler) {
  return (context) {
    final request = context.request;
    print(request['test']); // does not work
    print(context['test']); // does not work
    // Do something with the request
    return handler(context);
  };
}

In a ideal scenario I would like to access the variable in a typesafe manner via the middleware params, however I don't know if this is possible. I imagine middlewares are different from requests.

Handler middleware(Handler handler, String test) {
  return (context /*, test */) { // or here?
    print(test);
    return handler(context);
  };
}
niklasbartsch commented 1 year ago

You can do the following:

Handler middleware(Handler handler) {
  return (context) {
        final uri = context.request.uri;

        if (uri.pathSegments.contains('test')) {
          return Response(body: 'OK');
        }
        return handler(context);
      };
}
rubenferreira97 commented 1 year ago

@niklasbartsch In that example I can't access the variable value.