진짜로 써먹는 Issue Tracker API 만들기 — 기초부터 배포까지
솔직히 말하면, 예전에 저도 이런 경험이 있었어요. “API 강의”라고 해서 들었는데, 40분 동안 구조 이야기만 하다가 코드 한 줄도 안 치고 끝나는 영상들. 머릿속엔 개념만 둥둥 떠다니고, 손에는 아무것도 안 남는 느낌이죠.
그래서 이번에는 방향을 완전히 반대로 잡았습니다.
이번 글에서는 FastAPI crash course를 통해 실제로 돌아가는 Issue Tracker API를 처음부터 끝까지 만들어봅니다. CRUD는 기본이고, Pydantic schema, Swagger docs, middleware, CORS 설정, 그리고 Render 배포까지 전부 다룹니다.
AI 도구를 아예 안 쓰진 않아요. 타이핑을 조금 줄여주니까요. 하지만 핵심은 여전히 같습니다. 왜 이렇게 구성하는지, 각 요소가 무슨 역할을 하는지를 이해하는 것.
“AI는 코드를 만들어줄 수 있지만, 시스템을 이해하는 건 결국 사람 몫이다.”
우리가 만들 API는 이런 걸 할 수 있어요.
- Issue 생성
- Issue 목록 조회
- 특정 Issue 조회
- Issue 수정
- Issue 삭제
데이터 저장은 일부러 JSON 파일을 씁니다. 단순해서 좋아요. FastAPI 자체에 집중하기 딱 좋거든요. Node.js + Express 경험이 있다면, 중간중간 비교도 같이 해볼게요.

FastAPI, 정확히 뭐길래 이렇게 인기일까?
FastAPI는 Python 기반의 고성능 API framework입니다. 이름 그대로 “빠른 API”를 만드는 데 최적화되어 있죠.
내부적으로는 Starlette라는 ASGI toolkit 위에 올라가 있습니다. Starlette가 담당하는 건 이런 것들이에요.
- routing
- middleware
- request / response 처리
FastAPI는 그 위에서 개발자 경험을 확 끌어올립니다.
- Python type hint 기반 Pydantic validation
- 자동 serialization
- Swagger UI / ReDoc 자동 생성
- Dependency Injection 시스템
- OAuth2, JWT 같은 security utilities
- WebSocket, streaming 지원
Express로 API 만들다가 “이걸 왜 내가 다 직접 설정해야 하지?” 싶었던 적 있다면, FastAPI는 꽤 시원한 해답처럼 느껴질 거예요.
ASGI vs WSGI, 왜 중요한데?
이건 살짝만 짚고 갈게요.
- WSGI: 전통적인 방식, 기본적으로 synchronous
- ASGI: 비동기 처리 가능, 동시에 여러 request 처리
이번 프로젝트에서는 JSON file을 쓰기 때문에 async의 이점을 100% 쓰진 않아요. 하지만 SQLAlchemy 2.0 async 같은 걸 붙이면 FastAPI의 진짜 장점이 드러납니다.
트래픽이 늘어도 API가 버벅이지 않는 그 느낌, 아마 나중에 체감하게 될 거예요.
FastAPI 요청 흐름, 머릿속 그림으로 그려보면
대충 이런 구조라고 보면 됩니다.
Client (React, Vue, Mobile, Desktop 등) → HTTP request → (Nginx 같은 reverse proxy) → Uvicorn(ASGI server) → FastAPI → Pydantic validation → Storage → Response
중간중간에:
- middleware가 끼어들 수도 있고
- dependency가 주입되기도 하고
- Swagger UI로 바로 테스트도 가능하죠
지금은 추상적으로 느껴져도, 직접 만들어보면 금방 감이 옵니다.
Step 1. 프로젝트 세팅 (Virtual Environment + FastAPI 설치)
빈 폴더 하나 만듭니다.
예시:
- fastapi-issue-tracker
IDE(VS Code 추천)와 terminal을 동시에 열어주세요.
Virtual Environment 만들기
Mac / Linux:
- python -m venv .venv
- source .venv/bin/activate
Windows:
- python -m venv .venv
- .\.venv\Scripts\activate
터미널 앞에 (.venv) 표시가 보이면 성공입니다.
FastAPI 설치
이번에는 standard extra를 씁니다.
- pip install "fastapi[standard]"
Node 기준으로 보면, Express + 필수 미들웨어 한 번에 설치하는 느낌이라고 보면 돼요.
Step 2. Entry Point 만들기 (main.py)
Node에서 app.js나 server.js 같은 역할을 하는 파일입니다.
여기서 할 일은 단순해요.
- FastAPI import
- app 생성
- 간단한 route 정의
Health Check route
/health endpoint를 하나 만듭니다.
이런 endpoint는:
- 서버 살아있는지 확인하기 좋고
- 배포 후 모니터링에도 유용합니다
response는 간단히:
- { "status": "ok" }
FastAPI는 dict를 자동으로 JSON으로 바꿔줍니다.
서버 실행
- fastapi dev main.py
브라우저에서:
- http://localhost:8000/health
정상이라면 JSON 응답이 보일 거예요.
Swagger UI
- http://localhost:8000/docs
여기서 FastAPI의 진가가 느껴집니다.
모든 route가 자동으로 문서화되고, Try it out 버튼으로 바로 요청도 날릴 수 있어요. Postman이 따로 필요 없죠.
라우팅 기본 감 잡기 (GET, Path Param, Query, POST)
본격적으로 Issue API 만들기 전에, 패턴 몇 가지만 빠르게 보고 갑니다.
GET route
- @app.get("/items")
- list 반환
Path Parameter
- /items/{item_id}
- function argument로 item_id: int
Type hint 덕분에 validation도 자동으로 됩니다.
Query Parameter
- /items?page=1&limit=10
- function에 page: int = 1, limit: int = 10
POST body
Schema 없이 받으면 뭐든 들어옵니다.
그래서 우리가 곧 Pydantic를 쓰는 거죠.
Step 3. 프로젝트 구조 정리
main.py에 모든 걸 몰아넣는 건 금물입니다.
아래 구조로 갑니다.
- app/
- routes/
- issues.py
- storage.py
- schemas.py
- middleware/
- timer.py
- routes/
이 구조가 익숙해지면, 프로젝트가 커져도 덜 혼란스러워요.
Step 4. Issues Router 만들기
FastAPI의 APIRouter는 Express Router랑 거의 같은 개념입니다.
issues.py에서:
- router = APIRouter(prefix="/api/v1/issues", tags=["issues"])
prefix 덕분에 version 관리도 깔끔해집니다.
main.py에 router 연결
- app.include_router(issues_router)
Swagger 새로고침하면 Issues 섹션이 생깁니다.
이 순간, “아 이제 진짜 API 만든다”라는 느낌이 옵니다.
Step 5. JSON 기반 Storage (storage.py)
Database 대신 JSON 파일을 씁니다.
이유는 단순해요.
- FastAPI에 집중
- 불필요한 복잡도 제거
load_data() / save_data() 두 함수만 있으면 충분합니다.
실무에서는 물론 DB 쓰셔야죠. 하지만 학습 단계에선 이게 딱 좋아요.
Step 6. Pydantic Schemas (schemas.py)
여기서 FastAPI가 진짜 빛을 발합니다.
Enum
- IssueStatus: open / in_progress / closed
- IssuePriority: low / medium / high
허용된 값만 받게 강제합니다.
IssueCreate
POST 요청용 schema:
- title
- description
- priority (default: medium)
status는 서버에서 자동으로 open 설정
IssueUpdate
PUT 요청용:
- 모든 필드 Optional
일부만 수정 가능하게 만드는 게 포인트입니다.
IssueOut
response 전용 schema:
- id
- title
- description
- priority
- status
API contract가 명확해집니다.
Step 7. CRUD 전부 구현하기
GET /issues
전체 목록 조회
POST /issues
Issue 생성
- uuid 생성
- JSON 저장
- 201 status
GET /issues/{id}
단일 Issue 조회
- 없으면 404
PUT /issues/{id}
Issue 수정
- None 아닌 필드만 업데이트
DELETE /issues/{id}
Issue 삭제
- 204 No Content
이제 진짜 CRUD API 완성입니다.
Step 8. Middleware 추가 (Request Timer)
middleware는 request/response 사이에 끼어드는 로직입니다.
여기서는:
- request 처리 시간 측정
- X-Process-Time header로 응답에 추가
Swagger에서 header 확인할 수 있습니다.
Step 9. CORS 설정
Frontend랑 domain이 다르면 CORS 에러 납니다.
FastAPI의 CORSMiddleware로 해결합니다.
이번 예제에서는:
- 모든 origin 허용
실제 서비스에서는 domain 제한 필수입니다.
Step 10. requirements.txt 생성
- pip freeze > requirements.txt
배포할 때 필수입니다.
Step 11. Render로 배포
DevOps 깊게 안 파고도 배포 가능합니다.
Start command:
- uvicorn main:app --host 0.0.0.0 --port $PORT
배포 후:
- /api/v1/issues
- /docs
정상 동작 확인.
다음 단계는?
이 글에서는 기초 체력을 만드는 데 집중했습니다.
다음으로 추천하는 주제는:
- Authentication (JWT)
- DB 연동
- Permission / Role 관리
- Testing
하지만 여기까지 해봤다면, FastAPI가 왜 인기 있는지 체감했을 겁니다.
AI가 코드를 대신 써주는 시대일수록, 이런 구조적인 이해가 더 중요해집니다.
이제 여러분도 FastAPI로 뭔가 하나 제대로 만들어볼 준비가 됐어요.
'SW > Python' 카테고리의 다른 글
| Matplotlib 사용법 완전 정리: 설치부터 그래프 그리기까지 한 번에 배우기 (0) | 2026.02.20 |
|---|---|
| Python NumPy 기초부터 실전 예제까지 한 번에 정리한 완전 가이드 (array·axis·reshape 설명) (0) | 2026.02.11 |
| FastAPI + React + Clerk로 B2B SaaS 애플리케이션 구축하기 (2025 SEO 최적화 가이드) (0) | 2026.01.31 |
| Python Requests로 API 호출하는 방법 한 번에 정리하기 (GET·POST·인증까지) (0) | 2026.01.27 |
| Python AI Agent를 FastAPI + Vercel로 배포하는 방법 (LangChain · LangGraph 실전 예제) (0) | 2026.01.03 |