Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code | Sign in
(21)

Delta Between Two Patch Sets: appengine_django/auth/__init__.py

Issue 908: [issue6] Google's Users API Integration (Closed) SVN Base: http://google-app-engine-django.googlecode.com/svn/trunk/
Left Patch Set: Doc tests Created 3 months, 3 weeks ago
Right Patch Set: mail method fixed, code style Created 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Please Sign in to add in-line comments.
Jump to:
Left: Side by side diff | Download
Right: Side by side diff | Download
LEFTRIGHT
1 # Copyright 2008 Google Inc. 1 # Copyright 2008 Google Inc.
2 # 2 #
3 # Licensed under the Apache License, Version 2.0 (the "License"); 3 # Licensed under the Apache License, Version 2.0 (the "License");
4 # you may not use this file except in compliance with the License. 4 # you may not use this file except in compliance with the License.
5 # You may obtain a copy of the License at 5 # You may obtain a copy of the License at
6 # 6 #
7 # http://www.apache.org/licenses/LICENSE-2.0 7 # http://www.apache.org/licenses/LICENSE-2.0
8 # 8 #
9 # Unless required by applicable law or agreed to in writing, software 9 # Unless required by applicable law or agreed to in writing, software
10 # distributed under the License is distributed on an "AS IS" BASIS, 10 # distributed under the License is distributed on an "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 # See the License for the specific language governing permissions and 12 # See the License for the specific language governing permissions and
13 # limitations under the License. 13 # limitations under the License.
14 14
15 """ 15 """
16 Authentication module that mimics the behavior of Django's authentication 16 Authentication module that mimics the behavior of Django's authentication
17 implementation. 17 implementation.
18 18
19 To use this authentication module in an Appengine/Django project:
20 - add 'appengine_django.auth.middleware.AuthenticationMiddleware'
21 to MIDDLEWARE_CLASSES
22 - add 'appengine_django.auth.context_processors.auth'
23 to TEMPLATE_CONTEXT_PROCESSORS
24
19 Limitations: 25 Limitations:
26 - all user manipulation methods are not available
20 - all user permissions methods are not available 27 - all user permissions methods are not available
28 - user.get_profile method not implemented
29 - db.UserProperty returns user.User instead of DjangoUser
21 """ 30 """
22 31
23 from datetime import datetime 32 from datetime import datetime
24 import urllib 33 import urllib
25 34
35 from django.core import mail
26 from django.db.models.manager import EmptyManager 36 from django.db.models.manager import EmptyManager
27 from django.http import HttpResponseRedirect 37 from django.http import HttpResponseRedirect
28 from django.template import Node 38 from django.template import Node
29 from django.utils.encoding import smart_str 39 from django.utils.encoding import smart_str
30 40
31 from google.appengine.api import datastore_types 41 from google.appengine.api import datastore_types
32 from google.appengine.api import users 42 from google.appengine.api import users
33 from google.appengine.ext.db import UserProperty
34 from google.appengine.ext.webapp import template 43 from google.appengine.ext.webapp import template
35 44
36 from appengine_django import models 45 from appengine_django import models
37 46
38 register = template.create_template_register() 47 register = template.create_template_register()
39 template.register_template_library("appengine_django.auth") 48 template.register_template_library("appengine_django.auth")
49
50
51 class CallableString(str):
52 """String subclass that returns the string if it's called as a function.
53 This class is required for the user's email attribute.
54 """
55 def __call__(self):
56 return str(self)
57
58
59 class DjangoUser(users.User):
60 """App Engine User subclass that mimics the behavior of an Django user.
61
62 This class is added to datastore_types when importing this module
63 to make it usable for db.UserProperty().
64 """
65 id = None
66 is_active = True
67 first_name = None
68 last_name = None
69 password = None
70 _groups = EmptyManager()
71 _user_permissions = EmptyManager()
72
73 def __init__(self, *args, **kw):
74 super(DjangoUser, self).__init__(*args, **kw)
75 self.email = CallableString(self._User__email)
76
77 def __unicode__(self):
78 return self.username
79
80 def __str__(self):
81 return unicode(self).encode('utf-8')
82
83 def _get_username(self):
84 return self.nickname()
85 username = property(fget=_get_username)
86
87 def _is_superuser(self):
88 return users.is_current_user_admin()
89 is_superuser = property(fget=_is_superuser)
90 is_staff = property(fget=_is_superuser)
91
92 def _default_now(self):
93 return datetime.now()
94 last_login = property(fget=_default_now)
95 date_joined = property(fget=_default_now)
96
97 def save(self):
98 raise NotImplementedError
99
100 def delete(self):
101 raise NotImplementedError
102
103 def set_password(self, raw_password):
104 raise NotImplementedError
105
106 def check_password(self, raw_password):
107 raise NotImplementedError
108
109 def set_unusable_password(self):
110 raise NotImplementedError
111
112 def has_usable_password(self):
113 raise NotImplementedError
114
115 def _get_groups(self):
116 return self._groups
117 groups = property(_get_groups)
118
119 def _get_user_permissions(self):
120 return self._user_permissions
121 user_permissions = property(_get_user_permissions)
122
123 def get_group_permissions(self):
124 return self._user_permissions
125
126 def get_all_permissions(self):
127 return self._user_permissions
128
129 def has_perm(self, perm):
130 return False
131
132 def has_perms(self, perm_list):
133 return False
134
135 def has_module_perms(self, module):
136 return False
137
138 def get_and_delete_messages(self):
139 return []
140
141 def is_anonymous(self):
142 """Always return False"""
143 return False
144
145 def is_authenticated(self):
146 """Always return True"""
147 return True
148
149 def get_absolute_url(self):
150 return "/users/%s/" % urllib.quote(smart_str(self.username))
151
152 def get_full_name(self):
153 return ""
154
155 def email_user(self, subject, message, from_email):
156 """Sends an email to this user.
157
158 According to the App Engine email API the from_email must be the
159 email address of a registered administrator for the application.
160 """
161 mail.send_mail(subject,
162 message,
163 from_email,
164 [self.email])
165
166 def get_profile(self):
167 raise NotImplementedError
168 datastore_types._PROPERTY_TYPES.append(DjangoUser)
40 169
41 170
42 def login_required(function): 171 def login_required(function):
43 """Implementation of Django's login_required decorator. 172 """Implementation of Django's login_required decorator.
44 173
45 The login redirect URL is always set to request.path 174 The login redirect URL is always set to request.path
46 """ 175 """
47 def login_required_wrapper(request, *args, **kw): 176 def login_required_wrapper(request, *args, **kw):
48 if request.user.is_authenticated(): 177 if request.user.is_authenticated():
49 return function(request, *args, **kw) 178 return function(request, *args, **kw)
50 return HttpResponseRedirect(users.create_login_url(request.path)) 179 return HttpResponseRedirect(users.create_login_url(request.path))
51 return login_required_wrapper 180 return login_required_wrapper
52 181
53 182
54 class AuthLoginUrlsNode(Node): 183 class AuthLoginUrlsNode(Node):
55 """Template node that creates an appengine login or logout URL. 184 """Template node that creates an appengine login or logout URL.
56 185
57 If create_login_url is True the appengine's login URL is rendered into 186 If create_login_url is True the appengine's login URL is rendered into
58 the template, otherwise the logout URL. 187 the template, otherwise the logout URL.
59 """ 188 """
60 def __init__(self, create_login_url, redirect): 189 def __init__(self, create_login_url, redirect):
61 self.redirect = redirect 190 self.redirect = redirect
62 self.create_login_url = create_login_url 191 self.create_login_url = create_login_url
63 192
64 def render(self, context): 193 def render(self, context):
65 if self.create_login_url: 194 if self.create_login_url:
66 return users.create_login_url(self.redirect) 195 return users.create_login_url(self.redirect)
67 else: 196 else:
68 return users.create_logout_url(self.redirect) 197 return users.create_logout_url(self.redirect)
69 198
70 199
71 def auth_login_urls(parser, token): 200 def auth_login_urls(parser, token):
72 """Template tag registered as 'auth_login_url' and 'auth_logout_url' 201 """Template tag registered as 'auth_login_url' and 'auth_logout_url'
73 when the module is imported. 202 when the module is imported.
74 203
75 Both tags take an optional argument that specifies the redirect URL and 204 Both tags take an optional argument that specifies the redirect URL and
76 defaults to '/'. 205 defaults to '/'.
77 """ 206 """
78 bits = list(token.split_contents()) 207 bits = list(token.split_contents())
79 if len(bits) == 2: 208 if len(bits) == 2:
80 redirect = bits[1] 209 redirect = bits[1]
81 else: 210 else:
82 redirect = "/" 211 redirect = "/"
83 login = bits[0] == "auth_login_url" 212 login = bits[0] == "auth_login_url"
84 return AuthLoginUrlsNode(login, redirect) 213 return AuthLoginUrlsNode(login, redirect)
85 register.tag("auth_login_url", auth_login_urls) 214 register.tag("auth_login_url", auth_login_urls)
86 register.tag("auth_logout_url", auth_login_urls) 215 register.tag("auth_logout_url", auth_login_urls)
LEFTRIGHT

Powered by Google App Engine
This is Rietveld r305