Files
alrahma_sunday_school_api/tests/Feature/Api/V1/FullSurface/ApiPrivacyRetentionAndErasureContractTest.php
T
2026-06-11 11:46:12 -04:00

50 lines
2.0 KiB
PHP

<?php
namespace Tests\Feature\Api\V1\FullSurface;
use Tests\Feature\Api\V1\FullSurface\Support\FullSurfaceE2EContractCase;
class ApiPrivacyRetentionAndErasureContractTest extends FullSurfaceE2EContractCase
{
public function test_erasure_archive_and_privacy_routes_are_never_publicly_mutable(): void
{
$routes = $this->apiRoutesContainingAny(['privacy', 'erase', 'erasure', 'retention', 'archive', 'anonymize', 'gdpr', 'delete-account']);
foreach ($routes as $route) {
$method = $this->primaryMethod($route);
$uri = $route->uri();
if (! in_array($method, ['POST', 'PUT', 'PATCH', 'DELETE'], true)) {
continue;
}
$response = $this->json($method, $this->materializePath($uri), $this->payloadFor($method, $uri));
$this->assertStatusIn($response, [400, 401, 403, 404, 405, 419, 422], 'public privacy mutation '.$method.' '.$uri);
$this->assertNoServerError($response, 'public privacy mutation '.$method.' '.$uri);
}
}
public function test_privacy_related_exports_do_not_leak_sensitive_user_fields(): void
{
$routes = $this->apiRoutesContainingAny(['export', 'download', 'report', 'privacy', 'profile']);
$forbidden = ['password', 'remember_token', 'two_factor', 'api_token', 'secret', 'private_key'];
foreach (array_slice($routes, 0, 100) as $route) {
if ($this->primaryMethod($route) !== 'GET') {
continue;
}
$uri = $route->uri();
$response = $this->actingAs($this->actorFor($uri), 'api')->getJson($this->materializePath($uri));
$this->assertControlled($response, 'GET', $uri);
$this->assertNoServerError($response, 'privacy export/read at '.$uri);
foreach ($forbidden as $needle) {
$this->assertStringNotContainsStringIgnoringCase($needle, $response->getContent(), $uri.' must not leak '.$needle);
}
}
}
}