# 유령 데몬 사건 – 완전 메뉴얼 (실체 규명 · 대응 · 설계 원칙)

작성일: 2026-01-03 05:52:46 (Asia/Seoul)

---

## 0. 이 문서의 목적 (중요)

이 문서는 **메모가 아니다**.  
이번 “유령 데몬 사건”의 **전 과정, 판단, 실체 규명, 최종 설계 결론**을
다음에도 **다시 헷갈리지 않기 위해** 남기는 **운영 메뉴얼**이다.

- 감정/추측/기억에 의존하지 않는다
- 증거 기반 판단만 기록한다
- 다음에 같은 일이 발생하면 **이 문서 그대로 따라 하면 끝나게** 한다

---

## 1. 사건 요약 (한 문장)

> 데몬이 죽지 않는 문제가 아니라,  
> **유저 세션(pmaadmin)이 지속적으로 데몬을 재생성하고 있었다.**

---

## 2. 처음 나타난 현상

- daemon_upbit_Ticker 테이블에 데이터가 계속 쌓임
- 페이지/파일을 죽여도 계속 들어오는 것처럼 보임
- 데몬을 kill 해도 다시 살아나는 현상 발생
- “유령 데몬”, “죽지 않는 데몬”으로 인식됨

---

## 3. 잘못된 가설들 (이전에 했던 뻘짓 정리)

### ❌ 가설 1: DB 이벤트(event_scheduler)가 범인
- event_scheduler는 ON이었지만
- 실제 EVENTS는 비어 있었음
→ 범인 아님

### ❌ 가설 2: 데몬 프로세스가 혼자 살아 있음
- 데몬을 kill 해도 다시 생김
- 파일을 수정해도 영향 없음
→ 데몬은 원인이 아니라 **결과물**

### ❌ 가설 3: 파일에 exit 넣으면 데몬이 멈춘다
- 파일 정지는 **미래 실행 차단**
- 이미 떠 있는 데몬에는 영향 없음
→ 개념 혼동

---

## 4. 결정적 전환점 (실체 규명)

### 핵심 질문
> “누가 실제로 DB에 INSERT를 치고 있는가?”

### 사용한 방법
```sql
SHOW FULL PROCESSLIST;
```

- 1~2초 간격
- 최소 10~20회 연속 실행

### 드디어 포착된 증거

- User: **pmaadmin**
- Host: localhost
- Command: Query
- State: Commit / Updating status
- Info: `INSERT INTO daemon_upbit_Ticker (...)`

👉 **진범 확정**

---

## 5. 최종 실체 규명 (결론)

### ✔ 진범
- **유저 세션 (웹 계층)**
- DB 계정: **pmaadmin**
- php / phpMyAdmin / 웹 요청을 통해
- 매우 짧게 INSERT → COMMIT → 종료

### ✔ 데몬의 정체
- 데몬은 **유령**
- 스스로 존재하지 않음
- **명령자가 살려내는 결과물**

---

## 6. 왜 계속 안 잡혔는가

- INSERT가 매우 짧게 실행됨
- SHOW PROCESSLIST 한두 번으로는 포착 불가
- 연속 캡처해야만 보임

→ “없는 것처럼 보였다”는 착각 발생

---

## 7. 왜 데몬만 죽이면 안 됐는가

- 데몬을 죽이면
- 명령자(유저 세션)가 다시 실행
- 새로운 PID로 다시 태어남

즉,

> **데몬을 못 죽인 게 아니라  
> 죽여도 계속 다시 만들어졌던 것**

---

## 8. 정답 구조 (이번에 확정된 원칙)

### 1️⃣ 데몬은 관리 대상이 아니다
- 쫓아다닐 필요 없음
- 결과물일 뿐

### 2️⃣ 명령자가 핵심 통제 대상
- 실행 / 중지 / 재생성의 주체

### 3️⃣ 파일 레벨 제어가 가장 강력
- 파일이 곧 실행 여부
- 파일이 곧 신분증

---

## 9. 파일 중지 가드의 의미 (중요)

```php
<?php
// DAEMON EXECUTION BLOCKED
exit;
```

- 이 코드는:
  - **미래 실행을 100% 차단**
  - 명령자가 계속 호출해도 즉시 종료
  - CPU 사용 거의 0
- 단:
  - 이미 떠 있는 데몬은 **별도 사살 필요**

---

## 10. 데몬 사살과 재발 방지의 정답 순서

1. **파일 무력화 (중지 가드 삽입 or 파일명 변경)**
2. **이미 떠 있는 데몬 1회 사살**
3. 이후 감시만 하면 됨

---

## 11. 유령을 다루는 최종 설계 (가장 중요)

### 고유 ID 전략

- **파일명이 곧 고유 ID**
- 확장자 제거한 현재 파일명 사용

```php
$DAEMON_ID = pathinfo(__FILE__, PATHINFO_FILENAME);
```

---

## 12. 왜 “명령자에게 유령을 죽이라”가 불가능한가

- 명령자는:
  - 유령을 **만들 줄만 알지**
  - PID를 기억하거나 관리하지 않음
- 그래서:
  - “이 유령 죽여라”라는 명령 자체가 성립하지 않음

→ **다시 못 만들게 하는 게 정답**

---

## 13. 최종 운영 원칙 (고정)

1. 데몬은 태어나지 못하게 한다
2. 이미 태어난 건 한 번만 죽인다
3. 모든 제어는 PHP 파일로 한다
4. 유저 세션은 실행만 하고 판단하지 않는다
5. 파일명이 곧 고유 ID다

---

## 14. 이 문서의 의미

이 문서는:
- 추측의 기록 ❌
- 감정의 기록 ❌
- **실체 규명과 정답 설계의 기록 ⭕**

다음에 같은 증상이 오면:
> **이 문서 1번부터 그대로 따라 하면 끝**

---

끝.
