1、确定回调模块名

2、编写接口函数

3、在回调模块里编写六个必需的回调函数

1、确定回调模块名

my_bank

2、编写接口方法

start() 打开银行

stop() 关闭银行

new_account(Who) 创建一个新账户

deposit(Who,Amount) 把钱存入银行

withdraw(Who,Amount) 把钱取出来(如果有结余的话)。

gen_server:start_link({local,Name},Mod,…) 会启动一个本地服务器。如果第一个参数是原子global,它就会启动一个能被Erlang节点集群访问的全局服务器。start_link的第二参数是Mod,也就是回调模块名。宏?MODULE会展开成模块名my_bank。

gen_server:call(?MODULE,Term)被用来对服务器进行远程过程调用。

3、编写回调方法

回调模块必需导出六个回调方法:

init/1,handle_call/3,handle_cast/2,handle_info/2,terminate/2,code_change/3.

	其中的handle_call/3函数最为最重要

这个模块包含了一套简单的框架,可以填充它们来制作服务器。如果忘记定义合适的回调函数,编译器就会根据关键字-behaviour来生成警告或错误消息。start_link()函数里的服务器名(宏?SERVER)需要进行定义,因为它默认是没有定义的。

这段代码中的Reply会作为远程过程调用的返回值发挥客户端。

State 只是一个代表服务器全局状态的变量,它会在服务器里到处传递。在上面的银行模块中,这个状态不会发生变化,只是一个ETS表的索引,属于常量。

启动服务器
gen_server:start_link(Name,Mod,InitArgs,Otps) 这个调用是所有事务的起点。 它会创建一个名为Name的通用服务器,回调模块是Mod,Otps则控制通用服务器的行为。在这里可以指定消息记录、函数调试和其他行为。通用服务器通过调用Mod:init(InitArgs)启动。 初始化服务器 init(Args) -> {ok,State}|
{ok,State,Timeout}|
ignore|
{stop,Reson} init([]) ->
{ok,#state{}}. 如果返回{ok,State},就说明我们成功启动了服务器,初始状态是State。 调用服务器
要调用服务器,客户端程序需要执行gen_server:call(Name,Request).他最终调用的回调模块里的handle_call/3. handle_call(Request,From,State) ->
{reply,Reply,State}|
{reply,Reply,State,Timeout}|
{noreply,State}|
{noreply,State,Timeout}|
{stop,Reason,Reply,State}|
{stop,Reason,State} Request(gen_server:call/2的第二个参数)作为handle_call/3的第一个参数重新出现。From是发送请求的客户端进程PID,State则是客户端的当前状态。 通常会返回{reply,Reply,NewState},Reply会返回客户端,成为gen_server:call的返回值。NewState则是服务器接下来的状态。 noreply会让服务器继续工作,但客户端会等待一个回复,所以服务器必需把回复的任务委派给其他进程。用适当的stop会停止服务器。 gen_server:call和handle_call之间的交互,作用是实现远程过程调用。 调用和播发
gen_server:cast(Name,Msg)则实现了一个播发(cast),也就是没有返回值得调用(实际上就是一个消息,但习惯上称它为播发来与远程过程调用相区分)。
handle_cast(Msg,State) ->
{noreply,State}|
{noreply,State,Timeout}|
{stop,Reason,State} 发给服务器的自发性消息
回调函数handle_info(Info,State)被用来处理发给服务器的自发性消息。
自发性消息是一切未经显示调用gen_server:call或gen_server:cast而到达服务器的消息。
例如:如果服务器连接到另一个进程并捕捉推出信号,就可能会突然收到一个预料之外的{‘EXIT’,Pid,What}消息。除此之外,系统里任何知道通用服务器PID的进程都可以向它发送消息。这样的消息在服务器里表现为info值。
handle_info(_Info,State) ->
{noreply,State}|
{noreply,State,Timeout}|
{stop,Reason,State} 后会有期,宝贝
服务器会因为许多原因而终止。某个以handle_开头的函数也许会返回一个{stop,Resason,NewState},服务器也可能崩溃并生成{‘EXIT',reason}。在所有这些情况下,无论他们是怎样发生的,都会调用terminate(Reason,NewState)。模板如下:
这个函数是在某个gen_server即将终止时调用的。
它应当是Module:init/1的逆操作,并进行必要的清理。
当他返回时,<mod>gen_server</mod>终止并生成原因Reason。 terminate(Reason,State) -> void(). 这段代码不能返回一个新状态,因为已经终止。 但是了解服务器的终止状态非常有用。可以把状态保存到磁盘,把它放入消息发送给别的进程,或者根据应用程序的意愿丢弃它。如果想让服务期过后重启,就必须编写重启函数,由terminate/2触发。 代码更改
在服务器运行时更改它的状态。这个回调函数会在系统执行软件升级时由版本处理子系统调用。 在代码更改时转换进程状态
code_change(OldVsn,State,Extra) -> {ok,NewState}

参考引用:

Erlang程序设计(第二版)

OTP: gen_server的简单应用的更多相关文章

  1. erlang OTP gen_server 图解分析

    http://www.hoterran.info/otp-gen_server-sourcecode 在阅读erlang的otp源码gen_server.erl的时候,一直想写点什么,用一种最好的方式 ...

  2. OTP gen_server

    erlang behaviour小结之gen_server OTP入门 分类: Erlang2012-08-06 18:55 867人阅读 评论(0) 收藏 举报 servererlangcallba ...

  3. 使用Erlang和Yaws开发REST式的服务

    看过那张很出名的“Apache vs. Yaws”图么?是不是在考虑你也应该使用Yaws了?这些图给人的第一印象是,Yaws在可伸缩性上具有难以置信的巨大优势,它可以扩展到80000个并行的连接,而 ...

  4. Mochiweb的设计分析

    http://blog.csdn.net/dp0304/article/details/6994435 Web服务器的基本工作大致分3步: 接收HTTP请求: 处理HTTP请求,生成响应内容: 发送响 ...

  5. Erlang OTP编程初体验——gen_server和行为模式

    http://blog.sina.com.cn/s/blog_3fe961ae0101k4p6.html 行为模式其实非常类似于面向对象语言中的接口,至少笔者是这么理解的.OTP行为模式将一些反复出现 ...

  6. Erlang 104 OTP

    笔记系列 Erlang环境和顺序编程Erlang并发编程Erlang分布式编程YawsErlang/OTP 日期              变更说明 2014-12-21 A Outline, 1 A ...

  7. Erlang/OTP设计原则(文档翻译)

    http://erlang.org/doc/design_principles/des_princ.html 图和代码皆源自以上链接中Erlang官方文档,翻译时的版本为20.1. 这个设计原则,其实 ...

  8. Erlang cowboy 处理简单的HTTP请求

    Erlang cowboy 处理简单的HTTP请求 原文出自: Handling plain HTTP requests 处理请求的最简单的方式是写一个简单的HTTP处理器.它的模型参照Erlang/ ...

  9. Erlang/OTP:基于Behaviour的回调函数

    原始链接:https://blog.zhustec.me/posts/erlang-otp-1-callback-based-on-behaviour OTP 是什么 OTP 的全称是开源电信平台 ( ...

  10. Erlang generic standard behaviours -- gen_server hibernate

    hibernate 主要用于在内存空闲时,通过整理进程的stack,回收进程的heap 来达到回收内存节省资源的效果. hibernate 可用于OTP 进程以及普通进程, hibernate 的官方 ...

随机推荐

  1. JVM相关知识学习

    JVM的垃圾回收算法是什么? 分代回收算法:然后详细阐述年轻代有哪些算法,老年代有哪些算法 垃圾收集器总结: 最初使用的是Serial + Serial Old收集垃圾,最简单,因为二者都是单线程的, ...

  2. 关于 Knex update 语句报错:Undefined binding(s) detected when compiling UPDATE

    下图是详细的报错截图,我敢保证前端传递的数据一个不漏,但还是报我没有绑定对应的字段: 官方文档的使用案例基本上都是where 子句在 update 语句之前.但,select 语句的 where 子句 ...

  3. 02#Web 实战:实现树形控件

    前言 这是一篇个人练习 Web 前端各种常见的控件.组件的实战系列文章.本篇文章将介绍个人通过 JQuery + 无序列表 + CSS 动画完成一个简易的树形控件. 最终实现的效果是: 这样结构比较复 ...

  4. 如何创建一个浏览器版的`Window11`

    如何创建一个浏览器版的Window11 我们接下来将创建一个在浏览器运行的Window11,可以先看看效果图 这是基于Windows 11 in React修改的功能,我们接下来就将使用Windows ...

  5. Reverse for 'blog_detail.html' not found.解决方法

    初学django遇到了以下问题: 查找解决方法的时候发现有以下几个原因: 1.字母打错 2.多加了空格 随后 我发现 报错的代码中多加了'.html'..删掉后就没问题了.

  6. vue - 环境变量和模式

    1.在项目根目录中创建.env 或者 .env.xxx 的文件来指定环境变量 .env # 在所有的环境中被载入 .env.local # 在所有的环境中被载入,但会被 git 忽略 .env.[mo ...

  7. .NET6+WebApi+Vue 前后端分离后台管理系统(二)

    项目搭建: 这个项目使用的开发工具是:VSCode,工具的下载和安装这里就不赘述了,自行百度吧.使用的技术主要是: Vue3.Element Plus 等,Vue 项目的搭建这里也不赘述,如果不熟悉可 ...

  8. C++数据结构-结构体

    C++数据结构-结构体 学生信息 http://oj.61coding.cn/problem.php?cid=1028&pid=0 #include<bits/stdc++.h> ...

  9. Day12 面向对象

    面向对象 前提须知:Java中想要创建对象,必须要有类的存在 类和对象的关系: 依赖关系:需要根据类,创建对象 数量关系:根据一个类,可以创建出多个对象 创建Student类的对象进行使用 创建对象的 ...

  10. sping入门介绍-bean标签的属性

    bean标签的属性 1 .基础属性 <bean id="userDao" class="com.itheima.dao.impl.UserDaoImpl" ...