.netcore grpc的proto文件字段详解

这篇具有很好参考价值的文章主要介绍了.netcore grpc的proto文件字段详解。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

一、.proto文件字段概述

  1. grpc的接口传输参数都是根据.proto文件约定的字段格式进行传输的
  2. grpc提供了多种类型字段;主要包括标量值类型(基础类型)、日期时间、可为null类型、字节、列表、字典、Any类型(任意类型)、Oneof等
  3. 字段严格规范,是一种强类型文件协议

二、案例介绍

  1. 标量值类型
  2. 日期时间
  3. 可为null类型
  4. 字节
  5. 列表
  6. 字典
  7. Any类型
  8. Oneof:一种语言特性,可以通过该特性进行对象切换处理;使用 oneof 指定可能返回 A对象或B对象 的响应消息

三、服务端定义

  1. 定义通用消息实体
  2. 根据不同的类型创建对应的案例实体
  3. 特殊的字段需要导入指定的包才能使用
  4. 定义引用字段的各个服务接口
  5. 内部实现逻辑,及打印展示相应的字段结果
// 1.提供公共的实体proto文件
// 2.服务引用对应的proto文件


// 通用消息文件datamessages.proto
syntax = "proto3";

option csharp_namespace = "GrpcProject";

package grpc.serviceing;

// 基础类型实体
message BaseConfig{
	string name = 1;
	double position = 2;
	float distance= 3 ;
	int32 age = 4;
	int64 timeSpanId = 5;
	uint32 uAge = 6;
	uint64 uTimeSpanId = 7;
	sint32 sAge = 8;
	sint64 sTimeSpanId = 9;
	bool flag = 10;
}


// 日期类型实体 需要导入 日期namespace
import "google/protobuf/duration.proto";
import "google/protobuf/timestamp.proto";

message DateConfig{
	int64 id = 1;
	google.protobuf.Timestamp dateTimestamp = 2;
	google.protobuf.Duration dateDuration = 3;
}


// 字节类型
message ByteConfig{
	int64 id = 1;
	bytes positionBytes = 2;
}


// 可为null类型 需要导入 null的namespace
import "google/protobuf/wrappers.proto";

message NullConfig{
	int64 id = 1;
	google.protobuf.BoolValue nullBool = 2;
	google.protobuf.DoubleValue nullDoubule = 3;
	google.protobuf.FloatValue nullFloat = 4;
	google.protobuf.Int32Value nullInt = 5;
	google.protobuf.Int64Value nullLong = 6;
	google.protobuf.UInt32Value nullUInt = 7;
	google.protobuf.StringValue nullString = 8;
	google.protobuf.BytesValue nullBytes = 9;
}

//  集合类型
message ListConfig{
	int64 id = 1;
	// 数组
	repeated string names = 2;
	repeated ListDetailConfig details = 3;
	// 字典
	map<int32,string> attributes = 4;
	map<int32,ListDetailConfig> dicDetail = 5;
}

message ListDetailConfig{
	string name = 1;
	int32 height = 2;
}


// 任意类型 需要导入对应的包
import "google/protobuf/any.proto";
message AnyConfig{
	int32 id = 1;
	google.protobuf.Any anyObject = 2;
}

// Oneof类型  编译器在生成消息类时处理 oneof 关键字。 使用 oneof 指定可能返回 A 或 B 或 C 的响应消息
message OneofConfig{
	oneof result{
		A oA = 1;
		B oB = 2;
		C oC = 3;
	}
}

message A{
	int32 id = 1;
}

message B{
	int32 id = 1;
}

message C{
	int32 id =1;
}
// 接口服务定义protofield.proto文件

syntax = "proto3";

import "google/protobuf/empty.proto";
import "Protos/datamessages.proto";

option csharp_namespace = "GrpcProject";

package grpc.serviceing;

service FieldRpc{
	// 基础字段处理
	rpc BaseConfigService(BaseConfig) returns (google.protobuf.Empty);
	// 日期字段处理
	rpc DateConfigService(DateConfig) returns (google.protobuf.Empty);
	// 字节处理
	rpc ByteConfigService(ByteConfig) returns (google.protobuf.Empty);
	// null字段处理
	rpc NullConfigService(NullConfig) returns (google.protobuf.Empty);
	// 集合类型字段处理
	rpc ListConfigService(ListConfig) returns (google.protobuf.Empty);
	// 任意类型字段处理
	rpc AnyConfigService(AnyConfig) returns (google.protobuf.Empty);
	// Oneof类型字段处理
	rpc OneofConfigService(OneofConfig) returns (google.protobuf.Empty);
}
// 服务实现类

    /// <summary>
    /// 字段处理服务
    /// </summary>
    public class ProtoFieldService : FieldRpc.FieldRpcBase
    {
        // 基础配置
        public override async Task<Empty> BaseConfigService(BaseConfig request, ServerCallContext context)
        {
            await Console.Out.WriteLineAsync("\r\n--------------------------基础配置--------------------------\r\n");
            // 打印字段信息
            var properties = request.GetType().GetProperties();
            foreach (var property in properties)
            {
                var value = property.GetValue(request);

                await Console.Out.WriteLineAsync($"{property.Name}:{value}");
            }
            return new Empty();
        }

        // 日期配置
        public override async Task<Empty> DateConfigService(DateConfig request, ServerCallContext context)
        {
            await Console.Out.WriteLineAsync("\r\n--------------------------日期配置--------------------------\r\n");
            // timspan
            var duration = request.DateDuration.ToTimeSpan();
            await Console.Out.WriteLineAsync($"{nameof(duration)}:{duration.TotalSeconds}");
            // datetime
            var time = request.DateTimestamp.ToDateTime();
            await Console.Out.WriteLineAsync($"{nameof(time)}:{time:yyyy-MM-dd HH:mm:ss}");

            return new Empty();
        }

        // 字节
        public override async Task<Empty> ByteConfigService(ByteConfig request, ServerCallContext context)
        {
            await Console.Out.WriteLineAsync("\r\n--------------------------字节配置--------------------------\r\n");

            var bytes = request.PositionBytes.ToByteArray();
            var message = Encoding.UTF8.GetString(bytes, 0, bytes.Length);
            await Console.Out.WriteLineAsync($"{nameof(message)}:{message}");

            return new Empty();
        }
        // null配置
        public override async Task<Empty> NullConfigService(NullConfig request, ServerCallContext context)
        {
            await Console.Out.WriteLineAsync("\r\n--------------------------null配置--------------------------\r\n");
            // 打印字段信息
            var properties = request.GetType().GetProperties();
            foreach (var property in properties)
            {
                var value = property.GetValue(request);
                var printValue = value == null ? "返回null值" : value;
                await Console.Out.WriteLineAsync($"{property.Name}:{printValue}");
            }

            return new Empty();
        }

        // 集合
        public override async Task<Empty> ListConfigService(ListConfig request, ServerCallContext context)
        {
            await Console.Out.WriteLineAsync("\r\n--------------------------集合配置--------------------------\r\n");

            var id = request.Id;
            await Console.Out.WriteLineAsync($"主键标识:{id}\r\n");

            // 转换数组array
            await Console.Out.WriteLineAsync($"打印names信息:");
            var names = request.Names.ToArray();
            foreach (var name in names)
            {
                await Console.Out.WriteLineAsync(name);
            }

            // 转换list
            await Console.Out.WriteLineAsync($"\r\n打印detailList信息:");
            var detailList = request.Details.ToList();
            foreach (var item in detailList)
            {
                await Console.Out.WriteLineAsync($"ListDetailConfig:{nameof(item.Name)}  {item.Name};{nameof(item.Height)}  {item.Height}。");
            }

            // 字典

            await Console.Out.WriteLineAsync($"\r\n打印一般字典信息:");
            var dicAttributes = request.Attributes.ToDictionary(t => t.Key, t => t.Value);
            foreach (var attr in dicAttributes)
            {
                await Console.Out.WriteLineAsync($"key:{attr.Key};value:{attr.Value}。");
            }

            await Console.Out.WriteLineAsync($"\r\n打印对象字典信息:");
            foreach (var item in request.DicDetail)
            {
                await Console.Out.WriteLineAsync($"key:{item.Key};value:{item.Value.Name} | {item.Value.Height}。");
            }


            return new Empty();
        }

        // Any
        public override async Task<Empty> AnyConfigService(AnyConfig request, ServerCallContext context)
        {
            await Console.Out.WriteLineAsync("\r\n--------------------------Any配置--------------------------\r\n");

            var anyObject = request.AnyObject;

            // 检查是否是A对象
            if (anyObject.Is(A.Descriptor))
            {
                var a = anyObject.Unpack<A>();
                if (a is not null)
                {
                    await Console.Out.WriteLineAsync($"A对象:{a.Id}");
                }
            }
            else if (anyObject.Is(B.Descriptor))
            {
                var b = anyObject.Unpack<B>();
                if (b is not null)
                {
                    await Console.Out.WriteLineAsync($"B对象:{b.Id}");
                }
            }
            else if (anyObject.Is(C.Descriptor))
            {
                var c = anyObject.Unpack<C>();
                if (c is not null)
                {
                    await Console.Out.WriteLineAsync($"C对象:{c.Id}");
                }
            }
            else
            {
                await Console.Out.WriteLineAsync("Any未解析到任何对象");
            }


            return new Empty();
        }

        // oneof
        public override async Task<Empty> OneofConfigService(OneofConfig request, ServerCallContext context)
        {
            await Console.Out.WriteLineAsync("\r\n--------------------------Oneof配置--------------------------\r\n");

            // 检测对应的对象是否有值
            switch (request.ResultCase)
            {
                case OneofConfig.ResultOneofCase.None:
                    await Console.Out.WriteLineAsync("未检测到任何对象");
                    break;
                case OneofConfig.ResultOneofCase.OA:
                    await Console.Out.WriteLineAsync($"对象OA存在值:{request.OA.Id}");
                    break;
                case OneofConfig.ResultOneofCase.OB:
                    await Console.Out.WriteLineAsync($"对象OB存在值:{request.OB.Id}");
                    break;
                case OneofConfig.ResultOneofCase.OC:
                    await Console.Out.WriteLineAsync($"对象OC存在值:{request.OC.Id}");
                    break;
                default:
                    break;
            }


            return new Empty();
        }

    }

三、客户端定义

  1. 引用proto文件,配置为客户端类型
  2. 根据编译生成的函数进行传参调用
  3. 创建WPF测试客户端
  4. 各个服务接口创建对应的按钮进行调用
  5. 执行过程中,服务端控制台会打印对应的消息

.netcore grpc的proto文件字段详解,.netcore上的GRPC详解,.netcore,rpc

        // 基础
        private async void BtnBaseconfig_Click(object sender, RoutedEventArgs e)
        {
           await WpfFieldClient.Show(1);
            MessageBox();
        }


        // 日期
        private async void BtnDateconfig_Click(object sender, RoutedEventArgs e)
        {
            await WpfFieldClient.Show(2);
            MessageBox();
        }

        // 字节
        private async void BtnByteconfig_Click(object sender, RoutedEventArgs e)
        {
            await WpfFieldClient.Show(3);
            MessageBox();
        }

        // null
        private async void BtnNullconfig_Click(object sender, RoutedEventArgs e)
        {
            await WpfFieldClient.Show(4);
            MessageBox();
        }

        // list
        private async void BtnListconfig_Click(object sender, RoutedEventArgs e)
        {
            await WpfFieldClient.Show(5);
            MessageBox();
        }

        // any
        private async void BtnAnyconfig_Click(object sender, RoutedEventArgs e)
        {
            await WpfFieldClient.Show(6);
            MessageBox();
        }

        // Oneof
        private async void BtnOneofconfig_Click(object sender, RoutedEventArgs e)
        {
            await WpfFieldClient.Show(7);
            MessageBox();
        }

调用的类库:

    public class WpfFieldClient
    {
        /// <summary>
        /// 根据参数选择不同的方法执行
        /// </summary>
        /// <param name="k"></param>
        public static async Task Show(int k)
        {
            var channel = GrpcChannel.ForAddress("https://localhost:7188");

            var client = new GrpcProject.FieldRpc.FieldRpcClient(channel);
            // 基础
            BaseConfig config = new BaseConfig();
            config.Name = "张三";
            config.Position = 2.33D;
            config.Distance = 5.48F;
            config.Age = 10;
            config.TimeSpanId = 6538590027736100;
            config.SAge = 1921;
            config.STimeSpanId = 6538590027736130;
            config.Flag = true;
            // 日期
            DateConfig dateConfig = new DateConfig();
            dateConfig.Id = 179;
            dateConfig.DateDuration = Duration.FromTimeSpan(TimeSpan.FromSeconds(5));
            // 注意这里的时间是utc时间
            dateConfig.DateTimestamp = Timestamp.FromDateTime(DateTime.UtcNow);

            // 字节
            ByteConfig byteConfig = new ByteConfig();

            byteConfig.Id = 9854564654654;
            byteConfig.PositionBytes = ByteString.CopyFrom(Encoding.UTF8.GetBytes("庄这人的南的很"));

            // null
            NullConfig nullConfig = new NullConfig();
            nullConfig.Id = 1854564654654;
            nullConfig.NullBool = true;
            nullConfig.NullFloat = null;
            nullConfig.NullUInt = null;
            nullConfig.NullInt = 15;
            nullConfig.NullLong = 112345451234787;

            // ListConfig
            ListConfig listConfig = new ListConfig();
            var attributes = new Dictionary<int, string>
            {
                [1] = "one",
                [2] = "two",
                [3] = "three",
                [4] = "four",
                [5] = "five"
            };

            listConfig.Id = 123456456;
            listConfig.Attributes.Add(attributes);

            var dicDetail = new Dictionary<int, ListDetailConfig>
            {
                [1] = new ListDetailConfig { Height = 1, Name = "one" },
                [2] = new ListDetailConfig { Height = 2, Name = "two" },
                [3] = new ListDetailConfig { Height = 3, Name = "three" },
                [4] = new ListDetailConfig { Height = 4, Name = "four" },
                [5] = new ListDetailConfig { Height = 5, Name = "five" }
            };

            listConfig.DicDetail.Add(dicDetail);

            listConfig.Details.Add(new ListDetailConfig { Height = 8, Name = "Eight" });

            var detailConfigs = new List<ListDetailConfig>
            {
               new ListDetailConfig { Height=9,Name="nine"},
               new ListDetailConfig{ Height=10,Name="ten"}
            };

            listConfig.Details.Add(detailConfigs);

            // Any
            AnyConfig anyConfig = new AnyConfig();
            anyConfig.Id = 42564134;

            anyConfig.AnyObject = Any.Pack(new B { Id = 15 });

            // Oneof
            OneofConfig oneofConfig = new OneofConfig();
            oneofConfig.OA = new A { Id = 1 };
            //oneofConfig.OC = new C { Id = 2 };


            var emptyResult = k switch
            {
                1 => await client.BaseConfigServiceAsync(config),
                2 => await client.DateConfigServiceAsync(dateConfig),
                3 => await client.ByteConfigServiceAsync(byteConfig),
                4 => await client.NullConfigServiceAsync(nullConfig),
                5 => await client.ListConfigServiceAsync(listConfig),
                6 => await client.AnyConfigServiceAsync(anyConfig),
                7 => await client.OneofConfigServiceAsync(oneofConfig),
                _ => new Empty()
            };
        }
    }

五、执行结果

服务端:

.netcore grpc的proto文件字段详解,.netcore上的GRPC详解,.netcore,rpc

.netcore grpc的proto文件字段详解,.netcore上的GRPC详解,.netcore,rpc

 客户端:

.netcore grpc的proto文件字段详解,.netcore上的GRPC详解,.netcore,rpc

 六、源码地址

链接:https://pan.baidu.com/s/150TKY2Kgln3l_uKAsztyzw 
提取码:hkb9

下一篇https://blog.csdn.net/qq_31975127/article/details/132345428文章来源地址https://www.toymoban.com/news/detail-654508.html

到了这里,关于.netcore grpc的proto文件字段详解的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • Vscode配置grpc+c#+proto

            首先是环境配置,用的dotnet5.0的sdk,所以Vscode的C#插件版本要选择1.24,然后需要配置C# Snippets、NuGget Package Manager、vscode-proto3、vscode-solution-extension(可选)。         以vscode-solution-extension为例新建Asp.netCore web.app,删除多余项目。新建Protos文件夹,该文件夹内部放

    2024年02月17日
    浏览(39)
  • 探索YOLOv5微服务:gRPC Proto设计与优化策略

    YOLOv5(You Only Look Once, version 5)是一种流行的深度学习模型,用于实时对象检测。作为YOLO系列的最新迭代,它以其高效的性能和相对较低的资源需求而闻名。YOLOv5的核心优势在于其能够在单次前向传递中同时预测多个对象的类别和位置,这使得它在实时图像处理和视频分析领

    2024年01月21日
    浏览(44)
  • .netcore grpc日志记录配置

    通过配置文件appsettings.json进行配置 通过Program.cs进行配置 通过环境变量进行配置 客户端通过日志通道进行配置 配置环境变量:Logging__LogLevel__Grpc=Debug 配置Appsettings.json 配置Program.cs 配置客户端工厂 以上截图是目前为止已知的可以配置日志的方式。 链接:https://pan.baidu.com/s/1L

    2024年02月10日
    浏览(33)
  • .netcore grpc身份验证和授权

    权限认证这里使用IdentityServer4配合JWT进行认证 通过AddAuthentication和AddAuthorization方法进行鉴权授权注入;通过UseAuthentication和UseAuthorization启用鉴权授权 增加授权策略处理 使用密码模式,及简易内存处理 生成token带入grpc的metadata进行传递 服务端对应的方法标记特性[Authorize]进行

    2024年02月12日
    浏览(37)
  • .netcore grpc客户端工厂及依赖注入使用

    gRPC 与  HttpClientFactory  的集成提供了一种创建 gRPC 客户端的集中方式。 可以通过依赖包Grpc.Net.ClientFactory中的AddGrpcClient进行gRPC客户端依赖注入 AddGrpcClient函数提供了许多配置项用于处理一些其他事项;例如AOP、重试策略等 创建一个WPF客户端 在App.xaml.cs代码类里重写OnStartup方

    2024年02月12日
    浏览(34)
  • .NetCore gRpc 客户端与服务端的单工通信Demo

    方式一 使用vs 2022(也可以是其他版本)创建一个grpc的服务,如下这样 [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-uipEG9Xu-1687172462785)(C:UsersAdministratorAppDataRoamingTyporatypora-user-imagesimage-20230619183828284.png)] 简单方便,创建项目后的目录结构如下图

    2024年02月09日
    浏览(53)
  • 掌握 gRPC 和 RPC 的关键区别

    1、RPC 的本质 首先,我们探讨一下什么是  RPC 。RPC,缩写为 Remote Procedure Call Protocol,直译来看就是 远程过程调用协议 。 讲得通俗一些: RPC 是一种 通信机制 RPC 实现了 客户端/服务器 通信模型 官方的定义可能会这样解释: 它是一种协议,可以使程序能在网络上请求远程计

    2024年02月02日
    浏览(31)
  • nodejs微服务:RPC与GRPC框架

    RPC RPC(Remote Procedure Call Protocol),是远程过程调用的缩写 通俗的说就是调用远处的一个函数,与之相对应的是本地函数调用 本地函数调用:参数,返回值,代码段都在本地的一个进程空间内 远程函数调用:远程,即跨进程,这个进程部署在另一台服务器上,也就是调用另一台

    2023年04月20日
    浏览(37)
  • rpc、gRPC快速入门,python调用,protobuf协议

    远程过程调用协议RPC (Remote Procedure Call Protocol) RPC是指远程过程调用,也就是说两台服务器A,B,一个应用部署在A服务器上,想要调用B服务器上应用提供的函数/方法,由于不在一个内存空间,不能直接调用,需要通过网络来表达调用的语义和传达调用的数据 举例:在 a服务内

    2024年02月13日
    浏览(52)
  • 【gRPC】第1篇 全面讲解RPC原理(必收藏)

    目录 1、什么是 RPC  2、为什么要用 RPC  3、常用的 RPC 框架 4、RPC 的调用流程 RPC(Remote Procedure Call Protocol)远程过程调用协议 ,目标就是让远程服务调用更加简单、透明。 RPC 框架负责屏蔽底层的传输方式(TCP 或者 UDP)、序列化方式(XML/Json/ 二进制)和通信细节,服务调用

    2023年04月09日
    浏览(29)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包