Pickle(피클) 은 부산대학교 구성원을 위한 셀프서비스 클라우드 플랫폼입니다. 학교 이메일로 가입한 사용자가 VM을 신청하면 관리자가 승인하고, 플랫폼이 Proxmox VE 위에 자동으로 프로비저닝합니다. 만들어진 VM에는 SSH·브라우저 웹 터미널로 접속하고, 도메인 기반 HTTP(S) 게시로 외부에 서비스를 공개할 수 있습니다.
이 저장소는 Pickle의 백엔드입니다. REST API, JobRunr 백그라운드 워커, Proxmox VE 클라이언트로 구성된 단일 애플리케이션으로, VM 신청부터 프로비저닝·운영·삭제까지 전체 수명주기를 담당합니다. Spring Boot 4.1 / Java 25 / PostgreSQL 18.
주요 기능 영역:
- 계정:
@pusan.ac.kr이메일 인증 가입, TOTP 2단계 인증(관리자 강제 적용 프로파일 지원), 약관 버전 동의·재동의, 비밀번호 변경/재설정, 탈퇴·비활성화 (모든 전환은 token_version으로 기존 세션 즉시 무효화) - 조직/그룹: 기관 소속, 그룹 역할(소유자/편집자/참여자/열람자), 운영자 계층 및 권한 매트릭스 감사
- VM 수명주기: 신청·승인 흐름(희망 slug 지정), JobRunr 멱등 프로비저닝 파이프라인(템플릿 클론, cloud-init 비밀번호/플랫폼 SSH 키 주입, IPAM 할당, 게스트 에이전트 검증, 호스트키 수집), 전원 제어, 삭제 3종(본인 예약/관리자 예약/강제)과 삭제 보호, 사용 기간 만료 파이프라인(예고 알림·자동 정지·연장)
- 정합성 유지: 30초 상태 폴러, 드리프트 감지·영속화, 삭제 스위퍼, 실패 작업 NEEDS_ADMIN 복구 API (어떤 경로로도 자동 파괴는 하지 않음)
- 접속 경로 인가: SSH 게이트웨이 라우팅 오라클(공개키 신원, 호스트키 핀 제공), 웹 터미널 원타임 티켓 발급·재검증·세션 감사, HTTP(S) 게시 상태를 proxy-agent에 푸시
- 알림/공지: 인앱 알림함 + 비동기 이메일 디스패처(재시도 백오프, 재발송), 전체/기관/그룹 공지
- 운영: 감사 로그 조회(본인 활동 / 관리자 스코프), 화이트리스트 설정 편집기 (SSH·웹 터미널 킬 스위치 포함), 유지보수 모드, 보존 스위퍼
scripts/setup-hooks.sh # 최초 1회: git hook 설치
mvn spring-boot:run # 로컬 PostgreSQL 필요
scripts/verify.sh # 빌드 + 전체 테스트 (embedded PostgreSQL, Docker 불필요)테스트는 Zonky embedded-postgres로 DB를 내장 구동하고, Proxmox 클라이언트는
WireMock 스텁으로 검증합니다. OpenAPI 문서는 /api/v1/openapi로 노출되며
pickle-console 프론트엔드와의 단일 계약입니다(ContractDriftTest가 구현
범위를 계약과 비교해 드리프트를 차단).
필요한 값은 환경변수로 주입하며, 로컬 개발은 dev/test 기본값만으로 동작합니다.
| 변수 | 용도 | 기본값 |
|---|---|---|
PICKLE_DB_URL / PICKLE_DB_USER / PICKLE_DB_PASSWORD |
PostgreSQL 연결 | jdbc:postgresql://localhost:5432/pickle_dev / pickle / pickle |
PICKLE_JWT_SECRET |
HS256 서명 키(32바이트 이상). dev/test 외 프로파일에서는 필수(없으면 기동 실패) | dev/test 전용 내장 키 |
PICKLE_CREDENTIALS_KEY |
VM 초기 비밀번호 가역 저장용 AES-256-GCM 키(base64 32바이트). dev/test 외 필수 | dev/test 전용 내장 키 |
PICKLE_PROXMOX_TOKEN_ID / PICKLE_PROXMOX_TOKEN_SECRET / PICKLE_PROXMOX_CA_CERT |
Proxmox VE API 토큰과 CA 핀 | — |
PICKLE_SMTP_* |
실 SMTP(staging/prod 전용; dev/test는 MockMailSender가 로그/스풀로 대체) |
— |
PICKLE_VERIFICATION_BASE_URL / PICKLE_PASSWORD_RESET_BASE_URL |
메일 내 콘솔 링크 베이스 | https://pickle.pnuops.com/… |
PICKLE_PROXY_AGENT_* / PICKLE_SSHGW_* / PICKLE_TERMINAL_* |
proxy-agent 푸시, SSH 게이트웨이 라우팅, 웹 터미널 브리지 연동(토큰·URL·세션 상한 등) | — |
users.email은 citext 확장을 사용합니다. V2__identity.sql이
create extension if not exists citext를 실행하므로 마이그레이션 계정에 확장
생성 권한(또는 사전 설치)이 필요합니다.
DevDataSeeder가 이메일/slug 기준 insert-if-absent로 멱등 삽입합니다:
| 계정 | 환경변수 | dev 기본값 |
|---|---|---|
| SYS_ADMIN | PICKLE_SEED_SYSADMIN_EMAIL / PICKLE_SEED_SYSADMIN_PASSWORD |
admin@pickle.local / pickle-sysadmin-dev! |
기관 SW교육센터 (slug sw-edu) |
— | 자동 생성 |
ORG_ADMIN (sw-edu 소속) |
PICKLE_SEED_ORGADMIN_EMAIL / PICKLE_SEED_ORGADMIN_PASSWORD |
orgadmin@pickle.local / pickle-orgadmin-dev! |
기본값은 개발 전용이며, 공유 환경에서는 반드시 환경변수로 재설정합니다.
src/main/java/kr/ac/pusan/pickle/ 애플리케이션 코드 (기능 패키지 구조)
src/main/resources/db/migration/ Flyway 마이그레이션 (스키마의 단일 진실 원천)
scripts/ verify + hook 헬퍼
| 저장소 | 역할 |
|---|---|
| pickle-api | 백엔드 REST API, 프로비저닝 파이프라인, 접속 인가 |
| pickle-console | 웹 콘솔 (사용자·관리자 SPA) |
| pickle-sshgw | SSH 게이트웨이 + 웹 터미널 브리지 |
| pickle-proxy-agent | HTTP(S) 게시용 리버스 프록시 제어 에이전트 |
| pickle-infra | 인프라 프로비저닝 스크립트·런북 |