You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何将Go语言API网关与.NET微服务通过gRPC对接

问题描述

我正在开发一个项目,API网关用Go语言构建,同时有2个基于.NET开发的微服务。API网关对外暴露REST API,需要把REST请求转换成gRPC请求(所有微服务之间通过gRPC通信)。我已经把.NET项目里生成服务用的proto文件复制到网关了,但不知道接下来该怎么做,求解答。

网关项目位于GitHub仓库的batistuta-booking项目的develop/api-gateway分支下。

.NET项目中用于生成服务的.proto文件(暂未实现完整功能,仅包含一个示例方法):

syntax = "proto3";

option csharp_namespace = "user_service";

package user;

// The user service definition.
service UserService {
  rpc GetUser (US_Request) returns (US_Response);
}

// The request message containing the user's name.
message US_Request {
  string name = 1;
}

// The response message containing the greetings.
message US_Response {
  string message = 1;
}
后续操作步骤

1. 在Go网关中生成gRPC客户端代码

使用protoc工具配合Go的gRPC插件,将proto文件转换为Go语言的gRPC客户端代码:

  • 先安装依赖工具:
    # 安装Protocol Buffers编译器protoc(根据系统选择对应方式,如Ubuntu用apt、Mac用brew)
    # 安装Go的gRPC相关插件
    go install google.golang.org/protobuf/cmd/protoc-gen-go@latest
    go install google.golang.org/grpc/cmd/protoc-gen-go-grpc@latest
    
  • 在网关项目中执行生成命令(假设proto文件放在proto/user目录下):
    protoc --go_out=. --go_opt=paths=source_relative \
      --go-grpc_out=. --go-grpc_opt=paths=source_relative \
      proto/user/user.proto
    
    执行后会生成user_grpc.pb.go和user.pb.go两个文件,这就是Go语言的gRPC客户端代码。

2. 实现REST到gRPC的转换逻辑

在网关的REST接口处理函数中,调用生成的gRPC客户端,完成请求转换与转发:

package main

import (
	"context"
	"net/http"

	"github.com/gin-gonic/gin"
	"google.golang.org/grpc"
	"google.golang.org/grpc/credentials/insecure"

	pb "your-gateway-project-path/proto/user" // 替换为实际生成的pb包路径
)

func main() {
	r := gin.Default()

	// 连接到.NET的UserService微服务(替换为实际微服务地址)
	conn, err := grpc.Dial("user-service:50051", grpc.WithTransportCredentials(insecure.NewCredentials()))
	if err != nil {
		panic(err)
	}
	defer conn.Close()
	client := pb.NewUserServiceClient(conn)

	// 定义REST接口
	r.GET("/user/:name", func(c *gin.Context) {
		name := c.Param("name")
		// 构造gRPC请求
		req := &pb.USRequest{Name: name}
		// 调用gRPC服务
		resp, err := client.GetUser(context.Background(), req)
		if err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		// 转换为REST响应返回
		c.JSON(http.StatusOK, gin.H{"message": resp.Message})
	})

	r.Run(":8080")
}

3. 配置与优化(可选但推荐)

  • 若微服务地址可能动态变化,可引入Consul、Etcd等服务发现组件,让网关自动发现微服务地址,避免硬编码
  • 可添加超时、重试、限流等逻辑,提升网关的稳定性

4. 测试验证

  • 启动.NET的UserService微服务,确保gRPC端口正常监听
  • 启动Go网关,调用REST接口GET http://localhost:8080/user/xxx,检查是否能正确返回gRPC服务的响应

内容的提问来源于stack exchange,提问作者Damjan Dimitrijevic

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.22 15:30:14