Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(47)

Side by Side Diff: appengine/findit/common/rietveld.py

Issue 2079773004: [Findit] Add a Rietveld client to post a message to codereview of a culprit. (Closed) Base URL: https://chromium.googlesource.com/infra/infra.git@master
Patch Set: Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 # Copyright 2016 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file.
4
5 import logging
6 import re
7 import urlparse
8
9 from common.codereview import CodeReview
10 from common.http_client_appengine import HttpClientAppengine
11
12
13 _RIETVELD_ISSUE_NUMBER_RE = re.compile('^/(\d+)/?.*')
14
15
16 class Rietveld(CodeReview):
17 """The implementation of CodeReview interface for Rietveld."""
18 HTTP_CLIENT = HttpClientAppengine()
19
20 def _GetXsrfToken(self, rietveld_url):
21 """Returns the xsrf token for follow-up requests."""
22 headers = {
23 'X-Requesting-XSRF-Token': '1',
24 'Accept': 'text/plain',
25 }
26 url = '%s/xsrf_token' % rietveld_url
27 status_code, xsrf_token = self.HTTP_CLIENT.Post(
28 url, data=None, headers=headers)
29 if status_code != 200:
30 logging.error('Failed to get xsrf token from %s', rietveld_url)
31 xsrf_token = None
32 return xsrf_token
33
34 def _GetRietveldUrlAndIssueNumber(self, issue_url):
35 """Parses the given Rietveld issue url.
36
37 Args:
38 issue_url(str): The url to an issue on Rietveld.
39 Returns:
40 (rietveld_url, issue_number)
41 rietveld_url(str): The root url of the Rietveld app.
42 issue_number(str): The issue number.
43 """
44 u = urlparse.urlparse(issue_url)
45 rietveld_url = 'https://%s' % u.netloc # Enforce https.
chanli 2016/06/21 21:38:11 nit: Enforces?
stgao 2016/06/24 04:24:51 Done.
46 issue_number = _RIETVELD_ISSUE_NUMBER_RE.match(u.path).group(1)
47 return rietveld_url, issue_number
48
49 def _EncodeMultipartFormData(self, fields):
50 """Encodes form fields for multipart/form-data"""
51 BOUNDARY = '-F-I-N-D-I-T-M-E-S-S-A-G-E-'
52 CRLF = '\r\n'
53 lines = []
54 for key, value in fields.iteritems():
55 lines.append('--' + BOUNDARY)
56 lines.append('Content-Disposition: form-data; name="%s"' % key)
57 lines.append('')
58 lines.append(str(value))
59 lines.append('--' + BOUNDARY + '--')
60 lines.append('')
61 body = CRLF.join(lines)
62 content_type = 'multipart/form-data; boundary=%s' % BOUNDARY
63 return content_type, body
64
65 def PostMessage(self, issue_url, message):
66 rietveld_url, issue_number = self._GetRietveldUrlAndIssueNumber(issue_url)
67 url = '%s/%s/publish' % (rietveld_url, issue_number)
68 xsrf_token = self._GetXsrfToken(rietveld_url)
69 if not xsrf_token:
70 return False
71 form_fields = {
72 'xsrf_token': xsrf_token,
73 'message': message,
74 'message_only': 'True',
75 'add_as_reviewer': 'False',
76 'send_mail': 'True',
77 'no_redirect': 'True',
78 }
79 content_type, body = self._EncodeMultipartFormData(form_fields)
80 headers = {
81 'Content-Type': content_type,
82 'Accept': 'text/plain',
83 }
84 status_code, content = self.HTTP_CLIENT.Post(
85 url, data=body, headers=headers)
86 return status_code == 200 and content == 'OK'
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698