ساخت پروژه با معماری مایکروسرویس، زبان گولنگ، اندپوینت رست، کوبرنتیز و... (قسمت دوم)

این مطلب ادامه قسمت یک است. تو قسمت قبلی سرویس دهنده و سرویس گیرنده gRPC توسعه دادیم.تو این قسمت توضیح میدیم چطور اندپوینت‌های رست به سرویس gRPC اضافه کنیم. شما می‌تونید سورس کامل قسمت دوم رو از اینجا ببینید.

برای اضافه کردن اندپوینت‌های رست میخوایم از لایبرری grpc-gateway استفاده کنیم. اینجا یه مطلب خوب هست که با جزئیات توضیح میده grpc-gateway چطور کار میکنه.

https://medium.com/@thatcher/why-choose-between-grpc-and-rest-bc0d351f2f84


قدم اول: ملزومات رست رو به پروژه اضافه کنید.

اول از همه باید grpc-gateway و پلاگین داکیومنت جنریتور swagger نصب کنیم.

go get -u github.com/grpc-ecosystem/grpc-gateway/protoc-gen-grpc-gateway 
go get -u github.com/grpc-ecosystem/grpc-gateway/protoc-gen-swagger

لایبرری grpc-gateway در پوشه “%GOPATH%/src/github.com/grpc-ecosystem/grpc-gateway” نصب شد.

به پوشه include از لایبرری grpc-gateway نیاز داریم.

محتوای پوشه “%GOPATH%/src/github.com/grpc-ecosystem/grpc-gateway/third_party/googleapis/google” کپی کنید به پوشه “third_party/google” در پروژه‌تون.

پوشه “protoc-gen-swagger/options” در پوشه third_party پروژه تون بسازید.

mkdir -p third_party\protoc-gen-swagger\options

حالا فایل annotations.proto و openapiv2.proto از پوشه “%GOPATH%/src/github.com/grpc-ecosystem/grpc-gateway/protoc-gen-swagger/options” به پوشه “third_party\protoc-gen-swagger/options” پروژه‌تون کپی کنید.

فایل‌های پروژه‌تون باید شبیه به این شده باشه:

قبل اینکه ادامه بدیم فرض میکنیم کد جنریتور proto روی سیستم شما نصبه، برای اطمینان کد پایین رو اجرا کنید:
go get -u github.com/golang/protobuf/protoc-gen-go

حالا باید ملزومات رست رو به فایل api/proto/v1/todo-service.proto اضافه کنیم (جزئیات از اینجا ببینید)

https://gist.github.com/amsokol/57cd11e08b07542837fdbaa596864b5c
میتونید از اینجا درمورد Swagger در فایل‌های proto بیشتر بخونید.

حالا فولدر api/swagger/v1” ایجاد کنید (برای فایل‌های ساخته شده توسط Swagger) در روت اصلی پروژه:

mkdir -p api\swagger\v1

و محتوای فایل third_party/protoc-gen.cmd با کدهای پایین عوض کنید:

https://gist.github.com/amsokol/b81df9c0d48a0ab50dcbb4cf62d60b52

مطمئن بشید تو پوشه go-grpc-http-rest-microservice-tutorial هستید و کد زیر را اجرا کنید:

.\third_party\protoc-gen.cmd

فایل “pkg/api/v1/todo-service.pb.go” آپدیت شد و دو فایل جدید هم ایجاد شد:

  • pkg\api\v1\todo-service.pb.gw.go — فایل‌های مربوط به رست
  • api\swagger\v1\todo-service.swagger.json —  فایل‌های مربوط به داکیومنت جنریتور سوئگر

ساختار پروژه باید این شکلی شده باشه:

و تمام، همه ملزومات رست رو به پروژه اضافه کردیم.


قدم دوم: ایجاد سرور HTTP برای رست

فایل server.go در پوشه “pkg/protocol/rest” همراه با محتوای زیر ایجاد کنید:

https://gist.github.com/amsokol/00c3c83000a1e741f6abd130843fba0e
در یک پروژه واقعی نیاز دارید تا HTTPS کانفیگ کنی، می‌تونید یک نمونه اینجا ببینید.

حالا محتوای فایل pkg/cmd/server.go” آپدیت کنید تا سرور HTTP اجرا کنه:

https://gist.github.com/amsokol/23f4cb0ae6a440ffbe615f50cf92befa
شما باید بدونید HTTP gateway روی gRPC پیاده شده، تست‌های من نشون میده ۱-۳ میلی ثانیه سرعت کمتر شده.

ساختار پروژه باید شبیه به این شده باشه:

و تمام.


قدم سوم: اضافه کردن سرویس گیرنده رست.

فایل cmd/client-rest/main.go” همراه با محتوای زیر ایجاد کنید:

https://gist.github.com/amsokol/f22d11a666d432f7dc68aea0cee34696

این تمام کدی بود که باید برای سرویس گیرنده می‌نوشتید، ساختار پروژه باید این شکلی شده باشه:

آخرین قدم اینه مطمئن بشید سرور رست درست کار میکنه.

توی ترمینال سرور gRPC همراه با رست رو بیلد بگیرید (پارامترها رو با کانفیگ دیتابیس‌تون عوض کنید):

cd cmd/server 
go build . 
server.exe -grpc-port=9090 -http-port=8080 -db-host=<HOST>:3306 -db-user=<USER> -db-password=<PASSWORD> -db-schema=<SCHEMA>

اگر خروجی ترمینال همچین چیزی بود:

2018/10/14 13:53:27 starting HTTP/REST gateway... 
2018/10/14 13:53:27 starting gRPC server...

به این معنیه که سرور اجرا شده، یه ترمینال دیگه باز کنید و سرویس گیرنده رست اونجا بیلد کنید و اجرا بگیرید:

cd cmd/client-rest 
go build . 
client-rest.exe -server=http://localhost:8080

اگر خروجی ترمینال همچین چیزی بود:

2018/10/14 13:57:26 Create response: Code=200, Body={"api":"v1","id":"3"}
2018/10/14 13:57:26 Read response: Code=200, Body={"api":"v1","toDo":{"id":"3","title":"title (2018-10-14T10:27:26.633575Z)","description":"description (2018-10-14T10:27:26.633575Z)","reminder":"2018-10-14T10:27:26Z"}}
2018/10/14 13:57:26 Update response: Code=200, Body={"api":"v1","updated":"1"}
2018/10/14 13:57:26 ReadAll response: Code=200, Body={"api":"v1","toDos":[{"id":"3","title":"title (2018-10-14T10:27:26.633575Z) + updated","description":"description (2018-10-14T10:27:26.633575Z) + updated","reminder":"2018-10-14T10:27:26Z"}]}
2018/10/14 13:57:26 Delete response: Code=200, Body={"api":"v1","deleted":"1"}

یعنی همه چی درست کار میکنه.


خلاصه قسمت دوم:

تمام این‌ها برای قسمت دوم بود. ما سرویس گیرنده و سرویس دهنده رست رو برای gRPC توسعه دادیم.

سورس کد قسمت دوم از اینجا در دسترس شماست.

قسمت سوم درباره پیاده سازی میدلورهای (logging/tracing) روی سرویس gRPC و همچنین رست است.