diff options
| author | Mark Hatle <mark.hatle@windriver.com> | 2018-07-23 22:29:11 -0400 |
|---|---|---|
| committer | Richard Purdie <richard.purdie@linuxfoundation.org> | 2018-08-02 10:18:27 +0100 |
| commit | 1ac19d1bf111a4836625f5cbb28a751d5c427395 (patch) | |
| tree | ae9fa1448b425522952cbc8af90cf79912c746b1 /bitbake/lib/layerindexlib/tests/restapi.py | |
| parent | 0dea95093115acc08f6ad19dc931d532a601cbec (diff) | |
| download | poky-1ac19d1bf111a4836625f5cbb28a751d5c427395.tar.gz | |
bitbake: layerindexlib: Initial layer index processing module implementation
The layer index module is expected to be used by various parts of the system
in order to access a layerindex-web (such as layers.openembedded.org) and
perform basic processing on the information, such as dependency scanning.
Along with the layerindex implementation are associated tests. The tests
properly honor BB_SKIP_NETTESTS='yes' to prevent test failures.
Tests Implemented:
- Branch, LayerItem, LayerBranch, LayerDependency, Recipe, Machine and
Distro objects
- LayerIndex setup using the layers.openembedded.org restapi
- LayerIndex storing and retrieving from a file
- LayerIndex verify dependency resolution ordering
- LayerIndex setup using simulated cooker data
(Bitbake rev: fd0ee6c10dbb5592731e56f4c592fe687682a3e6)
Signed-off-by: Mark Hatle <mark.hatle@windriver.com>
Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
Diffstat (limited to 'bitbake/lib/layerindexlib/tests/restapi.py')
| -rw-r--r-- | bitbake/lib/layerindexlib/tests/restapi.py | 174 |
1 files changed, 174 insertions, 0 deletions
diff --git a/bitbake/lib/layerindexlib/tests/restapi.py b/bitbake/lib/layerindexlib/tests/restapi.py new file mode 100644 index 0000000000..bfaac43db4 --- /dev/null +++ b/bitbake/lib/layerindexlib/tests/restapi.py | |||
| @@ -0,0 +1,174 @@ | |||
| 1 | # Copyright (C) 2017-2018 Wind River Systems, Inc. | ||
| 2 | # | ||
| 3 | # This program is free software; you can redistribute it and/or modify | ||
| 4 | # it under the terms of the GNU General Public License version 2 as | ||
| 5 | # published by the Free Software Foundation. | ||
| 6 | # | ||
| 7 | # This program is distributed in the hope that it will be useful, | ||
| 8 | # but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 9 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||
| 10 | # See the GNU General Public License for more details. | ||
| 11 | # | ||
| 12 | # You should have received a copy of the GNU General Public License | ||
| 13 | # along with this program; if not, write to the Free Software | ||
| 14 | # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | ||
| 15 | |||
| 16 | import unittest | ||
| 17 | import tempfile | ||
| 18 | import os | ||
| 19 | import bb | ||
| 20 | |||
| 21 | import layerindexlib | ||
| 22 | from layerindexlib.tests.common import LayersTest | ||
| 23 | |||
| 24 | import logging | ||
| 25 | |||
| 26 | class LayerIndexWebRestApiTest(LayersTest): | ||
| 27 | |||
| 28 | if os.environ.get("BB_SKIP_NETTESTS") == "yes": | ||
| 29 | print("Unset BB_SKIP_NETTESTS to run network tests") | ||
| 30 | else: | ||
| 31 | def setUp(self): | ||
| 32 | LayersTest.setUp(self) | ||
| 33 | self.layerindex = layerindexlib.LayerIndex(self.d) | ||
| 34 | self.layerindex.load_layerindex('http://layers.openembedded.org/layerindex/api/;branch=sumo', load=['layerDependencies']) | ||
| 35 | |||
| 36 | def test_layerindex_is_empty(self): | ||
| 37 | self.assertFalse(self.layerindex.is_empty(), msg="Layerindex is empty") | ||
| 38 | |||
| 39 | def test_layerindex_store_file(self): | ||
| 40 | self.layerindex.store_layerindex('file://%s/file.json' % self.tempdir, self.layerindex.indexes[0]) | ||
| 41 | |||
| 42 | self.assertTrue(os.path.isfile('%s/file.json' % self.tempdir), msg="Temporary file was not created by store_layerindex") | ||
| 43 | |||
| 44 | reload = layerindexlib.LayerIndex(self.d) | ||
| 45 | reload.load_layerindex('file://%s/file.json' % self.tempdir) | ||
| 46 | |||
| 47 | self.assertFalse(reload.is_empty(), msg="Layerindex is empty") | ||
| 48 | |||
| 49 | # Calculate layerItems in original index that should NOT be in reload | ||
| 50 | layerItemNames = [] | ||
| 51 | for itemId in self.layerindex.indexes[0].layerItems: | ||
| 52 | layerItemNames.append(self.layerindex.indexes[0].layerItems[itemId].name) | ||
| 53 | |||
| 54 | for layerBranchId in self.layerindex.indexes[0].layerBranches: | ||
| 55 | layerItemNames.remove(self.layerindex.indexes[0].layerBranches[layerBranchId].layer.name) | ||
| 56 | |||
| 57 | for itemId in reload.indexes[0].layerItems: | ||
| 58 | self.assertFalse(reload.indexes[0].layerItems[itemId].name in layerItemNames, msg="Item reloaded when it shouldn't have been") | ||
| 59 | |||
| 60 | # Compare the original to what we wrote... | ||
| 61 | for type in self.layerindex.indexes[0]._index: | ||
| 62 | if type == 'apilinks' or \ | ||
| 63 | type == 'layerItems' or \ | ||
| 64 | type in self.layerindex.indexes[0].config['local']: | ||
| 65 | continue | ||
| 66 | for id in getattr(self.layerindex.indexes[0], type): | ||
| 67 | self.logger.debug(1, "type %s" % (type)) | ||
| 68 | |||
| 69 | self.assertTrue(id in getattr(reload.indexes[0], type), msg="Id number not in reloaded index") | ||
| 70 | |||
| 71 | self.logger.debug(1, "%s ? %s" % (getattr(self.layerindex.indexes[0], type)[id], getattr(reload.indexes[0], type)[id])) | ||
| 72 | |||
| 73 | self.assertEqual(getattr(self.layerindex.indexes[0], type)[id], getattr(reload.indexes[0], type)[id], msg="Reloaded contents different") | ||
| 74 | |||
| 75 | def test_layerindex_store_split(self): | ||
| 76 | self.layerindex.store_layerindex('file://%s' % self.tempdir, self.layerindex.indexes[0]) | ||
| 77 | |||
| 78 | reload = layerindexlib.LayerIndex(self.d) | ||
| 79 | reload.load_layerindex('file://%s' % self.tempdir) | ||
| 80 | |||
| 81 | self.assertFalse(reload.is_empty(), msg="Layer index is empty") | ||
| 82 | |||
| 83 | for type in self.layerindex.indexes[0]._index: | ||
| 84 | if type == 'apilinks' or \ | ||
| 85 | type == 'layerItems' or \ | ||
| 86 | type in self.layerindex.indexes[0].config['local']: | ||
| 87 | continue | ||
| 88 | for id in getattr(self.layerindex.indexes[0] ,type): | ||
| 89 | self.logger.debug(1, "type %s" % (type)) | ||
| 90 | |||
| 91 | self.assertTrue(id in getattr(reload.indexes[0], type), msg="Id number missing from reloaded data") | ||
| 92 | |||
| 93 | self.logger.debug(1, "%s ? %s" % (getattr(self.layerindex.indexes[0] ,type)[id], getattr(reload.indexes[0], type)[id])) | ||
| 94 | |||
| 95 | self.assertEqual(getattr(self.layerindex.indexes[0] ,type)[id], getattr(reload.indexes[0], type)[id], msg="reloaded data does not match original") | ||
| 96 | |||
| 97 | def test_dependency_resolution(self): | ||
| 98 | # Verify depth first searching... | ||
| 99 | (dependencies, invalidnames) = self.layerindex.find_dependencies(names=['meta-python']) | ||
| 100 | |||
| 101 | first = True | ||
| 102 | for deplayerbranch in dependencies: | ||
| 103 | layerBranch = dependencies[deplayerbranch][0] | ||
| 104 | layerDeps = dependencies[deplayerbranch][1:] | ||
| 105 | |||
| 106 | if not first: | ||
| 107 | continue | ||
| 108 | |||
| 109 | first = False | ||
| 110 | |||
| 111 | # Top of the deps should be openembedded-core, since everything depends on it. | ||
| 112 | self.assertEqual(layerBranch.layer.name, "openembedded-core", msg='OpenEmbedded-Core is no the first dependency') | ||
| 113 | |||
| 114 | # meta-python should cause an openembedded-core dependency, if not assert! | ||
| 115 | for dep in layerDeps: | ||
| 116 | if dep.layer.name == 'meta-python': | ||
| 117 | break | ||
| 118 | else: | ||
| 119 | self.logger.debug(1, "meta-python was not found") | ||
| 120 | self.assetTrue(False) | ||
| 121 | |||
| 122 | # Only check the first element... | ||
| 123 | break | ||
| 124 | else: | ||
| 125 | # Empty list, this is bad. | ||
| 126 | self.logger.debug(1, "Empty list of dependencies") | ||
| 127 | self.assertIsNotNone(first, msg="Empty list of dependencies") | ||
| 128 | |||
| 129 | # Last dep should be the requested item | ||
| 130 | layerBranch = dependencies[deplayerbranch][0] | ||
| 131 | self.assertEqual(layerBranch.layer.name, "meta-python", msg="Last dependency not meta-python") | ||
| 132 | |||
| 133 | def test_find_collection(self): | ||
| 134 | def _check(collection, expected): | ||
| 135 | self.logger.debug(1, "Looking for collection %s..." % collection) | ||
| 136 | result = self.layerindex.find_collection(collection) | ||
| 137 | if expected: | ||
| 138 | self.assertIsNotNone(result, msg="Did not find %s when it should be there" % collection) | ||
| 139 | else: | ||
| 140 | self.assertIsNone(result, msg="Found %s when it shouldn't be there" % collection) | ||
| 141 | |||
| 142 | tests = [ ('core', True), | ||
| 143 | ('openembedded-core', False), | ||
| 144 | ('networking-layer', True), | ||
| 145 | ('meta-python', True), | ||
| 146 | ('openembedded-layer', True), | ||
| 147 | ('notpresent', False) ] | ||
| 148 | |||
| 149 | for collection,result in tests: | ||
| 150 | _check(collection, result) | ||
| 151 | |||
| 152 | def test_find_layerbranch(self): | ||
| 153 | def _check(name, expected): | ||
| 154 | self.logger.debug(1, "Looking for layerbranch %s..." % name) | ||
| 155 | |||
| 156 | for index in self.layerindex.indexes: | ||
| 157 | for layerbranchid in index.layerBranches: | ||
| 158 | self.logger.debug(1, "Present: %s" % index.layerBranches[layerbranchid].layer.name) | ||
| 159 | result = self.layerindex.find_layerbranch(name) | ||
| 160 | if expected: | ||
| 161 | self.assertIsNotNone(result, msg="Did not find %s when it should be there" % collection) | ||
| 162 | else: | ||
| 163 | self.assertIsNone(result, msg="Found %s when it shouldn't be there" % collection) | ||
| 164 | |||
| 165 | tests = [ ('openembedded-core', True), | ||
| 166 | ('core', False), | ||
| 167 | ('meta-networking', True), | ||
| 168 | ('meta-python', True), | ||
| 169 | ('meta-oe', True), | ||
| 170 | ('notpresent', False) ] | ||
| 171 | |||
| 172 | for collection,result in tests: | ||
| 173 | _check(collection, result) | ||
| 174 | |||
