如何让两个Go程序远程调用?

如何让两个Go程序远程调用?

net/rpc 则是为了让两个 Go 程序之间直接对话

RPC 让你在写代码时,调用另一台远程机器上的函数,就像调用本地的函数一样简单。

Go 标准库中的 net/rpc 目前处于冻结状态 (不再增加新功能)。在现代的实际工程中,大家通常会使用 gRPCKratos 等更强大的框架。

RPC 的核心规则

net/rpc 要求你的函数必须遵守特定的签名格式,才能被远程调用。

  1. 方法所属的类型必须是导出的(首字母大写)。
  2. 方法本身必须是导出的(首字母大写)。
  3. 方法必须有两个参数,且都必须是导出类型或内置类型。
  4. 方法的第二个参数必须是指针(因为服务器要把结果写回这个指针里)。
  5. 方法必须返回一个 error 类型。
Go 复制代码
func (t *T) MethodName(args T1, reply *T2) error

常用 API

服务端 API

  • rpc.Register(rcvr any): 将你的结构体注册为 RPC 服务。结构体名默认就是服务名。
  • rpc.HandleHTTP(): 如果你想让 RPC 走 HTTP 协议,调用这个注册路由。
  • rpc.Accept(lis net.Listener): 如果你想走纯 TCP 协议,用这个接收连接。

客户端 API

  • rpc.Dial(network, address string): 连接远程 RPC 服务器(比如传 "tcp", "localhost:1234")。
  • rpc.DialHTTP(network, address string): 连接走 HTTP 协议的 RPC 服务器。
  • client.Call(serviceMethod string, args any, reply any): 同步调用远程函数。程序会在这里等待结果返回。

实例:实现一个远程乘法计算器

提供方:

go 复制代码
package main

import (
	"fmt"
	"net"
	"net/rpc"
)

// 1. 定义传入的参数结构体
type Args struct {
	A, B int
}

// 2. 定义服务结构体
type MathService struct{}

// 3. 实现服务方法(严格遵守 5 条规则)
func (m *MathService) Multiply(args Args, reply *int) error {
	*reply = args.A * args.B
	fmt.Printf("服务端执行:计算 %d * %d\n", args.A, args.B)
	return nil
}

func main() {
	// 实例化服务
	math := new(MathService)

	// 注册 RPC 服务,客户端就可以通过 "MathService.Multiply" 来调用了
	rpc.Register(math)

	// 启动 TCP 监听
	listener, err := net.Listen("tcp", ":1234")
	if err != nil {
		panic(err)
	}
	fmt.Println("RPC 服务端已启动,监听端口 1234...")

	// 接收请求并处理
	rpc.Accept(listener)
}

调用方:

go 复制代码
package main

import (
	"fmt"
	"log"
	"net/rpc"
)

// 客户端 需要定义一样的参数结构体
type Args struct {
	A, B int
}

func main() {
	// 1. 拨号连接 RPC 服务器
	client, err := rpc.Dial("tcp", "localhost:1234")
	if err != nil {
		log.Fatal("拨号失败:", err)
	}
	defer client.Close()

	// 2. 准备参数和接收结果的变量
	args := Args{A: 10, B: 20}
	var reply int

	// 3. 发起调用! 第一个参数是 "结构体名.方法名"
	err = client.Call("MathService.Multiply", args, &reply)
	if err != nil {
		log.Fatal("调用失败:", err)
	}

	fmt.Printf("调用成功!结果是: %d\n", reply)
}
相关推荐
不正经学生3 小时前
C语言预处理详解:编译器真正动手之前的那些事
c语言·开发语言·算法·面试·bug
门思科技3 小时前
LoRaWAN 设备类别:Class A、B、C 对比与选型指南
c语言·开发语言·php
恋恋西风6 小时前
C++ 理解 std::thread 在单核和多核上的行为差异
开发语言·c++
Brilliantwxx6 小时前
【Linux】 进程(9)程序与进程地址空间(基础+进阶+面试题)
linux·运维·服务器·开发语言·c++
BizzZ_7 小时前
C++(22)——类型转换和IO流
开发语言·c++
小范同学_7 小时前
JDK1.7 与 JDK1.8 HashMap 底层原理对比 + 数组并发扩容死循环详解
java·开发语言
geovindu7 小时前
CSharp: 万年历
开发语言·后端·c#·.net
我找到地球的支点啦8 小时前
Matlab系列(009) 一CRC循环冗余校验详解
开发语言·数据结构·算法·matlab·信息与通信
予昊8 小时前
从零实现“在线五子棋对战“:WebSocket 实时通信 + 段位匹配
java·开发语言·网络·websocket
weixin_461408588 小时前
Mybatis-flex小记
java·开发语言·mybatis