1. WSGI Server <-----> WSGI Middleware<-----> WSGI Application 

1.1 WSGI Server

  wsgi server可以理解为一个符合wsgi规范的web server,接收request请求,封装一系列环境变量,按照wsgi规范调用注册的wsgi app,最后将response返回给客户端。

1.2 WSGI Application

wsgi application就是一个普通的callable对象,当有请求到来时,wsgi server会调用这个wsgi application。

   这个对象接收两个参数,通常为environ,start_response。

   environ可以理解为环境变量,跟一次请求相关的所有信息都保存在了这个环境变量中,包括服务器信息,客户端信息,请求信息。

   start_response是一个callback函数,wsgi application通过调用start_response,将response headers/status 返回给wsgi server。

   此外这个wsgi application会return一个iterator对象 ,这个iterator就是response body。

1.3 WSGI Middleware

  中间件是为了使应用程序拥有额外的行为而存在的。如果你不能随意决定是否将它放到程序的前面,它就不再是中间件了。而是程序的一部分。

  比如:URL dispatch功能,权限判断。

1.4 WSGI模型示例
 
from wsgiref.simple_server import make_server

URL_PATTERNS= (
('hi/','say_hi'),
('hello/','say_hello'),
) class Dispatcher(object): def _match(self,path):
path = path.split('/')[1]
for url,app in URL_PATTERNS:
if path in url:
return app def __call__(self,environ, start_response):
path = environ.get('PATH_INFO','/')
app = self._match(path)
if app :
app = globals()[app]
return app(environ, start_response)
else:
start_response("404 NOT FOUND",[('Content-type', 'text/plain')])
return ["Page dose not exists!"] def say_hi(environ, start_response):
start_response("200 OK",[('Content-type', 'text/html')])
return ["kenshin say hi to you!"] def say_hello(environ, start_response):
start_response("200 OK",[('Content-type', 'text/html')])
return ["kenshin say hello to you!"] app = Dispatcher() httpd = make_server('', 8000, app)
print "Serving on port 8000..."
httpd.serve_forever()

2.WebOb

  WebOb是一个用于对WSGI Request环境进行包装,以及用于创建WSGI Response的一个包。

  WebOb把WSGI的几个参数、返回的方法都封装成了Reqeust、Response这两个对象,同时还提供了一个使用方便的Exception对象。

  Related API Link: http://docs.webob.org/en/latest/reference.html

2.1 Request

from webob import Request

req = Request.blank('/')

def wsgi_app(environ, start_response):
start_response('200 OK', [('Content-type', 'text/plain')])
return ['Hi!'] print req.call_application(wsgi_app)

2.2 Response

from webob import Response
from pprint import pprint
res = Response(content_type='text/plain', charset=None)
f = res.body_file
f.write('hey')
f.write('test') # pprint(res.status)
# pprint(res.headerlist)
# pprint(res.body)

2.3 Full Sample about Request and Response

from webob import Request
from webob import Response
from webob.dec import wsgify # @wsgify
def my_app(environ, start_response):
req = Request(environ)
res = Response()
res.content_type = 'text/plain'
parts = []
for name, value in sorted(req.environ.items()):
parts.append('%s: %r' % (name, value))
res.body = 'n'.join(parts)
return res(environ, start_response) req = Request.blank('/')
res = req.get_response(my_app)
print res

2.4 Exception

  下述总结了WebOb对于HTTP返回码的类定义。

Exception
HTTPException
HTTPOk
* - :class:`HTTPOk`
* - :class:`HTTPCreated`
* - :class:`HTTPAccepted`
* - :class:`HTTPNonAuthoritativeInformation`
* - :class:`HTTPNoContent`
* - :class:`HTTPResetContent`
* - :class:`HTTPPartialContent`
HTTPRedirection
* - :class:`HTTPMultipleChoices`
* - :class:`HTTPMovedPermanently`
* - :class:`HTTPFound`
* - :class:`HTTPSeeOther`
* - :class:`HTTPNotModified`
* - :class:`HTTPUseProxy`
* - :class:`HTTPTemporaryRedirect`
HTTPError
HTTPClientError
* - :class:`HTTPBadRequest`
* - :class:`HTTPUnauthorized`
* - :class:`HTTPPaymentRequired`
* - :class:`HTTPForbidden`
* - :class:`HTTPNotFound`
* - :class:`HTTPMethodNotAllowed`
* - :class:`HTTPNotAcceptable`
* - :class:`HTTPProxyAuthenticationRequired`
* - :class:`HTTPRequestTimeout`
* - :class:`HTTPConflict`
* - :class:`HTTPGone`
* - :class:`HTTPLengthRequired`
* - :class:`HTTPPreconditionFailed`
* - :class:`HTTPRequestEntityTooLarge`
* - :class:`HTTPRequestURITooLong`
* - :class:`HTTPUnsupportedMediaType`
* - :class:`HTTPRequestRangeNotSatisfiable`
* - :class:`HTTPExpectationFailed`
* - :class:`HTTPUnprocessableEntity`
* - :class:`HTTPLocked`
* - :class:`HTTPFailedDependency`
* - :class:`HTTPPreconditionRequired`
* - :class:`HTTPTooManyRequests`
* - :class:`HTTPRequestHeaderFieldsTooLarge`
* - :class:`HTTPUnavailableForLegalReasons`
HTTPServerError
* - :class:`HTTPInternalServerError`
* - :class:`HTTPNotImplemented`
* - :class:`HTTPBadGateway`
* - :class:`HTTPServiceUnavailable`
* - :class:`HTTPGatewayTimeout`
* - :class:`HTTPVersionNotSupported`
* - :class:`HTTPNetworkAuthenticationRequired`

WSGI学习系列WebOb的更多相关文章

  1. WSGI学习系列Paste

    Paste has been under development for a while, and has lots of code in it. The code is largely decoup ...

  2. WSGI学习系列WSME

    Introduction Web Services Made Easy (WSME) simplifies the writing of REST web services by providing ...

  3. WSGI学习系列Pecan

    Pecan Introduce Pecan是一个轻量级的基于Python的Web框架, Pecan的目标并不是要成为一个“full stack”的框架, 因此Pecan本身不支持类似Session和D ...

  4. WSGI学习系列多种方式创建WebServer

    def application(environ, start_response): start_response('200 OK', [('Content-Type', 'text/html')]) ...

  5. WSGI学习系列eventlet.wsgi

    WSGI是Web Service Gateway Interface的缩写. WSGI标准在PEP(Python Enhancement Proposal)中定义并被许多框架实现,其中包括现广泛使用的 ...

  6. 分布式学习系列【dubbo入门实践】

    分布式学习系列[dubbo入门实践] dubbo架构 组成部分:provider,consumer,registry,monitor: provider,consumer注册,订阅类似于消息队列的注册 ...

  7. Entity Framework Code First学习系列目录

    Entity Framework Code First学习系列说明:开发环境为Visual Studio 2010 + Entity Framework 5.0+MS SQL Server 2012, ...

  8. WCF学习系列汇总

    最近在学习WCF,打算把一整个系列的文章都”写“出来,包括理论和实践,这里的“写”是翻译,是国外的大牛写好的,我只是搬运工外加翻译.翻译的不好,大家请指正,谢谢了.如果觉得不错的话,也可以给我点赞,这 ...

  9. EF(Entity Framework)系统学习系列

    好久没写博客了,继续开启霸屏模式,好了,废话不多说,这次准备重新系统学一下EF,一个偶然的机会找到了一个学习EF的网站(http://www.entityframeworktutorial.net/) ...

随机推荐

  1. Linux命令:sed

    简介 sed 是一种在线编辑器,它一次处理一行内容.处理时,把当前处理的行存储在临时缓冲区中,称为“模式空间”(pattern space),接着用sed命令处理缓冲区中的内容,处理完成后,把缓冲区的 ...

  2. UVa 11464 Even Parity (二进制法枚举)

    题意:给你一个n*n的01矩阵,让你把最少的0变成1,使得每个元素的上,下,左,右的元素(如果有的话)之和均为偶数. 析:最好想的的办法就是暴力,就是枚举每个数字是变还是不变,但是...时间复杂度也太 ...

  3. POP介绍与使用实践(快速上手动画)[转]

    前言 动画在APP开发过程中 大家多多少少都会接触到 而且随着ios7的扁平化风格启用之后 越来越多的APP开始尝试加入各种绚丽的动画交互效果以增加APP的用户体验(当然 还是以国外的APP居多) 有 ...

  4. Object_C初始化方法, 遍历构造器

    //版本1 //- (id)init //{ //    work = @"工作"; //    return self; //} // //    //版本2:调用父类的init ...

  5. VC++ 定制应用程序的外观

    一.在窗口创建之前改变窗口的大小和标题 要改变应用程序窗口的大小可以通过在PreCreatWindowl函数中修改CREATSTRUCT结构体变量成员的值 BOOL CMainFrame::PreCr ...

  6. Hdu1728 逃离迷宫 2017-01-17 10:56 81人阅读 评论(0) 收藏

    逃离迷宫 Time Limit : 1000/1000ms (Java/Other)   Memory Limit : 32768/32768K (Java/Other) Total Submissi ...

  7. The Activities of September

  8. windows eclipse IDE打开当前类所在文件路径

    1. 展开如下菜单: Run ---- External Tools ---- External Tools Configurations 2. 在 program 下面新建一个工具 program- ...

  9. string 和String的区别

    string 是 System.String 的别名,习惯上,我们把字符串当作对象时(有值的对象实体),我们用string.而我们把它当类时(需要字符串类中定义的方法),我们用String,比如: s ...

  10. abp + angular $http + webapi 服务

    什么是angular $http服务 http是angularjs的一个核心服务,用于读取远程服务器的数据,也就是封装了浏览器原生的xhtmlrequest对象,可以直接同外部进行通信. 怎样使用an ...