1
0
Fork 0
mirror of https://github.com/archtechx/tenancy.git synced 2026-09-20 15:34:03 +00:00

Forget scoped disk's parent no matter how nested it is

This includes moving the TenantAssetController baseDiskName() method to FSBootstrapper and making it public static, since the same logic is used in two places now. Also cover the edge case where a scoped disk A has a scoped disk B as its parent, and B has A as its parent -- in that case, the method would be stuck in an infinite loop (also added separate test for this, commenting out the $visited-related code in baseDiskName will make the test fail).

Also updated the assetRoot's unnamed disk exception message.
This commit is contained in:
lukinovec 2026-09-03 16:16:27 +02:00 committed by Samuel Stancl
parent e20085588b
commit 9cda4cb3e4
4 changed files with 63 additions and 24 deletions

View file

@ -128,9 +128,9 @@ class FilesystemTenancyBootstrapper implements TenancyBootstrapper
$scopedDisks = [];
foreach ($this->app['config']['filesystems.disks'] as $name => $disk) {
if (isset($disk['driver'], $disk['disk'])
if (isset($disk['driver'])
&& $disk['driver'] === 'scoped'
&& in_array($disk['disk'], $tenantDisks, true)) {
&& in_array(static::baseDiskName($name), $tenantDisks, true)) {
$scopedDisks[] = $name;
}
}
@ -340,4 +340,34 @@ class FilesystemTenancyBootstrapper implements TenancyBootstrapper
return $bootstrapper->tenantStoragePath($bootstrapper->suffix($tenant));
}
/**
* Name of the disk whose root the passed disk uses.
*
* Disks using the 'scoped' driver have no root or url of their own -- they inherit these from their parent disk,
* which can be scoped as well, so only the final/base parent has to be tenant-aware.
*
* Returns null if the chain doesn't end with a named disk, i.e. when a parent disk is
* configured inline or when the disks reference each other.
*/
public static function baseDiskName(string $disk): string|null
{
// Keep track of visited disks to avoid infinite loops in case of disks referencing each other
$visited = [];
while (config("filesystems.disks.$disk.driver") === 'scoped') {
if (in_array($disk, $visited, true)) {
return null;
}
$visited[] = $disk;
if (! is_string($disk = config("filesystems.disks.$disk.disk"))) {
// Laravel allows configuring the parent disk inline as an array, and such a disk has no name
return null;
}
}
return $disk;
}
}