얼마 전에 저는 프론트엔드에는 Angular 2를, 백엔드에는 Golang을 사용한 채팅 애플리케이션입니다.. 웹 소켓 덕분에 둘 사이의 메시지 통신이 가능했습니다. 이 예제에서는 여러 Angular 2 클라이언트가 Golang 애플리케이션에 연결하여 서로 통신할 수 있었지만, 새 클라이언트는 과거 메시지를 볼 수 없었습니다. 이는 데이터가 전송된 후 저장되지 않았기 때문입니다.

이전에 만든 Golang 애플리케이션을 확장하여 다음을 포함할 것입니다. 카우치베이스 를 지원하므로 메시지가 전송된 후 저장되었다가 새 클라이언트가 연결될 때 로드됩니다.
요구 사항
이 프로젝트를 진행하려면 몇 가지 요구 사항이 있습니다. 다음과 같습니다:
이전 가이드에서 수행한 작업의 대부분을 다시 살펴볼 것이므로 채팅 서버가 작동하는 것이 매우 중요합니다. Couchbase NoSQL 데이터베이스를 포함시키는 것은 간단하지만 N1QL 쿼리를 지원하는 Couchbase가 이미 설치되어 있어야 합니다.
카우치베이스 서버 버킷 만들기 및 인덱스 추가하기
이 프로젝트는 Couchbase에서 버킷을 하나 이상 생성해야 합니다. 이 버킷에는 Golang 채팅 서버와 주고받는 모든 메시지 데이터가 저장됩니다. 저장된 데이터는 다음과 같은 형태입니다:
1 2 3 4 5 |
{ "sender": "62f142ce-7308-4dae-9eb0-3ae61d363c22", "content": "안녕하세요, 닉 라보이!", "timestamp": 1482174735 } |
카우치베이스를 사용하도록 선택할 수 있습니다. 기본값 버킷을 사용하거나 새 버킷을 만들 수 있습니다. 저는 다음과 같은 버킷을 사용하겠습니다. 예제 이 프로젝트에서.
쿼리가 포함되므로 버킷에서 사용할 수 있는 인덱스를 하나 이상 정의해야 합니다. 이 인덱스는 Couchbase 쿼리 워크벤치 또는 Couchbase 셸(CBQ)을 사용하여 만들 수 있습니다. 이러한 도구 중 하나를 사용하여 다음을 실행합니다:
1 |
만들기 기본 INDEX 켜기 `예제` 사용 GSI; |
인덱스가 생성되면 NoSQL 스토리지를 포함하도록 애플리케이션을 수정할 수 있습니다.
카우치베이스 서버에 연결 설정하기
Couchbase에 데이터 저장을 시작하려면 먼저 Go 애플리케이션에서 연결이 설정되어야 합니다. 만약 이전 가이드로 설정하면 Go 애플리케이션이 다음과 유사한 경로에 있을 수 있습니다. $GOPATH/src/github.com/nraboy/realtime-chat/main.go.
소스 코드 파일을 열기 전에 Couchbase용 Golang SDK를 설치해야 합니다. 실행하여 설치할 수 있습니다:
1 |
go get github.com/카우치베이스/gocb |
Couchbase SDK가 설치된 상태에서 다음을 엽니다. $GOPATH/src/github.com/nraboy/realtime-chat/main.go 를 추가하고 함수 외부에 다음 줄을 포함하세요:
1 |
var 버킷 *gocb.버킷 |
변수를 함수 외부에 포함시킨 이유는 특정 함수에 국한된 것이 아니라 애플리케이션에 전역적으로 적용되기를 원하기 때문입니다.
내부 메인
함수에서 클라이언트 관리자의 고루틴 전에 클러스터에 대한 연결을 설정하고 특정 버킷을 열려고 합니다. 이 작업은 다음을 통해 수행할 수 있습니다:
1 2 |
클러스터, _ := gocb.연결("couchbase://localhost") 버킷, _ = 클러스터.OpenBucket("예제", "") |
위의 시나리오에서는 로컬로 실행 중인 노드에 연결하고 예제 버킷을 만들 수 있습니다.
이제 Couchbase를 사용할 준비가 되었으므로 데이터 모델에 집중할 수 있습니다.
Couchbase JSON 데이터 모델 정의하기
앞서 제안된 JSON 데이터 모델을 살펴봤지만, 이를 Golang을 통해 가능하게 만들어야 합니다. 이를 위해 Golang 데이터 구조를 사용합니다.
다른 기존 데이터 구조 근처에는 다음을 포함하세요:
1 2 3 4 5 6 |
유형 메시지 구조체 { 발신자 문자열 `json:"발신자, 생략"` 수신자 문자열 `json:"수신자, 생략"` 콘텐츠 문자열 `json:"콘텐츠, 생략"` 타임스탬프 int64 `json:"타임스탬프, 생략"` } |
위 메시지
구조에는 JSON 요소에 매핑된 프로퍼티가 있습니다. 우리가 사용하기로 선택하지는 않았지만 있으면 좋을 것 같은 한 가지 요소는 수신자
. 나중에 특정 고객에게 메시지를 보내고 싶을 때가 있을지도 모릅니다.
카우치베이스는 다음과 같이 직접 작업할 수 있습니다. 메시지
구조를 사용하여 데이터를 저장하고 읽을 수 있습니다. 웹소켓을 통해 전송하려면 JSON으로 마샬링할 수 있습니다.
카우치베이스로 메시지 저장 및 불러오기
이제 데이터를 저장하고 로드하는 단계로 넘어갑니다. 연결이 설정된 데이터베이스 설정이 완료되었습니다. 데이터 모델이 생겼습니다. 이제 이를 활용해 보겠습니다.
간단하게 하기 위해 모든 문서 ID를 고유하게 유지하겠습니다. 이 작업은 명령줄을 통해 다음과 같이 설치할 수 있는 UUID 라이브러리를 통해 수행할 수 있습니다:
1 |
go get github.com/사토리/go.uuid |
애플리케이션 내에서 저장 메시지
메서드를 다음과 같이 설정합니다:
1 2 3 |
func 저장 메시지(메시지 *메시지) { 버킷.Upsert(uuid.NewV4().문자열(), 메시지, 0) } |
저희는 메시지
를 클릭하고 새 문서 키를 생성하여 데이터베이스에 삽입합니다. 즉, 모든 메시지가 고유한 문서로 저장됩니다.
그렇다면 연결이 설정되었을 때 데이터를 로드하는 것은 어떨까요?
1 2 3 4 5 6 7 8 |
func (관리자 *ClientManager) 로드메시지(클라이언트 *클라이언트) { 쿼리 := gocb.NewN1qlQuery("SELECT `example`.* FROM `example` ORDER BY timestamp") 행, _ := 버킷.ExecuteN1qlQuery(쿼리, nil) var 행 메시지 var jsonMessage []바이트 에 대한 행.다음(&행) { jsonMessage, _ = json.마샬(행) 클라이언트.보내기 |
위의 예에서 로드메시지
메서드에 대한 클라이언트
새로 연결된 클라이언트를 나타냅니다. 메시지 기록을 가져오려는 클라이언트입니다.
모든 메시지를 가져와서 순서대로 정렬하기 위해 N1QL 쿼리가 만들어집니다. 타임스탬프
값을 반환합니다. 쿼리의 각 결과는 JSON으로 마샬링되어 클라이언트 채널에 추가되어 전송됩니다.
그렇다면 이 두 가지 방법은 어떻게 사용할 수 있을까요?
웹소켓 연결이 설정되면 클라이언트 관리자가 브로드캐스팅을 위해 클라이언트를 등록합니다. 이는 프로젝트의 시작
메서드를 사용합니다. 에서 시작
메서드에는 클라이언트 등록을 위한 스위치 문이 있습니다. 다음과 같이 수정해 보겠습니다:
1 2 3 4 |
case conn := < -관리자.등록: 관리자.클라이언트[conn] = true jsonMessage, _ := json.마샬(&메시지{콘텐츠: "/새 소켓이 연결되었습니다."}) 관리자.보내기(jsonMessage, conn) 관리자.로드메시지(conn) |
클라이언트 연결이 등록되면 연결을 가져와서 해당 연결을 로드메시지
메서드를 생성했습니다. 이렇게 하면 이전에 저장된 모든 메시지가 해당 특정 클라이언트로 전송됩니다.
메시지를 저장하는 방법은 조금 달라집니다.
이전 튜토리얼에서는 읽기
메서드를 호출합니다. 다음과 같이 수정합니다:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
func (c *클라이언트) 읽기() { defer func(){ 관리자.등록 취소 < -c c.소켓.닫기() }() 에 대한{ _, 메시지, err := c.소켓.ReadMessage() 만약 err != nil { 관리자.등록 취소 < -c c.소켓.닫기() break } msg := &메시지 { 발신자: c.id, 콘텐츠: 문자열(메시지), 타임스탬프:(시간.지금()).Unix(), } jsonMessage, _ := json.마샬(msg) 저장 메시지(msg) 관리자.방송 < -jsonMessage } } |
중요한 것은 다음 줄입니다:
1 2 3 4 5 6 |
msg := &메시지 { 발신자: c.id, 콘텐츠: 문자열(메시지), 타임스탬프: (시간.지금()).Unix(), } 저장 메시지(msg) |
서버는 클라이언트로부터 메시지를 수신하고 실제 메시지
메시지를 보낸 사람과 시기 등의 추가 정보와 함께 전송합니다. 그런 다음 이 메시지는 데이터베이스에 저장됩니다.
Angular 2 클라이언트로 Golang 애플리케이션을 다시 실행해 보세요. 이제 메시지가 저장될 것입니다.
결론
방금 카우치베이스를 웹사이트에 추가하는 방법을 살펴봤습니다. 이전 웹소켓 예제 를 작성했습니다. 이전 예제에서는 웹 소켓을 사용하여 통신하는 클라이언트와 서버 채팅 애플리케이션이 있었습니다. 이 예제를 확장하여 새로운 채팅 참가자가 로드할 수 있도록 메시지 데이터를 Couchbase에 저장하기 시작했습니다.
좋은 작업
고마워요!