##// END OF EJS Templates
events: fix bug with _commits_as_dict which was returning only...
dan -
r795:bf02f99d default
parent child Browse files
Show More
@@ -1,257 +1,258 b''
1 1 # Copyright (C) 2016-2016 RhodeCode GmbH
2 2 #
3 3 # This program is free software: you can redistribute it and/or modify
4 4 # it under the terms of the GNU Affero General Public License, version 3
5 5 # (only), as published by the Free Software Foundation.
6 6 #
7 7 # This program is distributed in the hope that it will be useful,
8 8 # but WITHOUT ANY WARRANTY; without even the implied warranty of
9 9 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 10 # GNU General Public License for more details.
11 11 #
12 12 # You should have received a copy of the GNU Affero General Public License
13 13 # along with this program. If not, see <http://www.gnu.org/licenses/>.
14 14 #
15 15 # This program is dual-licensed. If you wish to learn more about the
16 16 # RhodeCode Enterprise Edition, including its added features, Support services,
17 17 # and proprietary license terms, please see https://rhodecode.com/licenses/
18 18
19 19 import logging
20 20
21 21 from rhodecode.translation import lazy_ugettext
22 22 from rhodecode.model.db import User, Repository, Session
23 23 from rhodecode.events.base import RhodecodeEvent
24 24 from rhodecode.lib.vcs.exceptions import CommitDoesNotExistError
25 25
26 26 log = logging.getLogger(__name__)
27 27
28 28 def _commits_as_dict(commit_ids, repos):
29 29 """
30 30 Helper function to serialize commit_ids
31 31
32 32 :param commit_ids: commits to get
33 33 :param repos: list of repos to check
34 34 """
35 35 from rhodecode.lib.utils2 import extract_mentioned_users
36 36 from rhodecode.model.db import Repository
37 37 from rhodecode.lib import helpers as h
38 38 from rhodecode.lib.helpers import process_patterns
39 39 from rhodecode.lib.helpers import urlify_commit_message
40 40
41 41 if not repos:
42 42 raise Exception('no repo defined')
43 43
44 44 if not isinstance(repos, (tuple, list)):
45 45 repos = [repos]
46 46
47 47 if not commit_ids:
48 48 return []
49 49
50 50 needed_commits = list(commit_ids)
51 51
52 52 commits = []
53 53 reviewers = []
54 54 for repo in repos:
55 55 if not needed_commits:
56 56 return commits # return early if we have the commits we need
57 57
58 58 vcs_repo = repo.scm_instance(cache=False)
59 59 try:
60 for commit_id in needed_commits:
60 # use copy of needed_commits since we modify it while iterating
61 for commit_id in list(needed_commits):
61 62 try:
62 63 cs = vcs_repo.get_changeset(commit_id)
63 64 except CommitDoesNotExistError:
64 65 continue # maybe its in next repo
65 66
66 67 cs_data = cs.__json__()
67 68 cs_data['mentions'] = extract_mentioned_users(cs_data['message'])
68 69 cs_data['reviewers'] = reviewers
69 70 cs_data['url'] = h.url('changeset_home',
70 71 repo_name=repo.repo_name,
71 72 revision=cs_data['raw_id'],
72 73 qualified=True
73 74 )
74 75 urlified_message, issues_data = process_patterns(
75 76 cs_data['message'], repo.repo_name)
76 77 cs_data['issues'] = issues_data
77 78 cs_data['message_html'] = urlify_commit_message(cs_data['message'],
78 79 repo.repo_name)
79 80 commits.append(cs_data)
80 81
81 82 needed_commits.remove(commit_id)
82 83
83 84 except Exception as e:
84 85 log.exception(e)
85 86 # we don't send any commits when crash happens, only full list matters
86 87 # we short circuit then.
87 88 return []
88 89
89 90 missing_commits = set(commit_ids) - set(c['raw_id'] for c in commits)
90 91 if missing_commits:
91 92 log.error('missing commits: %s' % ', '.join(missing_commits))
92 93
93 94 return commits
94 95
95 96
96 97 def _issues_as_dict(commits):
97 98 """ Helper function to serialize issues from commits """
98 99 issues = {}
99 100 for commit in commits:
100 101 for issue in commit['issues']:
101 102 issues[issue['id']] = issue
102 103 return issues
103 104
104 105 class RepoEvent(RhodecodeEvent):
105 106 """
106 107 Base class for events acting on a repository.
107 108
108 109 :param repo: a :class:`Repository` instance
109 110 """
110 111
111 112 def __init__(self, repo):
112 113 super(RepoEvent, self).__init__()
113 114 self.repo = repo
114 115
115 116 def as_dict(self):
116 117 from rhodecode.model.repo import RepoModel
117 118 data = super(RepoEvent, self).as_dict()
118 119 data.update({
119 120 'repo': {
120 121 'repo_id': self.repo.repo_id,
121 122 'repo_name': self.repo.repo_name,
122 123 'repo_type': self.repo.repo_type,
123 124 'url': RepoModel().get_url(self.repo)
124 125 }
125 126 })
126 127 return data
127 128
128 129
129 130 class RepoPreCreateEvent(RepoEvent):
130 131 """
131 132 An instance of this class is emitted as an :term:`event` before a repo is
132 133 created.
133 134 """
134 135 name = 'repo-pre-create'
135 136 display_name = lazy_ugettext('repository pre create')
136 137
137 138
138 139 class RepoCreateEvent(RepoEvent):
139 140 """
140 141 An instance of this class is emitted as an :term:`event` whenever a repo is
141 142 created.
142 143 """
143 144 name = 'repo-create'
144 145 display_name = lazy_ugettext('repository created')
145 146
146 147
147 148 class RepoPreDeleteEvent(RepoEvent):
148 149 """
149 150 An instance of this class is emitted as an :term:`event` whenever a repo is
150 151 created.
151 152 """
152 153 name = 'repo-pre-delete'
153 154 display_name = lazy_ugettext('repository pre delete')
154 155
155 156
156 157 class RepoDeleteEvent(RepoEvent):
157 158 """
158 159 An instance of this class is emitted as an :term:`event` whenever a repo is
159 160 created.
160 161 """
161 162 name = 'repo-delete'
162 163 display_name = lazy_ugettext('repository deleted')
163 164
164 165
165 166 class RepoVCSEvent(RepoEvent):
166 167 """
167 168 Base class for events triggered by the VCS
168 169 """
169 170 def __init__(self, repo_name, extras):
170 171 self.repo = Repository.get_by_repo_name(repo_name)
171 172 if not self.repo:
172 173 raise Exception('repo by this name %s does not exist' % repo_name)
173 174 self.extras = extras
174 175 super(RepoVCSEvent, self).__init__(self.repo)
175 176
176 177 @property
177 178 def actor(self):
178 179 if self.extras.get('username'):
179 180 return User.get_by_username(self.extras['username'])
180 181
181 182 @property
182 183 def actor_ip(self):
183 184 if self.extras.get('ip'):
184 185 return self.extras['ip']
185 186
186 187 @property
187 188 def server_url(self):
188 189 if self.extras.get('server_url'):
189 190 return self.extras['server_url']
190 191
191 192
192 193 class RepoPrePullEvent(RepoVCSEvent):
193 194 """
194 195 An instance of this class is emitted as an :term:`event` before commits
195 196 are pulled from a repo.
196 197 """
197 198 name = 'repo-pre-pull'
198 199 display_name = lazy_ugettext('repository pre pull')
199 200
200 201
201 202 class RepoPullEvent(RepoVCSEvent):
202 203 """
203 204 An instance of this class is emitted as an :term:`event` after commits
204 205 are pulled from a repo.
205 206 """
206 207 name = 'repo-pull'
207 208 display_name = lazy_ugettext('repository pull')
208 209
209 210
210 211 class RepoPrePushEvent(RepoVCSEvent):
211 212 """
212 213 An instance of this class is emitted as an :term:`event` before commits
213 214 are pushed to a repo.
214 215 """
215 216 name = 'repo-pre-push'
216 217 display_name = lazy_ugettext('repository pre push')
217 218
218 219
219 220 class RepoPushEvent(RepoVCSEvent):
220 221 """
221 222 An instance of this class is emitted as an :term:`event` after commits
222 223 are pushed to a repo.
223 224
224 225 :param extras: (optional) dict of data from proxied VCS actions
225 226 """
226 227 name = 'repo-push'
227 228 display_name = lazy_ugettext('repository push')
228 229
229 230 def __init__(self, repo_name, pushed_commit_ids, extras):
230 231 super(RepoPushEvent, self).__init__(repo_name, extras)
231 232 self.pushed_commit_ids = pushed_commit_ids
232 233
233 234 def as_dict(self):
234 235 data = super(RepoPushEvent, self).as_dict()
235 236 branch_url = repo_url = data['repo']['url']
236 237
237 238 commits = _commits_as_dict(
238 239 commit_ids=self.pushed_commit_ids, repos=[self.repo])
239 240 issues = _issues_as_dict(commits)
240 241
241 242 branches = set(
242 243 commit['branch'] for commit in commits if commit['branch'])
243 244 branches = [
244 245 {
245 246 'name': branch,
246 247 'url': '{}/changelog?branch={}'.format(
247 248 data['repo']['url'], branch)
248 249 }
249 250 for branch in branches
250 251 ]
251 252
252 253 data['push'] = {
253 254 'commits': commits,
254 255 'issues': issues,
255 256 'branches': branches,
256 257 }
257 258 return data
General Comments 0
You need to be logged in to leave comments. Login now