Go中跨语言实现传输的方法步骤

 更新时间:2026年04月07日 08:56:52   作者:我叫黑大帅  
gRPC是Google开源的高性能RPC框架,基于HTTP/2协议和ProtocolBuffers序列化,支持多语言、流式传输和企业级特性,文章详细介绍了gRPC的接口定义语言、服务定义、消息类型、RPC类型以及服务端和客户端的实现方式,需要的朋友可以参考下

gRPC 是 Google 开源的高性能 RPC 框架,基于 HTTP/2 协议和 Protocol Buffers(Protobuf)序列化,支持多语言、流式传输和企业级特性。与 RESTful API 相比,它性能更高、接口定义更规范,特别适合微服务架构和跨语言服务调用。

概念作用说明
Protocol Buffers(Protobuf)接口定义语言(IDL)用于定义服务接口和消息结构,跨语言、跨平台,序列化性能极高
Service(服务)定义 RPC 方法.proto 文件中定义,包含方法名、请求消息、响应消息
Message(消息)定义数据结构类似于 Go 的结构体,用于定义请求和响应的数据格式
Unary RPC(一元 RPC)最简单的 RPC 模式客户端发送一个请求,服务端返回一个响应,类似传统的 HTTP 请求
Server Streaming RPC(服务端流式)服务端流式返回客户端发送一个请求,服务端返回多个响应
Client Streaming RPC(客户端流式)客户端流式发送客户端发送多个请求,服务端返回一个响应
Bidirectional Streaming RPC(双向流式)双向流式传输客户端和服务端可以同时发送和接收多个消息
# 1. 安装 protoc 编译器
# Mac 
brew install protobuf 
# Linux 
apt install -y protobuf-compiler
# 2. 安装 Go 插件
go install google.golang.org/protobuf/cmd/protoc-gen-go@latest
go install google.golang.org/grpc/cmd/protoc-gen-go-grpc@latest
# 3. 安装 gRPC 核心库
go get google.golang.org/grpc

Unary RPC (一元 RPC)

grpc-demo/
├── proto/ 
│ └── user.proto # Protobuf 定义文件 
├── server/ 
│ └── main.go # gRPC 服务端
├── client/ 
│ └── main.go # gRPC 客户端 
└── go.mod

编写 Protobuf 定义(proto/user.proto

这是 gRPC 开发的核心,定义接口契约。

// 指定 Protobuf 版本 
syntax = "proto3"; 
// 指定生成的 Go 代码的包路径 
option go_package = "./proto"; 
// 定义包名 
package user;
// 定义消息(数据结构)
message User {
  uint32 id = 1; // 字段编号:1-15 占 1 字节,常用字段优先
  string username = 2;
  string email = 3;
}
message GetUserRequest {
  uint32 user_id = 1;
}
message GetUserResponse {
  User user = 1;
}
// 定义服务
service UserService {
  // 一元 RPC 方法
  rpc GetUser(GetUserRequest) returns (GetUserResponse);
}
  • syntax = "proto3"; :指定使用 Protobuf v3 版本(推荐,比 v2 更简洁)。
  • option go_package = "./proto"; :指定生成的 Go 代码的包路径。
  • 消息字段编号:每个字段必须有唯一的编号,1-15 占 1 字节,16-2047 占 2 字节,常用字段建议用 1-15。
  • service Xxx { rpc Yyy(Req) returns (Resp) }:定义服务,包含多个 RPC 方法。
  • rpc 方法名(请求) returns (响应) :定义 RPC 方法。
  • message Xxx { type field = tag; }:定义消息结构,tag 必须唯一
protoc --go_out=. --go-grpc_out=. proto/user.proto

执行成功后,会在 proto/ 目录下生成两个文件:

  • user.pb.go:消息结构的 Go 代码
  • user_grpc.pb.go:服务接口的 Go 代码

服务端实现

import (pb "grpc-demo/proto")

// 定义服务结构体,必须嵌入 Unimplemented*Server
type UserServer struct {
	pb.UnimplementedUserServiceServer // 必须嵌入,保证向前兼容
}

// 实现 Protobuf 中定义的 RPC 方法
func (s *UserServer) GetUser(ctx context.Context, req *pb.GetUserRequest) (*pb.GetUserResponse, error) {
	// 核心业务逻辑:查询数据库等
	user := &pb.User{
		Id:       req.UserId,
		Username: "zhangsan",
		Email:    "zhangsan@example.com",
	}
	return &pb.GetUserResponse{User: user}, nil
}

func main() {
	// 监听端口
	lis, _ := net.Listen("tcp", ":50051")
	// 创建 gRPC 服务器
	s := grpc.NewServer()
	// 将服务实现注册到 gRPC 服务器
	pb.RegisterUserServiceServer(s, &UserServer{})
	// 启动服务,监听 TCP 连接
	s.Serve(lis)
}
  • type XxxServer struct { pb.UnimplementedXxxServer }:定义服务结构体,必须嵌入 Unimplemented
  • pb.UnimplementedUserServiceServer:必须嵌入这个结构体,确保向前兼容,即使后续服务添加了新方法,旧的服务端代码也不会报错。
  • 实现服务接口:必须实现 .proto 文件中定义的所有 RPC 方法。

客户端实现

import (pb "grpc-demo/proto")

func main() {
	// 连接服务端
	conn, _ := grpc.Dial(
		"localhost:50051",
		grpc.WithTransportCredentials(insecure.NewCredentials()),
	)
	defer conn.Close()

	// 创建客户端
	client := pb.NewUserServiceClient(conn)

	// 调用 RPC 方法
	ctx := context.Background() // 空根上下文
	resp, _ := client.GetUser(ctx, &pb.GetUserRequest{UserId: 1})

	fmt.Printf("获取用户:%+v\n", resp.User)
}
  • client.Yyy(ctx, &Req{}):调用 RPC 方法

拦截器

拦截器类似 Gin 中间件,用于处理通用逻辑(日志、认证、限流)。

// 日志拦截器
func LogInterceptor(ctx context.Context, req any, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (any, error) {
	// 请求前逻辑
	fmt.Printf("收到请求:%s\n", info.FullMethod)
	
	// 调用实际 RPC 方法
	resp, err := handler(ctx, req)
	
	// 请求后逻辑
	return resp, err
}

// 注册拦截器
func main() {
	lis, _ := net.Listen("tcp", ":50051")
	// 创建服务器时注册拦截器
	s := grpc.NewServer(grpc.UnaryInterceptor(LogInterceptor))
	pb.RegisterUserServiceServer(s, &UserServer{})
	s.Serve(lis)
}
  • grpc.NewServer(grpc.UnaryInterceptor(...)):创建 gRPC 服务器并注册拦截器

以上就是Go中跨语言实现传输的方法步骤的详细内容,更多关于Go跨语言实现传输的资料请关注脚本之家其它相关文章!

相关文章

  • Go高级特性探究之信号处理详解

    Go高级特性探究之信号处理详解

    信号是在Unix和类Unix操作系统中用于通知进程发生了事件或异常的通信机制,本文主要来介绍一下Go中的信号处理的方法,需要的可以参考一下
    2023-06-06
  • golang 将[]byte转成16进制的实现

    golang 将[]byte转成16进制的实现

    这篇文章主要介绍了golang 将[]byte转成16进制的实现,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2020-12-12
  • 从零封装Gin框架配置初始化全局变量

    从零封装Gin框架配置初始化全局变量

    这篇文章主要为大家介绍了从零封装Gin框架配置初始化全局变量,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2024-01-01
  • 阿里云go开发环境搭建过程

    阿里云go开发环境搭建过程

    这篇文章主要介绍了阿里云go开发环境搭建过程,非常不错,具有参考借鉴价值,需要的朋友可以参考下
    2018-02-02
  • Go使用XORM操作MySQL的陷阱盘点分析

    Go使用XORM操作MySQL的陷阱盘点分析

    在 Go 语言开发中,大家为了方便,通常会选择使用 ORM 操作数据库,比如使用 XORM 或 GORM 操作 MySQL,本文我们来介绍一下使用 XORM[3] 操作 MySQL 可能会遇到的陷阱
    2023-11-11
  • 提升Golang应用性能:深入理解Context的应用

    提升Golang应用性能:深入理解Context的应用

    本文将深入探讨如何通过深入理解和正确应用Go语言中的Context来提升应用性能。需要的朋友可以参考下
    2023-09-09
  • GO语言实现简单TCP服务的方法

    GO语言实现简单TCP服务的方法

    这篇文章主要介绍了GO语言实现简单TCP服务的方法,实例分析了Go语言实现TCP服务的技巧,需要的朋友可以参考下
    2015-03-03
  • Go语言如何在Web服务中实现优雅关机

    Go语言如何在Web服务中实现优雅关机

    在这篇文章中,我们将通过一个简单的例子来演示如何在 Go 语言中使用 Gin 框架实现优雅关机,感兴趣的小伙伴可以跟随小编一起学习一下
    2024-11-11
  • go generate代码自动生成指南

    go generate代码自动生成指南

    这篇文章主要介绍了go generate代码自动生成指南,本文将探讨 go generate 命令的使用方法、原理以及一些实际应用场景,希望读者能够更好地理解和运用这个强大的工具
    2024-01-01
  • golang简易实现 k8s 的yaml上传并应用示例方案

    golang简易实现 k8s 的yaml上传并应用示例方案

    这篇文章主要为大家介绍了golang简易实现 k8s 的yaml上传并应用示例方案,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-07-07

最新评论