관리 메뉴

피터의 개발이야기

[GO] Go CRUD 프로젝트 아키텍처 본문

Programming/GO

[GO] Go CRUD 프로젝트 아키텍처

기록하는 백앤드개발자 2025. 4. 29. 06:11
반응형

ㅁ 들어가며

ㅇ Go로 DB 데이터를 CRUD(Create, Read, Update, Delete)하는 프로젝트를 구성하려고 한다. 가장 널리 사용되는 구조는 Clean Architecture 또는 Layered Architecture(MVC 기반)이다. 

아래는 Clean Architecture 기반의 Go CRUD 프로젝트 아키텍처 구성해 보았다.

 


ㅁ  전체 구조 (폴더 트리 예시)

go-crud-project/
├── cmd/                  # 애플리케이션 실행 진입점
│   └── main.go
├── config/               # 환경설정 관련
│   └── config.go
├── internal/
│   ├── domain/           # 비즈니스 도메인 정의 (Entity, Interface)
│   │   └── user.go
│   ├── repository/       # DB 접근 로직 (Interface + Implementation)
│   │   └── user_repo.go
│   ├── service/          # 비즈니스 로직
│   │   └── user_service.go
│   ├── handler/          # HTTP Handler (Controller 역할)
│   │   └── user_handler.go
│   └── router/           # 라우팅 설정
│       └── router.go
├── pkg/                  # 공통 유틸, 에러 처리, 미들웨어 등
│   ├── db/
│   │   └── mysql.go
│   └── logger/
│       └── logger.go
├── go.mod
└── go.sum

ㅁ 각 계층 설명

1. cmd/main.go

  • 프로그램 진입점
  • 설정 로딩, DB 연결, 라우터 실행
func main() {
    cfg := config.Load()
    db := db.Connect(cfg.Database)
    router := router.NewRouter(db)
    router.Run(":8080")
}

2. config/

  • 환경 변수 읽기 (.env 또는 yaml, json 등)
  • 데이터베이스, 서버 설정 등을 구조체로 관리

3. domain/

  • 도메인 모델과 인터페이스 정의
type User struct {
    ID    int    `json:"id"`
    Name  string `json:"name"`
    Email string `json:"email"`
}

type UserRepository interface {
    Create(user *User) error
    GetByID(id int) (*User, error)
    Update(user *User) error
    Delete(id int) error
    List() ([]User, error)
}

4. repository/

  • domain.UserRepository 인터페이스 구현
  • DB 접근 (예: GORM, sqlx 사용 가능)
type userRepo struct {
    db *gorm.DB
}

func (r *userRepo) Create(user *domain.User) error {
    return r.db.Create(user).Error
}

5. service/

  • 비즈니스 로직 처리
  • 트랜잭션 처리, 검증 로직 등 포함
type UserService struct {
    repo domain.UserRepository
}

func (s *UserService) Register(user *domain.User) error {
    // validation 가능
    return s.repo.Create(user)
}

6. handler/

  • HTTP 요청 핸들링 (Gin, Echo, Fiber 등 사용 가능)
func (h *UserHandler) CreateUser(c *gin.Context) {
    var user domain.User
    if err := c.BindJSON(&user); err != nil {
        c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
        return
    }
    err := h.service.Register(&user)
    if err != nil {
        c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
        return
    }
    c.JSON(http.StatusCreated, user)
}

7. router/

  • API 라우팅 정의
func NewRouter(db *gorm.DB) *gin.Engine {
    r := gin.Default()

    userRepo := repository.NewUserRepo(db)
    userService := service.NewUserService(userRepo)
    userHandler := handler.NewUserHandler(userService)

    userGroup := r.Group("/users")
    {
        userGroup.POST("/", userHandler.CreateUser)
        userGroup.GET("/", userHandler.ListUsers)
        userGroup.GET("/:id", userHandler.GetUser)
        userGroup.PUT("/:id", userHandler.UpdateUser)
        userGroup.DELETE("/:id", userHandler.DeleteUser)
    }

    return r
}

 


ㅁ 기술 스택

영역 도구 라이브러리
웹 프레임워크 Gin
ORM GORM
DB MySQL
설정 관리 Viper
로깅 Zap, Logrus
테스트 Go's testing, Testify

 

 

ㅁ 함께 보면 좋은 사이트

Building a CRUD App with Clean Architecture in Go

[Hands-on Guide] How to Implement Clean Architecture in Golang?

 

반응형
Comments