grpc基础-1.初识grpc

说到grpc,大部分是在微服务之间的服务调用中使用

所以就得了解单体架构和微服务架构

单体架构

  1. 只能对整体扩容,伸缩
  2. 一荣俱荣,一损俱损
  3. 代码耦合,项目的开发者往往需要知道整个系统的流程

微服务架构

可以按照服务进行单独扩容,升级

各个服务之间可独立开发,独立部署

传统rpc

服务端

package main

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

type Server struct {
}
type Req struct {
  Num1 int
  Num2 int
}
type Res struct {
  Num int
}

func (s Server) Add(req Req, res *Res) error {
  res.Num = req.Num1 + req.Num2
  return nil
}

func main() {
  // 注册rpc服务
  rpc.Register(new(Server))
  rpc.HandleHTTP()
  listen, err := net.Listen("tcp", ":8080")
  if err != nil {
    fmt.Println(err)
    return
  }
  http.Serve(listen, nil)
}

客户端

package main

import (
  "fmt"
  "net/rpc"
)

type Req struct {
  Num1 int
  Num2 int
}
type Res struct {
  Num int
}

func main() {
  req := Req{1, 2}
  client, err := rpc.DialHTTP("tcp", ":8080")
  if err != nil {
    fmt.Println(err)
    return
  }
  var res Res
  client.Call("Server.Add", req, &res)
  fmt.Println(res)
}

原生rpc的问题:

  1. 编写相对复杂,需要自己去关注实现过程
  2. 没有代码提示,容易写错

grpc模式

编写protobuf文件

syntax = "proto3"; // 指定proto版本
package hello_grpc;     // 指定默认包名

// 指定golang包名
option go_package = "/hello_grpc";

//定义rpc服务
service HelloService {
  // 定义函数
  rpc SayHello (HelloRequest) returns (HelloResponse) {}
}

// HelloRequest 请求内容
message HelloRequest {
  string name = 1;
  string message = 2;
}

// HelloResponse 响应内容
message HelloResponse{
  string name = 1;
  string message = 2;
}

proto文件没有高亮的话去下载一个grpc的插件

在grpc_proto目录下执行

protoc -I . --go_out=plugins=grpc:. .\hello.proto

或者在根目录下执行

protoc -I . --go_out=plugins=grpc:.\grpc_proto .\grpc_proto\hello.proto

我们可以编写一个bat文件,方便转换

set.bat

protoc -I . --go_out=plugins=grpc:.\grpc_proto .\grpc_proto\hello.proto

服务端

  1. 编写一个结构体,名字叫什么不重要
  2. 重要的是得实现protobuf中的所有方法
  3. 监听端口
  4. 注册服务
package main

import (
  "context"
  "fmt"
  "google.golang.org/grpc"
  "google.golang.org/grpc/grpclog"
  "grpc_study/grpc_proto/hello_grpc"
  "net"
)

// HelloServer1 得有一个结构体,需要实现这个服务的全部方法,叫什么名字不重要
type HelloServer1 struct {
}

func (HelloServer1) SayHello(ctx context.Context, request *hello_grpc.HelloRequest) (pd *hello_grpc.HelloResponse, err error) {
  fmt.Println("入参:", request.Name, request.Message)
  pd = new(hello_grpc.HelloResponse)
  pd.Name = "你好"
  pd.Message = "ok"
  return
}

func main() {
  // 监听端口
  listen, err := net.Listen("tcp", ":8080")
  if err != nil {
    grpclog.Fatalf("Failed to listen: %v", err)
  }
  
  // 创建一个gRPC服务器实例。
  s := grpc.NewServer()
  server := HelloServer1{}
  // 将server结构体注册为gRPC服务。
  hello_grpc.RegisterHelloServiceServer(s, &server)
  fmt.Println("grpc server running :8080")
  // 开始处理客户端请求。
  err = s.Serve(listen)
}

客户端

  1. 建立连接
  2. 调用方法
package main

import (
  "context"
  "fmt"
  "google.golang.org/grpc"
  "google.golang.org/grpc/credentials/insecure"
  "grpc_study/grpc_proto/hello_grpc"
  "log"
)

func main() {
  addr := ":8080"
  // 使用 grpc.Dial 创建一个到指定地址的 gRPC 连接。
  // 此处使用不安全的证书来实现 SSL/TLS 连接
  conn, err := grpc.Dial(addr, grpc.WithTransportCredentials(insecure.NewCredentials()))
  if err != nil {
    log.Fatalf(fmt.Sprintf("grpc connect addr [%s] 连接失败 %s", addr, err))
  }
  defer conn.Close()
  // 初始化客户端
  client := hello_grpc.NewHelloServiceClient(conn)
  result, err := client.SayHello(context.Background(), &hello_grpc.HelloRequest{
    Name:    "枫枫",
    Message: "ok",
  })
  fmt.Println(result, err)
}

如果需要经常操作这个连接对象,我们可以复用

func initClient() hello_grpc.HelloServiceClient {
  addr := ":8080"
  conn, err := grpc.Dial(addr, grpc.WithTransportCredentials(insecure.NewCredentials()))
  if err != nil {
    log.Fatalf(fmt.Sprintf("grpc connect addr [%s] 连接失败 %s", addr, err))
  }
  client := hello_grpc.NewHelloServiceClient(conn)
  return client
}

func main() {
  client := initClient()
  result, err := client.SayHello(context.Background(), &hello_grpc.HelloRequest{
    Name:    "枫枫",
    Message: "ok",
  })
  result, err = client.SayHello(context.Background(), &hello_grpc.HelloRequest{
    Name:    "哈哈哈",
    Message: "ok1",
  })
  
  fmt.Println(result, err)
}

<think>我们遇到了一个Maven依赖冲突问题,具体是io.grpc:grpc-core的版本冲突。错误信息显示有多个依赖要求不同版本的grpc-core(1.42.11.42.2)。为了解决这个问题,我们需要在pom.xml中显式指定一个统一的版本。 解决方案: 1. 在<properties>中定义grpc.version属性,并设置为1.42.2(因为从错误看,多数依赖要求1.42.2)。 2. 确保所有grpc相关的依赖都使用这个属性定义的版本。 3. 使用Maven的依赖管理(dependencyManagement)来统一管理版本。 但是,由于我们使用的是Spring Boot父pom,它已经管理了一些依赖版本,但可能没有管理grpc。因此,我们可以通过dependencyManagement来覆盖。 具体步骤: 修改pom.xml: - 在<properties>中设置grpc.version为1.42.2(或者1.42.1,但需要看哪个版本与其他依赖兼容,根据错误信息,建议使用1.42.2,因为多个传递依赖要求1.42.2)。 - 在<dependencyManagement>中添加grpc相关依赖的版本管理。 注意:由于我们使用了grpc-spring-boot-starter,它可能也管理了grpc版本,但错误显示它内部依赖了1.42.2和1.42.1,所以我们需要显式统一。 示例配置: 在<dependencyManagement>中添加如下依赖管理: ```xml <dependencyManagement> <dependencies> <!-- 统一管理grpc依赖版本 --> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-bom</artifactId> <version>${grpc.version}</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement> ``` 同时,确保在<properties>中设置了grpc.version: ```xml <properties> <grpc.version>1.42.2</grpc.version> </properties> ``` 这样,所有来自grpc-bom的依赖都会使用1.42.2版本。 完整示例: 修改后的pom.xml部分: ```xml <project> <!-- ... 其他部分 ... --> <properties> <java.version>1.8</java.version> <!-- 设置grpc版本为1.42.2 --> <grpc.version>1.42.2</grpc.version> <protobuf.version>3.19.4</protobuf.version> <grpc-spring-boot.version>2.13.1.RELEASE</grpc-spring-boot.version> <os-maven-plugin.version>1.7.0</os-maven-plugin.version> <protobuf-maven-plugin.version>0.6.1</protobuf-maven-plugin.version> </properties> <dependencyManagement> <dependencies> <!-- 导入grpc的BOM以统一版本 --> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-bom</artifactId> <version>${grpc.version}</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement> <dependencies> <!-- ... 其他依赖 ... --> <!-- grpc依赖不再指定版本,由BOM管理 --> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-stub</artifactId> </dependency> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-protobuf</artifactId> </dependency> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-netty-shaded</artifactId> </dependency> <!-- ... 其他依赖 ... --> </dependencies> <!-- ... 构建配置 ... --> </project> ``` 解释: 1. 我们通过导入grpc-bom(Bill of Materials)来管理所有grpc相关依赖的版本,这样所有grpc依赖的版本都会统一为我们在<properties>中设置的${grpc.version}(即1.42.2)。 2. 在<dependencies>中,我们不再为grpc依赖指定版本,因为BOM会提供版本。 3. 这样,Maven在解析依赖时就会使用统一的版本,避免冲突。 注意:如果项目中还有其他依赖引入了不同版本的grpc,现在也会被强制升级或降级到1.42.2。如果这个版本与其他依赖不兼容,可能需要调整版本号(例如,尝试1.42.1)或者排除冲突的传递依赖。 如果问题仍然存在,可以尝试使用mvn dependency:tree命令查看依赖树,确认是否还有其他依赖引入了不同版本的grpc-core。如果有,可以在相应的依赖中排除: ```xml <dependency> <groupId>some.group</groupId> <artifactId>some-artifact</artifactId> <version>1.0</version> <exclusions> <exclusion> <groupId>io.grpc</groupId> <artifactId>grpc-core</artifactId> </exclusion> </exclusions> </dependency> ``` 重新构建项目,应该可以解决版本冲突问题。 §§相关问题§§: 1. 如何通过Maven命令查看项目的依赖树? 2. 什么是Maven的BOM(Bill of Materials)?它是如何工作的? 3. 除了使用BOM,还有哪些方法解决Maven依赖冲突? 4. 在Spring Boot项目中,如何覆盖父pom管理的依赖版本?</think>这个错误表明 Maven 依赖解析中存在版本冲突,特别是 `io.grpc:grpc-core` 的不同版本要求(1.42.11.42.2)。以下是完整的解决方案: ### 解决方案:统一 gRPC 版本 #### 1. 修改 `pom.xml` 添加依赖管理 ```xml <properties> <!-- 统一所有 gRPC 相关依赖版本 --> <grpc.version>1.42.2</grpc.version> <protobuf.version>3.19.4</protobuf.version> <grpc-spring-boot.version>2.13.1.RELEASE</grpc-spring-boot.version> </properties> <dependencyManagement> <dependencies> <!-- 导入 gRPC BOM 统一管理版本 --> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-bom</artifactId> <version>${grpc.version}</version> <type>pom</type> <scope>import</scope> </dependency> <!-- 统一管理 grpc-spring-boot-starter 相关依赖 --> <dependency> <groupId>net.devh</groupId> <artifactId>grpc-spring-boot-starter</artifactId> <version>${grpc-spring-boot.version}</version> </dependency> </dependencies> </dependencyManagement> ``` #### 2. 更新依赖声明 ```xml <dependencies> <!-- gRPC 依赖 --> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-stub</artifactId> </dependency> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-protobuf</artifactId> </dependency> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-netty-shaded</artifactId> </dependency> <!-- Spring Boot gRPC 集成 --> <dependency> <groupId>net.devh</groupId> <artifactId>grpc-spring-boot-starter</artifactId> </dependency> </dependencies> ``` #### 3. 完整 `pom.xml` 示例 ```xml <?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.example</groupId> <artifactId>grpc-spring-demo</artifactId> <version>1.0.0</version> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>2.1.14.RELEASE</version> </parent> <properties> <java.version>1.8</java.version> <grpc.version>1.42.2</grpc.version> <protobuf.version>3.19.4</protobuf.version> <grpc-spring-boot.version>2.13.1.RELEASE</grpc-spring-boot.version> <os-maven-plugin.version>1.7.0</os-maven-plugin.version> <protobuf-maven-plugin.version>0.6.1</protobuf-maven-plugin.version> </properties> <dependencyManagement> <dependencies> <!-- 统一 gRPC 核心库版本 --> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-bom</artifactId> <version>${grpc.version}</version> <type>pom</type> <scope>import</scope> </dependency> <!-- 统一 grpc-spring-boot 相关库版本 --> <dependency> <groupId>net.devh</groupId> <artifactId>grpc-spring-boot-starter</artifactId> <version>${grpc-spring-boot.version}</version> </dependency> </dependencies> </dependencyManagement> <dependencies> <!-- Spring Boot Starter --> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <!-- gRPC 依赖 --> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-stub</artifactId> </dependency> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-protobuf</artifactId> </dependency> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-netty-shaded</artifactId> </dependency> <!-- Spring Boot gRPC 集成 --> <dependency> <groupId>net.devh</groupId> <artifactId>grpc-spring-boot-starter</artifactId> </dependency> </dependencies> <build> <extensions> <extension> <groupId>kr.motd.maven</groupId> <artifactId>os-maven-plugin</artifactId> <version>${os-maven-plugin.version}</version> </extension> </extensions> <plugins> <plugin> <groupId>org.xolstice.maven.plugins</groupId> <artifactId>protobuf-maven-plugin</artifactId> <version>${protobuf-maven-plugin.version}</version> <configuration> <protocArtifact>com.google.protobuf:protoc:${protobuf.version}:exe:${os.detected.classifier}</protocArtifact> <pluginId>grpc-java</pluginId> <pluginArtifact>io.grpc:protoc-gen-grpc-java:${grpc.version}:exe:${os.detected.classifier}</pluginArtifact> </configuration> <executions> <execution> <goals> <goal>compile</goal> <goal>compile-custom</goal> </goals> </execution> </executions> </plugin> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build> </project> ``` ### 问题分析 1. **版本冲突原因**: - `grpc-netty-shaded:1.42.1` 要求 `grpc-core:1.42.1` - `grpc-spring-boot-starter:2.13.1.RELEASE` 要求 `grpc-core:1.42.2` - 两者版本不兼容导致冲突 2. **解决方案核心**: - 使用 `<dependencyManagement>` 统一所有 gRPC 相关依赖版本 - 导入 `grpc-bom` 管理所有 gRPC 组件的版本 - 强制使用较新的 `1.42.2` 版本(兼容两个依赖) 3. **为什么选择 1.42.2**: - 向后兼容 1.42.1 的功能 - `grpc-spring-boot-starter` 明确要求 1.42.2 - 包含更多错误修复和安全更新 ### 验证解决方案 1. 运行 Maven 依赖树分析: ```bash mvn dependency:tree -Dincludes=io.grpc:grpc-core ``` 输出应显示统一版本: ``` [INFO] +- io.grpc:grpc-netty-shaded:jar:1.42.2:compile [INFO] | \- io.grpc:grpc-core:jar:1.42.2:compile [INFO] \- net.devh:grpc-spring-boot-starter:jar:2.13.1.RELEASE:compile [INFO] \- io.grpc:grpc-services:jar:1.42.2:compile [INFO] \- io.grpc:grpc-core:jar:1.42.2:compile ``` 2. 清理并重新构建项目: ```bash mvn clean install ``` ### 备选方案:显式排除冲突依赖 如果上述方案无效,可以显式排除冲突依赖: ```xml <dependency> <groupId>net.devh</groupId> <artifactId>grpc-spring-boot-starter</artifactId> <version>${grpc-spring-boot.version}</version> <exclusions> <exclusion> <groupId>io.grpc</groupId> <artifactId>grpc-core</artifactId> </exclusion> <exclusion> <groupId>io.grpc</groupId> <artifactId>grpc-services</artifactId> </exclusion> </exclusions> </dependency> <dependency> <groupId>io.grpc</groupId> <artifactId>grpc-services</artifactId> <version>${grpc.version}</version> </dependency> ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值