##// END OF EJS Templates
settings: fix #3944 add password reset permission
lisaq -
r1034:d1b70f85 default
parent child Browse files
Show More
@@ -0,0 +1,42 b''
1 import logging
2 import datetime
3
4 from sqlalchemy import *
5 from sqlalchemy.exc import DatabaseError
6 from sqlalchemy.orm import relation, backref, class_mapper, joinedload
7 from sqlalchemy.orm.session import Session
8 from sqlalchemy.ext.declarative import declarative_base
9
10 from rhodecode.lib.dbmigrate.migrate import *
11 from rhodecode.lib.dbmigrate.migrate.changeset import *
12 from rhodecode.lib.utils2 import str2bool
13
14 from rhodecode.model.meta import Base
15 from rhodecode.model import meta
16 from rhodecode.lib.dbmigrate.versions import _reset_base, notify
17
18 log = logging.getLogger(__name__)
19
20
21 def upgrade(migrate_engine):
22 """
23 Upgrade operations go here.
24 Don't create your own engine; bind migrate_engine to your metadata
25 """
26 _reset_base(migrate_engine)
27 from rhodecode.lib.dbmigrate.schema import db_4_5_0_0
28
29 fixups(db_4_5_0_0, meta.Session)
30
31 def downgrade(migrate_engine):
32 meta = MetaData()
33 meta.bind = migrate_engine
34
35 def fixups(models, _SESSION):
36 # ** create default permissions ** #
37 from rhodecode.model.permission import PermissionModel
38 PermissionModel(_SESSION()).create_permissions()
39
40 res = PermissionModel(_SESSION()).create_default_user_permissions(
41 models.User.DEFAULT_USER)
42 _SESSION().commit()
@@ -51,7 +51,7 b' PYRAMID_SETTINGS = {}'
51 EXTENSIONS = {}
51 EXTENSIONS = {}
52
52
53 __version__ = ('.'.join((str(each) for each in VERSION[:3])))
53 __version__ = ('.'.join((str(each) for each in VERSION[:3])))
54 __dbversion__ = 60 # defines current db version for migrations
54 __dbversion__ = 61 # defines current db version for migrations
55 __platform__ = platform.system()
55 __platform__ = platform.system()
56 __license__ = 'AGPLv3, and Commercial License'
56 __license__ = 'AGPLv3, and Commercial License'
57 __author__ = 'RhodeCode GmbH'
57 __author__ = 'RhodeCode GmbH'
@@ -81,6 +81,7 b' def get_user(request, apiuser, userid=Op'
81 "usergroup.read",
81 "usergroup.read",
82 "hg.repogroup.create.false",
82 "hg.repogroup.create.false",
83 "hg.create.none",
83 "hg.create.none",
84 "hg.password_reset.enabled",
84 "hg.extern_activate.manual",
85 "hg.extern_activate.manual",
85 "hg.create.write_on_repogroup.false",
86 "hg.create.write_on_repogroup.false",
86 "hg.usergroup.create.false",
87 "hg.usergroup.create.false",
@@ -92,6 +92,7 b' class PermissionsController(BaseControll'
92 self.__load_data()
92 self.__load_data()
93 _form = ApplicationPermissionsForm(
93 _form = ApplicationPermissionsForm(
94 [x[0] for x in c.register_choices],
94 [x[0] for x in c.register_choices],
95 [x[0] for x in c.password_reset_choices],
95 [x[0] for x in c.extern_activate_choices])()
96 [x[0] for x in c.extern_activate_choices])()
96
97
97 try:
98 try:
@@ -2314,6 +2314,10 b' class Permission(Base, BaseModel):'
2314 ('hg.register.manual_activate', _('User Registration with manual account activation')),
2314 ('hg.register.manual_activate', _('User Registration with manual account activation')),
2315 ('hg.register.auto_activate', _('User Registration with automatic account activation')),
2315 ('hg.register.auto_activate', _('User Registration with automatic account activation')),
2316
2316
2317 ('hg.password_reset.enabled', _('Password reset enabled')),
2318 ('hg.password_reset.hidden', _('Password reset hidden')),
2319 ('hg.password_reset.disabled', _('Password reset disabled')),
2320
2317 ('hg.extern_activate.manual', _('Manual activation of external account')),
2321 ('hg.extern_activate.manual', _('Manual activation of external account')),
2318 ('hg.extern_activate.auto', _('Automatic activation of external account')),
2322 ('hg.extern_activate.auto', _('Automatic activation of external account')),
2319
2323
@@ -2332,6 +2336,7 b' class Permission(Base, BaseModel):'
2332 'hg.create.write_on_repogroup.true',
2336 'hg.create.write_on_repogroup.true',
2333 'hg.fork.repository',
2337 'hg.fork.repository',
2334 'hg.register.manual_activate',
2338 'hg.register.manual_activate',
2339 'hg.password_reset.enabled',
2335 'hg.extern_activate.auto',
2340 'hg.extern_activate.auto',
2336 'hg.inherit_default_perms.true',
2341 'hg.inherit_default_perms.true',
2337 ]
2342 ]
@@ -427,7 +427,8 b' def LabsSettingsForm():'
427 return _LabSettingsForm
427 return _LabSettingsForm
428
428
429
429
430 def ApplicationPermissionsForm(register_choices, extern_activate_choices):
430 def ApplicationPermissionsForm(
431 register_choices, password_reset_choices, extern_activate_choices):
431 class _DefaultPermissionsForm(formencode.Schema):
432 class _DefaultPermissionsForm(formencode.Schema):
432 allow_extra_fields = True
433 allow_extra_fields = True
433 filter_extra_fields = True
434 filter_extra_fields = True
@@ -435,6 +436,7 b' def ApplicationPermissionsForm(register_'
435 anonymous = v.StringBoolean(if_missing=False)
436 anonymous = v.StringBoolean(if_missing=False)
436 default_register = v.OneOf(register_choices)
437 default_register = v.OneOf(register_choices)
437 default_register_message = v.UnicodeString()
438 default_register_message = v.UnicodeString()
439 default_password_reset = v.OneOf(password_reset_choices)
438 default_extern_activate = v.OneOf(extern_activate_choices)
440 default_extern_activate = v.OneOf(extern_activate_choices)
439
441
440 return _DefaultPermissionsForm
442 return _DefaultPermissionsForm
@@ -51,8 +51,8 b' class PermissionModel(BaseModel):'
51 'default_user_group_create': None,
51 'default_user_group_create': None,
52 'default_fork_create': None,
52 'default_fork_create': None,
53 'default_inherit_default_permissions': None,
53 'default_inherit_default_permissions': None,
54
55 'default_register': None,
54 'default_register': None,
55 'default_password_reset': None,
56 'default_extern_activate': None,
56 'default_extern_activate': None,
57
57
58 # object permissions below
58 # object permissions below
@@ -85,6 +85,11 b' class PermissionModel(BaseModel):'
85 ('hg.register.manual_activate', translator('Allowed with manual account activation')),
85 ('hg.register.manual_activate', translator('Allowed with manual account activation')),
86 ('hg.register.auto_activate', translator('Allowed with automatic account activation')),]
86 ('hg.register.auto_activate', translator('Allowed with automatic account activation')),]
87
87
88 c_obj.password_reset_choices = [
89 ('hg.password_reset.enabled', translator('Allow password recovery')),
90 ('hg.password_reset.hidden', translator('Hide password recovery link')),
91 ('hg.password_reset.disabled', translator('Disable password recovery')),]
92
88 c_obj.extern_activate_choices = [
93 c_obj.extern_activate_choices = [
89 ('hg.extern_activate.manual', translator('Manual activation of external account')),
94 ('hg.extern_activate.manual', translator('Manual activation of external account')),
90 ('hg.extern_activate.auto', translator('Automatic activation of external account')),]
95 ('hg.extern_activate.auto', translator('Automatic activation of external account')),]
@@ -149,6 +154,9 b' class PermissionModel(BaseModel):'
149 if perm.permission.permission_name.startswith('hg.register.'):
154 if perm.permission.permission_name.startswith('hg.register.'):
150 defaults['default_register' + suffix] = perm.permission.permission_name
155 defaults['default_register' + suffix] = perm.permission.permission_name
151
156
157 if perm.permission.permission_name.startswith('hg.password_reset.'):
158 defaults['default_password_reset' + suffix] = perm.permission.permission_name
159
152 if perm.permission.permission_name.startswith('hg.extern_activate.'):
160 if perm.permission.permission_name.startswith('hg.extern_activate.'):
153 defaults['default_extern_activate' + suffix] = perm.permission.permission_name
161 defaults['default_extern_activate' + suffix] = perm.permission.permission_name
154
162
@@ -182,6 +190,7 b' class PermissionModel(BaseModel):'
182
190
183 # application perms
191 # application perms
184 'default_register': 'hg.register.',
192 'default_register': 'hg.register.',
193 'default_password_reset': 'hg.password_reset.',
185 'default_extern_activate': 'hg.extern_activate.',
194 'default_extern_activate': 'hg.extern_activate.',
186
195
187 # object permissions below
196 # object permissions below
@@ -383,6 +392,7 b' class PermissionModel(BaseModel):'
383 'default_user_group_perm',
392 'default_user_group_perm',
384
393
385 'default_register',
394 'default_register',
395 'default_password_reset',
386 'default_extern_activate'])
396 'default_extern_activate'])
387 self.sa.commit()
397 self.sa.commit()
388 except (DatabaseError,):
398 except (DatabaseError,):
@@ -404,6 +414,7 b' class PermissionModel(BaseModel):'
404 'default_user_group_perm',
414 'default_user_group_perm',
405
415
406 'default_register',
416 'default_register',
417 'default_password_reset',
407 'default_extern_activate'])
418 'default_extern_activate'])
408 self.sa.commit()
419 self.sa.commit()
409 except (DatabaseError,):
420 except (DatabaseError,):
@@ -429,6 +440,7 b' class PermissionModel(BaseModel):'
429 'default_inherit_default_permissions',
440 'default_inherit_default_permissions',
430
441
431 'default_register',
442 'default_register',
443 'default_password_reset',
432 'default_extern_activate'])
444 'default_extern_activate'])
433
445
434 # overwrite default repo permissions
446 # overwrite default repo permissions
@@ -188,6 +188,10 b''
188 line-height: 1.5em;
188 line-height: 1.5em;
189 }
189 }
190 }
190 }
191
192 p.help-block {
193 margin-left: 0;
194 }
191 }
195 }
192
196
193 .user-menu.submenu {
197 .user-menu.submenu {
@@ -29,6 +29,15 b''
29 </div>
29 </div>
30
30
31 <div class="field">
31 <div class="field">
32 <div class="label label-select">
33 <label for="default_password_reset">${_('Password Reset')}:</label>
34 </div>
35 <div class="select">
36 ${h.select('default_password_reset','',c.password_reset_choices)}
37 </div>
38 </div>
39
40 <div class="field">
32 <div class="label label-textarea">
41 <div class="label label-textarea">
33 <label for="default_register_message">${_('Registration Page Message')}:</label>
42 <label for="default_register_message">${_('Registration Page Message')}:</label>
34 </div>
43 </div>
@@ -66,6 +75,7 b''
66 };
75 };
67
76
68 $("#default_register").select2(select2Options);
77 $("#default_register").select2(select2Options);
78 $("#default_password_reset").select2(select2Options);
69 $("#default_extern_activate").select2(select2Options);
79 $("#default_extern_activate").select2(select2Options);
70 });
80 });
71 </script>
81 </script>
@@ -308,7 +308,9 b''
308 <div class="field">
308 <div class="field">
309 <div class="label">
309 <div class="label">
310 <label for="password">${_('Password')}:</label>
310 <label for="password">${_('Password')}:</label>
311 <span class="forgot_password">${h.link_to(_('(Forgot password?)'),h.route_path('reset_password'))}</span>
311 %if h.HasPermissionAny('hg.password_reset.enabled')():
312 <span class="forgot_password">${h.link_to(_('(Forgot password?)'),h.route_path('reset_password'))}</span>
313 %endif
312 </div>
314 </div>
313 <div class="input">
315 <div class="input">
314 ${h.password('password',class_='focus',tabindex=2)}
316 ${h.password('password',class_='focus',tabindex=2)}
@@ -56,9 +56,17 b''
56 ${h.checkbox('remember', value=True, checked=defaults.get('remember'))}
56 ${h.checkbox('remember', value=True, checked=defaults.get('remember'))}
57 <label class="checkbox" for="remember">${_('Remember me')}</label>
57 <label class="checkbox" for="remember">${_('Remember me')}</label>
58
58
59 <p class="links">
59
60 ${h.link_to(_('Forgot your password?'), h.route_path('reset_password'))}
60 %if h.HasPermissionAny('hg.password_reset.enable')():
61 </p>
61 <p class="links">
62 ${h.link_to(_('Forgot your password?'), h.route_path('reset_password'))}
63 </p>
64 %elif h.HasPermissionAny('hg.password_reset.hidden')():
65 <p class="help-block">
66 ${_('Contact an administrator if you have forgotten your password.')}
67 </p>
68 %endif
69
62
70
63 ${h.submit('sign_in', _('Sign In'), class_="btn sign-in")}
71 ${h.submit('sign_in', _('Sign In'), class_="btn sign-in")}
64
72
@@ -28,39 +28,45 b''
28 <img class="sign-in-image" src="${h.asset('images/sign-in.png')}" alt="RhodeCode"/>
28 <img class="sign-in-image" src="${h.asset('images/sign-in.png')}" alt="RhodeCode"/>
29 </div>
29 </div>
30
30
31 <div id="register" class="right-column">
31 %if h.HasPermissionAny('hg.password_reset.disabled')():
32 <!-- login -->
32 <div class="right-column">
33 <div class="sign-in-title">
33 <p>${_('Password reset has been disabled.')}</p>
34 <h1>${_('Reset your Password')}</h1>
35 <h4>${h.link_to(_("Go to the login page to sign in."), request.route_path('login'))}</h4>
36 </div>
34 </div>
37 <div class="inner form">
35 %else:
38 ${h.form(request.route_path('reset_password'), needs_csrf_token=False)}
36 <div id="register" class="right-column">
39 <label for="email">${_('Email Address')}:</label>
37 <!-- login -->
40 ${h.text('email', defaults.get('email'))}
38 <div class="sign-in-title">
41 %if 'email' in errors:
39 <h1>${_('Reset your Password')}</h1>
42 <span class="error-message">${errors.get('email')}</span>
40 <h4>${h.link_to(_("Go to the login page to sign in."), request.route_path('login'))}</h4>
43 <br />
41 </div>
44 %endif
42 <div class="inner form">
45
43 ${h.form(request.route_path('reset_password'), needs_csrf_token=False)}
46 %if captcha_active:
44 <label for="email">${_('Email Address')}:</label>
47 <div class="login-captcha"
45 ${h.text('email', defaults.get('email'))}
48 <label for="email">${_('Captcha')}:</label>
46 %if 'email' in errors:
49 ${h.hidden('recaptcha_field')}
47 <span class="error-message">${errors.get('email')}</span>
50 <div id="recaptcha"></div>
51 %if 'recaptcha_field' in errors:
52 <span class="error-message">${errors.get('recaptcha_field')}</span>
53 <br />
48 <br />
54 %endif
49 %endif
55 </div>
50
56 %endif
51 %if captcha_active:
57
52 <div class="login-captcha"
58 ${h.submit('send', _('Send password reset email'), class_="btn sign-in")}
53 <label for="email">${_('Captcha')}:</label>
59 <div class="activation_msg">${_('Password reset link will be sent to matching email address')}</div>
54 ${h.hidden('recaptcha_field')}
60
55 <div id="recaptcha"></div>
61 ${h.end_form()}
56 %if 'recaptcha_field' in errors:
57 <span class="error-message">${errors.get('recaptcha_field')}</span>
58 <br />
59 %endif
60 </div>
61 %endif
62
63 ${h.submit('send', _('Send password reset email'), class_="btn sign-in")}
64 <div class="activation_msg">${_('Password reset link will be sent to matching email address')}</div>
65
66 ${h.end_form()}
67 </div>
62 </div>
68 </div>
63 </div>
69 %endif
64 </div>
70 </div>
65 </div>
71 </div>
66
72
General Comments 0
You need to be logged in to leave comments. Login now