1#!/usr/bin/env vpython3 2# Copyright 2022 The Chromium Authors 3# Use of this source code is governed by a BSD-style license that can be 4# found in the LICENSE file. 5 6import io 7import json 8import os 9import sys 10import unittest 11from unittest import mock 12 13import update_product_bundles 14 15sys.path.append(os.path.abspath(os.path.join(os.path.dirname(__file__), 16 'test'))) 17 18import common 19 20 21class TestUpdateProductBundles(unittest.TestCase): 22 def setUp(self): 23 ffx_mock = mock.Mock() 24 ffx_mock.returncode = 0 25 self._ffx_patcher = mock.patch('common.run_ffx_command', 26 return_value=ffx_mock) 27 self._ffx_mock = self._ffx_patcher.start() 28 self.addCleanup(self._ffx_mock.stop) 29 30 def testConvertToProductBundleDefaultsUnknownImage(self): 31 self.assertEqual( 32 update_product_bundles.convert_to_products(['unknown-image']), 33 ['unknown-image']) 34 35 def testConvertToProductBundleWarnsDeprecated(self): 36 with self.assertLogs(level='WARNING') as logs: 37 deprecated_images = [ 38 'qemu.arm64', 'qemu.x64', 'core.x64-dfv2-release', 39 'workstation_eng.chromebook-x64-release' 40 ] 41 self.assertEqual( 42 update_product_bundles.convert_to_products(deprecated_images), [ 43 'terminal.qemu-arm64', 'terminal.x64', 'core.x64-dfv2', 44 'workstation_eng.chromebook-x64' 45 ]) 46 for i, deprecated_image in enumerate(deprecated_images): 47 self.assertIn(f'Image name {deprecated_image} has been deprecated', 48 logs.output[i]) 49 50 51 @mock.patch('common.run_ffx_command') 52 def testRemoveRepositoriesRunsRemoveOnGivenRepos(self, ffx_mock): 53 update_product_bundles.remove_repositories(['foo', 'bar', 'fizz', 'buzz']) 54 55 ffx_mock.assert_has_calls([ 56 mock.call(cmd=('repository', 'remove', 'foo'), check=True), 57 mock.call(cmd=('repository', 'remove', 'bar'), check=True), 58 mock.call(cmd=('repository', 'remove', 'fizz'), check=True), 59 mock.call(cmd=('repository', 'remove', 'buzz'), check=True), 60 ]) 61 62 @mock.patch('os.path.exists') 63 @mock.patch('os.path.abspath') 64 def testGetRepositoriesPrunesReposThatDoNotExist(self, mock_abspath, 65 mock_exists): 66 with mock.patch('common.SDK_ROOT', 'some/path'): 67 self._ffx_mock.return_value.stdout = json.dumps([{ 68 "name": "terminal.x64", 69 "spec": { 70 "type": "pm", 71 "path": "some/path/that/exists" 72 } 73 }, { 74 "name": "workstation-eng.chromebook-x64", 75 "spec": { 76 "type": "pm", 77 "path": "some/path/that/does/not/exist" 78 } 79 }]) 80 mock_exists.side_effect = [True, False] 81 mock_abspath.side_effect = lambda x: x 82 83 self.assertEqual(update_product_bundles.get_repositories(), [{ 84 "name": "terminal.x64", 85 "spec": { 86 "type": "pm", 87 "path": "some/path/that/exists" 88 } 89 }]) 90 91 self._ffx_mock.assert_has_calls([ 92 mock.call(cmd=('--machine', 'json', 'repository', 'list'), 93 capture_output=True, 94 check=True), 95 mock.call(cmd=('repository', 'remove', 96 'workstation-eng.chromebook-x64'), 97 check=True) 98 ]) 99 100 @mock.patch('common.get_hash_from_sdk', return_value='abc') 101 # Disallow reading sdk_override. 102 @mock.patch('os.path.isfile', return_value=False) 103 def testLookupAndDownloadWithAuth(self, get_hash_mock, isfile_mock): 104 try: 105 common.get_host_os() 106 except: 107 # Ignore unsupported platforms. common.get_host_os used in 108 # update_product_bundles.main throws an unsupported exception. 109 return 110 auth_file = os.path.abspath( 111 os.path.join(os.path.dirname(__file__), 'get_auth_token.py')) 112 self._ffx_mock.return_value.stdout = 'http://download-url' 113 with mock.patch('sys.argv', 114 ['update_product_bundles.py', 'terminal.x64', '--auth']): 115 update_product_bundles.main() 116 self._ffx_mock.assert_has_calls([ 117 mock.call(cmd=[ 118 'product', 'lookup', 'terminal.x64', 'abc', '--base-url', 119 'gs://fuchsia/development/abc', '--auth', auth_file 120 ], 121 capture_output=True, 122 check=True), 123 mock.call(cmd=[ 124 'product', 'download', 'http://download-url', 125 os.path.join(common.IMAGES_ROOT, 'terminal', 'x64'), '--auth', 126 auth_file 127 ], 128 check=True) 129 ]) 130 131 132if __name__ == '__main__': 133 unittest.main() 134