Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 9 additions & 2 deletions scripts/pull-all.sh
Original file line number Diff line number Diff line change
Expand Up @@ -185,6 +185,7 @@ wait
# Aggregate results
OK=0
FAILED=()
WARNED=()

for repo in "${REPOS[@]}"; do
result_file="$RESULTS_DIR/$repo"
Expand All @@ -193,7 +194,7 @@ for repo in "${REPOS[@]}"; do
case "$status" in
OK) (( OK++ )) || true ;;
FAILED) FAILED+=("$repo") ;;
MISSING) FAILED+=("$repo (missing)") ;;
MISSING) WARNED+=("$repo (not cloned — skipped)") ;;
# SKIPPED — don't count
esac
fi
Expand Down Expand Up @@ -284,5 +285,11 @@ fi
# === End plugin cache refresh ===

echo ""
echo "${OK} repo(s) up to date. ${#FAILED[@]} failed."
if [[ ${#WARNED[@]} -gt 0 ]]; then
echo "WARN: ${#WARNED[@]} repo(s) not found locally and were skipped:"
for w in "${WARNED[@]}"; do
echo " WARN $w"
done
fi
echo "${OK} repo(s) up to date. ${#FAILED[@]} failed. ${#WARNED[@]} absent (skipped)."
[[ ${#FAILED[@]} -eq 0 ]] || exit 1
55 changes: 51 additions & 4 deletions tests/unit/scripts/test_pull_all.py
Original file line number Diff line number Diff line change
Expand Up @@ -244,8 +244,8 @@ def test_script_refuses_dirty_repo_before_branch_switch(
).strip()
assert current_branch == "main"

def test_script_handles_missing_repo(self) -> None:
"""Run pull-all.sh with a nonexistent repo name against a temp dir."""
def test_missing_repo_warns_and_exits_zero(self) -> None:
"""Absent repo emits a WARN line and exits 0 (OMN-13055)."""
with tempfile.TemporaryDirectory() as tmpdir:
result = subprocess.run(
["bash", str(PULL_ALL), "nonexistent_repo_xyz"],
Expand All @@ -254,8 +254,55 @@ def test_script_handles_missing_repo(self) -> None:
env={**os.environ, "OMNI_HOME": tmpdir},
check=False,
)
assert result.returncode != 0
assert "MISSING" in result.stdout
assert result.returncode == 0, (
f"Expected exit 0 for absent repo; got {result.returncode}. "
f"stdout={result.stdout!r} stderr={result.stderr!r}"
)
assert "MISSING" in result.stdout or "not cloned" in result.stdout, (
f"Expected warning about absent repo; stdout={result.stdout!r}"
)

def test_missing_repo_mixed_with_present_exits_zero(self, tmp_path: Path) -> None:
"""One absent + one OK repo: exit 0, absent repo warned (OMN-13055)."""
omni_home = tmp_path / "omni_home"
omni_home.mkdir()
fake_home = tmp_path / "home"
fake_home.mkdir()

_make_omniclaude_source(omni_home)

result = _run_pull_all(
omni_home, fake_home, repos=["omniclaude", "nonexistent_xyz"]
)
assert result.returncode == 0, (
f"Expected exit 0 when present repos all OK; "
f"stdout={result.stdout!r} stderr={result.stderr!r}"
)
assert "MISSING" in result.stdout or "not cloned" in result.stdout, (
f"Expected warning for absent repo; stdout={result.stdout!r}"
)
# The present repo must have been processed successfully.
assert "OK" in result.stdout, (
f"Expected OK for omniclaude; stdout={result.stdout!r}"
)

def test_failed_present_repo_still_exits_nonzero(self, tmp_path: Path) -> None:
"""When a present repo fails (dirty), exit 1 even if other repos are absent."""
omni_home = tmp_path / "omni_home"
omni_home.mkdir()
fake_home = tmp_path / "home"
fake_home.mkdir()

omniclaude = _make_omniclaude_source(omni_home)
# Make omniclaude dirty so it fails.
(omniclaude / "dirty.txt").write_text("uncommitted\n")

result = _run_pull_all(omni_home, fake_home, repos=["omniclaude", "absent_xyz"])
assert result.returncode != 0, (
f"Expected non-zero exit when a present repo fails; "
f"stdout={result.stdout!r} stderr={result.stderr!r}"
)
assert "dirty worktree" in result.stdout

def test_script_handles_bare_repo_no_crash(self) -> None:
"""Create a bare git repo and verify pull-all.sh does not crash."""
Expand Down
Loading