##// END OF EJS Templates
audit-logs: store repository name on pull action.
marcink -
r1737:c2645bad default
parent child Browse files
Show More
@@ -1,420 +1,421 b''
1 # -*- coding: utf-8 -*-
1 # -*- coding: utf-8 -*-
2
2
3 # Copyright (C) 2013-2017 RhodeCode GmbH
3 # Copyright (C) 2013-2017 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
21
22 """
22 """
23 Set of hooks run by RhodeCode Enterprise
23 Set of hooks run by RhodeCode Enterprise
24 """
24 """
25
25
26 import os
26 import os
27 import collections
27 import collections
28 import logging
28 import logging
29
29
30 import rhodecode
30 import rhodecode
31 from rhodecode import events
31 from rhodecode import events
32 from rhodecode.lib import helpers as h
32 from rhodecode.lib import helpers as h
33 from rhodecode.lib import audit_logger
33 from rhodecode.lib import audit_logger
34 from rhodecode.lib.utils import action_logger
34 from rhodecode.lib.utils import action_logger
35 from rhodecode.lib.utils2 import safe_str
35 from rhodecode.lib.utils2 import safe_str
36 from rhodecode.lib.exceptions import HTTPLockedRC, UserCreationError
36 from rhodecode.lib.exceptions import HTTPLockedRC, UserCreationError
37 from rhodecode.model.db import Repository, User
37 from rhodecode.model.db import Repository, User
38
38
39 log = logging.getLogger(__name__)
39 log = logging.getLogger(__name__)
40
40
41
41
42 HookResponse = collections.namedtuple('HookResponse', ('status', 'output'))
42 HookResponse = collections.namedtuple('HookResponse', ('status', 'output'))
43
43
44
44
45 def is_shadow_repo(extras):
45 def is_shadow_repo(extras):
46 """
46 """
47 Returns ``True`` if this is an action executed against a shadow repository.
47 Returns ``True`` if this is an action executed against a shadow repository.
48 """
48 """
49 return extras['is_shadow_repo']
49 return extras['is_shadow_repo']
50
50
51
51
52 def _get_scm_size(alias, root_path):
52 def _get_scm_size(alias, root_path):
53
53
54 if not alias.startswith('.'):
54 if not alias.startswith('.'):
55 alias += '.'
55 alias += '.'
56
56
57 size_scm, size_root = 0, 0
57 size_scm, size_root = 0, 0
58 for path, unused_dirs, files in os.walk(safe_str(root_path)):
58 for path, unused_dirs, files in os.walk(safe_str(root_path)):
59 if path.find(alias) != -1:
59 if path.find(alias) != -1:
60 for f in files:
60 for f in files:
61 try:
61 try:
62 size_scm += os.path.getsize(os.path.join(path, f))
62 size_scm += os.path.getsize(os.path.join(path, f))
63 except OSError:
63 except OSError:
64 pass
64 pass
65 else:
65 else:
66 for f in files:
66 for f in files:
67 try:
67 try:
68 size_root += os.path.getsize(os.path.join(path, f))
68 size_root += os.path.getsize(os.path.join(path, f))
69 except OSError:
69 except OSError:
70 pass
70 pass
71
71
72 size_scm_f = h.format_byte_size_binary(size_scm)
72 size_scm_f = h.format_byte_size_binary(size_scm)
73 size_root_f = h.format_byte_size_binary(size_root)
73 size_root_f = h.format_byte_size_binary(size_root)
74 size_total_f = h.format_byte_size_binary(size_root + size_scm)
74 size_total_f = h.format_byte_size_binary(size_root + size_scm)
75
75
76 return size_scm_f, size_root_f, size_total_f
76 return size_scm_f, size_root_f, size_total_f
77
77
78
78
79 # actual hooks called by Mercurial internally, and GIT by our Python Hooks
79 # actual hooks called by Mercurial internally, and GIT by our Python Hooks
80 def repo_size(extras):
80 def repo_size(extras):
81 """Present size of repository after push."""
81 """Present size of repository after push."""
82 repo = Repository.get_by_repo_name(extras.repository)
82 repo = Repository.get_by_repo_name(extras.repository)
83 vcs_part = safe_str(u'.%s' % repo.repo_type)
83 vcs_part = safe_str(u'.%s' % repo.repo_type)
84 size_vcs, size_root, size_total = _get_scm_size(vcs_part,
84 size_vcs, size_root, size_total = _get_scm_size(vcs_part,
85 repo.repo_full_path)
85 repo.repo_full_path)
86 msg = ('Repository `%s` size summary %s:%s repo:%s total:%s\n'
86 msg = ('Repository `%s` size summary %s:%s repo:%s total:%s\n'
87 % (repo.repo_name, vcs_part, size_vcs, size_root, size_total))
87 % (repo.repo_name, vcs_part, size_vcs, size_root, size_total))
88 return HookResponse(0, msg)
88 return HookResponse(0, msg)
89
89
90
90
91 def pre_push(extras):
91 def pre_push(extras):
92 """
92 """
93 Hook executed before pushing code.
93 Hook executed before pushing code.
94
94
95 It bans pushing when the repository is locked.
95 It bans pushing when the repository is locked.
96 """
96 """
97
97
98 usr = User.get_by_username(extras.username)
98 usr = User.get_by_username(extras.username)
99 output = ''
99 output = ''
100 if extras.locked_by[0] and usr.user_id != int(extras.locked_by[0]):
100 if extras.locked_by[0] and usr.user_id != int(extras.locked_by[0]):
101 locked_by = User.get(extras.locked_by[0]).username
101 locked_by = User.get(extras.locked_by[0]).username
102 reason = extras.locked_by[2]
102 reason = extras.locked_by[2]
103 # this exception is interpreted in git/hg middlewares and based
103 # this exception is interpreted in git/hg middlewares and based
104 # on that proper return code is server to client
104 # on that proper return code is server to client
105 _http_ret = HTTPLockedRC(
105 _http_ret = HTTPLockedRC(
106 _locked_by_explanation(extras.repository, locked_by, reason))
106 _locked_by_explanation(extras.repository, locked_by, reason))
107 if str(_http_ret.code).startswith('2'):
107 if str(_http_ret.code).startswith('2'):
108 # 2xx Codes don't raise exceptions
108 # 2xx Codes don't raise exceptions
109 output = _http_ret.title
109 output = _http_ret.title
110 else:
110 else:
111 raise _http_ret
111 raise _http_ret
112
112
113 # Propagate to external components. This is done after checking the
113 # Propagate to external components. This is done after checking the
114 # lock, for consistent behavior.
114 # lock, for consistent behavior.
115 if not is_shadow_repo(extras):
115 if not is_shadow_repo(extras):
116 pre_push_extension(repo_store_path=Repository.base_path(), **extras)
116 pre_push_extension(repo_store_path=Repository.base_path(), **extras)
117 events.trigger(events.RepoPrePushEvent(
117 events.trigger(events.RepoPrePushEvent(
118 repo_name=extras.repository, extras=extras))
118 repo_name=extras.repository, extras=extras))
119
119
120 return HookResponse(0, output)
120 return HookResponse(0, output)
121
121
122
122
123 def pre_pull(extras):
123 def pre_pull(extras):
124 """
124 """
125 Hook executed before pulling the code.
125 Hook executed before pulling the code.
126
126
127 It bans pulling when the repository is locked.
127 It bans pulling when the repository is locked.
128 """
128 """
129
129
130 output = ''
130 output = ''
131 if extras.locked_by[0]:
131 if extras.locked_by[0]:
132 locked_by = User.get(extras.locked_by[0]).username
132 locked_by = User.get(extras.locked_by[0]).username
133 reason = extras.locked_by[2]
133 reason = extras.locked_by[2]
134 # this exception is interpreted in git/hg middlewares and based
134 # this exception is interpreted in git/hg middlewares and based
135 # on that proper return code is server to client
135 # on that proper return code is server to client
136 _http_ret = HTTPLockedRC(
136 _http_ret = HTTPLockedRC(
137 _locked_by_explanation(extras.repository, locked_by, reason))
137 _locked_by_explanation(extras.repository, locked_by, reason))
138 if str(_http_ret.code).startswith('2'):
138 if str(_http_ret.code).startswith('2'):
139 # 2xx Codes don't raise exceptions
139 # 2xx Codes don't raise exceptions
140 output = _http_ret.title
140 output = _http_ret.title
141 else:
141 else:
142 raise _http_ret
142 raise _http_ret
143
143
144 # Propagate to external components. This is done after checking the
144 # Propagate to external components. This is done after checking the
145 # lock, for consistent behavior.
145 # lock, for consistent behavior.
146 if not is_shadow_repo(extras):
146 if not is_shadow_repo(extras):
147 pre_pull_extension(**extras)
147 pre_pull_extension(**extras)
148 events.trigger(events.RepoPrePullEvent(
148 events.trigger(events.RepoPrePullEvent(
149 repo_name=extras.repository, extras=extras))
149 repo_name=extras.repository, extras=extras))
150
150
151 return HookResponse(0, output)
151 return HookResponse(0, output)
152
152
153
153
154 def post_pull(extras):
154 def post_pull(extras):
155 """Hook executed after client pulls the code."""
155 """Hook executed after client pulls the code."""
156 user = User.get_by_username(extras.username)
156 user = User.get_by_username(extras.username)
157 action = 'pull'
157 action = 'pull'
158 action_logger(user, action, extras.repository, extras.ip, commit=True)
158 action_logger(user, action, extras.repository, extras.ip, commit=True)
159
159
160 audit_user = audit_logger.UserWrap(
160 audit_user = audit_logger.UserWrap(
161 username=extras.username,
161 username=extras.username,
162 ip_addr=extras.ip)
162 ip_addr=extras.ip)
163 repo = audit_logger.RepoWrap(repo_name=extras.repository)
163 audit_logger.store(
164 audit_logger.store(
164 action='user.pull', action_data={
165 action='user.pull', action_data={
165 'user_agent': extras.user_agent},
166 'user_agent': extras.user_agent},
166 user=audit_user, commit=True)
167 user=audit_user, repo=repo, commit=True)
167
168
168 # Propagate to external components.
169 # Propagate to external components.
169 if not is_shadow_repo(extras):
170 if not is_shadow_repo(extras):
170 post_pull_extension(**extras)
171 post_pull_extension(**extras)
171 events.trigger(events.RepoPullEvent(
172 events.trigger(events.RepoPullEvent(
172 repo_name=extras.repository, extras=extras))
173 repo_name=extras.repository, extras=extras))
173
174
174 output = ''
175 output = ''
175 # make lock is a tri state False, True, None. We only make lock on True
176 # make lock is a tri state False, True, None. We only make lock on True
176 if extras.make_lock is True and not is_shadow_repo(extras):
177 if extras.make_lock is True and not is_shadow_repo(extras):
177 Repository.lock(Repository.get_by_repo_name(extras.repository),
178 Repository.lock(Repository.get_by_repo_name(extras.repository),
178 user.user_id,
179 user.user_id,
179 lock_reason=Repository.LOCK_PULL)
180 lock_reason=Repository.LOCK_PULL)
180 msg = 'Made lock on repo `%s`' % (extras.repository,)
181 msg = 'Made lock on repo `%s`' % (extras.repository,)
181 output += msg
182 output += msg
182
183
183 if extras.locked_by[0]:
184 if extras.locked_by[0]:
184 locked_by = User.get(extras.locked_by[0]).username
185 locked_by = User.get(extras.locked_by[0]).username
185 reason = extras.locked_by[2]
186 reason = extras.locked_by[2]
186 _http_ret = HTTPLockedRC(
187 _http_ret = HTTPLockedRC(
187 _locked_by_explanation(extras.repository, locked_by, reason))
188 _locked_by_explanation(extras.repository, locked_by, reason))
188 if str(_http_ret.code).startswith('2'):
189 if str(_http_ret.code).startswith('2'):
189 # 2xx Codes don't raise exceptions
190 # 2xx Codes don't raise exceptions
190 output += _http_ret.title
191 output += _http_ret.title
191
192
192 return HookResponse(0, output)
193 return HookResponse(0, output)
193
194
194
195
195 def post_push(extras):
196 def post_push(extras):
196 """Hook executed after user pushes to the repository."""
197 """Hook executed after user pushes to the repository."""
197 action_tmpl = extras.action + ':%s'
198 action_tmpl = extras.action + ':%s'
198 commit_ids = extras.commit_ids[:29000]
199 commit_ids = extras.commit_ids[:29000]
199
200
200 action = action_tmpl % ','.join(commit_ids)
201 action = action_tmpl % ','.join(commit_ids)
201 action_logger(
202 action_logger(
202 extras.username, action, extras.repository, extras.ip, commit=True)
203 extras.username, action, extras.repository, extras.ip, commit=True)
203
204
204 audit_user = audit_logger.UserWrap(
205 audit_user = audit_logger.UserWrap(
205 username=extras.username,
206 username=extras.username,
206 ip_addr=extras.ip)
207 ip_addr=extras.ip)
207 repo = audit_logger.RepoWrap(repo_name=extras.repository)
208 repo = audit_logger.RepoWrap(repo_name=extras.repository)
208 audit_logger.store(
209 audit_logger.store(
209 action='user.push', action_data={
210 action='user.push', action_data={
210 'user_agent': extras.user_agent,
211 'user_agent': extras.user_agent,
211 'commit_ids': commit_ids[:10000]},
212 'commit_ids': commit_ids[:10000]},
212 user=audit_user, repo=repo, commit=True)
213 user=audit_user, repo=repo, commit=True)
213
214
214 # Propagate to external components.
215 # Propagate to external components.
215 if not is_shadow_repo(extras):
216 if not is_shadow_repo(extras):
216 post_push_extension(
217 post_push_extension(
217 repo_store_path=Repository.base_path(),
218 repo_store_path=Repository.base_path(),
218 pushed_revs=commit_ids,
219 pushed_revs=commit_ids,
219 **extras)
220 **extras)
220 events.trigger(events.RepoPushEvent(
221 events.trigger(events.RepoPushEvent(
221 repo_name=extras.repository,
222 repo_name=extras.repository,
222 pushed_commit_ids=commit_ids,
223 pushed_commit_ids=commit_ids,
223 extras=extras))
224 extras=extras))
224
225
225 output = ''
226 output = ''
226 # make lock is a tri state False, True, None. We only release lock on False
227 # make lock is a tri state False, True, None. We only release lock on False
227 if extras.make_lock is False and not is_shadow_repo(extras):
228 if extras.make_lock is False and not is_shadow_repo(extras):
228 Repository.unlock(Repository.get_by_repo_name(extras.repository))
229 Repository.unlock(Repository.get_by_repo_name(extras.repository))
229 msg = 'Released lock on repo `%s`\n' % extras.repository
230 msg = 'Released lock on repo `%s`\n' % extras.repository
230 output += msg
231 output += msg
231
232
232 if extras.locked_by[0]:
233 if extras.locked_by[0]:
233 locked_by = User.get(extras.locked_by[0]).username
234 locked_by = User.get(extras.locked_by[0]).username
234 reason = extras.locked_by[2]
235 reason = extras.locked_by[2]
235 _http_ret = HTTPLockedRC(
236 _http_ret = HTTPLockedRC(
236 _locked_by_explanation(extras.repository, locked_by, reason))
237 _locked_by_explanation(extras.repository, locked_by, reason))
237 # TODO: johbo: if not?
238 # TODO: johbo: if not?
238 if str(_http_ret.code).startswith('2'):
239 if str(_http_ret.code).startswith('2'):
239 # 2xx Codes don't raise exceptions
240 # 2xx Codes don't raise exceptions
240 output += _http_ret.title
241 output += _http_ret.title
241
242
242 output += 'RhodeCode: push completed\n'
243 output += 'RhodeCode: push completed\n'
243
244
244 return HookResponse(0, output)
245 return HookResponse(0, output)
245
246
246
247
247 def _locked_by_explanation(repo_name, user_name, reason):
248 def _locked_by_explanation(repo_name, user_name, reason):
248 message = (
249 message = (
249 'Repository `%s` locked by user `%s`. Reason:`%s`'
250 'Repository `%s` locked by user `%s`. Reason:`%s`'
250 % (repo_name, user_name, reason))
251 % (repo_name, user_name, reason))
251 return message
252 return message
252
253
253
254
254 def check_allowed_create_user(user_dict, created_by, **kwargs):
255 def check_allowed_create_user(user_dict, created_by, **kwargs):
255 # pre create hooks
256 # pre create hooks
256 if pre_create_user.is_active():
257 if pre_create_user.is_active():
257 allowed, reason = pre_create_user(created_by=created_by, **user_dict)
258 allowed, reason = pre_create_user(created_by=created_by, **user_dict)
258 if not allowed:
259 if not allowed:
259 raise UserCreationError(reason)
260 raise UserCreationError(reason)
260
261
261
262
262 class ExtensionCallback(object):
263 class ExtensionCallback(object):
263 """
264 """
264 Forwards a given call to rcextensions, sanitizes keyword arguments.
265 Forwards a given call to rcextensions, sanitizes keyword arguments.
265
266
266 Does check if there is an extension active for that hook. If it is
267 Does check if there is an extension active for that hook. If it is
267 there, it will forward all `kwargs_keys` keyword arguments to the
268 there, it will forward all `kwargs_keys` keyword arguments to the
268 extension callback.
269 extension callback.
269 """
270 """
270
271
271 def __init__(self, hook_name, kwargs_keys):
272 def __init__(self, hook_name, kwargs_keys):
272 self._hook_name = hook_name
273 self._hook_name = hook_name
273 self._kwargs_keys = set(kwargs_keys)
274 self._kwargs_keys = set(kwargs_keys)
274
275
275 def __call__(self, *args, **kwargs):
276 def __call__(self, *args, **kwargs):
276 log.debug('Calling extension callback for %s', self._hook_name)
277 log.debug('Calling extension callback for %s', self._hook_name)
277
278
278 kwargs_to_pass = dict((key, kwargs[key]) for key in self._kwargs_keys)
279 kwargs_to_pass = dict((key, kwargs[key]) for key in self._kwargs_keys)
279 # backward compat for removed api_key for old hooks. THis was it works
280 # backward compat for removed api_key for old hooks. THis was it works
280 # with older rcextensions that require api_key present
281 # with older rcextensions that require api_key present
281 if self._hook_name in ['CREATE_USER_HOOK', 'DELETE_USER_HOOK']:
282 if self._hook_name in ['CREATE_USER_HOOK', 'DELETE_USER_HOOK']:
282 kwargs_to_pass['api_key'] = '_DEPRECATED_'
283 kwargs_to_pass['api_key'] = '_DEPRECATED_'
283
284
284 callback = self._get_callback()
285 callback = self._get_callback()
285 if callback:
286 if callback:
286 return callback(**kwargs_to_pass)
287 return callback(**kwargs_to_pass)
287 else:
288 else:
288 log.debug('extensions callback not found skipping...')
289 log.debug('extensions callback not found skipping...')
289
290
290 def is_active(self):
291 def is_active(self):
291 return hasattr(rhodecode.EXTENSIONS, self._hook_name)
292 return hasattr(rhodecode.EXTENSIONS, self._hook_name)
292
293
293 def _get_callback(self):
294 def _get_callback(self):
294 return getattr(rhodecode.EXTENSIONS, self._hook_name, None)
295 return getattr(rhodecode.EXTENSIONS, self._hook_name, None)
295
296
296
297
297 pre_pull_extension = ExtensionCallback(
298 pre_pull_extension = ExtensionCallback(
298 hook_name='PRE_PULL_HOOK',
299 hook_name='PRE_PULL_HOOK',
299 kwargs_keys=(
300 kwargs_keys=(
300 'server_url', 'config', 'scm', 'username', 'ip', 'action',
301 'server_url', 'config', 'scm', 'username', 'ip', 'action',
301 'repository'))
302 'repository'))
302
303
303
304
304 post_pull_extension = ExtensionCallback(
305 post_pull_extension = ExtensionCallback(
305 hook_name='PULL_HOOK',
306 hook_name='PULL_HOOK',
306 kwargs_keys=(
307 kwargs_keys=(
307 'server_url', 'config', 'scm', 'username', 'ip', 'action',
308 'server_url', 'config', 'scm', 'username', 'ip', 'action',
308 'repository'))
309 'repository'))
309
310
310
311
311 pre_push_extension = ExtensionCallback(
312 pre_push_extension = ExtensionCallback(
312 hook_name='PRE_PUSH_HOOK',
313 hook_name='PRE_PUSH_HOOK',
313 kwargs_keys=(
314 kwargs_keys=(
314 'server_url', 'config', 'scm', 'username', 'ip', 'action',
315 'server_url', 'config', 'scm', 'username', 'ip', 'action',
315 'repository', 'repo_store_path', 'commit_ids'))
316 'repository', 'repo_store_path', 'commit_ids'))
316
317
317
318
318 post_push_extension = ExtensionCallback(
319 post_push_extension = ExtensionCallback(
319 hook_name='PUSH_HOOK',
320 hook_name='PUSH_HOOK',
320 kwargs_keys=(
321 kwargs_keys=(
321 'server_url', 'config', 'scm', 'username', 'ip', 'action',
322 'server_url', 'config', 'scm', 'username', 'ip', 'action',
322 'repository', 'repo_store_path', 'pushed_revs'))
323 'repository', 'repo_store_path', 'pushed_revs'))
323
324
324
325
325 pre_create_user = ExtensionCallback(
326 pre_create_user = ExtensionCallback(
326 hook_name='PRE_CREATE_USER_HOOK',
327 hook_name='PRE_CREATE_USER_HOOK',
327 kwargs_keys=(
328 kwargs_keys=(
328 'username', 'password', 'email', 'firstname', 'lastname', 'active',
329 'username', 'password', 'email', 'firstname', 'lastname', 'active',
329 'admin', 'created_by'))
330 'admin', 'created_by'))
330
331
331
332
332 log_create_pull_request = ExtensionCallback(
333 log_create_pull_request = ExtensionCallback(
333 hook_name='CREATE_PULL_REQUEST',
334 hook_name='CREATE_PULL_REQUEST',
334 kwargs_keys=(
335 kwargs_keys=(
335 'server_url', 'config', 'scm', 'username', 'ip', 'action',
336 'server_url', 'config', 'scm', 'username', 'ip', 'action',
336 'repository', 'pull_request_id', 'url', 'title', 'description',
337 'repository', 'pull_request_id', 'url', 'title', 'description',
337 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
338 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
338 'mergeable', 'source', 'target', 'author', 'reviewers'))
339 'mergeable', 'source', 'target', 'author', 'reviewers'))
339
340
340
341
341 log_merge_pull_request = ExtensionCallback(
342 log_merge_pull_request = ExtensionCallback(
342 hook_name='MERGE_PULL_REQUEST',
343 hook_name='MERGE_PULL_REQUEST',
343 kwargs_keys=(
344 kwargs_keys=(
344 'server_url', 'config', 'scm', 'username', 'ip', 'action',
345 'server_url', 'config', 'scm', 'username', 'ip', 'action',
345 'repository', 'pull_request_id', 'url', 'title', 'description',
346 'repository', 'pull_request_id', 'url', 'title', 'description',
346 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
347 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
347 'mergeable', 'source', 'target', 'author', 'reviewers'))
348 'mergeable', 'source', 'target', 'author', 'reviewers'))
348
349
349
350
350 log_close_pull_request = ExtensionCallback(
351 log_close_pull_request = ExtensionCallback(
351 hook_name='CLOSE_PULL_REQUEST',
352 hook_name='CLOSE_PULL_REQUEST',
352 kwargs_keys=(
353 kwargs_keys=(
353 'server_url', 'config', 'scm', 'username', 'ip', 'action',
354 'server_url', 'config', 'scm', 'username', 'ip', 'action',
354 'repository', 'pull_request_id', 'url', 'title', 'description',
355 'repository', 'pull_request_id', 'url', 'title', 'description',
355 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
356 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
356 'mergeable', 'source', 'target', 'author', 'reviewers'))
357 'mergeable', 'source', 'target', 'author', 'reviewers'))
357
358
358
359
359 log_review_pull_request = ExtensionCallback(
360 log_review_pull_request = ExtensionCallback(
360 hook_name='REVIEW_PULL_REQUEST',
361 hook_name='REVIEW_PULL_REQUEST',
361 kwargs_keys=(
362 kwargs_keys=(
362 'server_url', 'config', 'scm', 'username', 'ip', 'action',
363 'server_url', 'config', 'scm', 'username', 'ip', 'action',
363 'repository', 'pull_request_id', 'url', 'title', 'description',
364 'repository', 'pull_request_id', 'url', 'title', 'description',
364 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
365 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
365 'mergeable', 'source', 'target', 'author', 'reviewers'))
366 'mergeable', 'source', 'target', 'author', 'reviewers'))
366
367
367
368
368 log_update_pull_request = ExtensionCallback(
369 log_update_pull_request = ExtensionCallback(
369 hook_name='UPDATE_PULL_REQUEST',
370 hook_name='UPDATE_PULL_REQUEST',
370 kwargs_keys=(
371 kwargs_keys=(
371 'server_url', 'config', 'scm', 'username', 'ip', 'action',
372 'server_url', 'config', 'scm', 'username', 'ip', 'action',
372 'repository', 'pull_request_id', 'url', 'title', 'description',
373 'repository', 'pull_request_id', 'url', 'title', 'description',
373 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
374 'status', 'created_on', 'updated_on', 'commit_ids', 'review_status',
374 'mergeable', 'source', 'target', 'author', 'reviewers'))
375 'mergeable', 'source', 'target', 'author', 'reviewers'))
375
376
376
377
377 log_create_user = ExtensionCallback(
378 log_create_user = ExtensionCallback(
378 hook_name='CREATE_USER_HOOK',
379 hook_name='CREATE_USER_HOOK',
379 kwargs_keys=(
380 kwargs_keys=(
380 'username', 'full_name_or_username', 'full_contact', 'user_id',
381 'username', 'full_name_or_username', 'full_contact', 'user_id',
381 'name', 'firstname', 'short_contact', 'admin', 'lastname',
382 'name', 'firstname', 'short_contact', 'admin', 'lastname',
382 'ip_addresses', 'extern_type', 'extern_name',
383 'ip_addresses', 'extern_type', 'extern_name',
383 'email', 'api_keys', 'last_login',
384 'email', 'api_keys', 'last_login',
384 'full_name', 'active', 'password', 'emails',
385 'full_name', 'active', 'password', 'emails',
385 'inherit_default_permissions', 'created_by', 'created_on'))
386 'inherit_default_permissions', 'created_by', 'created_on'))
386
387
387
388
388 log_delete_user = ExtensionCallback(
389 log_delete_user = ExtensionCallback(
389 hook_name='DELETE_USER_HOOK',
390 hook_name='DELETE_USER_HOOK',
390 kwargs_keys=(
391 kwargs_keys=(
391 'username', 'full_name_or_username', 'full_contact', 'user_id',
392 'username', 'full_name_or_username', 'full_contact', 'user_id',
392 'name', 'firstname', 'short_contact', 'admin', 'lastname',
393 'name', 'firstname', 'short_contact', 'admin', 'lastname',
393 'ip_addresses',
394 'ip_addresses',
394 'email', 'last_login',
395 'email', 'last_login',
395 'full_name', 'active', 'password', 'emails',
396 'full_name', 'active', 'password', 'emails',
396 'inherit_default_permissions', 'deleted_by'))
397 'inherit_default_permissions', 'deleted_by'))
397
398
398
399
399 log_create_repository = ExtensionCallback(
400 log_create_repository = ExtensionCallback(
400 hook_name='CREATE_REPO_HOOK',
401 hook_name='CREATE_REPO_HOOK',
401 kwargs_keys=(
402 kwargs_keys=(
402 'repo_name', 'repo_type', 'description', 'private', 'created_on',
403 'repo_name', 'repo_type', 'description', 'private', 'created_on',
403 'enable_downloads', 'repo_id', 'user_id', 'enable_statistics',
404 'enable_downloads', 'repo_id', 'user_id', 'enable_statistics',
404 'clone_uri', 'fork_id', 'group_id', 'created_by'))
405 'clone_uri', 'fork_id', 'group_id', 'created_by'))
405
406
406
407
407 log_delete_repository = ExtensionCallback(
408 log_delete_repository = ExtensionCallback(
408 hook_name='DELETE_REPO_HOOK',
409 hook_name='DELETE_REPO_HOOK',
409 kwargs_keys=(
410 kwargs_keys=(
410 'repo_name', 'repo_type', 'description', 'private', 'created_on',
411 'repo_name', 'repo_type', 'description', 'private', 'created_on',
411 'enable_downloads', 'repo_id', 'user_id', 'enable_statistics',
412 'enable_downloads', 'repo_id', 'user_id', 'enable_statistics',
412 'clone_uri', 'fork_id', 'group_id', 'deleted_by', 'deleted_on'))
413 'clone_uri', 'fork_id', 'group_id', 'deleted_by', 'deleted_on'))
413
414
414
415
415 log_create_repository_group = ExtensionCallback(
416 log_create_repository_group = ExtensionCallback(
416 hook_name='CREATE_REPO_GROUP_HOOK',
417 hook_name='CREATE_REPO_GROUP_HOOK',
417 kwargs_keys=(
418 kwargs_keys=(
418 'group_name', 'group_parent_id', 'group_description',
419 'group_name', 'group_parent_id', 'group_description',
419 'group_id', 'user_id', 'created_by', 'created_on',
420 'group_id', 'user_id', 'created_by', 'created_on',
420 'enable_locking'))
421 'enable_locking'))
General Comments 0
You need to be logged in to leave comments. Login now