首页 > 其他分享 >golang的jsonrpc客户端通用写法

golang的jsonrpc客户端通用写法

时间:2022-12-01 20:04:00浏览次数:110  
标签:jsonrpc err nil int res req golang json 客户端

服务端

package main

import (
	"errors"
	"fmt"
	"log"
	"net"
	"net/rpc"
	"net/rpc/jsonrpc"
	"os"
)

// 算数运算结构体
type Arith struct {
}

// 算数运算请求结构体
type ArithRequest struct {
	A int
	B int
}

// 算数运算响应结构体
type ArithResponse struct {
	Pro int // 乘积
	Quo int // 商
	Rem int // 余数
}

// 乘法运算方法
func (this *Arith) Multiply(req ArithRequest, res *ArithResponse) error {
	res.Pro = req.A * req.B
	return nil
}

// 除法运算方法
func (this *Arith) Divide(req ArithRequest, res *ArithResponse) error {
	if req.B == 0 {
		return errors.New("divide by zero")
	}
	res.Quo = req.A / req.B
	res.Rem = req.A % req.B
	return nil
}

func main() {
	rpc.Register(new(Arith)) // 注册rpc服务

	lis, err := net.Listen("tcp", "127.0.0.1:8096")
	if err != nil {
		log.Fatalln("fatal error: ", err)
	}

	fmt.Fprintf(os.Stdout, "%s", "start connection")

	for {
		conn, err := lis.Accept() // 接收客户端连接请求
		if err != nil {
			continue
		}

		go func(conn net.Conn) { // 并发处理客户端请求
			fmt.Fprintf(os.Stdout, "%s", "new client in coming\n")
			jsonrpc.ServeConn(conn)
		}(conn)
	}
}

go标准库客户端

package main

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

// 算数运算请求结构体
type ArithRequest struct {
	A int
	B int
}

// 算数运算响应结构体
type ArithResponse struct {
	Pro int // 乘积
	Quo int // 商
	Rem int // 余数
}

func main() {
	conn, err := jsonrpc.Dial("tcp", "127.0.0.1:8096")
	if err != nil {
		log.Fatalln("dailing error: ", err)
	}

	req := ArithRequest{9, 2}
	var res ArithResponse

	err = conn.Call("Arith.Multiply", req, &res) // 乘法运算
	if err != nil {
		log.Fatalln("arith error: ", err)
	}
	fmt.Printf("%d * %d = %d\n", req.A, req.B, res.Pro)

	err = conn.Call("Arith.Divide", req, &res)
	if err != nil {
		log.Fatalln("arith error: ", err)
	}
	fmt.Printf("%d / %d, quo is %d, rem is %d\n", req.A, req.B, res.Quo, res.Rem)
}

通用客户端

主要是下面这种方式,其他任何语言都可以使用tcp封装入参和并且解析返回数据,因为入参和返回值都可以通过json进行解析

package main

import (
	"encoding/json"
	"fmt"
	"net"
)

func main() {
	err := f()
	if err != nil {
		panic(err)
	}
}

func f() error {
	c, err := net.Dial("tcp", "127.0.0.1:8096")
	if err != nil {
		return err
	}
	defer c.Close()

	type clientRequest struct {
		Method string `json:"method"`
		Params [1]any `json:"params"`
		Id     uint64 `json:"id"`
	}

	b, err := json.Marshal(clientRequest{
		Method: "Arith.Divide",
		Params: [1]any{json.RawMessage(`{"A":123,"B":31}`)},
		Id:     1,
	})
	if err != nil {
		return err
	}

	_, err = c.Write(b)
	if err != nil {
		return err
	}

	var clientResponse struct {
		Id     uint64           `json:"id"`
		Result *json.RawMessage `json:"result"`
		Error  any              `json:"error"`
	}

	err = json.NewDecoder(c).Decode(&clientResponse)
	if err != nil {
		return err
	}
	fmt.Println(clientResponse)

	var ArithResponse struct {
		Pro int // 乘积
		Quo int // 商
		Rem int // 余数
	}
	err = json.Unmarshal(*clientResponse.Result, &ArithResponse)
	if err != nil {
		return err
	}

	fmt.Println(ArithResponse)
	return nil
}

标签:jsonrpc,err,nil,int,res,req,golang,json,客户端
From: https://www.cnblogs.com/janbar/p/16942513.html

相关文章

  • SpringBoot(三) - Ribbon客户端负载均衡,Zuul网关,Config配置中心
    1、Ribbon客户端负载均衡1.1依赖1.2配置信息#feign默认加载了ribbon负载均衡,默认负载均衡机制是:轮询#负载均衡机制是添加在消费端(客户端)的,如果改为随机,指定服务名......
  • golang 模拟byte数组
    packagemainimport("fmt")typeBytes[]bytefuncmain(){ fmt.Println("hello") fmt.Println("--------------") //ascii字符=============================......
  • snmptrap发送客户端
    #pragmaonce#include"net-snmp/net-snmp-config.h"#include"net-snmp/net-snmp-includes.h"#include<string.h>#include<string>staticconstoidOID_SYSUPTIME[]={......
  • 7.golang语言学习,标识符的命名规范
    1.凡是自己可以命名的都是标识符2.命名规则a.由26个英文字母,数字0-9,_组成b.不能数字开头c.严格区分大小写d.不能包含空格e.下划线”_“本身在go......
  • 安装golang
    golang,本节目标为安装golang,并完成helloworld系统环境为win11,下载地址安装后检查版本PSC:\Users\pc>go.exeversiongoversiongo1.19.3windows/amd64设置国内......
  • golang 标准库log的封装
    都知道golang的log库可以拿来就用,但对于生产来说还不够,需要基于log库做点封装。除了这些还有其他问题,比如打印字段定制化,性能问题。本文不讨论太多,只对log进行简单封装,实现......
  • SpringBoot 3.0 新特性,内置声明式 HTTP 客户端
    httpinterface从Spring6和SpringBoot3开始,Spring框架支持将远程HTTP服务代理成带有特定注解的Javahttpinterface。类似的库,如OpenFeign和Retrofit仍然......
  • golang流式编程
    https://blog.csdn.net/u012986012/article/details/126833564  借助一些设计模式、流式编程、函数编程的方法可以让我们的Golang代码更清晰优雅,本文中描述了在错误处......
  • Go-05 Golang中的运算符
    packagemainimport"fmt"/* Golang中的运算符 Golang内置的运算符: 1.算术运算符:+-*/% 2.关系运算符:!===>>=<<= 返回值是True或者False 3.逻辑运......
  • Installing golang-1.18 on openEuler
    一、Installinggolang-1.18onopenEulerhttps://golang.google.cn1下载mkdir/opt/software&&cd/opt/softwarewgethttps://golang.google.cn/dl/go1.18.linux......