点击上方“程序员大咖”,选择“置顶公众号”
来源:叶俊权
cnblogs.com/yjq-code/p/Rpc.html
程序员大咖整理发布,转载请联系作者获得授权
一、特性
1、跨平台
2、提供负载均衡算法
3、支持ZK服务协调
4、提供了JSON、BinarySerializer、还有自定义的序列化方式
5、客户端提供Socket连接池,以便于快速交互,防止类似大文件上传时会阻塞
6、支持异步方法
7、支持.net与.netcore之间通信
8、支持采用MongoDb收集请求信息(采用双缓冲队列,极限的不影响传输速度)
9、提供请求日志监控后台(还未全部完善)
二、项目结构
编译器采用vs2017.
NRpcItem 是Framework下的NRpc源代码。NetCoreRpcItem是.NetCore下的源代码。NRpcSerializer是自己写的一个序列化方法,速度和json序列化对比稍慢一点,但是速度可以接收。
值得注意的是NRpcItem 里面采用Autofac来作为IOC容器,服务端的代码都必须要基于Autofac来实现依赖注入。
NRpc.AdminManage是日志监控后台,目前只有.netCore版本。
三、自定义序列化方法性能测试
虽然在执行速度上比json稍慢,但是支持对byte[]类型的序列化,而且客户端不需要任何的标记,方便使用。
实现过程中参考csharp-hessian的序列化实现方式,支持跨平台。
四、如何使用Rpc
1、服务端:
a、参考NetCoreRpc.Application项目,先定义好IStudentApplication以及他的实现类StudentApplication
b、参考NetCoreRpc.ServerTest项目中Program,先绑定好依赖注入信息,如果要使用zk,则加上.UseZK();扩展方法,不然不采用ZK的服务发现
> private static IServiceProvider BuildDi()
>
> {
>
> IServiceCollection services = new ServiceCollection();
>
> services.AddSingleton<ILoggerFactory, LoggerFactory>();
>
> services.AddSingleton(typeof(ILogger<>), typeof(Logger<>));
>
> services.AddSingleton<IStudentApplication, StudentApplication>();
>
> var str = Configuration.GetValue<string>("MongoDB:Str");
>
> var dbName = Configuration.GetValue<string>("MongoDB:DatabaseName");
>
> services.UseRpc()
>
> .UseMongoDBMonitor(() =>
>
> {
>
> return new MonogoDbConfig(str, dbName);
>
> });//.UseZK();
>
> var serviceProvider = services.BuildServiceProvider();
>
> var loggerFactory = serviceProvider.GetRequiredService<ILoggerFactory>();
>
> loggerFactory.AddNLog(new NLogProviderOptions { CaptureMessageTemplates = true, CaptureMessageProperties = true });
>
> loggerFactory.ConfigureNLog("NLog.config");
>
> return serviceProvider;
>
> }
c、配置文件信息,配置ZK和MongoDb链接配置信息
> {
>
> "NetCoreRpc": {
>
> "Zookeeper": {
>
> "Connection": "192.168.100.34:2181",
>
> "ParentName": "/NetCoreRpc/ClientTest"
>
> }
>
> },
>
> "MongoDB": {
>
> "Str": "mongodb://root:root@192.168.100.125:27017",
>
> "DatabaseName": "Rpc_Monitor"
>
> }
>
> }
d、开启监听
> private static void Main(string[] args)
>
> {
>
> Console.WriteLine("请输入监听端口:");
>
> var strPort = Console.ReadLine();
>
> var builder = new ConfigurationBuilder()
>
> .SetBasePath(Path.Combine(AppContext.BaseDirectory)).AddJsonFile("NetCoreRpc.json", optional: true);
>
> Configuration = builder.Build();
>
> var servicesProvider = BuildDi();
>
> DependencyManage.SetServiceProvider(servicesProvider, Configuration);
>
> NRpcServer nrpcServer = new NRpcServer(int.Parse(strPort));
>
> nrpcServer.Start("NetCoreRpc.Application");
>
> Console.WriteLine("Welcome to use NetCoreRpc!");
>
> Console.WriteLine("Input exit to exit");
>
> var str = Console.ReadLine();
>
> while (!string.Equals(str, "exit", StringComparison.OrdinalIgnoreCase))
>
> {
>
> str = Console.ReadLine();
>
> }
>
> nrpcServer.ShutDown();
>
> }
2、客户端如何调用
a、参考NetCoreRpc.ClientTest项目先配置一些基础的依赖信息
> private static IServiceProvider BuildDi()
>
> {
>
> IServiceCollection services = new ServiceCollection();
>
> services.AddOptions();
>
> services.Configure<RpcConfig>(Configuration.GetSection("NetCoreRpc"));
>
> services.AddSingleton<ILoggerFactory, LoggerFactory>();
>
> services.AddSingleton(typeof(ILogger<>), typeof(Logger<>));
>
> services.UseRpc().UseMongoDBMonitor(() =>
>
> {
>
> var str = Configuration.GetValue<string>("MongoDB:Str");
>
> var dbName = Configuration.GetValue<string>("MongoDB:DatabaseName");
>
> return new MonogoDbConfig(str, dbName);
>
> });//.UseZK();
>
> var serviceProvider = services.BuildServiceProvider();
>
> var loggerFactory = serviceProvider.GetRequiredService<ILoggerFactory>();
>
> //configure NLog
>
> loggerFactory.AddNLog(new NLogProviderOptions { CaptureMessageTemplates = true, CaptureMessageProperties = true });
>
> loggerFactory.ConfigureNLog("NLog.config");
>
> return serviceProvider;
>
> }
b、配置文件内容
> {
>
> "NetCoreRpc": {
>
> "RequestTimeouMillis": 10000,
>
> "Default": "192.168.129.117:12345",
>
> //"Group": [
>
> // {
>
> // "NameSpace": "",
>
> // "Address": "127.0.0.1:12345"
>
> // }
>
> //],
>
> "Zookeeper": {
>
> "Connection": "192.168.100.34:2181",
>
> "ParentName": "/NetCoreRpc/ClientTest"
>
> }
>
> },
>
> "MongoDB": {
>
> "Str": "mongodb://root:root@192.168.100.125:27017",
>
> "DatabaseName": "Rpc_Monitor"
>
> }
>
> }
配置服务端地址,也可以根据类的名字来配置服务端地址,因为一个客户端在业务多的时候可能调用了多个服务端,所以提供了根据类型的名字来配置服务端地址
c、如何开始调用
首先接口类和Model类的命名控件必须要与服务端一致,比如例子中的IStudentApplication与TestModel这两个。
然后通过代理类来实例化接口类,然后调用对应的方法即可。
> private static void Send()
>
> {
>
> var studentApplication = ProxyFactory.Create<IStudentApplication>();
>
> Console.WriteLine(studentApplication.Age());
>
> Console.WriteLine(studentApplication.IsYongPeople(15));
>
> var runTask = studentApplication.RunAsync(111);
>
> studentApplication.Say("Hello world");
>
> studentApplication.Say(Encoding.UTF8.GetBytes("Hi!"));
>
> Console.WriteLine(Encoding.UTF8.GetString(studentApplication.Say()));
>
> var test = studentApplication.Test();
>
> Console.WriteLine(test.ToString());
>
> studentApplication.Sleep();
>
> Console.WriteLine(runTask.Result);
>
> }
framework版本与.netcore版本大同小异,具体的实际使用请参考下各个项目的Test文件。
五、调用案例结果
六、服务端监控
监控应用还没有完善好,后续会完善的,对了监控应用必须基于MongoDB。
七、项目开源地址
https://github.com/yjqGitHub/NetCoreRpc
欢迎大家来吐槽,提建议,如果有兴趣一起来完善的就更好了。
▼点击「阅读原文」进入程序员商城