Wip #4872
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
name: Node CI | |
on: [push] | |
jobs: | |
test: | |
runs-on: ubuntu-latest | |
if: "!contains(github.event.head_commit.message, 'ci skip') && !contains(github.event.head_commit.message, 'skip ci')" | |
name: Run unit tests | |
env: | |
NX_CLOUD_ACCESS_TOKEN: ${{ secrets.NX_CLOUD_ACCESS_TOKEN }} | |
NX_BRANCH: ${{ github.event.number || github.ref_name }} | |
steps: | |
- name: Checkout repository | |
uses: actions/checkout@v4 | |
with: | |
# We need to fetch all branches and commits so that Nx affected has a base to compare against. | |
fetch-depth: 0 | |
- uses: nrwl/nx-set-shas@v4 | |
- name: Setup .npmrc file for NPM registry | |
uses: actions/setup-node@v4 | |
with: | |
node-version: '22' | |
registry-url: 'https://registry.npmjs.org' | |
cache: 'npm' | |
- name: Install dependencies | |
run: npm ci --no-audit | |
- name: Check types | |
run: npm exec nx affected -- --target typecheck --parallel | |
- name: Lint | |
run: npm exec nx affected -- --target lint --parallel | |
- name: Unit tests | |
run: npm exec nx affected -- --target test --run | |
- name: Build all packages | |
run: npm run build | |
- name: Pack packages for testing | |
run: | | |
mkdir ./packed-artifacts | |
npm pack --workspace="@grafana/create-plugin" --workspace="@grafana/sign-plugin" --pack-destination="./packed-artifacts" | |
cp ./.github/knip.json ./packed-artifacts | |
- name: Upload artifacts for testing | |
uses: actions/upload-artifact@v4 | |
with: | |
name: packed-artifacts | |
path: ./packed-artifacts | |
retention-days: 1 | |
generate-plugins: | |
name: Test plugin scaffolding | |
if: "!contains(github.event.head_commit.message, 'ci skip') && !contains(github.event.head_commit.message, 'skip ci')" | |
needs: [test] | |
runs-on: ubuntu-latest | |
permissions: | |
id-token: write | |
strategy: | |
matrix: | |
include: | |
- workingDir: 'myorg-nobackend-app' | |
cmd: create-plugin --pluginName='no-backend' --orgName='myorg' --pluginType='app' --no-hasBackend | |
hasBackend: false | |
- workingDir: 'myorg-backend-app' | |
cmd: create-plugin --pluginName='backend' --orgName='myorg' --pluginType='app' --hasBackend | |
hasBackend: true | |
- workingDir: 'myorg-nobackend-panel' | |
cmd: create-plugin --pluginName='no-backend' --orgName='myorg' --pluginType='panel' | |
hasBackend: false | |
- workingDir: 'myorg-nobackend-datasource' | |
cmd: create-plugin --pluginName='no-backend' --orgName='myorg' --pluginType='datasource' --no-hasBackend | |
hasBackend: false | |
- workingDir: 'myorg-backend-datasource' | |
cmd: create-plugin --pluginName='backend' --orgName='myorg' --pluginType='datasource' --hasBackend | |
hasBackend: true | |
- workingDir: 'myorg-nobackendscenes-app' | |
cmd: create-plugin --pluginName='no-backend-scenes' --orgName='myorg' --pluginType='scenesapp' --no-hasBackend | |
hasBackend: false | |
steps: | |
- name: Setup .npmrc file for NPM registry | |
uses: actions/setup-node@v4 | |
with: | |
node-version: '22' | |
registry-url: 'https://registry.npmjs.org' | |
- name: Download packed artifacts | |
uses: actions/download-artifact@v4 | |
with: | |
name: packed-artifacts | |
path: ./packed-artifacts | |
- name: Install npm packages globally | |
run: for file in *.tgz; do npm install -g "$file"; done | |
working-directory: ./packed-artifacts | |
- name: Generate plugin | |
run: ${{ matrix.cmd }} | |
- name: Install generated plugin dependencies | |
run: npm install --no-audit | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Lint plugin frontend | |
run: npm run lint | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Typecheck plugin frontend | |
run: npm run typecheck | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Build plugin frontend | |
run: npm run build | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Test plugin frontend | |
run: npm run test:ci | |
working-directory: ./${{ matrix.workingDir }} | |
- uses: actions/setup-go@v5 | |
with: | |
go-version: '~1.22' | |
check-latest: true | |
cache-dependency-path: ./${{ matrix.workingDir }}/go.sum | |
if: ${{ matrix.hasBackend == true }} | |
- name: Build plugin backend | |
uses: magefile/mage-action@v3 | |
with: | |
version: latest | |
args: -v build:linux | |
workdir: ./${{ matrix.workingDir }} | |
if: ${{ matrix.hasBackend == true }} | |
- name: Install playwright dependencies | |
if: ${{ matrix.workingDir != 'myorg-nobackend-scenesapp' }} | |
run: npm exec playwright install chromium | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Get secrets for DockerHub login | |
uses: grafana/shared-workflows/actions/get-vault-secrets@main | |
with: | |
common_secrets: | | |
DOCKERHUB_USERNAME=dockerhub:username | |
DOCKERHUB_PASSWORD=dockerhub:password | |
- name: Log in to Docker Hub | |
uses: docker/login-action@v3 | |
with: | |
username: ${{ env.DOCKERHUB_USERNAME }} | |
password: ${{ env.DOCKERHUB_PASSWORD }} | |
- name: Start grafana server for e2e tests | |
if: ${{ matrix.workingDir != 'myorg-nobackend-scenesapp' }} | |
run: docker compose up -d | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Wait for grafana server | |
uses: grafana/plugin-actions/wait-for-grafana@main | |
if: ${{ matrix.workingDir != 'myorg-nobackend-scenesapp' }} | |
- name: Run e2e tests | |
id: run-e2e-tests | |
if: ${{ matrix.workingDir != 'myorg-nobackend-scenesapp' }} | |
run: npm run e2e | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Stop grafana docker | |
if: ${{ matrix.workingDir != 'myorg-nobackend-scenesapp' }} | |
run: docker compose down | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Check plugin.json | |
run: | | |
cp -r dist/ ${{ matrix.workingDir }} | |
zip ${{ matrix.workingDir }}.zip ${{ matrix.workingDir }} -r | |
rm -r ${{ matrix.workingDir }} | |
docker run --pull=always \ | |
-v $PWD/${{ matrix.workingDir }}.zip:/archive.zip \ | |
grafana/plugin-validator-cli -analyzer=metadatavalid /archive.zip | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Archive E2E output | |
uses: actions/upload-artifact@v4 | |
if: ${{ matrix.workingDir != 'myorg-nobackend-scenesapp' && steps.run-e2e-tests.outcome != 'success' }} | |
with: | |
name: ${{ matrix.workingDir }}-playwright-report | |
path: ./${{ matrix.workingDir }}/playwright-report/ | |
retention-days: 5 | |
- name: '@grafana/sign-plugin - use GRAFANA_ACCESS_POLICY_TOKEN to sign generate-panel plugin' | |
if: ${{ matrix.workingDir == 'myorg-nobackend-panel' && github.actor != 'dependabot[bot]' }} | |
env: | |
GRAFANA_ACCESS_POLICY_TOKEN: ${{ secrets.GRAFANA_ACCESS_POLICY_TOKEN }} | |
run: sign-plugin --rootUrls http://www.example.com --signatureType private | |
working-directory: ./${{ matrix.workingDir }} | |
- name: '@grafana/sign-plugin - use GRAFANA_API_KEY to sign generate-panel plugin' | |
if: ${{ matrix.workingDir == 'myorg-nobackend-panel' && github.actor != 'dependabot[bot]' }} | |
env: | |
GRAFANA_API_KEY: ${{ secrets.GRAFANA_API_KEY }} | |
run: sign-plugin --rootUrls http://www.example.com --signatureType private | |
working-directory: ./${{ matrix.workingDir }} | |
- name: Frontend Knip Report | |
if: ${{ github.actor != 'dependabot[bot]' }} | |
# Knip uses the scaffolded plugin .gitignore file for ignore paths. | |
# github workflows use paths like home/runner/work/plugin-tools/plugin-tools | |
# so we need to remove /work otherwise knip returns false positives | |
run: | | |
sed -i '/^work\/$/d' .gitignore | |
npx -y knip --config ../packed-artifacts/knip.json --reporter markdown --no-exit-code | |
working-directory: ./${{ matrix.workingDir }} | |
release: | |
runs-on: ubuntu-latest | |
needs: [test, generate-plugins] | |
if: "!contains(github.event.head_commit.message, 'ci skip') && !contains(github.event.head_commit.message, 'skip ci') && github.actor != 'dependabot[bot]'" | |
name: Release packages | |
env: | |
NX_CLOUD_ACCESS_TOKEN: ${{ secrets.NX_CLOUD_ACCESS_TOKEN }} | |
NX_BRANCH: ${{ github.event.number || github.ref_name }} | |
NPM_TOKEN: ${{ secrets.NPM_TOKEN }} | |
permissions: | |
contents: read | |
id-token: write | |
steps: | |
- name: Generate token | |
id: generate_token | |
uses: tibdex/github-app-token@3beb63f4bd073e61482598c45c71c1019b59b73a | |
with: | |
app_id: ${{ secrets.PLUGINS_PLATFORM_BOT_APP_ID }} | |
private_key: ${{ secrets.PLUGINS_PLATFORM_BOT_APP_PEM }} | |
- uses: actions/checkout@v4 | |
with: | |
token: ${{ steps.generate_token.outputs.token }} | |
- name: Prepare repository | |
run: git fetch --unshallow --tags | |
- name: Setup environment | |
uses: actions/setup-node@v4 | |
with: | |
node-version: '22' | |
registry-url: 'https://registry.npmjs.org' | |
cache: 'npm' | |
- name: Install dependencies | |
run: npm ci --no-audit | |
- name: Build | |
run: npm run build | |
- name: Create Release | |
env: | |
GITHUB_TOKEN: ${{ steps.generate_token.outputs.token }} | |
NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} | |
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }} | |
run: npm run release |