使用 Pylons validate 和authenticate_form 装饰器

发布于 2024-09-04 05:00:49 字数 1460 浏览 5 评论 0原文

validate 和authenticate_form 装饰器似乎不能很好地协同工作。这是我的模板:

<html>
<title>Test</title>
<body>
${h.secure_form('/meow/do_post')}
<input type="text" name="dummy">
<form:error name="dummy"><br>
<input type="submit" name="doit" value="Do It">
${h.end_form()}
</body>
</html>

这是控制器:

import logging

from pylons import request, response, session, tmpl_context as c, url
from pylons.controllers.util import abort, redirect

from ocust.lib.base import BaseController, render
import formencode
import formencode.validators
from formencode import htmlfill
from pylons.decorators import validate
from pylons.decorators.secure import authenticate_form

class MeowForm(formencode.Schema):
    allow_extra_fields = True
    dummy = formencode.validators.NotEmpty()

class MeowController(BaseController):

    def index(self): 
        return render('/index.mako')

    @authenticate_form
    @validate(schema=MeowForm(), form='index')
    def do_post(self):
        return 'posted OK'

如果验证失败,则 @validate 装饰器使用 htmlfill.render 重新渲染表单,但这会删除身份验证令牌,因此下次会显示 403 CSRF 检测到的错误表格已提交。

身份验证令牌似乎被剥离,因为 @authenticate_form 从 request.POST 中删除了身份验证令牌。

如果使用它来代替:

@validate(schema=MeowForm(), form='index', force_defaults=False)

它工作得很好。如果force_defaults设置为False,会发生什么不好的事情吗? htmlfill 的文档似乎建议当默认值“是表单提交的结果”时将其设置为 True。

The validate and authenticate_form decorators don't seem to play nice together. This is my template:

<html>
<title>Test</title>
<body>
${h.secure_form('/meow/do_post')}
<input type="text" name="dummy">
<form:error name="dummy"><br>
<input type="submit" name="doit" value="Do It">
${h.end_form()}
</body>
</html>

And this is the controller:

import logging

from pylons import request, response, session, tmpl_context as c, url
from pylons.controllers.util import abort, redirect

from ocust.lib.base import BaseController, render
import formencode
import formencode.validators
from formencode import htmlfill
from pylons.decorators import validate
from pylons.decorators.secure import authenticate_form

class MeowForm(formencode.Schema):
    allow_extra_fields = True
    dummy = formencode.validators.NotEmpty()

class MeowController(BaseController):

    def index(self): 
        return render('/index.mako')

    @authenticate_form
    @validate(schema=MeowForm(), form='index')
    def do_post(self):
        return 'posted OK'

If validation fails, the form is re-rendered using htmlfill.render by the @validate decorator, but this strips out the authentication token, so a 403 CSRF detected error is shown the next time the form is submitted.

The authentication token seems to be stripped because @authenticate_form deletes the authentication token from request.POST.

If this is used instead:

@validate(schema=MeowForm(), form='index', force_defaults=False)

it works fine. Is there anything bad that can happen if force_defaults is set to False? The docs for htmlfill seem to recommend it be set to True when the defaults "are the result of a form submission".

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

哥,最终变帅啦 2024-09-11 05:00:49
@validate(schema=MeowForm(), form='index')
@authenticate_form
def do_post(self):

您需要更改装饰器的顺序,验证装饰器必须是最后一个

@validate(schema=MeowForm(), form='index')
@authenticate_form
def do_post(self):

You need to change order of decorators, authenticate decorator must be last

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文