1# Copyright 2014 Google Inc. All rights reserved. 2# 3# Licensed under the Apache License, Version 2.0 (the "License"); 4# you may not use this file except in compliance with the License. 5# You may obtain a copy of the License at 6# 7# http://www.apache.org/licenses/LICENSE-2.0 8# 9# Unless required by applicable law or agreed to in writing, software 10# distributed under the License is distributed on an "AS IS" BASIS, 11# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12# See the License for the specific language governing permissions and 13# limitations under the License. 14 15"""Copy of googleapiclient.http's mock functionality.""" 16 17import httplib2 18 19# TODO(craigcitro): Find a cleaner way to share this code with googleapiclient. 20 21 22class HttpMock(object): 23 """Mock of httplib2.Http""" 24 25 def __init__(self, headers=None): 26 """HttpMock constructor. 27 28 Args: 29 headers: dict, header to return with response 30 """ 31 if headers is None: 32 headers = {'status': '200'} 33 self.data = None 34 self.response_headers = headers 35 self.headers = None 36 self.uri = None 37 self.method = None 38 self.body = None 39 self.headers = None 40 41 def request(self, uri, 42 method='GET', 43 body=None, 44 headers=None, 45 redirections=1, 46 connection_type=None): 47 self.uri = uri 48 self.method = method 49 self.body = body 50 self.headers = headers 51 return httplib2.Response(self.response_headers), self.data 52 53 54class HttpMockSequence(object): 55 """Mock of httplib2.Http 56 57 Mocks a sequence of calls to request returning different responses for each 58 call. Create an instance initialized with the desired response headers 59 and content and then use as if an httplib2.Http instance:: 60 61 http = HttpMockSequence([ 62 ({'status': '401'}, b''), 63 ({'status': '200'}, b'{"access_token":"1/3w","expires_in":3600}'), 64 ({'status': '200'}, 'echo_request_headers'), 65 ]) 66 resp, content = http.request("http://examples.com") 67 68 There are special values you can pass in for content to trigger 69 behavours that are helpful in testing. 70 71 * 'echo_request_headers' means return the request headers in the response 72 body 73 * 'echo_request_body' means return the request body in the response body 74 """ 75 76 def __init__(self, iterable): 77 """HttpMockSequence constructor. 78 79 Args: 80 iterable: iterable, a sequence of pairs of (headers, body) 81 """ 82 self._iterable = iterable 83 self.follow_redirects = True 84 self.requests = [] 85 86 def request(self, uri, 87 method='GET', 88 body=None, 89 headers=None, 90 redirections=1, 91 connection_type=None): 92 resp, content = self._iterable.pop(0) 93 self.requests.append({'uri': uri, 'body': body, 'headers': headers}) 94 # Read any underlying stream before sending the request. 95 body_stream_content = (body.read() 96 if getattr(body, 'read', None) else None) 97 if content == 'echo_request_headers': 98 content = headers 99 elif content == 'echo_request_body': 100 content = (body 101 if body_stream_content is None else body_stream_content) 102 return httplib2.Response(resp), content 103 104 105class CacheMock(object): 106 107 def __init__(self): 108 self.cache = {} 109 110 def get(self, key, namespace=''): 111 # ignoring namespace for easier testing 112 return self.cache.get(key, None) 113