comparison rhodecode/controllers/admin/repos_groups.py @ 2031:82a88013a3fd

merge 1.3 into stable
author Marcin Kuzminski <marcin@python-works.com>
date Sun, 26 Feb 2012 17:25:09 +0200
parents 87f0800abc7b
children c8a8684efc74
comparison
equal deleted inserted replaced
2005:ab0e122b38a7 2031:82a88013a3fd
1 # -*- coding: utf-8 -*-
2 """
3 rhodecode.controllers.admin.repos_groups
4 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
5
6 Repositories groups controller for RhodeCode
7
8 :created_on: Mar 23, 2010
9 :author: marcink
10 :copyright: (C) 2010-2012 Marcin Kuzminski <marcin@python-works.com>
11 :license: GPLv3, see COPYING for more details.
12 """
13 # This program is free software: you can redistribute it and/or modify
14 # it under the terms of the GNU General Public License as published by
15 # the Free Software Foundation, either version 3 of the License, or
16 # (at your option) any later version.
17 #
18 # This program is distributed in the hope that it will be useful,
19 # but WITHOUT ANY WARRANTY; without even the implied warranty of
20 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 # GNU General Public License for more details.
22 #
23 # You should have received a copy of the GNU General Public License
24 # along with this program. If not, see <http://www.gnu.org/licenses/>.
25
1 import logging 26 import logging
2 import traceback 27 import traceback
3 import formencode 28 import formencode
4 29
5 from formencode import htmlfill 30 from formencode import htmlfill
6 from operator import itemgetter 31
7 32 from pylons import request, tmpl_context as c, url
8 from pylons import request, response, session, tmpl_context as c, url 33 from pylons.controllers.util import redirect
9 from pylons.controllers.util import abort, redirect
10 from pylons.i18n.translation import _ 34 from pylons.i18n.translation import _
11 35
12 from sqlalchemy.exc import IntegrityError 36 from sqlalchemy.exc import IntegrityError
13 37
14 from rhodecode.lib import helpers as h 38 from rhodecode.lib import helpers as h
15 from rhodecode.lib.auth import LoginRequired, HasPermissionAnyDecorator 39 from rhodecode.lib.auth import LoginRequired, HasPermissionAnyDecorator,\
40 HasReposGroupPermissionAnyDecorator
16 from rhodecode.lib.base import BaseController, render 41 from rhodecode.lib.base import BaseController, render
17 from rhodecode.model.db import Group 42 from rhodecode.model.db import RepoGroup
18 from rhodecode.model.repos_group import ReposGroupModel 43 from rhodecode.model.repos_group import ReposGroupModel
19 from rhodecode.model.forms import ReposGroupForm 44 from rhodecode.model.forms import ReposGroupForm
45 from rhodecode.model.meta import Session
46 from rhodecode.model.repo import RepoModel
47 from webob.exc import HTTPInternalServerError
20 48
21 log = logging.getLogger(__name__) 49 log = logging.getLogger(__name__)
22 50
23 51
24 class ReposGroupsController(BaseController): 52 class ReposGroupsController(BaseController):
30 @LoginRequired() 58 @LoginRequired()
31 def __before__(self): 59 def __before__(self):
32 super(ReposGroupsController, self).__before__() 60 super(ReposGroupsController, self).__before__()
33 61
34 def __load_defaults(self): 62 def __load_defaults(self):
35 c.repo_groups = Group.groups_choices() 63 c.repo_groups = RepoGroup.groups_choices()
36 c.repo_groups_choices = map(lambda k: unicode(k[0]), c.repo_groups) 64 c.repo_groups_choices = map(lambda k: unicode(k[0]), c.repo_groups)
37 65
66 repo_model = RepoModel()
67 c.users_array = repo_model.get_users_js()
68 c.users_groups_array = repo_model.get_users_groups_js()
69
38 def __load_data(self, group_id): 70 def __load_data(self, group_id):
39 """ 71 """
40 Load defaults settings for edit, and update 72 Load defaults settings for edit, and update
41 73
42 :param group_id: 74 :param group_id:
43 """ 75 """
44 self.__load_defaults() 76 self.__load_defaults()
45 77
46 repo_group = Group.get(group_id) 78 repo_group = RepoGroup.get(group_id)
47 79
48 data = repo_group.get_dict() 80 data = repo_group.get_dict()
49 81
50 data['group_name'] = repo_group.name 82 data['group_name'] = repo_group.name
83
84 # fill repository users
85 for p in repo_group.repo_group_to_perm:
86 data.update({'u_perm_%s' % p.user.username:
87 p.permission.permission_name})
88
89 # fill repository groups
90 for p in repo_group.users_group_to_perm:
91 data.update({'g_perm_%s' % p.users_group.users_group_name:
92 p.permission.permission_name})
51 93
52 return data 94 return data
53 95
54 @HasPermissionAnyDecorator('hg.admin') 96 @HasPermissionAnyDecorator('hg.admin')
55 def index(self, format='html'): 97 def index(self, format='html'):
56 """GET /repos_groups: All items in the collection""" 98 """GET /repos_groups: All items in the collection"""
57 # url('repos_groups') 99 # url('repos_groups')
58 100 sk = lambda g: g.parents[0].group_name if g.parents else g.group_name
59 sk = lambda g:g.parents[0].group_name if g.parents else g.group_name 101 c.groups = sorted(RepoGroup.query().all(), key=sk)
60 c.groups = sorted(Group.query().all(), key=sk)
61 return render('admin/repos_groups/repos_groups_show.html') 102 return render('admin/repos_groups/repos_groups_show.html')
62 103
63 @HasPermissionAnyDecorator('hg.admin') 104 @HasPermissionAnyDecorator('hg.admin')
64 def create(self): 105 def create(self):
65 """POST /repos_groups: Create a new item""" 106 """POST /repos_groups: Create a new item"""
66 # url('repos_groups') 107 # url('repos_groups')
67 self.__load_defaults() 108 self.__load_defaults()
68 repos_group_model = ReposGroupModel() 109 repos_group_form = ReposGroupForm(available_groups =
69 repos_group_form = ReposGroupForm(available_groups=
70 c.repo_groups_choices)() 110 c.repo_groups_choices)()
71 try: 111 try:
72 form_result = repos_group_form.to_python(dict(request.POST)) 112 form_result = repos_group_form.to_python(dict(request.POST))
73 repos_group_model.create(form_result) 113 ReposGroupModel().create(
114 group_name=form_result['group_name'],
115 group_description=form_result['group_description'],
116 parent=form_result['group_parent_id']
117 )
118 Session.commit()
74 h.flash(_('created repos group %s') \ 119 h.flash(_('created repos group %s') \
75 % form_result['group_name'], category='success') 120 % form_result['group_name'], category='success')
76 #TODO: in futureaction_logger(, '', '', '', self.sa) 121 #TODO: in futureaction_logger(, '', '', '', self.sa)
77 except formencode.Invalid, errors: 122 except formencode.Invalid, errors:
78 123
86 log.error(traceback.format_exc()) 131 log.error(traceback.format_exc())
87 h.flash(_('error occurred during creation of repos group %s') \ 132 h.flash(_('error occurred during creation of repos group %s') \
88 % request.POST.get('group_name'), category='error') 133 % request.POST.get('group_name'), category='error')
89 134
90 return redirect(url('repos_groups')) 135 return redirect(url('repos_groups'))
91
92 136
93 @HasPermissionAnyDecorator('hg.admin') 137 @HasPermissionAnyDecorator('hg.admin')
94 def new(self, format='html'): 138 def new(self, format='html'):
95 """GET /repos_groups/new: Form to create a new item""" 139 """GET /repos_groups/new: Form to create a new item"""
96 # url('new_repos_group') 140 # url('new_repos_group')
106 # h.form(url('repos_group', id=ID), 150 # h.form(url('repos_group', id=ID),
107 # method='put') 151 # method='put')
108 # url('repos_group', id=ID) 152 # url('repos_group', id=ID)
109 153
110 self.__load_defaults() 154 self.__load_defaults()
111 c.repos_group = Group.get(id) 155 c.repos_group = RepoGroup.get(id)
112 156
113 repos_group_model = ReposGroupModel() 157 repos_group_form = ReposGroupForm(
114 repos_group_form = ReposGroupForm(edit=True, 158 edit=True,
115 old_data=c.repos_group.get_dict(), 159 old_data=c.repos_group.get_dict(),
116 available_groups= 160 available_groups=c.repo_groups_choices
117 c.repo_groups_choices)() 161 )()
118 try: 162 try:
119 form_result = repos_group_form.to_python(dict(request.POST)) 163 form_result = repos_group_form.to_python(dict(request.POST))
120 repos_group_model.update(id, form_result) 164 ReposGroupModel().update(id, form_result)
165 Session.commit()
121 h.flash(_('updated repos group %s') \ 166 h.flash(_('updated repos group %s') \
122 % form_result['group_name'], category='success') 167 % form_result['group_name'], category='success')
123 #TODO: in futureaction_logger(, '', '', '', self.sa) 168 #TODO: in futureaction_logger(, '', '', '', self.sa)
124 except formencode.Invalid, errors: 169 except formencode.Invalid, errors:
125 170
133 log.error(traceback.format_exc()) 178 log.error(traceback.format_exc())
134 h.flash(_('error occurred during update of repos group %s') \ 179 h.flash(_('error occurred during update of repos group %s') \
135 % request.POST.get('group_name'), category='error') 180 % request.POST.get('group_name'), category='error')
136 181
137 return redirect(url('repos_groups')) 182 return redirect(url('repos_groups'))
138
139 183
140 @HasPermissionAnyDecorator('hg.admin') 184 @HasPermissionAnyDecorator('hg.admin')
141 def delete(self, id): 185 def delete(self, id):
142 """DELETE /repos_groups/id: Delete an existing item""" 186 """DELETE /repos_groups/id: Delete an existing item"""
143 # Forms posted to this method should contain a hidden field: 187 # Forms posted to this method should contain a hidden field:
145 # Or using helpers: 189 # Or using helpers:
146 # h.form(url('repos_group', id=ID), 190 # h.form(url('repos_group', id=ID),
147 # method='delete') 191 # method='delete')
148 # url('repos_group', id=ID) 192 # url('repos_group', id=ID)
149 193
150 repos_group_model = ReposGroupModel() 194 gr = RepoGroup.get(id)
151 gr = Group.get(id)
152 repos = gr.repositories.all() 195 repos = gr.repositories.all()
153 if repos: 196 if repos:
154 h.flash(_('This group contains %s repositores and cannot be ' 197 h.flash(_('This group contains %s repositores and cannot be '
155 'deleted' % len(repos)), 198 'deleted' % len(repos)),
156 category='error') 199 category='error')
157 return redirect(url('repos_groups')) 200 return redirect(url('repos_groups'))
158 201
159 try: 202 try:
160 repos_group_model.delete(id) 203 ReposGroupModel().delete(id)
204 Session.commit()
161 h.flash(_('removed repos group %s' % gr.group_name), category='success') 205 h.flash(_('removed repos group %s' % gr.group_name), category='success')
162 #TODO: in future action_logger(, '', '', '', self.sa) 206 #TODO: in future action_logger(, '', '', '', self.sa)
163 except IntegrityError, e: 207 except IntegrityError, e:
164 if e.message.find('groups_group_parent_id_fkey'): 208 if e.message.find('groups_group_parent_id_fkey') != -1:
165 log.error(traceback.format_exc()) 209 log.error(traceback.format_exc())
166 h.flash(_('Cannot delete this group it still contains ' 210 h.flash(_('Cannot delete this group it still contains '
167 'subgroups'), 211 'subgroups'),
168 category='warning') 212 category='warning')
169 else: 213 else:
176 h.flash(_('error occurred during deletion of repos ' 220 h.flash(_('error occurred during deletion of repos '
177 'group %s' % gr.group_name), category='error') 221 'group %s' % gr.group_name), category='error')
178 222
179 return redirect(url('repos_groups')) 223 return redirect(url('repos_groups'))
180 224
225 @HasReposGroupPermissionAnyDecorator('group.admin')
226 def delete_repos_group_user_perm(self, group_name):
227 """
228 DELETE an existing repositories group permission user
229
230 :param group_name:
231 """
232
233 try:
234 ReposGroupModel().revoke_user_permission(
235 repos_group=group_name, user=request.POST['user_id']
236 )
237 Session.commit()
238 except Exception:
239 log.error(traceback.format_exc())
240 h.flash(_('An error occurred during deletion of group user'),
241 category='error')
242 raise HTTPInternalServerError()
243
244 @HasReposGroupPermissionAnyDecorator('group.admin')
245 def delete_repos_group_users_group_perm(self, group_name):
246 """
247 DELETE an existing repositories group permission users group
248
249 :param group_name:
250 """
251
252 try:
253 ReposGroupModel().revoke_users_group_permission(
254 repos_group=group_name,
255 group_name=request.POST['users_group_id']
256 )
257 Session.commit()
258 except Exception:
259 log.error(traceback.format_exc())
260 h.flash(_('An error occurred during deletion of group'
261 ' users groups'),
262 category='error')
263 raise HTTPInternalServerError()
264
181 def show_by_name(self, group_name): 265 def show_by_name(self, group_name):
182 id_ = Group.get_by_group_name(group_name).group_id 266 id_ = RepoGroup.get_by_group_name(group_name).group_id
183 return self.show(id_) 267 return self.show(id_)
184 268
269 @HasReposGroupPermissionAnyDecorator('group.read', 'group.write',
270 'group.admin')
185 def show(self, id, format='html'): 271 def show(self, id, format='html'):
186 """GET /repos_groups/id: Show a specific item""" 272 """GET /repos_groups/id: Show a specific item"""
187 # url('repos_group', id=ID) 273 # url('repos_group', id=ID)
188 274
189 c.group = Group.get(id) 275 c.group = RepoGroup.get(id)
190 276
191 if c.group: 277 if c.group:
192 c.group_repos = c.group.repositories.all() 278 c.group_repos = c.group.repositories.all()
193 else: 279 else:
194 return redirect(url('home')) 280 return redirect(url('home'))
199 285
200 c.repos_list = c.cached_repo_list 286 c.repos_list = c.cached_repo_list
201 287
202 c.repo_cnt = 0 288 c.repo_cnt = 0
203 289
204 c.groups = self.sa.query(Group).order_by(Group.group_name)\ 290 c.groups = self.sa.query(RepoGroup).order_by(RepoGroup.group_name)\
205 .filter(Group.group_parent_id == id).all() 291 .filter(RepoGroup.group_parent_id == id).all()
206 292
207 return render('admin/repos_groups/repos_groups.html') 293 return render('admin/repos_groups/repos_groups.html')
208 294
209 @HasPermissionAnyDecorator('hg.admin') 295 @HasPermissionAnyDecorator('hg.admin')
210 def edit(self, id, format='html'): 296 def edit(self, id, format='html'):
211 """GET /repos_groups/id/edit: Form to edit an existing item""" 297 """GET /repos_groups/id/edit: Form to edit an existing item"""
212 # url('edit_repos_group', id=ID) 298 # url('edit_repos_group', id=ID)
213 299
214 id_ = int(id) 300 id_ = int(id)
215 301
216 c.repos_group = Group.get(id_) 302 c.repos_group = RepoGroup.get(id_)
217 defaults = self.__load_data(id_) 303 defaults = self.__load_data(id_)
218 304
219 # we need to exclude this group from the group list for editing 305 # we need to exclude this group from the group list for editing
220 c.repo_groups = filter(lambda x:x[0] != id_, c.repo_groups) 306 c.repo_groups = filter(lambda x: x[0] != id_, c.repo_groups)
221 307
222 return htmlfill.render( 308 return htmlfill.render(
223 render('admin/repos_groups/repos_groups_edit.html'), 309 render('admin/repos_groups/repos_groups_edit.html'),
224 defaults=defaults, 310 defaults=defaults,
225 encoding="UTF-8", 311 encoding="UTF-8",
226 force_defaults=False 312 force_defaults=False
227 ) 313 )
228
229