update(['is_active' => false]); DB::table('boards')->where('slug', 'gallery-test')->delete(); } /** * preview 라우트가 boards 그룹과 별도 throttle 버킷을 사용하는지 테스트 * * 게시판 API를 60회 호출해도 preview API가 429를 반환하지 않아야 합니다. */ public function test_preview_route_is_separated_into_its_own_prefix_group(): void { // Given: preview 라우트와 boards 그룹 라우트를 이름으로 조회 $boardsIndex = \Illuminate\Support\Facades\Route::getRoutes() ->getByName('api.modules.sirsoft-board.boards.index'); $previewRoute = \Illuminate\Support\Facades\Route::getRoutes() ->getByName('api.modules.sirsoft-board.boards.attachment.preview'); $this->assertNotNull($boardsIndex, 'boards.index 라우트가 등록되어야 합니다'); $this->assertNotNull($previewRoute, 'boards.attachment.preview 라우트가 등록되어야 합니다'); // Then: 두 라우트는 각각 독립된 Route::prefix 그룹에 속해야 한다 (action 클래스 명세로 확인) // 같은 그룹이면 preview 가 인증/권한 미들웨어까지 공유하게 되어 공개 썸네일 제공 의도를 어긴다. // boards.index 는 throttle 만 적용된 공개 그룹, preview 는 공개/익명 전용 별도 prefix 그룹. $boardsMiddleware = $boardsIndex->gatherMiddleware(); $previewMiddleware = $previewRoute->gatherMiddleware(); $this->assertContains('optional.sanctum', $previewMiddleware, 'preview 는 optional.sanctum 으로 공개 접근 가능해야 합니다'); $this->assertContains('optional.sanctum', $boardsMiddleware, 'boards 그룹은 optional.sanctum 이어야 합니다'); // preview 라우트 URI 에 attachment/{hash}/preview 가 포함되어야 합니다 $this->assertStringContainsString('attachment/{hash}/preview', $previewRoute->uri(), 'preview 라우트 URI 구조 확인'); } /** * preview API가 존재하지 않는 첨부파일에 대해 404를 반환하는지 테스트 */ public function test_preview_returns_404_for_nonexistent_attachment(): void { // Given: 게시판 생성 Board::factory()->create([ 'is_active' => true, 'slug' => 'gallery-test', 'name' => ['ko' => '갤러리 테스트', 'en' => 'Gallery Test'], ]); // When: 존재하지 않는 해시로 preview API 호출 $response = $this->getJson('/api/modules/sirsoft-board/boards/gallery-test/attachment/abcdef123456/preview'); // Then: 404 반환 $response->assertStatus(404); } /** * preview API가 존재하지 않는 게시판에 대해 404를 반환하는지 테스트 */ public function test_preview_returns_404_for_nonexistent_board(): void { // When: 존재하지 않는 게시판 슬러그로 preview API 호출 $response = $this->getJson('/api/modules/sirsoft-board/boards/nonexistent-board/attachment/abcdef123456/preview'); // Then: 404 반환 $response->assertStatus(404); } }