tornado-05请求分析request

WEB请求的那些事

在上节中,主要搭建了web服务,来响应客户端的请求。

这节中,我们来根据客户请求报文中的请求行(Request line) ,请求头部(Request Header),请求主体(Request body)的信息,来描述服务端如何处理。

请求行的格式:<method> <request-URL> <version>

tornado.web库

再次重申:tornado 用 web.RequestHandler 类,来处理客户请求。每一次客户发来请求,先由服务器应用APP根据路由映射,调用处理类,生成一个RequestHandler类对象。这个类对象负责处理 客户请求的请求信息,并根据类的处理方法,生成返回的响应报文。

我们这里,根据客户的请求报文三个部分,来看看 客户的请求报文 提供的信息。

处理请求方法Method--Request Line

  • 客户的请求方式在HTTP/1.1中,有八种之多。在生产环境中常用到的是get和post两种方法。

    get方法,主要用来请求数据。client端将请求的信息以URL编码的信息明文传递给服务器。

    post方法,主要用来传递数据给服务端。client端请求的信息以数据包形式传送给服务端。

    post请求,常用来提交表单的私密数据。get请求,网页中文件加载等。

  • 同一个Request-URL,可使用多个请求方法。表示 将概念相关的处理方法绑定在同一个URL中。

    比如用户信息,用get表示请求用户信息,用post表示修改用户的信息等。

    再如:Request-URL 为 http://ip:/book/book_id ,即可利用get 方法通过 book_id 得到书籍的详细信息。也可利用post方法,提交书籍的信息,从而修改书籍有详细信息。

  • 实现过程:(这里测试同一个URL绑定多个请求方法)

    #以一个请求地址的两种 请求方法为例。
    #在路由映射中添加:
    # (r"/book/(\d+)", BookInfoHandler)
    
    #添加处理类,注意这里的id来源。
    class BookInfoHandler(tornado.web.RequestHandler):
        def get(self,id):
            self.write(id);
        
        def post(self,id):
            self.write(id + "post")
            
    # 测试方法:在ubuntu中命令:
    # 测试get: 
    #curl http://192.168.128.140:8000/book/12345612
    # 测试post:
    #curl -d aaa=bbb http://192.168.128.140:8000/book/12345612
    

URL的秘密

  • URL书写风格

    • URL有两种表示风格。早期,查询字符串风格,在URL中以?表示传递的参数 ,比如在百度中搜索hello,URL的请求地址:https://www.baidu.com/s?wd=hello&ie=UTF-8
      • 后期,出现RESTFUL风格的表示方式(Representational State Transfe). 这种概念中,每一个URL 都表示一种资源,而将对资源的操作放在了请求体中。简单说来,也是一种HTTP的分层思想,将资源和操作分离开。

    查询字符串风格 :http://192.168.128.140:8000/book?id=123456

    RESTFUL风格 : http://192.168.128.140:8000/book/id/123456

    通过参数使用方法,通过路径调用方法

自定义参数 --URL和Request body

  • 在客户端的请求报文中,网站开发者的自定义参数,出现在两个地方:URL的查询字符串中,和请求报文的请求体(Request body)中。

  • get_argument 获取URL查询字符串或请求体中的参数信息。而get_arguments 获取查询字符串或请求体中的信息对应元素列表。命令使用方法:get_argument(target_name,default,strip=true) ,注意返回的信息是unicode字符串。

  • get_query_argument ,get_query_arguments。只查询URL字符串信息。

  • get_body_argument, get_body_arguments 查询请求主体中信息。

    # 常用get_argument 来获取参数。get_query_argument我在firefox测试才正常,而get_body_argument在curl下测试正常。所以建议使用get_argument.
    # get_argument和get_arguments,都接受一个参数的多个值,但get_argument只返回这个参数的最后一个值,get_arguments 返回这个参数值的列表。参考tornado源码的说明 。
    # 测试例子。添加路由:(r'/argument',ArgHandler) ,这里注意,如用上节的代码添加,需要先把根路由'/'删除或放在最下面,否则先匹配到根路由,就不再往下面匹配路由。
    class ArgHandler(tornado.web.RequestHandler):
        def get(self):
            arg1 = self.get_argument('arg1', '')
            print arg1
            self.write(arg1)
            
    # 这里再补充一个知识,便于服务器重启。
    # 正常情况下,我们每次修改这个服务器程序,都要在服务器端重新运行启动命令:python server.py
    # tornado为我们提供了一个服务器应用的参数,debug调试。开启会,如果代码有修改,它会重新加载,并且服务器出错,会在浏览器中返回错误信息。可在开发环境中使用,但不要在正式环境中使用。代码如此下:
    app = tornado.web.Application(
        handlers,
        debug = True
    )
    #注意,handlers后,添加逗号。
    
  • URL路由匹配问题

    第三节中,我们简单的说明了路由正则匹配的事情。这里我们需要注意几点:

    • 链接路由请求,在路由匹配时,只要匹配到。就不再向后匹配。
  • 如果使用正则分组,请求方法的参数要分组名保持个数相同。如果分组没命名,则按顺序传入参数。

  • 服务中处理 请求时,分组 做为参数 传递。对参数进行操作。(倒序)

    # 以第一例来说:(r"/book/(\d+)", BookInfoHandler),此处正则匹配时有一分组,分组将会以一个整体看待做为参数,传递给处理方法:BookInfoHandler。所以后面定义类的处理方法时有两个参数:get(self,id)。否则,web.RequestHandler类会报错。
    # 分组命令写法:(r"/book/(?P<bid>\d+)",BookInfoHandler),此处将分组命名为:bid.那么后面处理方法:BookInfoHandler必须将bid 作为参数,而不能用名字做为参数。如:get(self,bid)
    
    # 示例如下:
    # match with,匹配路由:(r"/book/(?P<bid>\d+)",BookInfoHandler)
    # 处理方法:倒着输出bid。
    class BookInfoHandler(tornado.web.RequestHandler):
        def get(self,bid):
            self.write(bid[::-1])
            
    # 运行服务器应用,在客户浏览器测试:http://192.168.128.140:8000/book/123456.
    # 在浏览器会显示 :654321
    

请求头部的元素--Request header

每一次客户请求报文中请求头部包含的客户端信息,我们都封装在这次请求生成的RequestHandler对象的request属性中。比如说请求头部包含的客户地址表示:self.request.remote_ip

下面列出一些比较请求信息:

* self.request.method HTTP请求方法。如:get,post,put等。
* self.request.url 请求的完整URL。 path:路径部分。query: 查询部分。
* self.request.body 请求主体。
* self.request.remote_ip , 客户端的IP地址作为字符串。如果HTTPServer.xheaders设置,将传递由负载均衡器 
在X-Real-Ip或X-Forwarded-For头中提供的真实IP地址。
* self.request.cookie  客户存储的cookie值。
* self.request.files 文件属性中使用文件上传。
* self.request.connection 长连接。
* self.request.request_time 返回此请求执行所花费的时间。
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,189评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,577评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,857评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,703评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,705评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,620评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,995评论 3 396
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,656评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,898评论 1 298
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,639评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,720评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,395评论 4 319
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,982评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,953评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,195评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,907评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,472评论 2 342

推荐阅读更多精彩内容