feat: add regenerate command to force rebuild of specific targets

The regenerate command accepts one or more target names and forces them
to be rebuilt even if they are up to date. This respects the
archive_folder setting, archiving previous versions before overwriting.
This commit is contained in:
Konstantin Fickel 2026-02-21 11:46:07 +01:00
parent 612ea0ae9d
commit d76951fe47
Signed by: kfickel
GPG key ID: A793722F9933C1A5
3 changed files with 124 additions and 3 deletions

View file

@ -136,6 +136,59 @@ class TestBuildCommand:
assert call_args[0][3] == "output.txt"
class TestRegenerateCommand:
"""Test the regenerate CLI command."""
def test_regenerate_forces_rebuild(self, cli_project: Path) -> None:
build_result = BuildResult(
built=["output.txt"], skipped=["image.png"], failed={}
)
with (
patch("hokusai.cli.Path") as mock_path_cls,
patch(
"hokusai.cli.run_build",
new_callable=AsyncMock,
return_value=build_result,
) as mock_run,
):
mock_path_cls.cwd.return_value = cli_project
result = runner.invoke(app, ["regenerate", "output.txt"])
assert result.exit_code == 0
assert "1 regenerated" in result.output
# Check force_dirty was passed
call_kwargs = mock_run.call_args[1]
assert call_kwargs["force_dirty"] == {"output.txt"}
def test_regenerate_multiple_targets(self, cli_project: Path) -> None:
build_result = BuildResult(
built=["output.txt", "image.png"], skipped=[], failed={}
)
with (
patch("hokusai.cli.Path") as mock_path_cls,
patch(
"hokusai.cli.run_build",
new_callable=AsyncMock,
return_value=build_result,
) as mock_run,
):
mock_path_cls.cwd.return_value = cli_project
result = runner.invoke(app, ["regenerate", "output.txt", "image.png"])
assert result.exit_code == 0
assert "2 regenerated" in result.output
call_kwargs = mock_run.call_args[1]
assert call_kwargs["force_dirty"] == {"output.txt", "image.png"}
def test_regenerate_unknown_target(self, cli_project: Path) -> None:
with patch("hokusai.cli.Path") as mock_path_cls:
mock_path_cls.cwd.return_value = cli_project
result = runner.invoke(app, ["regenerate", "nonexistent.txt"])
assert result.exit_code == 1
assert "Unknown target(s): nonexistent.txt" in result.output
class TestCleanCommand:
"""Test the clean CLI command."""