전체 글

반응형


Amazon Elastic Compute Cloud !

 

AWS 서비스들 가운데에서도 가장 유명하고 기본적인 서비스 중 하나로 EC2가 있습니다. AWS EC2Amazon Elastic Compute Cloud의 약자로 AWS 클라우드에서 확장 가능한 컴퓨팅 스토리지를 제공하는 서비스를 말합니다. EC2에서 원하는 사양의 인스턴스를 생성하여 가상 서버를 구축하고, 네트워킹 및 보안 구성과 스토리지 관리를 할 수 있습니다. 트래픽이 늘어나면 그 필요량만큼의 인스턴스를 생성하여 대응할 수 있고, 필요없어진 인스턴스는 종료하면 일정 시간 후 자동으로 삭제되어 과금되지 않습니다. 우리가 일반적으로 아는 가장 기본적인 클라우스 서버의 기능을 생각하시면 될 것입니다.

 

AWS EC2는 쉽게 배울 수 있고, 빠르게 사용이 가능하며, 프리 티어 유저분들의 경우 12개월간 특정 인스턴스를 무료로 사용하실 수 있습니다. 이전에 포스팅한 프로모션 크레딧을 사용하시면 더욱 좋을 것입니다.

 


 

 

우선 AWS EC2를 사용하기 위해서 콘솔 가입을 해주시고, 로그인 하신 후에 서비스 중 EC2를 선택해서 접속해주세요. 저는 자주 쓰는 서비스들 중 하나기 때문에 즐겨찾기 해두었습니다.

 

인스턴스를 비워둔 상태로, 처음 접속하시면 저와 똑같이 이렇게 보이실 것입니다.

 

NEW EC2 Experience가 적용되어 이전의 UI와 조금 다릅니다만 이전에 사용하셨던 분들도 사용하시기에는 큰 차이가 없습니다. 위의 화면은 EC2 대시보드라고 부릅니다.

 

 

EC2 사용을 위해 인스턴스를 생성해보도록 하겠습니다. 우측 상단의 인스턴스 시작을 눌러줍니다.

 

 

EC2를 사용하기 위해서 먼저 OS, App Server, App이 포함된 AMI를 선택합니다. 각 OS별로 프리 티어 사용가능 여부가 표시되어있으므로 확인하시고 프리 티어 사용자 분들께서는 프리 티어를 사용해보시는 것을 추천드립니다.

 

 

Amazon Linux 2와 같은 자체 Linux OS부터 Ubuntu, Red Hat, Debian, MS Server 등 다양한 OS 선택이 가능합니다. 프리 티어만 따로 보기도 가능합니다. 원하는 OS와 Application이 있는 사양을 선택하시면 됩니다.

 

 

프리 티어 사용 가능한 항목은 별도의 표시가 되어있습니다. t2 micro 유형이 프리 티어 사용 가능 항목이며 t2 부터 z1d 까지 정말 많은 종류의 인스턴스가 있습니다. 사양별로 선택이 가능하도록 잘 분류되어있습니다.

 

각 스펙별로 세분화하여 등록되어 있어 원하는 인스턴스를 자유롭게 선택 가능합니다.

 

다음 보안 그룹을 구성해줍니다. 

 

 

왼쪽 하단의 규칙 추가를 통해 원하는대로 규칙을 추가할 수 있으며 한 번 생성한 보안 그룹은 이후의 다른 인스턴스를 만들때 다시 활용이 가능합니다. 

 

 

HTTP와 IMAP, POP3와 같은 다양한 유형을 선택할 수 있으며 사용자 지정 TCP를 통해 TCP 포트 범위를 별도 지정하여 활용할 수 있습니다.

 

 

나머지 구성을 모두 끝내면 키 페어 생성 또는 선택 창이 뜹니다. 여기서 생성되는 키는 해당 인스턴스에 접속할 때 필요하므로 안전하게 잘 보관해주시고 유출되지 않도록 주의해야할 것입니다. 또 혹시 실수로 지우거나하는 경우 해당 서버에 접속이 안되니 관리에 특별히 신경써야합니다. 원하는 폴더에 잘 보관하셔서 키를 생성 혹은 기존에 생성하신 키 페어를 선택하신 후에 인스턴스를 시작할 수 있습니다.

 

 

다음과 같이 인스턴스가 생성되고 실행 중 상태가 뜨면 접속이 가능합니다.

 

 

인스턴스를 우클릭하고 연결을 선택하시면 다음과 같이 4가지 연결 방식 중 하나를 선택하여 우리가 방금 생성한 인스턴스에 연결할 수 있습니다.

 

성공적으로 접속되었으니 테스트 삼아 docker 설치도 해보았습니다.

 

 

터미널이나 cmd창에서 접속하기 위해서는 키 페어를 저장하고 있는 디렉토리로 가셔서 다음 명령어를 통해 접속이 가능합니다.

 

ssh -i /path/my-key-pair.pem my-instance-user-name@my-instance-public-dns-name

 

일반적으로 연결할 때 SSH 클라이언트를 클릭해보면 쉽게 명령어를 복사 붙여넣기 할 수 있도록 되어있으니 참고해주세요.

 


 

우리는 몇 번의 클릭만으로도 아주 간단하게 AWS EC2를 시작해볼 수 있었습니다. 이제 EC2를 활용해서 클라우드 컴퓨팅을 직접 체험해보세요!

반응형
반응형

BOJ 문제풀이!

 


 

 

BOJ 2292번 벌집 Go Lang 문제풀이입니다.

 

해당 문제는 첫번째 벌집인 1번 벌집 주위에 6개의 벌집이 생기며, 그 주변으로 총 6의 배수만큼씩 벌집이 증가하는 형태를 나타냅니다. 1번 방에서 시작하기 때문에 첫번째 6의 배수 안에 숫자로 가기 위해서는 총 두 번, 두번째 6의 배수 안의 숫자로는 세 번 이동하면 갈 수 있습니다.

 

이를 Go Lang에서 반복문과 조건문을 통해 구성하면 됩니다.

 

package main

import "fmt"

func main() {
	var a int
	fmt.Scanln(&a)

	b := 1
	c := 1
	for {
		if b >= a {
			break
		}
		b += c * 6
		c++
	}
	fmt.Println(c)
}

 


 

반응형
반응형

BOJ 문제풀이!


 

 

BOJ 1712번 손익분기점 Go Lang 문제풀이입니다.

 

해당 문제는 '가격'이 주어졌을 때, '고정비용' + '가변비용'의 합이 '가격'을 넘지 않는 바로 직전의 지점을 구하는 문제입니다.

 

손익분기점을 BE Point라는 이름으로 별도 함수화하여 메인 함수에서 호출하는 방법으로 소스를 작성하였습니다.

 

package main

import "fmt"

func bepoint(a, b, c int) int {
	if b >= c {
		return -1
	}
	return a/(c-b) + 1
}

func main() {
	var a, b, c int
	fmt.Scanln(&a, &b, &c)
	fmt.Println(bepoint(a, b, c))
}

 


 

 

반응형
반응형


 

2020 M1 MacBook Pro는 13.3인치라 너무 화면이 작습니다. 어쩔 수 없이(?) 모니터를 하나 써서 확장을 할 필요성이 있습니다. 개발자분들중에서는 긴 코드들도 한 화면에 보기 쉽도록 하기위해서 Pivot 모니터를 많이 사용하신다는 것을 알게되었고, 그 중에서도, 베젤이 크기 않은 것을 고르려고 했습니다. iMac 27인치 모델에 있는 손가락 한 마디보다 큰 베젤이 너무 낭비같이 느껴졌었거든요. 쿠팡, 11번가 등을 뒤적이다가 아주 저렴한 가격에 심지어 4K까지 지원이 되는 모니터를 찾을 수 있었습니다.

 

경성글로벌코리아( 너무 길어서 그런지 KSGK라고 쓰더군요 )의 UNDER DOG 71cm(28인치형) 4K 피벗 베젤리스 모니터가 그것입니다. 다소 아쉬운점들도 있었지만 무결점 기준 27만원의 저렴한 가격에 4K 피벗 28인치 모니터라는 점이 굉장히 메리트가 있는 제품이 아닌가 싶습니다. 직접 한 번 살펴보시죠. 

 

 


 

 

박스 포장되어 잘 도착한 KSGK UNDER DOG 모니터입니다. AMD RADEON 프리싱크를 지원하는 것으로 보이네요. 박스 겉면에 찍힌 자국이나 문제 있어보이는 부분이 없는지 확인하고 개봉해줍니다.

 

 

먼저 부속품들이 나옵니다. 조립해야할 거치대들이 보이네요.

 

 

모니터를 지지해줄 받침대와 전원 케이블, DP케이블이 기본 동봉되어있습니다. HDMI 케이블을 쓰실 경우에는 별도 구매를 해주셔야합니다.

 

 

부속품을 꺼내고 나면 양면으로 스티로폼에 쌓여있는 모니터를 확인할 수 있습니다. 모니터 앞뒤로 스티로폼이 잘 보호해주고 있어서 파손위험을 많이 줄이기 위해 노력했구나라는 느낌을 받을 수 있었습니다. 

 

 

베젤이 어디까지인지 이 사진에서 보이진 않지만 상당히 얇아 들고 움직일 때 주의를 기울였습니다. 모니터 아래에는 UNDER DOG라고 적혀있네요. LG도 저렇게 쓰던데..

 

 

조립자체는 굉장히 쉽습니다. 거치대 연결을 해주고 모니터를 홈에 잘 맞춰주기만 하면 튼튼하게 잘 고정됩니다. 조립과정을 찍어볼까 생각했었는데 별로 사진으로 찍을만한 부분도 없을만큼 간단합니다. 요즘 모니터들은 다 조립이 간편하게 된다는게 참 좋은 점인 것 같습니다.

 

 

조립 후 정면에서 보면 이런 모습입니다. 화면이 제법 넓습니다!

 

 

모니터를 잡고 살짝 돌리면 잘 돌아갑니다. Pivot도 잘 되는지 확인!

 

 

전원 케이블과 MacBook Pro와의 HDMI 연결을 끝내고 모니터 불량체크에 들어갑니다.

 

 

위와 같은 모니터 테스트는 monitor.co.kr 에서 쉽고 빠르게 진행할 수 있습니다.

 

monitor.co.kr - 모니터 불량화소 테스트 사이트

Copyright ⓒ monitor.co.kr. All rights reserved.

monitor.co.kr

 


 

모니터를 MacBook Pro에 연결하여 직접 3주 정도 사용해보았습니다. 일단 Pivot 모니터는 처음 써보았는데 코드를 보기에 좋은 점이 있지만 가로로 긴 와이드 28인치형이기 때문에 피벗으로 쓸 때 위가 너무 높아 적응이 좀 필요했습니다. 길이가 생각했던거보다 많이 길어서 Pivot으로 세웠을 때 생각보다 굉장히 길쭉한 느낌을 받았습니다.

 

이 모니터의 장점은 무엇보다 가성비라고 할 수 있겠습니다. 4K와 28인치, 베젤리스에 Pivot까지 만족하면서도 27만원대의 굉장히 저렴한 가격이 크게 다가옵니다. 같은 스펙의 LG, 필립스 등의 다른 대기업의 모델은 최소 40이상, 좀 좋은 모델은 70만원씩도 가는데 거의 반값 수준이라는 점이 가장 큰 메리트라고 볼 수 있겠습니다. 위의 개봉기 사진에도 있듯이 베젤이 굉장히 얇습니다. 저처럼 iMac의 말도안되게 넓은 베젤에 질리신 분들이라면 베젤리스를 선호할 수 밖에 없으실텐데 그 부분은 굉장히 만족스럽습니다. 4K 라는 점 또한 훌륭합니다.

 

다만 단점으로 A/S 부분은 당연히 대기업 수준의 눈높이로보면 안되는 것이라 제외하더라도, 모니터 설정 조작버튼이 아주 불편하게 뒤쪽에 있는데다가 클릭감도 좋지 못합니다. 많은 모니터들이 모니터 아래쪽에 조그스틱을 배치하는 것과 굉장히 대조되는 모습입니다. 모니터 설정하기가 쉽지 않다는 느낌을 많이 받으실 수 밖에 없을 것 같습니다. 또한 HDMI 사용시 모니터 자체 스피커를 사용할 수 있는데 음질이 굉장히 떨어집니다. 사실상 저는 없다고 생각하고 쓰는 수준인데, 어차피 대부분의 스피커는 이어폰이나 MacBook Pro의 스피커가 좋은 편이므로 모니터의 스피커는 쓰지 않기 때문에 크게 중요하지 않을 수도 있습니다. 어쨋거나 안쓰시게 될 정도로 스피커는 심각한 편인 것 같습니다. 

 

종합적으로 보자면 굉장히 뛰어난 가성비를 가진 4K 모니터입니다. 하나의 모니터로 다양한 활용이 가능하며 거의 대부분의 경우 굉장히 뛰어난 편에 속합니다. 생각보다 큰 단점들이 몇가지 존재하긴 하나 모니터 자체의 괜찮은 성능과 저렴한 가격을 생각하면 충분히 납득이 가능한 수준이라고 생각됩니다.

 

 

반응형
반응형


 

여러분은 블루투스 무선 마우스를 사용하고 계신가요? 저는 이번에 M1 MacBook Pro를 구매하게 되면서 기존에 데스크탑용으로 사용하고 있는 Logitec G403 유무선 마우스를 쓰려고 했으나! MacBook Pro에는 USB-A 타입의 포트가 없습니다. USB C type 단자가 두 개 있는게 전부죠. 허브를 사용해서 쓸 수 있기는 합니다만 제가 MacBook Pro를 구매한 이유가 휴대성도 꽤 큰 몫을 차지 했기 때문에, 허브를 늘 들고 다닐 수는 없고! 이 참에 블루투스 마우스도 함께 구매했습니다. 보통은 MacBook Pro와 함께 사용할 수 있는 정품 매직 마우스를 많이 사용하시지만, 저는 매직 마우스가 너무 불편해서 이번엔 방향을 좀 틀어서 아예 다른 브랜드로 구매해보았습니다.

 

Microsoft의 Arc 블루투스 무선 마우스입니다! Arc 무선 마우스는 실제 사용한 후기도 아주 간략하게 다뤄볼 것입니다. 필요하신 내용이 있으실 거라 생각해요. 간단 리뷰를 시작합니다!

 


Microsoft의 Arc 블루투스 무선 마우스는 블루투스 전용 마우스입니다. 

 

 

제가 구매한 Arc 무선 마우스의 색상은 라벤더 입니다. 개인적으로는 블랙이 다른 일반적인 마우스의 블랙보다 조금 더 딥블랙한 느낌이라 제 스타일이긴 했지만 품절인 관계로 고민 끝에 라벤더로 선택했습니다.

 

 

첫 인상은 생각보다 훨씬 괜찮아서 마음에 들었습니다. 스마트폰도 요즘 라벤더, 퍼플 같은 연보랏빛의 컬러가 인기인데 마우스의 경우 아이폰12 mini 퍼플이나 이번에 출시된 갤럭시 Z 플립3진한 느낌의 보랏빛이 아니라 더 색이 옅은 연보랏빛입니다. 라벤더 느낌이 잘 와닿는 컬러감이라는 느낌이었습니다. 일단 첫인상은 굉장히 굿!

 

 

Microsoft Arc 무선 마우스는 USB C타입 충전방식과 같이 내장배터리를 가지고 있지 않고, 별도의 AAA 건전지를 사용합니다. 배터리 최대 사용기간은 6개월이라고 합니다. 당연히 개인마다 사용시간 등에서 차이가 있을 수 있겠지만, 어쨋든 그만큼 오래 간다는 이야기인 것 같습니다. 충전방식의 마우스와 Arc 처럼 건전지를 사용하는 방식의 마우스는 보통 취향차이입니다만 어쨋든 저는 오래가는게 최고라 생각합니다. 어떤 방식이 되었든간에요.

 

 

일반적인 마우스와 달리 Arc 무선 마우스는 ON & OFF 방식이 독특하게 되어있습니다. 마우스를 사용하고 싶으면 마우스 중간부분에 힘을 주어 구부리는 느낌으로 누르게 되면 위의 사진처럼 마우스 느낌으로 휘게 되고 전원이 ON됩니다. 이 둥근 아치형태를 가진 마우스라서 이름도 Arc 무선 마우스인가봅니다.사용하지 않을 때는 별도의 버튼을 누를 필요없이(누를 버튼도 없습니다) 다시 원래대로 펴주시면 OFF됩니다. 

 

위에서보면 이런 느낌입니다.

 

마우스를 실제 사용해보시면, 크기가 생각보다 더 작습니다. 기본적으로 쭉 펴진 상태에서도 마우스가 큰 편이 아닌데 사용할 때는 Arc형태로 접히다보니까 처음 볼 때보다도 크기가 더 작아집니다. 손이 작으신분들께서는 쓰기에 좋으실지 모르겠으나 우선 저에게는 매우 불편했습니다. 클릭시에 손목에 무리가 많이 가는 편이었습니다. 그리고 스크롤이 매직 마우스와 같이 터치형식이어서 이 또한 호불호가 갈릴 순 있습니다만 개인적으로는 매직 마우스보다는 Arc 무선 마우스 쪽이 스크롤 느낌은 조금 더 좋았고 인식도 괜찮은 느낌이었습니다. 다만 Mac에서 사용되는 다양한 매직 마우스의 제스쳐들을 사용할 수 없는 단점이 있습니다. (두 손가락으로 이전 페이지 전환과 같은..) 

 


 

결론적으로,

 

휴대가 매우 간편하고 배터리가 오래가며(6개월정도) 라벤더 외에도 다양하게 구성된 색상들이 매우 매력적이며, 간편하게 사용할 수 있는 블루투스 마우스로는 아주 좋습니다. 

 

하지만 일반적인 마우스보다 훨씬 작은 크기터치 형식의 스크롤이 취향을 많이 탈 것 같다는 점이 단점이 될 수 있겠습니다.

 

게이밍용이나 마우스를 많이 사용하는 경우가 아니시라면 휴대와 색상이 매우 뛰어나고 좋으니 써보시는 것도 추천드립니다! 가격 같은 경우는 개인마다의 차이가 있을 수 있으니 중립의견! 저렴한 편은 아닙니다! (약 8~9만원 정도..)

 

 

반응형
반응형


 

다가올 2021년 하반기에 M1X 혹은 M2 CPU가 탑재된 16인치 MacBook Pro 발표가 어느정도 확정적으로 보이는 상황입니다. 하지만 저는 이번에 2020 M1 MacBook Pro를 구매했습니다. 조금 더 기다리지.. 라는 생각이 드셨나요? 사실 저 또한 마찬가지지만! 곧 노트북을 적극 사용해야할 시기가 오는데 보통 루머로 나오는 16인치 MacBook Pro 발표시기인 11월정도까지 기다릴 수는 없었습니다. 잘 사용하고 언젠가 또 바꿀 시기가 올 때는 더 많은 발전이 있겠죠? 최적의 MacBook 구매 시기는 가장 필요할 때라는 이야기가 있으니까요. 

 

그리하여, 이번에 구매하게 된 M1 MacBook Pro 개봉기 정도만 일단 아주 간단하게 작성해보려 합니다. 기본적 스펙이나 사용기, 팁 등은 조금 더 사용하고 나서 별도로 포스팅해볼까 합니다. 누구나 다 아는 내용으로 구성하기보다 우리 개발자들에게 좋은 것들은 어떤 것들이 있는지 직접 체험해보고 좋은 팁을 드릴 수 있도록 준비할께요!

 


 

 

2020 M1 MacBook Pro는 스펙에 상관없이 모두 13.3인치 모델입니다. 

 

 

제가 선택한 모델은 스페이스 그레이입니다. 실제 색상은 위의 사진보다는 조금 더 진회색의 느낌이 강합니다. 애플정품매장에서 실물로 봤던 실버 색상의 MacBook의 색상이 이런 느낌이라면, 스페이스 그레이는 이 색상에 조금 더 가깝습니다. 저에게는 스페이스 그레이가 조금 더 고급스러운 느낌이 들었습니다. 

 

 

구성품은 매우 심플합니다. 최근의 애플이 내세우고 있는 ESG 경영과 궤를 같이 한다고 해야할까요. 전체적으로 조금 많이 심플합니다. 가격도 있는데 좀 더 넣어주지.. C to C 케이블과 기본적인 설명서, Apple 스티커가 있는 작은 봉투가 있습니다.

 

 

봉투 안에는 생각보다 훨씬 거대한 전원 어댑터가 있습니다. 일반적으로 사용하는 윈도우 기반의 노트북들에 사용되는 전원 어댑터들도 가끔 스펙에 따라 꽤 큰 녀석들이 있는데, 제 개인적인 의견이지만 MacBook Pro의 전원 어댑터가 더 큰 느낌이 들었습니다. 무게도 상당히 묵직합니다.

 

 

MacBook Pro을 처음 열어보면 위와같이 되어있습니다. 열리자마자 알아서 전원On됩니다.

 

 

언어 설정을 시작으로, 기본적인 세팅을 할 수 있습니다!

 


 

정말 간단하고 심플한 개봉기는 여기까지입니다! 이 친구가 이제 저의 개발 동반자가 되어줄 것입니다. 오랫동안 잘 버텨주길!

반응형
반응형


 

AWS를 처음 접하신다면 일단 AWS의 제품들을 사용하기에 앞서, 우선 프리티어 사용가능 여부를 확인하시기 바랍니다.

 

AWS Free Tier의 유형. AWS 홈페이지에 자세한 안내가 있습니다!

 

AWS 프리티어 오퍼는 AWS 신규 가입자에게 12개월간 무료로 제공되는 서비스들을 활용할 수 있도록 하는 서비스입니다. 12개월동안 모든 제품군을 무료로 쓸 수 있다는 것은 아닙니다. 처음 사용을 시작한 시점부터 일정 기간까지만 무료 사용이 가능한 평가판 제품군이 있고, 언제나 무료로 사용가능한 제품군도 존재합니다. 

 

대표적으로 AWS의 EC2 (Elastic Compute Cloud) 는 750시간의 인스턴스를 제공하고, S3 (Simple Storage Service) 의 경우 5GB의 표준 스토리지 용량과 함께 PUT Request 2000건, GET Request 20,000건을 제공합니다. 제가 주로 사용하는 두 제품군의 경우는 위와 같습니다만, 다른 수많은 프리티어 제품군이 있고 각각의 무료 사용 한도나 기간 등이 다르기 때문에 필요하신 서비스는 직접 확인해보시는 것이 가장 좋습니다.

 

먼저 계정을 처음 생성하여 AWS를 사용하실 분들은 제가 설명드릴 Promotion Credits를 바로 등록하지마시고 프리 티어를 통해 경험해보시고 충분히 AWS에 적응이 되고 난 후에 사용하시는 것이 좋을 것입니다.

 

Promotion Credits를 등록하시게 되면 AWS의 다양한 제품군에 사용이 가능한 $300 크레딧을 받을 수 있습니다. 유료로만 사용가능한 Blockchain, IoT 등의 제품군을 경험해보시기 좋은 기회가 될 것입니다. 등록 방법은 매우 간단합니다.

 

우선 AWS 계정을 생성하시고, 생성하신 분들은 아래의 사이트로 접속하신 후에 AWS 프로모션 크레딧 신청 양식을 작성해주시면 됩니다.

 

 

크레딧 신청하기

 

클라우드 서비스 | 클라우드 컴퓨팅 솔루션| Amazon Web Services

개발자, 데이터 사이언티스트, 솔루션스 아키텍트 또는 AWS에서 구축하는 방법을 배우는 데 관심이 있는 모든 사용자용 무료 온라인 교육 AWS 전문가가 구축한 500개 이상의 무료 디지털 교육 과정

aws.amazon.com

 

작성하시고 나서 승인되면 $300 크레딧이 승인되었다는 메일이 도착합니다.

 

$300 크레딧을 받았습니다!

 

메일이 혹 도착하지 않으셨더라도 확인하실 수 있는 방법이 있습니다. aws 콘솔에 로그인 하셔서 자신의 아이디를 클릭해보시면 다음과 같은 창이 뜹니다

 

내 결제 대시보드로 가서 

 

 

크레딧란을 클릭합니다.

 

 

크레딧란에 $300 크레딧이 정상적으로 들어와있음을 확인하실 수 있습니다.

 

 

반응형
반응형

Go의 인기 Web Framework 'Gin' 


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


이번 시간에는 기사 리스트의 뼈대를 만들고 테스트해보도록 하겠습니다.

 

1. 뷰 템플릿 작성

 

메인 페이지에 기사(Article) 리스트가 표시될 예정이므로 새로 템플릿을 만들 필요는 없습니다. 하지만 현재의 내용을 기사 리스트로 대체하려면 index.html 템플릿에 변경이 필요합니다.

 

이 수정사항을 적용하기 위해서 기사 리스트가 payload라는 변수의 템플릿에 전달된다고 해봅시다. 이러한 가정하에서 다음의 snippet은 모든 기사의 리스트들을 표시해야 합니다.

 

  {{range .payload }}
    <!--ID를 기준으로 기사에 대한 링크를 만듭니다-->
    <a href="/article/view/{{.ID}}">
      <!--기사의 제목을 표시-->
      <h2>{{.Title}}</h2>
    </a>
    <!--기사의 컨텐츠를 표시-->
    <p>{{.Content}}</p>
  {{end}}

 

이 snippet은 payload 변수의 모든 항목을 반복하고, 각 기사의 제목과 컨텐츠를 표시합니다. 위의 snippet도 각 기사로 연결됩니다. 아직 개별 기사들을 표시하기 위한 라우트 핸들러를 정의하지 않았기 때문에 이 링크는 예상대로 작동되지 않을 것입니다.

 

업데이트 된 index.html 파일은 다음의 코드를 포함하여야 합니다.

 

<!--index.html-->

<!-- header.html 템플릿을 이 위치에 포함시킵니다. -->
{{ template "header.html" .}}

  <!--Loop over the `payload` variable, which is the list of articles-->
  {{range .payload }}
    <!-- ID를 기준으로 기사에 대한 링크를 만듭니다. -->
    <a href="/article/view/{{.ID}}">
      <!-- 기사의 제목을 표시 -->
      <h2>{{.Title}}</h2>
    </a>
    <!-- 기사의 컨텐츠를 표시 -->
    <p>{{.Content}}</p>
  {{end}}

<!-- footer.html 템플릿을 이 위치에 포함시킵니다 -->
{{ template "footer.html" .}}

 

2. 유닛 테스트를 포함한 라우터 핸들러 요구사항 지정

 

index 경로에 대한 핸들러를 만들기 전에 이 라우터 핸들러의 예상 동작을 정의하는 테스트를 먼저 만들어보도록 합시다. 이 테스트는 다음의 조건들을 확인해볼 것입니다

 

  1.  핸들러는 HTTP status 200을 응답합니다
  2.  반환된 HTML에는 'Home page' 텍스트가 포함된 제목 태그를 포함합니다. 

테스트를 위한 코드는 handlers.article_test.go 파일의 TestShowIndexPageUnauthentified 함수에 저장됩니다. 우리는 이 함수가 사용하는 헬퍼 기능을 common_test.go 파일에 두도록 할 것입니다.

 

handler.article_test.go의 내용은 다음과 같습니다

 

//------------------- handlers.article_test.go -----------------//

package main

import (
	"io/ioutil"
	"net/http"
	"net/http/httptest"
	"strings"
	"testing"
)

// ----- 홈페이지에 대한 GET 요청이 인증되지 않은 사용자에 대해 HTTP 200 코드가 있는 홈페이지를 반환하는지 테스트합니다 ----- //
func TestShowIndexPageUnauthenticated(t *testing.T) {
	r := getRouter(true)

	r.GET("/", showIndexPage)

	// ---- 위의 라우터로 보낼 요청을 생성합니다 ----- //
	req, _ := http.NewRequest("GET", "/", nil)

	testHTTPResponse(t, r, req, func(w *httptest.ResponseRecorder) bool {
		// ----- HTTP status 코드가 200인지 확인합니다 ----- //
		statusOK := w.Code == http.StatusOK

		// ------ 페이지의 제목이 'Home Page' 인지 테스트합니다 ------- //
		// --- HTML 페이지를 파싱하고 처리할 수 있는 라이브러리를 사용하여 훨씬 디테일한 테스트를 수행합니다 --- //
		p, err := ioutil.ReadAll(w.Body)
		pageOK := err == nil && strings.Index(string(p), "<title>Home Page</title>") > 0

		return statusOK && pageOK
	})
}

 

common_test.go 의 내용은 다음과 같습니다.

 

package main

import (
	"net/http"
	"net/http/httptest"
	"os"
	"testing"

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

var tmpArticleList []article

// ------- 이 함수는 테스트 함수를 실행하기 전, 설정에 사용합니다 ----- //
func TestMain(m *testing.M) {
	// ----- Gin을 테스트 모드로 설정합니다 ----- //
	gin.SetMode(gin.TestMode)

	// ------ 다른 테스트를 실행합니다 ------ //
	os.Exit(m.Run())
}

// ---- 테스트 중 라우터를 만드는 헬퍼 함수 ---- //
func getRouter(withTemplates bool) *gin.Engine {
	r := gin.Default()
	if withTemplates {
		r.LoadHTMLGlob("templates/*")
	}
	return r
}

// ----- 요청을 처리하고 응답을 테스트하는 헬퍼 함수 ------- //
func testHTTPResponse(t *testing.T, r *gin.Engine, req *http.Request, f func(w *httptest.ResponseRecorder) bool) {

	// ---- 응답 레코더 생성 ---- //
	w := httptest.NewRecorder()

	// ------ 서비스를 생성하고 위의 요청을 처리합니다 ----- //
	r.ServeHTTP(w, req)

	if !f(w) {
		t.Fail()
	}
}

// ---- 이 함수는 테스트를 위해 메인 리스트를 임시 리스트에 저장하는데 사용됩니다 ----- //
func saveLists() {
	tmpArticleList = articleList
}

// ------ 이 함수는 임시 리스트에서 메인 리스트를 복구하는데 사용됩니다 ------ //
func restoreLists() {
	articleList = tmpArticleList
}

 

우리는 이 테스트를 구현하기 위해 몇가지의 헬프 함수를 작성했습니다. 이 함수들은 유사한 기능을 테스트하기 위해 추가 테스트를 작성할 때, 상용 코드를 줄이는 데 도움을 줄 것입니다.

 

TestMain 함수는 Gin이 테스트 모드를 사용하도록 설정하고, 나머지 테스트 함수를 호출합니다. getRouter 함수는 메인 어플리케이션과 유사한 방법으로 라우터를 만들고 반환합니다. saveLists() 함수는 원본 기사 목록을 임시 변수에 저장합니다. 이 임시 변수는 restoreLists() 함수에 의해 유닛 테스트가 실행된 후 기사 리스트를 초기 상태로 복원하는데 사용됩니다.

 

최종적으로, testHTTPResponse 함수는 전달된 함수를 실행하여 테스트의 성공 여부를 나타내는 boolean true 값을 반환하는지 확인합니다. 이 함수는 HTTP 요청의 응답을 테스트하는 데 필요한 코드가 중복이 되지 않도록 하는데 도움을 줄 것입니다.

 

HTTP 코드와 반환된 HTML을 확인하려면 다음의 몇가지를 수행합니다.

 

  1.  새 라우터를 생성합니다.
  2. 기본 App이 사용하는 것과 동일한 핸들러를 사용하도록 경로를 정의합니다. (ShowIndexPage)
  3. 이 라우터에 접근할 수 있는 새 요청을 생성합니다.
  4. HTTP 코드와 HTML을 테스트하기 위해 응답을 처리하는 함수를 만듭니다.
  5. testHTTPResponse() 함수를 호출하여 이 테스트를 완료합니다

 

3. 라우터 핸들러 만들기

 

우리는 handler.article.go 파일에 기사와 관련된 기능에 대한 모든 라우터 핸들러를 생성할 것입니다. 인덱스 페이지 핸들러 showIndexPage 는 다음의 작업을 수행하도록 합니다.

 

3-1. 문서 목록을 가져옵니다.

 

이 작업은 이전에 정의된 getAllArticles 함수를 사용하여 수행될 수 있습니다.

 

articles := getAllArticles()

 

 

3-2. 기사 리스트를 전달하는 index.html 템플릿을 렌더링합니다.

 

이 작업은 아래의 코드를 사용합니다.

 

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

 

이전 단계의 버전과의 유일한 차이점은 payload라는 변수가 템플릿에 접근할 기사 리스트를 전달한다는 것입니다.

 

handlers.article.go 는 다음의 코드를 포함하여야 합니다.

 

// handlers.article.go

package main

import (
	"net/http"

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

func showIndexPage(c *gin.Context) {
	articles := getAllArticles()

	// ---- Context의 HTML 메소드를 호출하여 템플릿을 렌더링합니다 ---- //
	c.HTML(
		// ----- HTTP Status를 200(OK)로 설정합니다 ------ //
		http.StatusOK,
		// ----- index.html 템플릿을 사용합니다 ------ //
		"index.html",
		// ---- 페이지에서 사용하는 데이터를 전달합니다 ----- //
		gin.H{
			"title":   "Home Page",
			"payload": articles,
		},
	)

}

 

이제 어플리케이션을 실행하고 브라우저에서 https://localhost:8080 에 접속하면 다음과 같은 화면을 볼 수 있습니다.

 

기사 제목과 내용이 보입니다!

 

현재까지의 소스 tree는 다음과 같습니다.

 


다음 시간에는 메인 페이지가 아닌 기사 하나하나의 링크에 맞는 경로 설정을 해보도록 할 예정입니다. 이번 포스팅에서는 많은 내용의 코딩이 필요하므로 실수하지 않도록 꼼꼼하게 체크해주는 것도 필요합니다! 

반응형
반응형

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 템플릿과 라우터 핸들러를 만들어 각종 기능을 더 추가해보도록 할 예정입니다.

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

 

 

반응형
반응형

Go 의 인기 Web Framework 'Gin'


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


이번 시간에는 기본 튜토리얼 템플릿의 연결을 완료하고 검증해보는 과정의 첫 단계를 직접 만들어보고자 합니다.


1. 설치 완성하고 검증하기

템플릿을 모두 만드셨다면 이제 어플리케이션 도입부에 해당하는 파일을 만들 차례입니다. 인덱스 템플릿을 사용할 수 있도록 구성된 가장 단순한 웹 어플리케이션이 포함된 main.go를 만들어 보도록 하겠습니다. 우리는 Gin을 사용해서 네 단계로 이 과정을 진행할 수 있습니다.

 

1-1. 라우터 만들기

Gin에서 라우터를 만드는 기본적인 방법은 다음과 같습니다.

 

router := gin.Default()

 

이를 통해 어플리케이션의 빌드를 정의하는데 사용될 라우터를 만들 수 있습니다.

 

1-2. 템플릿 불러오기

라우터를 제작했다면, 다음의 방법으로 모든 템플릿을 불러올 수 있습니다

 

router.LoadHTMLGlob("templates/*")

 

이를 통해 Templates 폴더의 모든 템플릿 파일들이 불러와지고, 한 번 로딩되면 매번 요청 때마다 다시 읽어올 필요가 없고, 이러한 점이 Gin 웹 어플리케이션을 매우 빠르게 만들어줍니다.

 

1-3. 라우터 핸들러 정의하기

Gin의 가장 중요한 핵심어떻게 어플리케이션의 다양한 경로들을 나누고, 핸들러를 각 경로에 정의하는가에 있습니다. 이번에는 인덱스 페이지에 대한 라우터와 인라인 라우터 핸들러를 만들 것입니다.

 

	router.GET("/", func(c *gin.Context) {
    // ------ Context의 HTML 메소드를 호출하여 템플릿을 렌더링합니다. ----- //
		c.HTML(
			// ----- HTTP 상태를 200(OK)에 세팅합니다 ------ //
			http.StatusOK,
			// ------ index.html 템플릿을 사용합니다 ------- //
			"index.html",
			// ----- 페이지에서 사용하는 데이터 전달 ------- //
			gin.H{
				"title": "Home Page",
			},
		)
	})

 

router.GET 메소드는 GET 요청에 대한 라우터 핸들러를 정의하는데 사용됩니다.

 

라우터 핸들러에는 gin.Context 에 대한 포인터를 매개변수로 가지고 있습니다. 이 컨텍스트는 핸들러가 요청을 처리하는 데 필요할 수 있는 요청에 대한 모든 정보를 포함합니다. 예를 들면, Header, 쿠키와 같은 정보들을 말합니다.

 

컨텍스트에는 HTML, TEXT, JSON, XML 형식으로 응답을 렌더링하는 메소드도 있습니다. 이 경우 HTML 템플릿(index.html)을 렌더링하기 위해 context.html 메소드를 사용합니다. 이 메소드에 대한 호출에는 title값이 Home Page ("title": "Home Page" 부분)로 설정된 추가 데이터가 포함됩니다.  HTML 템플릿에서 사용할 수 있는 값입니다.

 

1-4. 어플리케이션 시작하기

어플리케이션을 시작하기 위해 라우터의 Run 메소드를 사용할 수 있습니다.

 

router.Run()

 

이를 통해 localhost에서 어플리케이션이 시작되고, 기본값으로 8080 포트에서 구동됩니다.

 

완성된 main.go 소스코드는 다음과 같습니다.

 

▶ 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",
			},
		)
	})

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

}

 

Mac OS의 경우 터미널, Windows의 경우 CMD 창에서 해당 프로젝트를 생성한 디렉토리로 이동한 후에 다음의 명령어를 실행시켜봅니다.

 

go build -o app

 

어플리케이션이 빌드되고 다음과 같이 실행할 수 있는 실행 파일 이름이 지정된 어플리케이션이 생성됩니다.

 

./app

 

여기까지 모든 진행사항을 충실히 작업하시면서 따라오셨다면, http://localhost:8080에서 우리가 제작한 어플리케이션에 접속할 수 있습니다. 실행시 다음과 같이 실행이 됩니다.

 

localhost:8080으로 접속한 화면

 

디버그 작업을 통해 로드된 HTML 템플릿을 확인!

 

현 시점에서의 어플리케이션 디렉토리 구조는 다음과 같이 구성이 되어있으실 겁니다

 

현재까지 작성된 디렉토리 구조

 


 

다음 시간에는 라우터를 초기화하고 기사(Article)을 작성할 수 있는 템플릿을 생성하고 테스트를 하는 과정을 진행해보도록 하겠습니다. 짧은 내용이지만 직접 제작해보시고 구동해보시면서 Gin을 체험해보세요!

반응형

+ Recent posts