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
3 changes: 3 additions & 0 deletions .github/PULL_REQUEST_TEMPLATE.md
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,9 @@ To upload images to a PR -- simply drag and drop an image while in edit mode and

## Checklist

Docker and GPU tests run on demand. Push the commits you want tested, then
comment `run-ci` on the pull request.

- [ ] I have read and understood the [contribution guidelines](https://isaac-sim.github.io/IsaacLab/main/source/refs/contributing.html)
- [ ] I have run the [`pre-commit` checks](https://pre-commit.com/) with `./isaaclab.sh --format`
- [ ] I have made corresponding changes to the documentation
Expand Down
2 changes: 1 addition & 1 deletion .github/scripts/resolve_backport_conflicts.py
Original file line number Diff line number Diff line change
Expand Up @@ -203,7 +203,7 @@ def _completion_payload(model: str, context: dict[str, Any]) -> dict[str, Any]:

Return a complete final UTF-8 file body for every required write action. Return empty content for every required delete
action. Use exactly the paths and required actions supplied. Do not add cleanup or changes unrelated to the source
commit.
commit. The final files must pass the repository's pre-commit hooks.

Return only one JSON object without Markdown. It must satisfy this JSON Schema exactly:
{json.dumps(schema, ensure_ascii=False, separators=(",", ":"))}"""
Expand Down
34 changes: 34 additions & 0 deletions .github/workflows/backport-release-3.0.yml
Original file line number Diff line number Diff line change
Expand Up @@ -245,6 +245,40 @@ jobs:
--model "$primary_model" \
--model "$fallback_model"

- name: Set up Python for inferred-resolution checks
if: steps.cherry_pick.outputs.conflict == 'true'
uses: actions/setup-python@a26af69be951a213d495a4c3e4e4022e16d87065 # v5
with:
python-version: "3.12"

- name: Run pre-commit on inferred resolution
if: steps.cherry_pick.outputs.conflict == 'true'
working-directory: repository
env:
SKIP: check-changelog-fragments
SOURCE_PARENT: ${{ steps.source.outputs.source_parent }}
SOURCE_SHA: ${{ github.event.pull_request.merge_commit_sha }}
TARGET_SHA: ${{ steps.source.outputs.target_sha }}
run: |
set -euo pipefail
python -m pip install pre-commit==4.6.2

set +e
pre-commit run --show-diff-on-failure --color=always --all-files
pre_commit_status=$?
set -e

if [ "$pre_commit_status" -ne 0 ]; then
while IFS= read -r -d '' path; do
git add --all -- "$path"
done < <(git diff --no-renames --name-only -z "$SOURCE_PARENT" "$SOURCE_SHA" --)
python3 ../automation/.github/scripts/backport.py validate-candidate \
--source_parent "$SOURCE_PARENT" \
--source "$SOURCE_SHA" \
--target "$TARGET_SHA"
pre-commit run --show-diff-on-failure --color=always --all-files
fi

- name: Validate and commit inferred resolution
if: steps.cherry_pick.outputs.conflict == 'true'
working-directory: repository
Expand Down
13 changes: 10 additions & 3 deletions .github/workflows/build.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,14 @@
# SPDX-License-Identifier: BSD-3-Clause

# region help
# Every test job runs on every PR.
# Docker builds and their dependent tests run only on a labeled PR event or a
# manual workflow dispatch. Do not filter the label with a job-level ``if``:
# GitHub treats skipped required jobs as successful status checks.
#
# GitHub cannot filter label names at trigger time, so adding any label to a PR
# starts this workflow. Only a ``ci:run-docker`` event cancels an in-flight run;
# other label events queue behind it so that a triage label cannot cancel a
# build whose required checks have already been reported.
#
# =============================================================================
# CI DEBUGGING TIPS
Expand Down Expand Up @@ -47,7 +54,7 @@ name: Docker + Tests

on:
pull_request:
types: [opened, synchronize, reopened]
types: [labeled]
branches:
- main
- develop
Expand All @@ -57,7 +64,7 @@ on:
# Concurrency control to prevent parallel runs on the same PR
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
cancel-in-progress: ${{ github.event.label.name == 'ci:run-docker' }}

permissions:
contents: read
Expand Down
107 changes: 107 additions & 0 deletions .github/workflows/run-docker-ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
# Copyright (c) 2022-2026, The Isaac Lab Project Developers (https://github.com/isaac-sim/IsaacLab/blob/main/CONTRIBUTORS.md).
# All rights reserved.
#
# SPDX-License-Identifier: BSD-3-Clause

name: Run Docker CI Command
run-name: Run Docker CI for PR #${{ github.event.issue.number }}

on:
# GitHub always runs ``issue_comment`` workflows from the repository default
# branch, so this file has to land there for the ``run-ci`` command to work.
issue_comment:
types: [created]

permissions:
contents: read
pull-requests: read

concurrency:
group: run-docker-ci-${{ github.event.issue.number }}
cancel-in-progress: false

jobs:
request-docker-ci:
name: Request Docker CI
if: >-
github.event.issue.pull_request &&
github.event.comment.body == 'run-ci'
runs-on: ubuntu-latest
timeout-minutes: 5
steps:
- name: Authorize the request
id: authorize
env:
COMMENT_AUTHOR: ${{ github.event.comment.user.login }}
GH_TOKEN: ${{ github.token }}
PR_NUMBER: ${{ github.event.issue.number }}
REPOSITORY: ${{ github.repository }}
run: |
set -euo pipefail

read -r pr_author pr_state head_sha < <(
gh api "repos/$REPOSITORY/pulls/$PR_NUMBER" --jq '[.user.login, .state, .head.sha] | @tsv'
)
if [ "$pr_state" != "open" ]; then
echo "::error::PR #$PR_NUMBER is not open."
exit 1
fi
if [ "${COMMENT_AUTHOR,,}" != "${pr_author,,}" ]; then
commenter_permission="$(
gh api "repos/$REPOSITORY/collaborators/$COMMENT_AUTHOR/permission" \
--jq '.permission' 2>/dev/null || printf 'none'
)"
case "$commenter_permission" in
admin|write) ;;
*)
echo "::error::Only PR author @$pr_author or a user with write access can request Docker CI."
exit 1
;;
esac
fi

echo "head_sha=$head_sha" >> "$GITHUB_OUTPUT"

- name: Create isaaclab-bot token
id: app-token
uses: actions/create-github-app-token@1b10c78c7865c340bc4f6099eb2f838309f1e8c3 # v3.1.1
with:
client-id: ${{ secrets.CHANGELOG_APP_CLIENT_ID }}
private-key: ${{ secrets.CHANGELOG_APP_PRIVATE_KEY }}
permission-pull-requests: write

- name: Trigger Docker CI
env:
EXPECTED_HEAD_SHA: ${{ steps.authorize.outputs.head_sha }}
GH_TOKEN: ${{ steps.app-token.outputs.token }}
LABEL: ci:run-docker
PR_NUMBER: ${{ github.event.issue.number }}
REPOSITORY: ${{ github.repository }}
run: |
set -euo pipefail

# GitHub resolves the head when it processes the label, so labeling a
# PR whose head has already moved on builds a revision nobody asked
# for. Skip the request instead of spending GPU minutes on it.
head_sha="$(gh api "repos/$REPOSITORY/pulls/$PR_NUMBER" --jq '.head.sha')"
if [ "$head_sha" != "$EXPECTED_HEAD_SHA" ]; then
echo "::error::PR #$PR_NUMBER moved from ${EXPECTED_HEAD_SHA:0:7} to ${head_sha:0:7} while this request was processed. Comment 'run-ci' again to test the current head."
exit 1
fi

endpoint="repos/$REPOSITORY/issues/$PR_NUMBER/labels"
gh api --method DELETE "$endpoint/$LABEL" --silent >/dev/null 2>&1 || true
gh api --method POST "$endpoint" -f "labels[]=$LABEL" --silent
gh api --method DELETE "$endpoint/$LABEL" --silent

# A push can still land between the check above and GitHub processing
# the label; nothing can make those two steps atomic. Re-read the head
# so the mismatch is reported rather than silently testing a revision
# the requester never saw.
built_sha="$(gh api "repos/$REPOSITORY/pulls/$PR_NUMBER" --jq '.head.sha')"
if [ "$built_sha" != "$EXPECTED_HEAD_SHA" ]; then
echo "::error::PR #$PR_NUMBER moved to ${built_sha:0:7} as the label was applied, so Docker CI is testing that revision and not the requested ${EXPECTED_HEAD_SHA:0:7}. Comment 'run-ci' again to test the current head."
exit 1
fi

echo "Requested Docker CI for PR #$PR_NUMBER at ${EXPECTED_HEAD_SHA:0:7}." >> "$GITHUB_STEP_SUMMARY"
Loading