Claude와 함께 MIT Missing Semester 강의를 실습하며 정리한 내용입니다.
들어가며
이번 강의는 의존성 관리, 버저닝, Docker 등 코드를 패키징하고 배포하는 방법을 다룬다.
핵심 개념
의존성과 환경
프로젝트는 다른 패키지에 의존한다. 문제는 dependency hell - A가 C v1.0 필요, B가 C v2.0 필요하면 충돌.
해결: 가상 환경으로 프로젝트별 의존성 격리. Python은 venv, Node.js는 node_modules가 이미 프로젝트별 격리 역할을 한다.
Lockfile
package.json- "이 범위의 버전 괜찮아" (예:^1.2.0)package-lock.json- "정확히 이 버전을 써" (예:1.2.3)
오늘 npm install하면 1.2.3이 설치되지만, 한 달 뒤엔 1.2.5가 설치될 수 있다. lockfile이 있으면 언제나 같은 버전이 설치돼서 재현성 보장. 그래서 lockfile은 반드시 Git에 커밋해야 한다.
head -20 package-lock.json # lockfile 내부 확인
cat package.json | grep -A 5 dependencies # ^ 버전 확인
npm ls --depth=0 # 실제 설치된 버전 목록Semantic Versioning (semver)
v1.2.3
│ │ └── patch: 버그 수정 (호환됨)
│ └── minor: 기능 추가 (호환됨)
└── major: 호환 안 되는 변경^1.2.0은 "1.x.x 범위에서 최신" → major만 고정. package.json에서 보이는 캐럿(^)의 의미.
Docker
"내 컴퓨터에선 되는데?"를 해결. 앱 + 환경을 통째로 패키징.
Dockerfile - 이미지 빌드 레시피:
FROM node:20-alpine
WORKDIR /app
COPY package*.json ./
RUN npm install
COPY . .
RUN npm run build
CMD ["npm", "start"]FROM- 베이스 이미지 (OS + 런타임)COPY- 파일 복사RUN- 빌드 시 실행할 명령어CMD- 컨테이너 실행 시 명령어
docker build -t my-app . # 이미지 빌드
docker run -p 3000:3000 my-app # 컨테이너 실행
docker run --rm -it alpine sh # Alpine Linux 컨테이너 진입 (exit으로 나오면 삭제)docker-compose - 여러 컨테이너를 함께 관리. docker compose up 한 방에 앱 + DB 실행.
환경변수로 설정 관리
코드에 비밀값 하드코딩 금지. 환경변수로 분리하고, .env 파일은 .gitignore에 넣어서 Git에 올라가지 않게 한다.
실습 기록
lockfile 확인
package.json의 ^ 버전과 package-lock.json의 정확한 버전을 비교. npm ls --depth=0으로 실제 설치된 의존성 확인.
Docker 컨테이너 체험
docker run --rm -it alpine sh로 Alpine Linux 컨테이너에 진입. cat /etc/os-release로 완전히 다른 OS인 것을 확인. exit하면 컨테이너도 함께 사라진다 (--rm 플래그).