feat(pipeline): keycloak-session-store 25편·virtualization 59편을 S3→S5→S6 으로 돌린다
기록 84편을 계약 에이전트로 다시 썼다. 기존 71편(kss 25 · virt 46)과, 계약에만 있고 안 쓰여 있던 새 글감 13편이다. 원장 84개를 열어 단계마다 스킬 영수증과 관문 종료 코드를 적었고 verify-pipeline-run.py 가 error 0 으로 닫는다. SSOT 결함 둘을 고쳤다. - kss 의 `약 58일` 이 반입 중 `약 59일` 로 바뀌어 있었다. 원 증거 파일이 「남은 일수: 88일 … 실제 갱신까지 약 58일」로 산수를 직접 적는다. D-4a 쪽 `약 59일` 은 강제 갱신 뒤(`VALID: 89 days`)라 맞는 값이라 그대로 뒀다. - virt §198 의 `11.6GB` 는 §178 의 원 측정 `Mem: 11648`(MiB)과 어긋나는데 원 가이드의 표기 그대로라 고치지 않고 쓰이는 자리에 대조를 적었다. 기록의 수치 오류 셋을 고쳤다 — CASE 요약의 「게스트 셋에 8240MB」(5120+3120 은 둘이다), k3s 편이 같은 것을 여섯·일곱·여덟로 세던 것, no-docker 편의 「셋을 더 든다」(§281 의 표는 네 행이고 디스크 행이 빠져 있었다). 계약을 셋 고쳤다. - kss 의 sourceRepository 리비전이 cdac9b8 이었는데 그 커밋에는 docs/guides/** 28개가 아예 없다. 9465582b 로 바꾸고, 반입한 바이트가 어느 커밋과도 같지 않다는 것을 측정값과 함께 적었다 — 반입은 커밋이 아니라 그 시점의 작업 트리에서 떠 온 것이다(kss 297/306 · virt 12/14 가 작업 트리와 같고, 200 커밋을 거슬러 전수 대조했을 때 가장 가까운 커밋도 28개가 어긋났다). - virt 계약이 「2026-09-11 재배분」이라고 적는데 SSOT 는 재배분 날짜를 적지 않고 재배분 뒤 값은 이미 2026-09-10 측정에 찍혀 있다. - kss 후보 대장이 지나친 절 아홉에 처분을 적었다(warn 9 → 0). 새 글감은 0건이고 넷은 앵커가 h3 슬러그의 접두가 아니라 중간 토막이라 검사기가 못 본 것이었다. style_profile.mjs 의 결함 둘을 고쳤다 — frontmatter 가 문장으로 세어져 (실측 398자짜리 「문장」 하나) 평균 길이를 기준 안으로 밀어 올리고 있었고, engPerSent 의 분자는 목록을 포함한 글에서, 분모는 목록을 걷어낸 글에서 세고 있었다(Question 기록에서 11.94 → 3.86). verify-pipeline.py 전 항목 PASS · error 0 · unittest 334건 OK. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5
parent
d473609e0a
commit
2109f726fe
+98
@@ -0,0 +1,98 @@
|
||||
---
|
||||
kind: REFERENCE
|
||||
slug: a-config-file-does-not-mean-the-same-thing-on-two-distros
|
||||
title: 같은 설정 파일이 두 배포판에서 같은 뜻이 아니다 — 옮기기 전에 세 가지를 본다
|
||||
topic: lab-environment-build
|
||||
topicName: 실험대 환경 구성
|
||||
project: virtualization
|
||||
status: 게시 전
|
||||
sourceRevision: 9465582b5d1630eb4ae7c4e078021486919bf6b6
|
||||
source:
|
||||
- final/document.md#203-실측으로-드러난-함정-셋
|
||||
- final/document.md#284-nginx-설정-구조-sites-available-은-nginx-기능이-아니다
|
||||
- final/document.md#288-게스트-배포판-debian이란-무엇이고-ubuntu와-무엇이-다른가
|
||||
- final/document.md#286-패키지명-대응표
|
||||
- final/document.md#287-없어서-오히려-편한-것
|
||||
- final/document.md#285-롤링-릴리스와-부분-업그레이드-금지
|
||||
- final/document.md#212-"이건-arch라서-하는-건가-"에-대한-답
|
||||
- final/document.md#209-nginx-keycloak-lab-conf-스티키-스위치와-신뢰-경계
|
||||
---
|
||||
|
||||
# 같은 설정 파일이 두 배포판에서 같은 뜻이 아니다 — 옮기기 전에 세 가지를 본다
|
||||
|
||||
설정 파일을 배포판이 다른 기계로 옮기기 전에 셋을 본다. 그 지시어가 대상의 판올림에 있는가, 패키지가 기본으로 켜 둔 것과 충돌하지 않는가, 그 배포판이 그 관례를 갖고 있는가. 이 실험대의 함정 셋이 전부 여기 걸렸다.
|
||||
|
||||
## 관계
|
||||
|
||||
- **단계별 구축 문서는 작성 시점이 아니라 실행 순서로 검증한다**
|
||||
그 기준은 순서와 위치를 보고 이 기준은 대상 기계를 본다. 그 기록이 자기 예외 절에서 배포판 차이를 이쪽으로 넘긴다.
|
||||
- **엣지 게스트에 nginx 를 세우고 호스트 DNAT 으로 밖에서 들어오는 길을 연다**
|
||||
Arch 호스트에서 쓰던 nginx 설정이 Debian 12 게스트로 건너가는 절차가 그 기록에 있다.
|
||||
- **cloud-init 시드로 게스트 세 대를 만들고 SSH 가 키로 붙게 한다**
|
||||
부트 시점 설정이 게스트 판올림의 검사기를 통과해야 하는 대목이 그 절차 안에 있다.
|
||||
- **cloud-init 이 안 도는 원인은 넷인데 증상은 「SSH 가 안 붙는다」 하나였다**
|
||||
원인이 옮긴 파일 안에 없을 때 증상이 어떻게 보이는지를 그 기록이 보여 준다.
|
||||
- **가까운 층부터 한 층씩 건너뛰며 확인한다 — 층마다 성공 신호가 다르다**
|
||||
증상이 난 층부터 좁혀 오는 절차이고, 이 기준은 그 층에 닿은 뒤 파일을 의심할지 기계를 의심할지를 가른다.
|
||||
|
||||
## 목적
|
||||
|
||||
이 기준이 막는 것은 원인이 파일 안에 없는 두 증상이다. 하나는 설정 전체가 뜨지 않는 것이고, 다른 하나는 파일을 제자리에 놓았는데 아무 일도 일어나지 않는 것이다. 둘 다 파일을 아무리 읽어도 나오지 않는다.
|
||||
|
||||
§203 이 실측으로 드러난 함정 셋을 적었는데 셋 다 배포판 차이였다. 이 실험대는 호스트가 Arch(nginx 1.30.4)이고 엣지 게스트가 Debian 12(nginx 1.22.1)라 같은 설정이 두 판올림 사이를 오갔다.
|
||||
|
||||
## 규칙
|
||||
|
||||
### 1. 그 지시어가 대상의 판올림에 있는가
|
||||
|
||||
`http2 on;` 은 nginx 1.25.1 이상이다. Arch 에서 쓰던 설정을 Debian 12 게스트로 그대로 옮기면 `unknown directive "http2"` 가 나면서 설정 전체가 죽는다.
|
||||
|
||||
없다는 것을 확인하는 데서 멈추면 규칙이 답을 내지 않는다. 양쪽에서 도는 형태가 무엇인지까지 찾는다. `listen 443 ssl http2;` 형태는 1.22 와 1.30 양쪽에서 다 돈다.
|
||||
|
||||
설정 정본 `deploy/lab/edge/nginx-keycloak-lab.conf` 의 주석이 그 형태를 고른 까닭을 파일 안에 적어 두었다. 따로 떼어 쓰는 지시어 쪽은 nginx 1.25.1 이상을 요구하는데 엣지 게스트는 nginx 1.22 를 쓰는 Debian 12 다. `listen` 의 인자로 쓰는 형태는 양쪽에서 다 돌고, 이 실험대가 실제로 돌리는 것도 그쪽이다.
|
||||
|
||||
### 2. 패키지가 기본으로 켜 둔 것과 충돌하지 않는가
|
||||
|
||||
Debian 계열은 `/etc/nginx/sites-enabled/default` 가 처음부터 붙어 있고 `:80` 에 `default_server` 로 선언돼 있어서, 실험대 설정의 `listen 80 default_server` 와 충돌한다. 심볼릭 링크를 걸 때 그 기본 사이트를 같이 지운다.
|
||||
|
||||
### 3. 그 배포판이 그 관례를 갖고 있는가
|
||||
|
||||
`sites-available` 과 `sites-enabled` 는 nginx 의 기능이 아니라 Debian/Ubuntu 패키지 메인테이너가 만든 관례다. nginx 가 아는 것은 `include` 지시어 하나뿐이고 나머지는 패키지가 미리 깔아 둔 디렉터리 구조다.
|
||||
|
||||
Arch 는 `/etc/nginx/nginx.conf` 한 파일이 전부이고 include 줄도 없다. `http { }` 안에 `include /etc/nginx/sites-enabled/*;` 를 직접 넣어야 이 파일이 효력을 갖는다. 넣지 않으면 아무 일도 일어나지 않고 오류조차 나지 않는다. 최종 병합된 설정에 내 파일이 들어갔는지는 `nginx -T` 로 확인한다.
|
||||
|
||||
2번과 3번은 같은 관례의 양면이다. 한쪽은 있어서 충돌하고 한쪽은 없어서 손으로 넣어야 한다.
|
||||
|
||||
## 적용 조건
|
||||
|
||||
한 기계에서 쓰던 설정 파일을 다른 배포판이나 다른 판올림의 기계로 옮기는 모든 곳에 적용한다. 이 실험대에서는 호스트 Arch 와 게스트 Debian 12 사이, 그리고 운영과 실험대 사이다.
|
||||
|
||||
특히 자주 걸리는 것 : 데몬 설정(nginx · systemd 유닛)과 부트 시점 설정(cloud-init)
|
||||
|
||||
이 기준은 파일을 옮길 때 한 번 도는 검사이지 막히는 것마다 꺼내 드는 설명이 아니다. §212 가 적었듯 낯선 것의 대부분은 배포판 때문이 아니다. 클라우드가 대신 해 주던 일(KVM · libvirt · cloud-init · DHCP 예약)과 이미 누가 해 두었던 일(nginx upstream · certbot · k3s 설치)이 대부분이고, 진짜 배포판 고유는 얼마 되지 않는다 — 이 실험대에서는 `conf.d` include 부재, 롤링 업그레이드, `libvirtd.socket`, 패키지명이다.
|
||||
|
||||
같은 구성을 Ubuntu 에서 해도 가상화와 네트워크 층은 명령 이름만 조금 바뀐다.
|
||||
|
||||
## 예외
|
||||
|
||||
같은 계열 안에서도 판올림이 다르면 1번이 그대로 걸린다. Debian 과 Ubuntu 는 `apt` 와 `dpkg` 와 systemd 와 디렉터리 구조가 같은 계열인데 패키지 판올림이 달라서다.
|
||||
|
||||
배포판이 같으면 안 걸리는 것도 아니다. Arch 는 롤링 릴리스이고 부분 업그레이드를 지원하지 않아서, `pacman -Sy 패키지` 로 DB 만 갱신하고 일부만 설치하면 같은 기계 안에서도 공유 라이브러리 판이 어긋난다.
|
||||
|
||||
순서와 위치 문제는 이 축에서 안 잡힌다. 「단계별 구축 문서는 작성 시점이 아니라 실행 순서로 검증한다」가 그쪽을 맡고, 그 기록이 자기 예외 절에서 이쪽을 가리킨다. 두 기준이 서로의 사각을 덮는다.
|
||||
|
||||
1번은 문서로 판올림을 대조해 예측할 수 있다. 2번과 3번은 그 배포판에 실제로 깔아 봐야 드러난다 — 기본으로 붙어 있는 사이트가 무엇인지와 그 배포판이 어떤 include 관례를 갖는지는 패키지 메인테이너가 정한다.
|
||||
|
||||
배포판 차이가 아닌 것을 이 기준으로 설명하지 않는다. SELinux 와 AppArmor 가 Arch 에 기본 활성이 아닌 것은 이 기준이 잡는 종류이지만, RHEL 계열에서 k3s 에 정책 패키지가 필요한 것은 옮긴 설정의 문제가 아니라 그 배포판의 보안 모듈 문제다.
|
||||
|
||||
## 예시
|
||||
|
||||
`http2 on;` 을 쓴 설정을 Debian 12 의 nginx 1.22.1 로 옮기자 `unknown directive "http2"` 로 설정 검사가 실패했다.
|
||||
|
||||
Debian 기본 사이트를 지우지 않은 채 실험대 설정을 켜자 `:80` 의 `default_server` 가 두 번 선언됐다.
|
||||
|
||||
Arch 에 `sites-enabled` 디렉터리를 만들어 파일을 넣었는데 `include` 줄이 없어 오류 없이 무시됐다.
|
||||
|
||||
게스트의 cloud-init 22.4.2 스키마 검사기가 `sudo` 를 리스트로 적은 형태를 거부했다. 어느 키가 걸렸는지는 알려 주지 않고 `users.0` 블록을 통째로 찍은 뒤 어느 스키마에도 안 맞는다고만 한다. 그 형태로도 부팅은 됐고 NOPASSWD sudo 도 멀쩡히 돌았다.
|
||||
|
||||
certbot DNS 플러그인의 패키지 이름이 Arch 에서 `certbot-dns-cloudflare` 이고 Debian/Ubuntu 에서 `python3-certbot-dns-cloudflare` 다.
|
||||
+85
@@ -0,0 +1,85 @@
|
||||
---
|
||||
kind: REFERENCE
|
||||
slug: verify-a-build-guide-in-execution-order
|
||||
title: 단계별 구축 문서는 작성 시점이 아니라 실행 순서로 검증한다
|
||||
topic: lab-environment-build
|
||||
topicName: 실험대 환경 구성
|
||||
project: virtualization
|
||||
status: 게시 전
|
||||
sourceRevision: 9465582b5d1630eb4ae7c4e078021486919bf6b6
|
||||
source:
|
||||
- final/document.md#182-이-구축에서-드러난-문서-결함의-공통-원인
|
||||
- final/document.md#178-이-부의-출처와-범위
|
||||
---
|
||||
|
||||
# 단계별 구축 문서는 작성 시점이 아니라 실행 순서로 검증한다
|
||||
|
||||
구축 가이드는 1단계의 환경에서 시작해 실행 순서로 검증한다. 단계마다 그 시점에 리소스가 이미 있는지와 그 명령을 어느 기계에서 치는지를 따로 본다. 기반 7단계 가이드를 순서대로 따라가자 결함 여섯이 나왔고, 틀린 명령은 하나도 없었다.
|
||||
|
||||
## 관계
|
||||
|
||||
- **엣지 nginx 를 호스트에서 게스트 VM 으로 옮긴다 — 성능이 아니라 더러워지는 층의 격리**
|
||||
이 기준이 검증하라는 가이드가 그 결정을 실제로 실행한 문서다. 결함 여섯 가운데 셋은 그 이동이 새로 요구한 일곱 가지와 같은 것을 다루는데, nginx 설치와 nginx 버전 차이와 인증서 경로다.
|
||||
- **호스트 안에서는 404, 밖에서는 connection refused — 앞 체인의 accept 가 libvirt 의 reject 를 막지 못했다**
|
||||
같은 connection refused 라도 04 단계의 결함은 명령을 칠 셸이 틀려서 났고, 그 기록의 거절은 libvirt 방화벽이 냈다. 어느 셸에서 쳤는지로 좁힌 뒤에도 안 풀리는 막힘을 그 기록이 받는다.
|
||||
- **WiFi 전용 호스트에서 대용량 qcow2 를 옮기는 데 실제로 몇 시간이 걸리는가**
|
||||
그 물음의 답이 이 검증을 선택으로 둘지 전제로 둘지를 가른다. 파일을 옮기는 것보다 가이드를 다시 도는 편이 빠르다고 나오면, 이 실험대는 문서로만 복원된다.
|
||||
|
||||
## 목적
|
||||
|
||||
이 기준이 막는 것은 각 줄이 참인데 순서대로는 못 따라가는 문서다. §182 이 든 여섯 결함에서 틀린 명령은 하나도 없었고 전부 실제로 돌았던 것이다. 다만 구축이 끝난 뒤의 환경에서 확인한 출력이 앞 단계에 적혀 있었다. §178 은 이 여섯이 실린 부의 범위를 구축에서 실제로 막힌 지점으로만 그었고, 막히지 않은 단계는 가이드에 있으니 여기서 반복하지 않는다고 적었다. 그래서 여섯은 가이드를 검토해 골라낸 것이 아니라, 그 단계까지 실제로 따라가다 막혀서 드러났다.
|
||||
|
||||
03 단계에서 /etc/nginx: No such file or directory 가 난 것은 설정 블록이 틀려서가 아니라 그 시점에 nginx 가 아직 깔려 있지 않아서다. 둘 중 어느 쪽인지는 문서를 읽어서는 알 수 없고 실제로 돌려 봐야 드러난다.
|
||||
|
||||
§182 은 검사할 것도 시점과 셸 둘로 갈라 적었다. 하나로 뭉뚱그리면 막힌 단계에서 무엇을 고쳐야 하는지가 안 나오기 때문이다.
|
||||
|
||||
## 규칙
|
||||
|
||||
### 1. 검증 순서를 문서 작성 순서가 아니라 실행 순서에 맞춘다
|
||||
|
||||
문서를 쓴 사람은 구축이 끝난 환경에 있고 읽는 사람은 아무것도 없는 환경에서 1단계부터 시작하니, 검증도 1단계의 환경에서 시작한다.
|
||||
|
||||
### 2. 단계마다 그 시점에 리소스가 이미 존재하는지 따로 본다
|
||||
|
||||
여섯 중 셋이 여기서 깨졌다. 03 단계는 nginx 설치 단계가 없어 /etc/nginx: No such file or directory 로 막혔다. 00·03·05·06 단계는 저장소가 lab host 에 있다고 가정해 cp: cannot stat 'deploy/...' 로 막혔다. 05 단계는 BFF 가 한참 뒤에 뜨는데도 그 시점에 -l app=bff 로 리소스를 조회했다.
|
||||
|
||||
셋 모두 문서를 읽을 때는 보이지 않는다. 설치 명령이 빠졌다는 것도 파일이 그 기계에 없다는 것도 그 단계까지 실제로 와 봐야 드러나기 때문이다.
|
||||
|
||||
### 3. 단계마다 그 명령을 어느 기계에서 치는지 문서가 말하게 한다
|
||||
|
||||
04 단계의 확인 명령이 여기서 깨졌다. 게스트에는 Tailscale 이 없기 때문에 엣지 VM 안에서 tailnet 주소를 치면 connection refused 가 돌아온다. 명령 자체는 맞고 칠 위치가 틀렸다.
|
||||
|
||||
§178 의 구성에서 호스트는 Arch Linux 이고 게스트는 Debian 12 genericcloud 세 대다. 문서가 주체를 적지 않으면 읽는 사람은 직전 단계에서 쓰던 셸에 그대로 친다.
|
||||
|
||||
### 4. 나중 시점의 환경에서 확인한 명령과 출력을 앞 단계로 옮겨 적지 않는다
|
||||
|
||||
§182 이 여섯의 공통 원인으로 든 것이 이 하나다. 구축이 끝난 환경에서는 리소스가 전부 서 있고 저장소도 제 기계에 있으니 어떤 확인 명령이든 돈다. 그 출력을 앞 단계에 붙이면 문서의 각 줄은 참이 되고, 순서대로 따라가는 사람만 막힌다. 그래서 이 결함은 문서를 검토해서는 안 나오고 실행해야 나온다. §182 은 결함 여섯에는 observed 를, 이 공통 원인 하나에는 inferred 를 붙였다. 여섯은 따라가다 본 것이고, 그것을 한 원인으로 묶은 것은 여섯을 놓고 내린 판단이다.
|
||||
|
||||
## 적용 조건
|
||||
|
||||
- 사람이 한 단계씩 따라 실행하도록 쓴 구축·운영 문서
|
||||
- 앞 단계의 결과 위에 뒤 단계가 서는 문서. 기반 7단계 가이드가 그런 문서다
|
||||
- 명령을 칠 기계가 둘 이상인 문서. 호스트와 게스트가 갈리면 어느 셸에서 치는지를 따로 본다
|
||||
- 단계가 하나 끼어들거나 대상 환경이 바뀐 뒤
|
||||
|
||||
## 예외
|
||||
|
||||
이 기준이 잡는 것은 순서와 위치이고 명령의 정확성은 아니다. §182 이 적었듯 개별 명령은 전부 실제로 돌았던 것이라, 이 검사를 통과해도 오타나 잘못된 플래그나 낡은 옵션은 그대로 지나간다. 04 단계의 인증서 경로가 그런 경우다. 와일드카드로 받은 인증서 묶음의 이름(lineage)은 live/hyeonworks.com/ 인데 문서에는 live/auth.hyeonworks.com/ 이라 적혀 있었다. 단계 순서를 맞춰도 그 줄은 틀린 채다.
|
||||
|
||||
배포판 차이도 이 두 검사로는 안 잡힌다. 03 단계의 설정 블록에 있던 http2 on; 은 Debian 12 의 nginx 1.22 에서 unknown directive 가 됐다. 순서를 맞춰도 같은 오류가 나므로 대상 배포판에서 실제로 돌려야 드러난다.
|
||||
|
||||
한 번 통과한 문서가 계속 통과하지도 않는다. 단계가 하나 끼어들거나 환경이 바뀌면 같은 검사를 다시 돌린다.
|
||||
|
||||
이 저장소에는 이 기준으로 가이드를 고친 뒤 처음부터 다시 따라가 본 기록이 없다. 규칙은 결함 여섯의 공통 원인에서 나왔고, 규칙이 결함을 막아 냈다는 관측은 아직 얻지 못했다.
|
||||
|
||||
다시 따라가 보지 않은 데는 까닭이 있다. §184 는 가이드 자신도 읽기 전용 확인만 실제로 돌려 출력을 실었고 만드는 명령은 구축할 때 친 것을 그대로 옮겼다고 적었다. VM 을 다시 만들거나 k3s 를 다시 깔면 지금 돌고 있는 실험대가 없어지기 때문이다. 그래서 단계마다의 생성 명령은 「그때 이렇게 쳤다」까지이고, 지금 다시 쳐도 같은 상태가 되는지는 확인되지 않았다.
|
||||
|
||||
## 예시
|
||||
|
||||
- 03 단계 : nginx 설치 단계가 없어 /etc/nginx: No such file or directory
|
||||
- 03 단계 : 설정 블록이 http2 on; 이라 Debian 12 의 nginx 1.22 에서 unknown directive
|
||||
- 04 단계 : 인증서 경로가 lineage 이름과 다르다. 와일드카드는 live/hyeonworks.com/ 인데 live/auth.hyeonworks.com/ 이라 적혀 있었다
|
||||
- 00·03·05·06 단계 : 저장소가 lab host 에 있다고 가정해 cp: cannot stat 'deploy/...'
|
||||
- 05 단계 : 그 단계에 없는 리소스를 -l app=bff 로 조회. BFF 는 한참 뒤에 뜬다
|
||||
- 04 단계 : 확인 명령을 칠 위치가 틀렸다. 엣지 VM 안에서 tailnet 주소를 치면 connection refused
|
||||
- 고친 뒤 처음부터 다시 따라가 본 기록 : x
|
||||
Reference in New Issue
Block a user