因为经常买双色球,嫌每次对彩票号麻烦,于是休息的时候做了个双色球兑奖的小程序,做完了发现业务还挺复杂的,于是改DDD重做设计,拆分服务,各种折腾...,不过这和本随笔没多大关系,等差不多了再总结一下,有空就写出来。

上面说了拆服务,拆成了录入,开奖,兑奖三个服务,三个服务开始是用消息队列的,不过后来发现其实就是服务的领域对象之间的交互,就联想到了Actor,面向对象于是一切都是对象,actor也是一切都是actor,看着就门当户对,于是就干掉消息队列。。。细节以后有机会再说。

上面其实也和这随笔没啥关系,有关系的是,因为时间关系,没去了解akka的文档,于是好奇一件事,服务器连接地址中的"user"是哪来的:

//var section = (AkkaConfigurationSection)ConfigurationManager.GetSection("akka");

//using (var system = ActorSystem.Create("TestClient", section.AkkaConfig))

  1. using (var system = ActorSystem.Create("TestClient"))
  2. {
  3. var actor = system.ActorSelection("akka.tcp://TestServer@localhost:8081/user/tester");
  4.  
  5. while (true)
  6. {
  7. var input = Console.ReadLine();
  8. if (input.Equals(""))
  9. {
  10. actor.Tell(new DTO(""));
  11. }
  12. else if (input.Equals(""))
  13. {
  14. actor.Tell(new DTO(""));
  15. }
  16. else
  17. {
  18. actor.Tell(new DTO("H W"));
  19. }
  20. }
  21. }

上面是客户端,下面是服务端:

  1. var config = ConfigurationFactory.ParseString(@"
  2. akka {
  3. actor {
  4. provider = ""Akka.Remote.RemoteActorRefProvider, Akka.Remote""
  5. }
  6. remote {
  7. helios.tcp {
  8. transport-class = ""Akka.Remote.Transport.Helios.HeliosTcpTransport, Akka.Remote""
  9. applied-adapters = []
  10. transport-protocol = tcp
  11. port = 8081
  12. hostname = localhost
  13. }
  14. }
  15. }
  16. ");
  17.  
  18. using (var system = ActorSystem.Create("TestServer", config))
  19. {
  20. system.ActorOf<TestDTOActor>("tester");
  21.  
  22. Console.ReadLine();
  23. }

文档想必很多,最近有别的要看,于是想想看看代码得了,反正一时还不会用到生产环境,到时候再说吧,先解决好奇的问题。

于是首先是ActorSystem的实现类ActorSystemImpl,system.ActorOf<TestDTOActor>("tester")对服务端路径影响的应该是ActorOf:

  1. public override IActorRef SystemActorOf<TActor>(string name = null)
  2. {
  3. return _provider.SystemGuardian.Cell.ActorOf<TActor>(name);
  4. }

于是找找_provider:

  1. public ActorSystemImpl(string name, Config config)
  2. {
  3. if(!Regex.Match(name, "^[a-zA-Z0-9][a-zA-Z0-9-]*$").Success)
  4. throw new ArgumentException(
  5. "invalid ActorSystem name [" + name +
  6. "], must contain only word characters (i.e. [a-zA-Z0-9] plus non-leading '-')");
  7. if(config == null)
  8. throw new ArgumentNullException("config");
  9.  
  10. _name = name;
  11. ConfigureSettings(config);
  12. ConfigureEventStream();
  13. ConfigureProvider();
  14. ConfigureTerminationCallbacks();
  15. ConfigureScheduler();
  16. ConfigureSerialization();
  17. ConfigureMailboxes();
  18. ConfigureDispatchers();
  19. ConfigureActorProducerPipeline();
  20. }
  21.  
  22. private void ConfigureSettings(Config config)
  23. {
  24. _settings = new Settings(this, config);
  25. }
  26.  
  27. private void ConfigureProvider()
  28. {
  29. Type providerType = Type.GetType(_settings.ProviderClass);
  30. global::System.Diagnostics.Debug.Assert(providerType != null, "providerType != null");
  31. var provider = (IActorRefProvider)Activator.CreateInstance(providerType, _name, _settings, _eventStream);
  32. _provider = provider;
  33. }
  1. public Settings(ActorSystem system, Config config)
  2. {
  3. _userConfig = config;
  4. _fallbackConfig = ConfigurationFactory.Default();
  5. RebuildConfig();
  6.  
  7. System = system;
  8.  
  9. ConfigVersion = Config.GetString("akka.version");
  10. ProviderClass = Config.GetString("akka.actor.provider");
  11. var providerType = Type.GetType(ProviderClass);
  12. if (providerType == null)
  13. throw new ConfigurationException(string.Format("'akka.actor.provider' is not a valid type name : '{0}'", ProviderClass));
  14. if (!typeof(IActorRefProvider).IsAssignableFrom(providerType))
  15. throw new ConfigurationException(string.Format("'akka.actor.provider' is not a valid actor ref provider: '{0}'", ProviderClass));
  16.  
  17. SupervisorStrategyClass = Config.GetString("akka.actor.guardian-supervisor-strategy");
  18.  
  19. AskTimeout = Config.GetTimeSpan("akka.actor.ask-timeout", allowInfinite: true);
  20. CreationTimeout = Config.GetTimeSpan("akka.actor.creation-timeout");
  21. UnstartedPushTimeout = Config.GetTimeSpan("akka.actor.unstarted-push-timeout");
  22.  
  23. SerializeAllMessages = Config.GetBoolean("akka.actor.serialize-messages");
  24. SerializeAllCreators = Config.GetBoolean("akka.actor.serialize-creators");
  25.  
  26. LogLevel = Config.GetString("akka.loglevel");
  27. StdoutLogLevel = Config.GetString("akka.stdout-loglevel");
  28. Loggers = Config.GetStringList("akka.loggers");
  29.  
  30. LoggerStartTimeout = Config.GetTimeSpan("akka.logger-startup-timeout");
  31.  
  32. //handled
  33. LogConfigOnStart = Config.GetBoolean("akka.log-config-on-start");
  34. LogDeadLetters = ;
  35. switch (Config.GetString("akka.log-dead-letters"))
  36. {
  37. case "on":
  38. case "true":
  39. LogDeadLetters = int.MaxValue;
  40. break;
  41. case "off":
  42. case "false":
  43. LogDeadLetters = ;
  44. break;
  45. default:
  46. LogDeadLetters = Config.GetInt("akka.log-dead-letters");
  47. break;
  48. }
  49. LogDeadLettersDuringShutdown = Config.GetBoolean("akka.log-dead-letters-during-shutdown");
  50. AddLoggingReceive = Config.GetBoolean("akka.actor.debug.receive");
  51. DebugAutoReceive = Config.GetBoolean("akka.actor.debug.autoreceive");
  52. DebugLifecycle = Config.GetBoolean("akka.actor.debug.lifecycle");
  53. FsmDebugEvent = Config.GetBoolean("akka.actor.debug.fsm");
  54. DebugEventStream = Config.GetBoolean("akka.actor.debug.event-stream");
  55. DebugUnhandledMessage = Config.GetBoolean("akka.actor.debug.unhandled");
  56. DebugRouterMisconfiguration = Config.GetBoolean("akka.actor.debug.router-misconfiguration");
  57. Home = Config.GetString("akka.home") ?? "";
  58. DefaultVirtualNodesFactor = Config.GetInt("akka.actor.deployment.default.virtual-nodes-factor");
  59.  
  60. SchedulerClass = Config.GetString("akka.scheduler.implementation");
  61. //TODO: dunno.. we dont have FiniteStateMachines, dont know what the rest is
  62. /*
  63. final val SchedulerClass: String = getString("akka.scheduler.implementation")
  64. final val Daemonicity: Boolean = getBoolean("akka.daemonic")
  65. final val DefaultVirtualNodesFactor: Int = getInt("akka.actor.deployment.default.virtual-nodes-factor")
  66. */
  67. }

很明显,看配置文件的akka.actor.provider:

  1. <configuration>
  2. <configSections>
  3. <section name="akka" type="Akka.Configuration.Hocon.AkkaConfigurationSection, Akka" />
  4. </configSections>
  5. <startup>
  6. <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
  7. </startup>
  8. <akka>
  9. <hocon>
  10. <![CDATA[
  11. akka {
  12. actor {
  13. provider = "Akka.Remote.RemoteActorRefProvider, Akka.Remote"
  14. }
  15. remote {
  16. helios.tcp {
  17. transport-class = "Akka.Remote.Transport.Helios.HeliosTcpTransport, Akka.Remote"
  18. applied-adapters = []
  19. transport-protocol = tcp
  20. port = 0
  21. hostname = localhost
  22. }
  23. }
  24. }
  25. ]]>
  26. </hocon>
  27. </akka>
  28. </configuration>

于是RemoteActorRefProvider:

  1. public LocalActorRef SystemGuardian { get { return _local.SystemGuardian; } }
  2.  
  3. public RemoteActorRefProvider(string systemName, Settings settings, EventStream eventStream)
  4. {
  5. settings.InjectTopLevelFallback(RemoteConfigFactory.Default());
  6.  
  7. var remoteDeployer = new RemoteDeployer(settings);
  8. Func<ActorPath, IInternalActorRef> deadLettersFactory = path => new RemoteDeadLetterActorRef(this, path, eventStream);
  9. _local = new LocalActorRefProvider(systemName, settings, eventStream, remoteDeployer, deadLettersFactory);
  10. RemoteSettings = new RemoteSettings(settings.Config);
  11. Deployer = remoteDeployer;
  12. _log = _local.Log;
  13. }

好吧,看LocalActorRefProvider:

  1. public void Init(ActorSystemImpl system)
  2. {
  3. _system = system;
  4. //The following are the lazy val statements in Akka
  5. var defaultDispatcher = system.Dispatchers.DefaultGlobalDispatcher;
  6. _defaultMailbox = () => new ConcurrentQueueMailbox(); //TODO:system.Mailboxes.FromConfig(Mailboxes.DefaultMailboxId)
  7. _rootGuardian = CreateRootGuardian(system);
  8. _tempContainer = new VirtualPathContainer(system.Provider, _tempNode, _rootGuardian, _log);
  9. _rootGuardian.SetTempContainer(_tempContainer);
  10. _userGuardian = CreateUserGuardian(_rootGuardian, "user");
  11. _systemGuardian = CreateSystemGuardian(_rootGuardian, "system", _userGuardian);
  12. //End of lazy val
  13.  
  14. _rootGuardian.Start();
  15. // chain death watchers so that killing guardian stops the application
  16. _systemGuardian.Tell(new Watch(_userGuardian, _systemGuardian)); //Should be SendSystemMessage
  17. _rootGuardian.Tell(new Watch(_systemGuardian, _rootGuardian)); //Should be SendSystemMessage
  18. _eventStream.StartDefaultLoggers(_system);
  19. }
  1. private LocalActorRef CreateUserGuardian(LocalActorRef rootGuardian, string name) //Corresponds to Akka's: override lazy val guardian: LocalActorRef
  2. {
  3. return CreateRootGuardianChild(rootGuardian, name, () =>
  4. {
  5. var props = Props.Create<GuardianActor>(UserGuardianSupervisorStrategy);
  6.  
  7. var userGuardian = new LocalActorRef(_system, props, DefaultDispatcher, _defaultMailbox, rootGuardian, RootPath/name);
  8. return userGuardian;
  9. });
  10. }

看样子,这个RootPath还重载了操作符:

  1. public static ActorPath operator /(ActorPath path, string name)
  2. {
  3. return new ChildActorPath(path, name, );
  4. }
  5.  
  6. public static ActorPath operator /(ActorPath path, IEnumerable<string> name)
  7. {
  8. var a = path;
  9. foreach (string element in name)
  10. {
  11. a = a / element;
  12. }
  13. return a;
  14. }

现在_userGuardian路径是看到了,生拼上去的,那么哪里用的呢

  1. LocalActorRefProvider:
  2.  
  3. public LocalActorRef Guardian { get { return _userGuardian; } }
  4.  
  5. RemoteActorRefProvider:
  6.  
  7. public LocalActorRef Guardian { get { return _local.Guardian; } }

再回来看system.ActorOf<TestDTOActor>("tester")这句:

  1. public override IActorRef ActorOf(Props props, string name = null)
  2. {
  3. return _provider.Guardian.Cell.ActorOf(props, name: name);
  4. }

这就是我自己配的provider造成的,其实还是配置问题,当然,这么看我们其实可以实现自己的provider,想怎么搞就怎么搞,有时间其实还是应该看下文档,不过想来文档应该会说怎么用什么样,当应该不会说怎么实现的,要知道为什么,怎么改,估计还是要自己看代码,此致。

Akka.net路径里的user的更多相关文章

  1. 22.访问jar包下资源路径里的文件

    访问jar包下资源路径里的文件 因为打包路径和你构建的代码路径是有差异的,想要查看真实的路径情况,可以查看编译后的classes目录下的文件结构. 想要获取资源文件流: private InputSt ...

  2. gcc 库路径里同时有相同文件名的动态库和静态库

    找不到库的处理方案 有两种方法: 一.可以把当前路径加入 /etc/ld.so.conf中然后运行ldconfig,或者以当前路径为参数运行ldconfig(要有root权限才行). 二.把当前路径加 ...

  3. Java Web项目里 classpath 具体指哪个路径

    classpath路径指什么 只知道把配置文件如:mybatis.xml.spring-web.xml.applicationContext.xml等放到src目录(就是存放代码.java文件的目录) ...

  4. java项目里classpath具体指哪儿个路径

    一.classpath路径指什么 只知道把配置文件如:mybatis.xml.spring-web.xml.applicationContext.xml等放到src目录(就是存放代码.java文件的目 ...

  5. AKKA文档2.1(java版)——什么是AKKA?

    可扩展的实时事务处理 我们相信编写并发.容错.可扩展的应用相当的困难.盖因大多数时候我们一直在使用错误的工具和错误的抽象等级.AKKA就是为了改变这一切的.我们利用角色模型提升了抽象等级,并且提供了一 ...

  6. Akka Typed系列:协议&行为

    引言 2019年11月6号LightBend公司发布了AKKA 2.6版本,带来了类型安全的actor,新的Akka Cluster底层通信设施——Artery,带来了更好的稳定性,使用Jackson ...

  7. Akka Typed 官方文档之随手记

    ️ 引言 近两年,一直在折腾用FP与OO共存的编程语言Scala,采取以函数式编程为主的方式,结合TDD和BDD的手段,采用Domain Driven Design的方法学,去构造DDDD应用(Dom ...

  8. https/相对路径,绝对路径

    1. htttps HTTPS(全称:Hyper Text Transfer Protocol over Secure Socket Layer),是以安全为目标的HTTP通道,简单讲是HTTP的安全 ...

  9. jsp--- jsp图片上传到了正确路径,但在正确路径显示不出来

    首先要说的是,路径里没有中文 图片也在正确路径 ************************************ 刷新(Refresh)一下项目

随机推荐

  1. .NET 提升教育 第一期:VIP 付费课程培训通知!

    为响应 @当年在远方 同学的建议,在年前尝试进行一次付费的VIP培训. 培训的课件:点击下载培训周期:10个课程左右,每晚1个半小时培训价格:1000元/人.报名方式:有意向的请加QQ群:路过秋天.N ...

  2. Dapper where Id in的解决方案

    简单记一下,一会出去有点事情~ 我们一般写sql都是==>update NoteInfo set NDataStatus=@NDataStatus where NId in (@NIds) Da ...

  3. JavaScript String对象

    本编主要介绍String 字符串对象. 目录 1. 介绍:阐述 String 对象的说明以及定义方式. 2. 实例属性:介绍 String 对象的实例属性: length. 3. 实例方法:介绍 St ...

  4. 【原】AFNetworking源码阅读(五)

    [原]AFNetworking源码阅读(五) 本文转载请注明出处 —— polobymulberry-博客园 1. 前言 上一篇中提及到了Multipart Request的构建方法- [AFHTTP ...

  5. ASP.NET Core应用针对静态文件请求的处理[3]: StaticFileMiddleware中间件如何处理针对文件请求

    我们通过<以Web的形式发布静态文件>和<条件请求与区间请求>中的实例演示,以及上面针对条件请求和区间请求的介绍,从提供的功能和特性的角度对这个名为StaticFileMidd ...

  6. 用scikit-learn学习DBSCAN聚类

    在DBSCAN密度聚类算法中,我们对DBSCAN聚类算法的原理做了总结,本文就对如何用scikit-learn来学习DBSCAN聚类做一个总结,重点讲述参数的意义和需要调参的参数. 1. scikit ...

  7. scala练习题1 基础知识

    1, 在scala REPL中输入3. 然后按下tab键,有哪些方法可以被调用? 24个方法可以被调用, 8个基本类型: 基本的操作符, 等:     2,在scala REPL中,计算3的平方根,然 ...

  8. mono for android学习过程系列教程(5)

    这一讲主要需要了解的安卓UI元素是Spinner.这个元素类似我们 winform和webform里面的下拉选项. 首先我们先建立一个新的项目,命名为SpinnerExample. 然后在Layout ...

  9. ubuntu15 coreclr

    看了很多文章心里痒痒,也下载个ubuntu想发布个asp.net5试试,自然是下载的最新版本15.结果涉及dnu restore,dnx...什么的都没反应,切换为mono就正常,奇怪了,按说core ...

  10. Mac-OSX的Python3.5虚拟环境下安装Opencv

    Mac-OSX的Python3.5虚拟环境下安装Opencv 1   关键词 关键词:Mac,OSX,Python3.5,Virtualenv,Opencv 2   概述 本文是一篇 环境搭建 的基础 ...