Flask-login的文档讨论了如何处理"next" URL . 这个想法似乎是:
-
用户转到
/secret
-
用户重定向到登录页面(例如
/login
) -
成功登录后,用户被重定向回
/secret
我发现使用Flask-login的唯一半完整示例是https://gist.github.com/bkdinoop/6698956 . 它包含HTML模板文件,我看到我是否可以将它们重新创建为自我训练练习 .
这是 /secret
和 /login
部分的简化版本:
@app.route("/secret")
@fresh_login_required
def secret():
return render_template("secret.html")
@app.route("/login", methods=["GET", "POST"])
def login():
<...login-checking code omitted...>
if user_is_logged_in:
flash("Logged in!")
return redirect(request.args.get("next") or url_for("index"))
else:
flash("Sorry, but you could not log in.")
return render_template("login.html")
这里是 login.html
:
<form name="loginform" action="{{ url_for('login') }}" method="POST">
Username: <input type="text" name="username" size="30" />
Password: <input type="password" name="password" size="30" />
<input type="submit" value="Login" />
现在,当用户访问 /secret
时,他被重定向到 /login?next=%2Fsecret
. 到目前为止,非常好 - "next"参数在查询字符串中 .
但是,当用户提交登录表单时,他将被重定向回索引页面,而不是返回到 /secret
URL .
我猜测原因是因为传入URL上的“next”参数没有合并到登录表单中,因此在处理表单时不会作为变量传递 . 但是正确的方法是什么解决这个?
一个解决方案似乎有效 - 更改 <form>
标签
<form name="loginform" action="{{ url_for('login') }}" method="POST">
至:
<form name="loginform" method="POST">
删除"action"属性后,浏览器(至少Windows上的Firefox 45)会自动使用当前URL,从而继承 ?next=%2Fsecret
查询字符串,该字符串成功将其发送到表单处理处理程序 .
但是省略了“action”表单属性并让浏览器在正确的解决方案中填充它?它适用于所有浏览器和平台吗?
或者Flask或Flask-login是否打算以不同的方式处理?
2 回答
如果您需要在表单中指定不同的操作属性,则无论如何都可以建议将 endpoints 而不是url放入url参数,因为它更容易验证 . 在这里工作's some code from the application I',也许这可以帮到你 .
覆盖Flask-Login的未授权处理程序,以使用 endpoints 而不是下一个参数中的url:
在您自己的网址中也使用
request.endpoint
:如果存在并且有效,则在下一个参数中重定向到 endpoints ,否则重定向到回退 .
@timakro提供了一个简洁的解决方案 . 如果要处理动态链接,例如
然后使用url_for(request.endpoint,** request.view_args),因为request.endpoint不包含动态可变信息:
以下代码应更改为: