autoinstall: Allow "autoinstall" as top-level key
This commit is contained in:
parent
a25f2e03c1
commit
ba3dbb52ef
|
@ -673,9 +673,28 @@ class SubiquityServer(Application):
|
|||
with open(cfg_path) as fp:
|
||||
config: dict[str, Any] = yaml.safe_load(fp)
|
||||
|
||||
autoinstall_config: dict[str, Any] = dict()
|
||||
autoinstall_config: dict[str, Any]
|
||||
|
||||
autoinstall_config = config
|
||||
# Support "autoinstall" as a top-level key
|
||||
if "autoinstall" in config:
|
||||
autoinstall_config = config.pop("autoinstall")
|
||||
|
||||
# but the only top level key
|
||||
if len(config) != 0:
|
||||
self.interactive = bool(autoinstall_config.get("interactive-sections"))
|
||||
msg: str = (
|
||||
"autoinstall.yaml is not a valid cloud config datasource.\n"
|
||||
"No other keys may be present alongside 'autoinstall' at "
|
||||
"the top level."
|
||||
)
|
||||
context.error(msg)
|
||||
raise AutoinstallValidationError(
|
||||
owner="top-level keys",
|
||||
details="autoinstall.yaml is not a valid cloud config datasource",
|
||||
)
|
||||
|
||||
else:
|
||||
autoinstall_config = config
|
||||
|
||||
return autoinstall_config
|
||||
|
||||
|
|
|
@ -20,6 +20,7 @@ from typing import Any
|
|||
from unittest.mock import AsyncMock, Mock, patch
|
||||
|
||||
import jsonschema
|
||||
import yaml
|
||||
from jsonschema.validators import validator_for
|
||||
|
||||
from subiquity.cloudinit import CloudInitSchemaValidationError
|
||||
|
@ -156,6 +157,7 @@ early-commands: ["{cmd}"]
|
|||
|
||||
class TestAutoinstallValidation(SubiTestCase):
|
||||
async def asyncSetUp(self):
|
||||
self.tempdir = self.tmp_dir()
|
||||
opts = Mock()
|
||||
opts.dry_run = True
|
||||
opts.output_base = self.tmp_dir()
|
||||
|
@ -171,6 +173,15 @@ class TestAutoinstallValidation(SubiTestCase):
|
|||
}
|
||||
self.server.make_apport_report = Mock()
|
||||
|
||||
def path(self, relative_path):
|
||||
return self.tmp_path(relative_path, dir=self.tempdir)
|
||||
|
||||
def create(self, path, contents):
|
||||
path = self.path(path)
|
||||
with open(path, "w") as fp:
|
||||
fp.write(contents)
|
||||
return path
|
||||
|
||||
# Pseudo Load Controllers to avoid patching the loading logic for each
|
||||
# controller when we still want access to class attributes
|
||||
def pseudo_load_controllers(self):
|
||||
|
@ -445,6 +456,44 @@ class TestAutoinstallValidation(SubiTestCase):
|
|||
|
||||
self.assertEqual(cfg, expected)
|
||||
|
||||
async def test_autoinstall_validation__top_level_autoinstall(self):
|
||||
"""Test allow autoinstall as top-level key"""
|
||||
|
||||
new_style = {
|
||||
"autoinstall": {
|
||||
"version": 1,
|
||||
"interactive-sections": ["identity"],
|
||||
"apt": "...",
|
||||
}
|
||||
}
|
||||
old_style = new_style["autoinstall"]
|
||||
|
||||
# Read new style correctly
|
||||
path = self.create("autoinstall.yaml", yaml.dump(new_style))
|
||||
self.assertEqual(self.server._read_config(cfg_path=path), old_style)
|
||||
|
||||
# No changes to old style
|
||||
path = self.create("autoinstall.yaml", yaml.dump(old_style))
|
||||
self.assertEqual(self.server._read_config(cfg_path=path), old_style)
|
||||
|
||||
async def test_autoinstall_validation__not_cloudinit_datasource(self):
|
||||
"""Test no cloud init datasources in new style autoinstall"""
|
||||
|
||||
new_style = {
|
||||
"autoinstall": {
|
||||
"version": 1,
|
||||
"interactive-sections": ["identity"],
|
||||
"apt": "...",
|
||||
},
|
||||
"cloudinit-data": "I am data",
|
||||
}
|
||||
|
||||
with self.assertRaises(AutoinstallValidationError) as ctx:
|
||||
path = self.create("autoinstall.yaml", yaml.dump(new_style))
|
||||
self.server._read_config(cfg_path=path)
|
||||
|
||||
self.assertEqual("top-level keys", ctx.exception.owner)
|
||||
|
||||
|
||||
class TestMetaController(SubiTestCase):
|
||||
async def test_interactive_sections_not_present(self):
|
||||
|
|
Loading…
Reference in New Issue