- analysis/·source-index·state.json 을 final/document.md 제2부·제3부로 접었다. SSOT 는 하나다 - 파일럿 — commit-ambiguity-as-a-result 를 새 기준으로 재선별. 후보 14 → 글감 5 (PROMOTE 5 · MERGE_INTO 3 · KEEP_IN_SSOT 4 · 보류 2). 기록 5건을 다시 썼고 그림 1개를 techviz 로 만들었다 - 재선별이 잡은 것: 제1부 §6.2·§11.1 이 자기 §13.2 와 어긋나 있었다(레인을 안 돌렸다 vs 돌렸다) — 정정. 이미 답이 나와 있던 Question 을 HEAD 재실행 질문으로 다시 세웠다. Concept 이 인용한 코드가 SSOT 에 없어 뺐다 - candidateScope·sourceRepository 기록. 나머지 43개 주제는 재선별 대기(PENDING 905) Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
118 lines
5.5 KiB
Markdown
118 lines
5.5 KiB
Markdown
---
|
|
kind: CASE
|
|
slug: analysis-finding-a09-f001
|
|
title: production 판정이 두 개의 리터럴 프로파일 이름에 걸려 있다
|
|
topic: file-transfer-and-storage
|
|
project: clean-architecture-backend-template
|
|
status: 게시 전
|
|
sourceRevision: 21234e38cdb9a926cbc92bb97a2aee2e4a7d2916
|
|
rootTreeNode: case:analysis-finding-a09-f001
|
|
evidenceCapturedOn: 2026-09-01
|
|
body: case-analysis-finding-a09-f001.body.md
|
|
assets:
|
|
- key: analysis-finding-a09-f001
|
|
file: ../../../final/evidence/rendered/analysis-finding-a09-f001.svg
|
|
evidence:
|
|
- ../../../final/evidence/raw/analysis-finding-a09-f001.txt
|
|
source:
|
|
- 원본 분석 절은 final/document.md#a09#L106 이다.
|
|
---
|
|
|
|
# production 판정이 두 개의 리터럴 프로파일 이름에 걸려 있다
|
|
|
|
개발용 제공자를 운영에서 쓰지 말라는 금지가 문서에 있고 그것을 강제하는 코드는 한 곳이다. 그 코드는 거부 검사인데 판정 근거가 이름 두 개의 허용 목록이다. 다른 이름을 쓰는 분기는 검사를 통과한다.
|
|
|
|
## 관계
|
|
|
|
- **거부 검사의 근거를 허용 목록으로 두면 목록 밖이 통과한다**
|
|
이 사례가 그 규칙의 형태다.
|
|
- **사라진 가드가 문서에만 남았고 그 부재는 이미 승인된 결정이다**
|
|
같은 계열의 강제 수단 사례다.
|
|
- **발행 rename만 경로 기반이고 그것을 지키는 것은 모듈 자신이 근사에 불과하다고 적은 사전검사다**
|
|
도달성이 형상에 달린 다른 사례다.
|
|
|
|
## 문제
|
|
|
|
리프 지침 문서의 금지 목록에 개발용 제공자를 운영에서 쓰는 것이 있다.
|
|
|
|
그것을 강제하는 코드가 어디 있는지 찾았다.
|
|
|
|
## 결론
|
|
|
|
한 곳이다.
|
|
|
|
활성 프로파일 목록을 소문자로 만들고, 그중 하나가 짧은 운영 이름이거나 긴 운영 이름과 같은지 본다.
|
|
|
|
이 저장소가 짧은 이름의 프로파일 설정 파일을 싣고 있으므로 현재 형상에서는 맞는다.
|
|
|
|
그리고 같은 방식으로 운영을 판정하는 리프는 이것 하나뿐이다. 저장소 전체가 공유하는 운영 판별 장치가 없다.
|
|
|
|
문제는 방향이다.
|
|
|
|
이것은 거부 검사인데 판정 근거가 허용 목록 두 개다.
|
|
|
|
지역이나 환경을 이름에 붙이거나 축약형이나 다른 낱말을 쓰는 분기는 이 검사를 통과한다. 그리고 개발용 제공자가 운영에서 조용히 선택된다.
|
|
|
|
그 제공자는 README 가 현재 경로 전용 개발 제공자라고 적은 것이다.
|
|
|
|
실패는 시작 시점이 아니라 데이터가 로컬 디스크에 쌓인 뒤에 드러난다.
|
|
|
|
판정은 P3 다. 이 저장소 형상에서는 도달하지 않는다.
|
|
|
|
기록하는 이유는 셋이다. 지침 문서가 금지 항목으로 명시했고, 강제 수단이 문자열 둘이며, 분기가 프로파일 이름을 바꾸는 것은 평범한 일이다.
|
|
|
|
수정은 운영 판별을 뒤집는 것이다. 이름을 묻는 대신 개발용 제공자를 허용한다는 명시적 설정을 요구하는 형태다. 이름이 아니라 의도를 묻는 것이다.
|
|
|
|
## 검증 환경
|
|
|
|
Spring Boot : 4.0.8
|
|
확인 방식 : 강제 코드 전수 검색과 저장소 전체 운영 판별 장치 확인
|
|
소스 수정 : x
|
|
|
|
## 재현 조건
|
|
|
|
원문은 final/evidence/raw/150 계열에 있다.
|
|
|
|
1. 지침 문서의 금지 목록을 읽는다.
|
|
2. 그 금지를 강제하는 코드를 저장소에서 찾는다.
|
|
3. 판정 조건이 무엇과 비교하는지 확인한다.
|
|
4. 같은 방식으로 운영을 판정하는 다른 리프가 있는지 센다.
|
|
5. 개발용 제공자의 README 서술을 확인한다.
|
|
|
|
## 본문
|
|
|
|
<!-- body:start -->
|
|
|
|
CLAUDE.md의 Forbidden 목록에 "local-dev in production"이 있고, 그것을 강제하는 코드는 이것 하나다.
|
|
|
|
```java
|
|
private boolean productionProfileActive() {
|
|
return activeProfiles.stream()
|
|
.map(profile -> profile.toLowerCase(Locale.ROOT))
|
|
.anyMatch(profile -> profile.equals("prod") || profile.equals("production"));
|
|
}
|
|
```
|
|
|
|
## 금지를 강제하는 코드 한 곳
|
|
|
|
:::evidence key="analysis-finding-a09-f001" alt="분석 문서 final/document.md#a09 에서 이 기록의 근거 절을 그대로 잘라낸 15줄. 코드베이스를 측정한 것이 아니라 원본 판정이 무엇을 적었는지를 보여 준다." caption="final/document.md#a09 발췌 — 15줄" zoom="true"
|
|
:::
|
|
|
|
## 현재 형상에서는 맞는다
|
|
|
|
이 저장소가 `application-prod.yml`을 싣고 있다. 그리고 `150-...` §8.2c에서 확인했듯 같은 방식으로 production을 판정하는 leaf는 이것 하나뿐이다 — 저장소 전체가 공유하는 production 판별 장치가 없다.
|
|
|
|
## 문제는 방향이다
|
|
|
|
이것은 **거부** 검사인데 판정 근거가 **허용 목록 두 개**다. `prd`, `production-eu`, `live`, `prod-apac` 같은 이름을 쓰는 fork는 이 검사를 통과하고, `filesystem-local-dev`가 production에서 조용히 선택된다 — 그 provider는 README가 "R1-only development provider"라고 적은 것이다. 실패는 startup이 아니라 데이터가 로컬 디스크에 쌓인 뒤에 드러난다.
|
|
|
|
## 기록하는 세 이유
|
|
|
|
(a) CLAUDE.md가 금지 항목으로 명시했고 (b) 강제 수단이 두 문자열이며 (c) fork가 프로파일 이름을 바꾸는 것은 평범한 일이다. 수정은 production 판별을 명시적 설정(예: `app.object-storage.allow-local-dev=true`를 요구)으로 뒤집는 것 — 이름이 아니라 의도를 묻는 형태다. P3.
|
|
|
|
## 확인하지 못한 것
|
|
|
|
목록 밖 이름의 프로파일로 실제로 띄워 개발용 제공자가 선택되는지 재현하지 않았다. 조건식상 그 결과가 나온다.
|
|
|
|
<!-- body:end -->
|