'succeeded']); $this->actingAs($user); setAdminPanelContext($environment); $component = baselineCompareLandingLivewire($environment) ->assertSee('Which baseline drift requires action?') ->assertSee('Needs attention') ->assertSee('Compare now') ->assertActionEnabled('compareNow') ->assertDontSee('OperationRun proof') ->assertDontSee('raw payload') ->assertDontSee('provider response'); expect(substr_count($component->html(), 'data-testid="baseline-compare-primary-action"'))->toBe(1); }); it('renders baseline compare as one decision with technical proof collapsed', function (): void { [$user, $environment] = createUserWithTenant(role: 'owner', workspaceRole: 'manager'); [$profile, $snapshot] = seedActiveBaselineForTenant($environment); $run = seedBaselineCompareRun($environment, $profile, $snapshot, [ 'reason_code' => BaselineCompareReasonCode::OverdueFindingsRemain->value, 'coverage' => [ 'effective_types' => ['deviceConfiguration'], 'covered_types' => ['deviceConfiguration'], 'uncovered_types' => [], 'proof' => true, ], ]); Finding::factory()->create([ 'managed_environment_id' => (int) $environment->getKey(), 'workspace_id' => (int) $environment->workspace_id, 'finding_type' => Finding::FINDING_TYPE_DRIFT, 'scope_key' => 'baseline_profile:'.$profile->getKey(), 'severity' => Finding::SEVERITY_HIGH, 'status' => Finding::STATUS_NEW, 'source' => OperationRunType::BaselineCompare->value, 'baseline_operation_run_id' => (int) $run->getKey(), ]); $this->actingAs($user); setAdminPanelContext($environment); $component = baselineCompareLandingLivewire($environment) ->assertSee('Which baseline drift requires action?') ->assertSee('Needs attention') ->assertSee('Review drift findings') ->assertSee('Technical details and audit links') ->assertSee('View compare readiness details') ->assertDontSee('OperationRun proof') ->assertDontSee('raw diff') ->assertDontSee('raw payload') ->assertDontSee('provider response'); $html = $component->html(); expect($html) ->not->toContain('data-testid="baseline-compare-technical-details" open') ->not->toContain('data-testid="baseline-compare-readiness-disclosure" open') ->not->toContain('data-testid="baseline-compare-diagnostics" open'); }); it('renders restore source decision without duplicate readiness status vocabulary', function (): void { [$user, $tenant, $backupSet] = spec398RestorePreviewFixture(); setAdminPanelContext($tenant); Livewire::actingAs($user) ->test(CreateRestoreRun::class) ->fillForm(['backup_set_id' => (int) $backupSet->getKey()]) ->assertSee('Is this restore safe to continue?') ->assertSee('Needs attention') ->assertSee('Primary next action') ->assertSee('Continue to scope.') ->assertSee('Backup quality summary') ->assertSee('Ready') ->assertSee('View safety gates and proof') ->assertDontSee('Restore readiness') ->assertDontSee('Restore needs preparation.') ->assertDontSee('Ready for final confirmation.') ->assertDontSee("Restore can't continue yet.") ->assertDontSee('Degraded input') ->assertDontSee('Operation proof is complete'); }); it('renders restore preview with capped rows and secondary proof collapsed', function (): void { [$user, $tenant, $backupSet, $backupItem] = spec398RestorePreviewFixture(); $data = spec398RestorePreviewData($backupSet, $backupItem); setAdminPanelContext($tenant); $component = Livewire::actingAs($user) ->test(CreateRestoreRun::class) ->set('data', $data) ->goToWizardStep(4) ->assertWizardCurrentStep(4) ->assertSee('Preview evidence') ->assertSee('Policies changed') ->assertSee('Requires review') ->assertSee('Validation blockers') ->assertSee('Next gate') ->assertSee('View secondary preview counts') ->assertSee('View safety gates and restore proof') ->assertSee('Spec398 Changed Policy 8') ->assertDontSee('Spec398 Changed Policy 9') ->assertDontSee('spec398 raw restore payload') ->assertDontSee('provider response payload'); $html = $component->html(); expect($html) ->toContain('data-testid="restore-run-preview-primary-metrics"') ->toContain('data-testid="restore-run-preview-secondary-metrics"') ->toContain('4 additional changed policies kept in detailed review.') ->not->toContain('data-testid="restore-run-preview-secondary-metrics" open') ->not->toContain('data-testid="restore-run-preview-evidence" open'); }); function spec398RestorePreviewFixture(): array { $tenant = ManagedEnvironment::factory()->create([ 'rbac_status' => 'ok', 'rbac_last_checked_at' => now(), ]); [$user, $tenant] = createUserWithTenant(tenant: $tenant, role: 'owner'); ensureDefaultProviderConnection($tenant, 'microsoft'); $policy = Policy::create([ 'managed_environment_id' => (int) $tenant->getKey(), 'external_id' => 'spec398-policy', 'policy_type' => 'deviceConfiguration', 'display_name' => 'Spec398 Restore Policy', 'platform' => 'windows', ]); $backupSet = BackupSet::factory()->create([ 'managed_environment_id' => (int) $tenant->getKey(), 'name' => 'Spec398 Restore Backup', 'status' => 'completed', 'item_count' => 1, ]); $backupItem = BackupItem::factory()->create([ 'managed_environment_id' => (int) $tenant->getKey(), 'backup_set_id' => (int) $backupSet->getKey(), 'policy_id' => (int) $policy->getKey(), 'policy_identifier' => $policy->external_id, 'policy_type' => $policy->policy_type, 'platform' => $policy->platform, 'payload' => [ 'id' => $policy->external_id, 'displayName' => $policy->display_name, 'settings' => ['encryption' => 'required'], ], 'metadata' => [ 'displayName' => $policy->display_name, ], 'assignments' => [], ]); return [$user, $tenant, $backupSet, $backupItem]; } function spec398RestorePreviewData(BackupSet $backupSet, BackupItem $backupItem): array { /** @var RestoreSafetyResolver $resolver */ $resolver = app(RestoreSafetyResolver::class); $previewDiffs = collect(range(1, 12)) ->map(fn (int $index): array => [ 'policy_identifier' => 'spec398-policy-'.$index, 'display_name' => 'Spec398 Changed Policy '.$index, 'policy_type' => 'deviceConfiguration', 'platform' => 'windows', 'action' => 'update', 'assignments_changed' => $index === 1, 'scope_tags_changed' => false, 'review_reason' => 'Spec398 preview change requires review.', 'review_action_label' => 'Review change', 'diff' => [ 'summary' => ['added' => 0, 'removed' => 0, 'changed' => 1], 'changed' => ['setting' => ['before' => 'off', 'after' => 'on']], 'added' => [], 'removed' => [], ], ]) ->all(); $data = [ 'backup_set_id' => (int) $backupSet->getKey(), 'scope_mode' => 'selected', 'backup_item_ids' => [(int) $backupItem->getKey()], 'is_dry_run' => true, 'group_mapping' => [], 'check_summary' => ['blocking' => 0, 'warning' => 1, 'safe' => 2], 'check_results' => [ ['code' => 'warning', 'severity' => 'warning', 'message' => 'Review assignment changes before execution.'], ['code' => 'safe', 'severity' => 'safe', 'message' => 'Scope fingerprint is current.'], ], 'checks_ran_at' => now('UTC')->toIso8601String(), 'preview_summary' => [ 'generated_at' => now('UTC')->toIso8601String(), 'policies_total' => 12, 'policies_changed' => 12, 'assignments_changed' => 1, 'scope_tags_changed' => 0, 'raw_payload_marker' => 'spec398 raw restore payload', 'provider_response' => 'provider response payload', ], 'preview_diffs' => $previewDiffs, 'preview_ran_at' => now('UTC')->toIso8601String(), ]; $data['check_basis'] = $resolver->checksBasisFromData($data); $data['preview_basis'] = $resolver->previewBasisFromData($data); return RestoreRunResource::synchronizeRestoreSafetyDraft($data); }