##// END OF EJS Templates
typing: added typehint
super-admin -
r5141:d2b5dad9 default
parent child Browse files
Show More
@@ -1,242 +1,241 b''
1 1 # Copyright (C) 2012-2023 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 import re
19 19 import textwrap
20 20 import dataclasses
21 21 import logging
22 import typing
23 22
24 23 from mako.template import Template
25 24
26 25 from rhodecode import events
27 26 from rhodecode.integrations.types.base import CommitParsingDataHandler, render_with_traceback
28 27
29 28 log = logging.getLogger(__name__)
30 29
31 30
32 31 @dataclasses.dataclass
33 32 class SlackData:
34 33 title: str
35 34 text: str
36 35 fields: list[dict] | None = None
37 36 overrides: dict | None = None
38 37
39 38
40 39 def html_to_slack_links(message):
41 40 return re.compile(r'<a .*?href=["\'](.+?)".*?>(.+?)</a>').sub(r'<\1|\2>', message)
42 41
43 42
44 43 REPO_PUSH_TEMPLATE = Template('''
45 44 <%
46 45 def branch_text(branch):
47 46 if branch:
48 47 return 'on branch: <{}|{}>'.format(branch_commits['branch']['url'], branch_commits['branch']['name'])
49 48 else:
50 49 ## case for SVN no branch push...
51 50 return 'to trunk'
52 51 %> \
53 52
54 53 % for branch, branch_commits in branches_commits.items():
55 54 ${len(branch_commits['commits'])} ${'commit' if len(branch_commits['commits']) == 1 else 'commits'} ${branch_text(branch)}
56 55 % for commit in branch_commits['commits']:
57 56 `<${commit['url']}|${commit['short_id']}>` - ${commit['message_html']|html_to_slack_links}
58 57 % endfor
59 58 % endfor
60 59 ''')
61 60
62 61
63 62 class SlackDataHandler(CommitParsingDataHandler):
64 63 name = 'slack'
65 64
66 65 def __init__(self):
67 66 pass
68 67
69 def __call__(self, event: events.RhodecodeEvent, data):
68 def __call__(self, event: events.RhodecodeEvent, data) -> SlackData:
70 69 if not isinstance(event, events.RhodecodeEvent):
71 70 raise TypeError(f"event {event} is not subtype of events.RhodecodeEvent")
72 71
73 72 actor = data["actor"]["username"]
74 73 default_title = f'*{actor}* caused a *{event.name}* event'
75 74 default_text = f'*{actor}* caused a *{event.name}* event'
76 75
77 76 default_slack_data = SlackData(title=default_title, text=default_text)
78 77
79 78 if isinstance(event, events.PullRequestCommentEvent):
80 79 return self.format_pull_request_comment_event(
81 80 event, data, default_slack_data
82 81 )
83 82 elif isinstance(event, events.PullRequestCommentEditEvent):
84 83 return self.format_pull_request_comment_event(
85 84 event, data, default_slack_data
86 85 )
87 86 elif isinstance(event, events.PullRequestReviewEvent):
88 87 return self.format_pull_request_review_event(event, data, default_slack_data)
89 88 elif isinstance(event, events.PullRequestEvent):
90 89 return self.format_pull_request_event(event, data, default_slack_data)
91 90 elif isinstance(event, events.RepoPushEvent):
92 91 return self.format_repo_push_event(event, data, default_slack_data)
93 92 elif isinstance(event, events.RepoCreateEvent):
94 93 return self.format_repo_create_event(event, data, default_slack_data)
95 94 else:
96 95 raise ValueError(
97 96 f'event type `{event.__class__}` has no handler defined')
98 97
99 98 def format_pull_request_comment_event(self, event, data, slack_data):
100 99 comment_text = data['comment']['text']
101 100 if len(comment_text) > 200:
102 101 comment_text = '<{comment_url}|{comment_text}...>'.format(
103 102 comment_text=comment_text[:200],
104 103 comment_url=data['comment']['url'],
105 104 )
106 105
107 106 fields = None
108 107 overrides = None
109 108 status_text = None
110 109
111 110 if data['comment']['status']:
112 111 status_color = {
113 112 'approved': '#0ac878',
114 113 'rejected': '#e85e4d'}.get(data['comment']['status'])
115 114
116 115 if status_color:
117 116 overrides = {"color": status_color}
118 117
119 118 status_text = data['comment']['status']
120 119
121 120 if data['comment']['file']:
122 121 fields = [
123 122 {
124 123 "title": "file",
125 124 "value": data['comment']['file']
126 125 },
127 126 {
128 127 "title": "line",
129 128 "value": data['comment']['line']
130 129 }
131 130 ]
132 131
133 132 template = Template(textwrap.dedent(r'''
134 133 *${data['actor']['username']}* left ${data['comment']['type']} on pull request <${data['pullrequest']['url']}|#${data['pullrequest']['pull_request_id']}>:
135 134 '''))
136 135 title = render_with_traceback(
137 136 template, data=data, comment=event.comment)
138 137
139 138 template = Template(textwrap.dedent(r'''
140 139 *pull request title*: ${pr_title}
141 140 % if status_text:
142 141 *submitted status*: `${status_text}`
143 142 % endif
144 143 >>> ${comment_text}
145 144 '''))
146 145 text = render_with_traceback(
147 146 template,
148 147 comment_text=comment_text,
149 148 pr_title=data['pullrequest']['title'],
150 149 status_text=status_text)
151 150
152 151 slack_data.title = title
153 152 slack_data.text = text
154 153 slack_data.fields = fields
155 154 slack_data.overrides = overrides
156 155
157 156 return slack_data
158 157
159 158 def format_pull_request_review_event(self, event, data, slack_data) -> SlackData:
160 159 template = Template(textwrap.dedent(r'''
161 160 *${data['actor']['username']}* changed status of pull request <${data['pullrequest']['url']}|#${data['pullrequest']['pull_request_id']} to `${data['pullrequest']['status']}`>:
162 161 '''))
163 162 title = render_with_traceback(template, data=data)
164 163
165 164 template = Template(textwrap.dedent(r'''
166 165 *pull request title*: ${pr_title}
167 166 '''))
168 167 text = render_with_traceback(
169 168 template,
170 169 pr_title=data['pullrequest']['title'])
171 170
172 171 slack_data.title = title
173 172 slack_data.text = text
174 173
175 174 return slack_data
176 175
177 176 def format_pull_request_event(self, event, data, slack_data) -> SlackData:
178 177 action = {
179 178 events.PullRequestCloseEvent: 'closed',
180 179 events.PullRequestMergeEvent: 'merged',
181 180 events.PullRequestUpdateEvent: 'updated',
182 181 events.PullRequestCreateEvent: 'created',
183 182 }.get(event.__class__, str(event.__class__))
184 183
185 184 template = Template(textwrap.dedent(r'''
186 185 *${data['actor']['username']}* `${action}` pull request <${data['pullrequest']['url']}|#${data['pullrequest']['pull_request_id']}>:
187 186 '''))
188 187 title = render_with_traceback(template, data=data, action=action)
189 188
190 189 template = Template(textwrap.dedent(r'''
191 190 *pull request title*: ${pr_title}
192 191 %if data['pullrequest']['commits']:
193 192 *commits*: ${len(data['pullrequest']['commits'])}
194 193 %endif
195 194 '''))
196 195 text = render_with_traceback(
197 196 template,
198 197 pr_title=data['pullrequest']['title'],
199 198 data=data)
200 199
201 200 slack_data.title = title
202 201 slack_data.text = text
203 202
204 203 return slack_data
205 204
206 205 def format_repo_push_event(self, event, data, slack_data) -> SlackData:
207 206 branches_commits = self.aggregate_branch_data(
208 207 data['push']['branches'], data['push']['commits'])
209 208
210 209 template = Template(r'''
211 210 *${data['actor']['username']}* pushed to repo <${data['repo']['url']}|${data['repo']['repo_name']}>:
212 211 ''')
213 212 title = render_with_traceback(template, data=data)
214 213
215 214 text = render_with_traceback(
216 215 REPO_PUSH_TEMPLATE,
217 216 data=data,
218 217 branches_commits=branches_commits,
219 218 html_to_slack_links=html_to_slack_links,
220 219 )
221 220
222 221 slack_data.title = title
223 222 slack_data.text = text
224 223
225 224 return slack_data
226 225
227 226 def format_repo_create_event(self, event, data, slack_data) -> SlackData:
228 227 template = Template(r'''
229 228 *${data['actor']['username']}* created new repository ${data['repo']['repo_name']}:
230 229 ''')
231 230 title = render_with_traceback(template, data=data)
232 231
233 232 template = Template(textwrap.dedent(r'''
234 233 repo_url: ${data['repo']['url']}
235 234 repo_type: ${data['repo']['repo_type']}
236 235 '''))
237 236 text = render_with_traceback(template, data=data)
238 237
239 238 slack_data.title = title
240 239 slack_data.text = text
241 240
242 241 return slack_data No newline at end of file
General Comments 0
You need to be logged in to leave comments. Login now