파일시스템과 영구 스토리지 마운트
업데이트: 2026-10-08
일반적인 클라우드 PaaS(Heroku, Render)나 컨테이너 서비스(AWS ECS, Cloud Run)를 사용할 때 개발자들을 가장 당혹스럽게 만드는 문제는 **"서버가 재배포되거나 재부팅되면 로컬에 저장해 둔 SQLite 파일이나 수집 데이터가 깨끗이 사라진다"**는 점입니다.
DashCloud는 프로세스가 가동되는 샌드박스 내부의 /app 경로를 독립된 초고속 NVMe 영구 물리 블록 볼륨에 영구 마운트합니다.
새로운 코드를 배포하거나 서버를 재부팅해도 내 데이터가 100% 안전하게 유지되는 파일시스템 아키텍처와 대시보드 파일 관리자 활용법을 상세히 다룹니다.
HOME은 /app 입니다 (Wings 호환)
기존 Pterodactyl/Wings 환경과의 호환을 위해 컨테이너의 홈 디렉터리(HOME)는 /app으로 설정됩니다. 또한 Wings 경로를 그대로 쓰는 코드를 위해 /home/container가 /app으로 연결된 심링크가 제공됩니다.
~,Path.home(),os.path.expanduser("~")→ 모두/app/home/container→/app(심링크)- 프로세스 작업 디렉터리(cwd)도
/app이므로 상대 경로는 자동으로 영구 볼륨에 저장됩니다
휘발성 디렉터리와 영구 디렉터리의 생명주기 비교
컨테이너 내부의 디렉터리는 위치에 따라 생명주기가 완전히 다릅니다:
/ (루트 파일시스템 - 휘발성 영역)
├─ bin/
├─ usr/
├─ tmp/ # [휘발성] 재부팅 시 초기화되는 임시 캐시 디렉터리
├─ home/container -> /app # [심링크] Wings 호환 경로
└─ app/ # [★ 물리 볼륨 영구 마운트 영역, HOME]
├─ main.py # 소스 코드 (새 배포 시 덮어쓰기)
├─ requirements.txt
├─ .local/ # [영구] pip 의존성 설치 위치 (PYTHONPATH)
├─ node_modules/ # [영구] npm 의존성
├─ .deps.hash # 의존성 변경 감지 마커 (내부용)
└─ data/ # [★ 영구 보존 데이터 영역]
├─ bot.db # [영구 보존] SQLite 유저 데이터베이스
├─ session.json # [영구 보존] 크롤러 로그인 인증 세션
├─ grid_state.json # [영구 보존] 퀀트 활성 주문 상태 장부
└─ exports/ # [영구 보존] 수집된 일일 CSV 엑셀 파일| 디렉터리 위치 | 스토리지 종류 | 재배포 시 데이터 유지 여부 | 권장 활용처 |
|---|---|---|---|
/app 및 /app/data | 독립 물리 영구 볼륨 | 100% 안전 보존 (유지됨 ✅) | SQLite DB, 세션 쿠키, CSV 로그, 영구 상태 |
/tmp | 컨테이너 임시 메모리 램디스크 | 재부팅 시 완전 초기화 (삭제됨 ❌) | 1회성 임시 이미지 처리, 임시 다운로드 청크 |
/var, /usr | 컨테이너 기본 OS 이미지 | 새 빌드 시 새 OS로 교체 (초기화) | 시스템 기본 라이브러리 및 패키지 |
파이썬이나 노드 스크립트에서 data/bot.db처럼 현재 디렉터리 하위의 상대 경로로 파일을 생성하면, 자동으로 /app/data/bot.db 물리 볼륨에 저장되므로 별도의 복잡한 마운트 경로를 신경 쓰지 않아도 됩니다. HOME=/app이므로 ~/data/bot.db도 동일합니다.
의존성 자동 설치와 .deps.hash
배포/재시작 시 런타임 이미지가 매니페스트 변경을 감지해 의존성을 자동 설치합니다.
- Python:
requirements.txt변경 시pip install --user(→/app/.local) 실행,PYTHONPATH자동 설정 - Node.js:
package-lock.json(없으면package.json) 변경 시npm ci/npm install실행 (→/app/node_modules) - 설치가 성공하면 매니페스트 해시가
.deps.hash에 기록되어, 다음 재시작부터는 재설치를 건너뜁니다. 설치가 중단된 경우(크래시 등)는 다음 부팅에서 자동으로 복구·재시도합니다 - 백업 복원 후에는 의존성이 자동으로 다시 설치됩니다 (백업에 의존성 트리를 포함하지 않기 때문)
의존성 설치는 별도의 일회성 설치 컨테이너(RAM/CPU 무제한)에서 실행되므로, 128MB 같은 저사양 봇에서도 빌드 컴파일이 OOM으로 죽지 않습니다.
백업 제외 규칙
백업(로컬 tar.gz / GDrive / restic)은 아래 항목을 의도적으로 제외합니다. 재설치로 복구 가능한 항목이거나 런타임 내부 상태이기 때문입니다.
| 제외 항목 | 범위 | 이유 |
|---|---|---|
node_modules, .venv, venv, __pycache__, .git | 하위 모든 위치 | 재설치/재클론 가능 |
.cache, .npm | 프로젝트 루트만 | 패키지 캐시 (중첩된 동명 디렉터리는 유저 데이터로 보존) |
.deps.hash, .node_modules.bak*, .node_modules.lock | 프로젝트 루트만 | 런타임 내부 상태 |
즉, data/ 하위의 파일·SQLite DB·수집 데이터는 백업에 포함되지만, 위 목록은 복원되지 않고 복원 직후 자동 재설치로 다시 생성됩니다.
새 버전 배포 시의 파일시스템 병합 원리
Git 푸시나 대시보드 업로드를 통해 새로운 코드를 배포할 때, DashCloud는 다음과 같이 파일을 병합합니다:
- 소스 코드 업데이트: 새로 업로드된
main.py나requirements.txt는 새로운 버전으로 교체됩니다. - 영구 데이터 보존: 사용자의 봇이 런타임 중에
/app/data/디렉터리에 기록해 둔 SQLite 데이터베이스(bot.db)나 CSV 파일은 새 배포에 포함되지 않은 파일이더라도 절대 삭제되지 않고 그대로 유지됩니다. - 의존성만 재설치: 매니페스트가 바뀐 경우
.deps.hash비교로 필요한 경우에만 설치가 다시 실행됩니다.
대시보드 웹 파일 관리자 활용
개발자는 복잡한 SFTP 클라이언트(FileZilla 등) 없이도, DashCloud 웹 대시보드에서 브라우저만으로 서버 내부의 파일을 직접 열람하고 조작할 수 있습니다.
주요 기능
- 원클릭 파일 다운로드:
/app/data/bot.db나 수집된 CSV 파일을 클릭하면 즉시 내 PC로 다운로드됩니다. - 웹 텍스트 에디터: 설정 파일(
config.json)이나.env파일을 웹 브라우저에서 직접 열어 수정하고 저장할 수 있습니다. - 드래그앤드롭 업로드: 로컬 PC에 있던 초기 SQLite DB 파일 등을 브라우저 화면에 끌어다 놓아 바로 올릴 수 있습니다.
- 압축/압축해제, 복사/이동/이름변경/삭제: 대용량 디렉터리는 페이지 단위로 불러옵니다 (기본 300개, "더 보기"로 확장).
잔여 디스크 용량 모니터링 (파이썬 코드)
크롤러가 대량의 스크린샷이나 시계열 데이터를 수집할 때 디스크가 가득 차면(Disk Full) 쓰기 작업이 실패합니다. 봇 내부에서 잔여 디스크 용량을 사전에 체크하는 방어 코드입니다.
import shutil
import logging
logger = logging.getLogger("DiskMonitor")
def check_disk_usage(path: str = "/app"):
"""잔여 디스크 용량 측정 (GB 단위)"""
total, used, free = shutil.disk_usage(path)
total_gb = total / (1024 ** 3)
used_gb = used / (1024 ** 3)
free_gb = free / (1024 ** 3)
used_percent = (used / total) * 100
logger.info(f"디스크 용량: 총 {total_gb:.1f}GB 중 {used_gb:.1f}GB 사용 ({used_percent:.1f}%), 잔여: {free_gb:.1f}GB")
# 잔여 공간이 200MB 미만이면 경고 발송
if free_gb < 0.2:
logger.critical("⚠️ 영구 볼륨 디스크 용량이 200MB 미만으로 위험 수준입니다!")
# 관리자 텔레그램으로 경고 발송관련 블로그
- 텔레그램 봇 24시간 무료 호스팅 완벽 가이드 — 영구 볼륨과 데이터 보존 비교
- 호스팅 블로그 전체 보기