##// END OF EJS Templates
Added application settings, are now customizable from database...
marcink -
r350:664a5b8c default
parent child Browse files
Show More
@@ -40,9 +40,8 b' class AdminController(BaseController):'
40
40
41 @HasPermissionAllDecorator('hg.admin')
41 @HasPermissionAllDecorator('hg.admin')
42 def index(self):
42 def index(self):
43 sa = meta.Session
44
43
45 users_log = sa.query(UserLog).order_by(UserLog.action_date.desc())
44 users_log = self.sa.query(UserLog).order_by(UserLog.action_date.desc())
46 p = int(request.params.get('page', 1))
45 p = int(request.params.get('page', 1))
47 c.users_log = Page(users_log, page=p, items_per_page=10)
46 c.users_log = Page(users_log, page=p, items_per_page=10)
48 c.log_data = render('admin/admin_log.html')
47 c.log_data = render('admin/admin_log.html')
@@ -23,19 +23,22 b' settings controller for pylons'
23 @author: marcink
23 @author: marcink
24 """
24 """
25 from formencode import htmlfill
25 from formencode import htmlfill
26 from pylons import request, session, tmpl_context as c, url, app_globals as g
26 from pylons import request, session, tmpl_context as c, url, app_globals as g, \
27 config
27 from pylons.controllers.util import abort, redirect
28 from pylons.controllers.util import abort, redirect
28 from pylons.i18n.translation import _
29 from pylons.i18n.translation import _
29 from pylons_app.lib import helpers as h
30 from pylons_app.lib import helpers as h
30 from pylons_app.lib.auth import LoginRequired, HasPermissionAllDecorator
31 from pylons_app.lib.auth import LoginRequired, HasPermissionAllDecorator
31 from pylons_app.lib.base import BaseController, render
32 from pylons_app.lib.base import BaseController, render
32 from pylons_app.lib.utils import repo2db_mapper, invalidate_cache
33 from pylons_app.lib.utils import repo2db_mapper, invalidate_cache, \
33 from pylons_app.model.db import User, UserLog
34 set_hg_app_config
34 from pylons_app.model.forms import UserForm
35 from pylons_app.model.db import User, UserLog, HgAppSettings
36 from pylons_app.model.forms import UserForm, ApplicationSettingsForm
35 from pylons_app.model.hg_model import HgModel
37 from pylons_app.model.hg_model import HgModel
36 from pylons_app.model.user_model import UserModel
38 from pylons_app.model.user_model import UserModel
37 import formencode
39 import formencode
38 import logging
40 import logging
41 import traceback
39
42
40 log = logging.getLogger(__name__)
43 log = logging.getLogger(__name__)
41
44
@@ -58,7 +61,15 b' class SettingsController(BaseController)'
58 def index(self, format='html'):
61 def index(self, format='html'):
59 """GET /admin/settings: All items in the collection"""
62 """GET /admin/settings: All items in the collection"""
60 # url('admin_settings')
63 # url('admin_settings')
61 return render('admin/settings/settings.html')
64
65 hgsettings = self.sa.query(HgAppSettings).scalar()
66 defaults = hgsettings.__dict__ if hgsettings else {}
67 return htmlfill.render(
68 render('admin/settings/settings.html'),
69 defaults=defaults,
70 encoding="UTF-8",
71 force_defaults=False
72 )
62
73
63 def create(self):
74 def create(self):
64 """POST /admin/settings: Create a new item"""
75 """POST /admin/settings: Create a new item"""
@@ -84,6 +95,45 b' class SettingsController(BaseController)'
84 repo2db_mapper(initial, rm_obsolete)
95 repo2db_mapper(initial, rm_obsolete)
85 invalidate_cache('cached_repo_list')
96 invalidate_cache('cached_repo_list')
86
97
98 if id == 'global':
99
100 application_form = ApplicationSettingsForm()()
101 try:
102 form_result = application_form.to_python(dict(request.POST))
103 title = form_result['app_title']
104 realm = form_result['app_auth_realm']
105
106 try:
107 hgsettings = self.sa.query(HgAppSettings).get(1)
108 hgsettings.app_auth_realm = realm
109 hgsettings.app_title = title
110
111 self.sa.add(hgsettings)
112 self.sa.commit()
113 set_hg_app_config(config)
114 h.flash(_('Updated application settings'),
115 category='success')
116
117 except:
118 log.error(traceback.format_exc())
119 h.flash(_('error occured during chaning application settings'),
120 category='error')
121
122 self.sa.rollback()
123
124
125 except formencode.Invalid as errors:
126 c.form_errors = errors.error_dict
127 return htmlfill.render(
128 render('admin/settings/settings.html'),
129 defaults=errors.value,
130 encoding="UTF-8")
131
132
133
134
135
136
87
137
88 return redirect(url('admin_settings'))
138 return redirect(url('admin_settings'))
89
139
@@ -76,7 +76,6 b' class UsersController(BaseController):'
76 defaults=errors.value,
76 defaults=errors.value,
77 encoding="UTF-8")
77 encoding="UTF-8")
78 except Exception:
78 except Exception:
79
80 h.flash(_('error occured during creation of user') \
79 h.flash(_('error occured during creation of user') \
81 % request.POST.get('username'), category='error')
80 % request.POST.get('username'), category='error')
82 return redirect(url('users'))
81 return redirect(url('users'))
@@ -47,7 +47,10 b' def get_crypt_password(password):'
47 @cache_region('super_short_term', 'cached_user')
47 @cache_region('super_short_term', 'cached_user')
48 def get_user_cached(username):
48 def get_user_cached(username):
49 sa = meta.Session
49 sa = meta.Session
50 try:
50 user = sa.query(User).filter(User.username == username).one()
51 user = sa.query(User).filter(User.username == username).one()
52 finally:
53 meta.Session.remove()
51 return user
54 return user
52
55
53 def authfunc(environ, username, password):
56 def authfunc(environ, username, password):
@@ -89,8 +92,12 b' def set_available_permissions(config):'
89 @param config:
92 @param config:
90 """
93 """
91 log.info('getting information about all available permissions')
94 log.info('getting information about all available permissions')
95 try:
92 sa = meta.Session
96 sa = meta.Session
93 all_perms = sa.query(Permission).all()
97 all_perms = sa.query(Permission).all()
98 finally:
99 meta.Session.remove()
100
94 config['available_permissions'] = [x.permission_name for x in all_perms]
101 config['available_permissions'] = [x.permission_name for x in all_perms]
95
102
96 def set_base_path(config):
103 def set_base_path(config):
@@ -141,6 +148,7 b' def fill_perms(user):'
141 else:
148 else:
142 p = perm.Permission.permission_name
149 p = perm.Permission.permission_name
143 user.permissions['repositories'][perm.Repo2Perm.repository] = p
150 user.permissions['repositories'][perm.Repo2Perm.repository] = p
151 meta.Session.remove()
144 return user
152 return user
145
153
146 def get_user(session):
154 def get_user(session):
@@ -34,7 +34,7 b' sys.path.append(ROOT)'
34 from pylons_app.lib.auth import get_crypt_password
34 from pylons_app.lib.auth import get_crypt_password
35 from pylons_app.model import init_model
35 from pylons_app.model import init_model
36 from pylons_app.model.db import User, Permission, HgAppUi, HgAppSettings
36 from pylons_app.model.db import User, Permission, HgAppUi, HgAppSettings
37 from pylons_app.model.meta import Session, Base
37 from pylons_app.model import meta
38 from sqlalchemy.engine import create_engine
38 from sqlalchemy.engine import create_engine
39 import logging
39 import logging
40
40
@@ -51,7 +51,7 b' class DbManage(object):'
51 dburi = 'sqlite:////%s' % jn(ROOT, self.dbname)
51 dburi = 'sqlite:////%s' % jn(ROOT, self.dbname)
52 engine = create_engine(dburi, echo=log_sql)
52 engine = create_engine(dburi, echo=log_sql)
53 init_model(engine)
53 init_model(engine)
54 self.sa = Session()
54 self.sa = meta.Session
55 self.db_exists = False
55 self.db_exists = False
56
56
57 def check_for_db(self, override):
57 def check_for_db(self, override):
@@ -71,7 +71,7 b' class DbManage(object):'
71 log.info("database exisist and it's going to be destroyed")
71 log.info("database exisist and it's going to be destroyed")
72 if self.db_exists:
72 if self.db_exists:
73 os.remove(jn(ROOT, self.dbname))
73 os.remove(jn(ROOT, self.dbname))
74 Base.metadata.create_all(checkfirst=override)
74 meta.Base.metadata.create_all(checkfirst=override)
75 log.info('Created tables for %s', self.dbname)
75 log.info('Created tables for %s', self.dbname)
76
76
77 def admin_prompt(self):
77 def admin_prompt(self):
@@ -52,8 +52,7 b' class SimpleHg(object):'
52 self.application = application
52 self.application = application
53 self.config = config
53 self.config = config
54 #authenticate this mercurial request using
54 #authenticate this mercurial request using
55 realm = self.config['hg_app_auth_realm']
55 self.authenticate = AuthBasicAuthenticator('', authfunc)
56 self.authenticate = AuthBasicAuthenticator(realm, authfunc)
57
56
58 def __call__(self, environ, start_response):
57 def __call__(self, environ, start_response):
59 if not is_mercurial(environ):
58 if not is_mercurial(environ):
@@ -64,6 +63,7 b' class SimpleHg(object):'
64 #===================================================================
63 #===================================================================
65 username = REMOTE_USER(environ)
64 username = REMOTE_USER(environ)
66 if not username:
65 if not username:
66 self.authenticate.realm = self.config['hg_app_auth_realm']
67 result = self.authenticate(environ)
67 result = self.authenticate(environ)
68 if isinstance(result, str):
68 if isinstance(result, str):
69 AUTH_TYPE.update(environ, 'basic')
69 AUTH_TYPE.update(environ, 'basic')
@@ -208,6 +208,8 b' class SimpleHg(object):'
208 except Exception as e:
208 except Exception as e:
209 sa.rollback()
209 sa.rollback()
210 log.error('could not log user action:%s', str(e))
210 log.error('could not log user action:%s', str(e))
211 finally:
212 meta.Session.remove()
211
213
212 def __invalidate_cache(self, repo_name):
214 def __invalidate_cache(self, repo_name):
213 """we know that some change was made to repositories and we should
215 """we know that some change was made to repositories and we should
@@ -29,7 +29,7 b' import logging'
29 from mercurial import ui, config, hg
29 from mercurial import ui, config, hg
30 from mercurial.error import RepoError
30 from mercurial.error import RepoError
31 from pylons_app.model.db import Repository, User, HgAppUi, HgAppSettings
31 from pylons_app.model.db import Repository, User, HgAppUi, HgAppSettings
32 from pylons_app.model.meta import Session
32 from pylons_app.model import meta
33 log = logging.getLogger(__name__)
33 log = logging.getLogger(__name__)
34
34
35
35
@@ -80,12 +80,21 b' def check_repo(repo_name, base_path, ver'
80
80
81 @cache_region('super_short_term', 'cached_hg_ui')
81 @cache_region('super_short_term', 'cached_hg_ui')
82 def get_hg_ui_cached():
82 def get_hg_ui_cached():
83 sa = Session()
83 try:
84 return sa.query(HgAppUi).all()
84 sa = meta.Session
85 ret = sa.query(HgAppUi).all()
86 finally:
87 meta.Session.remove()
88 return ret
89
85
90
86 def get_hg_settings():
91 def get_hg_settings():
87 sa = Session()
92 try:
93 sa = meta.Session
88 ret = sa.query(HgAppSettings).scalar()
94 ret = sa.query(HgAppSettings).scalar()
95 finally:
96 meta.Session.remove()
97
89 if not ret:
98 if not ret:
90 raise Exception('Could not get application settings !')
99 raise Exception('Could not get application settings !')
91 return ret
100 return ret
@@ -183,7 +192,7 b' def repo2db_mapper(initial_repo_list, re'
183 """
192 """
184 from pylons_app.model.repo_model import RepoModel
193 from pylons_app.model.repo_model import RepoModel
185
194
186 sa = Session()
195 sa = meta.Session
187 user = sa.query(User).filter(User.admin == True).first()
196 user = sa.query(User).filter(User.admin == True).first()
188
197
189 rm = RepoModel()
198 rm = RepoModel()
@@ -208,3 +217,5 b' def repo2db_mapper(initial_repo_list, re'
208 sa.delete(repo)
217 sa.delete(repo)
209 sa.commit()
218 sa.commit()
210
219
220
221 meta.Session.remove()
@@ -267,5 +267,14 b' def RepoSettingsForm(edit=False):'
267 return _RepoForm
267 return _RepoForm
268
268
269
269
270 def ApplicationSettingsForm():
271 class _ApplicationSettingsForm(formencode.Schema):
272 allow_extra_fields = True
273 filter_extra_fields = False
274 app_title = UnicodeString(strip=True, min=3, not_empty=True)
275 app_auth_realm = UnicodeString(strip=True, min=3, not_empty=True)
276
277 return _ApplicationSettingsForm
270
278
271
279
280
@@ -28,7 +28,7 b' from beaker.cache import cache_region'
28 from mercurial import ui
28 from mercurial import ui
29 from mercurial.hgweb.hgwebdir_mod import findrepos
29 from mercurial.hgweb.hgwebdir_mod import findrepos
30 from vcs.exceptions import RepositoryError, VCSError
30 from vcs.exceptions import RepositoryError, VCSError
31 from pylons_app.model.meta import Session
31 from pylons_app.model import meta
32 from pylons_app.model.db import Repository
32 from pylons_app.model.db import Repository
33 from sqlalchemy.orm import joinedload
33 from sqlalchemy.orm import joinedload
34 import logging
34 import logging
@@ -81,7 +81,7 b' class HgModel(object):'
81 :param repos_path: path to directory it could take syntax with
81 :param repos_path: path to directory it could take syntax with
82 * or ** for deep recursive displaying repositories
82 * or ** for deep recursive displaying repositories
83 """
83 """
84 sa = Session()
84 sa = meta.Session()
85 def check_repo_dir(path):
85 def check_repo_dir(path):
86 """
86 """
87 Checks the repository
87 Checks the repository
@@ -122,6 +122,7 b' class HgModel(object):'
122 repos_list[name].contact = dbrepo.user.full_contact
122 repos_list[name].contact = dbrepo.user.full_contact
123 except OSError:
123 except OSError:
124 continue
124 continue
125 meta.Session.remove()
125 return repos_list
126 return repos_list
126
127
127 def get_repos(self):
128 def get_repos(self):
@@ -20,7 +20,7 b''
20 ${h.form(url('admin_setting', id='mapping'),method='put')}
20 ${h.form(url('admin_setting', id='mapping'),method='put')}
21 <table class="table_disp">
21 <table class="table_disp">
22 <tr class="header">
22 <tr class="header">
23 <td colspan="2">${_('Remap andv rescan repositories')}</td>
23 <td colspan="2">${_('Remap and rescan repositories')}</td>
24 </tr>
24 </tr>
25 <tr align="right">
25 <tr align="right">
26 <td><span class="tooltip" tooltip_title="${h.tooltip(_('In case a repository was deleted from filesystem and there are leftovers in the database check this option to scan obsolete data in database and remove it.'))}">
26 <td><span class="tooltip" tooltip_title="${h.tooltip(_('In case a repository was deleted from filesystem and there are leftovers in the database check this option to scan obsolete data in database and remove it.'))}">
@@ -36,11 +36,11 b''
36 </tr>
36 </tr>
37 <tr>
37 <tr>
38 <td>${_('Application name')}</td>
38 <td>${_('Application name')}</td>
39 <td>${h.text('app_title')}</td>
39 <td>${h.text('app_title',size=30)}${self.get_form_error('app_title')}</td>
40 </tr>
40 </tr>
41 <tr>
41 <tr>
42 <td>${_('Realm text')}</td>
42 <td>${_('Realm text')}</td>
43 <td>${h.text('app_auth_realm')}</td>
43 <td>${h.text('app_auth_realm',size=30)}${self.get_form_error('app_auth_realm')}</td>
44 </tr>
44 </tr>
45 <tr>
45 <tr>
46 <td></td>
46 <td></td>
@@ -1,10 +1,10 b''
1 ## -*- coding: utf-8 -*-
1 ## -*- coding: utf-8 -*-
2 <%inherit file="base/base.html"/>
2 <%inherit file="base/base.html"/>
3 <%def name="title()">
3 <%def name="title()">
4 ${c.repos_prefix} Mercurial Repositories
4 ${c.repos_prefix}
5 </%def>
5 </%def>
6 <%def name="breadcrumbs()">
6 <%def name="breadcrumbs()">
7 ${c.repos_prefix} Mercurial Repositories
7 ${c.repos_prefix}
8 </%def>
8 </%def>
9 <%def name="page_nav()">
9 <%def name="page_nav()">
10 ${self.menu('home')}
10 ${self.menu('home')}
@@ -1,10 +1,10 b''
1 ## -*- coding: utf-8 -*-
1 ## -*- coding: utf-8 -*-
2 <%inherit file="base/base.html"/>
2 <%inherit file="base/base.html"/>
3 <%def name="title()">
3 <%def name="title()">
4 ${c.repos_prefix} Mercurial Repositories
4 ${c.repos_prefix}
5 </%def>
5 </%def>
6 <%def name="breadcrumbs()">
6 <%def name="breadcrumbs()">
7 ${c.repos_prefix} Mercurial Repositories
7 ${c.repos_prefix}
8 </%def>
8 </%def>
9 <%def name="page_nav()">
9 <%def name="page_nav()">
10 &nbsp;
10 &nbsp;
General Comments 0
You need to be logged in to leave comments. Login now