반응형

Go 의 인기 Web Framework 'Gin'


해당 튜토리얼은 'Building Go Web Applications and Microservices Using Gin'의 내용을 번역하며 개인적으로 정리한 것입니다.


이번 시간에는 라우터 초기화기사 모델을 디자인하고 테스트하는 과정을 제작해볼 예정입니다.

 

1. 경로 설정

이전 시간까지 main.go 파일에서 라우터를 만들고 설정해주었습니다. 어플리케이션의 커져감에 따라 경로 설정을 하나의 파일에서 작성하여 옮기는 것이 좋습니다. routes.go 파일에 함수 initializeRoutes() 를 만들고, 이 함수를 main() 함수에서 호출하여 모든 경로를 설정하게 될 것입니다. 라우터 핸들러를 별도의 함수로 정의하는 과정입니다.

 

위와 같은 작업을 수행할 routes.go 파일은 다음과 같습니다.

 

▶ routes.go

// routes.go

package main

func initializeRoutes() {
	
	// 인덱스 라우터 처리(Handle)
	router.GET("/", showIndexPage)
}

 

인덱스 페이지에 기사 목록들을 표시할 것이기 때문에 코드를 수정하고 나서도 추가 경로를 정의해줄 필요가 없습니다.

 

이제 main.go 파일에 initializeRoutes() 함수를 추가해줍니다.

 

▶ main.go

 

// main.go

package main

import (
	"net/http"

	"github.com/gin-gonic/gin"
)

var router *gin.Engine

func main() {
	// ---- Gin에서 기본적인 라우터 생성 ----- //
	router = gin.Default()

	// ----- 모든 템플릿 파일 로드 ------- //
	router.LoadHTMLGlob("templates/*")

	router.GET("/", func(c *gin.Context) {
		// Context의 HTML 메소드를 호출하여 템플릿을 렌더링합니다.

		c.HTML(
			// ----- HTTP 상태를 200(OK)에 세팅합니다 ------ //
			http.StatusOK,
			// ------ index.html 템플릿을 사용합니다 ------- //
			"index.html",
			// ----- 페이지에서 사용하는 데이터 전달 ------- //
			gin.H{
				"title": "Home Page",
			},
		)
	})

	// ------ 경로 초기화하기 -------- //
	initializeRoutes()

	// ------ 어플리케이션 서버 구동 ------- //
	router.Run()
}

 

2. 기사 모델 디자인하기

튜토리얼에서는 ID, Title, Content 총 3개의 필드만을 사용하는 단순한 기사 구조를 유지할 것입니다. 이 struct는 다음과 같이 표현할 수 있습니다.

 

type article struct {
  ID      int    `json:"id"`
  Title   string `json:"title"`
  Content string `json:"content"`
}

 

대부분의 어플리케이션은 DB를 사용하여 데이터를 관리합니다. 단순하게 유지하기 위해 다음 두 개의 하드 코딩된 기사로 기사 목록을 초기화하도록 하겠습니다.

 

var articleList = []article{
  article{ID: 1, Title: "1번 기사", Content: "기사 내용 1번"},
  article{ID: 2, Title: "2번 기사", Content: "기사 내용 2번"},
}

 

위의 코드를 models.article.go 라는 새로운 파일에 작성하도록 합니다. 이제 우리는 모든 기사 목록을 반환하는 함수를 만들어줄 필요가 있습니다. 이 함수의 이름을 getAllArticles() 이라고 지정하고, 파일에 저장합니다. 이번에는 이 과정에 대한 테스트를 작성해볼 것입니다. 이 테스트는 이름이 TestGetAllArticles가 되고, models.article_test.go 파일에 저장합니다.

 

getAllArticles() 함수에 대한 테스트(TestGetAllArticles)를 생성해보는 것으로 시작합니다. models.article_test.go 에는 이 Unit 테스트를 포함한 코드가 작성되어야 합니다.

 

▶ models.article_test.go

 

// models.article_test.go

package main

import "testing"

// ------ 모든 기사 목록을 가져오는 기능을 테스트합니다 ------- //
func TestGetAllArticles(t *testing.T) {
	alist := getAllArticles()

	// --- 반환된 기사 목록의 길이가, 리스트가 포함하고 있는 전역변수의 길이와 같은지 확인합니다 --- //
	if len(alist) != len(articleList) {
		t.Fail()
	}

	// ---- 3가지 필드값이 동일한지 확인해봅니다 ----- //
	for i, v := range alist {
		if v.Content != articleList[i].Content ||
			v.ID != articleList[i].ID ||
			v.Title != articleList[i].Title {

			t.Fail()
			break
		}
	}
}

 

이 Unit 테스트는 getAllArticles() 함수를 사용하여 모든 기사 목록을 가져오도록 합니다. 테스트에서는 우선, 이 함수에서 가져온 기사 목록과 전역변수 articleList에 있는 기사 목록과 동일한지를 검증합니다. 그 다음, 각 기사가 동일한지 확인하기 위해 기사 목록을 for반복문을 통해 반복실행합니다. 이 두 테스트 중 하나라도 실패하면 테스트는 실패하게 됩니다.

 

테스트를 작성하고나면 이제 models.article.go 파일에 실제 코드를 작성해보도록 합니다.

 

▶ models.article.go

 

// models.article.go

package main

type article struct {
  ID      int    `json:"id"`
  Title   string `json:"title"`
  Content string `json:"content"`
}

var articleList = []article{
  article{ID: 1, Title: "Article 1", Content: "Article 1 body"},
  article{ID: 2, Title: "Article 2", Content: "Article 2 body"},
}

// ----- 모든 기사 목록을 반환합니다 ----- //
func getAllArticles() []article {
  return articleList
}

 

여기까지 따라오셨다면 프로젝트 폴더 안의 디렉토리 구조는 다음과 같을 것입니다.

 

오류는 내용 업데이트를 통해 수정될거에요!

 


 

다음 시간에는 View 템플릿과 라우터 핸들러를 만들어 각종 기능을 더 추가해보도록 할 예정입니다.

차근차근 제작해나갑시다! 

 

 

반응형

+ Recent posts