pve9-repo-fix/cleanup-test-data.sh
Claude ae1782a6de fix: P001, P002 약국 보호 로직 추가
문제:
- cleanup 스크립트가 P0003 이후 삭제 시 P001, P002도 함께 삭제됨
- 문자열 비교 'P001' >= 'P0003'이 true로 평가됨

원인:
- SQLite 문자열 비교에서 'P001' < 'P0003'이지만
- 'P002' >= 'P0003'은 false인데, 기존 조건이 잘못됨

해결:
- LENGTH(pharmacy_code) = 5 조건 추가
- P0003 <= pharmacy_code <= P9999 범위 명시
- P001, P002 (4자), P0001, P0002 (5자) 모두 보호

변경 파일:
- cleanup-test-data.sh: 삭제 쿼리 수정
- CLEANUP_TEST_DATA.md: 문서 업데이트

보호되는 약국:
- P001: default 약국 (4자)
- P002: 새서울약국 (4자)
- P0002: 청춘약국 (5자, 범위 밖)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-14 10:53:59 +00:00

259 lines
7.7 KiB
Bash
Executable File

#!/bin/bash
# ================================
# 테스트 데이터 정리 스크립트
# ================================
#
# 용도: headscale 자동 등록 테스트 후 생성된 데이터 정리
# - farmq.db: P0003 이후 약국 삭제
# - gateway.db: ID 5 이후 사용자 삭제
# - Headscale: 테스트 노드 삭제 (선택)
#
set -e
# ================================
# 색상 정의
# ================================
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
CYAN='\033[0;36m'
WHITE='\033[1;37m'
NC='\033[0m' # No Color
# ================================
# 헤더 출력
# ================================
print_header() {
echo -e "${CYAN}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${NC}"
echo -e "${WHITE}$1${NC}"
echo -e "${CYAN}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${NC}"
}
# ================================
# 1. farmq.db 테스트 약국 삭제
# ================================
cleanup_farmq_db() {
print_header "1. farmq.db 테스트 약국 정리"
FARMQ_DB="/srv/headscale-tailscale-replacement/farmq-admin/farmq.db"
if [ ! -f "$FARMQ_DB" ]; then
echo -e "${RED}✗ farmq.db를 찾을 수 없습니다: $FARMQ_DB${NC}"
return 1
fi
echo -e "${BLUE}현재 약국 목록:${NC}"
python3 << EOF
import sqlite3
conn = sqlite3.connect('$FARMQ_DB')
cursor = conn.cursor()
cursor.execute('SELECT pharmacy_code, pharmacy_name, tailscale_ip FROM pharmacies ORDER BY pharmacy_code')
for row in cursor.fetchall():
print(f' {row[0]}: {row[1]} - {row[2]}')
conn.close()
EOF
echo -e "\n${YELLOW}P0003 이후 약국을 삭제하시겠습니까? (y/N)${NC}"
read -p "> " -r response </dev/tty
if [[ "$response" =~ ^[Yy]$ ]]; then
python3 << EOF
import sqlite3
conn = sqlite3.connect('$FARMQ_DB')
cursor = conn.cursor()
# P0003~P9999만 삭제 (P001, P002, P0001, P0002는 보호)
cursor.execute("DELETE FROM pharmacies WHERE pharmacy_code >= 'P0003' AND pharmacy_code <= 'P9999' AND LENGTH(pharmacy_code) = 5")
deleted_count = cursor.rowcount
conn.commit()
conn.close()
print(f'✓ {deleted_count}개 약국 삭제 완료')
EOF
echo -e "\n${GREEN}남은 약국 목록:${NC}"
python3 << EOF
import sqlite3
conn = sqlite3.connect('$FARMQ_DB')
cursor = conn.cursor()
cursor.execute('SELECT pharmacy_code, pharmacy_name, tailscale_ip FROM pharmacies ORDER BY pharmacy_code')
for row in cursor.fetchall():
print(f' {row[0]}: {row[1]} - {row[2]}')
conn.close()
EOF
else
echo -e "${YELLOW}건너뜀${NC}"
fi
}
# ================================
# 2. gateway.db 테스트 사용자 삭제
# ================================
cleanup_gateway_db() {
print_header "2. gateway.db 테스트 사용자 정리"
GATEWAY_DB="/srv/pharmq-gateway/gateway.db"
if [ ! -f "$GATEWAY_DB" ]; then
echo -e "${RED}✗ gateway.db를 찾을 수 없습니다: $GATEWAY_DB${NC}"
return 1
fi
echo -e "${BLUE}현재 사용자 목록:${NC}"
python3 << EOF
import sqlite3
conn = sqlite3.connect('$GATEWAY_DB')
cursor = conn.cursor()
cursor.execute('SELECT id, username, name, primary_pharmacy_code FROM users ORDER BY id')
for row in cursor.fetchall():
print(f' ID {row[0]}: {row[1]} ({row[2]}) - {row[3]}')
conn.close()
EOF
echo -e "\n${YELLOW}ID 5 이후 사용자를 삭제하시겠습니까? (y/N)${NC}"
read -p "> " -r response </dev/tty
if [[ "$response" =~ ^[Yy]$ ]]; then
python3 << EOF
import sqlite3
conn = sqlite3.connect('$GATEWAY_DB')
cursor = conn.cursor()
cursor.execute('DELETE FROM pharmacy_members WHERE user_id >= 5')
cursor.execute('DELETE FROM users WHERE id >= 5')
deleted_count = cursor.rowcount
conn.commit()
conn.close()
print(f'✓ {deleted_count}명 사용자 삭제 완료')
EOF
echo -e "\n${GREEN}남은 사용자 목록:${NC}"
python3 << EOF
import sqlite3
conn = sqlite3.connect('$GATEWAY_DB')
cursor = conn.cursor()
cursor.execute('SELECT id, username, name, primary_pharmacy_code FROM users ORDER BY id')
for row in cursor.fetchall():
print(f' ID {row[0]}: {row[1]} ({row[2]}) - {row[3]}')
conn.close()
EOF
else
echo -e "${YELLOW}건너뜀${NC}"
fi
}
# ================================
# 3. Headscale 테스트 노드 삭제
# ================================
cleanup_headscale_nodes() {
print_header "3. Headscale 테스트 노드 정리"
# Docker 컨테이너 확인
if ! docker ps | grep -q headscale; then
echo -e "${RED}✗ Headscale 컨테이너를 찾을 수 없습니다${NC}"
return 1
fi
echo -e "${BLUE}현재 노드 목록:${NC}"
docker exec headscale headscale nodes list
echo -e "\n${YELLOW}삭제할 노드 ID를 입력하세요 (공백으로 구분, Enter로 건너뛰기):${NC}"
echo -e "${YELLOW}예: 13 14 15 16${NC}"
read -p "> " -r node_ids </dev/tty
if [ -z "$node_ids" ]; then
echo -e "${YELLOW}건너뜀${NC}"
return 0
fi
echo -e "\n${BLUE}노드 삭제 중...${NC}"
for id in $node_ids; do
if docker exec headscale headscale nodes delete --identifier "$id" --force 2>/dev/null; then
echo -e "${GREEN}✓ Node ID $id 삭제 완료${NC}"
else
echo -e "${RED}✗ Node ID $id 삭제 실패${NC}"
fi
done
echo -e "\n${GREEN}남은 노드 목록:${NC}"
docker exec headscale headscale nodes list
}
# ================================
# 4. 백업 생성
# ================================
create_backup() {
print_header "백업 생성 (선택)"
echo -e "${YELLOW}데이터베이스 백업을 생성하시겠습니까? (y/N)${NC}"
read -p "> " -r response </dev/tty
if [[ "$response" =~ ^[Yy]$ ]]; then
TIMESTAMP=$(date +%Y%m%d_%H%M%S)
# farmq.db 백업
if [ -f "/srv/headscale-tailscale-replacement/farmq-admin/farmq.db" ]; then
cp /srv/headscale-tailscale-replacement/farmq-admin/farmq.db \
/srv/headscale-tailscale-replacement/farmq-admin/farmq.db.backup_$TIMESTAMP
echo -e "${GREEN}✓ farmq.db 백업 생성: farmq.db.backup_$TIMESTAMP${NC}"
fi
# gateway.db 백업
if [ -f "/srv/pharmq-gateway/gateway.db" ]; then
cp /srv/pharmq-gateway/gateway.db \
/srv/pharmq-gateway/gateway.db.backup_$TIMESTAMP
echo -e "${GREEN}✓ gateway.db 백업 생성: gateway.db.backup_$TIMESTAMP${NC}"
fi
else
echo -e "${YELLOW}백업 건너뜀${NC}"
fi
}
# ================================
# 메인 함수
# ================================
main() {
print_header "팜큐(FARMQ) 테스트 데이터 정리"
echo -e "${CYAN}이 스크립트는 다음 작업을 수행합니다:${NC}"
echo -e " 1. farmq.db에서 P0003 이후 약국 삭제"
echo -e " 2. gateway.db에서 ID 5 이후 사용자 삭제"
echo -e " 3. Headscale 테스트 노드 삭제 (선택)"
echo ""
echo -e "${YELLOW}⚠ 주의: 운영 데이터는 삭제되지 않습니다${NC}"
echo -e " - 보호되는 약국: P001, P002, P0002"
echo -e " - 보호되는 사용자: ID 1~4"
echo ""
read -p "계속하시겠습니까? (y/N) " -r response </dev/tty
if [[ ! "$response" =~ ^[Yy]$ ]]; then
echo -e "${YELLOW}취소되었습니다${NC}"
exit 0
fi
# 백업 생성 (선택)
create_backup
echo ""
# 1. farmq.db 정리
cleanup_farmq_db
echo ""
# 2. gateway.db 정리
cleanup_gateway_db
echo ""
# 3. Headscale 노드 정리
cleanup_headscale_nodes
echo ""
print_header "정리 완료!"
echo -e "${GREEN}모든 작업이 완료되었습니다.${NC}"
}
# 스크립트 실행
main "$@"