Sanic框架(二)

Sanic

Sanic Cookies读写

写web,Cookies会经常用到。Sanic可以读写Cookies,并以key-value(键值对)的方式存储。

读取cookies

from sanic.response import text

@app.route("/cookie")
async def test(request):
    test_cookie = request.cookies.get('test')
    return text("Test cookie set to: {}".format(test_cookie))

写入cookies

from sanic.response import text

@app.route("/cookie")
async def test(request):
    response = text("There's a cookie up in this response")
    response.cookies['test'] = 'It worked!'
    response.cookies['test']['domain'] = '.test.com'
    response.cookies['test']['httponly'] = True
    return response

cookies属性

  • expire(类型:datetime):cookie在客户端的浏览器到期时间。
  • path(类型:string):cookie应用的URL子集。默认为/。
  • comment(类型:string):注释(metadata)。
  • domain(类型:string):指定cookie有效的域。 明确指定的域必须- 始终以点开头。
  • max-age(类型:数字):cookie存活的秒数
  • secure(类型:boolean):指定cookie是否只通过HTTPS发送。
  • httponly(类型:boolean):指定cookie是否能被Javascript读取。

Sanic路由

url_for方法建立路由

1.传递给url_for的关键词参数如果不是请求参数就会被加入到URL的查询字符串

url = app.url_for('user_handler', user_id=3, arg_1='one', arg_2='two')
# /users/5?arg_1=one&arg_2=two

2.有些特殊参数(_anchor, _external, _scheme, _server)传递给url_for会建立特殊的url

url = app.url_for('user_handler', user_id=5, arg_one='one', _anchor='anchor')
# /users/5?arg_one=one#anchor

url = app.url_for('user_handler', user_id=5, arg_one='one', _external=True)
# //server/users/5?arg_one=one
# _external requires you to pass an argument _server or set SERVER_NAME in app.config if not url will be same as no _external

url = app.url_for('user_handler', user_id=5, arg_one='one', _scheme='http', _external=True)
# http://server/users/5?arg_one=one
# when specifying _scheme, _external must be True

# you can pass all special arguments at once
url = app.url_for('user_handler', user_id=5, arg_one=['one', 'two'], arg_two=2, _anchor='anchor', _scheme='http', _external=True, _server='another_server:8888')
# http://another_server:8888/users/5?arg_one=one&arg_one=two&arg_two=2#anchor

3.Websocket 路由

@app.websocket('/feed')
async def feed(request, ws):
    while True:
        data = 'hello!'
        print('Sending: ' + data)
        await ws.send(data)
        data = await ws.recv()
        print('Received: ' + data)

另外,app.add_websocket_route方法可以取代装饰器:

async def feed(request, ws):
    pass

app.add_websocket_route(my_websocket_handler, '/feed')

4.strict_slashes参数
决定路由是否严格匹配末尾的斜杠;

Sanic静态文件

  • 使用app.static()方法注册静态文件
# 提供文件夹`static`里面的文件到URL `/static`的访问。
app.static('/static', './static')
# 使用`url_for`创建URL时,默认为'static'的`name`可被省略。
app.url_for('static', filename='file.txt') == '/static/file.txt'
app.url_for('static', name='static', filename='file.txt') == '/static/file.txt'

  • 对blueprint使用url_for创建的URL会加上/bp前缀。
bp = Blueprint('bp', url_prefix='/bp')
bp.static('/static', './static')
bp.static('/the_best.png', '/home/ubuntu/test.png', name='best_png')
  • 方法app.static()支持虚拟主机。可以通过传入host参数实现
from sanic import Sanic

app = Sanic(__name__)

app.static('/static', './static')
app.static('/example_static', './example_static', host='www.test.com')

  • 有时候需要Sanic提供大文件(比如,视频,图片等)的访问,可以选择使用流文件替代直接下载
from sanic import Sanic

app = Sanic(__name__)

app.static('/large_video.mp4', '/home/large_video.mp4', stream_large_files=True)
  • 当stream_large_files为True时,Sanic将会使用file_stream()替代file()来提供静态文件访问。它默认的块大小是1KB,当然你可以根据需要修改块大小。
chunk_size = 1024 * 1024 * 8 # 设置块大小为 8KB
app.static('/large_video.mp4', '/home/ubuntu/large_video.mp4', stream_large_files=chunk_size)

Sanic中间件

中间件有两种类型:request和response,都是通过@app.middleware修饰器来声明的

  • 请求中间件只接受request对象作为参数。
  • 响应中间件同时接受request和response两个对象作为参数。

提前响应

这里的“提前”是指中间件直接返回HTTPResponse对象,这时请求将停止处理并返回response。如果这发生在request类型的中间件,路由处理函数将不会被调用。返回response将阻止后续的中间件继续执行

@app.middleware('request')
async def hand_request(request):
    return text('the request1')

@app.middleware('response')
async def hand_response(request, response):
    return text('the response2')

因为中间件hand_request返回了Response对象,其后续的中间件hand_response就不会被执行。

监听器

这些中间件通过修饰器@app.listener修饰接受app和loop参数的函数来实现。

  • before_server_start
  • after_server_start
  • before_server_stop
  • after_server_stop
监听器的注册

通过register_listener方法来注册监听器。

async def setup_db(app, loop):
    app.db = await db_setup()
from my_listener import setup_db

app = Sanic()
app.register_listener(setup_db, 'before_server_start')
添加任务

后台任务在事件循环开始后执行

async def notify_server_started_after_five_seconds(app):
    await asyncio.sleep(5)
    print('Server successfully started!')

app.add_task(notify_server_started_after_five_seconds(app))
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值