From 0dfd892f5e426a3a1df6c15233e1491e006a0d86 Mon Sep 17 00:00:00 2001 From: Vladimir Khlyunev Date: Fri, 29 Mar 2019 13:13:36 +0400 Subject: [PATCH] Add ability to disable bootmenu parameter Right now there are some kind of bug that prevents VM from booting when running at virtualized slave on latest xenial qemu packages & kernel. Disabling whole bootmenu parameter hepls. Change-Id: I838ee5cb69babc37f19093b2a378e984fcc0b958 --- .../0003_add_field_enable_bootmenu.py | 159 ++++++++++++++++++ devops/models/environment.py | 10 +- devops/models/node.py | 13 +- 3 files changed, 175 insertions(+), 7 deletions(-) create mode 100644 devops/migrations/0003_add_field_enable_bootmenu.py diff --git a/devops/migrations/0003_add_field_enable_bootmenu.py b/devops/migrations/0003_add_field_enable_bootmenu.py new file mode 100644 index 00000000..3c573afd --- /dev/null +++ b/devops/migrations/0003_add_field_enable_bootmenu.py @@ -0,0 +1,159 @@ +# -*- coding: utf-8 -*- +# flake8: noqa +from south.utils import datetime_utils as datetime +from south.db import db +from south.v2 import SchemaMigration + + +class Migration(SchemaMigration): + def forwards(self, orm): + # Adding field 'Node.enable_bootmenu' + db.add_column('devops_node', 'enable_bootmenu', + self.gf('django.db.models.fields.BooleanField')( + default=True), keep_default=False) + + def backwards(self, orm): + # Deleting field 'Node.enable_bootmenu' + db.delete_column('devops_node', 'enable_bootmenu') + + models = { + u'devops.address': { + 'Meta': {'object_name': 'Address'}, + u'id': ( + 'django.db.models.fields.AutoField', [], + {'primary_key': 'True'}), + 'interface': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Interface']"}), + 'ip_address': ('django.db.models.fields.GenericIPAddressField', [], + {'max_length': '39'}) + }, + u'devops.diskdevice': { + 'Meta': {'object_name': 'DiskDevice'}, + 'bus': ('django.db.models.fields.CharField', + [], {'max_length': '255'} + ), + 'device': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + u'id': ('django.db.models.fields.AutoField', [], + {'primary_key': 'True'}), + 'node': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Node']"}), + 'target_dev': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'type': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'volume': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Volume']", 'null': 'True'}) + }, + u'devops.environment': { + 'Meta': {'object_name': 'Environment'}, + 'created': ('django.db.models.fields.DateTimeField', [], + {'default': 'datetime.datetime.utcnow', + 'auto_now_add': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], + {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], + {'unique': 'True', 'max_length': '255'}) + }, + u'devops.interface': { + 'Meta': {'object_name': 'Interface'}, + u'id': ('django.db.models.fields.AutoField', [], + {'primary_key': 'True'}), + 'mac_address': ('django.db.models.fields.CharField', [], + {'unique': 'True', 'max_length': '255'}), + 'model': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'network': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Network']"}), + 'node': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Node']"}), + 'type': ('django.db.models.fields.CharField', [], + {'max_length': '255'}) + }, + u'devops.network': { + 'Meta': {'unique_together': "(('name', 'environment'),)", + 'object_name': 'Network'}, + 'created': ('django.db.models.fields.DateTimeField', [], + {'default': 'datetime.datetime.utcnow', + 'auto_now_add': 'True', 'blank': 'True'}), + 'environment': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Environment']", + 'null': 'True'}), + 'forward': ('django.db.models.fields.CharField', [], + {'max_length': '255', 'null': 'True'}), + 'has_dhcp_server': ('django.db.models.fields.BooleanField', [], + {}), + 'has_pxe_server': ('django.db.models.fields.BooleanField', [], {}), + 'has_reserved_ips': ('django.db.models.fields.BooleanField', [], + {'default': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], + {'primary_key': 'True'}), + 'ip_network': ('django.db.models.fields.CharField', [], + {'unique': 'True', 'max_length': '255'}), + 'name': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'tftp_root_dir': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'uuid': ('django.db.models.fields.CharField', [], + {'max_length': '255'}) + }, + u'devops.node': { + 'Meta': {'unique_together': "(('name', 'environment'),)", + 'object_name': 'Node'}, + 'architecture': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'boot': ('django.db.models.fields.CharField', [], + {'default': "'[]'", 'max_length': '255'}), + 'created': ('django.db.models.fields.DateTimeField', [], + {'default': 'datetime.datetime.utcnow', + 'auto_now_add': 'True', 'blank': 'True'}), + 'environment': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Environment']", + 'null': 'True'}), + 'enable_bootmenu': ('django.db.models.fields.BooleanField', [], + {'default': 'True'}), + 'has_vnc': ('django.db.models.fields.BooleanField', [], + {'default': 'True'}), + 'hypervisor': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + u'id': ('django.db.models.fields.AutoField', [], + {'primary_key': 'True'}), + 'memory': ('django.db.models.fields.IntegerField', [], + {'default': '1024'}), + 'metadata': ('django.db.models.fields.CharField', [], + {'max_length': '255', 'null': 'True'}), + 'name': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'os_type': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'role': ('django.db.models.fields.CharField', [], + {'max_length': '255', 'null': 'True'}), + 'uuid': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'vcpu': ('django.db.models.fields.PositiveSmallIntegerField', [], + {'default': '1'}) + }, + u'devops.volume': { + 'Meta': {'unique_together': "(('name', 'environment'),)", + 'object_name': 'Volume'}, + 'backing_store': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Volume']", 'null': 'True'}), + 'capacity': ('django.db.models.fields.BigIntegerField', [], {}), + 'created': ('django.db.models.fields.DateTimeField', [], + {'default': 'datetime.datetime.utcnow', + 'auto_now_add': 'True', 'blank': 'True'}), + 'environment': ('django.db.models.fields.related.ForeignKey', [], + {'to': u"orm['devops.Environment']", + 'null': 'True'}), + 'format': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + u'id': ('django.db.models.fields.AutoField', [], + {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], + {'max_length': '255'}), + 'uuid': ('django.db.models.fields.CharField', [], + {'max_length': '255'}) + } + } + + complete_apps = ['devops'] diff --git a/devops/models/environment.py b/devops/models/environment.py index 383a6f33..50a3b3ab 100644 --- a/devops/models/environment.py +++ b/devops/models/environment.py @@ -86,14 +86,16 @@ class Environment(DriverModel): def get_nodes(self, *args, **kwargs): return self.node_set.filter(*args, **kwargs) - def add_node(self, memory, name, vcpu=1, boot=None, role='fuel_slave'): + def add_node(self, memory, name, vcpu=1, boot=None, role='fuel_slave', + enable_bootmenu=True): return Node.node_create( name=name, memory=memory, vcpu=vcpu, environment=self, role=role, - boot=boot) + boot=boot, + enable_bootmenu=enable_bootmenu) def add_empty_volume(self, node, name, capacity, device='disk', bus='virtio', format='qcow2', multipath_count=0): @@ -378,7 +380,9 @@ class Environment(DriverModel): role=config_node['role'], memory=int(node_params['memory']), vcpu=int(node_params['vcpu']), - boot=node_params['boot']) + boot=node_params['boot'], + enable_bootmenu=node_params.get('enable_bootmenu', True) + ) self.create_interfaces(node_params['interfaces'], node) diff --git a/devops/models/node.py b/devops/models/node.py index fcbaf772..e301781a 100644 --- a/devops/models/node.py +++ b/devops/models/node.py @@ -49,6 +49,7 @@ class Node(DriverModel): os_type = choices('hvm') architecture = choices('x86_64', 'i686') boot = models.CharField(max_length=255, null=False, default=json.dumps([])) + enable_bootmenu = models.BooleanField(null=False, default=True) metadata = models.CharField(max_length=255, null=True) role = models.CharField(max_length=255, null=True) vcpu = models.PositiveSmallIntegerField(null=False, default=1) @@ -98,8 +99,10 @@ class Node(DriverModel): :returns: Boolean """ - return (self.is_admin and self.disk_devices.filter(bus='usb')) or \ - (self.is_slave and not self.pxe_boot_interface_is_eth0) + return self.enable_bootmenu and ( + (self.is_admin and self.disk_devices.filter(bus='usb')) or + (self.is_slave and not self.pxe_boot_interface_is_eth0) + ) @property def on_second_admin_network(self): @@ -516,7 +519,8 @@ class Node(DriverModel): @classmethod def node_create(cls, name, environment=None, role=None, vcpu=1, memory=1024, has_vnc=True, metadata=None, hypervisor='kvm', - os_type='hvm', architecture='x86_64', boot=None): + os_type='hvm', architecture='x86_64', boot=None, + enable_bootmenu=True): """Create node :rtype : Node @@ -527,6 +531,7 @@ class Node(DriverModel): name=name, environment=environment, role=role, vcpu=vcpu, memory=memory, has_vnc=has_vnc, metadata=metadata, hypervisor=hypervisor, - os_type=os_type, architecture=architecture, boot=json.dumps(boot) + os_type=os_type, architecture=architecture, boot=json.dumps(boot), + enable_bootmenu=enable_bootmenu ) return node