Skip to content

Commit 0dc7e5d

Browse files
committed
Add tenant parameter BEFORE existing prefixes by default, add tenantParameterBeforePrefix() to allow customizing this
1 parent ecc3374 commit 0dc7e5d

File tree

2 files changed

+39
-13
lines changed

2 files changed

+39
-13
lines changed

src/Actions/CloneRoutesAsTenant.php

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,7 @@ class CloneRoutesAsTenant
8686
{
8787
protected array $routesToClone = [];
8888
protected bool $addTenantParameter = true;
89+
protected bool $tenantParameterBeforePrefix = true;
8990
protected string|null $domain = null;
9091
protected Closure|null $cloneUsing = null; // The callback should accept Route instance or the route name (string)
9192
protected Closure|null $shouldClone = null;
@@ -177,6 +178,13 @@ public function shouldClone(Closure|null $shouldClone): static
177178
return $this;
178179
}
179180

181+
public function tenantParameterBeforePrefix(bool $tenantParameterBeforePrefix): static
182+
{
183+
$this->tenantParameterBeforePrefix = $tenantParameterBeforePrefix;
184+
185+
return $this;
186+
}
187+
180188
/** Clone an individual route. */
181189
public function cloneRoute(Route|string $route): static
182190
{
@@ -226,7 +234,13 @@ protected function createNewRoute(Route $route): Route
226234
$action->put('middleware', $middleware);
227235

228236
if ($this->addTenantParameter) {
229-
$action->put('prefix', $prefix . '/{' . PathTenantResolver::tenantParameterName() . '}');
237+
$tenantParameter = '{' . PathTenantResolver::tenantParameterName() . '}';
238+
239+
$newPrefix = $this->tenantParameterBeforePrefix
240+
? $tenantParameter . '/' . $prefix
241+
: $prefix . '/' . $tenantParameter;
242+
243+
$action->put('prefix', $newPrefix);
230244
}
231245

232246
/** @var Route $newRoute */

tests/CloneActionTest.php

Lines changed: 24 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -172,7 +172,7 @@
172172
false,
173173
]);
174174

175-
test('the clone action prefixes already prefixed routes correctly', function () {
175+
test('the clone action prefixes already prefixed routes correctly', function (bool $tenantParameterBeforePrefix) {
176176
$routes = [
177177
RouteFacade::get('/home', fn () => true)
178178
->middleware(['clone'])
@@ -195,7 +195,12 @@
195195
->prefix('prefix/'),
196196
];
197197

198-
app(CloneRoutesAsTenant::class)->handle();
198+
$cloneAction = app(CloneRoutesAsTenant::class);
199+
$cloneAction
200+
->tenantParameterBeforePrefix($tenantParameterBeforePrefix)
201+
->handle();
202+
203+
$expectedPrefix = $tenantParameterBeforePrefix ? '{tenant}/prefix' : 'prefix/{tenant}';
199204

200205
$clonedRoutes = [
201206
RouteFacade::getRoutes()->getByName('tenant.home'),
@@ -206,24 +211,25 @@
206211

207212
// The cloned route is prefixed correctly
208213
foreach ($clonedRoutes as $key => $route) {
209-
expect($route->getPrefix())->toBe("prefix/{tenant}");
214+
expect($route->getPrefix())->toBe($expectedPrefix);
210215

211216
$clonedRouteUrl = route($route->getName(), ['tenant' => $tenant = Tenant::create()]);
217+
$expectedPrefixInUrl = $tenantParameterBeforePrefix ? "{$tenant->id}/prefix" : "prefix/{$tenant->id}";
212218

213219
expect($clonedRouteUrl)
214220
// Original prefix does not occur in the cloned route's URL
215221
->not()->toContain("prefix/{$tenant->id}/prefix")
216222
->not()->toContain("//prefix")
217223
->not()->toContain("prefix//")
218224
// Instead, the route is prefixed correctly
219-
->toBe("http://localhost/prefix/{$tenant->id}/{$routes[$key]->getName()}");
225+
->toBe("http://localhost/{$expectedPrefixInUrl}/{$routes[$key]->getName()}");
220226

221227
// The cloned route is accessible
222228
pest()->get($clonedRouteUrl)->assertOk();
223229
}
224-
});
230+
})->with([true, false]);
225231

226-
test('clone action trims trailing slashes from prefixes given to nested route groups', function () {
232+
test('clone action trims trailing slashes from prefixes given to nested route groups', function (bool $tenantParameterBeforePrefix) {
227233
RouteFacade::prefix('prefix')->group(function () {
228234
RouteFacade::prefix('')->group(function () {
229235
// This issue seems to only happen when there's a group with a prefix, then a group with an empty prefix, and then a / route
@@ -237,25 +243,31 @@
237243
});
238244
});
239245

240-
app(CloneRoutesAsTenant::class)->handle();
246+
$cloneAction = app(CloneRoutesAsTenant::class);
247+
$cloneAction
248+
->tenantParameterBeforePrefix($tenantParameterBeforePrefix)
249+
->handle();
241250

242251
$clonedLandingUrl = route('tenant.landing', ['tenant' => $tenant = Tenant::create()]);
243252
$clonedHomeRouteUrl = route('tenant.home', ['tenant' => $tenant]);
244253

245254
$landingRoute = RouteFacade::getRoutes()->getByName('tenant.landing');
246255
$homeRoute = RouteFacade::getRoutes()->getByName('tenant.home');
247256

248-
expect($landingRoute->uri())->toBe('prefix/{tenant}');
249-
expect($homeRoute->uri())->toBe('prefix/{tenant}/home');
257+
$expectedPrefix = $tenantParameterBeforePrefix ? '{tenant}/prefix' : 'prefix/{tenant}';
258+
$expectedPrefixInUrl = $tenantParameterBeforePrefix ? "{$tenant->id}/prefix" : "prefix/{$tenant->id}";
259+
260+
expect($landingRoute->uri())->toBe($expectedPrefix);
261+
expect($homeRoute->uri())->toBe("{$expectedPrefix}/home");
250262

251263
expect($clonedLandingUrl)
252264
->not()->toContain("prefix//")
253-
->toBe("http://localhost/prefix/{$tenant->id}");
265+
->toBe("http://localhost/{$expectedPrefixInUrl}");
254266

255267
expect($clonedHomeRouteUrl)
256268
->not()->toContain("prefix//")
257-
->toBe("http://localhost/prefix/{$tenant->id}/home");
258-
});
269+
->toBe("http://localhost/{$expectedPrefixInUrl}/home");
270+
})->with([true, false]);
259271

260272
test('tenant routes are ignored from cloning and clone middleware in groups causes no issues', function () {
261273
// Should NOT be cloned, already has tenant parameter

0 commit comments

Comments
 (0)