Skip to content

Commit b4efb54

Browse files
committed
fix multiple parameters
1 parent 4b53481 commit b4efb54

File tree

2 files changed

+32
-2
lines changed

2 files changed

+32
-2
lines changed

pkgs/shelf_router/lib/src/router_entry.dart

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -71,19 +71,24 @@ class RouterEntry {
7171

7272
final params = <ParamInfo>[];
7373
var pattern = '';
74+
// Keep the index where the matches are located
75+
// so that we can calculate the positioning of
76+
// the extracted parameter
77+
var prevMatchIndex = 0;
7478
for (var m in _parser.allMatches(route)) {
7579
final firstGroup = m[1]!;
7680
pattern += RegExp.escape(firstGroup);
7781
if (m[2] != null) {
7882
final paramName = m[2]!;
79-
final startIdx = firstGroup.length;
80-
//final endIdx = startIdx + paramName.length;
83+
final startIdx = prevMatchIndex + firstGroup.length;
8184
final paramInfo = ParamInfo(
8285
name: paramName,
8386
startIdx: startIdx,
8487
endIdx: m.end,
8588
);
8689
params.add(paramInfo);
90+
prevMatchIndex = m.end;
91+
8792
if (m[3] != null && !_isNoCapture(m[3]!)) {
8893
throw ArgumentError.value(
8994
route, 'route', 'expression for "${m[2]}" is capturing');
@@ -139,9 +144,20 @@ class RouterEntry {
139144
}
140145
}
141146

147+
/// This class holds information about a parameter extracted
148+
/// from the route path.
149+
/// The indexes can by used by the mount logic to resolve the
150+
/// parametrized path when handling the request.
142151
class ParamInfo {
152+
/// This is the name of the parameter, without <, >
143153
final String name;
154+
155+
/// The index in the route String where the parameter
156+
/// expression starts (inclusive)
144157
final int startIdx;
158+
159+
/// The index in the route String where the parameter
160+
/// expression ends (exclusive)
145161
final int endIdx;
146162

147163
const ParamInfo({

pkgs/shelf_router/test/router_test.dart

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -260,6 +260,20 @@ void main() {
260260
expect(await get('/users/david/no-route'), 'catch-all-handler');
261261
});
262262

263+
test('can mount dynamic routes with multiple parameters', () async {
264+
var app = Router();
265+
app.mount(r'/first/<second>/third/<fourth>/last',
266+
(Request request, String second, String fourth) {
267+
var router = Router();
268+
router.get('/', (r) => Response.ok('$second $fourth'));
269+
return router(request);
270+
});
271+
272+
server.mount(app);
273+
274+
expect(await get('/first/hello/third/bye/last'), 'hello bye');
275+
});
276+
263277
test('can mount dynamic routes with regexp', () async {
264278
var app = Router();
265279

0 commit comments

Comments
 (0)