我有2个Web2Py应用程序,让我称之为 Provider 和 Receiver 。 Provider 提供基本身份验证功能, Receiver 使用它来登录。用户已在 Provider 和 Receiver的本地数据库中创建使用这些用户凭据成功登录。但是当我在我的控制器中使用RESTful方法时,如果我使用相同的用户名通过相同的浏览器会话手动登录到 Provider ,则jQuery-Ajax调用只能起作用。如果我不这样做并且只从 Receiver 登录,则表示已成功登录,但未成功执行Ajax GET调用。如果我使用一个用户名登录 Reciever ,使用其他用户名登录 Provider ,则Ajax GET会提取登录到 Provider 的用户的信息。我把它作为脚本放在 Receiver 的index.html
中:
var gBaseUrl="http://127.0.0.1:8000/Provider/sites/";
$(document).ready(function(){
$.ajax({
type: "GET",
async: true,
url: gBaseUrl+"get_username",
dataType: "text",
success: function(data){
$('#ContentView').append('<p> succeeded '+data+'</p>');
}
failure: function(data){
$('#ContentView').append('<p> failed '+data+'</p>');
}
});
});
如果我未在本地登录 Provider ,则不会向ContentView添加任何内容。这就是 Provider 的db.py
的样子:
## configure auth policy
auth.settings.registration_requires_verification = True
auth.settings.registration_requires_approval = True
auth.settings.reset_password_requires_verification = True
auth.settings.allow_basic_login = True
auth.settings.controller = 'default'
auth.settings.hmac_key = None
auth.settings.mailer = None
auth.settings.login_after_registration = False
要实现基本身份验证,提供商的default.py
具有以下功能:
def basic_auth():
"""
checks if the user is logged in and returns True/False.
if so user is in auth.user as well as in session.auth.user
"""
auth.basic()
if auth.user:
print("login success!")
print(auth.user.username, " is logging in!")
session.forget()
return True
else:
print("login failed!")
return False
然后返回用户名,在 Provider 的site
控制器中,我有:
@request.restful()
@auth.requires_login()
def get_username():
def GET():
return str(auth.user.username)
return locals()
ContentView只是我在div
中的空index.html
。
我还在requires
中稍微修改了gluon/tools.py
装饰器的实现:
if current.request.ajax:
raise HTTP(401)
...
elif self.settings.allow_basic_login_only or \
basic_accepted or current.request.is_restful:
raise HTTP(401, **{'WWW-Authenticate': 'Basic realm="My Realm"'})
...
答案 0 :(得分:1)
如果要通过基本身份验证登录,则需要在请求的HTTP头中提供登录凭据,而Ajax代码不会这样做。无论如何,更好的选择可能是使用内置的Central Authentication Service功能。由于您是从浏览器发出Ajax请求,因此会话cookie将随请求一起发送,因此没有理由将自己限制为基本身份验证。
更新:如果您需要使用基本身份验证,请注意jQuery .ajax()
方法需要username
和password
个参数。它还允许您直接设置标题。您还可以让服务器发送401响应并让浏览器处理凭据提示,但这不是最好的用户体验。
此外,如果Provider应用程序将在其他域上运行,请记住浏览器对Ajax请求强制same origin policy。在这种情况下,您需要实施JSONP或CORS。