上一篇已经分析了rpool 的三个module , 以及简单的物理关系. 这次主要分析用户进程和 worker_pool 进程还有worker_pool_worker 进程之间的调用关系. 在开始之前, 必须先明确一点, 就是一个worker_pool_worker 进程只有在处理完一个用户进程的任务之后才能开始处理另一用户进程的任务.

worker_pool 状态管理

在上一篇已经说明, worker_pool 管理了rpool 工作进程的ready idle busy 状态,从worker_pool 的代码可以看出, 对于idle 状态和busy 状态的处理逻辑是相同的.

 handle_call({next_free, CPid}, _From, State = #state { available =
[WPid | Avail1] }) ->
worker_pool_worker:next_job_from(WPid, CPid),
{reply, WPid, State #state { available = Avail1 }, hibernate};

以上是submit 请求在 available queue 不为空时的处理逻辑.

 handle_cast({run_async, Fun}, State = #state { available = [WPid | Avail1] }) ->
worker_pool_worker:submit_async(WPid, Fun),
{noreply, State #state { available = Avail1 }, hibernate};

而以上是submit_async 请求在available queue 不为空时的处理逻辑.

 handle_cast({idle, WPid}, State = #state { available = Avail,
pending = Pending }) ->
{noreply,
case queue:out(Pending) of
{empty, _Pending} ->
State #state { available = ordsets:add_element(WPid, Avail) };
{{value, {next_free, From, CPid}}, Pending1} ->
worker_pool_worker:next_job_from(WPid, CPid),
gen_server2:reply(From, WPid),
State #state { pending = Pending1 };
{{value, {run_async, Fun}}, Pending1} ->
worker_pool_worker:submit_async(WPid, Fun),
State #state { pending = Pending1 }
end, hibernate};

当某工作进程完成对用户进程任务的处理之后, cast 给worker_pool 进程 idle 消息, worker_pool 会:

1, 判断pending 是否为空, 若空, 则将工作进程add 到available中;

2, 若pending 为 next_free, 则执行submit 请求时的处理流程;

3, 若pending 为run_async, 则执行submit_async 请求时的处理流程.

submit

用户进程在调用submit 请求时的基本流程如上图所示:

1, 用户进程call 请求 worker_pool 进程 next_free

2, worker_pool 进程 获取available 中的工作进程(PidA)并返回给用户进程

3, 用户进程call 请求PidA 工作进程submit

工作进程PidA 在ready 或 idle 时,工作进程的state 信息就会被置为undefined .

也就是在first message 到达工作进程时, 工作进程的state 信息为undefined, 那么工作进程处理上图first message 的逻辑为:

 handle_cast({next_job_from, CPid}, undefined) ->
MRef = erlang:monitor(process, CPid),
{noreply, {from, CPid, MRef}, hibernate};

也就是 monitor 用户进程UPA, 并将自身的state 重置为 {from, CPid, MRef}, 然后等待UPA 进程的submit 请求, 也就是second message .

如果在这中间, UPA 异常退出, 工作进程就会收到{'DOWN' ... } message:

 handle_info({'DOWN', MRef, process, CPid, _Reason}, {from, CPid, MRef}) ->
ok = worker_pool:idle(self()),
{noreply, undefined, hibernate};

然后将state 重置为undefined .

submit_async

用户进程在调用submit_async 请求时的基本流程如上图所示:

1, 用户进程cast 请求worker_pool 进程 run_async 参数是需要execute Fun

2, worker_pool 进程获取available 中的工作进程(PidA)并 cast submit_async 请求给PidA 参数为PidA 和 Fun

3, 然后进程在handle_cast callback 中进行处理.

 handle_cast({submit_async, Fun}, undefined) ->
run(Fun),
ok = worker_pool:idle(self()),
{noreply, undefined, hibernate};

和submit 操作相比, 工作进程在处理submit_async 请求时,不需要monitor 用户进程(UPA), 不需要将Fun execute 执行的结果返回用户进程.

总结

在Mac 下omnigraffle 真的挺好用的,就是太贵了. :(

Erlang pool management -- RabbitMQ worker_pool 2的更多相关文章

  1. Erlang pool management -- RabbitMQ worker_pool

    在RabbitMQ中,pool 是以worker_pool 的形式存在的, 其主要用途之一是对Mnesia transaction 的操作. 而在RabbitMQ 中, pool 中的worker 数 ...

  2. Erlang pool management -- Emysql pool optimize

    在上一篇关于Emysql pool (http://www.cnblogs.com/--00/p/4281938.html)的分析的最后提到 现在的emysql_conn_mgr gen_server ...

  3. Erlang pool management -- Emysql pool

    从这篇开始,这一系列主要分析在开源社区中,Erlang 相关pool 的管理和使用. 在开源社区,Emysql 是Erlang 较为受欢迎的一个MySQL 驱动. Emysql 对pool 的管理和使 ...

  4. Ubuntu16.04下,erlang安装和rabbitmq安装步骤

    文章来源: Ubuntu16.04下,erlang安装和rabbitmq安装步骤 准备工作,先下载erlang和rabbitmq的安装包,注意他们的版本,版本不对可能会导致rabbitmq无法启动,这 ...

  5. 使用kombu的producer pool 向rabbitmq瞬间发送大量消息

    kombu比pika感觉考虑得全面多了,不知道为什么用的人好像少? 生产端是 python-socket.io 的client   接受socketio 消息后, 发到rabbitmq 按时序进行处理 ...

  6. erlang pool模块。

    出自: http://blog.sina.com.cn/s/blog_96b8a154010168ti.html

  7. Erlang及Rabbitmq安装

    1. 下载erlang源代码及RabbitMQ rpm安装包      $ wget http://www.erlang.org/download/otp_src_R16B02.tar.gz $ wg ...

  8. linux centos7 erlang rabbitmq安装

    最终的安装目录为/opt/erlang 和 /opt/rabbitmq wget http://erlang.org/download/otp_src_21.0.tar.gztar zxvf otp_ ...

  9. centos6.5 以 zero-dependency Erlang from RabbitMQ 搭建环境

    rabbitmq 官方安装文档可参考:http://www.rabbitmq.com/install-rpm.html  ,由于rabbitmq 使用Erlang 开发的,运行环境需要用到Erlang ...

随机推荐

  1. [SCOI2013]火柴棍数字(背包)

    题目 做饭 由于越高位越好,我们先得出能组成的最高位 \(f[i][j][k]\)表示从低到高位第\(i\)位,手里拿着\(j\)根火柴,第\(i\)位是否为\(0\)所需要的最少火柴 我们转移仅需得 ...

  2. Linux与Android 多点触摸协议【转】

    本文转载自:http://blog.csdn.net/xubin341719/article/details/7833277 一.Linux与Android 多点触摸协议 为了使用功能强大的多点触控设 ...

  3. win10系统下载地址

    Win10正式版微软官方原版ISO系统镜像下载: Win10正式版32位简体中文版(含家庭版.专业版) 文件名: cn_windows_10_multiple_editions_x86_dvd_684 ...

  4. CentOS防火墙iptables-config的相关配置参数详解

    默认/etc/sysoncifg/iptables-config的配置内容: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 2 ...

  5. HBase-集群状态信息

    代码如下 package com.hbase.HBaseAdmin; import java.io.IOException; import java.util.Collection; import j ...

  6. Flume-NG启动过程源码分析(二)(原创)

    在上一节中讲解了——Flume-NG启动过程源码分析(一)(原创)  本节分析配置文件的解析,即PollingPropertiesFileConfigurationProvider.FileWatch ...

  7. bzoj 1087 [SCOI2005]互不侵犯King 状态压缩dp

    1087: [SCOI2005]互不侵犯King Time Limit: 10 Sec  Memory Limit: 162 MB[Submit][Status][Discuss] Descripti ...

  8. Spring Boot入门——多文件上传大小超限问题解决

    多文件上传中遇到上传文件大小的问题 org.apache.tomcat.util.http.fileupload.FileUploadBase$FileSizeLimitExceededExcepti ...

  9. redis.h

    [对象] typedef struct redisObject {     unsigned type:4;[REDIS_STRING,REDIS_LIST, HASH, SET, ZSET]     ...

  10. LINUX C的学习

    好吧看着LINUX那么多的命令好难受= =看到第三章有介绍C的编译的,先写下试试喽. 可以用gedit或者vim,老师虽然大肆吹捧vim的经典原谅用的真吉儿难受- -,一开始没安装vim用的gedit ...