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

Side by Side Diff: utils.py

Issue 13892003: Added buildbot appengine frontend for chromium-build app (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/tools/chromium-build
Patch Set: Review fixes Created 7 years, 8 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 | Annotate | Revision Log
« templates/step.html ('K') | « templates/viewer_base.html ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1
1 # Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 # Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be 3 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file. 4 # found in the LICENSE file.
4 5
5 """Utils.""" 6 """Utils."""
6 7
8 import re
9 import time
10 import random
11 import logging
12 import sys
13 import string
14 import json
15
7 from google.appengine.api import users 16 from google.appengine.api import users
8 17
9 18
10 def admin_only(func): 19 def admin_only(func):
11 """Valid for BasePage objects only.""" 20 """Valid for BasePage objects only."""
12 def decorated(self, *args, **kwargs): 21 def decorated(self, *args, **kwargs):
13 if self.is_admin: 22 if self.is_admin:
14 return func(self, *args, **kwargs) 23 return func(self, *args, **kwargs)
15 else: 24 else:
16 self.response.headers['Content-Type'] = 'text/plain' 25 self.response.headers['Content-Type'] = 'text/plain'
(...skipping 11 matching lines...) Expand all
28 37
29 38
30 def require_user(func): 39 def require_user(func):
31 """A user must be logged in.""" 40 """A user must be logged in."""
32 def decorated(self, *args, **kwargs): 41 def decorated(self, *args, **kwargs):
33 if not self.user: 42 if not self.user:
34 self.redirect(users.create_login_url(self.request.url)) 43 self.redirect(users.create_login_url(self.request.url))
35 else: 44 else:
36 return func(self, *args, **kwargs) 45 return func(self, *args, **kwargs)
37 return decorated 46 return decorated
47
48
49 ############
50 # Decorators
51 ############
52
53 def render(template_filename, jinja_environment):
54 """Use a template to render results. The wrapped function is expected to
55 return a dict."""
56 def _render(fn):
57 def wrapper(self, *args, **kwargs):
58 results = fn(self, *args, **kwargs)
59 template = jinja_environment.get_template(template_filename)
60 self.response.out.write(template.render(results))
61 return wrapper
62 return _render
63
64
65 def render_iff_new_flag_set(template_filename, jinja_environment):
66 """Use the given template if and only if the 'new' flag is set by:
67 * The presence of the 'new' cookie.
68 * 'new' is passed in as an url parameter."""
69 def _render(fn):
70 def wrapper(self, *args, **kwargs):
71 new = self.request.get('new') or self.request.cookies.get('new')
72 kwargs.update({'new': new})
73 results = fn(self, *args, **kwargs)
74 if new:
75 template = jinja_environment.get_template(template_filename)
76 try:
77 self.response.out.write(template.render(results))
78 except Exception as e:
79 logging.error('Caught exception while calling %s with template %s' %
80 (self.__class__.__name__, template_filename))
81 raise e, None, sys.exc_info()[2]
82 else:
83 # Just treat the results as a large string blob.
84 self.response.out.write(results)
85 return wrapper
86 return _render
87
88
89 def render_json(fn):
90 """The function is expected to return a dict, and we want to render json."""
91 def wrapper(self, *args, **kwargs):
92 results = fn(self, *args, **kwargs)
93 self.response.out.write(json.dumps(results))
94 return wrapper
95
96
97 def maybe_render_json(template_filename, jinja_environment):
98 """If the variable 'json' exists in the request, return a json object.
99 Otherwise render the page using the template"""
100 def _render(fn):
101 def wrapper(self, *args, **kwargs):
102 results = fn(self, *args, **kwargs)
103 if self.request.get('json'):
104 self.response.out.write(json.dumps(results))
105 else:
106 template = jinja_environment.get_template(template_filename)
107 self.response.out.write(template.render(results))
108 return wrapper
109 return _render
110
111
112 def login_required(fn):
113 """Redirect user to a login page."""
114 def wrapper(self, *args, **kwargs):
115 user = users.get_current_user()
116 if not user:
117 self.redirect(users.create_login_url(self.request.uri))
118 return
119 else:
120 return fn(self, *args, **kwargs)
121 return wrapper
122
123
124 def google_login_required(fn):
125 """Return 403 unless the user is logged in from a @google.com domain."""
126 def wrapper(self, *args, **kwargs):
127 user = users.get_current_user()
128 if not user:
129 self.redirect(users.create_login_url(self.request.uri))
130 return
131 email_match = re.match('^(.*)@(.*)$', user.email())
132 if email_match:
133 _, domain = email_match.groups()
134 if domain == 'google.com':
135 return fn(self, *args, **kwargs)
136 self.error(403) # Unrecognized email or unauthroized domain.
137 self.response.out.write('unauthroized email %s' % user.user_id())
138 return wrapper
139
140
141 def admin_required(fn):
142 """Return 403 unless an admin is logged in."""
143 def wrapper(self, *args, **kwargs):
144 user = users.get_current_user()
145 if not user:
146 self.redirect(users.create_login_url(self.request.uri))
147 return
148 elif not users.is_current_user_admin():
149 self.error(403)
150 return
151 else:
152 return fn(self, *args, **kwargs)
153 return wrapper
154
155
156 def expect_request_param(*request_args):
157 """Strips out the expected args from a request and feeds it into the function
158 as the arguments. Optionally, typecast the argument from a string into a
159 different class. Examples include:
160 name (Get the request object called "name")
161 time as timestamp (Get "time", pass it in as "timestamp")
162 """
163 def _decorator(fn):
164 def wrapper(self, *args, **kwargs):
165 request_kwargs = {}
166 for arg in request_args:
167 # TODO(hinoka): Optional typecasting?
168 arg_match = re.match(r'^(\((\w+)\))?\s*(\w+)( as (\w+))?$', arg)
169 if arg_match:
170 _, _, name, _, target_name = arg_match.groups()
171 if not target_name:
172 target_name = name
173 request_item = self.request.get(name)
174 request_kwargs[target_name] = request_item
175 else:
176 raise Exception('Incorrect format %s' % arg)
177 kwargs.update(request_kwargs)
178 return fn(self, *args, **kwargs)
179 return wrapper
180 return _decorator
181
182
183 ###############
184 # Jinja filters
185 ###############
186
187 def delta_time(delta):
188 hours = int(delta/60/60)
189 minutes = int((delta - hours * 3600)/60)
190 seconds = int(delta - (hours * 3600) - (minutes * 60))
191 result = ''
192 if hours > 1:
193 result += '%d hrs, ' % hours
194 elif hours:
195 result += '%d hr, ' % hours
196 if minutes > 1:
197 result += '%d mins ' % minutes
198 elif minutes:
199 result += '%d min ' % minutes
200 if not hours:
201 if seconds > 1 or seconds == 0:
202 result += '%d secs.' % seconds
203 else:
204 result += '%d sec.' % seconds
205 return result
206
207
208 def time_since(timestamp):
209 delta = time.time() - timestamp
210 return delta_time(delta)
211
212
213 def nl2br(value):
214 return value.replace('\n','<br>\n')
215
216
217 def rot13_email(value):
218 nonce = ''.join(random.choice(
219 string.ascii_uppercase + string.digits) for x in range(6))
220 rep = ('<span id="obf-%s"><script>document.getElementById("obf-%s").'
221 'innerHTML="<n uers=\\"znvygb:%s\\" gnetrg=\\"_oynax\\">%s</n>".'
222 'replace(/[a-zA-Z]/g,function(c){return String.fromCharCode(('
223 'c<="Z"?90:122)>=(c=c.charCodeAt(0)+13)?c:c-26);});</script>'
224 '<noscript><span style="unicode-bidi:bidi-override;direction:rtl;"'
225 '>%s</span></noscript></span>')
226 return rep % (nonce, nonce, value.encode('rot13'),
227 value.encode('rot13'), value[::-1])
228
229
230 def _blockquote(value):
231 """Wrap blockquote levels recursively."""
232 new_value = ''
233 blockquote = False
234 for line in value.splitlines():
235 if blockquote:
236 if line.startswith('>'):
237 new_value += '%s\n' % line[1:].strip()
238 else:
239 blockquote = False
240 new_value += '</blockquote>%s\n' % line
241 else:
242 if line.startswith('>'):
243 blockquote = True
244 new_value += '<blockquote>%s\n' % line[1:].strip()
245 else:
246 new_value += '%s\n' % line
247 if blockquote:
248 new_value += '</blockquote>'
249 if re.search(r'^>', new_value, re.M):
250 return _blockquote(new_value)
251 else:
252 return new_value
253
254
255 def _resolve_crbug(match):
256 results = []
257 bugs = match.group(1).split(',')
258 for bug in bugs:
259 results.append('<a href="http://crbug.com/%s">%s</a>' % (bug, bug))
260 return 'BUG=%s' % ','.join(results)
261
262
263 def cl_comment(value):
264 """Add links to https:// addresses, BUG=####, and trim excessive newlines."""
265 value = re.sub(r'(https?://.*)', r'<a href="\1">\1</a>', value)
266 value = re.sub(r'BUG=([\d,]+)', _resolve_crbug, value)
267 # Add blockquotes.
268 value = _blockquote(value)
269 value = re.sub(r'\n', r'<br>', value)
270 # Obfuscure email addresses with rot13 encoding.
271 value = re.sub(r'(\w+@[\w.]+)', lambda m: rot13_email(m.group(1)), value)
272 return value
OLDNEW
« templates/step.html ('K') | « templates/viewer_base.html ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698