`
argan
  • 浏览: 129519 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

读了一下hotwheels的代码

阅读更多

上次提到的一个挑战,公开出来的一些代码,这两天抽时间仔细读了一下,感觉对OTP了解更多了(以前没怎么接触过完整的应用),下面是一些阅读笔记和简单的分析

 

hotwheels

 

程序入口 hotwheels,启动app hotwheels,通过hotwheels.app查看入口模块,

app的入口模块hotwheels_app,作为一个application,定义了几个子进程:

* 模块hotwheels_acceptor,作为TCP Server,监听端口,接受请求,名字为hotwheels_sup

* 模块topic,作为topic管理器,hotwheels_topic_sup

* 启动自己作为一个supervisor,名字为hotwheels_transport_sup

** 定义了一个child,是transport

 

TCP Server

 

TCP Server是一个gen_server,处理掉了几乎所有的异常情况,包括打开连接过多(Too Many Open Files),这时候他会sleep一会儿,然后继续处理

 

TCP Server启动的时候开始监听端口,接受请求,当有请求进来的时候,就让Child Instance Supervisor(hotwheels_app)启动一个

Child(transport)来处理这个客户端,这段代码是:

 

handle_connection(State, Socket) ->
    {ok, Pid} = hotwheels_app:start_transport(State#state.port),
    ok = gen_tcp:controlling_process(Socket, Pid),
    %% Instruct the new handler to own the socket.
    (State#state.module):set_socket(Pid, Socket).
 

 

transport

 

transport负责处理客户端连接,为了更灵活的处理,socket都被设置成{active,once}(这个原理请见xxx的分析)。

 

transport也是一个gen_server,在启动的时候没有注册名字,因此可以启动n个实例(由application来启动)

因为socket是active once的,因此所有收到的数据都将以message的方式送来,都需要通过handle_info来处理,客户端会发三种消息来,

SUBSCRIBE,UNSUBSCRIBE,PUBLISH,处理这三种消息的时候都是先将socket重新设置成{active,once},然后将消息交给topic去处理

 

transport设置了trap_exit为true,抓住并忽略掉了处理进程(topic)失败的情况

 

如果收到ACK消息,则应答一个ACK消息,同时带上时间戳

 

如果收到不认识的binary数据,则直接将数据发送给客户端(为啥?)

 

topic

 

topic 负责是pub sub的入口,负责调度,如果要sub的topic不存则,则通知pubsub模块初始化一个新的,然后用mapper模块记录下来

真正的pub,sub操作是由pubsub模块完成的,每个topic都由一个单独的pubsub进程管理

 

mapper

 

mapper模块很简单,就是管理进程的Pid和Topic名字之间的隐射关系,同时维护双向的关系,pid2topic,topic2pid,建立两张ets表,

分别保存这两种隐射关系

 

pubsub

 

记录每个subscribors,记录的数据结构是{Pid,Ref,Sock},Pid是subscribor的pid,Ref是sub的时候monitor的reference,Sock

是该客户端连接的socket,消息进来(publish)的时候:

 

handle_cast({publish, Msg}, State) ->
    io:format("info: ~p~n", [ets:info(State#state.subs)]),
    {A, B, C} = Start = now(),
    Msg1 = <<A:32, B:32, C:32, ?MESSAGE, Msg/binary>>,
    F = fun({_, _, Sock}, _) -> erlang:port_command(Sock, Msg1) end,  %% 使用port_command来发送
    erlang:process_flag(priority, high),
    ets:foldl(F, ok, State#state.subs),  %% 遍历ets里的所有内容
    End = now(),
    erlang:process_flag(priority, normal),
    io:format("time: ~p~n", [timer:now_diff(End, Start) / 1000]),
    {noreply, State};
 

 

 

分享到:
评论
1 楼 mryufeng 2009-09-09  
温习这个代码确实能学到很多东西。

相关推荐

    HotWheels-开源

    【HotWheels-开源】项目是一个开放源代码的赛车游戏,专为单人玩家设计,同时支持与电脑对手的竞争。这款游戏提供了多种难度等级,确保不同技能水平的玩家都能找到适合自己的挑战。它利用了OpenGL和IrrLicht这两个...

    Hotwheels-Backend:风火轮的后端

    风火轮风火轮的后端用户模型ID 创建于更新于电子邮件密码角色(客户|所有者|交付)用户CRUD 创建帐号登录查看个人资料编辑个人资料验证邮件餐厅模型名称类别地址封面图片编辑餐厅删除餐厅查看分类查看餐厅类别(分页...

    Hashed and Hierarchical Timing Wheels

    Hashed and Hierarchical Timing Wheels: Data Structures for the Efficient Implementation of a Timer Facility

    PyCrypto-Wheels.zip

    在Python生态系统中,"Wheels"是一种二进制包格式,它允许开发者无需编译源代码就能快速安装Python包,显著提高了安装效率,尤其是对于那些需要C扩展的库如PyCrypto而言。 描述中提到的“包括32位和64位”,意味着...

    wheels-in-tagil

    然而,我们可以根据这个标题推测这可能与一个项目、软件或者编程相关的代码库有关,因为“wheels”在编程领域通常指的是Python生态中的预编译软件包,而“tagil”可能是项目名或者是某种特定技术的代号。由于标签为...

    设计模式之建造者模式代码示例

    ", wheels='" + wheels + '\'' + ", body='" + body + '\'' + '}'; } } // 建造者接口 public interface CarBuilder { void setEngine(String engine); void setWheels(String wheels); void setBody(String...

    ROS入门实例代码深层剖析.pdf

    通过这些文件,开发者可以了解如何实现云台的平稳运动和跟踪目标,涉及到的节点包括fake_wheels_pub.py和head_tracker.py等。 3. rb1_apps:在应用层面,这部分代码展示了如何将ROS用于各种实际场合。例如,通过...

    German Language - THERMOPLASTIC GEAR WHEELS - CYLINDRICALGEARS - CALCULATION

    German Language - THERMOPLASTIC GEAR WHEELS - CYLINDRICALGEARS - CALCULATION 行业标准

    代码.docx C++经典考试习题

    virtual void print() const { std::cout &lt;&lt; "Wheels: " &lt;&lt; wheels , Weight: " ; } }; class Car : public Vehicle { private: int passengers; public: Car(int w, int wt, int p) : Vehicle(w, wt), ...

    Lucky Wheels幸运转盘 html5游戏项目源码JS

    Lucky Wheels幸运转盘 html5游戏项目源码js Lucky Wheels 是一款 HTML5 游戏,您可以旋转轮盘来赢得分数,它有 2 个轮盘,可以提供第二次机会来增加分数或失去全部分数。 ZIP包中包含分辨率为1280×768的游戏,可以...

    hid-lg4ff.rar_wheels

    从文件“hid-lg4ff.rar_wheels”和描述“Force feedback support for Logitech Gaming Wheels”中我们可以推测,这个压缩包包含了Logitech游戏轮盘力反馈功能的源码和相关文件。开发者可以通过研究这些文件来了解力...

    Arduino风火轮速度追踪第2部分-代码-项目开发

    在本项目中,"Arduino风火轮速度追踪第2部分-代码-项目开发",我们将深入探讨如何利用Arduino和蓝牙技术来创建一个有趣的玩具——Hot Wheels终点线计时器。这个设备可以精确地测量微型赛车(如Hot Wheels)通过终点...

    22Ch Train Wheels Monitor_labview_wheels_

    《22Ch Train Wheels Monitor》是基于LabVIEW开发的一个实例,它主要关注的是列车车轮监控系统。LabVIEW,全称Laboratory Virtual Instrument Engineering Workbench(实验室虚拟仪器工程工作台),是一款由美国国家...

    Food-Wheels-Mobile-源码.rar

    《Food-Wheels-Mobile-源码》是一个针对移动设备开发的食品配送应用的源代码库。这个项目可能包含了一系列用于创建一个完整的、用户友好的、功能丰富的应用程序的所有必要组件。源码通常包括前端用户界面(UI)的...

    Python库 | psutil_wheels-5.8.0-cp310-cp310-win_amd64.whl

    - **资源使用分析**:开发者可以利用`psutil`来分析其应用程序的资源消耗,以优化代码。 - **故障诊断**:当系统出现异常时,`psutil`可以帮助排查问题,例如检查是否有进程占用过多资源。 总之,`psutil`是一个...

    FOX Wheels Car Affordability

    【FOX Wheels Car Affordability】讨论的是汽车购买的经济承受能力问题,这涉及到个人或家庭的财务规划和汽车消费市场的现状。在这个话题中,我们关注的是如何判断一辆新车是否符合消费者的经济承受范围,以及如何...

    安装pyltp显示ERROR: ERROR: Failed to build installable wheels for some pyproject.toml based projects (py

    1. 确保Python 3.6环境已安装并正常运行。 2. 安装所有必要的依赖,如numpy、wheel等。 3. 下载与Python 3.6兼容的pyltp wheel文件。 4. 使用pip安装下载的wheel...6. 验证pyltp是否安装成功,可以尝试运行示例代码。

Global site tag (gtag.js) - Google Analytics