가용성/2026년 10월 3일 09시 사고
10월 3일 9시 2분부터 18시 8분까지 페미위키 첫 주소(https://femiwiki.com/)를 열면 빈 화면만 보였고, 문서 이름의 대소문자나 밑줄을 고쳐 넘겨주는 주소도 빈 화면이 되었습니다. 웹 서버의 캐시 모듈이 본문 없는 응답을 내보내지 않게 바뀌었는데, MediaWiki가 다른 주소로 넘겨주는 응답이 본문 없는 응답이었습니다. 문서 주소로 바로 들어온 이용자는 영향을 받지 않았습니다. 캐시 모듈을 고쳐 18시 8분에 배포하여 복구되었습니다.
| 시각 | 일어난 일 |
|---|---|
| 08:39 | 캐시에 문서를 gzip으로 압축해 저장하는 캐시 모듈 변경이 병합됨[1] |
| 09:02 | 이 변경을 담은 웹 서버가 배포됨.[2] 이때부터 넘겨주기 응답이 빈 화면이 됨 |
| 11:01 | 다른 작업으로 /favicon.ico를 웹 서버가 직접 내주게 되어, 이 주소는 넘겨주기를 거치지 않게 됨[3]
|
| 17:20 | 여러 프록시 주소에서 첫 주소로 요청이 몰리기 시작함. 이 사고와는 원인이 다름 |
| 17:40대 | 몰린 요청을 살피던 중 첫 주소가 빈 화면인 것을 발견함 |
| 17:58 | 상태 없이 끝난 응답을 알리는 알림이 들어감[4] |
| 18:08 | 캐시 모듈을 고친 웹 서버가 배포됨.[5] 18시 8분 52초부터 첫 주소가 다시 301로 대문으로 넘어감 |
원인
웹 서버 앞의 캐시 모듈은 캐시할 수 있는 응답을 버퍼에 받아 두었다가, 캐시에 넣은 뒤 버퍼에서 상태 코드와 헤더, 본문을 꺼내 내보냅니다. 버퍼가 비어 있으면 응답을 이미 그대로 흘려보낸 것으로 보고 아무것도 하지 않고 돌아가는데,[6] 전에는 버퍼에 상태 코드와 헤더가 늘 함께 들어 있었으므로 캐시할 응답이 이 조건에 걸리는 일이 없었습니다. 9시 2분에 배포된 변경은 상태 코드와 헤더를 버퍼 밖에 따로 두게 했고,[7] 그 뒤로는 본문 없는 응답이 이 조건에 걸려 상태 코드도 쓰이지 않은 채 끝났습니다.
첫 주소 /에 MediaWiki는 본문 없이 Location: /w/페미위키:대문을 담은 301 응답을 돌려줍니다. 이 응답은 캐시할 수 있으므로 버퍼에 받아졌지만, 캐시에 넣기 전에 돌아갔으므로 캐시에도 남지 않아 첫 요청부터 매번 같은 일이 되풀이되었습니다. 브라우저는 301 대신 본문 없는 200을 받아 넘어가지 않고 빈 화면을 보였습니다. 문서 이름을 고쳐 넘겨주는 /w/와 index.php?title= 주소, 특수 문서의 넘겨주기도 같은 일을 겪었습니다.
웹 서버 접근 로그에는 이런 응답의 상태가 0으로 남았습니다. 9시 2분 전 12시간 동안은 요청 약 871,000건 가운데 상태 0이 한 건도 없었습니다. 9시 2분부터 17시 50분까지 상태 0으로 끝난 요청은 다음과 같습니다.
| 주소 | 건수 | 비고 |
|---|---|---|
/ |
7,329 | 대부분 17시 20분부터 몰린 요청. 그 전에는 시간당 50건에서 70건으로, 배포 전 시간당 301 응답 48건에서 113건과 비슷함 |
/favicon.ico |
1,943 | 11시 1분까지. 브라우저 탭에 아이콘이 보이지 않았을 뿐임 |
/w/, index.php?title= 꼴의 넘겨주기 |
1,153 | 문서 이름 고치기와 특수 문서 |
/favicon-192.png와 대문으로 넘겨주는 그 밖의 주소 |
약 520 | /favicon-192.png가 310건이고 나머지는 대부분 취약점 탐색 요청
|
| 최근 바뀜의 실시간 갱신 요청 | 285 | 원래 본문 없는 200이므로 이용자가 잃은 것은 없음 |
수치는 Grafana Cloud Loki의 Caddy 접근 로그에서 잰 것입니다.[8]
알림
Route 53 상태 확인은 /w/ 아래의 실제 문서를, Grafana의 확인은 api.php와 사이트맵을 요청하여 넘겨주기를 거치는 경우가 없어 알림은 울리지 않았습니다. Route 53 상태 확인은 2xx면 본문이 비어도 정상으로 보므로, /를 요청했더라도 알아채지 못했을 것입니다. 접근 로그로 사이트가 멈췄는지 보는 Grafana 알림은 2xx 응답만 세는데, 다른 문서가 계속 2xx로 나갔으므로 상태 0 응답이 늘어도 반응하지 않았습니다.
고친 것
- 캐시 모듈이 본문 없는 응답도 상태 코드와 헤더를 내보내게 했습니다. caddy-mwcache#166에서 고쳐 infra#1109로 18시 8분에 배포했고, 배포 뒤 첫 주소가 301로 대문에 넘어가는 것을 확인했습니다. 웹 서버를 바꾸고 실패한 요청은 없었습니다.
- 웹 서버가 상태 없이 끝낸 응답이 10분에 5건을 넘으면 운영팀에 알리는 알림을 넣었습니다. 사고 전 일주일 동안은 이런 응답이 한 건도 없었습니다. infra#1105에서 고쳐 17시 58분에 병합했습니다.
남은 문제
- 배포 전에 넘겨주기 응답을 확인하는 검사가 없어 이번 변경이 그대로 배포되었습니다. 이미지 시험에서 넘겨주기와 문서를 캐시를 거쳐 두 번씩 요청하는 검사는 docker-mediawiki#1285에서, 새 웹 서버로 요청을 옮기기 전에 확인하는 검사는 infra#1104에서 다룹니다.
- 첫 주소를 열어 문서 제목을 확인하는 감시가 없습니다. infra#1103에서 다룹니다.
출처
- ↑ https://github.com/femiwiki/caddy-mwcache/pull/164
- ↑ https://github.com/femiwiki/infra/pull/1069
- ↑ https://github.com/femiwiki/infra/pull/1086
- ↑ https://github.com/femiwiki/infra/pull/1105
- ↑ https://github.com/femiwiki/infra/pull/1109
- ↑ https://github.com/femiwiki/caddy-mwcache/blob/88764d100aa9c829c001d1c4c99ee40ff0c3ff93/mwcache.go#L238
- ↑ https://github.com/femiwiki/caddy-mwcache/blob/88764d100aa9c829c001d1c4c99ee40ff0c3ff93/mwcache.go#L209-L231
- ↑ https://github.com/femiwiki/caddy-mwcache/issues/165