苏州网站定制公司哪家好,wordpress插件的页面文件,企业信息公示网查询官网,制造企业网站的建设目标一、前言 至今为止编程开发已经11个年头#xff0c;从 VB6.0,ASP时代到ASP.NET再到MVC, 从中见证了.NET技术发展#xff0c;从无畏无知的懵懂少年#xff0c;到现在的中年大叔#xff0c;从中的酸甜苦辣也只有本人自知。随着岁月的成长#xff0c;技术也从原来的三层设计到…一、前言 至今为止编程开发已经11个年头从 VB6.0,ASP时代到ASP.NET再到MVC, 从中见证了.NET技术发展从无畏无知的懵懂少年到现在的中年大叔从中的酸甜苦辣也只有本人自知。随着岁月的成长技术也从原来的三层设计到现在的领域驱动设计从原来的关系型数据库SQL 2000到现在的NOSQL (mongodb,couchbase,redis),从原来基于SOAP协议的web service到现在基于restful 协议的web api,wcf再到现在rpc微服务。技术的成长也带来岁月的痕迹。 现在微软又出了.NET CORE,为了紧跟微软的步伐研究了将近1年从中看了不少开源代码如NetEscapades.ConfigurationeShopOnContainersrabbit.RPC等等从中学到了不少知识后面利用所学加上自己的想法开发出分布式微服务框架surging。开源地址https://github.com/fanliang11/surging。下面会以三篇文章的形式介绍
surging
1.基于.NET CORE微服务框架 -surging的介绍和简单示例 开源
2.剥析surging的架构思想
3.后续surging的架构完善工作
二、什么是surging
surging从中文译义来说冲击汹涌也可以翻译成风起云涌。我所希望的是.net core 能成为i最流行的技术。
surging从技术层面来说就是基于RPC协议的分布式微服务技术框架,框架依赖于Netty 进行异步通信,采用Zookeeper作为服务注册中心集成了哈希随机和轮询作为负载均衡算法
1.服务化应用基本框架
框架的执行过程如下
1.服务提供者启动根据RPC协议通过配置的IP和port绑定到netty上
2.注册服务信息存储至Zookeeper
3.客户端CreateProxy调用服务时从内存中拿到上次通知的所有效的服务地址根据路由信息和负载均衡机制选择最终调用的服务地址发起调用
2.简单示例 创建IModuleServices IUserService.cs: [ServiceBundle] //服务标记 public interface IUserService { Task string GetUserName( int id); Task bool Exists( int id); Task int GetUserId( string userName); TaskDateTime GetUserLastSignInTime( int id); TaskUserModel GetUser( int id); Task bool Update( int id, UserModel model); TaskIDictionary string , string GetDictionary(); Task TryThrowException(); } 创建领域对象 UserModel: [ProtoContract] public class UserModel { [ProtoMember(1)] public string Name { get ; set ; } [ProtoMember(2)] public int Age { get ; set ; } } AssemblyInfo.cs扩展AssemblyModuleType来标识模块根据AssemblyModuleType进行相关规则的反射注册 [assembly: AssemblyTitle( Surging.IModuleServices.Common )] [assembly: AssemblyDescription( 业务模块接口 )] [assembly: AssemblyModuleType(ModuleType.InterFaceService)] // 如果此项目向 COM 公开则下列 GUID 用于类型库的 ID [assembly: Guid( 2103624d-2bc2-4164-9aa5-1408daed9dee )] 创建Domain Service
PersonService.cs [ModuleName( Person )] //标识实例化名称 public class PersonService : ServiceBase,IUserService { #region Implementation of IUserService private readonly UserRepository _repository; public PersonService(UserRepository repository) { this ._repository repository; } public Task string GetUserName( int id) { return GetServiceIUserService( User ).GetUserName(id); } public Task bool Exists( int id) { return Task.FromResult( true ); } public Task int GetUserId( string userName) { return Task.FromResult(1); } public TaskDateTime GetUserLastSignInTime( int id) { return Task.FromResult(DateTime.Now); } public TaskUserModel GetUser( int id) { return Task.FromResult( new UserModel { Name fanly , Age 18 }); } public Task bool Update( int id, UserModel model) { return Task.FromResult( true ); } public TaskIDictionary string , string GetDictionary() { return Task.FromResultIDictionary string , string ( new Dictionary string , string { { key , value } }); } public async Task Try() { Console.WriteLine( start ); await Task.Delay(5000); Console.WriteLine( end ); } public Task TryThrowException() { throw new Exception( 用户Id非法 ); } #endregion Implementation of IUserService } } UserService.cs [ModuleName( User )] //标识实例化名称 public class UserService: IUserService { #region Implementation of IUserService private readonly UserRepository _repository; public UserService(UserRepository repository) { this ._repository repository; } public Task string GetUserName( int id) { return Task.FromResult($ id:{id} is name fanly. ); } public Task bool Exists( int id) { return Task.FromResult( true ); } public Task int GetUserId( string userName) { return Task.FromResult(1); } public TaskDateTime GetUserLastSignInTime( int id) { return Task.FromResult(DateTime.Now); } public TaskUserModel GetUser( int id) { return Task.FromResult( new UserModel { Name fanly , Age 18 }); } public Task bool Update( int id, UserModel model) { return Task.FromResult( true ); } public TaskIDictionary string , string GetDictionary() { return Task.FromResultIDictionary string , string ( new Dictionary string , string { { key , value } }); } public async Task Try() { Console.WriteLine( start ); await Task.Delay(5000); Console.WriteLine( end ); } public Task TryThrowException() { throw new Exception( 用户Id非法 ); } #endregion Implementation of IUserService } } AssemblyInfo.cs扩展AssemblyModuleType来标识模块根据AssemblyModuleType进行相关规则的反射注册 [ModuleName( User )] //标识实例化名称 public class UserService: IUserService { #region Implementation of IUserService private readonly UserRepository _repository; public UserService(UserRepository repository) { this ._repository repository; } public Task string GetUserName( int id) { return Task.FromResult($ id:{id} is name fanly. ); } public Task bool Exists( int id) { return Task.FromResult( true ); } public Task int GetUserId( string userName) { return Task.FromResult(1); } public TaskDateTime GetUserLastSignInTime( int id) { return Task.FromResult(DateTime.Now); } public TaskUserModel GetUser( int id) { return Task.FromResult( new UserModel { Name fanly , Age 18 }); } public Task bool Update( int id, UserModel model) { return Task.FromResult( true ); } public TaskIDictionary string , string GetDictionary() { return Task.FromResultIDictionary string , string ( new Dictionary string , string { { key , value } }); } public async Task Try() { Console.WriteLine( start ); await Task.Delay(5000); Console.WriteLine( end ); } public Task TryThrowException() { throw new Exception( 用户Id非法 ); } #endregion Implementation of IUserService } } 3.服务端 using Autofac; using Autofac.Extensions.DependencyInjection; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Logging; using Surging.Core.Caching.Configurations; using Surging.Core.CPlatform; using Surging.Core.CPlatform.Runtime.Server; using Surging.Core.DotNetty; using Surging.Core.ProxyGenerator.Utilitys; using Surging.Core.System.Ioc; using Surging.Core.Zookeeper; using Surging.Core.Zookeeper.Configurations; using System; using System.Net; using System.Text; using System.Threading.Tasks; namespace Surging.Services.Server { public class Program { static void Main( string [] args) { Encoding.RegisterProvider(CodePagesEncodingProvider.Instance); var services new ServiceCollection(); var builder new ContainerBuilder(); ConfigureLogging(services); builder.Populate(services); ConfigureService(builder); ServiceLocator.Current builder.Build(); ConfigureCache(); ServiceLocator.GetServiceILoggerFactory() .AddConsole((c, l) ( int )l 3); StartService(); Console.ReadLine(); } /// summary /// 配置相关服务 /// /summary /// param namebuilder/param /// returns/returns private static void ConfigureService(ContainerBuilder builder) { builder.Initialize(); builder.RegisterServices(); builder.RegisterRepositories(); builder.RegisterModules(); builder.AddCoreServce() .AddServiceRuntime() .UseSharedFileRouteManager( c:\\routes.txt ) //配置本地路由文件路径 .UseDotNettyTransport() //配置Netty .UseZooKeeperRouteManager( new ConfigInfo( 192.168.1.6:2181 , /dotnet/unitTest/serviceRoutes )); //配置ZooKeeper builder.Register(p new CPlatformContainer(ServiceLocator.Current)); } /// summary /// 配置日志服务 /// /summary /// param nameservices/param public static void ConfigureLogging(IServiceCollection services) { services.AddLogging(); } /// summary /// 配置缓存服务 /// /summary public static void ConfigureCache() { new ConfigurationBuilder() .SetBasePath(AppContext.BaseDirectory) .AddCacheFile( cacheSettings.json , optional: false ); } /// summary /// 启动服务 /// /summary public static void StartService() { var serviceHost ServiceLocator.GetServiceIServiceHost(); Task.Factory.StartNew(async () { await serviceHost.StartAsync( new IPEndPoint(IPAddress.Parse( 127.0.0.1 ), 98)); Console.WriteLine($ 服务端启动成功{DateTime.Now}。 ); }).Wait(); } } } 4.客户端 using Autofac; using Autofac.Extensions.DependencyInjection; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Logging; using Surging.Core.CPlatform; using Surging.Core.DotNetty; using Surging.Core.ProxyGenerator; using Surging.Core.ProxyGenerator.Utilitys; using Surging.Core.System.Ioc; using System.Text; namespace Surging.Services.Client { public class Program { static void Main( string [] args) { Encoding.RegisterProvider(CodePagesEncodingProvider.Instance); var services new ServiceCollection(); var builder new ContainerBuilder(); ConfigureLogging(services); builder.Populate(services); ConfigureService(builder); ServiceLocator.Current builder.Build(); ServiceLocator.GetServiceILoggerFactory() .AddConsole((c, l) ( int )l 3); } /// summary /// 配置相关服务 /// /summary /// param namebuilder/param /// returns/returns private static void ConfigureService(ContainerBuilder builder) { builder.Initialize(); builder.RegisterServices(); builder.RegisterRepositories(); builder.RegisterModules(); var serviceBulider builder .AddClient() .UseSharedFileRouteManager( c:\\routes.txt ) .UseDotNettyTransport(); } /// summary /// 配置日志服务 /// /summary /// param nameservices/param public static void ConfigureLogging(IServiceCollection services) { services.AddLogging(); } /// summary /// 配置服务代理 /// /summary /// param namebuilder/param /// returns/returns public static IServiceProxyFactory RegisterServiceProx(ContainerBuilder builder) { var serviceProxyFactory ServiceLocator.GetServiceIServiceProxyFactory(); serviceProxyFactory.RegisterProxType(builder.GetInterfaceService().ToArray()); return serviceProxyFactory; } } } 远程服务调用 ServiceLocator.GetServiceIServiceProxyFactory().CreateProxyT(key) 本地模块和服务调用 ServiceLocator.GetServiceIServiceProxyFactory().CreateProxyT(key) 5.负载均衡
surging提供3种负载均衡方式:
Random:随机调用量越大分布越均匀默认是这种方式
Polling:轮询存在比较慢的机器容易在这台机器的请求阻塞较多
HashAlgorithm:一致性哈希对于相同参数的请求路由到一个服务提供者上。
6.其他功能
surging还会提供分布式缓存AOP数据拦截基于rabbitmq订阅发布, 监控服务后续完善后再来讲解。
6.性能测试
测试环境
CPU:Intel Core i7-4710MQ
内存16G
硬盘1T SSD512G HDD
网络局域网
测试结果如下 1万次调用也就2290MS平均单次也就0.229毫秒性能不错。
7.总结
surging 0.0.0.1版本的发布意味着分布式微服务已经走出了第一步以后还有很多工作需要完善。我会花很多空余时间去完善它。如果大家还有任何疑问或者感兴趣的话可以加入QQ群615562965
相关文章
谷歌发布的首款基于HTTP/2和protobuf的RPC框架GRPC拥抱.NET Core跨平台的轻量级RPCRabbit.Rpc基于DotNet Core的RPC框架(一) DotBPE.RPC快速开始
原文地址http://www.cnblogs.com/fanliang11/p/7049472.html .NET社区新闻深度好文微信中搜索dotNET跨平台或扫描二维码关注