blog-go: Go 기반 개인 블로그 시스템
Go로 구현한 블로그 관리 시스템
주요 기능
백엔드 (Go)
- REST API: Gin 프레임워크 기반 HTTP 서버
- SQLite 데이터베이스: 가벼우면서도 안정적인 데이터 저장
- JWT 인증: 토큰 기반 사용자 인증 시스템
- 미들웨어: Rate limiting, 보안 헤더, 액세스 로깅
CLI 도구
- 포스트 관리: 생성, 조회, 수정, 삭제
- 에디터 연동: 시스템 에디터($EDITOR)를 통한 마크다운 작성
- Import/Export: 마크다운 파일 가져오기/내보내기
아키텍처
프로젝트 구조
internal/
├── auth/ # 인증 도메인
│ ├── auth.go # 비즈니스 로직
│ ├── service.go # 서비스 계층
│ ├── user.go # 사용자 엔티티
│ └── helpers.go # JWT, 암호화 유틸
├── post/ # 게시글 도메인
│ ├── post.go # 포스트 엔티티 및 비즈니스 로직
│ ├── service.go # 포스트 서비스
│ └── repository.go # Repository 인터페이스
├── repo/ # 인프라 계층
│ ├── db.go # 데이터베이스 연결
│ ├── authRepository.go # 인증 데이터 접근
│ └── postRepository.go # 게시글 데이터 접근
├── server/ # 웹 계층
│ ├── server.go # 라우터 설정
│ ├── middlewares.go # 미들웨어
│ ├── postHandlers.go # 게시글 핸들러
│ └── authHandlers.go # 인증 핸들러
├── cli/ # CLI 명령어들
└── config/ # 환경 설정
CLI 도구 사용법
포스트 생성
# Notes 카테고리 포스트 생성
./cli create --notes
# Projects 카테고리 포스트 생성
./cli create --proj
에디터가 열리며, 첫 번째 # 제목이 포스트 제목으로 자동 설정.
포스트 관리
# 모든 포스트 조회
./cli list
# Notes만 조회
./cli list --notes
# 특정 포스트 내용 출력
./cli show 5
# 포스트 수정 (에디터에서)
./cli update 3
# 포스트 삭제 (확인 프롬프트)
./cli delete 2
Import/Export
# 마크다운 파일을 Notes로 가져오기
./cli import post.md --notes
# 포스트를 파일로 내보내기
./cli export 5 backup.md
API 엔드포인트
공개 API
GET /notes- Notes 카테고리 포스트 목록GET /projects- Projects 카테고리 포스트 목록GET /posts/:id- 특정 포스트 조회GET /checkhealth- 헬스체크
인증 API (선택적)
현재는 주석 처리되어 있으며, 필요시 활성화 가능:
POST /posts- 포스트 생성PUT /posts/:id- 포스트 수정DELETE /posts/:id- 포스트 삭제POST /auth/register- 회원가입POST /auth/login- 로그인
환경 설정
필수 환경변수
DBPATH=./blog.db # SQLite 데이터베이스 파일 경로
SERVERPORT=:8000 # 서버 포트
JWTSECRET=your-secret # JWT 서명 키 (선택적)
EDITOR=nvim # CLI에서 사용할 에디터 (선택적)
실행 방법
빌드
# 의존성 설치
go mod tidy
# 서버 빌드
go build -o server ./cmd/server
# CLI 도구 빌드
go build -o cli ./cmd/cli
실행
# 환경 변수 설정 (.env 파일)
echo "DBPATH=./dev.db" > .env
echo "SERVERPORT=:8000" >> .env
# 서버 시작
./server
# CLI 사용
./cli list
테스트
# 전체 테스트 실행
go test ./...
# 커버리지와 함께 실행
go test -cover ./...
# 특정 패키지만 테스트
go test ./internal/auth
go test ./internal/post
배포
프로덕션 빌드
CGO_ENABLED=1 go build -ldflags="-w -s" -o blog-server ./cmd/server
CGO_ENABLED=1 go build -ldflags="-w -s" -o blog-cli ./cmd/cli
SQLite 사용으로 인해 CGO_ENABLED=1이 필요.
배포 시 고려사항
- systemd 또는 PM2 같은 프로세스 매니저 사용
- nginx/caddy를 통한 리버스 프록시 설정
- HTTPS 인증서 설정
- 로그 로테이션 설정
- SQLite 파일의 정기적인 백업
성능 측정
로컬 환경(Arch Linux, Go 1.25.0)에서 Apache Bench를 이용한 성능 테스트 결과:
| 엔드포인트 | 초당 요청수 | 평균 응답시간 | 설명 |
|---|---|---|---|
| /checkhealth | 50,728 RPS | 0.197ms | 헬스체크 (DB 조회 없음) |
| /posts | 37,469 RPS | 0.267ms | 전체 포스트 목록 (DB 스캔) |
| /posts/1 | 39,082 RPS | 0.256ms | 단일 포스트 조회 (인덱스) |
부하 테스트
동시 접속 500으로 스트레스 테스트를 진행한 결과:
- 초당 35,696 요청 처리
- 평균 응답시간 14.007ms
- 99% 요청이 22ms 이내 처리
SQLite를 사용함에도 불구하고 DB 조회가 포함된 엔드포인트에서 37k+ RPS의 성능을 보여, 개인 블로그 운영에는 충분한 성능을 확인.
향후 개선 계획
- 검색 기능: 제목/내용 기반 전문 검색
- 태그 시스템: 포스트별 태그 분류
- 이미지 업로드: 마크다운 내 이미지 지원
- 정적 사이트 생성: SEO 최적화를 위한 SSG 지원
- 페이지네이션: 대량의 포스트 효율적 조회
기술적 특징
장점
- 단일 바이너리: 복잡한 의존성 없이 간단한 배포
- 테스트 용이성: Repository 패턴으로 모든 계층 독립 테스트
- 확장성: Clean Architecture로 기능 추가 용이
- CLI 편의성: 웹 인터페이스보다 빠른 콘텐츠 관리
- 경량성: SQLite 사용으로 최소한의 리소스
제한사항
- SQLite 동시성: 대용량 트래픽에는 PostgreSQL 고려 필요
- 파일 스토리지: 현재 이미지 등 파일 업로드 미지원
- 실시간 기능: 댓글, 알림 등 실시간 기능 없음