From 2f68fd4196641532847f8daef2b849b46f3c2fc2 Mon Sep 17 00:00:00 2001 From: Hyungi Ahn Date: Fri, 17 Apr 2026 08:25:30 +0900 Subject: [PATCH] =?UTF-8?q?fix(scripts):=20verify=5Fupload=5Fsize=20case?= =?UTF-8?q?=206=20=E2=80=94=20CL=20override=20=EB=8C=80=EC=8B=A0=20?= =?UTF-8?q?=EC=8B=A4=EC=A0=9C=20body=20=ED=81=AC=EA=B8=B0=EB=A1=9C=20?= =?UTF-8?q?=EC=8A=AC=EB=9E=99=20=EC=B4=88=EA=B3=BC=20=ED=85=8C=EC=8A=A4?= =?UTF-8?q?=ED=8A=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit httpx 의 h11 레이어가 Content-Length 와 body 길이 불일치를 client-side 에서 LocalProtocolError 로 거절해서, CL 헤더만 override 해 서버 pre-check 경로를 외부에서 격리 테스트하는 것이 불가능했음. 대신 body 자체가 slack 임계치를 초과하는 케이스로 변경 — multipart CL 이 자동으로 `max_bytes * slack_ratio` 를 넘어 서버 pre-check 가 먼저 catch 함. 또한 기존 case 7 (CL 위조) 는 같은 이유로 실현 불가능해 제거. 5 케이스에서 6 케이스로 조정. Co-Authored-By: Claude Opus 4.7 (1M context) --- scripts/verify_upload_size.py | 20 +++++++------------- 1 file changed, 7 insertions(+), 13 deletions(-) diff --git a/scripts/verify_upload_size.py b/scripts/verify_upload_size.py index 8098556..86d1dff 100644 --- a/scripts/verify_upload_size.py +++ b/scripts/verify_upload_size.py @@ -229,25 +229,19 @@ async def main() -> int: engine = create_async_engine(database_url) session_factory = async_sessionmaker(engine, class_=AsyncSession, expire_on_commit=False) + # CL override + body size mismatch 는 httpx 의 h11 레이어가 client-side 에서 + # LocalProtocolError 로 거절하므로 서버 pre-check 경로를 외부에서 격리 테스트 + # 하기 어렵다. 대신 body 가 정직하게 slack 임계치 초과인 케이스로 pre-check + # 경로도 간접 확인 (body + multipart 오버헤드가 slack 초과 → CL 헤더 자동 + # 계산 시에도 초과되어 pre-check 가 먼저 catch). + slack_over_size = int(max_bytes * SLACK_RATIO) + 1 cases: list[Case] = [ Case(name="0 bytes", size=0, expected_status=400), Case(name="1 byte", size=1, expected_status=201), Case(name="max_bytes minus 1", size=max_bytes - 1, expected_status=201), Case(name="max_bytes exact", size=max_bytes, expected_status=201), Case(name="max_bytes plus 1", size=max_bytes + 1, expected_status=413), - Case( - name="cl slack over (override CL)", - size=100, - expected_status=413, - content_length_override=str(int(max_bytes * SLACK_RATIO) + 1), - ), - Case( - name="cl forge (body > max, CL tiny)", - size=max_bytes + 1, - expected_status={400, 413, 422, 500}, - content_length_override="1024", - skip_reason=None, # best-effort; 실패해도 전체 PASS 판정에는 영향 없음 - ), + Case(name="slack over (body > max*slack)", size=slack_over_size, expected_status=413), ] print(f"=== base_url={base_url} max_bytes={max_bytes} slack={SLACK_RATIO} ===")