blob: b0c90084f81c66df2c624ca49c2a1abf7987f291 [file] [log] [blame]
Greg Edelston9cd16f52020-11-12 10:50:28 -07001#!/usr/bin/env python3
2# Copyright 2020 The Chromium OS Authors. All rights reserved.
3# Use of this source code is governed by a BSD-style license that can be
4# found in the LICENSE file.
5
6"""
7Unit tests for platform_json.py
8
9"""
10
Greg Edelstonf70963a2020-11-17 14:36:06 -070011import collections
12import io
13import json
Greg Edelston9cd16f52020-11-12 10:50:28 -070014import os
Greg Edelstonf70963a2020-11-17 14:36:06 -070015import sys
Greg Edelston9cd16f52020-11-12 10:50:28 -070016import tempfile
17import unittest
18
19import platform_json
20
21MOCK_CONSOLIDATED_JSON_CONTENTS = \
22'''{
23 "DEFAULTS": {
24 "platform": null,
25 "parent": null,
26 "field1": 5,
27 "field2": 5,
28 "field3": 5,
Greg Edelstonb3efad22020-11-24 11:09:39 -070029 "field4": 5,
30 "fieldArray": [
31 "elem5"
32 ]
Greg Edelston9cd16f52020-11-12 10:50:28 -070033 },
34 "my_platform": {
35 "platform": "my_platform",
36 "parent": "my_parent",
37 "field1": 1,
Greg Edelstonb3efad22020-11-24 11:09:39 -070038 "fieldArray": [
39 "elem1",
40 "elem2"
41 ],
Greg Edelston9cd16f52020-11-12 10:50:28 -070042 "models": {
43 "my_model": {
44 "field1": 4
Greg Edelston64fdc2e2020-11-19 15:04:18 -070045 },
46 "my_model2": {
47 "field2": 4
Greg Edelston9cd16f52020-11-12 10:50:28 -070048 }
49 }
50 },
51 "my_parent": {
52 "platform": "my_parent",
53 "parent": "my_grandparent",
54 "field1": 2,
55 "field2": 2
56 },
57 "my_grandparent": {
58 "platform": "my_grandparent",
59 "field1": 3,
60 "field2": 3,
61 "field3": 3
62 }
63}'''
64
Greg Edelston9cd16f52020-11-12 10:50:28 -070065
Greg Edelstonf70963a2020-11-17 14:36:06 -070066def _run_main(argv):
67 """Run platform_json.main(argv), capturing and returning stdout."""
68 original_stdout = sys.stdout
69 capture_io = io.StringIO()
70 sys.stdout = capture_io
71 try:
72 platform_json.main(argv)
73 return capture_io.getvalue()
74 finally:
75 capture_io.close()
76 sys.stdout = original_stdout
77
78
Greg Edelston64fdc2e2020-11-19 15:04:18 -070079class AbstractMockConfigTestCase(object):
Greg Edelstonf70963a2020-11-17 14:36:06 -070080 """Parent class to handle setup and teardown of mock configs."""
81
82 def setUp(self): # pylint:disable=invalid-name
Greg Edelston9cd16f52020-11-12 10:50:28 -070083 """Write mock JSON to a temporary file"""
84 _, self.mock_filepath = tempfile.mkstemp()
85 with open(self.mock_filepath, 'w') as mock_file:
86 mock_file.write(MOCK_CONSOLIDATED_JSON_CONTENTS)
87
Greg Edelstonf70963a2020-11-17 14:36:06 -070088 def tearDown(self): # pylint:disable=invalid-name
89 """Destroy the mock JSON file"""
90 os.remove(self.mock_filepath)
91
92
Greg Edelston64fdc2e2020-11-19 15:04:18 -070093class InheritanceTestCase(AbstractMockConfigTestCase, unittest.TestCase):
Greg Edelstonf70963a2020-11-17 14:36:06 -070094 """Ensure that all levels of inheritance are handled correctly"""
95
Greg Edelston9cd16f52020-11-12 10:50:28 -070096 def runTest(self): # pylint:disable=invalid-name
97 """Load platform config and check that it looks correct"""
Greg Edelston64fdc2e2020-11-19 15:04:18 -070098 consolidated_json = platform_json.load_consolidated_json(
99 self.mock_filepath)
100 my_platform = platform_json.calculate_config('my_platform',
101 None,
102 consolidated_json)
Greg Edelston9cd16f52020-11-12 10:50:28 -0700103 self.assertEqual(my_platform['field1'], 1) # No inheritance
104 self.assertEqual(my_platform['field2'], 2) # Direct inheritance
105 self.assertEqual(my_platform['field3'], 3) # Recursive inheritance
106 self.assertEqual(my_platform['field4'], 5) # Inherit from DEFAULTS
Greg Edelston64fdc2e2020-11-19 15:04:18 -0700107 my_model = platform_json.calculate_config('my_platform',
108 'my_model',
109 consolidated_json)
Greg Edelston9cd16f52020-11-12 10:50:28 -0700110 self.assertEqual(my_model['field1'], 4) # Model override
111 self.assertEqual(my_model['field2'], 2) # Everything else is the same
112 self.assertEqual(my_model['field3'], 3)
113 self.assertEqual(my_model['field4'], 5)
114
115
Greg Edelston64fdc2e2020-11-19 15:04:18 -0700116class EndToEndPlatformTestCase(AbstractMockConfigTestCase, unittest.TestCase):
Greg Edelstonf70963a2020-11-17 14:36:06 -0700117 """End-to-end testing for specifying the platform name."""
118
Greg Edelston64fdc2e2020-11-19 15:04:18 -0700119 def runTest(self): # pylint: disable=invalid-name
Greg Edelstonf70963a2020-11-17 14:36:06 -0700120 """Main test logic"""
121 # Basic platform specification
122 argv = ['my_platform', '-c', self.mock_filepath]
123 expected_json = collections.OrderedDict({
124 'platform': 'my_platform',
125 'parent': 'my_parent',
126 'field1': 1,
127 'field2': 2,
128 'field3': 3,
Greg Edelstonb3efad22020-11-24 11:09:39 -0700129 'field4': 5,
130 'fieldArray': [
131 'elem1',
132 'elem2',
133 ],
Greg Edelstonf70963a2020-11-17 14:36:06 -0700134 })
135 expected_output = json.dumps(expected_json, indent=4) + '\n'
136 self.assertEqual(_run_main(argv), expected_output)
137
138 # Condensed output
139 argv.append('--condense-output')
140 expected_output = json.dumps(expected_json, indent=None)
141 self.assertEqual(_run_main(argv), expected_output)
142
143 # Non-existent platform should raise an error
144 argv = ['fake_platform', '-c', self.mock_filepath]
145 with self.assertRaises(platform_json.PlatformNotFoundError):
146 _run_main(argv)
147
148
Greg Edelston64fdc2e2020-11-19 15:04:18 -0700149class EndToEndFieldTestCase(AbstractMockConfigTestCase, unittest.TestCase):
Greg Edelstonf70963a2020-11-17 14:36:06 -0700150 """End-to-end testing for specifying the field name."""
151
152 def runTest(self): # pylint: disable=invalid-name
153 """Main test logic"""
154 # Basic field specification
155 argv = ['my_platform', '-f', 'field1', '-c', self.mock_filepath]
156 self.assertEqual(_run_main(argv), '1\n')
157
158 # Condensed output should yield no newline
159 argv.append('--condense-output')
160 self.assertEqual(_run_main(argv), '1')
161
162 # Non-existent field should raise an error
163 argv = ['my_platform', '-f', 'fake_field', '-c', self.mock_filepath]
164 with self.assertRaises(platform_json.FieldNotFoundError):
165 _run_main(argv)
Greg Edelston9cd16f52020-11-12 10:50:28 -0700166
167
168if __name__ == '__main__':
169 unittest.main()