확장이 SP Kernel 미들웨어 그룹을 직접 조작하거나 라우트 파일에 미들웨어 FQCN 을 직접 부착하던 임시 방식을, 확장이 부착 대상(targets)을 명시 선언하고 코어가 요청 시점에 라우트명·URI 로 매칭해 실행하는 self-gate 로 정규화. 번들 7건(ecommerce/gdpr/pay 3종) 이전, audit 룰 3건·문서·버전 동기화 동반. 부수적으로 generate-skills.cjs 가 재생성 시 신의성실(부수의무) 섹션을 소실 시키던 회귀를 수정 — 스킬별 불릿을 스크립트 SSoT 로 편입해 재생성에도 보존.
84 lines
3.1 KiB
PHP
84 lines
3.1 KiB
PHP
<?php
|
|
|
|
namespace Tests\Feature\Extension;
|
|
|
|
use App\Contracts\Extension\ExtensionMiddlewareRegistryInterface;
|
|
use App\Extension\ExtensionMiddlewareRegistry;
|
|
use App\Http\Middleware\ExtensionMiddlewareGate;
|
|
use Illuminate\Http\Response;
|
|
use Illuminate\Support\Facades\Route;
|
|
use Mockery;
|
|
use Tests\TestCase;
|
|
|
|
/**
|
|
* 게이트 그룹 등록 파싱 통합 테스트.
|
|
*
|
|
* bootstrap/app.php 가 `ExtensionMiddlewareGate::class.':web,after_core'` 형태의
|
|
* 파라미터+그룹 문자열로 게이트를 등록하는데, 프로젝트 내 이 형태의 선례가 없어
|
|
* Laravel MiddlewareNameResolver + Pipeline::parsePipeString 이 실제로
|
|
* handle($req,$next,'web','after_core') 로 파싱하는지 실요청으로 검증한다.
|
|
*/
|
|
class ExtensionMiddlewareGateIntegrationTest extends TestCase
|
|
{
|
|
protected function tearDown(): void
|
|
{
|
|
ExtensionMiddlewareRegistry::flush();
|
|
parent::tearDown();
|
|
}
|
|
|
|
/**
|
|
* @effects gate_param_string_parses_group_and_timing_on_real_request
|
|
*/
|
|
public function test_gate_param_string_parses_group_and_timing_on_real_request(): void
|
|
{
|
|
IntegrationSpyMiddleware::$seen = [];
|
|
IntegrationSpyMiddleware::$ran = false;
|
|
|
|
// registry 를 mock — after_core/web 조회 시에만 매칭 미들웨어를 반환.
|
|
$registry = Mockery::mock(ExtensionMiddlewareRegistryInterface::class);
|
|
$registry->shouldReceive('resolveForRoute')
|
|
->andReturnUsing(function (string $routeName, string $path, string $group, string $timing): array {
|
|
IntegrationSpyMiddleware::$seen[] = "{$group},{$timing}";
|
|
|
|
return ($group === 'web' && $timing === 'after_core')
|
|
? [IntegrationSpyMiddleware::class]
|
|
: [];
|
|
});
|
|
$this->app->instance(ExtensionMiddlewareRegistryInterface::class, $registry);
|
|
|
|
// web 그룹에 게이트를 파라미터 문자열로 등록한 라우트 (bootstrap 등록 형태 복제).
|
|
Route::middleware([
|
|
ExtensionMiddlewareGate::class.':web,before_core',
|
|
ExtensionMiddlewareGate::class.':web,after_core',
|
|
])->get('/__gate_probe', fn () => new Response('ok'))->name('gate.probe');
|
|
|
|
$response = $this->get('/__gate_probe');
|
|
|
|
$response->assertOk();
|
|
$response->assertSee('ok');
|
|
|
|
// 게이트가 group/timing 파라미터를 정확히 파싱해 registry 를 조회했는지 확인.
|
|
$this->assertContains('web,before_core', IntegrationSpyMiddleware::$seen);
|
|
$this->assertContains('web,after_core', IntegrationSpyMiddleware::$seen);
|
|
|
|
// after_core 조회에서 반환된 매칭 미들웨어가 실제로 실행됐는지 확인.
|
|
$this->assertTrue(IntegrationSpyMiddleware::$ran, '파라미터 문자열 파싱 후 매칭 미들웨어가 실행되어야 합니다.');
|
|
}
|
|
}
|
|
|
|
/** 실행/조회 기록 픽스처 미들웨어. */
|
|
class IntegrationSpyMiddleware
|
|
{
|
|
public static bool $ran = false;
|
|
|
|
/** @var array<int, string> */
|
|
public static array $seen = [];
|
|
|
|
public function handle($request, \Closure $next)
|
|
{
|
|
self::$ran = true;
|
|
|
|
return $next($request);
|
|
}
|
|
}
|