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

Side by Side Diff: infra_libs/httplib2_utils.py

Issue 2114073002: Add HttpsMonitor (Closed) Base URL: https://chromium.googlesource.com/infra/infra.git@master
Patch Set: Add retryable and other things Created 4 years, 5 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
1 # Copyright 2015 The Chromium Authors. All rights reserved. 1 # Copyright 2015 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be 2 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file. 3 # found in the LICENSE file.
4 4
5 import collections 5 import collections
6 import copy 6 import copy
7 import json 7 import json
8 import logging 8 import logging
9 import os 9 import os
10 import re 10 import re
11 import socket 11 import socket
12 import sys 12 import sys
13 import time 13 import time
14 14
15 import httplib2 15 import httplib2
16 import oauth2client.client 16 import oauth2client.client
17 17
18 from googleapiclient import errors
18 from infra_libs.ts_mon.common import http_metrics 19 from infra_libs.ts_mon.common import http_metrics
19 20
20 DEFAULT_SCOPES = ['email'] 21 DEFAULT_SCOPES = ['email']
21 22
22 # default timeout for http requests, in seconds 23 # default timeout for http requests, in seconds
23 DEFAULT_TIMEOUT = 30 24 DEFAULT_TIMEOUT = 30
24 25
25 # This is part of the API. 26 # This is part of the API.
26 if sys.platform.startswith('win'): # pragma: no cover 27 if sys.platform.startswith('win'): # pragma: no cover
27 SERVICE_ACCOUNTS_CREDS_ROOT = 'C:\\creds\\service_accounts' 28 SERVICE_ACCOUNTS_CREDS_ROOT = 'C:\\creds\\service_accounts'
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after
154 credentials_filename, 155 credentials_filename,
155 scope=scope, 156 scope=scope,
156 service_accounts_creds_root=service_accounts_creds_root) 157 service_accounts_creds_root=service_accounts_creds_root)
157 158
158 if http_identifier: 159 if http_identifier:
159 http = InstrumentedHttp(http_identifier, timeout=timeout) 160 http = InstrumentedHttp(http_identifier, timeout=timeout)
160 else: 161 else:
161 http = httplib2.Http(timeout=timeout) 162 http = httplib2.Http(timeout=timeout)
162 return creds.authorize(http) 163 return creds.authorize(http)
163 164
165 class RetryableHttp(object):
Sergey Berezin 2016/07/06 20:13:28 nit (spelling): Retriable
Sergey Berezin 2016/07/06 20:13:29 Inherit from httplib2.Http, and call base class's
tnn 2016/07/06 22:05:18 Done.
166 """A httplib2.Http object that retries on failure."""
167
168 def __init__(self, http_obj, max_tries=5,
169 retrying_statuses=range(500,599)):
Sergey Berezin 2016/07/06 20:13:28 For efficiency, I'd either make it a set(range(500
tnn 2016/07/06 22:05:17 Done.
170 """
171 Args:
172 http_obj: an httplib2.Http instance
173 max_tries: a number of maximum tries
174 retrying_status_codes: a set of HTTP status codes that cause a retry
175 """
176 self.http_obj = http_obj
177 self.max_tries = max_tries
178 self.retrying_statuses = retrying_statuses
179
180 def request(self, uri, method="GET", body=None, *args, **kwargs):
Sergey Berezin 2016/07/06 20:13:28 nit: use single quotes for strings if possible: 'G
tnn 2016/07/06 22:05:18 Done.
181 for i in range(1, self.max_tries + 1):
182 try:
183 response, content = self.http_obj.request(
184 uri, method, body, *args, **kwargs)
Sergey Berezin 2016/07/06 20:13:29 nit: indent 4 spaces relative to the prev. line.
tnn 2016/07/06 22:05:18 I swear it looked like 4 spaces in my vim :S It tu
185
186 if response.status in self.retrying_statuses:
187 logging.info("RetryableHttp retries (%d) on receiving status: %d",
Sergey Berezin 2016/07/06 20:13:28 nit (wording suggestion): logging.info( 'R
tnn 2016/07/06 22:05:17 Done.
188 i, response.status)
189 continue
190 except (ValueError, errors.Error,
191 socket.timeout, socket.error, socket.herror, socket.gaierror,
Sergey Berezin 2016/07/06 20:13:28 nit: we always indent arguments to align: your_
tnn 2016/07/06 22:05:18 Done.
192 httplib2.HttpLib2Error) as error:
193 if i == self.max_tries:
194 logging.warning("RetryableHttp fails on exception: %s", error)
Sergey Berezin 2016/07/06 20:13:29 nit: 'single quotes'
tnn 2016/07/06 22:05:18 Done.
195 raise
196 else:
197 logging.info("RetryableHttp retries (%d) on exception: %s", i, error)
Sergey Berezin 2016/07/06 20:13:28 nit: 'single quotes', and similar wording suggesti
tnn 2016/07/06 22:05:18 Done.
198 continue
199 break
200
201 return response, content
202
164 203
165 class InstrumentedHttp(httplib2.Http): 204 class InstrumentedHttp(httplib2.Http):
166 """A httplib2.Http object that reports ts_mon metrics about its requests.""" 205 """A httplib2.Http object that reports ts_mon metrics about its requests."""
167 206
168 def __init__(self, name, time_fn=time.time, timeout=DEFAULT_TIMEOUT, 207 def __init__(self, name, time_fn=time.time, timeout=DEFAULT_TIMEOUT,
169 **kwargs): 208 **kwargs):
170 """ 209 """
171 Args: 210 Args:
172 name: An identifier for the HTTP requests made by this object. 211 name: An identifier for the HTTP requests made by this object.
173 time_fn: Function returning the current time in seconds. Use for testing 212 time_fn: Function returning the current time in seconds. Use for testing
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after
257 self.requests_made.append(self.HttpCall(uri, method, body, headers)) 296 self.requests_made.append(self.HttpCall(uri, method, body, headers))
258 headers = None 297 headers = None
259 body = None 298 body = None
260 for candidate in self._uris: 299 for candidate in self._uris:
261 if candidate[0].match(uri): 300 if candidate[0].match(uri):
262 _, headers, body = candidate 301 _, headers, body = candidate
263 break 302 break
264 if not headers: 303 if not headers:
265 raise AssertionError("Unexpected request to %s" % uri) 304 raise AssertionError("Unexpected request to %s" % uri)
266 return httplib2.Response(headers), body 305 return httplib2.Response(headers), body
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698