Go微服务: 基于GRPC结合Consul实现微服务调用

基于GRPC结合Consul实现微服务调用


1 )环境准备

  • 基于 go workspace 准备3个包: protos,server, client
  • 新建 demo目录,其内部结构如下
    ├── protos
    │     ├── go.mod
    │     └── users
    │           ├── users.proto
    │           ├── users.pb.go
    │           └── users_grpc.pb.go
    ├── server
    │   ├── go.mod
    │   └── main.go
    ├── client
    │   ├── go.mod
    │   └── main.go
    └── go.work
    
  • 这里可以看出是对用户操作的业务场景
  • 其实目前无关业务场景,用一个简单的示例来演示grpc和consul的结合
  • 这里可以看到,已经初始化了每个包,同时也基于 go work 处理了3个包之前可以调用的关系
  • 这里不再过多阐述,参考之前的博文
    • https://blog.csdn.net/Tyro_java/article/details/135430134
    • https://blog.csdn.net/Tyro_java/article/details/135297367
  • 启动 consul, $ consul agent -dev
    • 参考:https://blog.csdn.net/Tyro_java/article/details/129992606

2 )准备 protos

  • 由上面的目录设计可知,需要 users.proto
    syntax="proto3";
    option go_package="./users";service Users {rpc AddUser(AddUserReq) returns (AddUserRes);rpc GetUser(GetUserReq) returns (GetUserRes);
    }message UsersModel {string name = 1;int32 age = 2;
    }message AddUserReq {UsersModel user = 1;
    }message AddUserRes {string message = 1;bool success = 2;
    }message GetUserReq {
    }message GetUserRes {repeated UsersModel userList =1 ;
    }
    
  • 进入 demo/protos/users 目录生成 users.pb.go,users_grpc.pb.go
    • 执行 protoc --go_out=. --go_opt=paths=source_relative --go-grpc_out=. --go-grpc_opt=paths=source_relative ./users.proto

3 )处理 server

  • 新建 demo/server/main.go

    package mainimport ("context""fmt""protos/users""net""strconv""google.golang.org/grpc""github.com/hashicorp/consul/api"
    )// 定义通用度变量
    var (host string = "127.0.0.1"port int = 9000portStr string = strconv.Itoa(port)address = host + ":" + portStr
    )type Users struct {users.UnimplementedUsersServer
    }func (g Users) AddUser(c context.Context, req *users.AddUserReq) (*users.AddUserRes, error) {fmt.Println(req)return &users.AddUserRes{Success: true,Message: "增加用户成功",}, nil
    }func (g Users) GetUser(c context.Context, req *users.GetUserReq) (*users.GetUserRes, error) {var tempList []*users.UsersModelfor i := 0; i < 10; i++ {tempList = append(tempList, &users.UsersModel{Name:   "商品" + strconv.Itoa(i),Age:   int32(i),})}return &users.GetUserRes{UserList: tempList,}, nil
    }func main() {// ----------------------- 1. 注册consul服务 -----------------------// 1、初始化consul配置consulConfig := api.DefaultConfig()// consulConfig.Address = "127.0.0.1:8500"  // consul服务的默认地址可省略,如果不是本机,需要补充// 2、获取consul操作对象consulClient, _ := api.NewClient(consulConfig)// 3、配置注册服务的参数agentService := api.AgentServiceRegistration {ID:      "1", // 不要重复Tags:    []string{"test"},Name:    "UsersService",Port:    port, // 和下面 grpc server 的配置相同, 否则就连接不上微服务Address: host, // 同上Check: &api.AgentServiceCheck{TCP:      address,Timeout:  "5s",Interval: "30s",},}//  4、注册服务到consul上consulClient.Agent().ServiceRegister(&agentService)// ----------------------- 2. 注册GRPC -----------------------// 1、获取Grpc示例grpcServer := grpc.NewServer()// 2、注册服务users.RegisterUsersServer(grpcServer, &Users{})// 3、监听端口listener, err := net.Listen("tcp", address)if err != nil {fmt.Println(err)}// 4、退出服务的时候关闭监听defer listener.Close()// 5、启动服务grpcServer.Serve(listener)
    }
    
  • 主要关注 main 函数中,注册consul服务相关代码

  • 重新处理依赖 $ go mod tidy

  • 运行起来 $ go run main.go

  • 刷新发现 127.0.0.1:8500 这个 consul 注册中心面板出来了一个新的服务

4 )处理 client

  • 新建 demo/client/main.go

    package mainimport ("fmt""protos/users""context""strconv""google.golang.org/grpc""google.golang.org/grpc/credentials/insecure""github.com/hashicorp/consul/api"
    )func main() {// ------------------------------- 1. 初始化 consul 客户端 -------------------------------// 1、初始化 consul 配置consulConfig := api.DefaultConfig()// consulConfig.Address = "127.0.0.1:8500"  // 默认consul服务的地址,如有改变,重新指定// 2、获取consul操作对象consulClient, _ := api.NewClient(consulConfig)// ------------------------------- 2. 基于consul解析UserService的address -------------------------------usersServiceEntry, _, _ := consulClient.Health().Service("UsersService", "test", false, nil)usersServicePtr := usersServiceEntry[0].Service // service 指针对象userAddress := usersServicePtr.Address + ":" + strconv.Itoa(usersServicePtr.Port)// ------------------------------- 3. 基于GRPC连接和调用 -------------------------------// 1、建立连接userGrpcClient, err := grpc.Dial(userAddress, grpc.WithTransportCredentials(insecure.NewCredentials()))if err != nil {fmt.Println(err)}// 2、注册客户端userClient := users.NewUsersClient(userGrpcClient)// 3. 调用接口1:增加用户res1, _ := userClient.AddUser(context.Background(), &users.AddUserReq {User: &users.UsersModel {Name:   "测试",Age:   20,},})fmt.Println(res1)fmt.Println()// 4. 调用接口2:获取数据res2, _ := userClient.GetUser(context.Background(), &users.GetUserReq{})fmt.Println(res2.UserList)// ------------------------------- 4. 以上完成了 users 服务的调用,如果需要调用其他服务,仍需重复步骤2,获取其他服务的入口,再次进行步骤3处理 TODO -------------------------------
    }
    
  • 以上的调用,可以进行适当的封装来满足不同业务的调用,仅供演示

  • 当然结合数据库操作封装功能完成闭环调用,不再赘述

  • 在 demo/client 下执行 $ go mod tidy

  • 运行起来,$ go run main.go 发现服务端,客户端控制台都打印输出出来了

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/739853.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

怎么判断你的模型是好是坏?模型性能评估指标大全!

模型性能评估指标&#xff0c;大家一定不陌生&#xff01;很多小伙伴们都说难&#xff0c;但是它真的很重要很重要很重要&#xff01;它会对我们的模型有很多的指导&#xff0c;也会给我们真正做模型的时候提供一些指导性的思想&#xff0c;不然我们看到别人的东西只能跟着人家…

centos7.9升级ssh和openssl

一、环境 [roottmp179 package]# ssh -V OpenSSH_7.4p1, OpenSSL 1.0.2k-fips 26 Jan 2017 [roottmp179 package]# cat /etc/redhat-release CentOS Linux release 7.9.2009 (Core) 二、 升级前准备 mkdir /opt/package cd /opt/package wget https://www.openssl.org/source…

【linux】冯诺依曼体系与操作系统的理解

本篇文章是进程的预备知识&#xff0c;但也不仅仅是进程的预备知识&#xff0c; 也可以更好地帮助我们理解整个计算机体系。 目录 冯诺依曼体系结构&#xff1a;进一步理解操作系统&#xff1a; 冯诺依曼体系结构&#xff1a; 关于这张图先进行一下必要的解释&#xff1a; 输…

怎样通过IT服务台来增强IT项目管理?

当下&#xff0c;越来越多的企业和组织重视IT项目管理的重要性。而如何通过IT服务台来增强和提升IT项目管理效率&#xff0c;成为了许多企业领导和IT专业人员共同关注的话题。如何充分利用IT服务台&#xff0c;以促进IT项目管理水平的提升和项目成功率的增加变得至关重要。 1…

Codeforces Round 924 (Div. 2)---->B. Equalize

总思路&#xff1a;首先我们做这题的时候有两个点一定要知道&#xff1a; 1.当数组中有重复元素的时候&#xff0c;只有其中的一个才能贡献一个相同元素&#xff0c;其他的都不行&#xff08;因为是排列&#xff0c;一个数只出现一次&#xff09;&#xff0c;所以我们可以用使…

怎么免费下载无水印视频素材?赶快收藏这六个网站。

今天来教大家怎么下载无水印视频素材&#xff0c;其中一些是免费的&#xff0c;并且可以在商业项目中使用&#xff0c;这些网站都是无水印视频素材&#xff0c;可以放心使用。 蛙学网&#xff1a; 网站的内容非常丰富多彩&#xff0c;包括风景&#xff0c;夜景&#xff0c;食物…

论文阅读:Editing Large Language Models: Problems, Methods, and Opportunities

Editing Large Language Models: Problems, Methods, and Opportunities 论文链接 代码链接 摘要 由于大语言模型&#xff08;LLM&#xff09;中可能存在一些过时的、不适当的和错误的信息&#xff0c;所以有必要纠正模型中的相关信息。如何高效地修改模型中的相关信息而不影…

【JS】自动下拉网页刷新,当出现指定关键字,就打印出来

批量检查域名是否可以注册 1、有的网站数据是通过下拉发生请求&#xff0c;间隔x毫秒自动下拉 2、查找某个关键字&#xff0c;找到就打印出来 3、打印数据自动去重 4、当连续n次下拉&#xff0c;没有新div元素出来&#xff0c;就停止该循环 var map {}; var count 0; var l…

qt如何将QHash中的数据有序地放入到QList中

在qt中&#xff0c;要将QHash中的数据有序地放入到QList中&#xff0c;首先要明白&#xff1a; 我们可以遍历QHash中的键值对&#xff0c;并将其按照键的顺序或值的大小插入到QList中&#xff0c;直接用for循环即可。 #include <QCoreApplication> #include <QHas…

java学习(Arrays类和System类)

目录 目录 一.Arrays类 二.System常见方法 三、Biglnteger和BigDecimal&#xff08;高精度&#xff09; 1.Biglnter的常用方法 2.BigDecimal常见方法 3.日期类 1)第一代日期类 2&#xff09;第二代日期类 3)第三代日期类 一.Arrays类 Arrays包含了一系 列静态方法&am…

11、Linux-安装和配置Redis

目录 第一步&#xff0c;传输文件和解压 第二步&#xff0c;安装gcc编译器 第三步&#xff0c;编译Redis 第四步&#xff0c;安装Redis服务 第五步&#xff0c;配置Redis ①开启后台启动 ②关闭保护模式&#xff08;关闭之后才可以远程连接Redis&#xff09; ③设置远程…

12双体系Java学习之局部变量和作用域

局部变量 局部变量的作用域 参数变量

理解记忆相关

foreach循环 在 Java 中&#xff0c;foreach 循环&#xff08;也称为增强型 for 循环&#xff09;是一种简洁的语法&#xff0c;用于遍历数组或集合&#xff08;如 List、Set、Map 等&#xff09;。以下是 foreach 循环的基本用法&#xff1a; 遍历数组&#xff1a; String[] …

在 Python 中从键盘读取用户输入

文章目录 如何在 Python 中从键盘读取用户输入input 函数使用input读取键盘输入使用input读取特定类型的数据处理错误从用户输入中读取多个值 getpass 模块使用 PyInputPlus 自动执行用户输入评估总结 如何在 Python 中从键盘读取用户输入 原文《How to Read User Input From t…

Rust:为 Trait 定义默认的方法

当你提到“指定 trait 的实现”并使用 :: 符号时&#xff0c;你可能是指在某些情况下&#xff0c;你想直接通过 trait 而不是具体的类型来调用方法。这在 trait 提供了默认方法实现时尤其有用&#xff0c;因为你可以不依赖任何具体的类型实现来调用这些方法。 然而&#xff0c…

AI写真变现项目丨超级训练营SOP手册

出品方&#xff1a; 吴东子团队 x AI破局俱乐部 以下只是该SOP手册的部分介绍&#xff0c;AI写真变现项目上手到变现全流程&#xff0c;需要完整手册的可以dd我。 AI写真 首先什么是AI写真&#xff0c;顾名思义的话可以说成是用AI生成写真照&#xff0c;我们先暂且这么理解&am…

PostgreSQL教程(三十二):服务器管理(十四)之监控磁盘使用

本章讨论如何监控PostgreSQL数据库系统的磁盘使用情况。 一、判断磁盘用量 每个表都有一个主要的堆磁盘文件&#xff0c;大多数数据都存储在其中。如果一个表有着可能会很宽&#xff08;尺寸大&#xff09;的列&#xff0c; 则另外还有一个TOAST文件与这个表相关联&#xff0…

Java详解:单列 | 双列集合 | Collections类

○ 前言&#xff1a; 在开发实践中&#xff0c;我们需要一些能够动态增长长度的容器来保存我们的数据&#xff0c;java中为了解决数据存储单一的情况&#xff0c;java中就提供了不同结构的集合类&#xff0c;可以让我们根据不同的场景进行数据存储的选择&#xff0c;如Java中提…

【java数据结构】HashMap和HashSet

目录 一.认识哈希表&#xff1a; 1.1什么是哈希表&#xff1f; 1.2哈希表的表示&#xff1a; 1.3常见哈希函数&#xff1a; 二.认识HashMap和HashSet: 2.1关于Map.Entry的说明:,> 2.2Map常用方法说明&#xff1a; 2.3HashMap的使用案例&#xff1a; 2.4Set常见方法…