create([ 'workspace_id' => (int) $otherEnvironment->workspace_id, 'managed_environment_id' => (int) $otherEnvironment->getKey(), ]); expect(fn () => app(StartTenantConfigurationCapture::class)->start($environment, $foreignConnection, $user, [ 'conditionalAccessPolicy', ]))->toThrow(NotFoundHttpException::class); Queue::assertNothingPushed(); }); it('Spec420 revalidates provider connection scope in the queued job before graph work', function (): void { app(ResourceTypeRegistry::class)->syncDefaults(); [$user, $environment] = createMinimalUserWithTenant(role: 'owner'); [, $otherEnvironment] = createMinimalUserWithTenant(role: 'owner'); $foreignConnection = ProviderConnection::factory()->withCredential()->create([ 'workspace_id' => (int) $otherEnvironment->workspace_id, 'managed_environment_id' => (int) $otherEnvironment->getKey(), ]); $graph = spec420ScopeGraphClient(); app()->instance(GraphClientInterface::class, $graph); $run = OperationRun::factory()->withUser($user)->forTenant($environment)->create([ 'type' => OperationRunType::TenantConfigurationCapture->value, 'status' => OperationRunStatus::Queued->value, 'outcome' => OperationRunOutcome::Pending->value, 'context' => [ 'target_scope' => [ 'workspace_id' => (int) $environment->workspace_id, 'managed_environment_id' => (int) $environment->getKey(), 'provider_connection_id' => (int) $foreignConnection->getKey(), ], 'resource_types' => ['conditionalAccessPolicy'], 'required_capability' => 'evidence.manage', ], ]); expect(fn () => app(CaptureTenantConfigurationEvidenceJob::class, ['run' => $run])->handle( app(GenericContentEvidenceCaptureService::class), app(OperationRunService::class), app(AuditRecorder::class), ))->toThrow(RuntimeException::class, 'same-scope provider connection'); expect($graph->calls)->toBe([]); }); function spec420ScopeGraphClient(): GraphClientInterface { return new class implements GraphClientInterface { public array $calls = []; public function listPolicies(string $policyType, array $options = []): GraphResponse { $this->calls[] = ['policy_type' => $policyType, 'options' => $options]; return new GraphResponse(true, []); } public function getPolicy(string $policyType, string $policyId, array $options = []): GraphResponse { return new GraphResponse(false, [], 501); } public function getOrganization(array $options = []): GraphResponse { return new GraphResponse(false, [], 501); } public function applyPolicy(string $policyType, string $policyId, array $payload, array $options = []): GraphResponse { return new GraphResponse(false, [], 501); } public function getServicePrincipalPermissions(array $options = []): GraphResponse { return new GraphResponse(false, [], 501); } public function request(string $method, string $path, array $options = []): GraphResponse { return new GraphResponse(false, [], 501); } }; }