+3

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). 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.png Server 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.png image.png Client 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.png image.png Bi-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: %v\n", resp.GetMax())
		}
		close(waitc)
	}()

	<-waitc
}

Kết quả đây nè: image.png image.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


All Rights Reserved

Viblo
Let's register a Viblo Account to get more interesting posts.