Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
ee1c269
ci(orchestrator): migrate ephemeral CI runners from OpenStack to NVID…
pvkumara5 Jul 27, 2026
88d8c59
ci(orchestrator): pin AirLab OSMO JSON keys and runner image path
pvkumara5 Jul 29, 2026
165d011
docs(ci): document the OSMO-backed CI/CD pipeline
pvkumara5 Aug 7, 2026
f56810d
fix(ci): repair Docker builds on OSMO ephemeral runners
pvkumara5 Aug 7, 2026
4583165
fix(ci): seed PR Docker builds from a floating cache tag
pvkumara5 Aug 7, 2026
5550b76
ci(docker-build): retag unchanged images on VERSION bump
pvkumara5 Aug 7, 2026
b093327
fix(ci): parse quoted .env values before inline comments
pvkumara5 Aug 7, 2026
56a60c7
ci(docker-build): build/push services sequentially
pvkumara5 Aug 8, 2026
624dec7
chore: bump VERSION to 0.19.0-alpha.8 for retag validation
pvkumara5 Aug 8, 2026
d18efe9
fix(ci): unblock isaac-sim PX4 apt and robot colcon pytest
pvkumara5 Aug 11, 2026
81f7910
fix(ci): pass colcon --pytest-args as separate tokens
pvkumara5 Aug 11, 2026
959380d
fix(ci): quote colcon pytest args through bash -ic
pvkumara5 Aug 12, 2026
9667722
fix(ci): pass colcon pytest flags via PYTEST_ADDOPTS
pvkumara5 Aug 12, 2026
8acd7a5
fix(ci): rename helper so pytest does not treat it as a hook
pvkumara5 Aug 12, 2026
241d86a
ci: skip image-build for build_packages reruns
pvkumara5 Aug 12, 2026
865eb0d
fix(ci): disable pytest plugin autoload for colcon tests
pvkumara5 Aug 12, 2026
40f526f
fix(ci): skip lidar ament linters in package pytest config
pvkumara5 Aug 13, 2026
f937b50
ci: default system tests to isaacsim only
pvkumara5 Aug 14, 2026
95a8d87
Merge origin/develop into ci/osmo-orchestrator
pvkumara5 Aug 14, 2026
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
12 changes: 7 additions & 5 deletions .agents/skills/bump-version-and-release/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -64,19 +64,21 @@ Three workflows in `.github/workflows/` interact with `VERSION`:
- **Trigger:** push to `main` or `develop` whose changed paths include `.env`, **and** the `VERSION=` line in `.env` differs from the previous commit. Also runs on manual `workflow_dispatch`.
- **Behavior on tag change:**
1. Runs on a self-hosted ephemeral GPU runner (`[self-hosted, airstack-ephemeral]`).
2. `docker compose build` for profiles `desktop,isaac-sim,ms-airsim`.
3. `docker compose push` to `${PROJECT_DOCKER_REGISTRY}` (set in `.env` — currently `airlab-docker.andrew.cmu.edu/airstack`).
4. Keyless `cosign sign` of every pushed image digest via GitHub OIDC.
5. `cosign verify` against the workflow's certificate identity.
2. Plans per service via `.github/workflows/scripts/docker_image_plan.py` (content fingerprint vs previous versioned image label).
3. **Unchanged image inputs** → registry retag of the previous `v${PREV}_…` digest to `v${VERSION}_…` and `cache_*` (no rebuild).
4. **Changed inputs** (or missing/unlabeled previous image, or `force_rebuild=true`) → `docker compose build` / `push` for those services only, labeling the new digest with `org.airstack.content-fingerprint`.
5. Keyless `cosign sign` of every published image digest via GitHub OIDC.
6. `cosign verify` against the workflow's certificate identity.
- **Skip behavior:** if the merge commit on `main`/`develop` does not actually change `VERSION=`, the build job is skipped (the check-changes job sets `tag-changed=false`).
- **Docs-only VERSION bumps:** still required by `check-version-increment`, but publish should retag rather than rebuild once fingerprints are on the previous images. First publish after this feature lands (or `force_rebuild=true`) must rebuild to write the labels.

### 3. `deploy_docs_from_release.yaml` — versioned docs

- **Trigger:** GitHub `release` event with `types: [published]`.
- **Behavior:** runs `mike deploy --push --update-aliases <release.tag_name> latest`, publishing the docs site under the release tag and pointing the `latest` alias at it.
- Companion workflows publish unversioned docs from `main` (default alias `main`) and `develop` (alias `develop`).

So the full release path is: bump `VERSION` → PR → merge to `main`/`develop` (rebuild + push + sign) → cut a GitHub Release matching that VERSION (versioned docs go live).
So the full release path is: bump `VERSION` → PR → merge to `main`/`develop` (retag unchanged images and/or rebuild changed ones + push + sign) → cut a GitHub Release matching that VERSION (versioned docs go live).

## Choosing the Bump Type

Expand Down
5 changes: 3 additions & 2 deletions .agents/skills/run-system-tests/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,7 @@ The `system-tests.yml` workflow's `Parse pytest args` step automatically prepend
- `/pytest -m takeoff_hover_land` → effectively runs `-m "build_packages or takeoff_hover_land"`
- `/pytest` (no marks) → pytest defaults (everything)
- `/pytest -m build_docker` → unchanged (the build_docker tests rebuild from scratch anyway)
- `/pytest -m build_packages` → **pull-only** (retag `cache_*`, no `image-build`, no Isaac). Add `--no-image-build` on other marks to skip the bake.

This guarantees that ROS 2 workspaces are built inside the containers before any launch/liveliness test tries to source them. If you intentionally want to skip `build_packages` (e.g. you trust the prebuilt images), include it explicitly: `-m "liveliness and not build_packages"` would work, but the simpler path is to run locally where the prepend logic doesn't apply.

Expand Down Expand Up @@ -157,7 +158,7 @@ The `airstack_env` fixture is parametrized over `(sim, num_robots, iteration)` t

| Flag | Default | Affects | Becomes |
|------|---------|---------|---------|
| `--sim` | `msairsim,isaacsim` | `airstack_env` | One env-tuple per sim |
| `--sim` | `isaacsim` | `airstack_env` | One env-tuple per sim (`msairsim` opt-in) |
| `--num-robots` | `1,3` | `airstack_env` | Cross-product with sim |
| `--stress-iterations` | `1` | `airstack_env` | Up/down cycles per `(sim, num_robots)` |
| `--stable-duration` | `120` | `system.test_liveliness::test_stable` and `system.test_sensors::test_sensor_streams_stable` | Total seconds polled |
Expand Down Expand Up @@ -356,7 +357,7 @@ If multiple tests need the same setup, add a fixture in `conftest.py` (not in yo
- **Running on insufficient hardware**. `liveliness`, `sensors`, and `takeoff_hover_land` require an NVIDIA GPU plus nvidia-container-toolkit; without them the sim container won't get GPU access and topic Hz checks will time out. If you only have a CPU, scope to `-m "build_docker or build_packages"`.
- **Expecting interactive sim feedback**. `airstack_env` runs headless by default (`MS_AIRSIM_HEADLESS=true`, `ISAAC_SIM_HEADLESS=true`, `QT_QPA_PLATFORM=offscreen`). Don't add stdin prompts, GUI dialogs, or `input()` calls to test code — they will hang in CI. For local visual debugging only, pass `--gui`.
- **Not capturing metrics in a new test**. If a test fails silently (no metric recorded) the regression report has nothing to compare. Always record at least one scalar via `MetricsRecorder` so the test shows up in `metrics.json`.
- **Letting parametrize cardinality explode**. Defaults `--sim msairsim,isaacsim --num-robots 1,3` with `--stress-iterations 3` multiply stack bring-ups for each selected mark (`liveliness`, `sensors`, `takeoff_hover_land`, …) — expensive. Override locally to a single tuple while iterating.
- **Letting parametrize cardinality explode**. Default `--num-robots 1,3` (and `--sim msairsim` if you opt in) multiplies stack bring-ups for each selected mark (`liveliness`, `sensors`, `takeoff_hover_land`, …) — expensive. Override locally to a single tuple while iterating. `--sim` defaults to `isaacsim` only.
- **Hardcoded container names**. Always use `find_container`, `get_robot_containers`, or `wait_for_container` — replica suffixes (`-1`, `-2`, `-3`) and compose project prefixes change.
- **Asserting on stdout instead of using `read_log_tail`**. The conftest captures each subprocess's combined stdout/stderr in memory; assertions should reference it via `read_log_tail()` (`f"airstack up failed:\n{read_log_tail()}"`) so failures attach the relevant context to the JUnit XML.
- **Trying to SSH into a CI runner mid-job**. Workers are ephemeral OpenStack VMs destroyed within ~30s of job completion. Re-running the job creates a fresh VM. For genuine debugging on the runner, see `.github/orchestrator/README.md` (also exposed at `tests/ci-cd-orchestrator.md`) — but in 99% of cases, reproduce locally with `airstack test`.
Expand Down
2 changes: 1 addition & 1 deletion .env
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ PROJECT_NAME="airstack"
# If you've run ./airstack.sh setup, then this will auto-generate from the git commit hash every time a change is made
# to a Dockerfile or docker-compose.yaml file. Otherwise this can also be set explicitly to make a release version.
# auto-generated from git commit hash
VERSION="0.19.0-alpha.12"
VERSION="0.19.0-alpha.13"
# Choose "dev" or "prebuilt". "dev" is for mounted code that must be built live. "prebuilt" is for built ros_ws baked into the image
DOCKER_IMAGE_BUILD_MODE="dev"
# Where to push and pull images from. Can replace with your docker hub username if using docker hub.
Expand Down
Loading
Loading