nebraska: Break properties into two objects
There are typically two types of properties that nebraska is setup. One
is defined when the nebraska starts and never
changes (NebraskaProperties) and one can be changed during the lifetime
of the nebraska or be configured by each request (through function API
call or url query strings). This CL breaks these two kinds into two
separate objects so we can flexibly add new properties to each one of
them without too much code change, etc.
BUG=chromium:999047
TEST=cros flash
TEST=nebraska_unittest.py, auto_update_unittest.py
Change-Id: I4e7872f5659385bf31cf2c25bf3917564249df0e
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/dev-util/+/1951506
Tested-by: Amin Hassani <ahassani@chromium.org>
Commit-Queue: Amin Hassani <ahassani@chromium.org>
Reviewed-by: Jae Hoon Kim <kimjae@chromium.org>
diff --git a/autoupdate.py b/autoupdate.py
index 5485fb2..8a4af28 100644
--- a/autoupdate.py
+++ b/autoupdate.py
@@ -343,7 +343,9 @@
if self.max_updates == 0:
_Log('Request received but max number of updates already served.')
nebraska_obj = nebraska.Nebraska()
- return nebraska_obj.GetResponseToRequest(request, no_update=True)
+ response_props = nebraska.ResponseProperties(no_update=True)
+ return nebraska_obj.GetResponseToRequest(request,
+ response_props=response_props)
_Log('Update Check Received.')
@@ -357,10 +359,14 @@
'nebraska to respond with no-update. The error was %s', e)
_Log('Responding to client to use url %s to get image', base_url)
- nebraska_obj = nebraska.Nebraska(update_payloads_address=base_url,
- update_metadata_dir=local_payload_dir)
- return nebraska_obj.GetResponseToRequest(
- request, critical_update=self.critical_update)
+ nebraska_props = nebraska.NebraskaProperties(
+ update_payloads_address=base_url,
+ update_metadata_dir=local_payload_dir)
+ response_props = nebraska.ResponseProperties(
+ critical_update=self.critical_update)
+ nebraska_obj = nebraska.Nebraska(nebraska_props=nebraska_props)
+ return nebraska_obj.GetResponseToRequest(request,
+ response_props=response_props)
def HandleHostInfoPing(self, ip):
"""Returns host info dictionary for the given IP in JSON format."""
diff --git a/autoupdate_unittest.py b/autoupdate_unittest.py
index 93e8b06..648ef7c 100755
--- a/autoupdate_unittest.py
+++ b/autoupdate_unittest.py
@@ -39,6 +39,7 @@
self.port = 8080
self.test_board = 'test-board'
self.build_root = tempfile.mkdtemp('autoupdate_build_root')
+ self.tempdir = tempfile.mkdtemp('tempdir')
self.latest_dir = '12345_af_12-a1'
self.latest_verision = '12345_af_12'
self.static_image_dir = tempfile.mkdtemp('autoupdate_static_dir')
@@ -59,6 +60,7 @@
def tearDown(self):
shutil.rmtree(self.build_root)
+ shutil.rmtree(self.tempdir)
shutil.rmtree(self.static_image_dir)
def _DummyAutoupdateConstructor(self, **kwargs):
@@ -92,6 +94,22 @@
self.assertEqual(
json.loads(au_mock.HandleHostInfoPing(test_ip)), self.test_dict)
+ @mock.patch.object(autoupdate.Autoupdate, 'GetPathToPayload')
+ def testHandleUpdatePing(self, path_to_payload_mock):
+ """Tests HandleUpdatePing"""
+ au_mock = self._DummyAutoupdateConstructor()
+ path_to_payload_mock.return_value = self.tempdir
+ request = """<?xml version="1.0" encoding="UTF-8"?>
+<request protocol="3.0">
+ <os version="Indy" platform="Chrome OS" sp="10323.52.0_x86_64"></os>
+ <app appid="platform" version="1.0.0" delta_okay="true"
+ track="stable-channel" board="eve">
+ <ping active="1" a="1" r="1"></ping>
+ <updatecheck targetversionprefix=""></updatecheck>
+ </app>
+</request>"""
+
+ self.assertIn('error-unknownApplication', au_mock.HandleUpdatePing(request))
if __name__ == '__main__':
unittest.main()
diff --git a/nebraska/nebraska.py b/nebraska/nebraska.py
index f45e1ae..f1e5e27 100755
--- a/nebraska/nebraska.py
+++ b/nebraska/nebraska.py
@@ -327,15 +327,17 @@
format based on the format of an XML response template.
"""
- def __init__(self, request, properties):
+ def __init__(self, request, nebraska_props, response_props):
"""Initialize a reponse from a list of matching apps.
Args:
request: Request instance describing client requests.
- properties: An instance of NebraskaProperties.
+ nebraska_props: An instance of NebraskaProperties.
+ response_props: An instance of ResponseProperties.
"""
self._request = request
- self._properties = properties
+ self._nebraska_props = nebraska_props
+ self._response_props = response_props
curr = datetime.datetime.now()
# Jan 1 2007 is the start of Omaha v3 epoch:
@@ -366,7 +368,8 @@
for app_request in self._request.app_requests:
response_xml.append(
- self.AppResponse(app_request, self._properties).Compile())
+ self.AppResponse(app_request, self._nebraska_props,
+ self._response_props).Compile())
except Exception as err:
logging.error(traceback.format_exc())
@@ -383,12 +386,13 @@
responses to pings and events as appropriate.
"""
- def __init__(self, app_request, properties):
+ def __init__(self, app_request, nebraska_props, response_props):
"""Initialize an AppResponse.
Args:
app_request: AppRequest representing a client request.
- properties: An instance of NebraskaProperties.
+ nebraska_props: An instance of NebraskaProperties.
+ response_props: An instance of ResponseProperties.
"""
self._app_request = app_request
self._app_data = None
@@ -396,25 +400,26 @@
self._payloads_address = None
# Although, for installs the update_engine probably should not care about
# critical updates and should install even if OOBE has not been passed.
- self._critical_update = properties.critical_update
+ self._critical_update = response_props.critical_update
# If no update was requested, don't process anything anymore.
- if properties.no_update:
+ if response_props.no_update:
return
if self._app_request.request_type == Request.RequestType.INSTALL:
- self._app_data = properties.install_app_index.Find(self._app_request)
+ self._app_data = nebraska_props.install_app_index.Find(
+ self._app_request)
self._err_not_found = self._app_data is None
- self._payloads_address = properties.install_payloads_address
+ self._payloads_address = nebraska_props.install_payloads_address
elif self._app_request.request_type == Request.RequestType.UPDATE:
- self._app_data = properties.update_app_index.Find(self._app_request)
- self._payloads_address = properties.update_payloads_address
+ self._app_data = nebraska_props.update_app_index.Find(self._app_request)
+ self._payloads_address = nebraska_props.update_payloads_address
# This differentiates between apps that are not in the index and apps
# that are available, but do not have an update available. Omaha treats
# the former as an error, whereas the latter case should result in a
# response containing a "noupdate" tag.
self._err_not_found = (self._app_data is None and
- not properties.update_app_index.Contains(
+ not nebraska_props.update_app_index.Contains(
self._app_request))
if self._app_data:
@@ -508,7 +513,9 @@
self._directory = directory
self._index = []
- def Scan(self):
+ self._Scan()
+
+ def _Scan(self):
"""Scans the directory and loads all available properties files."""
if self._directory is None:
return
@@ -659,34 +666,9 @@
class NebraskaProperties(object):
- """An instance of this class contains some Nebraska properties."""
+ """An instance of this class contains Nebraska properties.
- def __init__(self, update_payloads_address, install_payloads_address,
- update_app_index, install_app_index):
- """Initializes the NebraskaProperties instance.
-
- Args:
- update_payloads_address: Address serving update payloads.
- install_payloads_address: Address serving install payloads.
- update_app_index: Index of update payloads.
- install_app_index: Index of install payloads.
- """
- self.update_payloads_address = update_payloads_address
- self.install_payloads_address = install_payloads_address
- self.update_app_index = update_app_index
- self.install_app_index = install_app_index
- self.critical_update = False
- self.no_update = False
-
-
-class Nebraska(object):
- """An instance of this class allows responding to incoming Omaha requests.
-
- This class has the responsibility to manufacture Omaha responses based on
- the input update requests. This should be the main point of use of the
- Nebraska. If any changes to the behavior of Nebraska is intended, like
- creating critical update responses, or messing up with firmware and kernel
- versions, new flags should be added here to add that feature.
+ These properties are valid and unchanged during the lifetime of the nebraska.
"""
def __init__(self,
@@ -694,7 +676,7 @@
install_payloads_address=None,
update_metadata_dir=None,
install_metadata_dir=None):
- """Initializes the Nebraska instance.
+ """Initializes the NebraskaProperties instance.
Args:
update_payloads_address: Address of the update payload server.
@@ -706,37 +688,67 @@
# Attach '/' at the end of the addresses if they don't have any. The update
# engine just concatenates the base address with the payload file name and
# if there is no '/' the path will be invalid.
- upa = os.path.join(update_payloads_address or '', '')
- ipa = (os.path.join(install_payloads_address, '')
- if install_payloads_address is not None else upa)
- uai = AppIndex(update_metadata_dir)
- iai = AppIndex(install_metadata_dir)
- uai.Scan()
- iai.Scan()
+ self.update_payloads_address = os.path.join(update_payloads_address or '',
+ '')
+ self.install_payloads_address = (
+ os.path.join(install_payloads_address or '', '') or
+ self.update_payloads_address)
+ self.update_app_index = AppIndex(update_metadata_dir)
+ self.install_app_index = AppIndex(install_metadata_dir)
- self._properties = NebraskaProperties(upa, ipa, uai, iai)
+class ResponseProperties(object):
+ """An instance of this class contains properties applied for each response.
+
+ These properties might change during the lifetime of the nebraska.
+ """
+ def __init__(self, critical_update=False, no_update=False):
+ """Initliazes the response properties.
+
+ Args:
+ critical_update: If true, the response will include 'deadline=now' which
+ indicates the update is critical.
+ no_update: If true, it will return a noupdate response regardless.
+ """
+ self.critical_update = critical_update
+ self.no_update = no_update
+
+
+class Nebraska(object):
+ """An instance of this class allows responding to incoming Omaha requests.
+
+ This class has the responsibility to manufacture Omaha responses based on
+ the input update requests. This should be the main point of use of the
+ Nebraska. If any changes to the behavior of Nebraska is intended, like
+ creating critical update responses, or messing up with firmware and kernel
+ versions, new flags should be added here to add that feature.
+ """
+ def __init__(self, nebraska_props=None, response_props=None):
+ """Initializes the Nebraska instance.
+
+ Args:
+ nebraska_props: An instance of NebraskaProperties.
+ response_props: An instance of ResponseProperties.
+ """
+ self._nebraska_props = nebraska_props or NebraskaProperties()
+ self._response_props = response_props or ResponseProperties()
self._request_log = []
- def GetResponseToRequest(self, request, critical_update=False,
- no_update=False):
+ def GetResponseToRequest(self, request, response_props=None):
"""Returns the response corresponding to a request.
Args:
request: The Request object representation of the incoming request.
- critical_update: If true, the response will include 'deadline=now' which
- indicates the update is critical.
- no_update: If true, it will return a noupdate response regardless.
+ response_props: An instance of ResponseProperties. If passed, it will
+ override the internal Nebraska version (default).
Returns:
The string representation of the created response.
"""
self._request_log.append(request.GetDict())
- properties = copy.copy(self._properties)
- properties.critical_update = critical_update
- properties.no_update = no_update
- response = Response(request, properties).GetXMLString()
+ response = Response(request, self._nebraska_props,
+ response_props or self._nebraska_props).GetXMLString()
# Make the XML response look pretty.
response_str = minidom.parseString(response).toprettyxml(indent=' ',
encoding='UTF-8')
@@ -836,11 +848,13 @@
if parsed_path == 'update':
critical_update = parsed_query.get('critical_update', []) == ['True']
no_update = parsed_query.get('no_update', []) == ['True']
+ response_props = ResponseProperties(critical_update=critical_update,
+ no_update=no_update)
try:
request_obj = Request(request)
response = self.server.owner.nebraska.GetResponseToRequest(
- request_obj, critical_update=critical_update, no_update=no_update)
+ request_obj, response_props)
self._SendResponse('application/xml', response)
except Exception as err:
logging.error('Failed to handle request (%s)', str(err))
@@ -985,11 +999,12 @@
logging.info('Starting nebraska ...')
- nebraska = Nebraska(
+ nebraska_props = NebraskaProperties(
update_payloads_address=opts.update_payloads_address,
install_payloads_address=opts.install_payloads_address,
update_metadata_dir=opts.update_metadata,
install_metadata_dir=opts.install_metadata)
+ nebraska = Nebraska(nebraska_props)
nebraska_server = NebraskaServer(nebraska, runtime_root=opts.runtime_root,
port=opts.port)
diff --git a/nebraska/nebraska_unittest.py b/nebraska/nebraska_unittest.py
index 42a65ab..c32799c 100755
--- a/nebraska/nebraska_unittest.py
+++ b/nebraska/nebraska_unittest.py
@@ -28,8 +28,8 @@
_INSTALL_DIR = 'test_install_dir'
_UPDATE_DIR = 'test_update_dir'
_PAYLOAD_ADDRESS = '111.222.212:2357'
-_UPDATE_PAYLOADS_ADDRESS = 'www.google.com/update'
-_INSTALL_PAYLOADS_ADDRESS = 'www.google.com/install'
+_UPDATE_PAYLOADS_ADDRESS = 'www.google.com/update/'
+_INSTALL_PAYLOADS_ADDRESS = 'www.google.com/install/'
# pylint: disable=protected-access
@@ -104,8 +104,10 @@
self.send_error = mock.MagicMock()
self.rfile = mock.MagicMock()
self.server = mock.MagicMock()
- self.server.owner = nebraska.NebraskaServer(nebraska.Nebraska(
- _PAYLOAD_ADDRESS, _PAYLOAD_ADDRESS))
+ nebraska_props = nebraska.NebraskaProperties(
+ update_payloads_address=_PAYLOAD_ADDRESS)
+ nebraska_obj = nebraska.Nebraska(nebraska_props=nebraska_props)
+ self.server.owner = nebraska.NebraskaServer(nebraska_obj)
class NebraskaTest(unittest.TestCase):
@@ -116,16 +118,21 @@
update_addr = 'foo/update/'
install_addr = 'foo/install/'
# pylint: disable=protected-access
- n = nebraska.Nebraska(update_addr, install_addr)
- self.assertEqual(n._properties.install_payloads_address, install_addr)
- self.assertEqual(n._properties.update_payloads_address, update_addr)
+ nebraska_props = nebraska.NebraskaProperties(
+ update_payloads_address=update_addr,
+ install_payloads_address=install_addr)
+ n = nebraska.Nebraska(nebraska_props=nebraska_props)
+ self.assertEqual(n._nebraska_props.install_payloads_address, install_addr)
+ self.assertEqual(n._nebraska_props.update_payloads_address, update_addr)
- n = nebraska.Nebraska(update_addr)
- self.assertEqual(n._properties.install_payloads_address, update_addr)
+ nebraska_props = nebraska.NebraskaProperties(
+ update_payloads_address=update_addr)
+ n = nebraska.Nebraska(nebraska_props=nebraska_props)
+ self.assertEqual(n._nebraska_props.install_payloads_address, update_addr)
n = nebraska.Nebraska()
- self.assertEqual(n._properties.update_payloads_address, '')
- self.assertEqual(n._properties.install_payloads_address, '')
+ self.assertEqual(n._nebraska_props.update_payloads_address, '')
+ self.assertEqual(n._nebraska_props.install_payloads_address, '')
class NebraskaHandlerTest(unittest.TestCase):
@@ -143,88 +150,82 @@
self.assertEqual(nebraska_handler._ParseURL('http://goo.gle/'), ('', {}))
- def testDoPostSuccess(self):
+ @mock.patch.object(nebraska.Nebraska, 'GetResponseToRequest',
+ return_value='foobar')
+ @mock.patch.object(nebraska, 'Request')
+ def testDoPostSuccess(self, _, response_mock):
"""Tests do_POST success."""
nebraska_handler = MockNebraskaHandler()
nebraska_handler.path = 'http://test.com/update'
- test_response = 'foobar'
- with mock.patch.object(nebraska.Nebraska,
- 'GetResponseToRequest') as response_mock:
- with mock.patch.object(nebraska, 'Request'):
- response_mock.return_value = test_response
- nebraska_handler.do_POST()
+ nebraska_handler.do_POST()
- response_mock.assert_called_once_with(mock.ANY, critical_update=False,
- no_update=False)
- nebraska_handler._SendResponse.assert_called_once_with(
- 'application/xml', test_response)
+ response_mock.assert_called_once()
+ nebraska_handler._SendResponse.assert_called_once_with(
+ 'application/xml', response_mock.return_value)
- def testDoPostSuccessWithCriticalUpdate(self):
+ @mock.patch.object(nebraska.Nebraska, 'GetResponseToRequest')
+ @mock.patch.object(nebraska, 'Request')
+ def testDoPostSuccessWithCriticalUpdate(self, _, response_mock):
"""Tests do_POST success with critical_update query string in URL."""
nebraska_handler = MockNebraskaHandler()
nebraska_handler.path = 'http://test.com/update/?critical_update=True'
- with mock.patch.object(nebraska.Nebraska,
- 'GetResponseToRequest') as response_mock:
- with mock.patch.object(nebraska, 'Request'):
- nebraska_handler.do_POST()
+ nebraska_handler.do_POST()
- response_mock.assert_called_once_with(mock.ANY, critical_update=True,
- no_update=False)
+ response_mock.assert_called_once()
+ self.assertTrue(
+ response_mock.call_args_list[0].response_props.critical_update)
- def testDoPostSuccessWithNoUpdate(self):
+ @mock.patch.object(nebraska.Nebraska, 'GetResponseToRequest')
+ @mock.patch.object(nebraska, 'Request')
+ def testDoPostSuccessWithNoUpdate(self, _, response_mock):
"""Tests do_POST success with no_update query string in URL."""
nebraska_handler = MockNebraskaHandler()
nebraska_handler.path = 'http://test.com/update/?no_update=True'
- with mock.patch.object(nebraska.Nebraska,
- 'GetResponseToRequest') as response_mock:
- with mock.patch.object(nebraska, 'Request'):
- nebraska_handler.do_POST()
+ nebraska_handler.do_POST()
- response_mock.assert_called_once_with(mock.ANY, critical_update=False,
- no_update=True)
+ response_mock.assert_called_once()
+ self.assertTrue(response_mock.call_args_list[0].response_props.no_update)
def testDoPostInvalidPath(self):
"""Test do_POST invalid path."""
nebraska_handler = MockNebraskaHandler()
nebraska_handler.path = 'http://test.com/invalid-path'
-
nebraska_handler.do_POST()
nebraska_handler.send_error.assert_called_once_with(
http_client.BAD_REQUEST,
'The requested path "invalid-path" was not found!')
- def testDoPostInvalidRequest(self):
+ @mock.patch.object(nebraska, 'traceback')
+ @mock.patch.object(nebraska.Request, 'ParseRequest',
+ side_effect=nebraska.InvalidRequestError)
+ def testDoPostInvalidRequest(self, _, traceback_mock):
"""Test do_POST invalid request."""
nebraska_handler = MockNebraskaHandler()
nebraska_handler.path = 'http://test.com/update'
+ nebraska_handler.do_POST()
- with mock.patch.object(nebraska, 'traceback') as traceback_mock:
- with mock.patch.object(nebraska.Request, 'ParseRequest') as parse_mock:
- parse_mock.side_effect = nebraska.InvalidRequestError
- nebraska_handler.do_POST()
+ self.assertEqual(traceback_mock.format_exc.call_count, 2)
+ nebraska_handler.send_error.assert_called_once_with(
+ http_client.INTERNAL_SERVER_ERROR, traceback_mock.format_exc())
- self.assertEqual(traceback_mock.format_exc.call_count, 2)
- nebraska_handler.send_error.assert_called_once_with(
- http_client.INTERNAL_SERVER_ERROR, traceback_mock.format_exc())
-
- def testDoPostInvalidResponse(self):
+ @mock.patch.object(nebraska, 'traceback')
+ @mock.patch.object(nebraska, 'Response')
+ def testDoPostInvalidResponse(self, response_mock, traceback_mock):
"""Tests do_POST invalid response handling."""
nebraska_handler = MockNebraskaHandler()
nebraska_handler.path = 'http://test.com/update'
- with mock.patch.object(nebraska, 'traceback') as traceback_mock:
- with mock.patch.object(nebraska, 'Response') as response_mock:
- response_instance = response_mock.return_value
- response_instance.GetXMLString.side_effect = Exception
- nebraska_handler.do_POST()
+ response_instance = response_mock.return_value
+ response_instance.GetXMLString.side_effect = Exception
+ nebraska_handler.do_POST()
- self.assertEqual(traceback_mock.format_exc.call_count, 2)
- nebraska_handler.send_error.assert_called_once_with(
- http_client.INTERNAL_SERVER_ERROR, traceback_mock.format_exc())
+ self.assertEqual(traceback_mock.format_exc.call_count, 2)
+ nebraska_handler.send_error.assert_called_once_with(
+ http_client.INTERNAL_SERVER_ERROR, traceback_mock.format_exc())
def testDoGetSuccess(self):
"""Tests do_GET success."""
@@ -249,7 +250,8 @@
def testStart(self):
"""Tests Start."""
- nebraska_instance = nebraska.Nebraska(_PAYLOAD_ADDRESS, _PAYLOAD_ADDRESS)
+ nebraska_props = nebraska.NebraskaProperties(_PAYLOAD_ADDRESS)
+ nebraska_instance = nebraska.Nebraska(nebraska_props=nebraska_props)
server = nebraska.NebraskaServer(nebraska_instance, port=_NEBRASKA_PORT)
with mock.patch.object(nebraska.BaseHTTPServer,
@@ -267,7 +269,8 @@
def testStop(self):
"""Tests Stop."""
- nebraska_instance = nebraska.Nebraska(_PAYLOAD_ADDRESS, _PAYLOAD_ADDRESS)
+ nebraska_props = nebraska.NebraskaProperties(_PAYLOAD_ADDRESS)
+ nebraska_instance = nebraska.Nebraska(nebraska_props=nebraska_props)
server = nebraska.NebraskaServer(nebraska_instance, port=_NEBRASKA_PORT)
# pylint: disable=protected-access
@@ -282,7 +285,8 @@
"""Tests PID and port files are correctly written."""
temp_dir = tempfile.mkdtemp()
runtime_root = os.path.join(temp_dir, 'runtime_root')
- nebraska_instance = nebraska.Nebraska(_PAYLOAD_ADDRESS, _PAYLOAD_ADDRESS)
+ nebraska_props = nebraska.NebraskaProperties(_PAYLOAD_ADDRESS)
+ nebraska_instance = nebraska.Nebraska(nebraska_props=nebraska_props)
server = nebraska.NebraskaServer(nebraska_instance, port=_NEBRASKA_PORT,
runtime_root=runtime_root)
@@ -417,7 +421,6 @@
with mock.patch.object(builtins, 'open') as open_mock:
listdir_mock.return_value = []
app_index = nebraska.AppIndex(_INSTALL_DIR)
- app_index.Scan()
self.assertFalse(app_index._index)
listdir_mock.assert_called_once_with(_INSTALL_DIR)
open_mock.assert_not_called()
@@ -428,7 +431,6 @@
with mock.patch.object(builtins, 'open') as open_mock:
listdir_mock.return_value = ['foo.bin', 'bar.bin', 'json']
app_index = nebraska.AppIndex(_INSTALL_DIR)
- app_index.Scan()
self.assertFalse(app_index._index)
listdir_mock.assert_called_once_with(_INSTALL_DIR)
open_mock.assert_not_called()
@@ -459,7 +461,6 @@
# Make sure the Scan() scans all the files and at least correct App IDs
# are generated.
app_index = nebraska.AppIndex(_INSTALL_DIR)
- app_index.Scan()
listdir_mock.assert_called_once_with(_INSTALL_DIR)
self.assertEqual(
[x.appid for x in app_index._index],
@@ -490,8 +491,7 @@
# Make sure we raise error when loading files raises one.
with self.assertRaises(IOError):
- app_index = nebraska.AppIndex(_INSTALL_DIR)
- app_index.Scan()
+ nebraska.AppIndex(_INSTALL_DIR)
def testScanInvalidApp(self):
"""Tests Scan on JSON files lacking required keys."""
@@ -518,8 +518,7 @@
# Make sure we raise error when properties files are invalid.
with self.assertRaises(KeyError):
- app_index = nebraska.AppIndex(_INSTALL_DIR)
- app_index.Scan()
+ nebraska.AppIndex(_INSTALL_DIR)
def testContains(self):
"""Tests Constains() correctly finds matching AppData."""
@@ -536,7 +535,6 @@
]
app_index = nebraska.AppIndex(_UPDATE_DIR)
- app_index.Scan()
no_match_request = GenerateAppRequest(appid='random')
self.assertFalse(app_index.Contains(no_match_request))
@@ -566,7 +564,6 @@
]
app_index = nebraska.AppIndex(_UPDATE_DIR)
- app_index.Scan()
request = GenerateAppRequest(appid='random')
# It will match against the AppData with an empty appid.
@@ -877,17 +874,15 @@
def testGetXMLStringSuccess(self):
"""Tests GetXMLString success."""
- properties = nebraska.NebraskaProperties(
- _UPDATE_PAYLOADS_ADDRESS,
- _INSTALL_PAYLOADS_ADDRESS,
- nebraska.AppIndex(mock.MagicMock()),
- nebraska.AppIndex(mock.MagicMock()))
+ nebraska_props = nebraska.NebraskaProperties(
+ update_payloads_address=_UPDATE_PAYLOADS_ADDRESS,
+ install_payloads_address=_INSTALL_PAYLOADS_ADDRESS)
app_list = (
GenerateAppData(is_delta=True, source_version='0.9.0'),
GenerateAppData(appid='bar', is_delta=True, source_version='1.9.0'),
GenerateAppData(appid='foobar'))
- properties.update_app_index._index = app_list
+ nebraska_props.update_app_index._index = app_list
request = mock.MagicMock()
request.app_requests = [
@@ -907,7 +902,8 @@
ping=True,
delta_okay=False)]
- response = nebraska.Response(request, properties).GetXMLString()
+ response = nebraska.Response(request, nebraska_props,
+ nebraska.ResponseProperties()).GetXMLString()
response_root = ElementTree.fromstring(response)
app_responses = response_root.findall('app')
@@ -922,132 +918,142 @@
def setUp(self):
"""Setting up common parameters."""
- self._properties = nebraska.NebraskaProperties(
- _UPDATE_PAYLOADS_ADDRESS,
- _INSTALL_PAYLOADS_ADDRESS,
- mock.MagicMock(),
- mock.MagicMock())
+ self._nebraska_props = nebraska.NebraskaProperties(
+ update_payloads_address=_UPDATE_PAYLOADS_ADDRESS,
+ install_payloads_address=_INSTALL_PAYLOADS_ADDRESS)
+ self._response_props = nebraska.ResponseProperties()
- def testAppResponseUpdate(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find', return_value=GenerateAppData())
+ def testAppResponseUpdate(self, find_mock):
"""Tests AppResponse for an update request with matching payload."""
app_request = GenerateAppRequest()
- match = GenerateAppData()
- self._properties.update_app_index.Find.return_value = match
+ match = find_mock.return_value
+ # Setting the install app index object to None to make sure it is not being
+ # called.
+ self._nebraska_props.install_app_index.Find = None
- response = nebraska.Response.AppResponse(app_request, self._properties)
+ response = nebraska.Response.AppResponse(app_request,
+ self._nebraska_props,
+ self._response_props)
self.assertIn(_UPDATE_PAYLOADS_ADDRESS.encode('utf-8'),
ElementTree.tostring(response.Compile()))
self.assertEqual(response._app_request, app_request)
self.assertFalse(response._err_not_found)
self.assertIs(response._app_data, match)
+ find_mock.assert_called_once_with(app_request)
- self._properties.update_app_index.Find.assert_called_once_with(app_request)
- self._properties.install_app_index.Find.assert_not_called()
-
- def testAppResponseInstall(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find', return_value=GenerateAppData())
+ def testAppResponseInstall(self, find_mock):
"""Tests AppResponse generation for install request with match."""
app_request = GenerateAppRequest(
request_type=nebraska.Request.RequestType.INSTALL)
- match = GenerateAppData()
- self._properties.install_app_index.Find.return_value = match
+ match = find_mock.return_value
+ # Setting the update app index object to None to make sure it is not being
+ # called.
+ self._nebraska_props.update_app_index.Find = None
- response = nebraska.Response.AppResponse(app_request, self._properties)
+ response = nebraska.Response.AppResponse(app_request,
+ self._nebraska_props,
+ self._response_props)
self.assertIn(_INSTALL_PAYLOADS_ADDRESS.encode('utf-8'),
ElementTree.tostring(response.Compile()))
self.assertEqual(response._app_request, app_request)
self.assertFalse(response._err_not_found)
self.assertIs(response._app_data, match)
+ find_mock.assert_called_once_with(app_request)
- self._properties.install_app_index.Find.assert_called_once_with(app_request)
- self._properties.update_app_index.Find.assert_not_called()
-
- def testAppResponseNoMatch(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find', return_value=None)
+ @mock.patch.object(nebraska.AppIndex, 'Contains', return_value=False)
+ def testAppResponseNoMatch(self, contains_mock, find_mock):
"""Tests AppResponse generation for update request with an unknown appid."""
app_request = GenerateAppRequest()
- self._properties.update_app_index.Find.return_value = None
- self._properties.update_app_index.Contains.return_value = False
-
- response = nebraska.Response.AppResponse(app_request, self._properties)
+ response = nebraska.Response.AppResponse(app_request,
+ self._nebraska_props,
+ self._response_props)
self.assertEqual(response._app_request, app_request)
self.assertTrue(response._err_not_found)
self.assertIsNone(response._app_data)
+ find_mock.assert_called_once_with(app_request)
+ contains_mock.assert_called_once_with(app_request)
- self._properties.update_app_index.Find.assert_called_once_with(app_request)
- self._properties.install_app_index.Find.assert_not_called()
-
- def testAppResponseNoUpdate(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find', return_value=None)
+ @mock.patch.object(nebraska.AppIndex, 'Contains', return_value=True)
+ # pylint: disable=unused-argument
+ def testAppResponseNoUpdate(self, contains_mock, find_mock):
"""Tests AppResponse generation for update request with no new versions."""
# GIVEN an update request.
app_request = GenerateAppRequest(
request_type=nebraska.Request.RequestType.UPDATE)
- # GIVEN Nebraska does not find an update.
- self._properties.update_app_index.Find.return_value = None
- # GIVEN it is a valid app.
- self._properties.update_app_index.Contains.return_value = True
# WHEN Nebraska sends a response.
- response = nebraska.Response.AppResponse(app_request, self._properties)
+ response = nebraska.Response.AppResponse(app_request,
+ self._nebraska_props,
+ self._response_props)
# THEN the response contains <updatecheck status="noupdate"/>.
update_check_tag = response.Compile().findall('updatecheck')[0]
self.assertEqual(update_check_tag.attrib['status'], 'noupdate')
- def testAppResponseNoUpdateFlag(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find', return_value=GenerateAppData())
+ @mock.patch.object(nebraska.AppIndex, 'Contains', return_value=True)
+ # pylint: disable=unused-argument
+ def testAppResponseNoUpdateFlag(self, contains_mock, find_mock):
"""Tests status="noupdate" is included in the response."""
app_request = GenerateAppRequest()
- match = GenerateAppData()
- self._properties.update_app_index.Find.return_value = match
- self._properties.update_app_index.Contains.return_value = True
- self._properties.no_update = True
+ self._response_props.no_update = True
response = nebraska.Response.AppResponse(
- app_request, self._properties).Compile()
+ app_request, self._nebraska_props, self._response_props).Compile()
+
update_check_tag = response.findall('updatecheck')[0]
self.assertEqual(update_check_tag.attrib['status'], 'noupdate')
- def testAppResponsePing(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find')
+ @mock.patch.object(nebraska.AppIndex, 'Contains', return_value=True)
+ def testAppResponsePing(self, contains_mock, find_mock):
"""Tests AppResponse generation for no-op with a ping request."""
app_request = GenerateAppRequest(
request_type=nebraska.Request.RequestType.EVENT, ping=True)
- self._properties.update_app_index.Find.return_value = None
- self._properties.update_app_index.Contains.return_value = True
-
- response = nebraska.Response.AppResponse(app_request, self._properties)
+ response = nebraska.Response.AppResponse(app_request,
+ self._nebraska_props,
+ self._response_props)
self.assertEqual(response._app_request, app_request)
self.assertFalse(response._err_not_found)
self.assertIsNone(response._app_data)
+ find_mock.assert_not_called()
+ contains_mock.assert_not_called()
- self._properties.update_app_index.Find.assert_not_called()
- self._properties.install_app_index.Find.assert_not_called()
-
- def testAppResponseEvent(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find')
+ @mock.patch.object(nebraska.AppIndex, 'Contains')
+ def testAppResponseEvent(self, contains_mock, find_mock):
"""Tests AppResponse generation for requests with events."""
app_request = GenerateAppRequest(
request_type=nebraska.Request.RequestType.EVENT)
- self._properties.update_app_index.Find.return_value = None
- self._properties.update_app_index.Contains.return_value = True
- response = nebraska.Response.AppResponse(app_request, self._properties)
+ response = nebraska.Response.AppResponse(app_request,
+ self._nebraska_props,
+ self._response_props)
self.assertEqual(response._app_request, app_request)
self.assertFalse(response._err_not_found)
self.assertIsNone(response._app_data)
+ find_mock.assert_not_called()
+ contains_mock.assert_not_called()
- self._properties.update_app_index.Find.assert_not_called()
- self._properties.install_app_index.Find.assert_not_called()
-
- def testCompileSuccess(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find', return_value=GenerateAppData())
+ def testCompileSuccess(self, find_mock):
"""Tests successful compilation of an AppData instance."""
app_request = GenerateAppRequest(
request_type=nebraska.Request.RequestType.INSTALL)
- match = GenerateAppData()
- self._properties.install_app_index.Find.return_value = match
+ match = find_mock.return_value
- response = nebraska.Response.AppResponse(app_request, self._properties)
+ response = nebraska.Response.AppResponse(app_request,
+ self._nebraska_props,
+ self._response_props)
compiled_response = response.Compile()
update_check_tag = compiled_response.find('updatecheck')
@@ -1063,11 +1069,9 @@
self.assertIsNotNone(package_tag)
self.assertIsNotNone(action_tag)
self.assertEqual(action_tag.attrib['sha256'], match.sha256)
-
self.assertEqual(compiled_response.attrib['status'], 'ok')
- self.assertEqual(update_check_tag.attrib['status'], 'ok')
-
self.assertEqual(compiled_response.attrib['appid'], match.appid)
+ self.assertEqual(update_check_tag.attrib['status'], 'ok')
self.assertEqual(url_tag.attrib['codebase'], _INSTALL_PAYLOADS_ADDRESS)
self.assertEqual(manifest_tag.attrib['version'], match.target_version)
self.assertEqual(package_tag.attrib['hash_sha256'].encode('utf-8'),
@@ -1082,41 +1086,48 @@
self.assertNotIn('deadline', action_tag.attrib)
self.assertNotIn('PublicKeyRsa', action_tag.attrib)
- def testCriticalUpdate(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find', return_value=GenerateAppData())
+ # pylint: disable=unused-argument
+ def testCriticalUpdate(self, find_mock):
"""Tests correct response for critical updates."""
app_request = GenerateAppRequest()
- match = GenerateAppData()
- self._properties.update_app_index.Find.return_value = match
- self._properties.critical_update = True
+ self._response_props.critical_update = True
+
response = nebraska.Response.AppResponse(
- app_request, self._properties).Compile()
+ app_request, self._nebraska_props, self._response_props).Compile()
+
action_tag = response.findall(
'updatecheck/manifest/actions/action')[1]
self.assertEqual(action_tag.attrib['deadline'], 'now')
- def testCriticalInstall(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find', return_value=GenerateAppData())
+ # pylint: disable=unused-argument
+ def testCriticalInstall(self, find_mock):
"""Tests correct response for critical installs."""
app_request = GenerateAppRequest(
request_type=nebraska.Request.RequestType.INSTALL)
- match = GenerateAppData()
- self._properties.update_app_index.Find.return_value = match
- self._properties.critical_update = True
+ self._response_props.critical_update = True
+
response = nebraska.Response.AppResponse(
- app_request, self._properties).Compile()
+ app_request, self._nebraska_props, self._response_props).Compile()
+
action_tag = response.findall(
'updatecheck/manifest/actions/action')[1]
self.assertEqual(action_tag.attrib['deadline'], 'now')
- def testPublicKey(self):
+ @mock.patch.object(nebraska.AppIndex, 'Find',
+ return_value=GenerateAppData(include_public_key=True))
+ def testPublicKey(self, find_mock):
"""Tests public key is included in the response."""
app_request = GenerateAppRequest()
- match = GenerateAppData(include_public_key=True)
- self._properties.update_app_index.Find.return_value = match
+
response = nebraska.Response.AppResponse(
- app_request, self._properties).Compile()
+ app_request, self._nebraska_props, self._response_props).Compile()
+
action_tag = response.findall(
'updatecheck/manifest/actions/action')[1]
- self.assertEqual(action_tag.attrib['PublicKeyRsa'], match.public_key)
+ self.assertEqual(action_tag.attrib['PublicKeyRsa'],
+ find_mock.return_value.public_key)
if __name__ == '__main__':