TenantAtlas/apps/platform/tests/Feature/Evidence/EvidenceSnapshotCanonicalControlReferenceTest.php
ahmido 6a5b8a3a11
Some checks failed
Main Confidence / confidence (push) Failing after 50s
feat: canonical control catalog foundation (#272)
## Summary
- add a config-seeded canonical control catalog plus shared resolution primitives and Microsoft subject bindings
- propagate canonical control references into findings-derived evidence snapshots and tenant review composition
- add the feature spec artifacts and focused Pest coverage, plus the supporting workspace and Sail helper adjustments included in this branch

## Testing
- cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Unit/Governance/CanonicalControlCatalogTest.php tests/Unit/Governance/CanonicalControlResolverTest.php tests/Feature/Governance/CanonicalControlResolutionIntegrationTest.php tests/Feature/Evidence/EvidenceSnapshotCanonicalControlReferenceTest.php tests/Feature/TenantReview/TenantReviewCanonicalControlReferenceTest.php tests/Feature/PlatformRelocation/CommandModelSmokeTest.php
- cd apps/platform && ./vendor/bin/sail bin pint --dirty --format agent

Co-authored-by: Ahmed Darrazi <ahmed.darrazi@live.de>
Reviewed-on: #272
2026-04-24 12:26:02 +00:00

68 lines
2.5 KiB
PHP

<?php
declare(strict_types=1);
use App\Models\Finding;
use App\Services\Evidence\EvidenceSnapshotService;
use App\Services\Evidence\Sources\FindingsSummarySource;
it('adds shared canonical control references to findings-derived evidence summaries', function (): void {
[$user, $tenant] = createUserWithTenant(role: 'owner');
Finding::factory()->permissionPosture()->create([
'tenant_id' => (int) $tenant->getKey(),
'workspace_id' => (int) $tenant->workspace_id,
]);
Finding::factory()->entraAdminRoles()->create([
'tenant_id' => (int) $tenant->getKey(),
'workspace_id' => (int) $tenant->workspace_id,
]);
Finding::factory()->create([
'tenant_id' => (int) $tenant->getKey(),
'workspace_id' => (int) $tenant->workspace_id,
'finding_type' => Finding::FINDING_TYPE_DRIFT,
'evidence_jsonb' => [
'policy_type' => 'deviceConfiguration',
],
]);
$item = app(FindingsSummarySource::class)->collect($tenant);
$summary = $item['summary_payload'];
expect($summary['canonical_controls'])->toHaveCount(3)
->and(collect($summary['canonical_controls'])->pluck('control_key')->all())->toEqualCanonicalizing([
'endpoint_hardening_compliance',
'privileged_access_governance',
'strong_authentication',
]);
foreach ($summary['entries'] as $entry) {
expect($entry['canonical_control_resolution']['status'])->toBe('resolved')
->and($entry['canonical_control_resolution']['control'])->toHaveKey('control_key')
->and($entry)->not->toHaveKey('control_label');
}
$payload = app(EvidenceSnapshotService::class)->buildSnapshotPayload($tenant);
expect($payload['summary']['canonical_controls'])->toHaveCount(3);
});
it('keeps missing bindings explicit instead of inventing evidence fallback labels', function (): void {
[$user, $tenant] = createUserWithTenant(role: 'owner');
Finding::factory()->create([
'tenant_id' => (int) $tenant->getKey(),
'workspace_id' => (int) $tenant->workspace_id,
'finding_type' => 'unknown_provider_signal',
]);
$summary = app(FindingsSummarySource::class)->collect($tenant)['summary_payload'];
$entry = $summary['entries'][0];
expect($entry['canonical_control_resolution'])->toMatchArray([
'status' => 'unresolved',
'reason_code' => 'missing_binding',
])->and($entry['canonical_control_resolution'])->not->toHaveKey('control')
->and($entry)->not->toHaveKey('control_label');
});