mirror of
https://github.com/archtechx/tenancy.git
synced 2025-12-12 11:14:04 +00:00
Update path identification and Fortify integration-related logic (#13)
* Add commented UrlBinding + FortifyRouteTenancy bootstrappers to the config * Improve FortifyRoute bootstrapper docblock * Rename bootstrappers * Complete renaming * Pass defaults of the original URL generator to the new one * Fix URL generator-related test (query string id test WIP) * Fix code style (php-cs-fixer) * Make Fortify bootstrapper not depend on the UrlGenerator bootstrapper, update comments * Fix testing UrlGenerator bootstrapper * Update TenancyUrlGenerator annotations * Pass tenant parameter manually in Fortify bootstrapper * Properly test TenancyUrlGenerator functionality * Get rid of query string in Fortify bootstrapper * Fix code style (php-cs-fixer) * Delete outdated comment * Improve comment * Improve before/afterEach * Encourage passing parameters using TenancyUrlGenerator instead of URL::defaults() * Delete rest of defaulting logic * Fix code style (php-cs-fixer) * Delete test group * Update ForgetTenantParameter docblock * Update passTenantParameterToRoutes annotation * Complete todo in test * Improve test * Update comment * Improve comment * Add keepQueryParameters bool to Fortify bootstrapper * Test keepQueryParameters * minor docblock update * minor docblock changes * Delete extra import * Update src/Overrides/TenancyUrlGenerator.php Co-authored-by: Samuel Štancl <samuel.stancl@gmail.com> * Improve comment * Rename test * Update bypass parameter-related test comments * Fix merge * Rename $keepQueryParameters * Add docblock * Add comment * Refactor Fortify bootstrapper * Fix code style (php-cs-fixer) * Fix comment * Skip Fortify bootstrapper test * minor code improvements * Improve fortify bootstrapper test * Add Fortify bootstrapper annotation, improve code * Fix code style (php-cs-fixer) * Add commenet * Complete resource syncing todo (cleanup not needed) * Delete incorrect namespace * Complete route context trait name todo * Fix code style (php-cs-fixer) --------- Co-authored-by: PHP CS Fixer <phpcsfixer@example.com> Co-authored-by: Samuel Štancl <samuel.stancl@gmail.com>
This commit is contained in:
parent
c043661318
commit
4953c69fd8
16 changed files with 255 additions and 141 deletions
|
|
@ -3,10 +3,10 @@
|
|||
declare(strict_types=1);
|
||||
|
||||
use Illuminate\Support\Str;
|
||||
use Stancl\Tenancy\Enums\Context;
|
||||
use Illuminate\Support\Facades\DB;
|
||||
use Illuminate\Support\Facades\URL;
|
||||
use Stancl\JobPipeline\JobPipeline;
|
||||
use Illuminate\Broadcasting\Channel;
|
||||
use Illuminate\Support\Facades\File;
|
||||
use Stancl\Tenancy\Tests\Etc\Tenant;
|
||||
use Illuminate\Support\Facades\Cache;
|
||||
|
|
@ -20,9 +20,7 @@ use Stancl\Tenancy\Jobs\CreateDatabase;
|
|||
use Stancl\Tenancy\Events\TenantCreated;
|
||||
use Stancl\Tenancy\Events\TenantDeleted;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Support\Facades\Broadcast;
|
||||
use Stancl\Tenancy\Events\DeletingTenant;
|
||||
use Illuminate\Broadcasting\PrivateChannel;
|
||||
use Illuminate\Filesystem\FilesystemAdapter;
|
||||
use Illuminate\Broadcasting\BroadcastManager;
|
||||
use Stancl\Tenancy\Events\TenancyInitialized;
|
||||
|
|
@ -30,25 +28,26 @@ use Illuminate\Contracts\Routing\UrlGenerator;
|
|||
use Stancl\Tenancy\Jobs\CreateStorageSymlinks;
|
||||
use Stancl\Tenancy\Jobs\RemoveStorageSymlinks;
|
||||
use Stancl\Tenancy\Listeners\BootstrapTenancy;
|
||||
use Stancl\Tenancy\Resolvers\PathTenantResolver;
|
||||
use Stancl\Tenancy\Tests\Etc\TestingBroadcaster;
|
||||
use Stancl\Tenancy\Listeners\DeleteTenantStorage;
|
||||
use Stancl\Tenancy\Overrides\TenancyUrlGenerator;
|
||||
use Stancl\Tenancy\Listeners\RevertToCentralContext;
|
||||
use Stancl\Tenancy\Bootstrappers\RootUrlBootstrapper;
|
||||
use Stancl\Tenancy\Overrides\TenancyBroadcastManager;
|
||||
use Illuminate\Contracts\Broadcasting\ShouldBroadcast;
|
||||
use Stancl\Tenancy\Middleware\InitializeTenancyByPath;
|
||||
use Stancl\Tenancy\Bootstrappers\CacheTagsBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\UrlBindingBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\UrlTenancyBootstrapper;
|
||||
use Illuminate\Routing\Exceptions\UrlGenerationException;
|
||||
use Stancl\Tenancy\Bootstrappers\MailTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\RedisTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\UrlGeneratorBootstrapper;
|
||||
use Stancl\Tenancy\Middleware\InitializeTenancyBySubdomain;
|
||||
use Stancl\Tenancy\Bootstrappers\DatabaseTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Middleware\InitializeTenancyByRequestData;
|
||||
use Stancl\Tenancy\Bootstrappers\BroadcastChannelPrefixBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\FilesystemTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\BroadcastingConfigBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\PrefixCacheTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\BroadcastChannelPrefixBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\Integrations\FortifyRouteTenancyBootstrapper;
|
||||
|
||||
beforeEach(function () {
|
||||
|
|
@ -59,7 +58,7 @@ beforeEach(function () {
|
|||
// Reset static properties of classes used in this test file to their default values
|
||||
BroadcastingConfigBootstrapper::$credentialsMap = [];
|
||||
TenancyBroadcastManager::$tenantBroadcasters = ['pusher', 'ably'];
|
||||
UrlTenancyBootstrapper::$rootUrlOverride = null;
|
||||
RootUrlBootstrapper::$rootUrlOverride = null;
|
||||
|
||||
Event::listen(
|
||||
TenantCreated::class,
|
||||
|
|
@ -74,11 +73,12 @@ beforeEach(function () {
|
|||
|
||||
afterEach(function () {
|
||||
// Reset static properties of classes used in this test file to their default values
|
||||
UrlTenancyBootstrapper::$rootUrlOverride = null;
|
||||
RootUrlBootstrapper::$rootUrlOverride = null;
|
||||
PrefixCacheTenancyBootstrapper::$tenantCacheStores = [];
|
||||
TenancyBroadcastManager::$tenantBroadcasters = ['pusher', 'ably'];
|
||||
BroadcastingConfigBootstrapper::$credentialsMap = [];
|
||||
TenancyUrlGenerator::$prefixRouteNames = false;
|
||||
TenancyUrlGenerator::$passTenantParameterToRoutes = true;
|
||||
});
|
||||
|
||||
test('database data is separated', function () {
|
||||
|
|
@ -501,7 +501,7 @@ test('MailTenancyBootstrapper reverts the config and mailer credentials to defau
|
|||
});
|
||||
|
||||
test('url bootstrapper overrides the root url when tenancy gets initialized and reverts the url to the central one after tenancy ends', function() {
|
||||
config(['tenancy.bootstrappers' => [UrlTenancyBootstrapper::class]]);
|
||||
config(['tenancy.bootstrappers' => [RootUrlBootstrapper::class]]);
|
||||
|
||||
Route::group([
|
||||
'middleware' => InitializeTenancyBySubdomain::class,
|
||||
|
|
@ -521,7 +521,7 @@ test('url bootstrapper overrides the root url when tenancy gets initialized and
|
|||
return $scheme . '://' . $tenant->getTenantKey() . '.' . $hostname;
|
||||
};
|
||||
|
||||
UrlTenancyBootstrapper::$rootUrlOverride = $rootUrlOverride;
|
||||
RootUrlBootstrapper::$rootUrlOverride = $rootUrlOverride;
|
||||
|
||||
$tenant = Tenant::create();
|
||||
$tenantUrl = $rootUrlOverride($tenant);
|
||||
|
|
@ -546,36 +546,43 @@ test('url bootstrapper overrides the root url when tenancy gets initialized and
|
|||
});
|
||||
|
||||
test('url binding tenancy bootstrapper swaps the url generator instance correctly', function() {
|
||||
config(['tenancy.bootstrappers' => [UrlBindingBootstrapper::class]]);
|
||||
config(['tenancy.bootstrappers' => [UrlGeneratorBootstrapper::class]]);
|
||||
|
||||
tenancy()->initialize(Tenant::create());
|
||||
expect(app('url'))->toBeInstanceOf(TenancyUrlGenerator::class);
|
||||
expect(url())->toBeInstanceOf(TenancyUrlGenerator::class);
|
||||
|
||||
tenancy()->end();
|
||||
expect(app('url'))->toBeInstanceOf(UrlGenerator::class);
|
||||
expect(url())->toBeInstanceOf(UrlGenerator::class);
|
||||
expect(app('url'))->toBeInstanceOf(UrlGenerator::class)
|
||||
->not()->toBeInstanceOf(TenancyUrlGenerator::class);
|
||||
expect(url())->toBeInstanceOf(UrlGenerator::class)
|
||||
->not()->toBeInstanceOf(TenancyUrlGenerator::class);
|
||||
});
|
||||
|
||||
test('url binding tenancy bootstrapper changes route helper behavior correctly', function() {
|
||||
test('url generator bootstrapper can prefix route names passed to the route helper', function() {
|
||||
Route::get('/central/home', fn () => route('home'))->name('home');
|
||||
// Tenant route name prefix is 'tenant.' by default
|
||||
Route::get('/{tenant}/home', fn () => route('tenant.home'))->name('tenant.home')->middleware(['tenant', InitializeTenancyByPath::class]);
|
||||
Route::get('/query-string', fn () => route('query-string'))->name('query-string')->middleware(['tenant', InitializeTenancyByRequestData::class]);
|
||||
|
||||
$tenant = Tenant::create();
|
||||
$tenantKey = $tenant->getTenantKey();
|
||||
$centralRouteUrl = route('home');
|
||||
$tenantRouteUrl = route('tenant.home', ['tenant' => $tenantKey]);
|
||||
$queryStringCentralUrl = route('query-string');
|
||||
$queryStringTenantUrl = route('query-string', ['tenant' => $tenantKey]);
|
||||
TenancyUrlGenerator::$bypassParameter = 'bypassParameter';
|
||||
$bypassParameter = TenancyUrlGenerator::$bypassParameter;
|
||||
|
||||
config(['tenancy.bootstrappers' => [UrlBindingBootstrapper::class]]);
|
||||
TenancyUrlGenerator::$prefixRouteNames = true;
|
||||
config(['tenancy.bootstrappers' => [UrlGeneratorBootstrapper::class]]);
|
||||
|
||||
tenancy()->initialize($tenant);
|
||||
|
||||
// Route names don't get prefixed when TenancyUrlGenerator::$prefixRouteNames is false
|
||||
expect(route('home'))->not()->toBe($centralRouteUrl);
|
||||
// When TenancyUrlGenerator::$passTenantParameterToRoutes is true (default)
|
||||
// The route helper receives the tenant parameter
|
||||
// So in order to generate central URL, we have to pass the bypass parameter
|
||||
expect(route('home', ['bypassParameter' => true]))->toBe($centralRouteUrl);
|
||||
|
||||
|
||||
TenancyUrlGenerator::$prefixRouteNames = true;
|
||||
// The $prefixRouteNames property is true
|
||||
// The route name passed to the route() helper ('home') gets prefixed prefixed with 'tenant.' automatically
|
||||
expect(route('home'))->toBe($tenantRouteUrl);
|
||||
|
|
@ -584,58 +591,149 @@ test('url binding tenancy bootstrapper changes route helper behavior correctly',
|
|||
// Also, the route receives the tenant parameter automatically
|
||||
expect(route('tenant.home'))->toBe($tenantRouteUrl);
|
||||
|
||||
// The $bypassParameter parameter ('central' by default) can bypass the route name prefixing
|
||||
// When the bypass parameter is true, the generated route URL points to the route named 'home'
|
||||
// Also, check if the bypass parameter gets removed from the generated URL query string
|
||||
expect(route('home', [$bypassParameter => true]))->toBe($centralRouteUrl)
|
||||
->not()->toContain($bypassParameter);
|
||||
// When the bypass parameter is false, the generated route URL points to the prefixed route ('tenant.home')
|
||||
expect(route('home', [$bypassParameter => false]))->toBe($tenantRouteUrl)
|
||||
->not()->toContain($bypassParameter);
|
||||
|
||||
TenancyUrlGenerator::$prefixRouteNames = false;
|
||||
// Route names don't get prefixed – TenancyUrlGenerator::$prefixRouteNames is false
|
||||
expect(route('home', [$bypassParameter => true]))->toBe($centralRouteUrl);
|
||||
expect(route('query-string'))->toBe($queryStringTenantUrl);
|
||||
|
||||
TenancyUrlGenerator::$passTenantParameterToRoutes = false;
|
||||
expect(route('query-string'))->toBe($queryStringCentralUrl);
|
||||
|
||||
TenancyUrlGenerator::$passTenantParameterToRoutes = true;
|
||||
expect(route('query-string'))->toBe($queryStringTenantUrl);
|
||||
|
||||
// Ending tenancy reverts route() behavior changes
|
||||
tenancy()->end();
|
||||
|
||||
expect(route('home'))->toBe($centralRouteUrl);
|
||||
expect(route('query-string'))->toBe($queryStringCentralUrl);
|
||||
expect(route('tenant.home', ['tenant' => $tenantKey]))->toBe($tenantRouteUrl);
|
||||
});
|
||||
|
||||
test('both the name prefixing and the tenant parameter logic gets skipped when bypass parameter is used', function () {
|
||||
$tenantParameterName = PathTenantResolver::tenantParameterName();
|
||||
|
||||
Route::get('/central/home', fn () => route('home'))->name('home');
|
||||
// Tenant route name prefix is 'tenant.' by default
|
||||
Route::get('/{tenant}/home', fn () => route('tenant.home'))->name('tenant.home')->middleware(['tenant', InitializeTenancyByPath::class]);
|
||||
|
||||
$tenant = Tenant::create();
|
||||
$centralRouteUrl = route('home');
|
||||
$tenantRouteUrl = route('tenant.home', ['tenant' => $tenant->getTenantKey()]);
|
||||
config(['tenancy.bootstrappers' => [UrlGeneratorBootstrapper::class]]);
|
||||
|
||||
TenancyUrlGenerator::$prefixRouteNames = true;
|
||||
TenancyUrlGenerator::$bypassParameter = 'bypassParameter';
|
||||
|
||||
tenancy()->initialize($tenant);
|
||||
|
||||
// The $bypassParameter parameter ('central' by default) can bypass the route name prefixing
|
||||
// When the bypass parameter is true, the generated route URL points to the route named 'home'
|
||||
expect(route('home', ['bypassParameter' => true]))->toBe($centralRouteUrl)
|
||||
// Bypass parameter prevents passing the tenant parameter directly
|
||||
->not()->toContain($tenantParameterName . '=')
|
||||
// Bypass parameter gets removed from the generated URL automatically
|
||||
->not()->toContain('bypassParameter');
|
||||
|
||||
// When the bypass parameter is false, the generated route URL points to the prefixed route ('tenant.home')
|
||||
expect(route('home', ['bypassParameter' => false]))->toBe($tenantRouteUrl)
|
||||
->not()->toContain('bypassParameter');
|
||||
});
|
||||
|
||||
test('url generator bootstrapper can make route helper generate links with the tenant parameter', function() {
|
||||
Route::get('/query_string', fn () => route('query_string'))->name('query_string')->middleware(['universal', InitializeTenancyByRequestData::class]);
|
||||
Route::get('/path', fn () => route('path'))->name('path');
|
||||
Route::get('/{tenant}/path', fn () => route('tenant.path'))->name('tenant.path')->middleware([InitializeTenancyByPath::class]);
|
||||
|
||||
$tenant = Tenant::create();
|
||||
$tenantKey = $tenant->getTenantKey();
|
||||
$queryStringCentralUrl = route('query_string');
|
||||
$queryStringTenantUrl = route('query_string', ['tenant' => $tenantKey]);
|
||||
$pathCentralUrl = route('path');
|
||||
$pathTenantUrl = route('tenant.path', ['tenant' => $tenantKey]);
|
||||
|
||||
// Makes the route helper receive the tenant parameter whenever available
|
||||
// Unless the bypass parameter is true
|
||||
TenancyUrlGenerator::$passTenantParameterToRoutes = true;
|
||||
|
||||
TenancyUrlGenerator::$bypassParameter = 'bypassParameter';
|
||||
|
||||
config(['tenancy.bootstrappers' => [UrlGeneratorBootstrapper::class]]);
|
||||
|
||||
expect(route('path'))->toBe($pathCentralUrl);
|
||||
// Tenant parameter required, but not passed since tenancy wasn't initialized
|
||||
expect(fn () => route('tenant.path'))->toThrow(UrlGenerationException::class);
|
||||
|
||||
tenancy()->initialize($tenant);
|
||||
|
||||
// Tenant parameter is passed automatically
|
||||
expect(route('path'))->not()->toBe($pathCentralUrl); // Parameter added as query string – bypassParameter needed
|
||||
expect(route('path', ['bypassParameter' => true]))->toBe($pathCentralUrl);
|
||||
expect(route('tenant.path'))->toBe($pathTenantUrl);
|
||||
|
||||
expect(route('query_string'))->toBe($queryStringTenantUrl)->toContain('tenant=');
|
||||
expect(route('query_string', ['bypassParameter' => 'true']))->toBe($queryStringCentralUrl)->not()->toContain('tenant=');
|
||||
|
||||
tenancy()->end();
|
||||
|
||||
expect(route('query_string'))->toBe($queryStringCentralUrl);
|
||||
|
||||
// Tenant parameter required, but shouldn't be passed since tenancy isn't initialized
|
||||
expect(fn () => route('tenant.path'))->toThrow(UrlGenerationException::class);
|
||||
|
||||
// Route-level identification
|
||||
pest()->get("http://localhost/central/home")->assertSee($centralRouteUrl);
|
||||
pest()->get("http://localhost/$tenantKey/home")->assertSee($tenantRouteUrl);
|
||||
pest()->get("http://localhost/query-string?tenant=$tenantKey")->assertSee($queryStringTenantUrl);
|
||||
pest()->get("http://localhost/query_string")->assertSee($queryStringCentralUrl);
|
||||
pest()->get("http://localhost/query_string?tenant=$tenantKey")->assertSee($queryStringTenantUrl);
|
||||
pest()->get("http://localhost/path")->assertSee($pathCentralUrl);
|
||||
pest()->get("http://localhost/$tenantKey/path")->assertSee($pathTenantUrl);
|
||||
});
|
||||
|
||||
test('fortify route tenancy bootstrapper updates fortify config correctly', function() {
|
||||
config(['tenancy.bootstrappers' => [FortifyRouteTenancyBootstrapper::class]]);
|
||||
|
||||
Route::get('/', function () {
|
||||
return true;
|
||||
})->name($tenantHomeRouteName = 'tenant.home');
|
||||
|
||||
FortifyRouteTenancyBootstrapper::$fortifyHome = $tenantHomeRouteName;
|
||||
FortifyRouteTenancyBootstrapper::$fortifyRedirectTenantMap = ['logout' => FortifyRouteTenancyBootstrapper::$fortifyHome];
|
||||
$originalFortifyHome = config('fortify.home');
|
||||
$originalFortifyRedirects = config('fortify.redirects');
|
||||
|
||||
tenancy()->initialize(Tenant::create());
|
||||
expect(config('fortify.home'))->toBe($homeUrl = route($tenantHomeRouteName));
|
||||
expect(config('fortify.redirects'))->toBe(['logout' => $homeUrl]);
|
||||
Route::get('/home', function () {
|
||||
return true;
|
||||
})->name($homeRouteName = 'home');
|
||||
|
||||
Route::get('/{tenant}/home', function () {
|
||||
return true;
|
||||
})->name($pathIdHomeRouteName = 'tenant.home');
|
||||
|
||||
Route::get('/welcome', function () {
|
||||
return true;
|
||||
})->name($welcomeRouteName = 'welcome');
|
||||
|
||||
Route::get('/{tenant}/welcome', function () {
|
||||
return true;
|
||||
})->name($pathIdWelcomeRouteName = 'path.welcome');
|
||||
|
||||
FortifyRouteTenancyBootstrapper::$fortifyHome = $homeRouteName;
|
||||
|
||||
// Make login redirect to the central welcome route
|
||||
FortifyRouteTenancyBootstrapper::$fortifyRedirectMap['login'] = [
|
||||
'route_name' => $welcomeRouteName,
|
||||
'context' => Context::CENTRAL,
|
||||
];
|
||||
|
||||
tenancy()->initialize($tenant = Tenant::create());
|
||||
// The bootstraper makes fortify.home always receive the tenant parameter
|
||||
expect(config('fortify.home'))->toBe('http://localhost/home?tenant=' . $tenant->getTenantKey());
|
||||
|
||||
// The login redirect route has the central context specified, so it doesn't receive the tenant parameter
|
||||
expect(config('fortify.redirects'))->toEqual(['login' => 'http://localhost/welcome']);
|
||||
|
||||
tenancy()->end();
|
||||
expect(config('fortify.home'))->toBe($originalFortifyHome);
|
||||
expect(config('fortify.redirects'))->toBe($originalFortifyRedirects);
|
||||
|
||||
// Making a route's context will pass the tenant parameter to the route
|
||||
FortifyRouteTenancyBootstrapper::$fortifyRedirectMap['login']['context'] = Context::TENANT;
|
||||
|
||||
tenancy()->initialize($tenant);
|
||||
|
||||
expect(config('fortify.redirects'))->toEqual(['login' => 'http://localhost/welcome?tenant=' . $tenant->getTenantKey()]);
|
||||
|
||||
// Make the home and login route accept the tenant as a route parameter
|
||||
// To confirm that tenant route parameter gets filled automatically too (path identification works as well as query string)
|
||||
FortifyRouteTenancyBootstrapper::$fortifyHome = $pathIdHomeRouteName;
|
||||
FortifyRouteTenancyBootstrapper::$fortifyRedirectMap['login']['route_name'] = $pathIdWelcomeRouteName;
|
||||
|
||||
tenancy()->end();
|
||||
|
||||
tenancy()->initialize($tenant);
|
||||
|
||||
expect(config('fortify.home'))->toBe("http://localhost/{$tenant->getTenantKey()}/home");
|
||||
expect(config('fortify.redirects'))->toEqual(['login' => "http://localhost/{$tenant->getTenantKey()}/welcome"]);
|
||||
});
|
||||
|
||||
test('database tenancy bootstrapper throws an exception if DATABASE_URL is set', function (string|null $databaseUrl) {
|
||||
|
|
|
|||
|
|
@ -116,10 +116,6 @@ test('early identification works with path identification', function (bool $useK
|
|||
->assertOk()
|
||||
->assertContent($tenantPost->title . '-' . $tenantComment->comment);
|
||||
assertTenancyInitializedInEarlyIdentificationRequest();
|
||||
|
||||
// Tenant routes that use path identification receive the tenant parameter automatically
|
||||
// (setDefaultTenantForRouteParametersWhenInitializingTenancy() in Stancl\Tenancy\Middleware\InitializeTenancyByPath)
|
||||
expect(route('tenant-route'))->toBe(route('tenant-route', ['tenant' => $tenant->getTenantKey()]));
|
||||
})->with([
|
||||
'route-level identification' => false,
|
||||
'kernel identification' => true,
|
||||
|
|
|
|||
|
|
@ -129,26 +129,6 @@ test('tenant parameter name can be customized', function () {
|
|||
->get('/acme/foo/abc/xyz');
|
||||
});
|
||||
|
||||
test('tenant parameter is set for all routes as the default parameter once the tenancy initialized', function () {
|
||||
Tenant::create([
|
||||
'id' => 'acme',
|
||||
]);
|
||||
|
||||
expect(tenancy()->initialized)->toBeFalse();
|
||||
|
||||
// make a request that will initialize tenancy
|
||||
pest()->get(route('foo', ['tenant' => 'acme', 'a' => 1, 'b' => 2]));
|
||||
|
||||
expect(tenancy()->initialized)->toBeTrue();
|
||||
expect(tenant('id'))->toBe('acme');
|
||||
|
||||
// assert that the route WITHOUT the tenant parameter matches the route WITH the tenant parameter
|
||||
expect(route('baz', ['a' => 1, 'b' => 2]))->toBe(route('baz', ['tenant' => 'acme', 'a' => 1, 'b' => 2]));
|
||||
|
||||
expect(route('baz', ['a' => 1, 'b' => 2]))->toBe('http://localhost/acme/baz/1/2'); // assert the full route string
|
||||
pest()->get(route('baz', ['a' => 1, 'b' => 2]))->assertOk(); // Assert route don't need tenant parameter
|
||||
});
|
||||
|
||||
test('tenant parameter does not have to be the first in order to initialize tenancy', function() {
|
||||
Tenant::create([
|
||||
'id' => $tenantId = 'another-tenant',
|
||||
|
|
|
|||
|
|
@ -43,9 +43,6 @@ beforeEach(function () {
|
|||
|
||||
Event::listen(TenancyInitialized::class, BootstrapTenancy::class);
|
||||
Event::listen(TenancyEnded::class, RevertToCentralContext::class);
|
||||
|
||||
// todo1 Is this cleanup needed?
|
||||
UpdateSyncedResource::$shouldQueue = false; // Global state cleanup
|
||||
Event::listen(SyncedResourceSaved::class, UpdateSyncedResource::class);
|
||||
|
||||
// Run migrations on central connection
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ use Stancl\Tenancy\Listeners\BootstrapTenancy;
|
|||
use Stancl\Tenancy\Middleware\InitializeTenancyByPath;
|
||||
use Stancl\Tenancy\Middleware\InitializeTenancyByRequestData;
|
||||
use Stancl\Tenancy\Bootstrappers\FilesystemTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\UrlBindingBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\UrlGeneratorBootstrapper;
|
||||
use Stancl\Tenancy\Overrides\TenancyUrlGenerator;
|
||||
|
||||
beforeEach(function () {
|
||||
|
|
@ -22,6 +22,7 @@ beforeEach(function () {
|
|||
]]);
|
||||
|
||||
TenancyUrlGenerator::$prefixRouteNames = false;
|
||||
TenancyUrlGenerator::$passTenantParameterToRoutes = true;
|
||||
|
||||
/** @var CloneRoutesAsTenant $cloneAction */
|
||||
$cloneAction = app(CloneRoutesAsTenant::class);
|
||||
|
|
@ -78,9 +79,11 @@ test('asset helper returns a link to an external url when asset url is not null'
|
|||
|
||||
test('asset helper works correctly with path identification', function (bool $kernelIdentification) {
|
||||
TenancyUrlGenerator::$prefixRouteNames = true;
|
||||
TenancyUrlGenerator::$passTenantParameterToRoutes = true;
|
||||
|
||||
config(['tenancy.filesystem.asset_helper_tenancy' => true]);
|
||||
config(['tenancy.identification.default_middleware' => InitializeTenancyByPath::class]);
|
||||
config(['tenancy.bootstrappers' => array_merge([UrlBindingBootstrapper::class], config('tenancy.bootstrappers'))]);
|
||||
config(['tenancy.bootstrappers' => array_merge([UrlGeneratorBootstrapper::class], config('tenancy.bootstrappers'))]);
|
||||
|
||||
$tenantAssetRoute = Route::prefix('{tenant}')->get('/tenant_helper', function () {
|
||||
return tenant_asset('foo');
|
||||
|
|
|
|||
|
|
@ -14,9 +14,10 @@ use Stancl\Tenancy\Bootstrappers\BroadcastChannelPrefixBootstrapper;
|
|||
use Stancl\Tenancy\Facades\GlobalCache;
|
||||
use Stancl\Tenancy\TenancyServiceProvider;
|
||||
use Stancl\Tenancy\Facades\Tenancy as TenancyFacade;
|
||||
use Stancl\Tenancy\Bootstrappers\UrlTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\RootUrlBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\MailTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\RedisTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\UrlGeneratorBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\DatabaseTenancyBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\BroadcastingConfigBootstrapper;
|
||||
use Stancl\Tenancy\Bootstrappers\FilesystemTenancyBootstrapper;
|
||||
|
|
@ -113,7 +114,7 @@ abstract class TestCase extends \Orchestra\Testbench\TestCase
|
|||
'tenancy.bootstrappers' => [
|
||||
DatabaseTenancyBootstrapper::class,
|
||||
FilesystemTenancyBootstrapper::class,
|
||||
UrlTenancyBootstrapper::class,
|
||||
RootUrlBootstrapper::class,
|
||||
],
|
||||
'queue.connections.central' => [
|
||||
'driver' => 'sync',
|
||||
|
|
@ -128,7 +129,8 @@ abstract class TestCase extends \Orchestra\Testbench\TestCase
|
|||
$app->singleton(BroadcastingConfigBootstrapper::class);
|
||||
$app->singleton(BroadcastChannelPrefixBootstrapper::class);
|
||||
$app->singleton(MailTenancyBootstrapper::class);
|
||||
$app->singleton(UrlTenancyBootstrapper::class);
|
||||
$app->singleton(RootUrlBootstrapper::class);
|
||||
$app->singleton(UrlGeneratorBootstrapper::class);
|
||||
}
|
||||
|
||||
protected function getPackageProviders($app)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue