Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
be17dc278c | ||
|
|
58b8d5b5de | ||
|
|
48f23b554f | ||
|
|
d32bb40cbd | ||
|
|
34954aa396 | ||
|
|
b9d728334f | ||
|
|
02d7c02a19 |
@@ -34,12 +34,13 @@ permissions:
|
||||
|
||||
You are a CI failure investigator for the grm repo.
|
||||
|
||||
## Working Directory
|
||||
## Working Directory & Virtual Environment
|
||||
|
||||
The grm repo is at `/home/emo/dev/ideas/oblachno/grm`. Always `cd` there first:
|
||||
```bash
|
||||
cd /home/emo/dev/ideas/oblachno/grm
|
||||
```
|
||||
The grm repo is at `/home/emo/dev/ideas/oblachno/grm`. Always `cd` there first.
|
||||
|
||||
All Python tools run inside `.venv`. `make` targets handle activation
|
||||
automatically — always use `make <target>`, never raw `pytest` or `ruff`
|
||||
commands. If `.venv` doesn't exist, run `make setup` first.
|
||||
|
||||
## CI Job Dependency Graph
|
||||
|
||||
|
||||
@@ -31,10 +31,14 @@ permissions:
|
||||
|
||||
You are a dependency upgrade specialist for the grm repo.
|
||||
|
||||
## Working Directory
|
||||
## Working Directory & Virtual Environment
|
||||
|
||||
The grm repo is at `/home/emo/dev/ideas/oblachno/grm`. Always `cd` there first.
|
||||
|
||||
All Python tools run inside `.venv`. `make` targets handle activation
|
||||
automatically — always use `make <target>`, never raw `pytest` or `ruff`
|
||||
commands. If `.venv` doesn't exist, run `make setup` first.
|
||||
|
||||
## Dependency Reference Locations
|
||||
|
||||
- **Python deps**: `pyproject.toml` — `[project] dependencies` and `[project.optional-dependencies]`
|
||||
@@ -88,8 +92,8 @@ pip install -e .[dev] # reinstall with new deps
|
||||
ansible-galaxy install -r ansible/requirements.yml # update collections
|
||||
make pytest-cov # 100% coverage
|
||||
make lint-all # ruff + pyright + bandit + ansible-lint + checkmake + actionlint
|
||||
python3 -m devx.tools.check_pyproject_deps
|
||||
python3 -m devx.tools.check_test_speed --max-seconds 4 --max-single-seconds 0.5
|
||||
.venv/bin/python -m devx.tools.check_pyproject_deps
|
||||
.venv/bin/python -m devx.tools.check_test_speed --max-seconds 4 --max-single-seconds 0.5
|
||||
```
|
||||
|
||||
If the dependency affects Ansible behavior, also run molecule:
|
||||
|
||||
@@ -25,10 +25,14 @@ permissions:
|
||||
|
||||
You are a documentation sync specialist for the grm repo.
|
||||
|
||||
## Working Directory
|
||||
## Working Directory & Virtual Environment
|
||||
|
||||
The grm repo is at `/home/emo/dev/ideas/oblachno/grm`. Always `cd` there first.
|
||||
|
||||
All Python tools run inside `.venv`. `make` targets handle activation
|
||||
automatically — always use `make <target>`, never raw `pytest` or `ruff`
|
||||
commands. If `.venv` doesn't exist, run `make setup` first.
|
||||
|
||||
## Documentation Structure
|
||||
|
||||
```
|
||||
@@ -54,14 +58,14 @@ docs/
|
||||
|
||||
### Step 1: Check documentation coverage
|
||||
```bash
|
||||
python3 -m devx.ci.doc_coverage --fail-on-missing
|
||||
.venv/bin/python -m devx.ci.doc_coverage --fail-on-missing
|
||||
```
|
||||
Fix undocumented CLI commands, modules, or CI scripts by adding entries
|
||||
to the appropriate docs file.
|
||||
|
||||
### Step 2: Lint documentation structure
|
||||
```bash
|
||||
python3 -m devx.ci.lint_docs --root .
|
||||
.venv/bin/python -m devx.ci.lint_docs --root .
|
||||
```
|
||||
Fix: broken internal links, heading hierarchy skips, TODO/FIXME markers,
|
||||
trailing whitespace.
|
||||
@@ -74,7 +78,7 @@ Update any references to files that were renamed or deleted.
|
||||
|
||||
### Step 4: Verify wiki sync (if investigating a sync failure)
|
||||
```bash
|
||||
python3 -m devx.ci.sync_wiki --repo oblachno-oss/grm --strict
|
||||
.venv/bin/python -m devx.ci.sync_wiki --repo oblachno-oss/grm --strict
|
||||
```
|
||||
Check `docs/mapping.json` — every docs file should have a mapping entry.
|
||||
If adding a new docs file, add it to mapping.json with a wiki-compatible
|
||||
|
||||
@@ -25,10 +25,14 @@ permissions:
|
||||
|
||||
You are a molecule test runner for the grm repo.
|
||||
|
||||
## Working Directory
|
||||
## Working Directory & Virtual Environment
|
||||
|
||||
The grm repo is at `/home/emo/dev/ideas/oblachno/grm`. Always `cd` there first.
|
||||
|
||||
All Python tools run inside `.venv`. `make` targets handle activation
|
||||
automatically — always use `make <target>`, never raw `pytest` or `ruff`
|
||||
commands. If `.venv` doesn't exist, run `make setup` first.
|
||||
|
||||
## Available Scenarios (7 total)
|
||||
|
||||
| Scenario | Purpose | Makefile target |
|
||||
|
||||
@@ -27,10 +27,14 @@ permissions:
|
||||
|
||||
You are a Gitea Actions workflow validator for the grm repo.
|
||||
|
||||
## Working Directory
|
||||
## Working Directory & Virtual Environment
|
||||
|
||||
The grm repo is at `/home/emo/dev/ideas/oblachno/grm`. Always `cd` there first.
|
||||
|
||||
All Python tools run inside `.venv`. `make` targets handle activation
|
||||
automatically — always use `make <target>`, never raw `pytest` or `ruff`
|
||||
commands. If `.venv` doesn't exist, run `make setup` first.
|
||||
|
||||
## Key Files
|
||||
|
||||
- `.gitea/workflows/ci.yml` — PR pipeline (quality, detect-changes, pre-merge-check, discover-runners, molecule-tests, molecule-report, release-dry-run, pr-review, auto-merge)
|
||||
|
||||
@@ -0,0 +1,71 @@
|
||||
# testing-and-debugging
|
||||
|
||||
Make targets for testing, debugging, and CI investigation. **Use these
|
||||
instead of raw `pytest`, `ruff`, or `molecule` commands.**
|
||||
|
||||
## Why Make Targets
|
||||
|
||||
Make targets encapsulate the correct venv activation, PYTHONPATH, env
|
||||
vars, and flags. Running raw commands bypasses venv activation and
|
||||
produces false failures (missing dependencies, wrong Python version).
|
||||
|
||||
## Unit Tests
|
||||
|
||||
| Task | Command | Notes |
|
||||
|------|---------|-------|
|
||||
| Run all unit tests | `make test-unit` | Fast, no coverage |
|
||||
| Run with coverage | `make pytest-cov` | **Required before push** — enforces 100% |
|
||||
| Run single test | `make pytest-cov TEST=tests/test_foo.py::test_bar` | |
|
||||
|
||||
## Linting
|
||||
|
||||
| Task | Command | Notes |
|
||||
|------|---------|-------|
|
||||
| Full lint | `make lint-all` | ruff + pyright + bandit + ansible-lint + checkmake + actionlint |
|
||||
| Ruff only | `make lint-ruff` | |
|
||||
| Type check | `make typecheck` | pyright |
|
||||
| Bandit | `make lint-bandit` | Security linter |
|
||||
| Workflow lint | `make workflow-check` | actionlint + act_runner dry-run |
|
||||
|
||||
## Molecule Tests
|
||||
|
||||
| Task | Command | Notes |
|
||||
|------|---------|-------|
|
||||
| All scenarios | `make molecule` | All 6 scenarios on Ubuntu 22.04 |
|
||||
| All platforms | `make molecule-all` | All 6 scenarios on all 4 OSes |
|
||||
| Parallel | `make molecule-all-parallel` | MOLECULE_JOBS=4 |
|
||||
|
||||
## Pre-Push Verification
|
||||
|
||||
**Before pushing any branch:**
|
||||
|
||||
```bash
|
||||
make pre-push
|
||||
```
|
||||
|
||||
This runs `lint-all` + `pytest-cov`. The pre-push git hook only
|
||||
validates the Vikunja task exists — it does NOT run tests. You must
|
||||
run `make pre-push` manually.
|
||||
|
||||
## CI Failure Investigation
|
||||
|
||||
When investigating a CI failure:
|
||||
|
||||
1. **Fetch logs via MCP** — use `mcp_call_tool` with gitea server,
|
||||
`actions_run_read` method, `download_job_log` tool
|
||||
2. **Reproduce locally** — use `make pytest-cov` or `make lint-ci`
|
||||
depending on which CI job failed
|
||||
3. **Never run raw pytest** — always use the make target
|
||||
|
||||
## Virtual Environment
|
||||
|
||||
All commands run inside `.venv`. `make` targets handle activation
|
||||
automatically. For raw commands (rare), activate first:
|
||||
|
||||
```bash
|
||||
source activate.sh # bash/zsh
|
||||
source activate.fish # fish
|
||||
source activate.zsh # zsh
|
||||
```
|
||||
|
||||
If `.venv` doesn't exist, run `make setup` first.
|
||||
@@ -1,5 +1,19 @@
|
||||
# AGENTS.md — Project Conventions for GRM
|
||||
|
||||
## Virtual Environment
|
||||
|
||||
All Python tools, tests, and scripts run inside a standard `.venv` directory.
|
||||
Activate it before running any non-`make` command:
|
||||
|
||||
```bash
|
||||
source activate.sh # bash/zsh
|
||||
source activate.fish # fish
|
||||
source activate.zsh # zsh
|
||||
```
|
||||
|
||||
If `.venv` doesn't exist, run `make setup` first. The `make` targets handle
|
||||
venv activation automatically — always prefer `make <target>` over raw commands.
|
||||
|
||||
## Build & Test Commands
|
||||
|
||||
```bash
|
||||
@@ -419,6 +433,33 @@ Change classification is config-driven via `[tool.devx.classify]` in `pyproject.
|
||||
- Secrets are passed via temp JSON files, never on the command line (CWE-214)
|
||||
- CI triggers only on `opened` and `synchronize` PR events (not `labeled`)
|
||||
|
||||
### Container-Level Fix Verification (Mandatory)
|
||||
|
||||
**Rule:** Before pushing any fix that modifies container state (CA certs,
|
||||
config files, installed packages, daemon restarts), reproduce the exact
|
||||
sequence locally with the actual Docker image. Do not push to CI as the
|
||||
first test.
|
||||
|
||||
This is a hard rule, not a suggestion. CI cycles take 20+ minutes and
|
||||
ephemeral staging VMs are destroyed after each run, making interactive
|
||||
debugging impossible. A local reproduction takes 30 seconds and catches
|
||||
silent failures immediately.
|
||||
|
||||
**Procedure:**
|
||||
1. `docker pull <actual_image>`
|
||||
2. `docker run -d --name <test> ...` and wait for it to start
|
||||
3. Run the exact commands from the Ansible task or script
|
||||
4. Verify the state change took effect
|
||||
5. Clean up: `docker rm -f <test>`
|
||||
|
||||
### Verified State Modification (Mandatory)
|
||||
|
||||
Ansible tasks that modify container state with `changed_when: false`
|
||||
MUST include a post-task verification step that confirms the state
|
||||
change took effect. `changed_when: false` suppresses both change
|
||||
detection AND failure visibility — a task can silently do nothing and
|
||||
report `ok`.
|
||||
|
||||
## Ansible Role Structure
|
||||
|
||||
```
|
||||
|
||||
@@ -2,6 +2,12 @@
|
||||
|
||||
All notable changes to this project will be documented in this file.
|
||||
|
||||
## [0.14.1] - 2026-07-01
|
||||
|
||||
### Refactor
|
||||
|
||||
- Align venv management to devx.mak targets
|
||||
|
||||
## [0.14.0] - 2026-07-01
|
||||
|
||||
### Features
|
||||
|
||||
@@ -25,6 +25,18 @@ DEVX_LINT_PATHS := src/ scripts/ tests/
|
||||
DEVX_MAK := $(shell $(BIN)/python -c \
|
||||
"from pathlib import Path; import devx; print(Path(devx.__file__).parent / 'make' / 'devx.mak')" \
|
||||
2>/dev/null)
|
||||
# Fallback: when the venv doesn't exist yet, try system python3 or /opt/venv.
|
||||
# In CI, /opt/venv has devx pre-installed; locally, devx may be in system python.
|
||||
ifeq ($(strip $(DEVX_MAK)),)
|
||||
DEVX_MAK := $(shell python3 -c \
|
||||
"from pathlib import Path; import devx; print(Path(devx.__file__).parent / 'make' / 'devx.mak')" \
|
||||
2>/dev/null)
|
||||
endif
|
||||
ifeq ($(strip $(DEVX_MAK)),)
|
||||
DEVX_MAK := $(shell /opt/venv/bin/python -c \
|
||||
"from pathlib import Path; import devx; print(Path(devx.__file__).parent / 'make' / 'devx.mak')" \
|
||||
2>/dev/null)
|
||||
endif
|
||||
-include $(DEVX_MAK)
|
||||
|
||||
# Full setup for local development (all deps, tools, collections, hooks)
|
||||
@@ -77,28 +89,14 @@ setup-image:
|
||||
pip install -e .$(if $(EXTRAS),[$(EXTRAS)],); \
|
||||
else echo "[setup-image] /opt/venv not found — falling back to setup-ci"; $(MAKE) setup-ci; fi
|
||||
|
||||
# Helper: run pip install with Gitea registry configured
|
||||
# Usage: $(PIP_INSTALL) install -e '.[ci,lint]'
|
||||
PIP_INSTALL := if [ -z "$$CI_GITEA_TOKEN" ]; then . ./.env 2>/dev/null; fi; \
|
||||
CI_GITEA_TOKEN="$$CI_GITEA_TOKEN"; \
|
||||
if [ -n "$$CI_GITEA_TOKEN" ]; then export PIP_EXTRA_INDEX_URL="https://$$CI_GITEA_USERNAME:$$CI_GITEA_TOKEN@git.oblachno.oblachno.fyi/api/packages/oblachno-oss/pypi/simple/"; fi; \
|
||||
$(BIN)/pip
|
||||
|
||||
$(VENV)/bin/activate:
|
||||
@python3 -c "import sys; v=sys.version_info; assert v >= (3, 12), f'Python 3.12+ required, found {v.major}.{v.minor}'; print(f'Python {v.major}.{v.minor}.{v.micro} OK')"
|
||||
$(PYTHON) -m venv $(VENV)
|
||||
$(BIN)/pip install --upgrade pip setuptools wheel
|
||||
|
||||
.env:
|
||||
@if [ ! -f .env ]; then \
|
||||
cp .env.example .env; \
|
||||
echo "Created .env from .env.example — please edit it with your credentials."; \
|
||||
fi
|
||||
|
||||
activate-scripts: $(VENV)/bin/activate
|
||||
@test -f activate.sh || (echo '#!/usr/bin/env bash' > activate.sh && echo 'source "$$(cd "$$(dirname "$${BASH_SOURCE[0]}")" && pwd)/.venv/bin/activate"' >> activate.sh && chmod +x activate.sh)
|
||||
@test -f activate.fish || (echo '#!/usr/bin/env fish' > activate.fish && echo 'set -l script_dir (dirname (status --current-filename))' >> activate.fish && echo 'source "$$script_dir/.venv/bin/activate.fish"' >> activate.fish && chmod +x activate.fish)
|
||||
@test -f activate.zsh || (echo '#!/usr/bin/env zsh' > activate.zsh && echo '0="$${ZERO:-$${0:#$$ZSH_ARGZERO}}"' >> activate.zsh && echo '0="$${$${(M)0:#/*}:-$$PWD/$$0}"' >> activate.zsh && echo 'source "$${0:A:h}/.venv/bin/activate"' >> activate.zsh && chmod +x activate.zsh)
|
||||
# venv, .env, activate-scripts, and PIP_INSTALL are provided by devx.mak
|
||||
# (devx-venv, devx-env, devx-activate-scripts, DEVX_PIP_INSTALL)
|
||||
# Aliases for convenience and backward compatibility:
|
||||
.PHONY: venv activate-scripts
|
||||
PIP_INSTALL := $(DEVX_PIP_INSTALL)
|
||||
venv: devx-venv
|
||||
.env: devx-env
|
||||
activate-scripts: devx-activate-scripts
|
||||
|
||||
install:
|
||||
@if [ -z "$(HOST)" ]; then echo "HOST is required. Example: make install HOST=192.168.1.10"; exit 1; fi
|
||||
|
||||
@@ -8,12 +8,12 @@ Each runner runs in an isolated **rootless Docker** environment under a dedicate
|
||||
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/src/branch/master/LICENSE)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/wiki)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/releases)
|
||||
[](https://www.python.org/downloads/)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/wiki)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/releases)
|
||||
[](https://www.python.org/downloads/)
|
||||
|
||||
## Why GRM?
|
||||
|
||||
|
||||
+6
-6
@@ -8,12 +8,12 @@ Each runner runs in an isolated **rootless Docker** environment under a dedicate
|
||||
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/src/branch/master/LICENSE)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/wiki)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/releases)
|
||||
[](https://www.python.org/downloads/)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/wiki)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/actions)
|
||||
[](https://git.oblachno.oblachno.fyi/oblachno-oss/grm/releases)
|
||||
[](https://www.python.org/downloads/)
|
||||
|
||||
## Overview
|
||||
|
||||
|
||||
+2
-2
@@ -34,7 +34,7 @@ ci = [
|
||||
"build==1.5.0",
|
||||
"twine==6.2.0",
|
||||
# Reusable CI/CD and dev tools (auto-merge, pr-review, pre-push checks, etc.)
|
||||
"devx==0.30.0",
|
||||
"devx==0.32.0",
|
||||
]
|
||||
# Lint and type-checking tools (quality job)
|
||||
lint = [
|
||||
@@ -54,7 +54,7 @@ molecule = [
|
||||
dev = [
|
||||
"gitea-runner-manager[ci,lint,molecule]",
|
||||
# Reusable CI/CD and dev tools (pre-push hooks, create-task, create-pr)
|
||||
"devx==0.30.0",
|
||||
"devx==0.32.0",
|
||||
# Non-Python dev dependency: checkmake (Makefile linter)
|
||||
# Install via: go install github.com/checkmake/checkmake/cmd/checkmake@latest
|
||||
]
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
"""Gitea Runner Manager — lean CLI for managing Gitea Actions runners."""
|
||||
|
||||
__version__ = "0.14.0"
|
||||
__version__ = "0.14.1"
|
||||
|
||||
Reference in New Issue
Block a user