다이어트 서비스 첫 뼈대에 담은 구조 설계 결정
목차
새 프로젝트 뼈대를 처음 잡는 날은 늘 묘하게 설렌다.
diet.hedvion.com 이라는 도메인으로 새 서비스를 시작하기로 결정하고, 오늘 그 첫 scaffold를 올렸다. 커밋 메시지 그대로 "initial scaffold" — 아직 실제 기능은 한 줄도 없고, 프로젝트가 존재한다는 사실만 형상화된 단계다.
왜 scaffold 커밋이 중요한가
팀을 이끌다 보면 "첫 커밋이 뭐가 중요해?" 라는 시각을 종종 마주친다. 근데 내 생각은 반대다. 첫 scaffold가 엉성하면 그 이후 모든 작업이 엉성한 관습 위에 쌓인다. 오늘 올린 파일 목록을 보면:
| 파일 | 역할 |
|---|---|
.env.example |
환경 변수 템플릿 — 팀원/배포 환경에서 어떤 키가 필요한지 문서화 |
.gitignore |
실제 .env 파일 등 민감 정보가 레포에 올라가지 않도록 가드 |
README.md |
프로젝트 목적 / 로컬 실행 방법 최소 기술 |
astro.config.mjs |
프론트엔드 프레임워크 Astro 기본 설정 진입점 |
bot/.env.example |
봇 서브모듈 전용 환경 변수 템플릿 |
bot/data_source.py |
봇의 데이터 소스 레이어 초기 뼈대 |
파일 여섯 개지만 구조가 이미 두 개 레이어로 나뉘어 있다는 게 보인다. 루트는 Astro 기반 프론트엔드, bot/ 디렉터리는 Python 봇 서브시스템. 이 두 가지가 같은 레포에서 출발하는 구조인데, 이 결정은 나중에 한번쯤 재검토가 필요하다. 모노레포로 묶어서 가는 게 편할 수도 있고, 규모가 커지면 분리하는 게 맞을 수도 있다. 지금은 빠른 시작을 위해 함께 두는 걸로.
.env.example 두 개를 분리한 이유
루트에도 .env.example, bot/ 안에도 .env.example. 이걸 하나로 합치지 않은 건 의도적인 결정이다.
프론트엔드(Astro)와 봇(Python)은 실행 환경 자체가 다르다. Astro는 Node.js 빌드 타임에 환경 변수를 주입받고, Python 봇은 런타임에 직접 읽는다. 배포 파이프라인도 다를 가능성이 높다. 이 두 컨텍스트의 환경 변수를 하나의 .env 파일로 합치면 단기적으로 편해 보이지만, 나중에 서로 다른 CI/CD 파이프라인에서 각자 필요한 값만 주입하려 할 때 분리 비용이 더 크게 든다.
# 루트 .env.example (Astro / 프론트 레이어)
PUBLIC_API_BASE_URL=
SOME_BUILD_TIME_KEY=
# bot/.env.example (Python 봇 레이어)
DATA_SOURCE_URL=
BOT_TOKEN=
처음부터 이렇게 나눠두면 팀원이 새로 합류했을 때 "나는 봇만 건드리면 되니까 bot/.env.example 만 보면 되겠구나" 라고 바로 파악할 수 있다. 온보딩 비용이 낮아지는 지점이다.
data_source.py — 봇의 첫 레이어 결정
bot/data_source.py 가 첫 Python 파일로 등장했다는 게 흥미롭다. 봇의 커맨드 핸들러나 진입점이 아니라 데이터 소스 레이어부터 뼈대를 잡았다는 뜻인데, 이건 꽤 좋은 설계 감각이라고 본다.
봇 프로젝트에서 흔히 보이는 실수 중 하나가 핸들러 안에 데이터 접근 로직을 직접 박아 넣는 것이다. 처음엔 빠르고 편한데, 데이터 소스가 바뀌거나 테스트를 붙이려는 순간 전부 다 뜯어야 한다. data_source.py 를 먼저 분리해두면 핸들러는 "어디서 데이터를 가져오는지" 를 몰라도 된다. 추후 데이터 소스가 로컬 파일이든, 외부 API든, DB든 이 레이어만 바꾸면 된다.
# bot/data_source.py 초기 뼈대 패턴 예시
class DataSource:
def __init__(self, config: dict):
self.config = config
def fetch(self, query: str):
raise NotImplementedError
아직 구현은 없고 인터페이스만 잡혀 있을 것이다. 그게 scaffold의 역할이기도 하고.
회고
오늘 작업 자체는 짧았지만 결정은 몇 가지 했다.
- Astro + Python 봇 조합으로 간다
- 모노레포 구조, 단 두 레이어는 환경 변수부터 명확히 분리
- 봇은 데이터 소스 레이어를 먼저 추상화해서 시작
이 정도 결정을 첫 커밋에 녹여두면, 다음 사람이 이 레포를 처음 열었을 때 "아, 이렇게 가는 구나" 를 파악하는 데 5분이면 충분하다. README가 그 역할을 해줘야 하고, 파일 구조가 그 이야기를 뒷받침해줘야 한다.
다음은 실제 Astro 페이지 구성과 봇 핸들러 진입점을 붙이는 작업이 될 것 같다.
🛒 이 글과 어울리는 추천 상품
*위 링크는 쿠팡파트너스 활동의 일환이며, 일정액의 수수료를 제공받을 수 있습니다.
댓글 0
첫 댓글 달아줘.