def test_returns_only_lts(self): release = factory.make_name("release") name = "ubuntu/%s" % release support_eol = factory.make_date().strftime("%Y-%m-%d") release_title = "%s LTS" % release resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name ) factory.make_BootSourceCache( os="ubuntu", release=release, release_title=release_title, support_eol=support_eol, ) other_release = factory.make_name("release") other_name = "ubuntu/%s" % other_release other_support_eol = factory.make_date().strftime("%Y-%m-%d") factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED, name=other_name ) factory.make_BootSourceCache( os="ubuntu", release=other_release, release_title=other_release, support_eol=other_support_eol, ) self.assertEqual( [resource], BootResource.objects.get_available_commissioning_resources(), )
def test_get_commissionable_resource_returns_sorted_by_architecture(self): os = factory.make_name("os") series = factory.make_name("series") name = "%s/%s" % (os, series) resource_b = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name, architecture="b/generic", ) resource_a = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name, architecture="a/generic", ) resource_c = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name, architecture="c/generic", ) commissionables = BootResource.objects.get_commissionable_resource( os, series ) self.assertEqual( [resource_a, resource_b, resource_c], list(commissionables) )
def test__returns_empty_if_no_cache(self): release = factory.make_name("release") name = "ubuntu/%s" % release factory.make_usable_boot_resource(rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name) self.assertEqual( [], BootResource.objects.get_available_commissioning_resources())
def make_boot_sources(self): kernels = [] ubuntu = UbuntuDistroInfo() for row in ubuntu._rows: release_year = int(row['version'].split('.')[0]) if release_year < 12: continue elif release_year < 16: style = row['series'][0] else: style = row['version'] for kflavor in [ 'generic', 'lowlatency', 'edge', 'lowlatency-edge' ]: if kflavor == 'generic': kernel = "hwe-%s" % style else: kernel = "hwe-%s-%s" % (style, kflavor) arch = factory.make_name('arch') architecture = "%s/%s" % (arch, kernel) release = row['series'].split(' ')[0] factory.make_usable_boot_resource( name="ubuntu/" + release, kflavor=kflavor, extra={'subarches': kernel}, architecture=architecture, rtype=BOOT_RESOURCE_TYPE.SYNCED) factory.make_BootSourceCache(os="ubuntu", arch=arch, subarch=kernel, release=release) kernels.append((kernel, '%s (%s)' % (release, kernel))) return kernels
def test_get_supported_hwe_kernel_includes_all_subarches(self): factory.make_usable_boot_resource( architecture='amd64/hwe-16.04', extra={'subarches': 'hwe-p,hwe-t,hwe-16.04,hwe-16.10'}) self.assertEquals( ['hwe-p', 'hwe-t', 'hwe-16.04', 'hwe-16.10'], BootResource.objects.get_supported_hwe_kernels())
def test_get_usable_hwe_kernel_doesnt_include_all_subarches(self): factory.make_usable_boot_resource( architecture="amd64/hwe-16.04", extra={"subarches": "hwe-p,hwe-t,hwe-16.04,hwe-16.10"}, ) self.assertEqual(["hwe-16.04"], BootResource.objects.get_usable_hwe_kernels())
def test_get_commissionable_resource_returns_iterable(self): os = factory.make_name('os') series = factory.make_name('series') name = '%s/%s' % (os, series) factory.make_usable_boot_resource(rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name) commissionables = BootResource.objects.get_commissionable_resource( os, series) self.assertIsInstance(commissionables, Iterable)
def test_architectures(self): arches = [ "%s/%s" % (factory.make_name("arch"), factory.make_name("subarch")) for _ in range(3) ] for arch in arches: factory.make_usable_boot_resource(architecture=arch) handler = GeneralHandler(factory.make_User(), {}) self.assertEqual(sorted(arches), handler.architectures({}))
def test_get_commissionable_resource_returns_only_for_os_series(self): os = factory.make_name('os') series = factory.make_name('series') name = '%s/%s' % (os, series) resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name) factory.make_usable_boot_resource() commissionables = BootResource.objects.get_commissionable_resource( os, series) self.assertItemsEqual([resource], commissionables)
def test_get_usable_architectures(self): arches = [ '%s/%s' % (factory.make_name('arch'), factory.make_name('subarch')) for _ in range(4) ] incomplete_arch = arches.pop() factory.make_incomplete_boot_resource(architecture=incomplete_arch) for arch in arches: factory.make_usable_boot_resource(architecture=arch) usable_arches = BootResource.objects.get_usable_architectures() self.assertIsInstance(usable_arches, list) self.assertItemsEqual(arches, usable_arches)
def test_get_default_commissioning_resource_returns_first_arch(self): os = factory.make_name('os') series = factory.make_name('series') name = '%s/%s' % (os, series) arches = ['ppc64el/generic', 'arm64/generic'] for arch in arches: factory.make_usable_boot_resource(rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name, architecture=arch) self.assertEqual( 'arm64/generic', BootResource.objects.get_default_commissioning_resource( os, series).architecture)
def test_get_default_commissioning_resource_returns_first_arch(self): os = factory.make_name("os") series = factory.make_name("series") name = "%s/%s" % (os, series) arches = ["ppc64el/generic", "arm64/generic"] for arch in arches: factory.make_usable_boot_resource(rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name, architecture=arch) self.assertEqual( "arm64/generic", BootResource.objects.get_default_commissioning_resource( os, series).architecture, )
def make_usable_boot_resource(self, arch=None, subarch=None): """Create a set of boot resources, so the architecture becomes usable. This will make the resources' architecture show up in the list of usable architectures. """ if arch is None: arch = factory.make_name('arch') if subarch is None: subarch = factory.make_name('subarch') for purpose in ['install', 'commissioning']: architecture = '%s/%s' % (arch, subarch) factory.make_usable_boot_resource(rtype=BOOT_RESOURCE_TYPE.SYNCED, architecture=architecture)
def test_returns_usable_kernels(self): if self.subarch == "generic": generic_kernels = [] for i in self.kernels: kernel_parts = i.split("-") if len(kernel_parts) > 2: kflavor = kernel_parts[2] else: kflavor = "generic" generic_kernels.append(i) factory.make_usable_boot_resource( name=self.name, rtype=BOOT_RESOURCE_TYPE.SYNCED, architecture="%s/%s" % (self.arch, i), kflavor=kflavor, rolling=True, ) factory.make_incomplete_boot_resource( name=self.name, rtype=BOOT_RESOURCE_TYPE.SYNCED, architecture="%s/%s" % (self.arch, factory.make_name("incomplete")), kflavor=kflavor, ) else: generic_kernels = self.kernels factory.make_usable_boot_resource( name=self.name, rtype=BOOT_RESOURCE_TYPE.SYNCED, architecture="%s/%s" % (self.arch, self.subarch), rolling=True, ) self.assertEqual( sorted(self.kernels), sorted( BootResource.objects.get_usable_hwe_kernels( self.name, self.arch ) ), "%s should return %s as its usable kernel" % (self.name, self.kernels), ) self.assertEqual( generic_kernels, BootResource.objects.get_usable_hwe_kernels( self.name, self.arch, "generic" ), "%s should return %s as its usable kernel" % (self.name, generic_kernels), )
def test_get_usable_architectures_combines_subarches(self): arches = set() for _ in range(3): arch = factory.make_name('arch') subarches = [factory.make_name('subarch') for _ in range(3)] architecture = "%s/%s" % (arch, subarches[0]) for subarch in subarches: arches.add('%s/%s' % (arch, subarch)) factory.make_usable_boot_resource( architecture=architecture, extra={'subarches': ','.join(subarches)}) usable_arches = BootResource.objects.get_usable_architectures() self.assertIsInstance(usable_arches, list) self.assertItemsEqual(arches, usable_arches)
def test__returns_longest_remaining_supported_lts_first(self): trusty_resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED, name="ubuntu/trusty") factory.make_BootSourceCache( os="ubuntu", release="trusty", release_title="14.04 LTS", support_eol="2019-04-17") xenial_resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED, name="ubuntu/xenial") factory.make_BootSourceCache( os="ubuntu", release="xenial", release_title="16.04 LTS", support_eol="2021-04-17") self.assertEqual( [xenial_resource, trusty_resource], BootResource.objects.get_available_commissioning_resources())
def test_adds_boot_resource_set_to_existing_uploaded_boot_resource(self): os = factory.make_name('os') series = factory.make_name('series') OperatingSystemRegistry.register_item(os, CustomOS()) self.addCleanup(OperatingSystemRegistry.unregister_item, os) name = '%s/%s' % (os, series) architecture = make_usable_architecture(self) resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.UPLOADED, name=name, architecture=architecture) upload_type, filetype = self.pick_filetype() size = random.randint(1024, 2048) content = factory.make_string(size).encode('utf-8') upload_name = factory.make_name('filename') uploaded_file = SimpleUploadedFile(content=content, name=upload_name) data = { 'name': name, 'architecture': architecture, 'filetype': upload_type, 'keep_old': True, } form = BootResourceForm(data=data, files={'content': uploaded_file}) self.assertTrue(form.is_valid(), form._errors) form.save() resource = reload_object(resource) resource_set = resource.sets.order_by('id').last() rfile = resource_set.files.first() self.assertTrue(filetype, rfile.filetype) self.assertTrue(filetype, rfile.filename) self.assertTrue(size, rfile.largefile.total_size) with rfile.largefile.content.open('rb') as stream: written_content = stream.read() self.assertEqual(content, written_content) self.assertEqual(resource.rtype, BOOT_RESOURCE_TYPE.UPLOADED)
def test_adds_boot_resource_set_to_existing_boot_resource(self): name = factory.make_name("name") architecture = make_usable_architecture(self) resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.UPLOADED, name=name, architecture=architecture, ) upload_type, filetype = self.pick_filetype() size = random.randint(1024, 2048) content = factory.make_string(size).encode("utf-8") upload_name = factory.make_name("filename") uploaded_file = SimpleUploadedFile(content=content, name=upload_name) data = { "name": name, "architecture": architecture, "filetype": upload_type, "keep_old": True, } form = BootResourceForm(data=data, files={"content": uploaded_file}) self.assertTrue(form.is_valid(), form._errors) form.save() resource = reload_object(resource) resource_set = resource.sets.order_by("id").last() rfile = resource_set.files.first() self.assertTrue(filetype, rfile.filetype) self.assertTrue(filetype, rfile.filename) self.assertTrue(size, rfile.largefile.total_size) with rfile.largefile.content.open("rb") as stream: written_content = stream.read() self.assertEqual(content, written_content)
def test__returns_multiple_resource_for_hwe_resources(self): os = factory.make_name('os') series = factory.make_name('series') name = '%s/%s' % (os, series) arch = factory.make_name('arch') subarches = [factory.make_name('hwe') for _ in range(3)] resources = [ factory.make_usable_boot_resource(rtype=BOOT_RESOURCE_TYPE.SYNCED, name=name, architecture='%s/%s' % (arch, subarch)) for subarch in subarches ] images = [] for resource in resources: label = resource.get_latest_complete_set().label purposes = [factory.make_name('purpose') for _ in range(3)] arch, subarch = resource.split_arch() images.extend([ make_rpc_boot_image(osystem=os, release=series, architecture=arch, subarchitecture=subarch, label=label, purpose=purpose) for purpose in purposes ]) self.assertItemsEqual( resources, BootResource.objects.get_resources_matching_boot_images(images))
def test_removes_old_bootresourcefiles(self): # Regression test for LP:1660418 os = factory.make_name('os') series = factory.make_name('series') OperatingSystemRegistry.register_item(os, CustomOS()) self.addCleanup(OperatingSystemRegistry.unregister_item, os) name = '%s/%s' % (os, series) architecture = make_usable_architecture(self) resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.UPLOADED, name=name, architecture=architecture) upload_type, filetype = self.pick_filetype() size = random.randint(1024, 2048) content = factory.make_string(size).encode('utf-8') upload_name = factory.make_name('filename') uploaded_file = SimpleUploadedFile(content=content, name=upload_name) data = { 'name': name, 'architecture': architecture, 'filetype': upload_type, } form = BootResourceForm(data=data, files={'content': uploaded_file}) self.assertTrue(form.is_valid(), form._errors) form.save() self.assertEqual( 1, BootResourceFile.objects.filter( resource_set__resource=resource).count())
def test__commissioning_node_uses_min_hwe_kernel(self): rack_controller = factory.make_RackController() local_ip = factory.make_ip_address() remote_ip = factory.make_ip_address() node = factory.make_Node_with_Interface_on_Subnet( status=NODE_STATUS.COMMISSIONING, min_hwe_kernel="hwe-16.10") arch = node.split_arch()[0] ubuntu = factory.make_default_ubuntu_release_bootable(arch) factory.make_usable_boot_resource( name=ubuntu.name, architecture="%s/hwe-16.10" % arch, kflavor='generic', rtype=BOOT_RESOURCE_TYPE.SYNCED) mac = node.get_boot_interface().mac_address observed_config = get_config( rack_controller.system_id, local_ip, remote_ip, mac=mac) self.assertEqual("hwe-16.10", observed_config["subarch"])
def test_commissioningform_contains_real_and_ui_choice(self): release = factory.pick_ubuntu_release() name = 'ubuntu/%s' % release arch = factory.make_name('arch') kernel = 'hwe-' + release[0] # Disable boot sources signals otherwise the test fails due to unrun # post-commit tasks at the end of the test. self.useFixture(SignalsDisabled('bootsources')) factory.make_BootSourceCache(os=name, subarch=kernel, release=release) factory.make_usable_boot_resource(name=name, architecture='%s/%s' % (arch, kernel), rtype=BOOT_RESOURCE_TYPE.SYNCED) Config.objects.set_config('commissioning_distro_series', release) form = CommissioningForm() self.assertItemsEqual([('', '--- No minimum kernel ---'), (kernel, '%s (%s)' % (release, kernel))], form.fields['default_min_hwe_kernel'].choices)
def make_boot_sources(self): kernels = [] ubuntu = UbuntuDistroInfo() # LP: #1711191 - distro-info 0.16+ no longer returns dictionaries or # lists, and it now returns objects instead. As such, we need to # handle both cases for backwards compatibility. try: ubuntu_rows = ubuntu._rows except AttributeError: ubuntu_rows = [row.__dict__ for row in ubuntu._releases] for row in ubuntu_rows: release_year = int(row["version"].split(".")[0]) if release_year < 12: continue elif release_year < 16: style = row["series"][0] else: style = row["version"] for kflavor in [ "generic", "lowlatency", "edge", "lowlatency-edge", ]: if kflavor == "generic": kernel = "hwe-%s" % style else: kernel = "hwe-%s-%s" % (style, kflavor) arch = factory.make_name("arch") architecture = "%s/%s" % (arch, kernel) release = row["series"].split(" ")[0] factory.make_usable_boot_resource( name="ubuntu/" + release, kflavor=kflavor, extra={"subarches": kernel}, architecture=architecture, rtype=BOOT_RESOURCE_TYPE.SYNCED, ) factory.make_BootSourceCache(os="ubuntu", arch=arch, subarch=kernel, release=release) kernels.append((kernel, "%s (%s)" % (release, kernel))) return kernels
def test_GET_returns_boot_resource(self): resource = factory.make_usable_boot_resource() response = self.client.get(get_boot_resource_uri(resource)) self.assertEqual(http.client.OK, response.status_code) returned_resource = json_load_bytes(response.content) # The returned object contains a 'resource_uri' field. self.assertEqual(reverse('boot_resource_handler', args=[resource.id]), returned_resource['resource_uri']) self.assertThat(returned_resource, ContainsAll(['id', 'type', 'name', 'architecture']))
def test__returns_False_if_image_label_doesnt_match_resource(self): resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED) os, series = resource.name.split('/') arch, subarch = resource.split_arch() image = make_rpc_boot_image( osystem=os, release=series, architecture=arch, subarchitecture=subarch, label=factory.make_name('label')) self.assertFalse(BootResource.objects.boot_images_are_in_sync([image]))
def test__returns_True_for_uploaded_resource(self): resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.UPLOADED) arch, subarch = resource.split_arch() label = resource.get_latest_complete_set().label image = make_rpc_boot_image( osystem="custom", release=resource.name, architecture=arch, subarchitecture=subarch, label=label) self.assertTrue(BootResource.objects.boot_images_are_in_sync([image]))
def test__returns_False_if_image_subarch_not_supported_by_resource(self): resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED) os, series = resource.name.split('/') arch, subarch = resource.split_arch() label = resource.get_latest_complete_set().label image = make_rpc_boot_image( osystem=os, release=series, architecture=arch, subarchitecture=factory.make_name('subarch'), label=label) self.assertFalse(BootResource.objects.boot_images_are_in_sync([image]))
def test__returns_True_for_generated_resource(self): resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.GENERATED) os, series = resource.name.split('/') arch, subarch = resource.split_arch() label = resource.get_latest_complete_set().label image = make_rpc_boot_image( osystem=os, release=series, architecture=arch, subarchitecture=subarch, label=label) self.assertTrue(BootResource.objects.boot_images_are_in_sync([image]))
def test__returns_resource_with_wildcard_label(self): resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED) os, series = resource.name.split('/') arch, subarch = resource.split_arch() image = make_rpc_boot_image( osystem=os, release=series, architecture=arch, subarchitecture=subarch, label='*') self.assertItemsEqual( [resource], BootResource.objects.get_resources_matching_boot_images([image]))
def test__returns_empty_list_if_label_doesnt_match_resource(self): resource = factory.make_usable_boot_resource( rtype=BOOT_RESOURCE_TYPE.SYNCED) os, series = resource.name.split('/') arch, subarch = resource.split_arch() image = make_rpc_boot_image( osystem=os, release=series, architecture=arch, subarchitecture=subarch, label=factory.make_name('label')) self.assertEqual( [], BootResource.objects.get_resources_matching_boot_images([image]))