diff --git a/.github/workflows/linux-eic-shell.yml b/.github/workflows/linux-eic-shell.yml new file mode 100644 index 0000000..c43b0d1 --- /dev/null +++ b/.github/workflows/linux-eic-shell.yml @@ -0,0 +1,400 @@ +name: Build against eic-shell + +on: + push: + branches: + - main + tags: + - '*' + pull_request: + merge_group: + workflow_dispatch: + inputs: + organization: + description: 'eic-shell organization' + default: 'eicweb' + required: false + type: string + platform: + description: 'eic-shell platform' + default: 'eic_xl' + required: false + type: string + release: + description: 'eic-shell release' + default: 'nightly' + required: false + type: string + detector_version: + description: 'epic geometry version' + default: 'main' + required: false + type: string + +concurrency: + group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.run_id }} + cancel-in-progress: true + +permissions: + contents: read + actions: read + pull-requests: read + +env: + organization: ${{ inputs.organization || vars.organization || 'eicweb' }} + platform: ${{ inputs.platform || 'eic_xl' }} + release: ${{ inputs.release || 'nightly' }} + detector_version: ${{ inputs.detector_version || 'main' }} + +jobs: + build: + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + CXX: [g++, clang++] + CMAKE_BUILD_TYPE: [Release] + steps: + - uses: actions/checkout@v6 + - uses: cvmfs-contrib/github-action-cvmfs@v5 + - name: Build and install + uses: eic/run-cvmfs-osg-eic-shell@main + with: + organization: "${{ env.organization }}" + platform-release: "${{ env.platform }}:${{ env.release }}" + run: | + CXX="${{ matrix.CXX }}" cmake -B build -S . \ + -DCMAKE_BUILD_TYPE=${{ matrix.CMAKE_BUILD_TYPE }} \ + -DCMAKE_INSTALL_PREFIX=install + cmake --build build -j $(getconf _NPROCESSORS_ONLN) --target install + - name: Compress install directory + run: tar -caf install.tar.zst install/ + - uses: actions/upload-artifact@v7 + with: + name: install-${{ matrix.CXX }}-eic-shell-${{ matrix.CMAKE_BUILD_TYPE }}-${{ env.platform }}-${{ env.release }} + path: install.tar.zst + if-no-files-found: error + + npsim-gun: + runs-on: ubuntu-latest + needs: build + strategy: + fail-fast: false + matrix: + particle: [pi, e] + detector_config: [epic_craterlake] + steps: + - uses: actions/checkout@v6 + - uses: actions/download-artifact@v8 + with: + name: install-g++-eic-shell-Release-${{ env.platform }}-${{ env.release }} + path: . + - name: Uncompress install artifact + run: tar -xaf install.tar.zst + - uses: cvmfs-contrib/github-action-cvmfs@v5 + - name: Produce simulation files + uses: eic/run-cvmfs-osg-eic-shell@main + with: + organization: "${{ env.organization }}" + platform-release: "${{ env.platform }}:${{ env.release }}" + setup: /opt/detector/epic-${{ env.detector_version }}/bin/thisepic.sh + run: | + export DETECTOR_CACHE=/opt/detector/epic-${{ env.detector_version }}/share/epic + export PATH=$PWD/install/bin${PATH:+:$PATH} + export LD_LIBRARY_PATH=$PWD/install/lib${LD_LIBRARY_PATH:+:$LD_LIBRARY_PATH} + npsim --compactFile ${DETECTOR_PATH}/${{ matrix.detector_config }}.xml -G \ + --random.seed 1 \ + --gun.particle "${{ matrix.particle }}-" \ + --gun.momentumMin "1*GeV" \ + --gun.momentumMax "20*GeV" \ + --gun.distribution "uniform" \ + -N 100 \ + --outputFile sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }}.edm4hep.root \ + -v WARNING + - uses: actions/upload-artifact@v7 + with: + name: sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }}.edm4hep.root + path: sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }}.edm4hep.root + if-no-files-found: error + - name: Download previous artifact + uses: dawidd6/action-download-artifact@v21 + with: + branch: ${{ github.event.pull_request.base.ref || github.ref_name }} + path: ref/ + name: sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }}.edm4hep.root + workflow: .github/workflows/linux-eic-shell.yml + workflow_conclusion: "" + if_no_artifact_found: warn + - name: Compare to previous artifacts + uses: eic/run-cvmfs-osg-eic-shell@main + with: + organization: "${{ env.organization }}" + platform-release: "${{ env.platform }}:${{ env.release }}" + setup: /opt/detector/epic-${{ env.detector_version }}/bin/thisepic.sh + run: | + export PATH=$PWD/install/bin${PATH:+:$PATH} + mkdir capybara-reports + shopt -s nullglob + capybara bara ref/sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }}.edm4hep.root* sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }}.edm4hep.root + mv capybara-reports sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }} + touch .sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }} + - uses: actions/upload-artifact@v7 + with: + name: sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }}.capy + path: | + .sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }} + sim_${{ matrix.particle }}_1GeV_20GeV_${{ matrix.detector_config }}/ + if-no-files-found: error + + npsim-dis: + runs-on: ubuntu-latest + needs: build + strategy: + fail-fast: false + matrix: + beam: [5x41, 10x100, 18x275] + minq2: [1, 1000] + detector_config: [epic_craterlake] + exclude: + - beam: 5x41 + minq2: 1000 + steps: + - uses: actions/checkout@v6 + - uses: actions/download-artifact@v8 + with: + name: install-g++-eic-shell-Release-${{ env.platform }}-${{ env.release }} + path: . + - name: Uncompress install artifact + run: tar -xaf install.tar.zst + - uses: cvmfs-contrib/github-action-cvmfs@v5 + - name: Produce simulation files + uses: eic/run-cvmfs-osg-eic-shell@main + with: + organization: "${{ env.organization }}" + platform-release: "${{ env.platform }}:${{ env.release }}" + setup: /opt/detector/epic-${{ env.detector_version }}/bin/thisepic.sh + run: | + export DETECTOR_CACHE=/opt/detector/epic-${{ env.detector_version }}/share/epic + export PATH=$PWD/install/bin${PATH:+:$PATH} + export LD_LIBRARY_PATH=$PWD/install/lib${LD_LIBRARY_PATH:+:$LD_LIBRARY_PATH} + url=root://dtn-eic.jlab.org//volatile/eic/EPIC/EVGEN/DIS/NC/${{ matrix.beam }}/minQ2=${{ matrix.minq2 }}/pythia8NCDIS_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_beamEffects_xAngle=-0.025_hiDiv_1.hepmc3.tree.root + npsim --compactFile ${DETECTOR_PATH}/${{ matrix.detector_config }}.xml \ + -N 100 \ + --inputFiles ${url} \ + --random.seed 1 \ + --outputFile sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }}.edm4hep.root \ + -v WARNING + - name: Upload ROOT output + uses: actions/upload-artifact@v7 + with: + name: sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }}.edm4hep.root + path: sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }}.edm4hep.root + if-no-files-found: error + - name: Download previous artifact + uses: dawidd6/action-download-artifact@v21 + with: + branch: ${{ github.event.pull_request.base.ref || github.ref_name }} + path: ref/ + name: sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }}.edm4hep.root + workflow: .github/workflows/linux-eic-shell.yml + workflow_conclusion: "" + if_no_artifact_found: warn + - name: Compare to previous artifacts + uses: eic/run-cvmfs-osg-eic-shell@main + with: + organization: "${{ env.organization }}" + platform-release: "${{ env.platform }}:${{ env.release }}" + setup: /opt/detector/epic-${{ env.detector_version }}/bin/thisepic.sh + run: | + export PATH=$PWD/install/bin${PATH:+:$PATH} + mkdir capybara-reports + shopt -s nullglob + capybara bara ref/sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }}.edm4hep.root* sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }}.edm4hep.root + mv capybara-reports sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }} + touch .sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }} + - uses: actions/upload-artifact@v7 + with: + name: sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }}.capy + path: | + .sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }} + sim_dis_${{ matrix.beam }}_minQ2=${{ matrix.minq2 }}_${{ matrix.detector_config }}/ + if-no-files-found: error + + merge-npsim-capybara: + runs-on: ubuntu-latest + needs: + - npsim-gun + - npsim-dis + steps: + - uses: actions/upload-artifact/merge@v7 + with: + name: capybara-report + pattern: '*.capy' + delete-merged: true + + list-open-prs: + uses: eic/actions/.github/workflows/list-open-prs.yml@main + + get-docs-from-open-prs: + runs-on: ubuntu-latest + needs: + - list-open-prs + - merge-npsim-capybara + strategy: + matrix: ${{ fromJSON(needs.list-open-prs.outputs.json) }} + fail-fast: false + max-parallel: 4 + steps: + - name: Download capybara artifact (other PRs) + id: download_capybara + uses: dawidd6/action-download-artifact@v21 + if: github.event.pull_request.number != matrix.pr + with: + commit: ${{ matrix.head_sha }} + path: publishing_docs/pr/${{ matrix.pr }}/capybara/ + name: capybara-report + workflow: ".github/workflows/linux-eic-shell.yml" + workflow_conclusion: "completed" + if_no_artifact_found: ignore + - name: Download capybara artifact (this PR) + uses: actions/download-artifact@v8 + if: github.event.pull_request.number == matrix.pr + with: + name: capybara-report + path: publishing_docs/pr/${{ matrix.pr }}/capybara/ + - uses: actions/upload-artifact@v7 + with: + name: github-pages-staging-pr-${{ matrix.pr }} + path: publishing_docs/ + if-no-files-found: ignore + + get-docs-from-main: + runs-on: ubuntu-latest + needs: + - merge-npsim-capybara + steps: + - name: Download capybara artifact (in PR) + id: download_capybara + uses: dawidd6/action-download-artifact@v21 + if: github.ref_name != 'main' + with: + branch: main + path: publishing_docs/capybara/ + name: capybara-report + workflow: ".github/workflows/linux-eic-shell.yml" + workflow_conclusion: "completed" + if_no_artifact_found: ignore + - name: Download capybara artifact (on main) + uses: actions/download-artifact@v8 + if: github.ref_name == 'main' + with: + name: capybara-report + path: publishing_docs/capybara/ + - name: Populate capybara summary (on main) + if: github.ref_name == 'main' || steps.download_capybara.outputs.found_artifact == 'true' + run: | + echo "### Capybara summary for main" >> publishing_docs/capybara/index.md + find publishing_docs/capybara/ -mindepth 1 -maxdepth 1 -type d -printf \ + "- [%f](https://eic.github.io/npsim/capybara/%f/index.html)\n" | sort >> publishing_docs/capybara/index.md + - name: Create capybara step summary (this PR) + if: github.ref_name == 'main' + run: | + cat publishing_docs/capybara/index.md >> $GITHUB_STEP_SUMMARY + - name: Ensure publishing_docs is non-empty + run: mkdir -p publishing_docs && touch publishing_docs/.keep + - uses: actions/upload-artifact@v7 + with: + name: github-pages-staging-main + path: publishing_docs/ + if-no-files-found: error + include-hidden-files: true + + build-artifacts-page: + runs-on: ubuntu-latest + needs: + - get-docs-from-open-prs + - get-docs-from-main + if: | + always() && + !cancelled() && + !failure() + steps: + - name: Download artifacts for page + uses: actions/download-artifact@v8 + with: + pattern: github-pages-staging-* + path: artifacts/ + - name: Build static page content + run: | + mkdir -p _site + for dir in artifacts/github-pages-staging-*/; do + [ -d "$dir" ] && cp -r "$dir"/. _site/ || true + done + mkdir -p _site/pr + echo "### PRs" >> _site/pr/index.md + find _site/pr -mindepth 1 -maxdepth 1 -type d -printf "- [%f](%f/index.md)\n" | sort >> _site/pr/index.md + - name: Upload GitHub Pages artifact + uses: actions/upload-pages-artifact@v5 + with: + path: _site/ + retention-days: 7 + - name: Populate capybara summary + if: ${{ github.event_name == 'pull_request' }} + run: | + echo "### Capybara summary for PR ${{ github.event.pull_request.number }}" >> capybara_${{ github.event.pull_request.number }}.md + [ -d _site/pr/${{ github.event.pull_request.number }}/capybara/ ] && \ + find _site/pr/${{ github.event.pull_request.number }}/capybara/ -mindepth 1 -maxdepth 1 -type d -printf \ + "- [%f](https://eic.github.io/npsim/pr/${{ github.event.pull_request.number }}/capybara/%f/index.html)\n" | sort >> capybara_${{ github.event.pull_request.number }}.md || true + echo "Last updated $(TZ=America/New_York date -Iminutes) ${{ github.event.pull_request.head.sha }}" >> capybara_${{ github.event.pull_request.number }}.md + - name: Create capybara step summary + if: ${{ github.event_name == 'pull_request' }} + run: | + cat capybara_${{ github.event.pull_request.number }}.md >> $GITHUB_STEP_SUMMARY + - name: Upload capybara summary + if: ${{ github.event_name == 'pull_request' }} + uses: actions/upload-artifact@v7 + with: + name: capybara_${{ github.event.pull_request.number }}.md + path: capybara_${{ github.event.pull_request.number }}.md + + deploy-artifacts-page: + needs: + - build-artifacts-page + if: | + always() && + !cancelled() && + !failure() + permissions: + pages: write + id-token: write + pull-requests: write + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + runs-on: ubuntu-latest + steps: + - name: Deploy to GitHub Pages + id: deployment + continue-on-error: false + uses: actions/deploy-pages@v5 + - name: Find capybara comment + if: ${{ github.event_name == 'pull_request' }} + id: find_comment + uses: peter-evans/find-comment@v4 + with: + issue-number: ${{ github.event.pull_request.number }} + comment-author: 'github-actions[bot]' + body-includes: Capybara summary + - name: Fetch capybara summary + if: ${{ github.event_name == 'pull_request' }} + uses: actions/download-artifact@v8 + with: + name: capybara_${{ github.event.pull_request.number }}.md + - name: Create or update capybara comment + if: ${{ github.event_name == 'pull_request' }} + uses: peter-evans/create-or-update-comment@v5 + with: + comment-id: ${{ steps.find_comment.outputs.comment-id }} + issue-number: ${{ github.event.pull_request.number }} + body-file: capybara_${{ github.event.pull_request.number }}.md + edit-mode: replace