热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

erlang并发编程分布式02

分布式编程天生分布式的程序优点:性能:不同部分在不同的机器上并行运行来让程序跑得更快。可靠性:如果一台机器出了故障,可

分布式编程

天生分布式的程序

优点:


  • 性能: 不同部分在不同的机器上并行运行来让程序跑得更快。
  • 可靠性:如果一台机器出了故障,可以在另一台机器上继续。
  • 可扩展性:可以通过添加机器提升处理能力。

COOKIE 保护系统

每个节点都有一个COOKIE,如果它想与其他任何节点通信,它的COOKIE就必须和对方节点的COOKIE相同

Erlang集群的定义就是一组带有相同COOKIE的互连节点。

COOKIE从不会在网络中明文传输,它只用来对某次会话进行初始认证。

COOKIE的三种设置方法:


  • $HOME/.erlang.COOKIE 存放相同的COOKIE   chmod 400 .erlang.COOKIE 文件只能被它的所有者访问。
  • erl -setCOOKIE C (不安全,别人容易查看到)
  • erlang:set_COOKIE(node(),C) 把本地COOKIE设置成原子C

 

分布式Erlang 

高度信任,任何节点都可以在其他Erlang节点上执行任意操作。

编写一个用于分布式的程序demo

-module(kvs).
-export([start/0,store/2,lookup/1]).%% 启动进程监听收到的消息
start() -> register(kvs,spawn(fun() -> loop() end)).%% 调用rpc存入Key-Value
store(Key,Value) -> rpc({store,Key,Value}).
%% 查询存入Key-Value
lookup(Key) -> rpc({lookup,Key}).rpc(Q) ->kvs ! {self(),Q},receive{kvs,Replay} ->Replayend.loop() ->receive{From,{store,Key,Value}} ->put(Key,{ok,Value}),From ! {kvs,true},loop();{From,{lookup,Key}} ->From ! {kvs,get(Key)},loop()end.

一台电脑启动执行

kvs:start().kvs:store(weather,raining).kvs:lookup(weather).

一台电脑启动两个节点执行

%% 开启一个节点gandalf@localhost
erl -sname gandalf
kvs:start().%% 开启第二个节点bilbo@localhost
erl -sname bilbo
rpc:call(gandalf@localhost,kvs,store,[weather,fine]).
rpc:call(gandalf@localhost,kvs,lookup,[weather]).

两台服务器相互通信(同局网),需要设置相同的COOKIE 才能通信

%% 开启一个节点gandalf@doris.myerl.example.com
erl -name gandalf -setCOOKIE abc
kvs:start().%% 开启第二个节点bilbo@doris.myerl.example.com
erl -name bilbo -setCOOKIE abc
rpc:call(gandalf@doris.myerl.example.com,kvs,store,[weather,fine]).
rpc:call(gandalf@doris.myerl.example.com,kvs,lookup,[weather]).

两台服务器相互通信(外网)

erl -name ... -setCOOKIE ... -kernel inet_dist_listen_min Min\inet_dist_listen_max Max

相互调用的内置函数

rpc提供了许多远程过程调用服务。

global里的函数可以用来在分布式系统里注册名称和加锁,以及维护一个全连接网络。

%% rpc最重要的函数,它会在指定节点上执行apply(Mod,Function,Args)
call(Node,Mod,Function,Args) -> Result | {badrpc,Reason}-spec spawn(Node,Fun) -> Pid
-spec spawn(Node,Mod,Func,ArgList) -> Pid-spec spawn_link(Node,Fun) -> Pid
-spec spawn_link(Node,Mod,Func,ArgList) -> Pid%% 强制断开与某节点的连接
-spec disconnect_node(Node) -> bool | ignored-spec monitor_node(Node,Flag) -> true%% Arg不传查找本地节点名称,Arg可以是Pid、引用或者端口
-spec node(Arg) -> Node%% 查询所有与我们连接的节点
-sepc nodes() -> [Node]%% 查询节点是否活着
-spec is_alive() -> bool()

例子:远程分裂

-module(dist_demo).
-export([rpc/4],start/1).start(Node) ->spawn(Node,fun() -> loop() end).%% 发送调用指定方法消息,获取返回值
rpc(Pid,M,F,A) ->Pid ! {rpc,self(),M,F,A},receive{Pid,Response} -> Responseend.%% 监听需要调用的本地方法
loop() -> receive{rpc,Pid,M,F,A} ->Pid ! {self(),(catch apply(M,F,A))},end.

%% 开启一个gandalf节点
erl -name gandalf -setCOOKIE abc%% 开启一个bilbo节点
erl -name bilbo -setCOOKIE abc%% 通过bilbo在gandalf开启一个进程,执行指定任务
Pid = dist_demo:start('gandalf@doris.myerl.example.com').
dist_demo:rpc(Pid,erlang,node,[]).

例子:模拟文件传输

Pid = dist_demo:start('gandalf@doris,myerl.example.com').%% 获取当前文件路径
dist_demo:rpc(Pid,file,get_cwd,[]).%% 获取文件目录
dist_demo:rpc(Pid,file,list_dir,["."]).%% 获取文件具体内容
dist_demo:rpc(Pid,file,read_file,["dist_demo.erl"]).

 

基于套接字的分布式模型

不可信环境中,更安全。

lib_chan 显式控制自己的机器能分裂出哪些进程。

%% 启动一个基于$HOME/.erlang_config/lib_chan.conf的服务器
-spec start_server() -> true
%% 指定配置文件启动服务器
-spec start_server(Config) -> true%% 客户端连接上服务器,然后开始相互发消息
%% ip、端口号、服务器名、密码、传递参数
-spec connect(Host,Port,S,P,ArgsC) -> {ok,Pid} | {error,Why}

Config 配置部分内容

%% 开始监听端口号:NNNN
{port,NNNN}   %% S服务器名称、P服务器密码、模块、方法、传递参数(这个方法类似启动类)
{service,S,password,P,mfa,SomeMode,SomeFunc,SomeArgS}      

就会通过分裂SomeMod: SomeFunc(MM, ArgsC, SomeArgsS)创建一个进程,负责处理来自客户端的消息。 这里的MM是一个代理进程的PID,可以用来向客户端发送消息。参数ArgsC来自于 客户端的连接调用

例子:

配置

{port,1234}.
{service,nameServer,password,"ABXy45",mfa,mod_name_server,start_me_up,notUserd}.

connect(Host,1234,nameServer,"ABXy45",nil).   服务器会分裂mod_name_server:start_me_up(MM, nil, notUsed)MM是一个代理进程的PID,用来和客户端通信。

服务器主类

-module(mod_name_server).
-export([start_me_up/3]).start_me_up(MM,_ArgsC,_ArgS) ->loop(MM).loop(MM) ->receive{chan,MM,{store,K,V}} ->kvs:store(K,V),loop(MM);{chan,MM,{lookup,K}} ->MM ! {send,kvs:lookup(K)},loop(MM);{chan_closed,MM} ->trueend.

特点:


  • 客户端给服务器发送一条消息{send,X},它会在mod_name_server变成{chan,MM,X}
  • 连接关闭,会受到{chan_closed,MM}格式的消息
  • 服务器给客户端发送消息MM !{send,X}
  • 服务器主动关闭连接 MM !close

执行例子:

 

 


推荐阅读
  • 2012年9月12日优酷土豆校园招聘笔试题目解析与备考指南
    2012年9月12日,优酷土豆校园招聘笔试题目解析与备考指南。在选择题部分,有一道题目涉及中国人的血型分布情况,具体为A型30%、B型20%、O型40%、AB型10%。若需确保在随机选取的样本中,至少有一人为B型血的概率不低于90%,则需要选取的最少人数是多少?该问题不仅考察了概率统计的基本知识,还要求考生具备一定的逻辑推理能力。 ... [详细]
  • ARM汇编基础基于Keil创建STM32汇编程序的编写
    文章目录一、新建项目(1)工具介绍(2)创建项目:二、配置环境(1)配置芯片&#x ... [详细]
  • 在《PHP应用性能优化实战指南:从理论到实践的全面解析》一文中,作者分享了一次实际的PHP应用优化经验。文章回顾了先前进行的一次优化项目,指出即使系统运行时间较长后出现的各种问题和性能瓶颈,通过采用一些通用的优化策略仍然能够有效解决。文中不仅详细阐述了优化的具体步骤和方法,还结合实例分析了优化前后的性能对比,为读者提供了宝贵的参考和借鉴。 ... [详细]
  • 本课程详细介绍了如何使用Python Flask框架从零开始构建鱼书应用,涵盖高级编程技巧和实战项目。通过视频教学,学员将学习到Flask的高效用法,包括数据库事务处理和书籍交易模型的实现。特别感谢AI资源网提供的课程下载支持。 ... [详细]
  • 浅析python实现布隆过滤器及Redis中的缓存穿透原理_python
    本文带你了解了位图的实现,布隆过滤器的原理及Python中的使用,以及布隆过滤器如何应对Redis中的缓存穿透,相信你对布隆过滤 ... [详细]
  • [转]doc,ppt,xls文件格式转PDF格式http:blog.csdn.netlee353086articledetails7920355确实好用。需要注意的是#import ... [详细]
  • 如何在Java中使用DButils类
    这期内容当中小编将会给大家带来有关如何在Java中使用DButils类,文章内容丰富且以专业的角度为大家分析和叙述,阅读完这篇文章希望大家可以有所收获。D ... [详细]
  • 本文详细介绍了 PHP 中对象的生命周期、内存管理和魔术方法的使用,包括对象的自动销毁、析构函数的作用以及各种魔术方法的具体应用场景。 ... [详细]
  • 在《Cocos2d-x学习笔记:基础概念解析与内存管理机制深入探讨》中,详细介绍了Cocos2d-x的基础概念,并深入分析了其内存管理机制。特别是针对Boost库引入的智能指针管理方法进行了详细的讲解,例如在处理鱼的运动过程中,可以通过编写自定义函数来动态计算角度变化,利用CallFunc回调机制实现高效的游戏逻辑控制。此外,文章还探讨了如何通过智能指针优化资源管理和避免内存泄漏,为开发者提供了实用的编程技巧和最佳实践。 ... [详细]
  • 在 Axublog 1.1.0 版本的 `c_login.php` 文件中发现了一个严重的 SQL 注入漏洞。该漏洞允许攻击者通过操纵登录请求中的参数,注入恶意 SQL 代码,从而可能获取敏感信息或对数据库进行未授权操作。建议用户尽快更新到最新版本并采取相应的安全措施以防止潜在的风险。 ... [详细]
  • 本文介绍了如何在 Windows 系统上利用 Docker 构建一个包含 NGINX、PHP、MySQL、Redis 和 Elasticsearch 的集成开发环境。通过详细的步骤说明,帮助开发者快速搭建和配置这一复杂的技术栈,提升开发效率和环境一致性。 ... [详细]
  • 本文作为探讨PHP依赖注入容器系列文章的开篇,将首先通过具体示例详细阐述依赖注入的基本概念及其重要性,为后续深入解析容器的实现奠定基础。 ... [详细]
  • 在PHP的设计中,预定义了9个超级全局变量、8个魔术变量和13个魔术函数,这些变量和函数无需声明即可在脚本的任意位置使用。这些特性在PHP开发中极为常见,能够显著提升开发效率和代码的灵活性。相比之下,Java并没有类似的内置机制,但通过其他方式如上下文对象和反射机制,也可以实现类似的功能。本文将详细探讨这两种语言中这些特殊变量和函数的使用方法及其应用场景。 ... [详细]
  • 开发心得:深入探讨Servlet、Dubbo与MyBatis中的责任链模式应用
    开发心得:深入探讨Servlet、Dubbo与MyBatis中的责任链模式应用 ... [详细]
  • HTTP协议作为互联网通信的基础,其重要性不言而喻。相比JDK自带的URLConnection,HttpClient不仅提升了易用性和灵活性,还在性能、稳定性和安全性方面进行了显著优化。本文将深入解析HttpClient的使用方法与技巧,帮助开发者更好地掌握这一强大的工具。 ... [详细]
author-avatar
焦作艾文斯
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有