《Erlang开发及应用.ppt》由会员分享,可在线阅读,更多相关《Erlang开发及应用.ppt(35页珍藏版)》请在得力文库 - 分享文档赚钱的网站上搜索。
1、Erlang开发及应用WhatisErlang?a.ERicssonLANGuage?b.函数式编程语言(FP)c.面向并发(OC),基于消息d.Ericsson创建,最初用于电信系统开发e.成熟,稳定,具有20多年历史f.适于电信系统,分布式系统,高并发服务器g.OpenSource,跨平台,GC不适于底层系统开发Historya.1980sEricsson实验室思考如何轻松开发电信系统应用b.1987年左右,Erlang浮出水面c.1989年JAM虚拟机C语言实现d.1996年OTP项目启动,融合开发经验,提供易用,强大的Erlang开发库e.1998年开源f.2007年Programmi
2、ngErlang出版g.目前版本ErlangR13B1(5.7.2)Erlang优势a.多核SMP支持b.内建分布式支持c.基于轻量进程及消息的高并发模型d.代码热替换e.开发速度快,高性能,高稳定性f.FP编程,代码灵活高效,副作用小g.丰富的分析及监控程序h.经过商业产品,长久大规模验证i.OpenSource,代码面前无秘密ErlangHelloWorld代码hello.erl:1-module(hello).2-compile(export_all).34main()-5io:format(helloworld!n).编译:$erlchello.erl运行:$erlEshellV5.7
3、.1(abortwithG)1hello:main().helloworld!okErlangHelloWorldCONT1-module(hello).声明模块名称,其必须和文件名一致.模块是Erlang项目中代码组织的基本方式.2-compile(export_all).指明编译选项,export_all用来导出所有本模块中的函数,exportedfunction是模块的接口,其他模块只能调用exportedfunction4main()-为函数头(head),包含函数名称和参数,后紧随一个-分割符5io:format(helloworld!n).为函数体(body),包含Erlang表达
4、式,这里调用io模块的format函数在默认输出中打印helloworld!在上面的运行结果中,最后有一个ok,这是io:format/1的返回值,表示打印成功,Erlang中任何函数都有返回值.Erlang语法a.DataTypes8种基本类型integer-4,-4,2#100,16#4,920828990801238101010.float-3.0,3.5e2,6.5e-2,(IEEE75464bit)atom-hello,your_name,roothost,IsAtombinary-reference-make_ref(),一个随机值fun-fun()-some_exprendpor
5、t-与外部应用进行交互的接口pid-processidentifier,用来操作process2种复合类型tuple-foo,male,28,china,list-ip,any,port,1234,binaryErlang语法CONTa.PatternMatch语言层级的模式匹配,代码更加简洁.适用于函数调用,case,receive,try表达式及=操作caseValueofNwhenis_integer(N)-N;_whenis_list(Value)-list_to_integer(Value)end变量大写字母或_开头,只能包含数字,字母,_,.如X,Name1,_Phone,_,Ho
6、st变量分为Unbound和Bound,Unbound变量只能用在模式匹配中.变量Bound后,Value就不可修改变量只能单次赋值(并发及调试考虑)N=3(ok)N=4(oops!notmatch)Erlang语法CONTa.Binary匹配b.使用binary可以轻松的实现二进制协议.c.(1)解析IP包:d.-define(IP_VERSION,4).e.-define(IP_MIN_HDR_LEN,5).DgramSize=size(Dgram),caseDgramofwhenHLen=5,4*HLen=OptsLen=4*(HLen-?IP_MIN_HDR_LEN),=RestDgr
7、am,Erlang语法CONTa.(2)自定义协议b.假如我们定义了一个协议,前2bytes(16位)标记消息体的长度,后面为消息体,最后为占用1个byte的结尾符0 xef,示意图如下:c.-length-payload-efd.|-2-|-Length-|-1-|(单位byte)e.则对应的binary匹配表达式如下:f.g.Packet=.h.casePacketofi.-j.body,PayLoad;k._-l.error,invalid_packetm.end.Erlang语法CONTa.序列化与反序列化b.Erlang中序列化非常简单c.term_to_binary/1-将任意数据
8、转化为二进制序列d.binary_to_term/1-将编码的二进制数据转化为Erlang数据e.比如:f.Obj=apple,price,2.0,origin,shandong,g.Bin=term_to_binary(Obj),h.Obj=binary_to_term(Bin)i.CouchDB中大量使用erlang的序列化相关函数,完成数据的存储与加载.Erlang语法CONTa.函数一切皆函数,每个调用都有return,函数可以作为基本数据类型.作为返回值:op_fun(+)-fun(N1,N2)-N1+N2end;op_fun(-)-fun(N1,N2)-N1-N2end.作为参数:
9、FIsEven=fun(E)-Eband2#1=:=0end.lists:filter(FIsEven,1,2,3,4,5,6).2,4,6Erlang语法CONTa.TailRecursion尾递归b.Erlang中没有for,while关键字c.可以利用递归实现循环d.在server开发中,确保使用尾递归:e.server_loop(Args)-f.someaction.g.server_loop(Args).h.使用尾递归,可以消耗很少的内存,仅仅是一个地址跳转.i.server_loop(Args)-j.someaction.k.server_loop(Args),l.other_fu
10、n().Erlang语法CONTa.发送Message!基于消息通信,NoLock!NoSharedMemroy!Pid!msg,hello,Iloveerlang向Pid(本地或远程主机)代表的进程发送消息receive1,阻塞等待任意消息:receiveMsg-okend3,等待消息,超时为5sec:receiveMsg-okafter5000-timeoutend2,实现sleep:receiveafterTime-okend4,检测是否存在消息:receiveSomeMsg-existafter0-no_existendErlang并发关于Processa.每个Process拥有一个m
11、ailbox,保存消息b.Processes之间通过发送异步Message进行交互,无共享状态c.轻量,兼有OSProcess的隔离及OSThread的高效d.Process具有自己Stack,Heap,GCe.Process可以位于Local,也可以位于RemoteMachinef.Process能够进行多种形式的管理及控制(link,monitor,exitsignal)g.Process为erlang高并发,高容错,分布式的基础h.并发Process数:default32768,max268435456Erlang并发CONTa.创建Processb.spawn(Fun),比如c.spa
12、wn(fun()-io:format(impn,self()end).d.ime.spawn(Mod,Fun,Args),比如f.spawn(io,format,impn,self().img.spawn_link,spawn_opt,spawn_monitor.h.销毁Processi.进程内部调用exit(Reason),比如exit(normal),正常退出j.进程内部发生异常导致程序退出k.其他进程调用exit(PidBeTerminate,Reason)Erlang并发CONT基于Process的httpserver框架(oneloopprocess,perconectionperp
13、rocess):setupuplistensocket,spawn(listen_process).inlisten_process:whilecanacceptnewclientconnectaccept,spawn(client_process)loopinclient_process:processprotocol,closesocket.Erlang并发CONT使用Erlang我们可以:以清晰的以清晰的风风格开格开发发高并高并发发的的应应用用我们将不在受困于:线程池的复杂死锁,竞赛的窘迫内存泄露局部问题,导致的全局崩溃与跨平台多核SMP的格格不入Erlang分布式a.ErlangNod
14、e是分布式通讯的基本单元,可以位于同一机器or多台机器,实现了原语级的节点通讯b.ErlangNode通过erl-snameNameorerlang-nameName启动,同一台机器可以启动多个Nodec.每台机器上启动ErlangNode时,都会启动一个epmd(ErlangPortMapperDaemon,port4396),用来进行Node和Machine之间的映射d.不同机器的Node之间通过Tcp连接进行Message传输(可以自定义分布式通讯实现,如通过ssh)e.global维护一个全局的Nodes网络f.spawn_link|_opt都具有分布式版本,可以再其他节点创建Proc
15、essErlang分布式CONTa.rpc模块可以在其他Node上执行操作b.slave,remsh,remoteshell等方式启动,连接ErlangNodec.Erlang中进程具有位置透明性d.通过message及receive表达式,轻松实现同步or异步,timeout等网络通信中多种机制e.Erlang本身提供tcp,udp等常规的网络编程方式f.使用Erlang内建分布式机制,可以快速开发多种应用,也可以基于socket开发各种专有应用Erlang分布式CONTErlang分布式CONT节点A2连接节点B2步骤1.NodeA2,B2启动,绑定一个本机端口,并注册到本机的epmd(d
16、efaultport4396)2.A2连接HostBepmd,请求获取B2节点的绑定端口3.HostBepmd将B2的bindport及dist协议版本等信息返回给A24.A2与B2协商,建立tcp连接,如果连接成功,维护一个tick,来定期检测B2节点5.A2与B2节点之间的消息,通过此连接进行发送ErlangOTPa.OTP(OpenTelecomPlatform),其定义了一系列项目开发中需要的模式及部署升级策略,为提高开发效率,构建高效,稳定系统提供了巨大的帮助。b.同最初时的专有电信平台应用已没有太多关系c.当前系统都是采用OTP进行开发d.Erlang中各种lib都是基于OTP开发
17、e.可以理解成某种轻量的框架,或者具体化的设计模式f.behaviours包含:application,supervisor,gen_server,gen_fsm,gen_eventg.application,release,releasehandlingh.提供应用的部署,升级,回退等实现ErlangOTPCONTBehaviours通过定义一些简单的callback模块实现特定功能.a.application定义application,实现某种功能,由其他behaviours组成b.supervisor-定义一个supervisortree,实现各种策略的任务重启机制c.gen_serve
18、r-定义一个通用的server模型,一个processloop,提供同步异步接口d.gen_fsm-实现一个状态机e.gen_event-实现一个eventmanager及eventhandler模型与其它语言的交互a.ExternalAppb.外部应用崩溃不会影响Erlang虚拟机a.Ports-通过port与外部应用交互(stdin/stdout)b.Erl_Iterface-提供c的封装,方便开发port应用c.LinkinDriverd.sharedlibrary(SOinUnix,DLLinWindows),影响Erlang虚拟机稳定性(不推荐)e.Portdirvers-提供c封装
19、,运行在erlang虚拟机内部f.CNodesg.遵照erlang的交互协议,使用c实现的一个erlangnodeh.Jinterfacei.提供一系列与Erlang进行交互的Java包Erlang代码片段a.求某个数的阶乘factorial(0)-1;factorial(N)-Nfactorial(N-1).获取远程机器的issue信息(linux)-module(issue).-compile(export_all).%startserverserver()-register(issue_server,spawn(funserver_loop/0).server_loop()-receiv
20、eFrom,get,issue-From!issue,get_issue();_-okend,server_loop().Erlang代码片段CONtget_issue()-ok,Bin=file:read_file(/etc/issue),Bin.%startclientclient(ServerNode)-true=net_kernel:connect_node(ServerNode),issue_server,ServerNode!self(),get,issue,receiveissue,Issue-io:format(serverissue:sn,Issue)after1000-io
21、:format(receiveissuetimeoutn)end.调用:$erl-snameserver(serverlitao)1issue:server().true$erl-snameclient(clientlitao)1issue:client(serverlitao).serverissue:Ubuntu9.04nl产品开发流程1.架构设计2.单台or分布式?Master-SlaveorGrid?Monitor,Failover,NetComunication,Database,Replica.3.OTPBehaviourhowmanyapplication?usesupervis
22、or,gen_server,gen_fsm,gen_event4.Coding,及单元测试用例.每个module都经过测试(eunit)5.编写系统测试框架,覆盖测试,确保系统正确(commontest)6.压力测试,分析性能瓶颈,进行优化(fprof)7.系统上线,监控功能(ganglia,nagios,monit)8.新的功能或需求,重复2-7一些工具appmon-OTPapplication监控工具cover-erlang代码覆盖测试ntop-显示Node中进程信息(unixtop)make-erlang中的make工具pman-erlang中进程管理器tv-ets和mnesia查看器f
23、prof-erlang系统性能分析common_test-erlang测试框架dialyzer-代码静态分析debugger-单步调试工具,基于(tcl/tk)学习资源Erlang官方网站ErlangChinaErlangMailistErlangPlanetErlang非业余研究ErlangDisplay开源项目ejabberd-theErlangJabber/XMPPdaemonRabbitMQ-AMQPserverCouchDB-schema-freedocumentdatabaseTsung-multi-protocoldistributedloadtestingScalaris-di
24、stributedkey-valuestoreDisco-MapReduceFrameworkMochiweb-PowerfulHttpServerTookit自己动手发起erlang开源项目!案例a.AXD301b.高并发的电信交换机c.99.9999999%可靠性(3ms故障/年)d.超过100万行Erlang代码e.软实时系统f.高容错案例a.WEBIM后台(mochiweb)b.7+百万活跃用户c.100serverd.ajax+comet(long-polling)更多应用x=t(q$mZiVfRbO7K4G0D.zw-s*o!lXhUdQaM6J3F:Czv-s&o!kXhUdQa
25、M6J2F:Bzv-s&o!kXhTdQ9M6I2F;Bzv-r&o#kXgTdP9M6I2F;Byv)r&o#kXgTdP9M5I2E;Bx=t(q%mZjVfSbO8K4H0D.zw+s*p!lYhUeQaN6J3F:Cyv)r&n#kWgTcP9L5I2E;Bx=t(q$mZiVfRbO7K4H0D.zw-s*o!lXhUdQaN6J3F:Czv-s&o!lXhUdQaM6J2F:Bzv-s&o!kXhTdQ9M6I2F:Bzv-r&o#kXhTdQ9M6I2F;Byv-r&o#kXgTdP9M5I2E;Byv)r&n#kWgTcP9M5I2E;Bx=t(q$mZiVfSbO8K4H0D
26、.zw-s*o!lXhUeQaN6J3F:Czw-s*o!lXhUdQaM6J2F:Byu)ZiVfSbO8K4H0D.zw-s*o!lYhUeQaN6J3F:Czw-s*o!lXhUdQaM6J2F:Czv-s&o!kXhTdQaM6J2F:Bzv-r&o!kXhTdQ9M6I2F;Bzv-r&o#kXgTdP9M5I2F;Byv)r&n#kWgTdP9M5I2E;Bx=t(q$mZjVfSbO8K4H0D.zw-s*p!lYhUeQaN6J3F:Cyv)r&n#kWgTcP9L5I1E;Bx=t(q$mZiVfRbO7K4G0D.zw-s*o!lXhUdQaM6J3F:Czv-s&o!kX
27、hUdQaM6J2F:Bzv-s&o!kXhTdQ9M6I2F;Bzv-s&o!lXhUdQaM6J2F:Bzv-s&o!kXhTdQ9M6I2F:Bzv-r&o#kXgTdQ9M6I2F;Byv)r&o#kXgTdP9M5I2E;Bx=u(q%mZjVfSbO8K4H0D.Aw+s*p!lYhUeQaN6J3F:Cyv)r&n#kWgTcP9L5I2E;Bx=t(q$mZiVfRbO8K4H0D.zw-s*o!lXhUeQaN6J3F:Czv-s*o!lXhUdQaM6J2F:Bzv-s&o!kXhTdQ9M6J2F:Bzv-r&o#kXhTdQ9M6I2F;B)q%nZjWfScP8L5H
28、1E.Aw+t*p$lYiVeRbN7K3G0Czv-r&o#kXhTdQ9M6I2F;Bzv-r&o#kXgTdP9M5I2E;Byv)r&n#kWgTdP9M5I2E;Bx=t(q$mZiVfSbO8K4H0D.zw-s*o!lYhUeQaN6J3F:Czw-s*o!lXhUdQaM6J2F:Czv-s&o!kXhTdQaM6J2F:Bzv-s&o!kXhTdQ9M6I2F;Bzv-r&o#kXgTdP9M6I2F;Byv)r&n#kXgTdP9M5I.Aw+t*p$lYiUeRaN7J3G0Czv-r&o#kXgTdP9M6I2F;Byv)r&n#kXgTdP9M5I2E;Bx=t(q%
29、mZjVfSbO8K4H0D.zw+s*p!lYhUeQaN6J3F:Cyv)r&n#kWgTcP9L5I1E;Bx=t(q$mZiVfRbO7K4H0D.zw-s*o!lXhUdQaN6J3F:Czv-s&o!lXhUdQaM6J2F:Bzv-s&o!kXhTdQ9M6I2F:Bzv-r&o#kXgTdQ9M6I2F;Byv-r&o#kXgTdP9M5IAw+t*p$lYiUeRbN7K3G0Czv-r&o#kXhTdQ9M6I2F;Byv-r&o#kXgTdP9M5I2E;Byv)r&n#kWgTcP9M5I2E;Bx=t(q$mZiVfSbO8K4H0D.zw-s*o!lXhUeQaN6
30、J3F:Czw-s*o!lXhUdQaM6J2F:By(q$mZiVfSbO8K4H0D.zw-s*o!lYhUeQaN6J3F:Czw-s*o!lXhUdQaM6J2F:Czv-s&o!kXhTdQaM6J2F:Bzv-r&o!kXhTdQ9M6I2F;Bx=u)q%nZjWfScO8L4H1D.Aw+t*p$hTdQaM6J2F:Bzv-s&o!kXhTdQ9M6I2F;Bzv-r&o#kXgTdP9M6I2F;Byv)r&n#kXgTdP9M5I2E;Bx=t(q%mZjVfSbO8K4H0D.zw-s*p!lYhUeQaN6J3F:Cyv)r&n#kWgTcP9L5I1E;Bx=t(q
31、$mZiVfRbO7K4H0D.zw-s*o!lXhUdQaM6J3F:Cyu)r%n#jWgScP9L5I1w+s*p!lYhUeQaN6J3F:Cyv)r&n#kWgTcP9L5I1E;Bx=t(q$mZiVfRbO7K4H0D.zw-s*o!lXhUdQaN6J3F:Czv-s&o!lXhUdQaM6J2F:Bzv-s&o!kXhTdQ9M6I2F:Bzv-r&o#kXgTdQ9M6I2F;Byv-r&o#kXgTdP9M5I2E;Bx=u(q%mZeRbN7K3G0Czv-r&o#kXhTdQ9M6I2F;Byv-r&o#kXgTdP9M5I2E;Byv)r&n#kWgTcP9M5I2E;Bx=t(q$mZiVfSbO8K4H0D.zw-s*o!lXhUeQaN6J3Fx=u(q%mZjVfSbO8K4H1D.Aw+s*p!lYhUeQaN6J3G:Cyv)r&n#kWgTcP9M5I2E;Bx=t(q$mZiVfSbO8K4H0D.zw-s*o!lYhUeQaN6J3F:Czw-s*o!lXhUdQaM6J2F:Cyu)r%n#jWgScP8L5H1E;As*o!lYhUeQaN6J3F:Czw-s*o!lXhUdQaM6J2F:Czv-s&o!kXhTdQaM6J2F:By=u)q%nZjWgScP8L
限制150内