Some checks failed
Main Confidence / confidence (push) Failing after 54s
Integrates latest TenantPilot platform changes from `platform-dev` into `dev`. Refresh method in this update: merge from `origin/dev` into `platform-dev` on explicit user request. This PR was created by agent on user request; do not merge automatically. Co-authored-by: Ahmed Darrazi <ahmed.darrazi@live.de> Reviewed-on: #308
97 lines
3.8 KiB
PHP
97 lines
3.8 KiB
PHP
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
use App\Filament\Pages\CrossTenantComparePage;
|
|
use App\Models\Tenant;
|
|
use App\Models\User;
|
|
use App\Models\Workspace;
|
|
use App\Models\WorkspaceMembership;
|
|
use App\Services\Auth\WorkspaceCapabilityResolver;
|
|
use App\Support\Workspaces\WorkspaceContext;
|
|
use Filament\Actions\Action;
|
|
use Illuminate\Foundation\Testing\RefreshDatabase;
|
|
use Livewire\Livewire;
|
|
use Tests\Feature\Concerns\BuildsPortfolioCompareFixtures;
|
|
|
|
uses(RefreshDatabase::class, BuildsPortfolioCompareFixtures::class);
|
|
|
|
it('returns 404 for non-members on the cross-tenant compare route', function (): void {
|
|
$workspace = Workspace::factory()->create();
|
|
$user = User::factory()->create();
|
|
|
|
$this->actingAs($user)
|
|
->withSession([WorkspaceContext::SESSION_KEY => (int) $workspace->getKey()])
|
|
->get(CrossTenantComparePage::getUrl(panel: 'admin'))
|
|
->assertNotFound();
|
|
});
|
|
|
|
it('returns 403 for workspace members missing baseline view capability on the compare route', function (): void {
|
|
$workspace = Workspace::factory()->create();
|
|
$viewer = User::factory()->create();
|
|
|
|
WorkspaceMembership::factory()->create([
|
|
'workspace_id' => (int) $workspace->getKey(),
|
|
'user_id' => (int) $viewer->getKey(),
|
|
'role' => 'readonly',
|
|
]);
|
|
|
|
$resolver = \Mockery::mock(WorkspaceCapabilityResolver::class);
|
|
$resolver->shouldReceive('isMember')->andReturnTrue();
|
|
$resolver->shouldReceive('can')->andReturnFalse();
|
|
app()->instance(WorkspaceCapabilityResolver::class, $resolver);
|
|
|
|
$this->actingAs($viewer)
|
|
->withSession([WorkspaceContext::SESSION_KEY => (int) $workspace->getKey()])
|
|
->get(CrossTenantComparePage::getUrl(panel: 'admin'))
|
|
->assertForbidden();
|
|
});
|
|
|
|
it('returns 404 when the requested target tenant is outside the actor scope', function (): void {
|
|
$fixture = $this->makeCrossTenantCompareFixture();
|
|
$hiddenTarget = Tenant::factory()->create([
|
|
'workspace_id' => (int) $fixture['workspace']->getKey(),
|
|
'name' => 'Hidden Target',
|
|
]);
|
|
|
|
$session = $this->setAdminWorkspaceContext($fixture['user'], $fixture['workspace']);
|
|
|
|
$this->withSession($session)
|
|
->get(CrossTenantComparePage::getUrl(parameters: [
|
|
'source_tenant_id' => (int) $fixture['sourceTenant']->getKey(),
|
|
'target_tenant_id' => (int) $hiddenTarget->getKey(),
|
|
], panel: 'admin'))
|
|
->assertNotFound();
|
|
});
|
|
|
|
it('keeps promotion preflight visible but disabled for readonly members and forbids forced execution', function (): void {
|
|
$fixture = $this->makeCrossTenantCompareFixture(workspaceRole: 'readonly', tenantRole: 'readonly');
|
|
|
|
$this->createPortfolioCompareSubject(
|
|
tenant: $fixture['sourceTenant'],
|
|
displayName: 'Readonly Policy',
|
|
snapshot: ['settings' => [['key' => 'readonly', 'value' => 1]]],
|
|
);
|
|
$this->createPortfolioCompareSubject(
|
|
tenant: $fixture['targetTenant'],
|
|
displayName: 'Readonly Policy',
|
|
snapshot: ['settings' => [['key' => 'readonly', 'value' => 1]]],
|
|
);
|
|
|
|
$this->setAdminWorkspaceContext($fixture['user'], $fixture['workspace']);
|
|
|
|
$query = [
|
|
'source_tenant_id' => (int) $fixture['sourceTenant']->getKey(),
|
|
'target_tenant_id' => (int) $fixture['targetTenant']->getKey(),
|
|
'policy_type' => ['deviceConfiguration'],
|
|
];
|
|
|
|
Livewire::withQueryParams($query)
|
|
->actingAs($fixture['user'])
|
|
->test(CrossTenantComparePage::class)
|
|
->assertActionVisible('generatePromotionPreflight')
|
|
->assertActionDisabled('generatePromotionPreflight')
|
|
->assertActionExists('generatePromotionPreflight', fn (Action $action): bool => $action->getTooltip() === 'You need workspace baseline manage access to generate a promotion preflight.')
|
|
->call('generatePromotionPreflight')
|
|
->assertForbidden();
|
|
}); |