Thực hành gRPC với Golang

gRPC Chúng ta có thể tìm hiểu về gRPC và Golang ở những topic trước của mình hoặc bàng các từ khóa trên mạng(gRPC thì nên search trên mạng để có góc nhìn sâu hơn nhe, mình ko chuyên gRPC cho lắm). Hôm nay chúng ta sẽ cùng thực hành gRPC với Golang nhé. Bài

gRPC

Chúng ta có thể tìm hiểu về gRPC và Golang ở những topic trước của mình hoặc bàng các từ khóa trên mạng(gRPC thì nên search trên mạng để có góc nhìn sâu hơn nhe, mình ko chuyên gRPC cho lắm).
image.png
Hôm nay chúng ta sẽ cùng thực hành gRPC với Golang nhé. Bài viết được dựa theo khóa học của anh FunzyDev các bạn có thể tham khảo chi tiết hơn ở đấy nhé, còn mình chỉ thực hành đơn giản với client server và 4 api của gRPC thôi.
Cài đặt
Tất nhiên là phải chuẩn bị cài đặt những công cụ cần thiết trước đã 😄. Nếu các bạn sử dụng windows có cài đặt Protocol Buffers qua link này nhé: https://www.geeksforgeeks.org/how-to-install-protocol-buffers-on-windows/

Tiếp theo là các package của Go dành cho grpc và protocol.

go get -u github.com/golang/protobuf/protoc-gen-go
go get -u google.golang.org/grpc

Được rồi giờ vào setup code nào. Ở đây mình sẽ setup 1 chương trình chạy các tính toán đơn giản nhé:

Các bạn tạo cho mình file .proto với đường dẫn như sau

calculator/calculatorpb/calculator.proto

Sau đó trong file .proto ta có:
image.png
Ở đây mình có define sẵn một service Calculator. Sau đó chúng ta sẽ generate code với 2 dòng terminal như sau:

protoc calculator/calculatorpb/calculator.proto --go-grpc_out=.
protoc calculator/calculatorpb/calculator.proto --go_out=.

Sau đó ta sẽ thấy một thư mục mới với 2 file là calculator_grpc.pb.go và calculator.pb.go
image.png
Tiếp đó ta sẽ tạo Server và Client nhé. Đầu tiên là Server với đường dẫn server/server.go:
image.png

Và Client với đường dẫn là client/client.go:
image.png
Sau khi setup xong hết cả Server và Client ta sẽ đi vào triển khai cả 4 API nhé:
Unary API
Mình sẽ setup một API SUM nhé: đầu tiên là khai báo API SUM trong service và tạo ra 2 message để có thể request và response nhé.
image.png
Sau đó ta sẽ chạy lại 2 dòng protoc trên( ở đây mình có sử dụng makefile để làm ngắn câu lệnh hơn các bạn có thể tham khảo)
image.png
Tiếp đến là Server và Client:
image.png
server.go
image.png
client.go
Sau đó ta callSum(client) ở hàm main file client.go rồi run cả Server và Client để thấy kết quả nhé
image.png

image.pngServer Streaming API
Chúng ta sẽ lặp lại các bước trên nhưng sẽ có thay đổi một chút ở phần cài đặt protoc để generate code nhé. Ở đây mình sẽ tiếp tục với API phân tích thừa số nguyên tố:
image.png
Và make gen-cal thôi hehe. Tiếp đến là Server và Client như cũ nhé:
image.png
server.go
image.png
client.go
Các kết quả mà ta nhận được ở cả Server và Client:
image.pngimage.pngClient Streaming API
Cố lên nào gần xong rồi, sự khác biệt giữa 4 API là không quá lơn nhưng tác dụng thì lại rất nhiều để các bạn có thể sử dụng vào nhiều solution khác nhau.
image.png
calculator.proto
image.png
server.go
image.png
client.go
Ta có kết quả:
image.pngimage.pngBi-Directional Streaming API
Phương thức cuối cùng rồi, ở đây mình sẽ làm một API tìm max nhé:
image.png
calculator.proto
image.png
server.go
Ở file client.go function khá dài nên mình sẽ để ở đây luôn nhá:

func callMax(c calculatorpb.CalculatorServiceClient) {
	log.Println("callMax is running")
	stream, err := c.Max(context.Background())
	if err != nil {
		log.Fatalf("call max err %v", err)
	}
	waitc := make(chan struct{})

	go func() {
		////send requests
		listReq := []calculatorpb.MaxRequest{
			{
				Num: 5,
			},
			{
				Num: 10,
			},
			{
				Num: 15,
			},
			{
				Num: 20,
			},
			{
				Num: 50,
			},
		}
		for _, req := range listReq {
			err := stream.Send(&req)
			if err != nil {
				log.Fatalf("sned find max request err %v", err)
			}
			time.Sleep(1000 * time.Millisecond)
		}
		stream.CloseSend()
	}()

	go func() {
		for {
			resp, err := stream.Recv()
			if err == io.EOF {
				log.Println("ending find max api...")
				break
			}
			if err != nil {
				log.Fatalf("recv find max err %v", err)
				break
			}

			log.Printf("max: %vn", resp.GetMax())
		}
		close(waitc)
	}()

	<-waitc
}

Kết quả đây nè:
image.pngimage.png

Kết

Vậy là mình đã giới thiệu được 4 API của gRPC tuy nhiên phần giải thích khá ít, các bạn có thể tham khảo chi tiết hơn ở youtube của anh FunzyDev nhé FunzyDev. Sau khi tiếp xúc với gRPC thì cá nhân mình thấy gRPC thật sự tuyệt vời và giúp chúng ta rút gọn thời gian cho những function phải implement, mình hy vọng bài viết sẽ có ích cho các bạn trong viết tiếp cận với golang cũng như gRPC. Đây chỉ là chia sẻ kiến thức cá nhân cũng như là topic để mình tự củng cố kiến thức lại nên nếu các bạn có góp ý cũng như chỉ dẫn hãy góp ý cho mình biết nhé. Cảm ơn các bạn đã đọc bài viết này, have a nice day ❤️.

Bài viết đã tham khảo

Nguồn: viblo.asia

Bài viết liên quan

Thay đổi Package Name của Android Studio dể dàng với plugin APR

Nếu bạn đang gặp khó khăn hoặc bế tắc trong việc thay đổi package name trong And

Lỗi không Update Meta_Value Khi thay thế hình ảnh cũ bằng hình ảnh mới trong WordPress

Mã dưới đây hoạt động tốt có 1 lỗi không update được postmeta ” meta_key=

Bài 1 – React Native DevOps các khái niệm và các cài đặt căn bản

Hướng dẫn setup jenkins agent để bắt đầu build mobile bằng jenkins cho devloper an t

Chuyển đổi từ monolith sang microservices qua ví dụ

1. Why microservices? Microservices là kiến trúc hệ thống phần mềm hướng dịch vụ,