##// END OF EJS Templates
implements #237 added password confirmation for my account and admin edit user.
marcink -
r1597:019026a8 beta
parent child Browse files
Show More
@@ -1,692 +1,694 b''
1 """ this is forms validation classes
1 """ this is forms validation classes
2 http://formencode.org/module-formencode.validators.html
2 http://formencode.org/module-formencode.validators.html
3 for list off all availible validators
3 for list off all availible validators
4
4
5 we can create our own validators
5 we can create our own validators
6
6
7 The table below outlines the options which can be used in a schema in addition to the validators themselves
7 The table below outlines the options which can be used in a schema in addition to the validators themselves
8 pre_validators [] These validators will be applied before the schema
8 pre_validators [] These validators will be applied before the schema
9 chained_validators [] These validators will be applied after the schema
9 chained_validators [] These validators will be applied after the schema
10 allow_extra_fields False If True, then it is not an error when keys that aren't associated with a validator are present
10 allow_extra_fields False If True, then it is not an error when keys that aren't associated with a validator are present
11 filter_extra_fields False If True, then keys that aren't associated with a validator are removed
11 filter_extra_fields False If True, then keys that aren't associated with a validator are removed
12 if_key_missing NoDefault If this is given, then any keys that aren't available but are expected will be replaced with this value (and then validated). This does not override a present .if_missing attribute on validators. NoDefault is a special FormEncode class to mean that no default values has been specified and therefore missing keys shouldn't take a default value.
12 if_key_missing NoDefault If this is given, then any keys that aren't available but are expected will be replaced with this value (and then validated). This does not override a present .if_missing attribute on validators. NoDefault is a special FormEncode class to mean that no default values has been specified and therefore missing keys shouldn't take a default value.
13 ignore_key_missing False If True, then missing keys will be missing in the result, if the validator doesn't have .if_missing on it already
13 ignore_key_missing False If True, then missing keys will be missing in the result, if the validator doesn't have .if_missing on it already
14
14
15
15
16 <name> = formencode.validators.<name of validator>
16 <name> = formencode.validators.<name of validator>
17 <name> must equal form name
17 <name> must equal form name
18 list=[1,2,3,4,5]
18 list=[1,2,3,4,5]
19 for SELECT use formencode.All(OneOf(list), Int())
19 for SELECT use formencode.All(OneOf(list), Int())
20
20
21 """
21 """
22 import os
22 import os
23 import re
23 import re
24 import logging
24 import logging
25 import traceback
25 import traceback
26
26
27 import formencode
27 import formencode
28 from formencode import All
28 from formencode import All
29 from formencode.validators import UnicodeString, OneOf, Int, Number, Regex, \
29 from formencode.validators import UnicodeString, OneOf, Int, Number, Regex, \
30 Email, Bool, StringBoolean, Set
30 Email, Bool, StringBoolean, Set
31
31
32 from pylons.i18n.translation import _
32 from pylons.i18n.translation import _
33 from webhelpers.pylonslib.secure_form import authentication_token
33 from webhelpers.pylonslib.secure_form import authentication_token
34
34
35 from rhodecode.config.routing import ADMIN_PREFIX
35 from rhodecode.config.routing import ADMIN_PREFIX
36 from rhodecode.lib.utils import repo_name_slug
36 from rhodecode.lib.utils import repo_name_slug
37 from rhodecode.lib.auth import authenticate, get_crypt_password
37 from rhodecode.lib.auth import authenticate, get_crypt_password
38 from rhodecode.lib.exceptions import LdapImportError
38 from rhodecode.lib.exceptions import LdapImportError
39 from rhodecode.model.user import UserModel
39 from rhodecode.model.user import UserModel
40 from rhodecode.model.repo import RepoModel
40 from rhodecode.model.repo import RepoModel
41 from rhodecode.model.db import User, UsersGroup, Group
41 from rhodecode.model.db import User, UsersGroup, Group
42 from rhodecode import BACKENDS
42 from rhodecode import BACKENDS
43
43
44 log = logging.getLogger(__name__)
44 log = logging.getLogger(__name__)
45
45
46 #this is needed to translate the messages using _() in validators
46 #this is needed to translate the messages using _() in validators
47 class State_obj(object):
47 class State_obj(object):
48 _ = staticmethod(_)
48 _ = staticmethod(_)
49
49
50 #==============================================================================
50 #==============================================================================
51 # VALIDATORS
51 # VALIDATORS
52 #==============================================================================
52 #==============================================================================
53 class ValidAuthToken(formencode.validators.FancyValidator):
53 class ValidAuthToken(formencode.validators.FancyValidator):
54 messages = {'invalid_token':_('Token mismatch')}
54 messages = {'invalid_token':_('Token mismatch')}
55
55
56 def validate_python(self, value, state):
56 def validate_python(self, value, state):
57
57
58 if value != authentication_token():
58 if value != authentication_token():
59 raise formencode.Invalid(self.message('invalid_token', state,
59 raise formencode.Invalid(self.message('invalid_token', state,
60 search_number=value), value, state)
60 search_number=value), value, state)
61
61
62 def ValidUsername(edit, old_data):
62 def ValidUsername(edit, old_data):
63 class _ValidUsername(formencode.validators.FancyValidator):
63 class _ValidUsername(formencode.validators.FancyValidator):
64
64
65 def validate_python(self, value, state):
65 def validate_python(self, value, state):
66 if value in ['default', 'new_user']:
66 if value in ['default', 'new_user']:
67 raise formencode.Invalid(_('Invalid username'), value, state)
67 raise formencode.Invalid(_('Invalid username'), value, state)
68 #check if user is unique
68 #check if user is unique
69 old_un = None
69 old_un = None
70 if edit:
70 if edit:
71 old_un = UserModel().get(old_data.get('user_id')).username
71 old_un = UserModel().get(old_data.get('user_id')).username
72
72
73 if old_un != value or not edit:
73 if old_un != value or not edit:
74 if User.get_by_username(value, case_insensitive=True):
74 if User.get_by_username(value, case_insensitive=True):
75 raise formencode.Invalid(_('This username already '
75 raise formencode.Invalid(_('This username already '
76 'exists') , value, state)
76 'exists') , value, state)
77
77
78 if re.match(r'^[a-zA-Z0-9]{1}[a-zA-Z0-9\-\_\.]+$', value) is None:
78 if re.match(r'^[a-zA-Z0-9]{1}[a-zA-Z0-9\-\_\.]+$', value) is None:
79 raise formencode.Invalid(_('Username may only contain '
79 raise formencode.Invalid(_('Username may only contain '
80 'alphanumeric characters '
80 'alphanumeric characters '
81 'underscores, periods or dashes '
81 'underscores, periods or dashes '
82 'and must begin with alphanumeric '
82 'and must begin with alphanumeric '
83 'character'), value, state)
83 'character'), value, state)
84
84
85 return _ValidUsername
85 return _ValidUsername
86
86
87
87
88 def ValidUsersGroup(edit, old_data):
88 def ValidUsersGroup(edit, old_data):
89
89
90 class _ValidUsersGroup(formencode.validators.FancyValidator):
90 class _ValidUsersGroup(formencode.validators.FancyValidator):
91
91
92 def validate_python(self, value, state):
92 def validate_python(self, value, state):
93 if value in ['default']:
93 if value in ['default']:
94 raise formencode.Invalid(_('Invalid group name'), value, state)
94 raise formencode.Invalid(_('Invalid group name'), value, state)
95 #check if group is unique
95 #check if group is unique
96 old_ugname = None
96 old_ugname = None
97 if edit:
97 if edit:
98 old_ugname = UsersGroup.get(
98 old_ugname = UsersGroup.get(
99 old_data.get('users_group_id')).users_group_name
99 old_data.get('users_group_id')).users_group_name
100
100
101 if old_ugname != value or not edit:
101 if old_ugname != value or not edit:
102 if UsersGroup.get_by_group_name(value, cache=False,
102 if UsersGroup.get_by_group_name(value, cache=False,
103 case_insensitive=True):
103 case_insensitive=True):
104 raise formencode.Invalid(_('This users group '
104 raise formencode.Invalid(_('This users group '
105 'already exists') , value,
105 'already exists') , value,
106 state)
106 state)
107
107
108
108
109 if re.match(r'^[a-zA-Z0-9]{1}[a-zA-Z0-9\-\_\.]+$', value) is None:
109 if re.match(r'^[a-zA-Z0-9]{1}[a-zA-Z0-9\-\_\.]+$', value) is None:
110 raise formencode.Invalid(_('Group name may only contain '
110 raise formencode.Invalid(_('Group name may only contain '
111 'alphanumeric characters '
111 'alphanumeric characters '
112 'underscores, periods or dashes '
112 'underscores, periods or dashes '
113 'and must begin with alphanumeric '
113 'and must begin with alphanumeric '
114 'character'), value, state)
114 'character'), value, state)
115
115
116 return _ValidUsersGroup
116 return _ValidUsersGroup
117
117
118
118
119 def ValidReposGroup(edit, old_data):
119 def ValidReposGroup(edit, old_data):
120 class _ValidReposGroup(formencode.validators.FancyValidator):
120 class _ValidReposGroup(formencode.validators.FancyValidator):
121
121
122 def validate_python(self, value, state):
122 def validate_python(self, value, state):
123 #TODO WRITE VALIDATIONS
123 #TODO WRITE VALIDATIONS
124 group_name = value.get('group_name')
124 group_name = value.get('group_name')
125 group_parent_id = int(value.get('group_parent_id') or -1)
125 group_parent_id = int(value.get('group_parent_id') or -1)
126
126
127 # slugify repo group just in case :)
127 # slugify repo group just in case :)
128 slug = repo_name_slug(group_name)
128 slug = repo_name_slug(group_name)
129
129
130 # check for parent of self
130 # check for parent of self
131 if edit and old_data['group_id'] == group_parent_id:
131 if edit and old_data['group_id'] == group_parent_id:
132 e_dict = {'group_parent_id':_('Cannot assign this group '
132 e_dict = {'group_parent_id':_('Cannot assign this group '
133 'as parent')}
133 'as parent')}
134 raise formencode.Invalid('', value, state,
134 raise formencode.Invalid('', value, state,
135 error_dict=e_dict)
135 error_dict=e_dict)
136
136
137 old_gname = None
137 old_gname = None
138 if edit:
138 if edit:
139 old_gname = Group.get(
139 old_gname = Group.get(
140 old_data.get('group_id')).group_name
140 old_data.get('group_id')).group_name
141
141
142 if old_gname != group_name or not edit:
142 if old_gname != group_name or not edit:
143 # check filesystem
143 # check filesystem
144 gr = Group.query().filter(Group.group_name == slug)\
144 gr = Group.query().filter(Group.group_name == slug)\
145 .filter(Group.group_parent_id == group_parent_id).scalar()
145 .filter(Group.group_parent_id == group_parent_id).scalar()
146
146
147 if gr:
147 if gr:
148 e_dict = {'group_name':_('This group already exists')}
148 e_dict = {'group_name':_('This group already exists')}
149 raise formencode.Invalid('', value, state,
149 raise formencode.Invalid('', value, state,
150 error_dict=e_dict)
150 error_dict=e_dict)
151
151
152 return _ValidReposGroup
152 return _ValidReposGroup
153
153
154 class ValidPassword(formencode.validators.FancyValidator):
154 class ValidPassword(formencode.validators.FancyValidator):
155
155
156 def to_python(self, value, state):
156 def to_python(self, value, state):
157
157
158 if value:
158 if value:
159
159
160 if value.get('password'):
160 if value.get('password'):
161 try:
161 try:
162 value['password'] = get_crypt_password(value['password'])
162 value['password'] = get_crypt_password(value['password'])
163 except UnicodeEncodeError:
163 except UnicodeEncodeError:
164 e_dict = {'password':_('Invalid characters in password')}
164 e_dict = {'password':_('Invalid characters in password')}
165 raise formencode.Invalid('', value, state, error_dict=e_dict)
165 raise formencode.Invalid('', value, state, error_dict=e_dict)
166
166
167 if value.get('password_confirmation'):
167 if value.get('password_confirmation'):
168 try:
168 try:
169 value['password_confirmation'] = \
169 value['password_confirmation'] = \
170 get_crypt_password(value['password_confirmation'])
170 get_crypt_password(value['password_confirmation'])
171 except UnicodeEncodeError:
171 except UnicodeEncodeError:
172 e_dict = {'password_confirmation':_('Invalid characters in password')}
172 e_dict = {'password_confirmation':_('Invalid characters in password')}
173 raise formencode.Invalid('', value, state, error_dict=e_dict)
173 raise formencode.Invalid('', value, state, error_dict=e_dict)
174
174
175 if value.get('new_password'):
175 if value.get('new_password'):
176 try:
176 try:
177 value['new_password'] = \
177 value['new_password'] = \
178 get_crypt_password(value['new_password'])
178 get_crypt_password(value['new_password'])
179 except UnicodeEncodeError:
179 except UnicodeEncodeError:
180 e_dict = {'new_password':_('Invalid characters in password')}
180 e_dict = {'new_password':_('Invalid characters in password')}
181 raise formencode.Invalid('', value, state, error_dict=e_dict)
181 raise formencode.Invalid('', value, state, error_dict=e_dict)
182
182
183 return value
183 return value
184
184
185 class ValidPasswordsMatch(formencode.validators.FancyValidator):
185 class ValidPasswordsMatch(formencode.validators.FancyValidator):
186
186
187 def validate_python(self, value, state):
187 def validate_python(self, value, state):
188
188
189 if value['password'] != value['password_confirmation']:
189 pass_val = value.get('password') or value.get('new_password')
190 if pass_val != value['password_confirmation']:
190 e_dict = {'password_confirmation':
191 e_dict = {'password_confirmation':
191 _('Passwords do not match')}
192 _('Passwords do not match')}
192 raise formencode.Invalid('', value, state, error_dict=e_dict)
193 raise formencode.Invalid('', value, state, error_dict=e_dict)
193
194
194 class ValidAuth(formencode.validators.FancyValidator):
195 class ValidAuth(formencode.validators.FancyValidator):
195 messages = {
196 messages = {
196 'invalid_password':_('invalid password'),
197 'invalid_password':_('invalid password'),
197 'invalid_login':_('invalid user name'),
198 'invalid_login':_('invalid user name'),
198 'disabled_account':_('Your account is disabled')
199 'disabled_account':_('Your account is disabled')
199 }
200 }
200
201
201 # error mapping
202 # error mapping
202 e_dict = {'username':messages['invalid_login'],
203 e_dict = {'username':messages['invalid_login'],
203 'password':messages['invalid_password']}
204 'password':messages['invalid_password']}
204 e_dict_disable = {'username':messages['disabled_account']}
205 e_dict_disable = {'username':messages['disabled_account']}
205
206
206 def validate_python(self, value, state):
207 def validate_python(self, value, state):
207 password = value['password']
208 password = value['password']
208 username = value['username']
209 username = value['username']
209 user = User.get_by_username(username)
210 user = User.get_by_username(username)
210
211
211 if authenticate(username, password):
212 if authenticate(username, password):
212 return value
213 return value
213 else:
214 else:
214 if user and user.active is False:
215 if user and user.active is False:
215 log.warning('user %s is disabled', username)
216 log.warning('user %s is disabled', username)
216 raise formencode.Invalid(self.message('disabled_account',
217 raise formencode.Invalid(self.message('disabled_account',
217 state=State_obj),
218 state=State_obj),
218 value, state,
219 value, state,
219 error_dict=self.e_dict_disable)
220 error_dict=self.e_dict_disable)
220 else:
221 else:
221 log.warning('user %s not authenticated', username)
222 log.warning('user %s not authenticated', username)
222 raise formencode.Invalid(self.message('invalid_password',
223 raise formencode.Invalid(self.message('invalid_password',
223 state=State_obj), value, state,
224 state=State_obj), value, state,
224 error_dict=self.e_dict)
225 error_dict=self.e_dict)
225
226
226 class ValidRepoUser(formencode.validators.FancyValidator):
227 class ValidRepoUser(formencode.validators.FancyValidator):
227
228
228 def to_python(self, value, state):
229 def to_python(self, value, state):
229 try:
230 try:
230 User.query().filter(User.active == True)\
231 User.query().filter(User.active == True)\
231 .filter(User.username == value).one()
232 .filter(User.username == value).one()
232 except Exception:
233 except Exception:
233 raise formencode.Invalid(_('This username is not valid'),
234 raise formencode.Invalid(_('This username is not valid'),
234 value, state)
235 value, state)
235 return value
236 return value
236
237
237 def ValidRepoName(edit, old_data):
238 def ValidRepoName(edit, old_data):
238 class _ValidRepoName(formencode.validators.FancyValidator):
239 class _ValidRepoName(formencode.validators.FancyValidator):
239 def to_python(self, value, state):
240 def to_python(self, value, state):
240
241
241 repo_name = value.get('repo_name')
242 repo_name = value.get('repo_name')
242
243
243 slug = repo_name_slug(repo_name)
244 slug = repo_name_slug(repo_name)
244 if slug in [ADMIN_PREFIX, '']:
245 if slug in [ADMIN_PREFIX, '']:
245 e_dict = {'repo_name': _('This repository name is disallowed')}
246 e_dict = {'repo_name': _('This repository name is disallowed')}
246 raise formencode.Invalid('', value, state, error_dict=e_dict)
247 raise formencode.Invalid('', value, state, error_dict=e_dict)
247
248
248
249
249 if value.get('repo_group'):
250 if value.get('repo_group'):
250 gr = Group.get(value.get('repo_group'))
251 gr = Group.get(value.get('repo_group'))
251 group_path = gr.full_path
252 group_path = gr.full_path
252 # value needs to be aware of group name in order to check
253 # value needs to be aware of group name in order to check
253 # db key This is an actual just the name to store in the
254 # db key This is an actual just the name to store in the
254 # database
255 # database
255 repo_name_full = group_path + Group.url_sep() + repo_name
256 repo_name_full = group_path + Group.url_sep() + repo_name
256
257
257 else:
258 else:
258 group_path = ''
259 group_path = ''
259 repo_name_full = repo_name
260 repo_name_full = repo_name
260
261
261
262
262 value['repo_name_full'] = repo_name_full
263 value['repo_name_full'] = repo_name_full
263 rename = old_data.get('repo_name') != repo_name_full
264 rename = old_data.get('repo_name') != repo_name_full
264 create = not edit
265 create = not edit
265 if rename or create:
266 if rename or create:
266
267
267 if group_path != '':
268 if group_path != '':
268 if RepoModel().get_by_repo_name(repo_name_full,):
269 if RepoModel().get_by_repo_name(repo_name_full,):
269 e_dict = {'repo_name':_('This repository already '
270 e_dict = {'repo_name':_('This repository already '
270 'exists in a group "%s"') %
271 'exists in a group "%s"') %
271 gr.group_name}
272 gr.group_name}
272 raise formencode.Invalid('', value, state,
273 raise formencode.Invalid('', value, state,
273 error_dict=e_dict)
274 error_dict=e_dict)
274 elif Group.get_by_group_name(repo_name_full):
275 elif Group.get_by_group_name(repo_name_full):
275 e_dict = {'repo_name':_('There is a group with this'
276 e_dict = {'repo_name':_('There is a group with this'
276 ' name already "%s"') %
277 ' name already "%s"') %
277 repo_name_full}
278 repo_name_full}
278 raise formencode.Invalid('', value, state,
279 raise formencode.Invalid('', value, state,
279 error_dict=e_dict)
280 error_dict=e_dict)
280
281
281 elif RepoModel().get_by_repo_name(repo_name_full):
282 elif RepoModel().get_by_repo_name(repo_name_full):
282 e_dict = {'repo_name':_('This repository '
283 e_dict = {'repo_name':_('This repository '
283 'already exists')}
284 'already exists')}
284 raise formencode.Invalid('', value, state,
285 raise formencode.Invalid('', value, state,
285 error_dict=e_dict)
286 error_dict=e_dict)
286
287
287 return value
288 return value
288
289
289 return _ValidRepoName
290 return _ValidRepoName
290
291
291 def ValidForkName():
292 def ValidForkName():
292 class _ValidForkName(formencode.validators.FancyValidator):
293 class _ValidForkName(formencode.validators.FancyValidator):
293 def to_python(self, value, state):
294 def to_python(self, value, state):
294
295
295 repo_name = value.get('fork_name')
296 repo_name = value.get('fork_name')
296
297
297 slug = repo_name_slug(repo_name)
298 slug = repo_name_slug(repo_name)
298 if slug in [ADMIN_PREFIX, '']:
299 if slug in [ADMIN_PREFIX, '']:
299 e_dict = {'repo_name': _('This repository name is disallowed')}
300 e_dict = {'repo_name': _('This repository name is disallowed')}
300 raise formencode.Invalid('', value, state, error_dict=e_dict)
301 raise formencode.Invalid('', value, state, error_dict=e_dict)
301
302
302 if RepoModel().get_by_repo_name(repo_name):
303 if RepoModel().get_by_repo_name(repo_name):
303 e_dict = {'fork_name':_('This repository '
304 e_dict = {'fork_name':_('This repository '
304 'already exists')}
305 'already exists')}
305 raise formencode.Invalid('', value, state,
306 raise formencode.Invalid('', value, state,
306 error_dict=e_dict)
307 error_dict=e_dict)
307 return value
308 return value
308 return _ValidForkName
309 return _ValidForkName
309
310
310
311
311 def SlugifyName():
312 def SlugifyName():
312 class _SlugifyName(formencode.validators.FancyValidator):
313 class _SlugifyName(formencode.validators.FancyValidator):
313
314
314 def to_python(self, value, state):
315 def to_python(self, value, state):
315 return repo_name_slug(value)
316 return repo_name_slug(value)
316
317
317 return _SlugifyName
318 return _SlugifyName
318
319
319 def ValidCloneUri():
320 def ValidCloneUri():
320 from mercurial.httprepo import httprepository, httpsrepository
321 from mercurial.httprepo import httprepository, httpsrepository
321 from rhodecode.lib.utils import make_ui
322 from rhodecode.lib.utils import make_ui
322
323
323 class _ValidCloneUri(formencode.validators.FancyValidator):
324 class _ValidCloneUri(formencode.validators.FancyValidator):
324
325
325 def to_python(self, value, state):
326 def to_python(self, value, state):
326 if not value:
327 if not value:
327 pass
328 pass
328 elif value.startswith('https'):
329 elif value.startswith('https'):
329 try:
330 try:
330 httpsrepository(make_ui('db'), value).capabilities
331 httpsrepository(make_ui('db'), value).capabilities
331 except Exception, e:
332 except Exception, e:
332 log.error(traceback.format_exc())
333 log.error(traceback.format_exc())
333 raise formencode.Invalid(_('invalid clone url'), value,
334 raise formencode.Invalid(_('invalid clone url'), value,
334 state)
335 state)
335 elif value.startswith('http'):
336 elif value.startswith('http'):
336 try:
337 try:
337 httprepository(make_ui('db'), value).capabilities
338 httprepository(make_ui('db'), value).capabilities
338 except Exception, e:
339 except Exception, e:
339 log.error(traceback.format_exc())
340 log.error(traceback.format_exc())
340 raise formencode.Invalid(_('invalid clone url'), value,
341 raise formencode.Invalid(_('invalid clone url'), value,
341 state)
342 state)
342 else:
343 else:
343 raise formencode.Invalid(_('Invalid clone url, provide a '
344 raise formencode.Invalid(_('Invalid clone url, provide a '
344 'valid clone http\s url'), value,
345 'valid clone http\s url'), value,
345 state)
346 state)
346 return value
347 return value
347
348
348 return _ValidCloneUri
349 return _ValidCloneUri
349
350
350 def ValidForkType(old_data):
351 def ValidForkType(old_data):
351 class _ValidForkType(formencode.validators.FancyValidator):
352 class _ValidForkType(formencode.validators.FancyValidator):
352
353
353 def to_python(self, value, state):
354 def to_python(self, value, state):
354 if old_data['repo_type'] != value:
355 if old_data['repo_type'] != value:
355 raise formencode.Invalid(_('Fork have to be the same '
356 raise formencode.Invalid(_('Fork have to be the same '
356 'type as original'), value, state)
357 'type as original'), value, state)
357
358
358 return value
359 return value
359 return _ValidForkType
360 return _ValidForkType
360
361
361 class ValidPerms(formencode.validators.FancyValidator):
362 class ValidPerms(formencode.validators.FancyValidator):
362 messages = {'perm_new_member_name':_('This username or users group name'
363 messages = {'perm_new_member_name':_('This username or users group name'
363 ' is not valid')}
364 ' is not valid')}
364
365
365 def to_python(self, value, state):
366 def to_python(self, value, state):
366 perms_update = []
367 perms_update = []
367 perms_new = []
368 perms_new = []
368 #build a list of permission to update and new permission to create
369 #build a list of permission to update and new permission to create
369 for k, v in value.items():
370 for k, v in value.items():
370 #means new added member to permissions
371 #means new added member to permissions
371 if k.startswith('perm_new_member'):
372 if k.startswith('perm_new_member'):
372 new_perm = value.get('perm_new_member', False)
373 new_perm = value.get('perm_new_member', False)
373 new_member = value.get('perm_new_member_name', False)
374 new_member = value.get('perm_new_member_name', False)
374 new_type = value.get('perm_new_member_type')
375 new_type = value.get('perm_new_member_type')
375
376
376 if new_member and new_perm:
377 if new_member and new_perm:
377 if (new_member, new_perm, new_type) not in perms_new:
378 if (new_member, new_perm, new_type) not in perms_new:
378 perms_new.append((new_member, new_perm, new_type))
379 perms_new.append((new_member, new_perm, new_type))
379 elif k.startswith('u_perm_') or k.startswith('g_perm_'):
380 elif k.startswith('u_perm_') or k.startswith('g_perm_'):
380 member = k[7:]
381 member = k[7:]
381 t = {'u':'user',
382 t = {'u':'user',
382 'g':'users_group'}[k[0]]
383 'g':'users_group'}[k[0]]
383 if member == 'default':
384 if member == 'default':
384 if value['private']:
385 if value['private']:
385 #set none for default when updating to private repo
386 #set none for default when updating to private repo
386 v = 'repository.none'
387 v = 'repository.none'
387 perms_update.append((member, v, t))
388 perms_update.append((member, v, t))
388
389
389 value['perms_updates'] = perms_update
390 value['perms_updates'] = perms_update
390 value['perms_new'] = perms_new
391 value['perms_new'] = perms_new
391
392
392 #update permissions
393 #update permissions
393 for k, v, t in perms_new:
394 for k, v, t in perms_new:
394 try:
395 try:
395 if t is 'user':
396 if t is 'user':
396 self.user_db = User.query()\
397 self.user_db = User.query()\
397 .filter(User.active == True)\
398 .filter(User.active == True)\
398 .filter(User.username == k).one()
399 .filter(User.username == k).one()
399 if t is 'users_group':
400 if t is 'users_group':
400 self.user_db = UsersGroup.query()\
401 self.user_db = UsersGroup.query()\
401 .filter(UsersGroup.users_group_active == True)\
402 .filter(UsersGroup.users_group_active == True)\
402 .filter(UsersGroup.users_group_name == k).one()
403 .filter(UsersGroup.users_group_name == k).one()
403
404
404 except Exception:
405 except Exception:
405 msg = self.message('perm_new_member_name',
406 msg = self.message('perm_new_member_name',
406 state=State_obj)
407 state=State_obj)
407 raise formencode.Invalid(msg, value, state,
408 raise formencode.Invalid(msg, value, state,
408 error_dict={'perm_new_member_name':msg})
409 error_dict={'perm_new_member_name':msg})
409 return value
410 return value
410
411
411 class ValidSettings(formencode.validators.FancyValidator):
412 class ValidSettings(formencode.validators.FancyValidator):
412
413
413 def to_python(self, value, state):
414 def to_python(self, value, state):
414 #settings form can't edit user
415 #settings form can't edit user
415 if value.has_key('user'):
416 if value.has_key('user'):
416 del['value']['user']
417 del['value']['user']
417
418
418 return value
419 return value
419
420
420 class ValidPath(formencode.validators.FancyValidator):
421 class ValidPath(formencode.validators.FancyValidator):
421 def to_python(self, value, state):
422 def to_python(self, value, state):
422
423
423 if not os.path.isdir(value):
424 if not os.path.isdir(value):
424 msg = _('This is not a valid path')
425 msg = _('This is not a valid path')
425 raise formencode.Invalid(msg, value, state,
426 raise formencode.Invalid(msg, value, state,
426 error_dict={'paths_root_path':msg})
427 error_dict={'paths_root_path':msg})
427 return value
428 return value
428
429
429 def UniqSystemEmail(old_data):
430 def UniqSystemEmail(old_data):
430 class _UniqSystemEmail(formencode.validators.FancyValidator):
431 class _UniqSystemEmail(formencode.validators.FancyValidator):
431 def to_python(self, value, state):
432 def to_python(self, value, state):
432 value = value.lower()
433 value = value.lower()
433 if old_data.get('email') != value:
434 if old_data.get('email') != value:
434 user = User.query().filter(User.email == value).scalar()
435 user = User.query().filter(User.email == value).scalar()
435 if user:
436 if user:
436 raise formencode.Invalid(
437 raise formencode.Invalid(
437 _("This e-mail address is already taken"),
438 _("This e-mail address is already taken"),
438 value, state)
439 value, state)
439 return value
440 return value
440
441
441 return _UniqSystemEmail
442 return _UniqSystemEmail
442
443
443 class ValidSystemEmail(formencode.validators.FancyValidator):
444 class ValidSystemEmail(formencode.validators.FancyValidator):
444 def to_python(self, value, state):
445 def to_python(self, value, state):
445 value = value.lower()
446 value = value.lower()
446 user = User.query().filter(User.email == value).scalar()
447 user = User.query().filter(User.email == value).scalar()
447 if user is None:
448 if user is None:
448 raise formencode.Invalid(_("This e-mail address doesn't exist.") ,
449 raise formencode.Invalid(_("This e-mail address doesn't exist.") ,
449 value, state)
450 value, state)
450
451
451 return value
452 return value
452
453
453 class LdapLibValidator(formencode.validators.FancyValidator):
454 class LdapLibValidator(formencode.validators.FancyValidator):
454
455
455 def to_python(self, value, state):
456 def to_python(self, value, state):
456
457
457 try:
458 try:
458 import ldap
459 import ldap
459 except ImportError:
460 except ImportError:
460 raise LdapImportError
461 raise LdapImportError
461 return value
462 return value
462
463
463 class AttrLoginValidator(formencode.validators.FancyValidator):
464 class AttrLoginValidator(formencode.validators.FancyValidator):
464
465
465 def to_python(self, value, state):
466 def to_python(self, value, state):
466
467
467 if not value or not isinstance(value, (str, unicode)):
468 if not value or not isinstance(value, (str, unicode)):
468 raise formencode.Invalid(_("The LDAP Login attribute of the CN "
469 raise formencode.Invalid(_("The LDAP Login attribute of the CN "
469 "must be specified - this is the name "
470 "must be specified - this is the name "
470 "of the attribute that is equivalent "
471 "of the attribute that is equivalent "
471 "to 'username'"),
472 "to 'username'"),
472 value, state)
473 value, state)
473
474
474 return value
475 return value
475
476
476 #===============================================================================
477 #===============================================================================
477 # FORMS
478 # FORMS
478 #===============================================================================
479 #===============================================================================
479 class LoginForm(formencode.Schema):
480 class LoginForm(formencode.Schema):
480 allow_extra_fields = True
481 allow_extra_fields = True
481 filter_extra_fields = True
482 filter_extra_fields = True
482 username = UnicodeString(
483 username = UnicodeString(
483 strip=True,
484 strip=True,
484 min=1,
485 min=1,
485 not_empty=True,
486 not_empty=True,
486 messages={
487 messages={
487 'empty':_('Please enter a login'),
488 'empty':_('Please enter a login'),
488 'tooShort':_('Enter a value %(min)i characters long or more')}
489 'tooShort':_('Enter a value %(min)i characters long or more')}
489 )
490 )
490
491
491 password = UnicodeString(
492 password = UnicodeString(
492 strip=True,
493 strip=True,
493 min=3,
494 min=3,
494 not_empty=True,
495 not_empty=True,
495 messages={
496 messages={
496 'empty':_('Please enter a password'),
497 'empty':_('Please enter a password'),
497 'tooShort':_('Enter %(min)i characters or more')}
498 'tooShort':_('Enter %(min)i characters or more')}
498 )
499 )
499
500
500
501 #chained validators have access to all data
502 chained_validators = [ValidAuth]
501 chained_validators = [ValidAuth]
503
502
504 def UserForm(edit=False, old_data={}):
503 def UserForm(edit=False, old_data={}):
505 class _UserForm(formencode.Schema):
504 class _UserForm(formencode.Schema):
506 allow_extra_fields = True
505 allow_extra_fields = True
507 filter_extra_fields = True
506 filter_extra_fields = True
508 username = All(UnicodeString(strip=True, min=1, not_empty=True),
507 username = All(UnicodeString(strip=True, min=1, not_empty=True),
509 ValidUsername(edit, old_data))
508 ValidUsername(edit, old_data))
510 if edit:
509 if edit:
511 new_password = All(UnicodeString(strip=True, min=6, not_empty=False))
510 new_password = All(UnicodeString(strip=True, min=6, not_empty=False))
511 password_confirmation = All(UnicodeString(strip=True, min=6, not_empty=False))
512 admin = StringBoolean(if_missing=False)
512 admin = StringBoolean(if_missing=False)
513 else:
513 else:
514 password = All(UnicodeString(strip=True, min=6, not_empty=True))
514 password = All(UnicodeString(strip=True, min=6, not_empty=True))
515 password_confirmation = All(UnicodeString(strip=True, min=6, not_empty=False))
516
515 active = StringBoolean(if_missing=False)
517 active = StringBoolean(if_missing=False)
516 name = UnicodeString(strip=True, min=1, not_empty=True)
518 name = UnicodeString(strip=True, min=1, not_empty=True)
517 lastname = UnicodeString(strip=True, min=1, not_empty=True)
519 lastname = UnicodeString(strip=True, min=1, not_empty=True)
518 email = All(Email(not_empty=True), UniqSystemEmail(old_data))
520 email = All(Email(not_empty=True), UniqSystemEmail(old_data))
519
521
520 chained_validators = [ValidPassword]
522 chained_validators = [ValidPasswordsMatch, ValidPassword]
521
523
522 return _UserForm
524 return _UserForm
523
525
524
526
525 def UsersGroupForm(edit=False, old_data={}, available_members=[]):
527 def UsersGroupForm(edit=False, old_data={}, available_members=[]):
526 class _UsersGroupForm(formencode.Schema):
528 class _UsersGroupForm(formencode.Schema):
527 allow_extra_fields = True
529 allow_extra_fields = True
528 filter_extra_fields = True
530 filter_extra_fields = True
529
531
530 users_group_name = All(UnicodeString(strip=True, min=1, not_empty=True),
532 users_group_name = All(UnicodeString(strip=True, min=1, not_empty=True),
531 ValidUsersGroup(edit, old_data))
533 ValidUsersGroup(edit, old_data))
532
534
533 users_group_active = StringBoolean(if_missing=False)
535 users_group_active = StringBoolean(if_missing=False)
534
536
535 if edit:
537 if edit:
536 users_group_members = OneOf(available_members, hideList=False,
538 users_group_members = OneOf(available_members, hideList=False,
537 testValueList=True,
539 testValueList=True,
538 if_missing=None, not_empty=False)
540 if_missing=None, not_empty=False)
539
541
540 return _UsersGroupForm
542 return _UsersGroupForm
541
543
542 def ReposGroupForm(edit=False, old_data={}, available_groups=[]):
544 def ReposGroupForm(edit=False, old_data={}, available_groups=[]):
543 class _ReposGroupForm(formencode.Schema):
545 class _ReposGroupForm(formencode.Schema):
544 allow_extra_fields = True
546 allow_extra_fields = True
545 filter_extra_fields = True
547 filter_extra_fields = True
546
548
547 group_name = All(UnicodeString(strip=True, min=1, not_empty=True),
549 group_name = All(UnicodeString(strip=True, min=1, not_empty=True),
548 SlugifyName())
550 SlugifyName())
549 group_description = UnicodeString(strip=True, min=1,
551 group_description = UnicodeString(strip=True, min=1,
550 not_empty=True)
552 not_empty=True)
551 group_parent_id = OneOf(available_groups, hideList=False,
553 group_parent_id = OneOf(available_groups, hideList=False,
552 testValueList=True,
554 testValueList=True,
553 if_missing=None, not_empty=False)
555 if_missing=None, not_empty=False)
554
556
555 chained_validators = [ValidReposGroup(edit, old_data)]
557 chained_validators = [ValidReposGroup(edit, old_data)]
556
558
557 return _ReposGroupForm
559 return _ReposGroupForm
558
560
559 def RegisterForm(edit=False, old_data={}):
561 def RegisterForm(edit=False, old_data={}):
560 class _RegisterForm(formencode.Schema):
562 class _RegisterForm(formencode.Schema):
561 allow_extra_fields = True
563 allow_extra_fields = True
562 filter_extra_fields = True
564 filter_extra_fields = True
563 username = All(ValidUsername(edit, old_data),
565 username = All(ValidUsername(edit, old_data),
564 UnicodeString(strip=True, min=1, not_empty=True))
566 UnicodeString(strip=True, min=1, not_empty=True))
565 password = All(UnicodeString(strip=True, min=6, not_empty=True))
567 password = All(UnicodeString(strip=True, min=6, not_empty=True))
566 password_confirmation = All(UnicodeString(strip=True, min=6, not_empty=True))
568 password_confirmation = All(UnicodeString(strip=True, min=6, not_empty=True))
567 active = StringBoolean(if_missing=False)
569 active = StringBoolean(if_missing=False)
568 name = UnicodeString(strip=True, min=1, not_empty=True)
570 name = UnicodeString(strip=True, min=1, not_empty=True)
569 lastname = UnicodeString(strip=True, min=1, not_empty=True)
571 lastname = UnicodeString(strip=True, min=1, not_empty=True)
570 email = All(Email(not_empty=True), UniqSystemEmail(old_data))
572 email = All(Email(not_empty=True), UniqSystemEmail(old_data))
571
573
572 chained_validators = [ValidPasswordsMatch, ValidPassword]
574 chained_validators = [ValidPasswordsMatch, ValidPassword]
573
575
574 return _RegisterForm
576 return _RegisterForm
575
577
576 def PasswordResetForm():
578 def PasswordResetForm():
577 class _PasswordResetForm(formencode.Schema):
579 class _PasswordResetForm(formencode.Schema):
578 allow_extra_fields = True
580 allow_extra_fields = True
579 filter_extra_fields = True
581 filter_extra_fields = True
580 email = All(ValidSystemEmail(), Email(not_empty=True))
582 email = All(ValidSystemEmail(), Email(not_empty=True))
581 return _PasswordResetForm
583 return _PasswordResetForm
582
584
583 def RepoForm(edit=False, old_data={}, supported_backends=BACKENDS.keys(),
585 def RepoForm(edit=False, old_data={}, supported_backends=BACKENDS.keys(),
584 repo_groups=[]):
586 repo_groups=[]):
585 class _RepoForm(formencode.Schema):
587 class _RepoForm(formencode.Schema):
586 allow_extra_fields = True
588 allow_extra_fields = True
587 filter_extra_fields = False
589 filter_extra_fields = False
588 repo_name = All(UnicodeString(strip=True, min=1, not_empty=True),
590 repo_name = All(UnicodeString(strip=True, min=1, not_empty=True),
589 SlugifyName())
591 SlugifyName())
590 clone_uri = All(UnicodeString(strip=True, min=1, not_empty=False),
592 clone_uri = All(UnicodeString(strip=True, min=1, not_empty=False),
591 ValidCloneUri()())
593 ValidCloneUri()())
592 repo_group = OneOf(repo_groups, hideList=True)
594 repo_group = OneOf(repo_groups, hideList=True)
593 repo_type = OneOf(supported_backends)
595 repo_type = OneOf(supported_backends)
594 description = UnicodeString(strip=True, min=1, not_empty=True)
596 description = UnicodeString(strip=True, min=1, not_empty=True)
595 private = StringBoolean(if_missing=False)
597 private = StringBoolean(if_missing=False)
596 enable_statistics = StringBoolean(if_missing=False)
598 enable_statistics = StringBoolean(if_missing=False)
597 enable_downloads = StringBoolean(if_missing=False)
599 enable_downloads = StringBoolean(if_missing=False)
598
600
599 if edit:
601 if edit:
600 #this is repo owner
602 #this is repo owner
601 user = All(UnicodeString(not_empty=True), ValidRepoUser)
603 user = All(UnicodeString(not_empty=True), ValidRepoUser)
602
604
603 chained_validators = [ValidRepoName(edit, old_data), ValidPerms]
605 chained_validators = [ValidRepoName(edit, old_data), ValidPerms]
604 return _RepoForm
606 return _RepoForm
605
607
606 def RepoForkForm(edit=False, old_data={}, supported_backends=BACKENDS.keys()):
608 def RepoForkForm(edit=False, old_data={}, supported_backends=BACKENDS.keys()):
607 class _RepoForkForm(formencode.Schema):
609 class _RepoForkForm(formencode.Schema):
608 allow_extra_fields = True
610 allow_extra_fields = True
609 filter_extra_fields = False
611 filter_extra_fields = False
610 fork_name = All(UnicodeString(strip=True, min=1, not_empty=True),
612 fork_name = All(UnicodeString(strip=True, min=1, not_empty=True),
611 SlugifyName())
613 SlugifyName())
612 description = UnicodeString(strip=True, min=1, not_empty=True)
614 description = UnicodeString(strip=True, min=1, not_empty=True)
613 private = StringBoolean(if_missing=False)
615 private = StringBoolean(if_missing=False)
614 repo_type = All(ValidForkType(old_data), OneOf(supported_backends))
616 repo_type = All(ValidForkType(old_data), OneOf(supported_backends))
615
617
616 chained_validators = [ValidForkName()]
618 chained_validators = [ValidForkName()]
617
619
618 return _RepoForkForm
620 return _RepoForkForm
619
621
620 def RepoSettingsForm(edit=False, old_data={}, supported_backends=BACKENDS.keys(),
622 def RepoSettingsForm(edit=False, old_data={}, supported_backends=BACKENDS.keys(),
621 repo_groups=[]):
623 repo_groups=[]):
622 class _RepoForm(formencode.Schema):
624 class _RepoForm(formencode.Schema):
623 allow_extra_fields = True
625 allow_extra_fields = True
624 filter_extra_fields = False
626 filter_extra_fields = False
625 repo_name = All(UnicodeString(strip=True, min=1, not_empty=True),
627 repo_name = All(UnicodeString(strip=True, min=1, not_empty=True),
626 SlugifyName())
628 SlugifyName())
627 description = UnicodeString(strip=True, min=1, not_empty=True)
629 description = UnicodeString(strip=True, min=1, not_empty=True)
628 repo_group = OneOf(repo_groups, hideList=True)
630 repo_group = OneOf(repo_groups, hideList=True)
629 private = StringBoolean(if_missing=False)
631 private = StringBoolean(if_missing=False)
630
632
631 chained_validators = [ValidRepoName(edit, old_data), ValidPerms,
633 chained_validators = [ValidRepoName(edit, old_data), ValidPerms,
632 ValidSettings]
634 ValidSettings]
633 return _RepoForm
635 return _RepoForm
634
636
635
637
636 def ApplicationSettingsForm():
638 def ApplicationSettingsForm():
637 class _ApplicationSettingsForm(formencode.Schema):
639 class _ApplicationSettingsForm(formencode.Schema):
638 allow_extra_fields = True
640 allow_extra_fields = True
639 filter_extra_fields = False
641 filter_extra_fields = False
640 rhodecode_title = UnicodeString(strip=True, min=1, not_empty=True)
642 rhodecode_title = UnicodeString(strip=True, min=1, not_empty=True)
641 rhodecode_realm = UnicodeString(strip=True, min=1, not_empty=True)
643 rhodecode_realm = UnicodeString(strip=True, min=1, not_empty=True)
642 rhodecode_ga_code = UnicodeString(strip=True, min=1, not_empty=False)
644 rhodecode_ga_code = UnicodeString(strip=True, min=1, not_empty=False)
643
645
644 return _ApplicationSettingsForm
646 return _ApplicationSettingsForm
645
647
646 def ApplicationUiSettingsForm():
648 def ApplicationUiSettingsForm():
647 class _ApplicationUiSettingsForm(formencode.Schema):
649 class _ApplicationUiSettingsForm(formencode.Schema):
648 allow_extra_fields = True
650 allow_extra_fields = True
649 filter_extra_fields = False
651 filter_extra_fields = False
650 web_push_ssl = OneOf(['true', 'false'], if_missing='false')
652 web_push_ssl = OneOf(['true', 'false'], if_missing='false')
651 paths_root_path = All(ValidPath(), UnicodeString(strip=True, min=1, not_empty=True))
653 paths_root_path = All(ValidPath(), UnicodeString(strip=True, min=1, not_empty=True))
652 hooks_changegroup_update = OneOf(['True', 'False'], if_missing=False)
654 hooks_changegroup_update = OneOf(['True', 'False'], if_missing=False)
653 hooks_changegroup_repo_size = OneOf(['True', 'False'], if_missing=False)
655 hooks_changegroup_repo_size = OneOf(['True', 'False'], if_missing=False)
654 hooks_pretxnchangegroup_push_logger = OneOf(['True', 'False'], if_missing=False)
656 hooks_pretxnchangegroup_push_logger = OneOf(['True', 'False'], if_missing=False)
655 hooks_preoutgoing_pull_logger = OneOf(['True', 'False'], if_missing=False)
657 hooks_preoutgoing_pull_logger = OneOf(['True', 'False'], if_missing=False)
656
658
657 return _ApplicationUiSettingsForm
659 return _ApplicationUiSettingsForm
658
660
659 def DefaultPermissionsForm(perms_choices, register_choices, create_choices):
661 def DefaultPermissionsForm(perms_choices, register_choices, create_choices):
660 class _DefaultPermissionsForm(formencode.Schema):
662 class _DefaultPermissionsForm(formencode.Schema):
661 allow_extra_fields = True
663 allow_extra_fields = True
662 filter_extra_fields = True
664 filter_extra_fields = True
663 overwrite_default = StringBoolean(if_missing=False)
665 overwrite_default = StringBoolean(if_missing=False)
664 anonymous = OneOf(['True', 'False'], if_missing=False)
666 anonymous = OneOf(['True', 'False'], if_missing=False)
665 default_perm = OneOf(perms_choices)
667 default_perm = OneOf(perms_choices)
666 default_register = OneOf(register_choices)
668 default_register = OneOf(register_choices)
667 default_create = OneOf(create_choices)
669 default_create = OneOf(create_choices)
668
670
669 return _DefaultPermissionsForm
671 return _DefaultPermissionsForm
670
672
671
673
672 def LdapSettingsForm(tls_reqcert_choices, search_scope_choices, tls_kind_choices):
674 def LdapSettingsForm(tls_reqcert_choices, search_scope_choices, tls_kind_choices):
673 class _LdapSettingsForm(formencode.Schema):
675 class _LdapSettingsForm(formencode.Schema):
674 allow_extra_fields = True
676 allow_extra_fields = True
675 filter_extra_fields = True
677 filter_extra_fields = True
676 pre_validators = [LdapLibValidator]
678 pre_validators = [LdapLibValidator]
677 ldap_active = StringBoolean(if_missing=False)
679 ldap_active = StringBoolean(if_missing=False)
678 ldap_host = UnicodeString(strip=True,)
680 ldap_host = UnicodeString(strip=True,)
679 ldap_port = Number(strip=True,)
681 ldap_port = Number(strip=True,)
680 ldap_tls_kind = OneOf(tls_kind_choices)
682 ldap_tls_kind = OneOf(tls_kind_choices)
681 ldap_tls_reqcert = OneOf(tls_reqcert_choices)
683 ldap_tls_reqcert = OneOf(tls_reqcert_choices)
682 ldap_dn_user = UnicodeString(strip=True,)
684 ldap_dn_user = UnicodeString(strip=True,)
683 ldap_dn_pass = UnicodeString(strip=True,)
685 ldap_dn_pass = UnicodeString(strip=True,)
684 ldap_base_dn = UnicodeString(strip=True,)
686 ldap_base_dn = UnicodeString(strip=True,)
685 ldap_filter = UnicodeString(strip=True,)
687 ldap_filter = UnicodeString(strip=True,)
686 ldap_search_scope = OneOf(search_scope_choices)
688 ldap_search_scope = OneOf(search_scope_choices)
687 ldap_attr_login = All(AttrLoginValidator, UnicodeString(strip=True,))
689 ldap_attr_login = All(AttrLoginValidator, UnicodeString(strip=True,))
688 ldap_attr_firstname = UnicodeString(strip=True,)
690 ldap_attr_firstname = UnicodeString(strip=True,)
689 ldap_attr_lastname = UnicodeString(strip=True,)
691 ldap_attr_lastname = UnicodeString(strip=True,)
690 ldap_attr_email = UnicodeString(strip=True,)
692 ldap_attr_email = UnicodeString(strip=True,)
691
693
692 return _LdapSettingsForm
694 return _LdapSettingsForm
@@ -1,91 +1,100 b''
1 ## -*- coding: utf-8 -*-
1 ## -*- coding: utf-8 -*-
2 <%inherit file="/base/base.html"/>
2 <%inherit file="/base/base.html"/>
3
3
4 <%def name="title()">
4 <%def name="title()">
5 ${_('Add user')} - ${c.rhodecode_name}
5 ${_('Add user')} - ${c.rhodecode_name}
6 </%def>
6 </%def>
7 <%def name="breadcrumbs_links()">
7 <%def name="breadcrumbs_links()">
8 ${h.link_to(_('Admin'),h.url('admin_home'))}
8 ${h.link_to(_('Admin'),h.url('admin_home'))}
9 &raquo;
9 &raquo;
10 ${h.link_to(_('Users'),h.url('users'))}
10 ${h.link_to(_('Users'),h.url('users'))}
11 &raquo;
11 &raquo;
12 ${_('add new user')}
12 ${_('add new user')}
13 </%def>
13 </%def>
14
14
15 <%def name="page_nav()">
15 <%def name="page_nav()">
16 ${self.menu('admin')}
16 ${self.menu('admin')}
17 </%def>
17 </%def>
18
18
19 <%def name="main()">
19 <%def name="main()">
20 <div class="box">
20 <div class="box">
21 <!-- box / title -->
21 <!-- box / title -->
22 <div class="title">
22 <div class="title">
23 ${self.breadcrumbs()}
23 ${self.breadcrumbs()}
24 </div>
24 </div>
25 <!-- end box / title -->
25 <!-- end box / title -->
26 ${h.form(url('users'))}
26 ${h.form(url('users'))}
27 <div class="form">
27 <div class="form">
28 <!-- fields -->
28 <!-- fields -->
29 <div class="fields">
29 <div class="fields">
30 <div class="field">
30 <div class="field">
31 <div class="label">
31 <div class="label">
32 <label for="username">${_('Username')}:</label>
32 <label for="username">${_('Username')}:</label>
33 </div>
33 </div>
34 <div class="input">
34 <div class="input">
35 ${h.text('username',class_='small')}
35 ${h.text('username',class_='small')}
36 </div>
36 </div>
37 </div>
37 </div>
38
38
39 <div class="field">
39 <div class="field">
40 <div class="label">
40 <div class="label">
41 <label for="password">${_('Password')}:</label>
41 <label for="password">${_('Password')}:</label>
42 </div>
42 </div>
43 <div class="input">
43 <div class="input">
44 ${h.password('password',class_='small')}
44 ${h.password('password',class_='small')}
45 </div>
45 </div>
46 </div>
46 </div>
47
47
48 <div class="field">
48 <div class="field">
49 <div class="label">
49 <div class="label">
50 <label for="password_confirmation">${_('Password confirmation')}:</label>
51 </div>
52 <div class="input">
53 ${h.password('password_confirmation',class_="small",autocomplete="off")}
54 </div>
55 </div>
56
57 <div class="field">
58 <div class="label">
50 <label for="name">${_('First Name')}:</label>
59 <label for="name">${_('First Name')}:</label>
51 </div>
60 </div>
52 <div class="input">
61 <div class="input">
53 ${h.text('name',class_='small')}
62 ${h.text('name',class_='small')}
54 </div>
63 </div>
55 </div>
64 </div>
56
65
57 <div class="field">
66 <div class="field">
58 <div class="label">
67 <div class="label">
59 <label for="lastname">${_('Last Name')}:</label>
68 <label for="lastname">${_('Last Name')}:</label>
60 </div>
69 </div>
61 <div class="input">
70 <div class="input">
62 ${h.text('lastname',class_='small')}
71 ${h.text('lastname',class_='small')}
63 </div>
72 </div>
64 </div>
73 </div>
65
74
66 <div class="field">
75 <div class="field">
67 <div class="label">
76 <div class="label">
68 <label for="email">${_('Email')}:</label>
77 <label for="email">${_('Email')}:</label>
69 </div>
78 </div>
70 <div class="input">
79 <div class="input">
71 ${h.text('email',class_='small')}
80 ${h.text('email',class_='small')}
72 </div>
81 </div>
73 </div>
82 </div>
74
83
75 <div class="field">
84 <div class="field">
76 <div class="label label-checkbox">
85 <div class="label label-checkbox">
77 <label for="active">${_('Active')}:</label>
86 <label for="active">${_('Active')}:</label>
78 </div>
87 </div>
79 <div class="checkboxes">
88 <div class="checkboxes">
80 ${h.checkbox('active',value=True)}
89 ${h.checkbox('active',value=True)}
81 </div>
90 </div>
82 </div>
91 </div>
83
92
84 <div class="buttons">
93 <div class="buttons">
85 ${h.submit('save',_('save'),class_="ui-button")}
94 ${h.submit('save',_('save'),class_="ui-button")}
86 </div>
95 </div>
87 </div>
96 </div>
88 </div>
97 </div>
89 ${h.end_form()}
98 ${h.end_form()}
90 </div>
99 </div>
91 </%def>
100 </%def>
@@ -1,149 +1,158 b''
1 ## -*- coding: utf-8 -*-
1 ## -*- coding: utf-8 -*-
2 <%inherit file="/base/base.html"/>
2 <%inherit file="/base/base.html"/>
3
3
4 <%def name="title()">
4 <%def name="title()">
5 ${_('Edit user')} ${c.user.username} - ${c.rhodecode_name}
5 ${_('Edit user')} ${c.user.username} - ${c.rhodecode_name}
6 </%def>
6 </%def>
7
7
8 <%def name="breadcrumbs_links()">
8 <%def name="breadcrumbs_links()">
9 ${h.link_to(_('Admin'),h.url('admin_home'))}
9 ${h.link_to(_('Admin'),h.url('admin_home'))}
10 &raquo;
10 &raquo;
11 ${h.link_to(_('Users'),h.url('users'))}
11 ${h.link_to(_('Users'),h.url('users'))}
12 &raquo;
12 &raquo;
13 ${_('edit')} "${c.user.username}"
13 ${_('edit')} "${c.user.username}"
14 </%def>
14 </%def>
15
15
16 <%def name="page_nav()">
16 <%def name="page_nav()">
17 ${self.menu('admin')}
17 ${self.menu('admin')}
18 </%def>
18 </%def>
19
19
20 <%def name="main()">
20 <%def name="main()">
21 <div class="box box-left">
21 <div class="box box-left">
22 <!-- box / title -->
22 <!-- box / title -->
23 <div class="title">
23 <div class="title">
24 ${self.breadcrumbs()}
24 ${self.breadcrumbs()}
25 </div>
25 </div>
26 <!-- end box / title -->
26 <!-- end box / title -->
27 ${h.form(url('update_user', id=c.user.user_id),method='put')}
27 ${h.form(url('update_user', id=c.user.user_id),method='put')}
28 <div class="form">
28 <div class="form">
29 <div class="field">
29 <div class="field">
30 <div class="gravatar_box">
30 <div class="gravatar_box">
31 <div class="gravatar"><img alt="gravatar" src="${h.gravatar_url(c.user.email)}"/></div>
31 <div class="gravatar"><img alt="gravatar" src="${h.gravatar_url(c.user.email)}"/></div>
32 <p>
32 <p>
33 <strong>${_('Change your avatar at')} <a href="http://gravatar.com">gravatar.com</a></strong><br/>
33 <strong>${_('Change your avatar at')} <a href="http://gravatar.com">gravatar.com</a></strong><br/>
34 ${_('Using')} ${c.user.email}
34 ${_('Using')} ${c.user.email}
35 </p>
35 </p>
36 </div>
36 </div>
37 </div>
37 </div>
38 <div class="field">
38 <div class="field">
39 <div class="label">
39 <div class="label">
40 <label>${_('API key')}</label> ${c.user.api_key}
40 <label>${_('API key')}</label> ${c.user.api_key}
41 </div>
41 </div>
42 </div>
42 </div>
43
43
44 <div class="fields">
44 <div class="fields">
45 <div class="field">
45 <div class="field">
46 <div class="label">
46 <div class="label">
47 <label for="username">${_('Username')}:</label>
47 <label for="username">${_('Username')}:</label>
48 </div>
48 </div>
49 <div class="input">
49 <div class="input">
50 ${h.text('username',class_='medium')}
50 ${h.text('username',class_='medium')}
51 </div>
51 </div>
52 </div>
52 </div>
53
53
54 <div class="field">
54 <div class="field">
55 <div class="label">
55 <div class="label">
56 <label for="ldap_dn">${_('LDAP DN')}:</label>
56 <label for="ldap_dn">${_('LDAP DN')}:</label>
57 </div>
57 </div>
58 <div class="input">
58 <div class="input">
59 ${h.text('ldap_dn',class_='medium')}
59 ${h.text('ldap_dn',class_='medium')}
60 </div>
60 </div>
61 </div>
61 </div>
62
62
63 <div class="field">
63 <div class="field">
64 <div class="label">
64 <div class="label">
65 <label for="new_password">${_('New password')}:</label>
65 <label for="new_password">${_('New password')}:</label>
66 </div>
66 </div>
67 <div class="input">
67 <div class="input">
68 ${h.password('new_password',class_='medium',autocomplete="off")}
68 ${h.password('new_password',class_='medium',autocomplete="off")}
69 </div>
69 </div>
70 </div>
70 </div>
71
71
72 <div class="field">
72 <div class="field">
73 <div class="label">
73 <div class="label">
74 <label for="password_confirmation">${_('New password confirmation')}:</label>
75 </div>
76 <div class="input">
77 ${h.password('password_confirmation',class_="medium",autocomplete="off")}
78 </div>
79 </div>
80
81 <div class="field">
82 <div class="label">
74 <label for="name">${_('First Name')}:</label>
83 <label for="name">${_('First Name')}:</label>
75 </div>
84 </div>
76 <div class="input">
85 <div class="input">
77 ${h.text('name',class_='medium')}
86 ${h.text('name',class_='medium')}
78 </div>
87 </div>
79 </div>
88 </div>
80
89
81 <div class="field">
90 <div class="field">
82 <div class="label">
91 <div class="label">
83 <label for="lastname">${_('Last Name')}:</label>
92 <label for="lastname">${_('Last Name')}:</label>
84 </div>
93 </div>
85 <div class="input">
94 <div class="input">
86 ${h.text('lastname',class_='medium')}
95 ${h.text('lastname',class_='medium')}
87 </div>
96 </div>
88 </div>
97 </div>
89
98
90 <div class="field">
99 <div class="field">
91 <div class="label">
100 <div class="label">
92 <label for="email">${_('Email')}:</label>
101 <label for="email">${_('Email')}:</label>
93 </div>
102 </div>
94 <div class="input">
103 <div class="input">
95 ${h.text('email',class_='medium')}
104 ${h.text('email',class_='medium')}
96 </div>
105 </div>
97 </div>
106 </div>
98
107
99 <div class="field">
108 <div class="field">
100 <div class="label label-checkbox">
109 <div class="label label-checkbox">
101 <label for="active">${_('Active')}:</label>
110 <label for="active">${_('Active')}:</label>
102 </div>
111 </div>
103 <div class="checkboxes">
112 <div class="checkboxes">
104 ${h.checkbox('active',value=True)}
113 ${h.checkbox('active',value=True)}
105 </div>
114 </div>
106 </div>
115 </div>
107
116
108 <div class="field">
117 <div class="field">
109 <div class="label label-checkbox">
118 <div class="label label-checkbox">
110 <label for="admin">${_('Admin')}:</label>
119 <label for="admin">${_('Admin')}:</label>
111 </div>
120 </div>
112 <div class="checkboxes">
121 <div class="checkboxes">
113 ${h.checkbox('admin',value=True)}
122 ${h.checkbox('admin',value=True)}
114 </div>
123 </div>
115 </div>
124 </div>
116 <div class="buttons">
125 <div class="buttons">
117 ${h.submit('save',_('Save'),class_="ui-button")}
126 ${h.submit('save',_('Save'),class_="ui-button")}
118 ${h.reset('reset',_('Reset'),class_="ui-button")}
127 ${h.reset('reset',_('Reset'),class_="ui-button")}
119 </div>
128 </div>
120 </div>
129 </div>
121 </div>
130 </div>
122 ${h.end_form()}
131 ${h.end_form()}
123 </div>
132 </div>
124 <div class="box box-right">
133 <div class="box box-right">
125 <!-- box / title -->
134 <!-- box / title -->
126 <div class="title">
135 <div class="title">
127 <h5>${_('Permissions')}</h5>
136 <h5>${_('Permissions')}</h5>
128 </div>
137 </div>
129 ${h.form(url('user_perm', id=c.user.user_id),method='put')}
138 ${h.form(url('user_perm', id=c.user.user_id),method='put')}
130 <div class="form">
139 <div class="form">
131 <!-- fields -->
140 <!-- fields -->
132 <div class="fields">
141 <div class="fields">
133 <div class="field">
142 <div class="field">
134 <div class="label label-checkbox">
143 <div class="label label-checkbox">
135 <label for="create_repo_perm">${_('Create repositories')}:</label>
144 <label for="create_repo_perm">${_('Create repositories')}:</label>
136 </div>
145 </div>
137 <div class="checkboxes">
146 <div class="checkboxes">
138 ${h.checkbox('create_repo_perm',value=True)}
147 ${h.checkbox('create_repo_perm',value=True)}
139 </div>
148 </div>
140 </div>
149 </div>
141 <div class="buttons">
150 <div class="buttons">
142 ${h.submit('save',_('Save'),class_="ui-button")}
151 ${h.submit('save',_('Save'),class_="ui-button")}
143 ${h.reset('reset',_('Reset'),class_="ui-button")}
152 ${h.reset('reset',_('Reset'),class_="ui-button")}
144 </div>
153 </div>
145 </div>
154 </div>
146 </div>
155 </div>
147 ${h.end_form()}
156 ${h.end_form()}
148 </div>
157 </div>
149 </%def>
158 </%def>
@@ -1,211 +1,222 b''
1 ## -*- coding: utf-8 -*-
1 ## -*- coding: utf-8 -*-
2 <%inherit file="/base/base.html"/>
2 <%inherit file="/base/base.html"/>
3
3
4 <%def name="title()">
4 <%def name="title()">
5 ${_('My account')} ${c.rhodecode_user.username} - ${c.rhodecode_name}
5 ${_('My account')} ${c.rhodecode_user.username} - ${c.rhodecode_name}
6 </%def>
6 </%def>
7
7
8 <%def name="breadcrumbs_links()">
8 <%def name="breadcrumbs_links()">
9 ${_('My Account')}
9 ${_('My Account')}
10 </%def>
10 </%def>
11
11
12 <%def name="page_nav()">
12 <%def name="page_nav()">
13 ${self.menu('admin')}
13 ${self.menu('admin')}
14 </%def>
14 </%def>
15
15
16 <%def name="main()">
16 <%def name="main()">
17
17
18 <div class="box box-left">
18 <div class="box box-left">
19 <!-- box / title -->
19 <!-- box / title -->
20 <div class="title">
20 <div class="title">
21 ${self.breadcrumbs()}
21 ${self.breadcrumbs()}
22 </div>
22 </div>
23 <!-- end box / title -->
23 <!-- end box / title -->
24 <div>
24 <div>
25 ${h.form(url('admin_settings_my_account_update'),method='put')}
25 ${h.form(url('admin_settings_my_account_update'),method='put')}
26 <div class="form">
26 <div class="form">
27
27
28 <div class="field">
28 <div class="field">
29 <div class="gravatar_box">
29 <div class="gravatar_box">
30 <div class="gravatar"><img alt="gravatar" src="${h.gravatar_url(c.user.email)}"/></div>
30 <div class="gravatar"><img alt="gravatar" src="${h.gravatar_url(c.user.email)}"/></div>
31 <p>
31 <p>
32 <strong>${_('Change your avatar at')} <a href="http://gravatar.com">gravatar.com</a></strong><br/>
32 <strong>${_('Change your avatar at')} <a href="http://gravatar.com">gravatar.com</a></strong><br/>
33 ${_('Using')} ${c.user.email}
33 ${_('Using')} ${c.user.email}
34 </p>
34 </p>
35 </div>
35 </div>
36 </div>
36 </div>
37 <div class="field">
37 <div class="field">
38 <div class="label">
38 <div class="label">
39 <label>${_('API key')}</label> ${c.user.api_key}
39 <label>${_('API key')}</label> ${c.user.api_key}
40 </div>
40 </div>
41 </div>
41 </div>
42 <div class="fields">
42 <div class="fields">
43 <div class="field">
43 <div class="field">
44 <div class="label">
44 <div class="label">
45 <label for="username">${_('Username')}:</label>
45 <label for="username">${_('Username')}:</label>
46 </div>
46 </div>
47 <div class="input">
47 <div class="input">
48 ${h.text('username',class_="medium")}
48 ${h.text('username',class_="medium")}
49 </div>
49 </div>
50 </div>
50 </div>
51
51
52 <div class="field">
52 <div class="field">
53 <div class="label">
53 <div class="label">
54 <label for="new_password">${_('New password')}:</label>
54 <label for="new_password">${_('New password')}:</label>
55 </div>
55 </div>
56 <div class="input">
56 <div class="input">
57 ${h.password('new_password',class_="medium",autocomplete="off")}
57 ${h.password('new_password',class_="medium",autocomplete="off")}
58 </div>
58 </div>
59 </div>
59 </div>
60
60
61 <div class="field">
61 <div class="field">
62 <div class="label">
62 <div class="label">
63 <label for="password_confirmation">${_('New password confirmation')}:</label>
64 </div>
65 <div class="input">
66 ${h.password('password_confirmation',class_="medium",autocomplete="off")}
67 </div>
68 </div>
69
70 <div class="field">
71 <div class="label">
63 <label for="name">${_('First Name')}:</label>
72 <label for="name">${_('First Name')}:</label>
64 </div>
73 </div>
65 <div class="input">
74 <div class="input">
66 ${h.text('name',class_="medium")}
75 ${h.text('name',class_="medium")}
67 </div>
76 </div>
68 </div>
77 </div>
69
78
70 <div class="field">
79 <div class="field">
71 <div class="label">
80 <div class="label">
72 <label for="lastname">${_('Last Name')}:</label>
81 <label for="lastname">${_('Last Name')}:</label>
73 </div>
82 </div>
74 <div class="input">
83 <div class="input">
75 ${h.text('lastname',class_="medium")}
84 ${h.text('lastname',class_="medium")}
76 </div>
85 </div>
77 </div>
86 </div>
78
87
79 <div class="field">
88 <div class="field">
80 <div class="label">
89 <div class="label">
81 <label for="email">${_('Email')}:</label>
90 <label for="email">${_('Email')}:</label>
82 </div>
91 </div>
83 <div class="input">
92 <div class="input">
84 ${h.text('email',class_="medium")}
93 ${h.text('email',class_="medium")}
85 </div>
94 </div>
86 </div>
95 </div>
87
96
88 <div class="buttons">
97 <div class="buttons">
89 ${h.submit('save',_('Save'),class_="ui-button")}
98 ${h.submit('save',_('Save'),class_="ui-button")}
90 ${h.reset('reset',_('Reset'),class_="ui-button")}
99 ${h.reset('reset',_('Reset'),class_="ui-button")}
91 </div>
100 </div>
92 </div>
101 </div>
93 </div>
102 </div>
94 ${h.end_form()}
103 ${h.end_form()}
95 </div>
104 </div>
96 </div>
105 </div>
97
106
98 <div class="box box-right">
107 <div class="box box-right">
99 <!-- box / title -->
108 <!-- box / title -->
100 <div class="title">
109 <div class="title">
101 <h5>${_('My repositories')}
110 <h5>${_('My repositories')}
102 <input class="top-right-rounded-corner top-left-rounded-corner bottom-left-rounded-corner bottom-right-rounded-corner" id="q_filter" size="15" type="text" name="filter" value="${_('quick filter...')}"/>
111 <input class="top-right-rounded-corner top-left-rounded-corner bottom-left-rounded-corner bottom-right-rounded-corner" id="q_filter" size="15" type="text" name="filter" value="${_('quick filter...')}"/>
103 </h5>
112 </h5>
104 %if h.HasPermissionAny('hg.admin','hg.create.repository')():
113 %if h.HasPermissionAny('hg.admin','hg.create.repository')():
105 <ul class="links">
114 <ul class="links">
106 <li>
115 <li>
107 <span>${h.link_to(_('ADD REPOSITORY'),h.url('admin_settings_create_repository'))}</span>
116 <span>${h.link_to(_('ADD REPOSITORY'),h.url('admin_settings_create_repository'))}</span>
108 </li>
117 </li>
109 </ul>
118 </ul>
110 %endif
119 %endif
111 </div>
120 </div>
112 <!-- end box / title -->
121 <!-- end box / title -->
113 <div class="table">
122 <div class="table">
114 <table>
123 <table>
115 <thead>
124 <thead>
116 <tr>
125 <tr>
117 <th class="left">${_('Name')}</th>
126 <th class="left">${_('Name')}</th>
118 <th class="left">${_('revision')}</th>
127 <th class="left">${_('revision')}</th>
119 <th colspan="2" class="left">${_('action')}</th>
128 <th colspan="2" class="left">${_('action')}</th>
120 </thead>
129 </thead>
121 <tbody>
130 <tbody>
122 %if c.user_repos:
131 %if c.user_repos:
123 %for repo in c.user_repos:
132 %for repo in c.user_repos:
124 <tr>
133 <tr>
125 <td>
134 <td>
126 %if repo['dbrepo']['repo_type'] =='hg':
135 %if repo['dbrepo']['repo_type'] =='hg':
127 <img class="icon" title="${_('Mercurial repository')}" alt="${_('Mercurial repository')}" src="${h.url("/images/icons/hgicon.png")}"/>
136 <img class="icon" title="${_('Mercurial repository')}" alt="${_('Mercurial repository')}" src="${h.url("/images/icons/hgicon.png")}"/>
128 %elif repo['dbrepo']['repo_type'] =='git':
137 %elif repo['dbrepo']['repo_type'] =='git':
129 <img class="icon" title="${_('Git repository')}" alt="${_('Git repository')}" src="${h.url("/images/icons/giticon.png")}"/>
138 <img class="icon" title="${_('Git repository')}" alt="${_('Git repository')}" src="${h.url("/images/icons/giticon.png")}"/>
130 %else:
139 %else:
131
140
132 %endif
141 %endif
133 %if repo['dbrepo']['private']:
142 %if repo['dbrepo']['private']:
134 <img class="icon" alt="${_('private')}" src="${h.url("/images/icons/lock.png")}"/>
143 <img class="icon" alt="${_('private')}" src="${h.url("/images/icons/lock.png")}"/>
135 %else:
144 %else:
136 <img class="icon" alt="${_('public')}" src="${h.url("/images/icons/lock_open.png")}"/>
145 <img class="icon" alt="${_('public')}" src="${h.url("/images/icons/lock_open.png")}"/>
137 %endif
146 %endif
138
147
139 ${h.link_to(repo['name'], h.url('summary_home',repo_name=repo['name']),class_="repo_name")}
148 ${h.link_to(repo['name'], h.url('summary_home',repo_name=repo['name']),class_="repo_name")}
140 %if repo['dbrepo_fork']:
149 %if repo['dbrepo_fork']:
141 <a href="${h.url('summary_home',repo_name=repo['dbrepo_fork']['repo_name'])}">
150 <a href="${h.url('summary_home',repo_name=repo['dbrepo_fork']['repo_name'])}">
142 <img class="icon" alt="${_('public')}"
151 <img class="icon" alt="${_('public')}"
143 title="${_('Fork of')} ${repo['dbrepo_fork']['repo_name']}"
152 title="${_('Fork of')} ${repo['dbrepo_fork']['repo_name']}"
144 src="${h.url('/images/icons/arrow_divide.png')}"/></a>
153 src="${h.url('/images/icons/arrow_divide.png')}"/></a>
145 %endif
154 %endif
146 </td>
155 </td>
147 <td><span class="tooltip" title="${repo['last_change']}">${("r%s:%s") % (repo['rev'],h.short_id(repo['tip']))}</span></td>
156 <td><span class="tooltip" title="${repo['last_change']}">${("r%s:%s") % (repo['rev'],h.short_id(repo['tip']))}</span></td>
148 <td><a href="${h.url('repo_settings_home',repo_name=repo['name'])}" title="${_('edit')}"><img class="icon" alt="${_('private')}" src="${h.url('/images/icons/application_form_edit.png')}"/></a></td>
157 <td><a href="${h.url('repo_settings_home',repo_name=repo['name'])}" title="${_('edit')}"><img class="icon" alt="${_('private')}" src="${h.url('/images/icons/application_form_edit.png')}"/></a></td>
149 <td>
158 <td>
150 ${h.form(url('repo_settings_delete', repo_name=repo['name']),method='delete')}
159 ${h.form(url('repo_settings_delete', repo_name=repo['name']),method='delete')}
151 ${h.submit('remove_%s' % repo['name'],'',class_="delete_icon action_button",onclick="return confirm('Confirm to delete this repository');")}
160 ${h.submit('remove_%s' % repo['name'],'',class_="delete_icon action_button",onclick="return confirm('Confirm to delete this repository');")}
152 ${h.end_form()}
161 ${h.end_form()}
153 </td>
162 </td>
154 </tr>
163 </tr>
155 %endfor
164 %endfor
156 %else:
165 %else:
166 <div style="padding:5px 0px 10px 0px;">
157 ${_('No repositories yet')}
167 ${_('No repositories yet')}
158 %if h.HasPermissionAny('hg.admin','hg.create.repository')():
168 %if h.HasPermissionAny('hg.admin','hg.create.repository')():
159 ${h.link_to(_('create one now'),h.url('admin_settings_create_repository'))}
169 ${h.link_to(_('create one now'),h.url('admin_settings_create_repository'),class_="ui-button-small")}
160 %endif
170 %endif
171 </div>
161 %endif
172 %endif
162 </tbody>
173 </tbody>
163 </table>
174 </table>
164 </div>
175 </div>
165
176
166 </div>
177 </div>
167 <script type="text/javascript">
178 <script type="text/javascript">
168 var D = YAHOO.util.Dom;
179 var D = YAHOO.util.Dom;
169 var E = YAHOO.util.Event;
180 var E = YAHOO.util.Event;
170 var S = YAHOO.util.Selector;
181 var S = YAHOO.util.Selector;
171
182
172 var q_filter = D.get('q_filter');
183 var q_filter = D.get('q_filter');
173 var F = YAHOO.namespace('q_filter');
184 var F = YAHOO.namespace('q_filter');
174
185
175 E.on(q_filter,'click',function(){
186 E.on(q_filter,'click',function(){
176 q_filter.value = '';
187 q_filter.value = '';
177 });
188 });
178
189
179 F.filterTimeout = null;
190 F.filterTimeout = null;
180
191
181 F.updateFilter = function() {
192 F.updateFilter = function() {
182 // Reset timeout
193 // Reset timeout
183 F.filterTimeout = null;
194 F.filterTimeout = null;
184
195
185 var obsolete = [];
196 var obsolete = [];
186 var nodes = S.query('div.table tr td a.repo_name');
197 var nodes = S.query('div.table tr td a.repo_name');
187 var req = q_filter.value.toLowerCase();
198 var req = q_filter.value.toLowerCase();
188 for (n in nodes){
199 for (n in nodes){
189 D.setStyle(nodes[n].parentNode.parentNode,'display','')
200 D.setStyle(nodes[n].parentNode.parentNode,'display','')
190 }
201 }
191 if (req){
202 if (req){
192 for (n in nodes){
203 for (n in nodes){
193 if (nodes[n].innerHTML.toLowerCase().indexOf(req) == -1) {
204 if (nodes[n].innerHTML.toLowerCase().indexOf(req) == -1) {
194 obsolete.push(nodes[n]);
205 obsolete.push(nodes[n]);
195 }
206 }
196 }
207 }
197 if(obsolete){
208 if(obsolete){
198 for (n in obsolete){
209 for (n in obsolete){
199 D.setStyle(obsolete[n].parentNode.parentNode,'display','none');
210 D.setStyle(obsolete[n].parentNode.parentNode,'display','none');
200 }
211 }
201 }
212 }
202 }
213 }
203 }
214 }
204
215
205 E.on(q_filter,'keyup',function(e){
216 E.on(q_filter,'keyup',function(e){
206 clearTimeout(F.filterTimeout);
217 clearTimeout(F.filterTimeout);
207 F.filterTimeout = setTimeout(F.updateFilter,600);
218 F.filterTimeout = setTimeout(F.updateFilter,600);
208 });
219 });
209
220
210 </script>
221 </script>
211 </%def>
222 </%def>
@@ -1,208 +1,212 b''
1 # -*- coding: utf-8 -*-
1 # -*- coding: utf-8 -*-
2
2
3 from rhodecode.lib.auth import get_crypt_password, check_password
3 from rhodecode.lib.auth import get_crypt_password, check_password
4 from rhodecode.model.db import User, RhodeCodeSettings
4 from rhodecode.model.db import User, RhodeCodeSettings
5 from rhodecode.tests import *
5 from rhodecode.tests import *
6
6
7 class TestAdminSettingsController(TestController):
7 class TestAdminSettingsController(TestController):
8
8
9 def test_index(self):
9 def test_index(self):
10 response = self.app.get(url('admin_settings'))
10 response = self.app.get(url('admin_settings'))
11 # Test response...
11 # Test response...
12
12
13 def test_index_as_xml(self):
13 def test_index_as_xml(self):
14 response = self.app.get(url('formatted_admin_settings', format='xml'))
14 response = self.app.get(url('formatted_admin_settings', format='xml'))
15
15
16 def test_create(self):
16 def test_create(self):
17 response = self.app.post(url('admin_settings'))
17 response = self.app.post(url('admin_settings'))
18
18
19 def test_new(self):
19 def test_new(self):
20 response = self.app.get(url('admin_new_setting'))
20 response = self.app.get(url('admin_new_setting'))
21
21
22 def test_new_as_xml(self):
22 def test_new_as_xml(self):
23 response = self.app.get(url('formatted_admin_new_setting', format='xml'))
23 response = self.app.get(url('formatted_admin_new_setting', format='xml'))
24
24
25 def test_update(self):
25 def test_update(self):
26 response = self.app.put(url('admin_setting', setting_id=1))
26 response = self.app.put(url('admin_setting', setting_id=1))
27
27
28 def test_update_browser_fakeout(self):
28 def test_update_browser_fakeout(self):
29 response = self.app.post(url('admin_setting', setting_id=1), params=dict(_method='put'))
29 response = self.app.post(url('admin_setting', setting_id=1), params=dict(_method='put'))
30
30
31 def test_delete(self):
31 def test_delete(self):
32 response = self.app.delete(url('admin_setting', setting_id=1))
32 response = self.app.delete(url('admin_setting', setting_id=1))
33
33
34 def test_delete_browser_fakeout(self):
34 def test_delete_browser_fakeout(self):
35 response = self.app.post(url('admin_setting', setting_id=1), params=dict(_method='delete'))
35 response = self.app.post(url('admin_setting', setting_id=1), params=dict(_method='delete'))
36
36
37 def test_show(self):
37 def test_show(self):
38 response = self.app.get(url('admin_setting', setting_id=1))
38 response = self.app.get(url('admin_setting', setting_id=1))
39
39
40 def test_show_as_xml(self):
40 def test_show_as_xml(self):
41 response = self.app.get(url('formatted_admin_setting', setting_id=1, format='xml'))
41 response = self.app.get(url('formatted_admin_setting', setting_id=1, format='xml'))
42
42
43 def test_edit(self):
43 def test_edit(self):
44 response = self.app.get(url('admin_edit_setting', setting_id=1))
44 response = self.app.get(url('admin_edit_setting', setting_id=1))
45
45
46 def test_edit_as_xml(self):
46 def test_edit_as_xml(self):
47 response = self.app.get(url('formatted_admin_edit_setting',
47 response = self.app.get(url('formatted_admin_edit_setting',
48 setting_id=1, format='xml'))
48 setting_id=1, format='xml'))
49
49
50
50
51 def test_ga_code_active(self):
51 def test_ga_code_active(self):
52 self.log_user()
52 self.log_user()
53 old_title = 'RhodeCode'
53 old_title = 'RhodeCode'
54 old_realm = 'RhodeCode authentication'
54 old_realm = 'RhodeCode authentication'
55 new_ga_code = 'ga-test-123456789'
55 new_ga_code = 'ga-test-123456789'
56 response = self.app.post(url('admin_setting', setting_id='global'),
56 response = self.app.post(url('admin_setting', setting_id='global'),
57 params=dict(
57 params=dict(
58 _method='put',
58 _method='put',
59 rhodecode_title=old_title,
59 rhodecode_title=old_title,
60 rhodecode_realm=old_realm,
60 rhodecode_realm=old_realm,
61 rhodecode_ga_code=new_ga_code
61 rhodecode_ga_code=new_ga_code
62 ))
62 ))
63
63
64 self.checkSessionFlash(response, 'Updated application settings')
64 self.checkSessionFlash(response, 'Updated application settings')
65
65
66 self.assertEqual(RhodeCodeSettings
66 self.assertEqual(RhodeCodeSettings
67 .get_app_settings()['rhodecode_ga_code'], new_ga_code)
67 .get_app_settings()['rhodecode_ga_code'], new_ga_code)
68
68
69 response = response.follow()
69 response = response.follow()
70 self.assertTrue("""_gaq.push(['_setAccount', '%s']);""" % new_ga_code
70 self.assertTrue("""_gaq.push(['_setAccount', '%s']);""" % new_ga_code
71 in response.body)
71 in response.body)
72
72
73 def test_ga_code_inactive(self):
73 def test_ga_code_inactive(self):
74 self.log_user()
74 self.log_user()
75 old_title = 'RhodeCode'
75 old_title = 'RhodeCode'
76 old_realm = 'RhodeCode authentication'
76 old_realm = 'RhodeCode authentication'
77 new_ga_code = ''
77 new_ga_code = ''
78 response = self.app.post(url('admin_setting', setting_id='global'),
78 response = self.app.post(url('admin_setting', setting_id='global'),
79 params=dict(
79 params=dict(
80 _method='put',
80 _method='put',
81 rhodecode_title=old_title,
81 rhodecode_title=old_title,
82 rhodecode_realm=old_realm,
82 rhodecode_realm=old_realm,
83 rhodecode_ga_code=new_ga_code
83 rhodecode_ga_code=new_ga_code
84 ))
84 ))
85
85
86 self.assertTrue('Updated application settings' in
86 self.assertTrue('Updated application settings' in
87 response.session['flash'][0][1])
87 response.session['flash'][0][1])
88 self.assertEqual(RhodeCodeSettings
88 self.assertEqual(RhodeCodeSettings
89 .get_app_settings()['rhodecode_ga_code'], new_ga_code)
89 .get_app_settings()['rhodecode_ga_code'], new_ga_code)
90
90
91 response = response.follow()
91 response = response.follow()
92 self.assertTrue("""_gaq.push(['_setAccount', '%s']);""" % new_ga_code
92 self.assertTrue("""_gaq.push(['_setAccount', '%s']);""" % new_ga_code
93 not in response.body)
93 not in response.body)
94
94
95
95
96 def test_title_change(self):
96 def test_title_change(self):
97 self.log_user()
97 self.log_user()
98 old_title = 'RhodeCode'
98 old_title = 'RhodeCode'
99 new_title = old_title + '_changed'
99 new_title = old_title + '_changed'
100 old_realm = 'RhodeCode authentication'
100 old_realm = 'RhodeCode authentication'
101
101
102 for new_title in ['Changed', 'Ε»Γ³Ε‚wik', old_title]:
102 for new_title in ['Changed', 'Ε»Γ³Ε‚wik', old_title]:
103 response = self.app.post(url('admin_setting', setting_id='global'),
103 response = self.app.post(url('admin_setting', setting_id='global'),
104 params=dict(
104 params=dict(
105 _method='put',
105 _method='put',
106 rhodecode_title=new_title,
106 rhodecode_title=new_title,
107 rhodecode_realm=old_realm,
107 rhodecode_realm=old_realm,
108 rhodecode_ga_code=''
108 rhodecode_ga_code=''
109 ))
109 ))
110
110
111 self.checkSessionFlash(response, 'Updated application settings')
111 self.checkSessionFlash(response, 'Updated application settings')
112 self.assertEqual(RhodeCodeSettings
112 self.assertEqual(RhodeCodeSettings
113 .get_app_settings()['rhodecode_title'],
113 .get_app_settings()['rhodecode_title'],
114 new_title.decode('utf-8'))
114 new_title.decode('utf-8'))
115
115
116 response = response.follow()
116 response = response.follow()
117 self.assertTrue("""<h1><a href="/">%s</a></h1>""" % new_title
117 self.assertTrue("""<h1><a href="/">%s</a></h1>""" % new_title
118 in response.body)
118 in response.body)
119
119
120
120
121 def test_my_account(self):
121 def test_my_account(self):
122 self.log_user()
122 self.log_user()
123 response = self.app.get(url('admin_settings_my_account'))
123 response = self.app.get(url('admin_settings_my_account'))
124
124
125 self.assertTrue('value="test_admin' in response.body)
125 self.assertTrue('value="test_admin' in response.body)
126
126
127 def test_my_account_update(self):
127 def test_my_account_update(self):
128 self.log_user()
128 self.log_user()
129
129
130 new_email = 'new@mail.pl'
130 new_email = 'new@mail.pl'
131 new_name = 'NewName'
131 new_name = 'NewName'
132 new_lastname = 'NewLastname'
132 new_lastname = 'NewLastname'
133 new_password = 'test123'
133 new_password = 'test123'
134
134
135
135
136 response = self.app.post(url('admin_settings_my_account_update'),
136 response = self.app.post(url('admin_settings_my_account_update'),
137 params=dict(_method='put',
137 params=dict(_method='put',
138 username='test_admin',
138 username='test_admin',
139 new_password=new_password,
139 new_password=new_password,
140 password_confirmation = new_password,
140 password='',
141 password='',
141 name=new_name,
142 name=new_name,
142 lastname=new_lastname,
143 lastname=new_lastname,
143 email=new_email,))
144 email=new_email,))
144 response.follow()
145 response.follow()
145
146
146 assert 'Your account was updated successfully' in response.session['flash'][0][1], 'no flash message about success of change'
147 assert 'Your account was updated successfully' in response.session['flash'][0][1], 'no flash message about success of change'
147 user = self.sa.query(User).filter(User.username == 'test_admin').one()
148 user = self.sa.query(User).filter(User.username == 'test_admin').one()
148 assert user.email == new_email , 'incorrect user email after update got %s vs %s' % (user.email, new_email)
149 assert user.email == new_email , 'incorrect user email after update got %s vs %s' % (user.email, new_email)
149 assert user.name == new_name, 'updated field mismatch %s vs %s' % (user.name, new_name)
150 assert user.name == new_name, 'updated field mismatch %s vs %s' % (user.name, new_name)
150 assert user.lastname == new_lastname, 'updated field mismatch %s vs %s' % (user.lastname, new_lastname)
151 assert user.lastname == new_lastname, 'updated field mismatch %s vs %s' % (user.lastname, new_lastname)
151 assert check_password(new_password, user.password) is True, 'password field mismatch %s vs %s' % (user.password, new_password)
152 assert check_password(new_password, user.password) is True, 'password field mismatch %s vs %s' % (user.password, new_password)
152
153
153 #bring back the admin settings
154 #bring back the admin settings
154 old_email = 'test_admin@mail.com'
155 old_email = 'test_admin@mail.com'
155 old_name = 'RhodeCode'
156 old_name = 'RhodeCode'
156 old_lastname = 'Admin'
157 old_lastname = 'Admin'
157 old_password = 'test12'
158 old_password = 'test12'
158
159
159 response = self.app.post(url('admin_settings_my_account_update'), params=dict(
160 response = self.app.post(url('admin_settings_my_account_update'), params=dict(
160 _method='put',
161 _method='put',
161 username='test_admin',
162 username='test_admin',
162 new_password=old_password,
163 new_password=old_password,
164 password_confirmation = old_password,
163 password='',
165 password='',
164 name=old_name,
166 name=old_name,
165 lastname=old_lastname,
167 lastname=old_lastname,
166 email=old_email,))
168 email=old_email,))
167
169
168 response.follow()
170 response.follow()
169 self.checkSessionFlash(response,
171 self.checkSessionFlash(response,
170 'Your account was updated successfully')
172 'Your account was updated successfully')
171
173
172 user = self.sa.query(User).filter(User.username == 'test_admin').one()
174 user = self.sa.query(User).filter(User.username == 'test_admin').one()
173 assert user.email == old_email , 'incorrect user email after update got %s vs %s' % (user.email, old_email)
175 assert user.email == old_email , 'incorrect user email after update got %s vs %s' % (user.email, old_email)
174
176
175 assert user.email == old_email , 'incorrect user email after update got %s vs %s' % (user.email, old_email)
177 assert user.email == old_email , 'incorrect user email after update got %s vs %s' % (user.email, old_email)
176 assert user.name == old_name, 'updated field mismatch %s vs %s' % (user.name, old_name)
178 assert user.name == old_name, 'updated field mismatch %s vs %s' % (user.name, old_name)
177 assert user.lastname == old_lastname, 'updated field mismatch %s vs %s' % (user.lastname, old_lastname)
179 assert user.lastname == old_lastname, 'updated field mismatch %s vs %s' % (user.lastname, old_lastname)
178 assert check_password(old_password, user.password) is True , 'password updated field mismatch %s vs %s' % (user.password, old_password)
180 assert check_password(old_password, user.password) is True , 'password updated field mismatch %s vs %s' % (user.password, old_password)
179
181
180
182
181 def test_my_account_update_err_email_exists(self):
183 def test_my_account_update_err_email_exists(self):
182 self.log_user()
184 self.log_user()
183
185
184 new_email = 'test_regular@mail.com'#already exisitn email
186 new_email = 'test_regular@mail.com'#already exisitn email
185 response = self.app.post(url('admin_settings_my_account_update'), params=dict(
187 response = self.app.post(url('admin_settings_my_account_update'), params=dict(
186 _method='put',
188 _method='put',
187 username='test_admin',
189 username='test_admin',
188 new_password='test12',
190 new_password='test12',
191 password_confirmation = 'test122',
189 name='NewName',
192 name='NewName',
190 lastname='NewLastname',
193 lastname='NewLastname',
191 email=new_email,))
194 email=new_email,))
192
195
193 assert 'This e-mail address is already taken' in response.body, 'Missing error message about existing email'
196 assert 'This e-mail address is already taken' in response.body, 'Missing error message about existing email'
194
197
195
198
196 def test_my_account_update_err(self):
199 def test_my_account_update_err(self):
197 self.log_user('test_regular2', 'test12')
200 self.log_user('test_regular2', 'test12')
198
201
199 new_email = 'newmail.pl'
202 new_email = 'newmail.pl'
200 response = self.app.post(url('admin_settings_my_account_update'), params=dict(
203 response = self.app.post(url('admin_settings_my_account_update'), params=dict(
201 _method='put',
204 _method='put',
202 username='test_admin',
205 username='test_admin',
203 new_password='test12',
206 new_password='test12',
207 password_confirmation = 'test122',
204 name='NewName',
208 name='NewName',
205 lastname='NewLastname',
209 lastname='NewLastname',
206 email=new_email,))
210 email=new_email,))
207 assert 'An email address must contain a single @' in response.body, 'Missing error message about wrong email'
211 assert 'An email address must contain a single @' in response.body, 'Missing error message about wrong email'
208 assert 'This username already exists' in response.body, 'Missing error message about existing user'
212 assert 'This username already exists' in response.body, 'Missing error message about existing user'
@@ -1,119 +1,122 b''
1 from rhodecode.tests import *
1 from rhodecode.tests import *
2 from rhodecode.model.db import User
2 from rhodecode.model.db import User
3 from rhodecode.lib.auth import check_password
3 from rhodecode.lib.auth import check_password
4 from sqlalchemy.orm.exc import NoResultFound
4 from sqlalchemy.orm.exc import NoResultFound
5
5
6 class TestAdminUsersController(TestController):
6 class TestAdminUsersController(TestController):
7
7
8 def test_index(self):
8 def test_index(self):
9 response = self.app.get(url('users'))
9 response = self.app.get(url('users'))
10 # Test response...
10 # Test response...
11
11
12 def test_index_as_xml(self):
12 def test_index_as_xml(self):
13 response = self.app.get(url('formatted_users', format='xml'))
13 response = self.app.get(url('formatted_users', format='xml'))
14
14
15 def test_create(self):
15 def test_create(self):
16 self.log_user()
16 self.log_user()
17 username = 'newtestuser'
17 username = 'newtestuser'
18 password = 'test12'
18 password = 'test12'
19 password_confirmation = password
19 name = 'name'
20 name = 'name'
20 lastname = 'lastname'
21 lastname = 'lastname'
21 email = 'mail@mail.com'
22 email = 'mail@mail.com'
22
23
23 response = self.app.post(url('users'), {'username':username,
24 response = self.app.post(url('users'), {'username':username,
24 'password':password,
25 'password':password,
26 'password_confirmation':password_confirmation,
25 'name':name,
27 'name':name,
26 'active':True,
28 'active':True,
27 'lastname':lastname,
29 'lastname':lastname,
28 'email':email})
30 'email':email})
29
31
30
32
31 assert '''created user %s''' % (username) in response.session['flash'][0], 'No flash message about new user'
33 assert '''created user %s''' % (username) in response.session['flash'][0], 'No flash message about new user'
32
34
33 new_user = self.sa.query(User).filter(User.username == username).one()
35 new_user = self.sa.query(User).filter(User.username == username).one()
34
36
35
37
36 assert new_user.username == username, 'wrong info about username'
38 assert new_user.username == username, 'wrong info about username'
37 assert check_password(password, new_user.password) == True , 'wrong info about password'
39 assert check_password(password, new_user.password) == True , 'wrong info about password'
38 assert new_user.name == name, 'wrong info about name'
40 assert new_user.name == name, 'wrong info about name'
39 assert new_user.lastname == lastname, 'wrong info about lastname'
41 assert new_user.lastname == lastname, 'wrong info about lastname'
40 assert new_user.email == email, 'wrong info about email'
42 assert new_user.email == email, 'wrong info about email'
41
43
42
44
43 response.follow()
45 response.follow()
44 response = response.follow()
46 response = response.follow()
45 assert """edit">newtestuser</a>""" in response.body
47 assert """edit">newtestuser</a>""" in response.body
46
48
47 def test_create_err(self):
49 def test_create_err(self):
48 self.log_user()
50 self.log_user()
49 username = 'new_user'
51 username = 'new_user'
50 password = ''
52 password = ''
51 name = 'name'
53 name = 'name'
52 lastname = 'lastname'
54 lastname = 'lastname'
53 email = 'errmail.com'
55 email = 'errmail.com'
54
56
55 response = self.app.post(url('users'), {'username':username,
57 response = self.app.post(url('users'), {'username':username,
56 'password':password,
58 'password':password,
57 'name':name,
59 'name':name,
58 'active':False,
60 'active':False,
59 'lastname':lastname,
61 'lastname':lastname,
60 'email':email})
62 'email':email})
61
63
62 assert """<span class="error-message">Invalid username</span>""" in response.body
64 assert """<span class="error-message">Invalid username</span>""" in response.body
63 assert """<span class="error-message">Please enter a value</span>""" in response.body
65 assert """<span class="error-message">Please enter a value</span>""" in response.body
64 assert """<span class="error-message">An email address must contain a single @</span>""" in response.body
66 assert """<span class="error-message">An email address must contain a single @</span>""" in response.body
65
67
66 def get_user():
68 def get_user():
67 self.sa.query(User).filter(User.username == username).one()
69 self.sa.query(User).filter(User.username == username).one()
68
70
69 self.assertRaises(NoResultFound, get_user), 'found user in database'
71 self.assertRaises(NoResultFound, get_user), 'found user in database'
70
72
71 def test_new(self):
73 def test_new(self):
72 response = self.app.get(url('new_user'))
74 response = self.app.get(url('new_user'))
73
75
74 def test_new_as_xml(self):
76 def test_new_as_xml(self):
75 response = self.app.get(url('formatted_new_user', format='xml'))
77 response = self.app.get(url('formatted_new_user', format='xml'))
76
78
77 def test_update(self):
79 def test_update(self):
78 response = self.app.put(url('user', id=1))
80 response = self.app.put(url('user', id=1))
79
81
80 def test_update_browser_fakeout(self):
82 def test_update_browser_fakeout(self):
81 response = self.app.post(url('user', id=1), params=dict(_method='put'))
83 response = self.app.post(url('user', id=1), params=dict(_method='put'))
82
84
83 def test_delete(self):
85 def test_delete(self):
84 self.log_user()
86 self.log_user()
85 username = 'newtestuserdeleteme'
87 username = 'newtestuserdeleteme'
86 password = 'test12'
88 password = 'test12'
87 name = 'name'
89 name = 'name'
88 lastname = 'lastname'
90 lastname = 'lastname'
89 email = 'todeletemail@mail.com'
91 email = 'todeletemail@mail.com'
90
92
91 response = self.app.post(url('users'), {'username':username,
93 response = self.app.post(url('users'), {'username':username,
92 'password':password,
94 'password':password,
95 'password_confirmation':password,
93 'name':name,
96 'name':name,
94 'active':True,
97 'active':True,
95 'lastname':lastname,
98 'lastname':lastname,
96 'email':email})
99 'email':email})
97
100
98 response = response.follow()
101 response = response.follow()
99
102
100 new_user = self.sa.query(User).filter(User.username == username).one()
103 new_user = self.sa.query(User).filter(User.username == username).one()
101 response = self.app.delete(url('user', id=new_user.user_id))
104 response = self.app.delete(url('user', id=new_user.user_id))
102
105
103 assert """successfully deleted user""" in response.session['flash'][0], 'No info about user deletion'
106 assert """successfully deleted user""" in response.session['flash'][0], 'No info about user deletion'
104
107
105
108
106 def test_delete_browser_fakeout(self):
109 def test_delete_browser_fakeout(self):
107 response = self.app.post(url('user', id=1), params=dict(_method='delete'))
110 response = self.app.post(url('user', id=1), params=dict(_method='delete'))
108
111
109 def test_show(self):
112 def test_show(self):
110 response = self.app.get(url('user', id=1))
113 response = self.app.get(url('user', id=1))
111
114
112 def test_show_as_xml(self):
115 def test_show_as_xml(self):
113 response = self.app.get(url('formatted_user', id=1, format='xml'))
116 response = self.app.get(url('formatted_user', id=1, format='xml'))
114
117
115 def test_edit(self):
118 def test_edit(self):
116 response = self.app.get(url('edit_user', id=1))
119 response = self.app.get(url('edit_user', id=1))
117
120
118 def test_edit_as_xml(self):
121 def test_edit_as_xml(self):
119 response = self.app.get(url('formatted_edit_user', id=1, format='xml'))
122 response = self.app.get(url('formatted_edit_user', id=1, format='xml'))
General Comments 0
You need to be logged in to leave comments. Login now