##// END OF EJS Templates
repositories: handle vcs backend unavailable correctly in advanced settings.
marcink -
r3382:f260e60e default
parent child Browse files
Show More
@@ -1,314 +1,316 b''
1 # -*- coding: utf-8 -*-
1 # -*- coding: utf-8 -*-
2
2
3 # Copyright (C) 2011-2019 RhodeCode GmbH
3 # Copyright (C) 2011-2019 RhodeCode GmbH
4 #
4 #
5 # This program is free software: you can redistribute it and/or modify
5 # This program is free software: you can redistribute it and/or modify
6 # it under the terms of the GNU Affero General Public License, version 3
6 # it under the terms of the GNU Affero General Public License, version 3
7 # (only), as published by the Free Software Foundation.
7 # (only), as published by the Free Software Foundation.
8 #
8 #
9 # This program is distributed in the hope that it will be useful,
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 # GNU General Public License for more details.
12 # GNU General Public License for more details.
13 #
13 #
14 # You should have received a copy of the GNU Affero General Public License
14 # You should have received a copy of the GNU Affero General Public License
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
16 #
16 #
17 # This program is dual-licensed. If you wish to learn more about the
17 # This program is dual-licensed. If you wish to learn more about the
18 # RhodeCode Enterprise Edition, including its added features, Support services,
18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20
20
21 import logging
21 import logging
22
22
23 from pyramid.view import view_config
23 from pyramid.view import view_config
24 from pyramid.httpexceptions import HTTPFound
24 from pyramid.httpexceptions import HTTPFound
25
25
26 from rhodecode import events
26 from rhodecode import events
27 from rhodecode.apps._base import RepoAppView
27 from rhodecode.apps._base import RepoAppView
28 from rhodecode.lib import helpers as h
28 from rhodecode.lib import helpers as h
29 from rhodecode.lib import audit_logger
29 from rhodecode.lib import audit_logger
30 from rhodecode.lib.auth import (
30 from rhodecode.lib.auth import (
31 LoginRequired, HasRepoPermissionAnyDecorator, CSRFRequired,
31 LoginRequired, HasRepoPermissionAnyDecorator, CSRFRequired,
32 HasRepoPermissionAny)
32 HasRepoPermissionAny)
33 from rhodecode.lib.exceptions import AttachedForksError, AttachedPullRequestsError
33 from rhodecode.lib.exceptions import AttachedForksError, AttachedPullRequestsError
34 from rhodecode.lib.utils2 import safe_int
34 from rhodecode.lib.utils2 import safe_int
35 from rhodecode.lib.vcs import RepositoryError
35 from rhodecode.lib.vcs import RepositoryError
36 from rhodecode.model.db import Session, UserFollowing, User, Repository
36 from rhodecode.model.db import Session, UserFollowing, User, Repository
37 from rhodecode.model.repo import RepoModel
37 from rhodecode.model.repo import RepoModel
38 from rhodecode.model.scm import ScmModel
38 from rhodecode.model.scm import ScmModel
39
39
40 log = logging.getLogger(__name__)
40 log = logging.getLogger(__name__)
41
41
42
42
43 class RepoSettingsView(RepoAppView):
43 class RepoSettingsView(RepoAppView):
44
44
45 def load_default_context(self):
45 def load_default_context(self):
46 c = self._get_local_tmpl_context()
46 c = self._get_local_tmpl_context()
47 return c
47 return c
48
48
49 def _get_users_with_permissions(self):
49 def _get_users_with_permissions(self):
50 user_permissions = {}
50 user_permissions = {}
51 for perm in self.db_repo.permissions():
51 for perm in self.db_repo.permissions():
52 user_permissions[perm.user_id] = perm
52 user_permissions[perm.user_id] = perm
53
53
54 return user_permissions
54 return user_permissions
55
55
56 @LoginRequired()
56 @LoginRequired()
57 @HasRepoPermissionAnyDecorator('repository.admin')
57 @HasRepoPermissionAnyDecorator('repository.admin')
58 @view_config(
58 @view_config(
59 route_name='edit_repo_advanced', request_method='GET',
59 route_name='edit_repo_advanced', request_method='GET',
60 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
60 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
61 def edit_advanced(self):
61 def edit_advanced(self):
62 c = self.load_default_context()
62 c = self.load_default_context()
63 c.active = 'advanced'
63 c.active = 'advanced'
64
64
65 c.default_user_id = User.get_default_user().user_id
65 c.default_user_id = User.get_default_user().user_id
66 c.in_public_journal = UserFollowing.query() \
66 c.in_public_journal = UserFollowing.query() \
67 .filter(UserFollowing.user_id == c.default_user_id) \
67 .filter(UserFollowing.user_id == c.default_user_id) \
68 .filter(UserFollowing.follows_repository == self.db_repo).scalar()
68 .filter(UserFollowing.follows_repository == self.db_repo).scalar()
69
69
70 c.has_origin_repo_read_perm = False
70 c.has_origin_repo_read_perm = False
71 if self.db_repo.fork:
71 if self.db_repo.fork:
72 c.has_origin_repo_read_perm = h.HasRepoPermissionAny(
72 c.has_origin_repo_read_perm = h.HasRepoPermissionAny(
73 'repository.write', 'repository.read', 'repository.admin')(
73 'repository.write', 'repository.read', 'repository.admin')(
74 self.db_repo.fork.repo_name, 'repo set as fork page')
74 self.db_repo.fork.repo_name, 'repo set as fork page')
75
75
76 c.ver_info_dict = self.rhodecode_vcs_repo.get_hooks_info()
77
76 return self._get_template_context(c)
78 return self._get_template_context(c)
77
79
78 @LoginRequired()
80 @LoginRequired()
79 @HasRepoPermissionAnyDecorator('repository.admin')
81 @HasRepoPermissionAnyDecorator('repository.admin')
80 @CSRFRequired()
82 @CSRFRequired()
81 @view_config(
83 @view_config(
82 route_name='edit_repo_advanced_archive', request_method='POST',
84 route_name='edit_repo_advanced_archive', request_method='POST',
83 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
85 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
84 def edit_advanced_archive(self):
86 def edit_advanced_archive(self):
85 """
87 """
86 Archives the repository. It will become read-only, and not visible in search
88 Archives the repository. It will become read-only, and not visible in search
87 or other queries. But still visible for super-admins.
89 or other queries. But still visible for super-admins.
88 """
90 """
89
91
90 _ = self.request.translate
92 _ = self.request.translate
91
93
92 try:
94 try:
93 old_data = self.db_repo.get_api_data()
95 old_data = self.db_repo.get_api_data()
94 RepoModel().archive(self.db_repo)
96 RepoModel().archive(self.db_repo)
95
97
96 repo = audit_logger.RepoWrap(repo_id=None, repo_name=self.db_repo.repo_name)
98 repo = audit_logger.RepoWrap(repo_id=None, repo_name=self.db_repo.repo_name)
97 audit_logger.store_web(
99 audit_logger.store_web(
98 'repo.archive', action_data={'old_data': old_data},
100 'repo.archive', action_data={'old_data': old_data},
99 user=self._rhodecode_user, repo=repo)
101 user=self._rhodecode_user, repo=repo)
100
102
101 ScmModel().mark_for_invalidation(self.db_repo_name, delete=True)
103 ScmModel().mark_for_invalidation(self.db_repo_name, delete=True)
102 h.flash(
104 h.flash(
103 _('Archived repository `%s`') % self.db_repo_name,
105 _('Archived repository `%s`') % self.db_repo_name,
104 category='success')
106 category='success')
105 Session().commit()
107 Session().commit()
106 except Exception:
108 except Exception:
107 log.exception("Exception during archiving of repository")
109 log.exception("Exception during archiving of repository")
108 h.flash(_('An error occurred during archiving of `%s`')
110 h.flash(_('An error occurred during archiving of `%s`')
109 % self.db_repo_name, category='error')
111 % self.db_repo_name, category='error')
110 # redirect to advanced for more deletion options
112 # redirect to advanced for more deletion options
111 raise HTTPFound(
113 raise HTTPFound(
112 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name,
114 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name,
113 _anchor='advanced-archive'))
115 _anchor='advanced-archive'))
114
116
115 # flush permissions for all users defined in permissions
117 # flush permissions for all users defined in permissions
116 affected_user_ids = self._get_users_with_permissions().keys()
118 affected_user_ids = self._get_users_with_permissions().keys()
117 events.trigger(events.UserPermissionsChange(affected_user_ids))
119 events.trigger(events.UserPermissionsChange(affected_user_ids))
118
120
119 raise HTTPFound(h.route_path('home'))
121 raise HTTPFound(h.route_path('home'))
120
122
121 @LoginRequired()
123 @LoginRequired()
122 @HasRepoPermissionAnyDecorator('repository.admin')
124 @HasRepoPermissionAnyDecorator('repository.admin')
123 @CSRFRequired()
125 @CSRFRequired()
124 @view_config(
126 @view_config(
125 route_name='edit_repo_advanced_delete', request_method='POST',
127 route_name='edit_repo_advanced_delete', request_method='POST',
126 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
128 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
127 def edit_advanced_delete(self):
129 def edit_advanced_delete(self):
128 """
130 """
129 Deletes the repository, or shows warnings if deletion is not possible
131 Deletes the repository, or shows warnings if deletion is not possible
130 because of attached forks or other errors.
132 because of attached forks or other errors.
131 """
133 """
132 _ = self.request.translate
134 _ = self.request.translate
133 handle_forks = self.request.POST.get('forks', None)
135 handle_forks = self.request.POST.get('forks', None)
134 if handle_forks == 'detach_forks':
136 if handle_forks == 'detach_forks':
135 handle_forks = 'detach'
137 handle_forks = 'detach'
136 elif handle_forks == 'delete_forks':
138 elif handle_forks == 'delete_forks':
137 handle_forks = 'delete'
139 handle_forks = 'delete'
138
140
139 try:
141 try:
140 old_data = self.db_repo.get_api_data()
142 old_data = self.db_repo.get_api_data()
141 RepoModel().delete(self.db_repo, forks=handle_forks)
143 RepoModel().delete(self.db_repo, forks=handle_forks)
142
144
143 _forks = self.db_repo.forks.count()
145 _forks = self.db_repo.forks.count()
144 if _forks and handle_forks:
146 if _forks and handle_forks:
145 if handle_forks == 'detach_forks':
147 if handle_forks == 'detach_forks':
146 h.flash(_('Detached %s forks') % _forks, category='success')
148 h.flash(_('Detached %s forks') % _forks, category='success')
147 elif handle_forks == 'delete_forks':
149 elif handle_forks == 'delete_forks':
148 h.flash(_('Deleted %s forks') % _forks, category='success')
150 h.flash(_('Deleted %s forks') % _forks, category='success')
149
151
150 repo = audit_logger.RepoWrap(repo_id=None, repo_name=self.db_repo.repo_name)
152 repo = audit_logger.RepoWrap(repo_id=None, repo_name=self.db_repo.repo_name)
151 audit_logger.store_web(
153 audit_logger.store_web(
152 'repo.delete', action_data={'old_data': old_data},
154 'repo.delete', action_data={'old_data': old_data},
153 user=self._rhodecode_user, repo=repo)
155 user=self._rhodecode_user, repo=repo)
154
156
155 ScmModel().mark_for_invalidation(self.db_repo_name, delete=True)
157 ScmModel().mark_for_invalidation(self.db_repo_name, delete=True)
156 h.flash(
158 h.flash(
157 _('Deleted repository `%s`') % self.db_repo_name,
159 _('Deleted repository `%s`') % self.db_repo_name,
158 category='success')
160 category='success')
159 Session().commit()
161 Session().commit()
160 except AttachedForksError:
162 except AttachedForksError:
161 repo_advanced_url = h.route_path(
163 repo_advanced_url = h.route_path(
162 'edit_repo_advanced', repo_name=self.db_repo_name,
164 'edit_repo_advanced', repo_name=self.db_repo_name,
163 _anchor='advanced-delete')
165 _anchor='advanced-delete')
164 delete_anchor = h.link_to(_('detach or delete'), repo_advanced_url)
166 delete_anchor = h.link_to(_('detach or delete'), repo_advanced_url)
165 h.flash(_('Cannot delete `{repo}` it still contains attached forks. '
167 h.flash(_('Cannot delete `{repo}` it still contains attached forks. '
166 'Try using {delete_or_detach} option.')
168 'Try using {delete_or_detach} option.')
167 .format(repo=self.db_repo_name, delete_or_detach=delete_anchor),
169 .format(repo=self.db_repo_name, delete_or_detach=delete_anchor),
168 category='warning')
170 category='warning')
169
171
170 # redirect to advanced for forks handle action ?
172 # redirect to advanced for forks handle action ?
171 raise HTTPFound(repo_advanced_url)
173 raise HTTPFound(repo_advanced_url)
172
174
173 except AttachedPullRequestsError:
175 except AttachedPullRequestsError:
174 repo_advanced_url = h.route_path(
176 repo_advanced_url = h.route_path(
175 'edit_repo_advanced', repo_name=self.db_repo_name,
177 'edit_repo_advanced', repo_name=self.db_repo_name,
176 _anchor='advanced-delete')
178 _anchor='advanced-delete')
177 attached_prs = len(self.db_repo.pull_requests_source +
179 attached_prs = len(self.db_repo.pull_requests_source +
178 self.db_repo.pull_requests_target)
180 self.db_repo.pull_requests_target)
179 h.flash(
181 h.flash(
180 _('Cannot delete `{repo}` it still contains {num} attached pull requests. '
182 _('Cannot delete `{repo}` it still contains {num} attached pull requests. '
181 'Consider archiving the repository instead.').format(
183 'Consider archiving the repository instead.').format(
182 repo=self.db_repo_name, num=attached_prs), category='warning')
184 repo=self.db_repo_name, num=attached_prs), category='warning')
183
185
184 # redirect to advanced for forks handle action ?
186 # redirect to advanced for forks handle action ?
185 raise HTTPFound(repo_advanced_url)
187 raise HTTPFound(repo_advanced_url)
186
188
187 except Exception:
189 except Exception:
188 log.exception("Exception during deletion of repository")
190 log.exception("Exception during deletion of repository")
189 h.flash(_('An error occurred during deletion of `%s`')
191 h.flash(_('An error occurred during deletion of `%s`')
190 % self.db_repo_name, category='error')
192 % self.db_repo_name, category='error')
191 # redirect to advanced for more deletion options
193 # redirect to advanced for more deletion options
192 raise HTTPFound(
194 raise HTTPFound(
193 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name,
195 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name,
194 _anchor='advanced-delete'))
196 _anchor='advanced-delete'))
195
197
196 raise HTTPFound(h.route_path('home'))
198 raise HTTPFound(h.route_path('home'))
197
199
198 @LoginRequired()
200 @LoginRequired()
199 @HasRepoPermissionAnyDecorator('repository.admin')
201 @HasRepoPermissionAnyDecorator('repository.admin')
200 @CSRFRequired()
202 @CSRFRequired()
201 @view_config(
203 @view_config(
202 route_name='edit_repo_advanced_journal', request_method='POST',
204 route_name='edit_repo_advanced_journal', request_method='POST',
203 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
205 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
204 def edit_advanced_journal(self):
206 def edit_advanced_journal(self):
205 """
207 """
206 Set's this repository to be visible in public journal,
208 Set's this repository to be visible in public journal,
207 in other words making default user to follow this repo
209 in other words making default user to follow this repo
208 """
210 """
209 _ = self.request.translate
211 _ = self.request.translate
210
212
211 try:
213 try:
212 user_id = User.get_default_user().user_id
214 user_id = User.get_default_user().user_id
213 ScmModel().toggle_following_repo(self.db_repo.repo_id, user_id)
215 ScmModel().toggle_following_repo(self.db_repo.repo_id, user_id)
214 h.flash(_('Updated repository visibility in public journal'),
216 h.flash(_('Updated repository visibility in public journal'),
215 category='success')
217 category='success')
216 Session().commit()
218 Session().commit()
217 except Exception:
219 except Exception:
218 h.flash(_('An error occurred during setting this '
220 h.flash(_('An error occurred during setting this '
219 'repository in public journal'),
221 'repository in public journal'),
220 category='error')
222 category='error')
221
223
222 raise HTTPFound(
224 raise HTTPFound(
223 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name))
225 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name))
224
226
225 @LoginRequired()
227 @LoginRequired()
226 @HasRepoPermissionAnyDecorator('repository.admin')
228 @HasRepoPermissionAnyDecorator('repository.admin')
227 @CSRFRequired()
229 @CSRFRequired()
228 @view_config(
230 @view_config(
229 route_name='edit_repo_advanced_fork', request_method='POST',
231 route_name='edit_repo_advanced_fork', request_method='POST',
230 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
232 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
231 def edit_advanced_fork(self):
233 def edit_advanced_fork(self):
232 """
234 """
233 Mark given repository as a fork of another
235 Mark given repository as a fork of another
234 """
236 """
235 _ = self.request.translate
237 _ = self.request.translate
236
238
237 new_fork_id = safe_int(self.request.POST.get('id_fork_of'))
239 new_fork_id = safe_int(self.request.POST.get('id_fork_of'))
238
240
239 # valid repo, re-check permissions
241 # valid repo, re-check permissions
240 if new_fork_id:
242 if new_fork_id:
241 repo = Repository.get(new_fork_id)
243 repo = Repository.get(new_fork_id)
242 # ensure we have at least read access to the repo we mark
244 # ensure we have at least read access to the repo we mark
243 perm_check = HasRepoPermissionAny(
245 perm_check = HasRepoPermissionAny(
244 'repository.read', 'repository.write', 'repository.admin')
246 'repository.read', 'repository.write', 'repository.admin')
245
247
246 if repo and perm_check(repo_name=repo.repo_name):
248 if repo and perm_check(repo_name=repo.repo_name):
247 new_fork_id = repo.repo_id
249 new_fork_id = repo.repo_id
248 else:
250 else:
249 new_fork_id = None
251 new_fork_id = None
250
252
251 try:
253 try:
252 repo = ScmModel().mark_as_fork(
254 repo = ScmModel().mark_as_fork(
253 self.db_repo_name, new_fork_id, self._rhodecode_user.user_id)
255 self.db_repo_name, new_fork_id, self._rhodecode_user.user_id)
254 fork = repo.fork.repo_name if repo.fork else _('Nothing')
256 fork = repo.fork.repo_name if repo.fork else _('Nothing')
255 Session().commit()
257 Session().commit()
256 h.flash(
258 h.flash(
257 _('Marked repo %s as fork of %s') % (self.db_repo_name, fork),
259 _('Marked repo %s as fork of %s') % (self.db_repo_name, fork),
258 category='success')
260 category='success')
259 except RepositoryError as e:
261 except RepositoryError as e:
260 log.exception("Repository Error occurred")
262 log.exception("Repository Error occurred")
261 h.flash(str(e), category='error')
263 h.flash(str(e), category='error')
262 except Exception:
264 except Exception:
263 log.exception("Exception while editing fork")
265 log.exception("Exception while editing fork")
264 h.flash(_('An error occurred during this operation'),
266 h.flash(_('An error occurred during this operation'),
265 category='error')
267 category='error')
266
268
267 raise HTTPFound(
269 raise HTTPFound(
268 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name))
270 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name))
269
271
270 @LoginRequired()
272 @LoginRequired()
271 @HasRepoPermissionAnyDecorator('repository.admin')
273 @HasRepoPermissionAnyDecorator('repository.admin')
272 @CSRFRequired()
274 @CSRFRequired()
273 @view_config(
275 @view_config(
274 route_name='edit_repo_advanced_locking', request_method='POST',
276 route_name='edit_repo_advanced_locking', request_method='POST',
275 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
277 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
276 def edit_advanced_locking(self):
278 def edit_advanced_locking(self):
277 """
279 """
278 Toggle locking of repository
280 Toggle locking of repository
279 """
281 """
280 _ = self.request.translate
282 _ = self.request.translate
281 set_lock = self.request.POST.get('set_lock')
283 set_lock = self.request.POST.get('set_lock')
282 set_unlock = self.request.POST.get('set_unlock')
284 set_unlock = self.request.POST.get('set_unlock')
283
285
284 try:
286 try:
285 if set_lock:
287 if set_lock:
286 Repository.lock(self.db_repo, self._rhodecode_user.user_id,
288 Repository.lock(self.db_repo, self._rhodecode_user.user_id,
287 lock_reason=Repository.LOCK_WEB)
289 lock_reason=Repository.LOCK_WEB)
288 h.flash(_('Locked repository'), category='success')
290 h.flash(_('Locked repository'), category='success')
289 elif set_unlock:
291 elif set_unlock:
290 Repository.unlock(self.db_repo)
292 Repository.unlock(self.db_repo)
291 h.flash(_('Unlocked repository'), category='success')
293 h.flash(_('Unlocked repository'), category='success')
292 except Exception as e:
294 except Exception as e:
293 log.exception("Exception during unlocking")
295 log.exception("Exception during unlocking")
294 h.flash(_('An error occurred during unlocking'), category='error')
296 h.flash(_('An error occurred during unlocking'), category='error')
295
297
296 raise HTTPFound(
298 raise HTTPFound(
297 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name))
299 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name))
298
300
299 @LoginRequired()
301 @LoginRequired()
300 @HasRepoPermissionAnyDecorator('repository.admin')
302 @HasRepoPermissionAnyDecorator('repository.admin')
301 @view_config(
303 @view_config(
302 route_name='edit_repo_advanced_hooks', request_method='GET',
304 route_name='edit_repo_advanced_hooks', request_method='GET',
303 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
305 renderer='rhodecode:templates/admin/repos/repo_edit.mako')
304 def edit_advanced_install_hooks(self):
306 def edit_advanced_install_hooks(self):
305 """
307 """
306 Install Hooks for repository
308 Install Hooks for repository
307 """
309 """
308 _ = self.request.translate
310 _ = self.request.translate
309 self.load_default_context()
311 self.load_default_context()
310 self.rhodecode_vcs_repo.install_hooks(force=True)
312 self.rhodecode_vcs_repo.install_hooks(force=True)
311 h.flash(_('installed updated hooks into this repository'),
313 h.flash(_('installed updated hooks into this repository'),
312 category='success')
314 category='success')
313 raise HTTPFound(
315 raise HTTPFound(
314 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name))
316 h.route_path('edit_repo_advanced', repo_name=self.db_repo_name))
@@ -1,286 +1,289 b''
1 <%namespace name="base" file="/base/base.mako"/>
1 <%namespace name="base" file="/base/base.mako"/>
2
2
3 <%
3 <%
4 elems = [
4 elems = [
5 (_('Repository ID'), c.rhodecode_db_repo.repo_id, '', ''),
5 (_('Repository ID'), c.rhodecode_db_repo.repo_id, '', ''),
6 (_('Owner'), lambda:base.gravatar_with_user(c.rhodecode_db_repo.user.email), '', ''),
6 (_('Owner'), lambda:base.gravatar_with_user(c.rhodecode_db_repo.user.email), '', ''),
7 (_('Created on'), h.format_date(c.rhodecode_db_repo.created_on), '', ''),
7 (_('Created on'), h.format_date(c.rhodecode_db_repo.created_on), '', ''),
8 (_('Updated on'), h.format_date(c.rhodecode_db_repo.updated_on), '', ''),
8 (_('Updated on'), h.format_date(c.rhodecode_db_repo.updated_on), '', ''),
9 (_('Cached Commit id'), lambda: h.link_to(c.rhodecode_db_repo.changeset_cache.get('short_id'), h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.rhodecode_db_repo.changeset_cache.get('raw_id'))), '', ''),
9 (_('Cached Commit id'), lambda: h.link_to(c.rhodecode_db_repo.changeset_cache.get('short_id'), h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.rhodecode_db_repo.changeset_cache.get('raw_id'))), '', ''),
10 (_('Attached scoped tokens'), len(c.rhodecode_db_repo.scoped_tokens), '', [x.user for x in c.rhodecode_db_repo.scoped_tokens]),
10 (_('Attached scoped tokens'), len(c.rhodecode_db_repo.scoped_tokens), '', [x.user for x in c.rhodecode_db_repo.scoped_tokens]),
11 (_('Pull requests source'), len(c.rhodecode_db_repo.pull_requests_source), '', ['pr_id:{}, repo:{}'.format(x.pull_request_id,x.source_repo.repo_name) for x in c.rhodecode_db_repo.pull_requests_source]),
11 (_('Pull requests source'), len(c.rhodecode_db_repo.pull_requests_source), '', ['pr_id:{}, repo:{}'.format(x.pull_request_id,x.source_repo.repo_name) for x in c.rhodecode_db_repo.pull_requests_source]),
12 (_('Pull requests target'), len(c.rhodecode_db_repo.pull_requests_target), '', ['pr_id:{}, repo:{}'.format(x.pull_request_id,x.target_repo.repo_name) for x in c.rhodecode_db_repo.pull_requests_target]),
12 (_('Pull requests target'), len(c.rhodecode_db_repo.pull_requests_target), '', ['pr_id:{}, repo:{}'.format(x.pull_request_id,x.target_repo.repo_name) for x in c.rhodecode_db_repo.pull_requests_target]),
13 ]
13 ]
14 %>
14 %>
15
15
16 <div class="panel panel-default">
16 <div class="panel panel-default">
17 <div class="panel-heading" id="advanced-info" >
17 <div class="panel-heading" id="advanced-info" >
18 <h3 class="panel-title">${_('Repository: %s') % c.rhodecode_db_repo.repo_name} <a class="permalink" href="#advanced-info"> ΒΆ</a></h3>
18 <h3 class="panel-title">${_('Repository: %s') % c.rhodecode_db_repo.repo_name} <a class="permalink" href="#advanced-info"> ΒΆ</a></h3>
19 </div>
19 </div>
20 <div class="panel-body">
20 <div class="panel-body">
21 ${base.dt_info_panel(elems)}
21 ${base.dt_info_panel(elems)}
22 </div>
22 </div>
23 </div>
23 </div>
24
24
25
25
26 <div class="panel panel-default">
26 <div class="panel panel-default">
27 <div class="panel-heading" id="advanced-fork">
27 <div class="panel-heading" id="advanced-fork">
28 <h3 class="panel-title">${_('Fork Reference')} <a class="permalink" href="#advanced-fork"> ΒΆ</a></h3>
28 <h3 class="panel-title">${_('Fork Reference')} <a class="permalink" href="#advanced-fork"> ΒΆ</a></h3>
29 </div>
29 </div>
30 <div class="panel-body">
30 <div class="panel-body">
31 ${h.secure_form(h.route_path('edit_repo_advanced_fork', repo_name=c.rhodecode_db_repo.repo_name), request=request)}
31 ${h.secure_form(h.route_path('edit_repo_advanced_fork', repo_name=c.rhodecode_db_repo.repo_name), request=request)}
32
32
33 % if c.rhodecode_db_repo.fork:
33 % if c.rhodecode_db_repo.fork:
34 <div class="panel-body-title-text">${h.literal(_('This repository is a fork of %(repo_link)s') % {'repo_link': h.link_to_if(c.has_origin_repo_read_perm,c.rhodecode_db_repo.fork.repo_name, h.route_path('repo_summary', repo_name=c.rhodecode_db_repo.fork.repo_name))})}
34 <div class="panel-body-title-text">${h.literal(_('This repository is a fork of %(repo_link)s') % {'repo_link': h.link_to_if(c.has_origin_repo_read_perm,c.rhodecode_db_repo.fork.repo_name, h.route_path('repo_summary', repo_name=c.rhodecode_db_repo.fork.repo_name))})}
35 | <button class="btn btn-link btn-danger" type="submit">Remove fork reference</button></div>
35 | <button class="btn btn-link btn-danger" type="submit">Remove fork reference</button></div>
36 % endif
36 % endif
37
37
38 <div class="field">
38 <div class="field">
39 ${h.hidden('id_fork_of')}
39 ${h.hidden('id_fork_of')}
40 ${h.submit('set_as_fork_%s' % c.rhodecode_db_repo.repo_name,_('Set'),class_="btn btn-small",)}
40 ${h.submit('set_as_fork_%s' % c.rhodecode_db_repo.repo_name,_('Set'),class_="btn btn-small",)}
41 </div>
41 </div>
42 <div class="field">
42 <div class="field">
43 <span class="help-block">${_('Manually set this repository as a fork of another from the list')}</span>
43 <span class="help-block">${_('Manually set this repository as a fork of another from the list')}</span>
44 </div>
44 </div>
45 ${h.end_form()}
45 ${h.end_form()}
46 </div>
46 </div>
47 </div>
47 </div>
48
48
49
49
50 <div class="panel panel-default">
50 <div class="panel panel-default">
51 <div class="panel-heading" id="advanced-journal">
51 <div class="panel-heading" id="advanced-journal">
52 <h3 class="panel-title">${_('Public Journal Visibility')} <a class="permalink" href="#advanced-journal"> ΒΆ</a></h3>
52 <h3 class="panel-title">${_('Public Journal Visibility')} <a class="permalink" href="#advanced-journal"> ΒΆ</a></h3>
53 </div>
53 </div>
54 <div class="panel-body">
54 <div class="panel-body">
55 ${h.secure_form(h.route_path('edit_repo_advanced_journal', repo_name=c.rhodecode_db_repo.repo_name), request=request)}
55 ${h.secure_form(h.route_path('edit_repo_advanced_journal', repo_name=c.rhodecode_db_repo.repo_name), request=request)}
56 <div class="field">
56 <div class="field">
57 %if c.in_public_journal:
57 %if c.in_public_journal:
58 <button class="btn btn-small" type="submit">
58 <button class="btn btn-small" type="submit">
59 ${_('Remove from Public Journal')}
59 ${_('Remove from Public Journal')}
60 </button>
60 </button>
61 %else:
61 %else:
62 <button class="btn btn-small" type="submit">
62 <button class="btn btn-small" type="submit">
63 ${_('Add to Public Journal')}
63 ${_('Add to Public Journal')}
64 </button>
64 </button>
65 %endif
65 %endif
66 </div>
66 </div>
67 <div class="field" >
67 <div class="field" >
68 <span class="help-block">${_('All actions made on this repository will be visible to everyone following the public journal.')}</span>
68 <span class="help-block">${_('All actions made on this repository will be visible to everyone following the public journal.')}</span>
69 </div>
69 </div>
70 ${h.end_form()}
70 ${h.end_form()}
71 </div>
71 </div>
72 </div>
72 </div>
73
73
74
74
75 <div class="panel panel-default">
75 <div class="panel panel-default">
76 <div class="panel-heading" id="advanced-locking">
76 <div class="panel-heading" id="advanced-locking">
77 <h3 class="panel-title">${_('Locking state')} <a class="permalink" href="#advanced-locking"> ΒΆ</a></h3>
77 <h3 class="panel-title">${_('Locking state')} <a class="permalink" href="#advanced-locking"> ΒΆ</a></h3>
78 </div>
78 </div>
79 <div class="panel-body">
79 <div class="panel-body">
80 ${h.secure_form(h.route_path('edit_repo_advanced_locking', repo_name=c.rhodecode_db_repo.repo_name), request=request)}
80 ${h.secure_form(h.route_path('edit_repo_advanced_locking', repo_name=c.rhodecode_db_repo.repo_name), request=request)}
81
81
82 %if c.rhodecode_db_repo.locked[0]:
82 %if c.rhodecode_db_repo.locked[0]:
83 <div class="panel-body-title-text">${'Locked by %s on %s. Lock reason: %s' % (h.person_by_id(c.rhodecode_db_repo.locked[0]),
83 <div class="panel-body-title-text">${'Locked by %s on %s. Lock reason: %s' % (h.person_by_id(c.rhodecode_db_repo.locked[0]),
84 h.format_date(h. time_to_datetime(c.rhodecode_db_repo.locked[1])), c.rhodecode_db_repo.locked[2])}</div>
84 h.format_date(h. time_to_datetime(c.rhodecode_db_repo.locked[1])), c.rhodecode_db_repo.locked[2])}</div>
85 %else:
85 %else:
86 <div class="panel-body-title-text">${_('This Repository is not currently locked.')}</div>
86 <div class="panel-body-title-text">${_('This Repository is not currently locked.')}</div>
87 %endif
87 %endif
88
88
89 <div class="field" >
89 <div class="field" >
90 %if c.rhodecode_db_repo.locked[0]:
90 %if c.rhodecode_db_repo.locked[0]:
91 ${h.hidden('set_unlock', '1')}
91 ${h.hidden('set_unlock', '1')}
92 <button class="btn btn-small" type="submit"
92 <button class="btn btn-small" type="submit"
93 onclick="return confirm('${_('Confirm to unlock repository.')}');">
93 onclick="return confirm('${_('Confirm to unlock repository.')}');">
94 <i class="icon-unlock"></i>
94 <i class="icon-unlock"></i>
95 ${_('Unlock repository')}
95 ${_('Unlock repository')}
96 </button>
96 </button>
97 %else:
97 %else:
98 ${h.hidden('set_lock', '1')}
98 ${h.hidden('set_lock', '1')}
99 <button class="btn btn-small" type="submit"
99 <button class="btn btn-small" type="submit"
100 onclick="return confirm('${_('Confirm to lock repository.')}');">
100 onclick="return confirm('${_('Confirm to lock repository.')}');">
101 <i class="icon-lock"></i>
101 <i class="icon-lock"></i>
102 ${_('Lock repository')}
102 ${_('Lock repository')}
103 </button>
103 </button>
104 %endif
104 %endif
105 </div>
105 </div>
106 <div class="field" >
106 <div class="field" >
107 <span class="help-block">
107 <span class="help-block">
108 ${_('Force repository locking. This only works when anonymous access is disabled. Pulling from the repository locks the repository to that user until the same user pushes to that repository again.')}
108 ${_('Force repository locking. This only works when anonymous access is disabled. Pulling from the repository locks the repository to that user until the same user pushes to that repository again.')}
109 </span>
109 </span>
110 </div>
110 </div>
111 ${h.end_form()}
111 ${h.end_form()}
112 </div>
112 </div>
113 </div>
113 </div>
114
114
115
115
116 <div class="panel panel-default">
116 <div class="panel panel-default">
117 <div class="panel-heading" id="advanced-hooks">
117 <div class="panel-heading" id="advanced-hooks">
118 <h3 class="panel-title">${_('Hooks')} <a class="permalink" href="#advanced-hooks"> ΒΆ</a></h3>
118 <h3 class="panel-title">${_('Hooks')} <a class="permalink" href="#advanced-hooks"> ΒΆ</a></h3>
119 </div>
119 </div>
120 <div class="panel-body">
120 <div class="panel-body">
121 <% ver_info_dict = c.rhodecode_db_repo.scm_instance().get_hooks_info() %>
122
123 <table class="rctable">
121 <table class="rctable">
124 <th>${_('Hook type')}</th>
122 <th>${_('Hook type')}</th>
125 <th>${_('Hook version')}</th>
123 <th>${_('Hook version')}</th>
126 <th>${_('Current version')}</th>
124 <th>${_('Current version')}</th>
127
125 % if c.ver_info_dict:
128 <tr>
126 <tr>
129 <td>${_('PRE HOOK')}</td>
127 <td>${_('PRE HOOK')}</td>
130 <td>${ver_info_dict['pre_version']}</td>
128 <td>${c.ver_info_dict['pre_version']}</td>
131 <td>${c.rhodecode_version}</td>
129 <td>${c.rhodecode_version}</td>
132 </tr>
130 </tr>
133 <tr>
131 <tr>
134 <td>${_('POST HOOK')}</td>
132 <td>${_('POST HOOK')}</td>
135 <td>${ver_info_dict['post_version']}</td>
133 <td>${c.ver_info_dict['post_version']}</td>
136 <td>${c.rhodecode_version}</td>
134 <td>${c.rhodecode_version}</td>
137 </tr>
135 </tr>
136 % else:
137 <tr>
138 <td>${_('Unable to read hook information from VCS Server')}</td>
139 </tr>
140 % endif
138 </table>
141 </table>
139
142
140 <a href="${h.route_path('edit_repo_advanced_hooks', repo_name=c.repo_name)}"
143 <a href="${h.route_path('edit_repo_advanced_hooks', repo_name=c.repo_name)}"
141 onclick="return confirm('${_('Confirm to reinstall hooks for this repository.')}');">
144 onclick="return confirm('${_('Confirm to reinstall hooks for this repository.')}');">
142 ${_('Update Hooks')}
145 ${_('Update Hooks')}
143 </a>
146 </a>
144 </div>
147 </div>
145 </div>
148 </div>
146
149
147 <div class="panel panel-warning">
150 <div class="panel panel-warning">
148 <div class="panel-heading" id="advanced-archive">
151 <div class="panel-heading" id="advanced-archive">
149 <h3 class="panel-title">${_('Archive repository')} <a class="permalink" href="#advanced-archive"> ΒΆ</a></h3>
152 <h3 class="panel-title">${_('Archive repository')} <a class="permalink" href="#advanced-archive"> ΒΆ</a></h3>
150 </div>
153 </div>
151 <div class="panel-body">
154 <div class="panel-body">
152 ${h.secure_form(h.route_path('edit_repo_advanced_archive', repo_name=c.repo_name), request=request)}
155 ${h.secure_form(h.route_path('edit_repo_advanced_archive', repo_name=c.repo_name), request=request)}
153
156
154 <div style="margin: 0 0 20px 0" class="fake-space"></div>
157 <div style="margin: 0 0 20px 0" class="fake-space"></div>
155
158
156 <div class="field">
159 <div class="field">
157 <button class="btn btn-small btn-danger" type="submit"
160 <button class="btn btn-small btn-danger" type="submit"
158 onclick="return confirm('${_('Confirm to archive this repository: %s') % c.repo_name}');">
161 onclick="return confirm('${_('Confirm to archive this repository: %s') % c.repo_name}');">
159 <i class="icon-remove-sign"></i>
162 <i class="icon-remove-sign"></i>
160 ${_('Archive this repository')}
163 ${_('Archive this repository')}
161 </button>
164 </button>
162 </div>
165 </div>
163 <div class="field">
166 <div class="field">
164 <span class="help-block">
167 <span class="help-block">
165 ${_('Archiving the repository will make it entirely read-only. The repository cannot be committed to.'
168 ${_('Archiving the repository will make it entirely read-only. The repository cannot be committed to.'
166 'It is hidden from the search results and dashboard. ')}
169 'It is hidden from the search results and dashboard. ')}
167 </span>
170 </span>
168 </div>
171 </div>
169
172
170 ${h.end_form()}
173 ${h.end_form()}
171 </div>
174 </div>
172 </div>
175 </div>
173
176
174
177
175 <div class="panel panel-danger">
178 <div class="panel panel-danger">
176 <div class="panel-heading" id="advanced-delete">
179 <div class="panel-heading" id="advanced-delete">
177 <h3 class="panel-title">${_('Delete repository')} <a class="permalink" href="#advanced-delete"> ΒΆ</a></h3>
180 <h3 class="panel-title">${_('Delete repository')} <a class="permalink" href="#advanced-delete"> ΒΆ</a></h3>
178 </div>
181 </div>
179 <div class="panel-body">
182 <div class="panel-body">
180 ${h.secure_form(h.route_path('edit_repo_advanced_delete', repo_name=c.repo_name), request=request)}
183 ${h.secure_form(h.route_path('edit_repo_advanced_delete', repo_name=c.repo_name), request=request)}
181 <table class="display">
184 <table class="display">
182 <tr>
185 <tr>
183 <td>
186 <td>
184 ${_ungettext('This repository has %s fork.', 'This repository has %s forks.', c.rhodecode_db_repo.forks.count()) % c.rhodecode_db_repo.forks.count()}
187 ${_ungettext('This repository has %s fork.', 'This repository has %s forks.', c.rhodecode_db_repo.forks.count()) % c.rhodecode_db_repo.forks.count()}
185 </td>
188 </td>
186 <td>
189 <td>
187 %if c.rhodecode_db_repo.forks.count():
190 %if c.rhodecode_db_repo.forks.count():
188 <input type="radio" name="forks" value="detach_forks" checked="checked"/> <label for="forks">${_('Detach forks')}</label>
191 <input type="radio" name="forks" value="detach_forks" checked="checked"/> <label for="forks">${_('Detach forks')}</label>
189 %endif
192 %endif
190 </td>
193 </td>
191 <td>
194 <td>
192 %if c.rhodecode_db_repo.forks.count():
195 %if c.rhodecode_db_repo.forks.count():
193 <input type="radio" name="forks" value="delete_forks"/> <label for="forks">${_('Delete forks')}</label>
196 <input type="radio" name="forks" value="delete_forks"/> <label for="forks">${_('Delete forks')}</label>
194 %endif
197 %endif
195 </td>
198 </td>
196 </tr>
199 </tr>
197 <% attached_prs = len(c.rhodecode_db_repo.pull_requests_source + c.rhodecode_db_repo.pull_requests_target) %>
200 <% attached_prs = len(c.rhodecode_db_repo.pull_requests_source + c.rhodecode_db_repo.pull_requests_target) %>
198 % if c.rhodecode_db_repo.pull_requests_source or c.rhodecode_db_repo.pull_requests_target:
201 % if c.rhodecode_db_repo.pull_requests_source or c.rhodecode_db_repo.pull_requests_target:
199 <tr>
202 <tr>
200 <td>
203 <td>
201 ${_ungettext('This repository has %s attached pull request.', 'This repository has %s attached pull requests.', attached_prs) % attached_prs}
204 ${_ungettext('This repository has %s attached pull request.', 'This repository has %s attached pull requests.', attached_prs) % attached_prs}
202 <br/>
205 <br/>
203 ${_('Consider to archive this repository instead.')}
206 ${_('Consider to archive this repository instead.')}
204 </td>
207 </td>
205 <td></td>
208 <td></td>
206 <td></td>
209 <td></td>
207 </tr>
210 </tr>
208 % endif
211 % endif
209 </table>
212 </table>
210 <div style="margin: 0 0 20px 0" class="fake-space"></div>
213 <div style="margin: 0 0 20px 0" class="fake-space"></div>
211
214
212 <div class="field">
215 <div class="field">
213 <button class="btn btn-small btn-danger" type="submit"
216 <button class="btn btn-small btn-danger" type="submit"
214 onclick="return confirm('${_('Confirm to delete this repository: %s') % c.repo_name}');">
217 onclick="return confirm('${_('Confirm to delete this repository: %s') % c.repo_name}');">
215 <i class="icon-remove-sign"></i>
218 <i class="icon-remove-sign"></i>
216 ${_('Delete this repository')}
219 ${_('Delete this repository')}
217 </button>
220 </button>
218 </div>
221 </div>
219 <div class="field">
222 <div class="field">
220 <span class="help-block">
223 <span class="help-block">
221 ${_('This repository will be renamed in a special way in order to make it inaccessible to RhodeCode Enterprise and its VCS systems. If you need to fully delete it from the file system, please do it manually, or with rhodecode-cleanup-repos command available in rhodecode-tools.')}
224 ${_('This repository will be renamed in a special way in order to make it inaccessible to RhodeCode Enterprise and its VCS systems. If you need to fully delete it from the file system, please do it manually, or with rhodecode-cleanup-repos command available in rhodecode-tools.')}
222 </span>
225 </span>
223 </div>
226 </div>
224
227
225 ${h.end_form()}
228 ${h.end_form()}
226 </div>
229 </div>
227 </div>
230 </div>
228
231
229
232
230 <script>
233 <script>
231
234
232 var currentRepoId = ${c.rhodecode_db_repo.repo_id};
235 var currentRepoId = ${c.rhodecode_db_repo.repo_id};
233
236
234 var repoTypeFilter = function(data) {
237 var repoTypeFilter = function(data) {
235 var results = [];
238 var results = [];
236
239
237 if (!data.results[0]) {
240 if (!data.results[0]) {
238 return data
241 return data
239 }
242 }
240
243
241 $.each(data.results[0].children, function() {
244 $.each(data.results[0].children, function() {
242 // filter out the SAME repo, it cannot be used as fork of itself
245 // filter out the SAME repo, it cannot be used as fork of itself
243 if (this.repo_id != currentRepoId) {
246 if (this.repo_id != currentRepoId) {
244 this.id = this.repo_id;
247 this.id = this.repo_id;
245 results.push(this)
248 results.push(this)
246 }
249 }
247 });
250 });
248 data.results[0].children = results;
251 data.results[0].children = results;
249 return data;
252 return data;
250 };
253 };
251
254
252 $("#id_fork_of").select2({
255 $("#id_fork_of").select2({
253 cachedDataSource: {},
256 cachedDataSource: {},
254 minimumInputLength: 2,
257 minimumInputLength: 2,
255 placeholder: "${_('Change repository') if c.rhodecode_db_repo.fork else _('Pick repository')}",
258 placeholder: "${_('Change repository') if c.rhodecode_db_repo.fork else _('Pick repository')}",
256 dropdownAutoWidth: true,
259 dropdownAutoWidth: true,
257 containerCssClass: "drop-menu",
260 containerCssClass: "drop-menu",
258 dropdownCssClass: "drop-menu-dropdown",
261 dropdownCssClass: "drop-menu-dropdown",
259 formatResult: formatRepoResult,
262 formatResult: formatRepoResult,
260 query: $.debounce(250, function(query){
263 query: $.debounce(250, function(query){
261 self = this;
264 self = this;
262 var cacheKey = query.term;
265 var cacheKey = query.term;
263 var cachedData = self.cachedDataSource[cacheKey];
266 var cachedData = self.cachedDataSource[cacheKey];
264
267
265 if (cachedData) {
268 if (cachedData) {
266 query.callback({results: cachedData.results});
269 query.callback({results: cachedData.results});
267 } else {
270 } else {
268 $.ajax({
271 $.ajax({
269 url: pyroutes.url('repo_list_data'),
272 url: pyroutes.url('repo_list_data'),
270 data: {'query': query.term, repo_type: '${c.rhodecode_db_repo.repo_type}'},
273 data: {'query': query.term, repo_type: '${c.rhodecode_db_repo.repo_type}'},
271 dataType: 'json',
274 dataType: 'json',
272 type: 'GET',
275 type: 'GET',
273 success: function(data) {
276 success: function(data) {
274 data = repoTypeFilter(data);
277 data = repoTypeFilter(data);
275 self.cachedDataSource[cacheKey] = data;
278 self.cachedDataSource[cacheKey] = data;
276 query.callback({results: data.results});
279 query.callback({results: data.results});
277 },
280 },
278 error: function(data, textStatus, errorThrown) {
281 error: function(data, textStatus, errorThrown) {
279 alert("Error while fetching entries.\nError code {0} ({1}).".format(data.status, data.statusText));
282 alert("Error while fetching entries.\nError code {0} ({1}).".format(data.status, data.statusText));
280 }
283 }
281 })
284 })
282 }
285 }
283 })
286 })
284 });
287 });
285 </script>
288 </script>
286
289
General Comments 0
You need to be logged in to leave comments. Login now