django-simple-sso原始workflow
- User wants to log into a Client by clicking a “Login” button. The initially requested URL can be passed using the next GET parameter.
- The Client’s Python code does a HTTP request to the Server to request a authentication token, this is called the Request Token Request.
- The Server returns a Request Token.
- The Client redirects the User to a view on the Server using the Request Token, this is the Authorization Request.
- If the user is not logged in the the Server, they are prompted to log in.
- The user is redirected to the Client including the Request Token and a Auth Token, this is the Authentication Request.
- The Client’s Python code does a HTTP request to the Server to verify the Auth Token, this is called the Auth Token Verification Request.
- If the Auth Token is valid, the Server returns a serialized Django User object.
- The Client logs the user in using the Django User recieved from the Server.
前后端分离项目使用django-simple-sso的验证过程
- 用户请求前端页面,前端页面请求get_user_info接口,session有效可以返回用户信息。
- 当无法获取用户信息时,说明client端登陆失效。调用client端登陆接口。此接口会向server端获取request-token。server端会保存此token到token表中。
- user被重定向到server端的authorize接口,参数request-token。验证server端session是否有效,
"GET /server/authorize/?token=adpvzavQValZBGCzpGJE2QpnRQxNJVlWpQJ4h0uP8d2CuK0P7tBGuBXbUuyBqQyT HTTP/1.1" 302 0
- 无效则重定向到登陆页面,登陆后再次请求authorize接口。
- 有效则重定向到client端authenticate接口。此接口会向server端请求用户信息,并且请用户信息保存在client端的auth_user表中
部分代码
因为要实现不同域名之间的跳转,所以覆盖了原代码中的get_next方法,不进行任何安全限制。
class ClientLoginView(client.LoginView):
def get_next(self):
return self.request.GET.get('next', None) # 允许跳转到外部域
class ClientAuthenticateView(client.AuthenticateView):
def get(self, request):
raw_access_token = request.GET['access_token']
access_token = URLSafeTimedSerializer(self.client.private_key).loads(raw_access_token)
user = self.client.get_user(access_token)
user.backend = self.client.backend
login(request, user)
next = self.get_next()
return HttpResponseRedirect(next)
def get_next(self):
return self.request.GET.get('next', None) # 允许跳转到外部域