Erlang cowboy 处理简单的HTTP请求

原文出自:

Handling plain HTTP requests

处理请求的最简单的方式是写一个简单的HTTP处理器。它的模型参照Erlang/OTP的gen_server,但是做了简化,Cowboy按次序调用了3个回调函数。

Initialization

第一个回调,init/3,所有处理器都有这个函数,用于区分处理器类型,简单的HTTP处理器仅仅返回ok。

init(_Type, Req, _Opts) ->
    {ok, Req, no_state}.

这个函数接收用于处理请求的传输和协议模块的名字。可以快速处理请求。例如当采用TCP而不是SSL访问的时,下面的处理器会崩溃:

init({ssl, _}, Req, _Opts) ->
    {ok, Req, no_state}.

这个函数还可以接收与前面路由部分设置有关联的选项。如果你的处理器没有使用选项,推荐使用匹配[],这样可以快速诊断设置错误:

init(_Type, Req, []) ->
    {ok, Req, no_state}.

如果用户没有设置,你不用验证选项。如果用户设置了选项,并且存在设置错误,你可以令它崩溃。例如,要求的lang选项不存在的话,下面的代码会崩溃:

init(_Type, Req, Opts) ->
    {_, _Lang} = lists:keyfind(lang, 1, Opts),
    {ok, Req, no_state}.

如果用户不想给出出错的原因,你可以返回一个有意义的错误给用户。既然这时返回给用户了,就不用继续处理器的代码了,因此使用shutdown返回值尽早结束调用:

init(_Type, Req, Opts) ->
    case lists:keyfind(lang, 1, Opts) of
        false ->
            {ok, Req2} = cowboy_req:reply(500, [
                {<<"content-type">>, <<"text/plain">>}
            ], "Missing option 'lang'.", Req),
            {shutdown, Req2, no_state};
        _ ->
            {ok, Req, no_state}
    end.

一旦选项验证通过,我们就可以安全地使用它们。就可以传递给其余的处理器。这也是返回值元组的第3个元素state所要表达的。

我们建议在此创造一个state record。这个record会让处理器的代码更清晰,也可以更好地利用Dialyzer进行类型检查。

-record(state, {
    lang :: en | fr
    %% More fields here.
}).

init(_Type, Req, Opts) ->
    {_, Lang} = lists:keyfind(lang, 1, Opts),
    {ok, Req, #state{lang=Lang}}.

Handling the request

第2个回调函数, handle/2,是特定于简单HTTP处理器的。你将要在此处理请求的。一个什么都不做的占位的处理器如下:

handle(Req, State) ->
    {ok, Req, State}.

上面函数没有返回值。为取得请求的信息或发送响应,应该在这里使用Req对象。Req 对象自成一章。下面的处理器发送一个相当原始的响应:

handle(Req, State) ->
    {ok, Req2} = cowboy_req:reply(200, [
        {<<"content-type">>, <<"text/plain">>}
    ], <<"Hello World!">>, Req),
    {ok, Req2, State}.

Cleaning up

第3个回调函数也是最后一个, terminate/3, 一般什么留空:

terminate(_Reason, Req, State) ->
    ok.

这个回调严格用于必要的清理。不能在这个函数里发送响应。没有其他的返回值。

如果你使用进程字典,计时器,监控器或者正在接收消息,你可以使用这个函数进行清理,由于Cowboy可能为下一个活动的请求重用这个进程。

在你的处理器中,发生这些的机会是很渺茫的。通常在Erlang代码里不鼓励使用进程字典。如果想要使用计时器,监控器或接收消息,不如使用loop处理器——一种不同类型的处理器专门满足这种需要。

这个函数一直可用,所以你应该使用它。它一直被调用。

Erlang cowboy 处理简单的HTTP请求的更多相关文章

  1. Erlang cowboy 架构

    Erlang cowboy Architecture架构 Erlang cowboy参考: http://ninenines.eu/docs/en/cowboy/1.0/guide/ 本章Archit ...

  2. Erlang cowboy routing 路由

    Erlang cowboy routing 路由 本文译自: http://ninenines.eu/docs/en/cowboy/1.0/guide/routing/ Routing 默认情况下,C ...

  3. Erlang cowboy 入门参考之现代Web的发展历史

    Erlang cowboy 入门参考之现代Web发展史 原文: http://ninenines.eu/docs/en/cowboy/1.0/guide/modern_web/ 让我回顾一下web技术 ...

  4. Erlang cowboy websocket 服务器

    Erlang cowboy websocket 服务器 原文见于: http://marcelog.github.io/articles/erlang_websocket_server_cowboy_ ...

  5. Erlang cowboy 入门参考

    Erlang cowboy 入门参考 cheungmine,2014-10-28 本文翻译自: http://ninenines.eu/docs/en/cowboy/HEAD/guide/gettin ...

  6. Erlang cowboy 处理不规范的client

    Erlang cowboy 处理不规范的client Cowboy 1.0 參考 本章: Dealing with broken clients 存在很多HTTP协议的实现版本号. 很多广泛使用的cl ...

  7. Erlang cowboy 处理不规范的客户端

    Erlang cowboy 处理不规范的客户端 Cowboy 1.0 参考 本章: Dealing with broken clients 存在许多HTTP协议的实现版本.许多广泛使用的客户端,如浏览 ...

  8. Erlang cowboy http request生命周期

    Erlang cowboy http request生命周期 翻译自: http://ninenines.eu/docs/en/cowboy/1.0/guide/http_req_life/ requ ...

  9. Xamarin.Android之封装个简单的网络请求类

    一.前言 回忆到上篇 <Xamarin.Android再体验之简单的登录Demo> 做登录时,用的是GET的请求,还用的是同步, 于是现在将其简单的改写,做了个简单的封装,包含基于Http ...

随机推荐

  1. Java并发框架——AQS中断的支持

    线程的定义给我们提供了并发执行多个任务的方式,大多数情况下我们会让每个任务都自行执行结束,这样能保证事务的一致性,但是有时我们希望在任务执行中取消任务,使线程停止.在java中要让线程安全.快速.可靠 ...

  2. java中List接口的实现类 ArrayList,LinkedList,Vector 的区别 list实现类源码分析

    java面试中经常被问到list常用的类以及内部实现机制,平时开发也经常用到list集合类,因此做一个源码级别的分析和比较之间的差异. 首先看一下List接口的的继承关系: list接口继承Colle ...

  3. DVB-C系统中QAM调制与解调仿真

    本文简单记录一下自己学习<通信原理>的时候调试的一个仿真DVB-C(Cable,数字有线电视)系统中QAM调制和解调的程序.自己一直是研究"信源"方面的东西,所以对&q ...

  4. Java进阶(三十五)java int与integer的区别

    Java进阶(三十五)java int与Integer的区别 前言 int与Integer的区别从大的方面来说就是基本数据类型与其包装类的区别: int 是基本类型,直接存数值,而Integer是对象 ...

  5. ROS(indigo)一个简单灵活和可扩展的2D多机器人仿真器stdr_simulator

    官方网址:http://wiki.ros.org/stdr_simulator 教程非常详细,参考即可.这里引用一张架构图.hydro,indigo,jade,kinetic均可用. 可以使用Qt编译 ...

  6. Java-IO之FileDescriptor

    FileDescriptor是文件描述符,可以被用来表示开放文件,开放套接字等,FileDescriptor可以被看成某个文件,但无法对该文件进行操作,需要新创建FileDescriptor对应的Fi ...

  7. Swing中经常会遇到的若干问题——JTable(持续更新)

    本文是在学习中的总结,欢迎转载但请注明出处:http://blog.csdn.net/pistolove/article/details/40955213 (1)让组件在屏幕中央显示 public s ...

  8. Gradle笔记——依赖管理基础

    1. 什么是依赖管理 依赖管理可以分为两部分:一是依赖,即项目构建或运行时所需要的一些文件:二是发布,即构建完成后上传到某个地方. 1.1 依赖 大部分的项目都需要第三方库类或项目文件,这些文件就是项 ...

  9. TCP的ACK确认系列 — 延迟确认

    主要内容:TCP的延迟确认.延迟确认定时器的实现. 内核版本:3.15.2 我的博客:http://blog.csdn.net/zhangskd 延迟确认模式 发送方在发送数据包时,如果发送的数据包有 ...

  10. IT职场: 选择外企利与弊

    前几天有个同学打电话问我选择国内企业与外企的利弊,很可笑的是他是学机械的:既然和我完全不在一个行业,因此我只是说了我们IT外企的利与弊,毕竟隔行如隔山. 首先简单自我介绍一下,我所在的公司是美资500 ...