From 6f04071d885ae4f2479a87ca4baf88b6e4945e33 Mon Sep 17 00:00:00 2001 From: Katerina Koukiou Date: Tue, 9 Feb 2021 13:58:15 +0100 Subject: [PATCH] Introduce a github action which builds a cockpit preview when requested It currently reacts to /livetest comments on PRs and builds cockpit from the PR's checkout. Then serves it on logs.cockpit-project.org on a port specified on a follow-up comment to the /livetest. Cockpit developers can now utilize this workflow to review a PR without having to pull and compile the code locally. --- .github/workflows/livetest.yml.disabled | 101 ++++++++++++++++++++++++ 1 file changed, 101 insertions(+) create mode 100644 .github/workflows/livetest.yml.disabled diff --git a/.github/workflows/livetest.yml.disabled b/.github/workflows/livetest.yml.disabled new file mode 100644 index 0000000..42a1f80 --- /dev/null +++ b/.github/workflows/livetest.yml.disabled @@ -0,0 +1,101 @@ +name: Live test cockpit from PRs +# Triggered when a repository collaborator comments /livetest on a PR +# This is currently configured to run on cockpit-project org. +# If your project lives somewhere else than the github cockpit-project organization, +# you need to set up your own relay host, add a secret with the private SSH key, and +# adjust the RELAY_HOST env variable and SINK_SSHRELAY_PRIVATE secret name. + +on: + issue_comment: + types: [created] + +jobs: + pr-info: + runs-on: ubuntu-20.04 + steps: + - name: Query author repository permissions + uses: octokit/request-action@v2.x + id: user_permission + with: + route: GET /repos/${{ github.repository }}/collaborators/${{ github.event.sender.login }}/permission + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + + # restrict /livetest to users with admin or write permission for the repository + # see https://docs.github.com/en/free-pro-team@latest/rest/reference/repos#get-repository-permissions-for-a-user + # store output if user is allowed in allowed_user job output so it has to be checked in downstream job + - name: Check if user does have correct permissions + if: contains('admin write', fromJson(steps.user_permission.outputs.data).permission) + id: check_user_perm + run: | + echo "User '${{ github.event.sender.login }}' has permission '${{ fromJson(steps.user_permission.outputs.data).permission }}' allowed values: 'admin', 'write'" + echo "::set-output name=allowed_user::true" + + outputs: + allowed_user: ${{ steps.check_user_perm.outputs.allowed_user }} + + live-test: + needs: pr-info + if: needs.pr-info.outputs.allowed_user == 'true' && github.event.issue.pull_request && startsWith(github.event.comment.body, '/livetest') + runs-on: ubuntu-20.04 + env: + RELAY_HOST: logs.cockpit-project.org + steps: + - name: Install dependencies + run: | + sudo apt update + sudo apt install -y cockpit-system cockpit-ws nodejs npm sassc make + + - name: Clone repository + uses: actions/checkout@v2 + with: + # need this to also fetch tags + fetch-depth: 0 + + - name: Compile and install the project + run: make && sudo make install + + - name: Create a new test user + # WARNING: if you want to add this users to sudoers make sure to propertly delete the SINK_SSHRELAY_PRIVATE + run: sudo useradd --create-home livetest; echo livetest:foobar | sudo chpasswd + + - name: Get the commit SHA that triggered the workflow + id: get_commit_sha + run: | + echo "::set-output name=sha_short::$(git rev-parse --short HEAD)" + + - name: Get ssh gateway port to forward to + id: remote_port + env: + SHA_SHORT: "${{ steps.get_commit_sha.outputs.sha_short }}" + run: | + echo ::set-output name=SSH_GATEWAY_PORT::$((16#$SHA_SHORT % 32768 + 1500)) + + - name: Write a comment on the PR with link to the cockpit instance + uses: actions/github-script@v3 + with: + github-token: ${{ secrets.GITHUB_TOKEN }} + script: | + github.issues.createComment({ + issue_number: context.issue.number, + owner: context.repo.owner, + repo: context.repo.repo, + body: 'Cockpit preview: https://${{ env.RELAY_HOST }}:${{ steps.remote_port.outputs.SSH_GATEWAY_PORT }}' + }) + + - name: Create an SSH private key from the secret + run: | + sudo touch /run/SINK_SSHRELAY_PRIVATE && sudo chown $(id -u):$(id -g) /run/SINK_SSHRELAY_PRIVATE + echo "${{ secrets.SINK_SSHRELAY_PRIVATE }}" > /run/SINK_SSHRELAY_PRIVATE + chmod 600 /run/SINK_SSHRELAY_PRIVATE + mkdir -p ~/.ssh && ssh-keyscan -H ${{ env.RELAY_HOST }} > ~/.ssh/known_hosts + + - name: Forward cockpit port 9090 to a server we can access + run: ssh -f -R ':${{ steps.remote_port.outputs.SSH_GATEWAY_PORT }}':localhost:9090 -i /run/SINK_SSHRELAY_PRIVATE -o ExitOnForwardFailure=yes sshgw@${{ env.RELAY_HOST }} 'sleep infinity' + + - name: Block workflow from finishing + run: sleep 4h + + - name: Cleanup ssh process + if: ${{ always() }} + run: pkill ssh || true