From df9c37ad9335d8918c8d242da2ae9c55fb530fe9 Mon Sep 17 00:00:00 2001 From: Victor Date: Thu, 6 Aug 2026 20:13:02 -0300 Subject: [PATCH 1/3] Fix examples/config-sample.json to match the current config format The sample config has not been valid since the 2023 disk layout rework and currently fails to parse, so the file the README points users at cannot be used: - sector_size was null, but SectorSize became a required object - partitions were missing the dev_path key, which the parser reads - the /home size used the Percent unit, which no longer exists - /home started at 20 GiB while / ended at 20993 MiB, overlapping it - gfx_driver kept the old "All open-source (default)" value Sizes and keys now mirror what the installer itself writes when saving a configuration. --- examples/config-sample.json | 43 +++++++++++++++++++++++++++---------- 1 file changed, 32 insertions(+), 11 deletions(-) diff --git a/examples/config-sample.json b/examples/config-sample.json index ac366b6c9f..be2769ce58 100644 --- a/examples/config-sample.json +++ b/examples/config-sample.json @@ -17,12 +17,16 @@ "partitions": [ { "btrfs": [], + "dev_path": null, "flags": [ "boot" ], "fs_type": "fat32", "size": { - "sector_size": null, + "sector_size": { + "unit": "B", + "value": 512 + }, "unit": "MiB", "value": 512 }, @@ -30,7 +34,10 @@ "mountpoint": "/boot", "obj_id": "2c3fa2d5-2c79-4fab-86ec-22d0ea1543c0", "start": { - "sector_size": null, + "sector_size": { + "unit": "B", + "value": 512 + }, "unit": "MiB", "value": 1 }, @@ -39,10 +46,14 @@ }, { "btrfs": [], + "dev_path": null, "flags": [], "fs_type": "ext4", "size": { - "sector_size": null, + "sector_size": { + "unit": "B", + "value": 512 + }, "unit": "GiB", "value": 20 }, @@ -50,7 +61,10 @@ "mountpoint": "/", "obj_id": "3e7018a0-363b-4d05-ab83-8e82d13db208", "start": { - "sector_size": null, + "sector_size": { + "unit": "B", + "value": 512 + }, "unit": "MiB", "value": 513 }, @@ -59,20 +73,27 @@ }, { "btrfs": [], + "dev_path": null, "flags": [], "fs_type": "ext4", "size": { - "sector_size": null, - "unit": "Percent", - "value": 100 + "sector_size": { + "unit": "B", + "value": 512 + }, + "unit": "GiB", + "value": 10 }, "mount_options": [], "mountpoint": "/home", "obj_id": "ce58b139-f041-4a06-94da-1f8bad775d3f", "start": { - "sector_size": null, - "unit": "GiB", - "value": 20 + "sector_size": { + "unit": "B", + "value": 512 + }, + "unit": "MiB", + "value": 20993 }, "status": "create", "type": "primary" @@ -138,7 +159,7 @@ "parallel_downloads": 5 }, "profile_config": { - "gfx_driver": "All open-source (default)", + "gfx_driver": "All open-source", "greeter": "sddm", "profile": { "details": [ From ed47743186c47d6c846b31737cbabdde656ec6da Mon Sep 17 00:00:00 2001 From: Victor Date: Thu, 6 Aug 2026 20:25:22 -0300 Subject: [PATCH 2/3] Cover the example configs with a parsing test Nothing in the test suite or CI reads examples/, which is how the sample config could stay broken for years while every other config surface kept working. Parse both example files through ArchConfigHandler, and check the partition entries directly since the parser only reaches them when the configured device exists on the machine, which is never true in CI. --- tests/conftest.py | 10 ++++++++++ tests/test_args.py | 50 +++++++++++++++++++++++++++++++++++++++++++++- 2 files changed, 59 insertions(+), 1 deletion(-) diff --git a/tests/conftest.py b/tests/conftest.py index 819c839716..d3f2bc7e34 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -8,6 +8,16 @@ def config_fixture() -> Path: return Path(__file__).parent / 'data' / 'test_config.json' +@pytest.fixture(scope='session') +def example_config_fixture() -> Path: + return Path(__file__).parent.parent / 'examples' / 'config-sample.json' + + +@pytest.fixture(scope='session') +def example_creds_fixture() -> Path: + return Path(__file__).parent.parent / 'examples' / 'creds-sample.json' + + @pytest.fixture(scope='session') def btrfs_config_fixture() -> Path: return Path(__file__).parent / 'data' / 'test_config_btrfs.json' diff --git a/tests/test_args.py b/tests/test_args.py index 324f5a1173..100d104451 100644 --- a/tests/test_args.py +++ b/tests/test_args.py @@ -1,3 +1,4 @@ +import json import os from importlib.metadata import version from pathlib import Path @@ -17,7 +18,7 @@ ) from archinstall.lib.models.authentication import AuthenticationConfiguration, U2FLoginConfiguration, U2FLoginMethod from archinstall.lib.models.bootloader import Bootloader, BootloaderConfiguration -from archinstall.lib.models.device import DiskLayoutConfiguration, DiskLayoutType +from archinstall.lib.models.device import DiskLayoutConfiguration, DiskLayoutType, Size from archinstall.lib.models.locale import LocaleConfiguration from archinstall.lib.models.mirrors import CustomRepository, CustomServer, MirrorConfiguration, MirrorRegion, SignCheck, SignOption from archinstall.lib.models.network import NetworkConfiguration, Nic, NicType @@ -388,3 +389,50 @@ def test_encrypted_creds_with_env_var( groups=[], ), ] + + +def test_example_config_parsing( + monkeypatch: MonkeyPatch, + example_config_fixture: Path, + example_creds_fixture: Path, +) -> None: + monkeypatch.setattr( + 'sys.argv', + [ + 'archinstall', + '--config', + str(example_config_fixture), + '--creds', + str(example_creds_fixture), + ], + ) + + handler = ArchConfigHandler() + arch_config = handler.config + + assert arch_config.disk_config is not None + assert arch_config.profile_config is not None + assert arch_config.auth_config is not None + assert arch_config.auth_config.users + + +def test_example_config_partitions(example_config_fixture: Path) -> None: + # partition entries are only parsed when the configured device is present on + # the machine, which is never the case in CI, so read them here directly + config = json.loads(example_config_fixture.read_text()) + + for device in config['disk_config']['device_modifications']: + previous_end = None + + for partition in device['partitions']: + assert 'dev_path' in partition + + start = Size.parse_args(partition['start']) + end = start + Size.parse_args(partition['size']) + + assert start.is_valid_start() + + if previous_end is not None: + assert start >= previous_end + + previous_end = end From bcc3d18a0a857abc4877a90ffe472102d9f3dbf0 Mon Sep 17 00:00:00 2001 From: Victor Date: Wed, 12 Aug 2026 00:48:20 -0300 Subject: [PATCH 3/3] Fail the partition test when the example config has none The loops in test_example_config_partitions would not execute if device_modifications or a device's partitions were empty, so the test could pass while checking nothing. --- tests/test_args.py | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/tests/test_args.py b/tests/test_args.py index 100d104451..685c01ff13 100644 --- a/tests/test_args.py +++ b/tests/test_args.py @@ -420,11 +420,18 @@ def test_example_config_partitions(example_config_fixture: Path) -> None: # partition entries are only parsed when the configured device is present on # the machine, which is never the case in CI, so read them here directly config = json.loads(example_config_fixture.read_text()) + device_modifications = config['disk_config']['device_modifications'] + + assert device_modifications + + for device in device_modifications: + partitions = device['partitions'] + + assert partitions - for device in config['disk_config']['device_modifications']: previous_end = None - for partition in device['partitions']: + for partition in partitions: assert 'dev_path' in partition start = Size.parse_args(partition['start'])