clan.cli.inventory: init partial write
This commit is contained in:
@@ -119,6 +119,37 @@ def load_inventory_json(
|
||||
return inventory
|
||||
|
||||
|
||||
def patch(d: dict[str, Any], path: str, content: Any) -> None:
|
||||
"""
|
||||
Update the value at a specific dot-separated path in a nested dictionary.
|
||||
|
||||
:param d: The dictionary to update.
|
||||
:param path: The dot-separated path to the key (e.g., 'foo.bar').
|
||||
:param content: The new value to set.
|
||||
"""
|
||||
keys = path.split(".")
|
||||
current = d
|
||||
for key in keys[:-1]:
|
||||
current = current.setdefault(key, {})
|
||||
current[keys[-1]] = content
|
||||
|
||||
|
||||
@API.register
|
||||
def patch_inventory_with(base_dir: Path, section: str, content: dict[str, Any]) -> None:
|
||||
inventory_file = get_path(base_dir)
|
||||
|
||||
curr_inventory = {}
|
||||
with inventory_file.open("r") as f:
|
||||
curr_inventory = json.load(f)
|
||||
|
||||
patch(curr_inventory, section, content)
|
||||
|
||||
with inventory_file.open("w") as f:
|
||||
json.dump(curr_inventory, f, indent=2)
|
||||
|
||||
commit_file(inventory_file, base_dir, commit_message=f"inventory.{section}: Update")
|
||||
|
||||
|
||||
@API.register
|
||||
def set_inventory(
|
||||
inventory: Inventory | dict[str, Any], flake_dir: str | Path, message: str
|
||||
|
||||
36
pkgs/clan-cli/tests/test_patch_inventory.py
Normal file
36
pkgs/clan-cli/tests/test_patch_inventory.py
Normal file
@@ -0,0 +1,36 @@
|
||||
# Functions to test
|
||||
from clan_cli.inventory import patch
|
||||
|
||||
|
||||
def test_patch_nested() -> None:
|
||||
orig = {"a": 1, "b": {"a": 2.1, "b": 2.2}, "c": 3}
|
||||
|
||||
patch(orig, "b.b", "foo")
|
||||
|
||||
# Should only update the nested value
|
||||
assert orig == {"a": 1, "b": {"a": 2.1, "b": "foo"}, "c": 3}
|
||||
|
||||
|
||||
def test_patch_nested_dict() -> None:
|
||||
orig = {"a": 1, "b": {"a": 2.1, "b": 2.2}, "c": 3}
|
||||
|
||||
# This should update the whole "b" dict
|
||||
# Which also removes all other keys
|
||||
patch(orig, "b", {"b": "foo"})
|
||||
|
||||
# Should only update the nested value
|
||||
assert orig == {"a": 1, "b": {"b": "foo"}, "c": 3}
|
||||
|
||||
|
||||
def test_create_missing_paths() -> None:
|
||||
orig = {"a": 1}
|
||||
|
||||
patch(orig, "b.c", "foo")
|
||||
|
||||
# Should only update the nested value
|
||||
assert orig == {"a": 1, "b": {"c": "foo"}}
|
||||
|
||||
orig = {}
|
||||
patch(orig, "a.b.c", "foo")
|
||||
|
||||
assert orig == {"a": {"b": {"c": "foo"}}}
|
||||
Reference in New Issue
Block a user