diff --git a/.forgejo/prepare-end-to-end/action.yml b/.forgejo/prepare-end-to-end/action.yml index a713112b..8ae5cdd8 100644 --- a/.forgejo/prepare-end-to-end/action.yml +++ b/.forgejo/prepare-end-to-end/action.yml @@ -1,3 +1,7 @@ +inputs: + built: + description: 'True if a source build is available, false otherwise' + runs: using: "composite" steps: @@ -11,11 +15,18 @@ runs: /usr/local/bin/garage key: S3 - - uses: https://data.forgejo.org/actions/setup-forgejo@v2.0.11 + - uses: https://data.forgejo.org/actions/setup-forgejo@v3.1.6 with: install-only: true - run: forgejo-binary.sh ensure_user forgejo + - name: inputs context dump for debug + run: | + set -x + cat <> $FORGEJO_OUTPUT + echo "built=no" >> $FORGEJO_OUTPUT exit 0 fi @@ -55,40 +54,72 @@ jobs: $forgejo --version mv $forgejo /tmp/forgejo-upload/forgejo-$version done + + echo "forgejo_versions_json=$(node -p "JSON.stringify(process.argv[1].split(' '))" "$(cat forgejo/build-from-sources)")" >> $FORGEJO_OUTPUT + echo "built=yes" >> $FORGEJO_OUTPUT + + - name: steps context dump for debug + run: | + set -x + cat <> $GITHUB_OUTPUT - - run: ./end-to-end.sh prepare_dockerd - - run: su forgejo -c "./end-to-end.sh test_actions ${{ matrix.info.version }}" - - name: update documentation - uses: https://data.forgejo.org/actions/cascading-pr@v2.1 - with: - origin-url: ${{ env.GITHUB_SERVER_URL }} - origin-repo: ${{ github.repository }} - origin-token: ${{ secrets.CASCADE_DOCS_ORIGIN_TOKEN }} - origin-ref: refs/heads/main - destination-url: https://codeberg.org - destination-fork-repo: ${{ vars.CASCADE_DOCS_DESTINATION_DOER }}/docs - destination-repo: forgejo/docs - destination-branch: ${{ matrix.info.branch || format('v{0}', matrix.info.version) }} - destination-token: ${{ secrets.CASCADE_DOCS_DESTINATION_TOKEN }} - prefix: ${{ env.GITHUB_REPOSITORY }}-${{ matrix.info.version }} - update: .forgejo/cascading-docs - env: - FORCE_VERSION: "${{ vars.CASCADE_DOCS_FORCE_VERSION }}" - VERSION: "${{ steps.full-version.outputs.value }}" - upgrade: name: upgrade and storage needs: [build] - runs-on: lxc-bookworm + runs-on: lxc-trixie steps: - uses: https://data.forgejo.org/actions/checkout@v4 - uses: ./.forgejo/prepare-end-to-end + with: + built: ${{ needs.build.outputs.built }} - run: su forgejo -c "./end-to-end.sh test_upgrades" - run: su forgejo -c "./end-to-end.sh test_storage" + - if: ${{ needs.build.outputs.built == 'yes' }} + uses: ./.forgejo/upload-coverage + with: + scope: upgrade - name: full logs if: always() run: su forgejo -c "./end-to-end.sh show_logs" diff --git a/Dockerfile b/Dockerfile index 7cf8242e..e31cb6d8 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,27 +1,33 @@ -FROM code.forgejo.org/oci/node:20-bookworm +FROM data.forgejo.org/oci/node:24-trixie ENV PATH=$PATH:/setup-forgejo ENV _CONTAINERS_USERNS_CONFIGURED="" -ADD https://code.forgejo.org/actions/setup-forgejo.git /setup-forgejo - RUN apt-get update && \ apt-get --assume-yes --no-install-recommends install \ + aardvark-dns \ ca-certificates \ curl \ daemon \ + fuse-overlayfs \ + gettext \ git \ jq \ + libcap2-bin \ + neovim \ + nftables \ + passt \ podman \ + podman-compose \ podman-docker \ procps \ + pup \ slirp4netns \ - sqlite3 \ sudo \ tcpdump \ uidmap \ wget && \ - adduser forgejo-tests && \ + adduser -u 1001 forgejo-tests && \ groupadd wheel && \ adduser forgejo-tests wheel && \ echo "%wheel ALL=(ALL) NOPASSWD:ALL" > /etc/sudoers && \ @@ -29,9 +35,13 @@ RUN apt-get update && \ echo "forgejo-tests:10000:9999" > /etc/subgid && \ mkdir /srv/forgejo-binaries && \ chown forgejo-tests:forgejo-tests /srv/forgejo-binaries && \ - apt-get clean + apt-get clean && \ + apt-get autoremove --purge && \ + apt-get autoclean -COPY . /e2e +COPY --chown=1001:1001 . /e2e + +RUN git clone https://code.forgejo.org/actions/setup-forgejo.git /setup-forgejo USER forgejo-tests diff --git a/README.md b/README.md index cdcf5db0..33fcfdbd 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,18 @@ # Forgejo end-to-end tests +- [Forgejo end-to-end tests](#forgejo-end-to-end-tests) + - [Removing legacy tests](#removing-legacy-tests) + - [Hacking](#hacking) + - [Running from locally built binary](#running-from-locally-built-binary) + - [Forgejo](#forgejo) + - [Forgejo runner](#forgejo-runner) + - [Running from locally built container image](#running-from-locally-built-container-image) + - [Running actions tests locally](#running-actions-tests-locally) + - [Running federation tests locally](#running-federation-tests-locally) + - [Federated Mastodon Follow Test](#federated-mastodon-follow-test) + - [Running other tests locally](#running-other-tests-locally) + - [Running tests in Docker/Podman](#running-tests-in-dockerpodman) + A series of tests scenarios and assertions covering [Forgejo](https://codeberg.org/forgejo/forgejo) and the [Forgejo runner](https://code.forgejo.org/forgejo/runner). @@ -7,7 +20,7 @@ runner](https://code.forgejo.org/forgejo/runner). They are designed to run using Forgejo releases and development versions compiled from designated repositories. -# Removing legacy tests +## Removing legacy tests End-to-end tests cover the supported range of releases and when one of them is EOL, it must be removed as well as the tests that target it @@ -17,7 +30,7 @@ When a release is EOL, a branch is cut with a name following the pattern `legacy/vX.Y-vA.B`. For instance when `v8.0` is published and `v1.21` is EOL, the branch `legacy/v8.0-v1.21` is cut. -# Hacking +## Hacking docker and sudo must be installed with insecure registries allowed in /etc/docker/daemon.json for the IP that will be used for forgejo such @@ -46,12 +59,12 @@ git clone https://code.forgejo.org/forgejo/end-to-end cd end-to-end ``` -## Running from locally built binary +### Running from locally built binary Before injecting a manually built binary, make sure a simple test was run so that the directories are populated. -### Forgejo +#### Forgejo From a checkout of https://codeberg.org/forgejo/forgejo/ @@ -62,7 +75,7 @@ cp -a forgejo /srv/forgejo-binaries/forgejo-11.0 It will be used whenever the version `11.0` is specified in a test. -### Forgejo runner +#### Forgejo runner From a checkout of https://code.forgejo.org/forgejo/runner @@ -71,6 +84,12 @@ make --always-make forgejo-runner cp forgejo-runner /tmp/forgejo-end-to-end/forgejo-runner ``` +### Running from locally built container image + +```bash +docker buildx build --output=type=docker --tag codeberg.org/forgejo/forgejo:latest . +``` + ## Running actions tests locally To run and debug workflows from `actions/example-*`, from the root of @@ -82,6 +101,7 @@ admin permissions. But they do not need to run as root and must work fine when run as a regular user. ```sh +export FORGEJO_RUNNER_LOGS=/tmp/forgejo-end-to-end/forgejo-runner.log ./end-to-end.sh run dependencies ./end-to-end.sh actions_setup 10.0 firefox 0.0.0.0:3000 # user root / admin1234 @@ -102,7 +122,10 @@ the source directory, mimic what `.forgejo/workflows/end-to-end.yml` does. ./end-to-end.sh federation_setup 12.0 firefox 0.0.0.0:3001 # user root / admin1234 firefox 0.0.0.0:3002 # user root / admin1234 +firefox 0.0.0.0:3003 # user root / admin1234 ./end-to-end.sh federation_verify_scenario star +./end-to-end.sh federation_verify_scenario gotosocial +./end-to-end.sh federation_verify_scenario mastodon ./end-to-end.sh federation_teardown ``` diff --git a/actions/actions.sh b/actions/actions.sh index bb21e8a1..0b200824 100755 --- a/actions/actions.sh +++ b/actions/actions.sh @@ -133,7 +133,7 @@ function test_actions() { done fi - if dpkg --compare-versions $runner_version gt 6.0.1; then + if dpkg --compare-versions $runner_version gt 10.0.0; then run actions_verify_example force-rebuild fi @@ -143,7 +143,7 @@ function test_actions() { done fi - for example in echo lxc config-options cache checkout service container expression local-action docker-action if if-fail push tag push-cancel artifacts pull-request context; do + for example in echo matrix needs workflow-call lxc config-options cache cache-pull-request checkout service container expression local-action docker-action if if-fail push tag push-cancel artifacts pull-request context private-workflow-call create-runner-file; do run actions_verify_example $example done @@ -151,6 +151,10 @@ function test_actions() { run actions_verify_example cache-proxy fi + if dpkg --compare-versions $runner_version ge 8.0.0; then + run actions_verify_example shell + fi + if dpkg --compare-versions $version lt 7.1; then for example in cron; do run actions_verify_example $example @@ -172,5 +176,14 @@ function test_actions() { if dpkg --compare-versions $version ge 9.0; then run actions_verify_example schedule-noncancel fi + + if dpkg --compare-versions $version ge 14.0; then + run actions_verify_example matrix-dynamic + fi + + if dpkg --compare-versions $version ge 15.0; then + run actions_verify_example workflow-call-expansion + run actions_verify_example id-tokens + fi done } diff --git a/actions/example-automerge/.forgejo/workflows/test.yml b/actions/example-automerge/.forgejo/workflows/test.yml index 3ce5da04..7bb4ce29 100644 --- a/actions/example-automerge/.forgejo/workflows/test.yml +++ b/actions/example-automerge/.forgejo/workflows/test.yml @@ -5,7 +5,7 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm options: "--volume /srv/example:/srv/example" steps: diff --git a/actions/example-cache-proxy/getter/.forgejo/workflows/get.yml b/actions/example-cache-proxy/getter/.forgejo/workflows/get.yml index ffaf9e9d..5dc434dd 100644 --- a/actions/example-cache-proxy/getter/.forgejo/workflows/get.yml +++ b/actions/example-cache-proxy/getter/.forgejo/workflows/get.yml @@ -4,7 +4,7 @@ jobs: build: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm steps: - name: cache restore id: cachestep diff --git a/actions/example-cache-proxy/storer/.forgejo/workflows/store.yml b/actions/example-cache-proxy/storer/.forgejo/workflows/store.yml index f8d42047..db9b101a 100644 --- a/actions/example-cache-proxy/storer/.forgejo/workflows/store.yml +++ b/actions/example-cache-proxy/storer/.forgejo/workflows/store.yml @@ -4,7 +4,7 @@ jobs: build: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm steps: - name: create something run: echo SOMETHING > /usr/local/bin/something diff --git a/actions/example-cache-pull-request/.forgejo/workflows/test.yml b/actions/example-cache-pull-request/.forgejo/workflows/test.yml new file mode 100644 index 00000000..43a96d41 --- /dev/null +++ b/actions/example-cache-pull-request/.forgejo/workflows/test.yml @@ -0,0 +1,96 @@ +on: + pull_request: + types: + - opened + - closed + +jobs: + save-cache: + runs-on: docker + container: + image: data.forgejo.org/oci/node:20-bookworm + steps: + - name: cache restore + id: cachestep1 + uses: https://data.forgejo.org/actions/cache/restore@v4 + with: + path: | + /usr/local/bin/something + key: cachekey-${{ forge.event.pull_request.head.repo.full_name }} + + - name: cache hit + run: | + set -x + test "${{ steps.cachestep1.outputs.cache-hit }}" != true + + - name: create something + run: echo SOMETHING > /usr/local/bin/something + + - name: cache save + uses: https://data.forgejo.org/actions/cache/save@v4 + with: + path: | + /usr/local/bin/something + key: ${{ steps.cachestep1.outputs.cache-primary-key }} + + restore-cache: + runs-on: docker + needs: [save-cache] + container: + image: data.forgejo.org/oci/node:20-bookworm + steps: + - name: cache restore + id: cachestep2 + uses: https://data.forgejo.org/actions/cache/restore@v4 + with: + path: | + /usr/local/bin/something + key: cachekey-${{ forge.event.pull_request.head.repo.full_name }} + + - name: verify something + run: | + set -x + test SOMETHING = $(cat /usr/local/bin/something) + + - name: cache hit + run: | + set -x + test "${{ steps.cachestep2.outputs.cache-hit }}" = true + + test: + runs-on: docker + needs: [restore-cache] + container: + image: data.forgejo.org/oci/node:20-bookworm + options: "--volume /srv/example:/srv/example" + + steps: + - name: setup + shell: bash + run: | + set -x + test $FORGEJO_TOKEN = ${{ env.FORGEJO_TOKEN }} + test $FORGEJO_TOKEN = ${{ forge.token }} + export DEBIAN_FRONTEND=noninteractive ; apt-get -qq update ; apt-get install -y -qq curl git >& /dev/null + curl -sS -o /usr/local/bin/forgejo-curl.sh https://code.forgejo.org/forgejo/forgejo-curl/raw/branch/main/forgejo-curl.sh && chmod +x /usr/local/bin/forgejo-curl.sh + forgejo-curl.sh --token "$FORGEJO_TOKEN" login $FORGEJO_SERVER_URL + forgejo-curl.sh api_json $FORGEJO_SERVER_URL/api/v1/user + + - name: determine if the PR is from a fork + id: forked + run: | + set -x + if test ${{ forge.event.pull_request.base.repo.full_name }} = ${{ forge.event.pull_request.head.repo.full_name }} ; then + echo value=false >> $FORGEJO_OUTPUT + else + echo value=true >> $FORGEJO_OUTPUT + fi + + - name: save event + run: | + set -x + d=/srv/example/cache-pull-request/contexts/${{ forgejo.event.pull_request.head.repo.owner.username }}/$FORGEJO_EVENT_NAME + mkdir -p $d + cat > $d/forgejo-${{ forgejo.event.action }} <<'EOF' + ${{ toJSON(forgejo) }} + EOF diff --git a/actions/example-cache-pull-request/assert-contexts-closed.sh b/actions/example-cache-pull-request/assert-contexts-closed.sh new file mode 100755 index 00000000..4c0f8e27 --- /dev/null +++ b/actions/example-cache-pull-request/assert-contexts-closed.sh @@ -0,0 +1,9 @@ +#!/bin/bash + +set -ex + +c=$d/contexts + +for user in cache-fork-org root; do + test -f $c/$user/pull_request/forgejo-closed +done diff --git a/actions/example-cache-pull-request/assert-contexts-opened.sh b/actions/example-cache-pull-request/assert-contexts-opened.sh new file mode 100755 index 00000000..73fcccda --- /dev/null +++ b/actions/example-cache-pull-request/assert-contexts-opened.sh @@ -0,0 +1,9 @@ +#!/bin/bash + +set -ex + +c=$d/contexts + +for user in cache-fork-org root; do + test -f $c/$user/pull_request/forgejo-opened +done diff --git a/actions/example-cache-pull-request/run.sh b/actions/example-cache-pull-request/run.sh new file mode 100755 index 00000000..85020281 --- /dev/null +++ b/actions/example-cache-pull-request/run.sh @@ -0,0 +1,80 @@ +TMPDIR=$(mktemp -d) + +trap "rm -fr $TMPDIR" EXIT + +api=$url/api/v1 +export d=/srv/example/cache-pull-request + +function main() { + mkdir -p $d + + # + # open a pull request + # - from the same repository + # - from a forked repository + # + forgejo-test-helper.sh push_workflow actions/example-$example $url root example-$example setup-forgejo $token + + forgejo-curl.sh api_json --data-raw '{"username":"cache-fork-org"}' $api/orgs + forgejo-curl.sh api_json --data-raw '{"organization":"cache-fork-org"}' $api/repos/root/example-cache-pull-request/forks + + ( + cd $d + git clone $url/cache-fork-org/example-cache-pull-request fork + cd fork + git config user.email root@example.com + git config user.name username + touch file-unique-to-the-pr-branch + git add . + git commit -m 'fork change' + git push + ) + + forgejo.sh retry forgejo-curl.sh api_json --data-raw '{"title":"PR from fork","base":"main","head":"cache-fork-org:main"}' $api/repos/root/example-cache-pull-request/pulls + + ( + cd $d + git clone $url/root/example-cache-pull-request + cd example-cache-pull-request + git checkout -b other + git config user.email root@example.com + git config user.name username + touch file-unique-to-the-forked-pr + git add . + git commit -m 'other change' + git push --force -u origin other + ) + + forgejo.sh retry forgejo-curl.sh api_json --data-raw '{"title":"PR same repo","base":"main","head":"other"}' $api/repos/root/example-cache-pull-request/pulls + + export RETRY_DELAYS="10 20 60 60 60 60 60" + + # + # wait for the opened event to succeed using the cache on all pull requests + # + if ! forgejo.sh retry $EXAMPLE_DIR/assert-contexts-opened.sh; then + echo "assert-contexts-opened.sh failed; printing related logs and information:" + find $d + sed -e 's/^/[RUNNER LOGS]/' <$FORGEJO_RUNNER_LOGS + return 1 + fi + + # + # merge all pull requests + # + forgejo-curl.sh api_json $api/repos/root/example-cache-pull-request/pulls | jq -r '.[] | .number' | while read pr; do + forgejo-curl.sh api_json --data-raw '{"Do":"merge"}' $api/repos/root/example-cache-pull-request/pulls/$pr/merge + done + + # + # wait for the closed event to succeed using the cache on all pull requests + # + if ! forgejo.sh retry $EXAMPLE_DIR/assert-contexts-closed.sh; then + echo "assert-contexts-closed.sh failed; printing related logs and information:" + find $d + sed -e 's/^/[RUNNER LOGS]/' <$FORGEJO_RUNNER_LOGS + return 1 + fi +} + +main diff --git a/actions/example-cache-pull-request/runner-config.yaml b/actions/example-cache-pull-request/runner-config.yaml new file mode 100644 index 00000000..11818cc5 --- /dev/null +++ b/actions/example-cache-pull-request/runner-config.yaml @@ -0,0 +1,30 @@ + +log: + level: debug + +runner: + file: .runner + capacity: 1 + env_file: .env + timeout: 3h + insecure: false + fetch_timeout: 5s + fetch_interval: 2s + labels: ["docker:docker://code.forgejo.org/oci/node:20-bookworm"] + +cache: + enabled: true + dir: "/srv/example/cache" + host: "" + port: 0 + +container: + network: "bridge" + privileged: false + options: + workdir_parent: + valid_volumes: ["/srv/example"] + docker_host: "" + +host: + workdir_parent: diff --git a/actions/example-cache-pull-request/setup.sh b/actions/example-cache-pull-request/setup.sh new file mode 100755 index 00000000..0fb6d859 --- /dev/null +++ b/actions/example-cache-pull-request/setup.sh @@ -0,0 +1,2 @@ +mkdir -p /srv/example/cache-pull-request +FORGEJO_RUNNER_CONFIG=$EXAMPLE_DIR/runner-config.yaml forgejo-runner.sh reload diff --git a/actions/example-cache-pull-request/teardown.sh b/actions/example-cache-pull-request/teardown.sh new file mode 100755 index 00000000..b410c513 --- /dev/null +++ b/actions/example-cache-pull-request/teardown.sh @@ -0,0 +1 @@ +forgejo-runner.sh reload diff --git a/actions/example-cache/.forgejo/workflows/test.yml b/actions/example-cache/.forgejo/workflows/test.yml index a431d5f6..7acc5c59 100644 --- a/actions/example-cache/.forgejo/workflows/test.yml +++ b/actions/example-cache/.forgejo/workflows/test.yml @@ -4,7 +4,7 @@ jobs: save-cache: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm steps: - name: cache restore id: cachestep1 @@ -33,7 +33,7 @@ jobs: runs-on: docker needs: [save-cache] container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm steps: - name: cache restore id: cachestep2 diff --git a/actions/example-config-options/.forgejo/workflows/test.yml b/actions/example-config-options/.forgejo/workflows/test.yml index d9c03241..7845e441 100644 --- a/actions/example-config-options/.forgejo/workflows/test.yml +++ b/actions/example-config-options/.forgejo/workflows/test.yml @@ -8,9 +8,19 @@ jobs: steps: - run: | test -f /srv/example-config-options-volume-valid + - run: | + ! test -w /srv/example-config-options-volume-valid - run: | ! test -f /srv/example-config-options-volume-invalid - run: | + set -x test "$FROB" = "NITZ" - run: | + set -x + test "$VAR_FROM_ENV_FILE" = "VALUE_FROM_ENV_FILE" + - run: | + set -x + test "$VAR_FROM_ENV_IN_CONFIG" = "VALUE_FROM_ENV_IN_CONFIG" + - run: | + set -x test "$(cat /etc/hostname)" = customname diff --git a/actions/example-config-options/env_file b/actions/example-config-options/env_file new file mode 100644 index 00000000..c5b811ba --- /dev/null +++ b/actions/example-config-options/env_file @@ -0,0 +1 @@ +VAR_FROM_ENV_FILE=VALUE_FROM_ENV_FILE diff --git a/actions/example-config-options/runner-config.yaml b/actions/example-config-options/runner-config.yaml index 0daf906f..37b7b0ae 100644 --- a/actions/example-config-options/runner-config.yaml +++ b/actions/example-config-options/runner-config.yaml @@ -6,7 +6,9 @@ log: runner: file: .runner capacity: 1 - env_file: .env + envs: + VAR_FROM_ENV_IN_CONFIG: VALUE_FROM_ENV_IN_CONFIG + env_file: env_file timeout: 3h insecure: true fetch_timeout: 5s @@ -22,7 +24,7 @@ cache: container: network: "" privileged: false - options: "--volume /srv/example-config-options-volume-valid:/srv/example-config-options-volume-valid --volume /srv/example-config-options-volume-invalid:/srv/example-config-options-volume-invalid --env FROB=NITZ" + options: "--volume /srv/example-config-options-volume-valid:/srv/example-config-options-volume-valid:ro --volume /srv/example-config-options-volume-invalid:/srv/example-config-options-volume-invalid --env FROB=NITZ" workdir_parent: valid_volumes: ["/srv/example-config-options-volume-valid"] docker_host: "" diff --git a/actions/example-config-options/setup.sh b/actions/example-config-options/setup.sh index d9f6ea9c..1e62e683 100755 --- a/actions/example-config-options/setup.sh +++ b/actions/example-config-options/setup.sh @@ -1,3 +1,6 @@ >/srv/example-config-options-volume-valid >/srv/example-config-options-volume-invalid -FORGEJO_RUNNER_CONFIG=$EXAMPLE_DIR/runner-config.yaml forgejo-runner.sh reload +TMPDIR=$(mktemp -d) +cp $EXAMPLE_DIR/runner-config.yaml $EXAMPLE_DIR/env_file $TMPDIR +sed -i -e "s|env_file:.*|env_file: $TMPDIR/env_file|" $TMPDIR/runner-config.yaml +FORGEJO_RUNNER_CONFIG=$TMPDIR/runner-config.yaml forgejo-runner.sh reload diff --git a/actions/example-container/.forgejo/workflows/test.yml b/actions/example-container/.forgejo/workflows/test.yml index ded75cd8..ecf04290 100644 --- a/actions/example-container/.forgejo/workflows/test.yml +++ b/actions/example-container/.forgejo/workflows/test.yml @@ -3,6 +3,6 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/alpine:3.21 + image: data.forgejo.org/oci/alpine:3.23 steps: - run: grep Alpine /etc/os-release diff --git a/actions/example-context/.forgejo/workflows/test.yml b/actions/example-context/.forgejo/workflows/test.yml index a894bfd2..07f80fa9 100644 --- a/actions/example-context/.forgejo/workflows/test.yml +++ b/actions/example-context/.forgejo/workflows/test.yml @@ -4,7 +4,7 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm volumes: - /srv/example:/srv/example steps: @@ -15,174 +15,240 @@ jobs: test "$CI" = true test "$CI" = "${{ env.CI }}" - - name: GITHUB_ACTION + - name: FORGEJO_ACTION run: | set -x - echo "$GITHUB_ACTION" | grep -E '^[0-9]+$' - test "$GITHUB_ACTION" = "${{ env.GITHUB_ACTION }}" - test "$GITHUB_ACTION" = "${{ github.ACTION }}" + echo "$FORGEJO_ACTION" | grep -E '^[0-9]+$' + test "$FORGEJO_ACTION" = "${{ env.FORGEJO_ACTION }}" + test "$FORGEJO_ACTION" = "${{ github.ACTION }}" + test "$FORGEJO_ACTION" = "${{ forge.ACTION }}" + test "$FORGEJO_ACTION" = "${{ forgejo.ACTION }}" + test "$FORGEJO_ACTION" = "$GITHUB_ACTION" # See also actions/example-local-action/.forgejo/local-action/action.yml - - name: GITHUB_ACTION_PATH + - name: FORGEJO_ACTION_PATH run: | set -x - test -z "$GITHUB_ACTION_PATH" - test "$GITHUB_ACTION_PATH" = "${{ env.GITHUB_ACTION_PATH }}" - test "$GITHUB_ACTION_PATH" = "${{ github.ACTION_PATH }}" + test -z "$FORGEJO_ACTION_PATH" + test "$FORGEJO_ACTION_PATH" = "${{ env.FORGEJO_ACTION_PATH }}" + test "$FORGEJO_ACTION_PATH" = "${{ github.ACTION_PATH }}" + test "$FORGEJO_ACTION_PATH" = "${{ forge.ACTION_PATH }}" + test "$FORGEJO_ACTION_PATH" = "${{ forgejo.ACTION_PATH }}" + test "$FORGEJO_ACTION_PATH" = "$GITHUB_ACTION_PATH" - name: when running an action - if: ${{ env.GITHUB_ACTIONS }} + if: ${{ env.FORGEJO_ACTIONS }} uses: SELF@main with: input-one: "otherone" - - name: GITHUB_ACTION_REPOSITORY - run: test -f /srv/example/example-context/GITHUB_ACTION_REPOSITORY + - name: FORGEJO_ACTION_REPOSITORY + run: test -f /srv/example/example-context/FORGEJO_ACTION_REPOSITORY - - name: GITHUB_ACTION_PATH - run: test -f /srv/example/example-context/GITHUB_ACTION_PATH + - name: FORGEJO_ACTION_PATH + run: test -f /srv/example/example-context/FORGEJO_ACTION_PATH - - name: GITHUB_ACTIONS + - name: FORGEJO_ACTIONS run: | set -x - test "$GITHUB_ACTIONS" = true - test "$GITHUB_ACTIONS" = "${{ env.GITHUB_ACTIONS }}" + test "$FORGEJO_ACTIONS" = true + test "$FORGEJO_ACTIONS" = "${{ env.FORGEJO_ACTIONS }}" + test "$FORGEJO_ACTIONS" = "$GITHUB_ACTIONS" - - name: GITHUB_ACTOR + - name: FORGEJO_ACTOR run: | set -x - test "$GITHUB_ACTOR" - test "$GITHUB_ACTOR" = "${{ env.GITHUB_ACTOR }}" - test "$GITHUB_ACTOR" = "${{ github.ACTOR }}" + test "$FORGEJO_ACTOR" + test "$FORGEJO_ACTOR" = "${{ env.FORGEJO_ACTOR }}" + test "$FORGEJO_ACTOR" = "${{ github.ACTOR }}" + test "$FORGEJO_ACTOR" = "${{ forge.ACTOR }}" + test "$FORGEJO_ACTOR" = "${{ forgejo.ACTOR }}" + test "$FORGEJO_ACTOR" = "$GITHUB_ACTOR" - - name: GITHUB_API_URL + - name: FORGEJO_API_URL shell: bash run: | set -x - [[ "$GITHUB_API_URL" =~ /api/v1$ ]] - test "$GITHUB_API_URL" = "${{ env.GITHUB_API_URL }}" - test "$GITHUB_API_URL" = "${{ github.API_URL }}" + [[ "$FORGEJO_API_URL" =~ /api/v1$ ]] + test "$FORGEJO_API_URL" = "${{ env.FORGEJO_API_URL }}" + test "$FORGEJO_API_URL" = "${{ github.API_URL }}" + test "$FORGEJO_API_URL" = "${{ forge.API_URL }}" + test "$FORGEJO_API_URL" = "${{ forgejo.API_URL }}" + test "$FORGEJO_API_URL" = "$GITHUB_API_URL" # See also actions/example-pull-request/.forgejo/workflows/test.yml - - name: GITHUB_BASE_REF + - name: FORGEJO_BASE_REF run: | set -x - test -z "$GITHUB_BASE_REF" - test "$GITHUB_BASE_REF" = "${{ env.GITHUB_BASE_REF }}" - test "$GITHUB_BASE_REF" = "${{ github.BASE_REF }}" + test -z "$FORGEJO_BASE_REF" + test "$FORGEJO_BASE_REF" = "${{ env.FORGEJO_BASE_REF }}" + test "$FORGEJO_BASE_REF" = "${{ github.BASE_REF }}" + test "$FORGEJO_BASE_REF" = "${{ forge.BASE_REF }}" + test "$FORGEJO_BASE_REF" = "${{ forgejo.BASE_REF }}" + test "$FORGEJO_BASE_REF" = "$GITHUB_BASE_REF" # See also actions/example-pull-request/.forgejo/workflows/test.yml - - name: GITHUB_HEAD_REF + - name: FORGEJO_HEAD_REF run: | set -x - test -z "$GITHUB_HEAD_REF" - test "$GITHUB_HEAD_REF" = "${{ env.GITHUB_HEAD_REF }}" - test "$GITHUB_HEAD_REF" = "${{ github.HEAD_REF }}" + test -z "$FORGEJO_HEAD_REF" + test "$FORGEJO_HEAD_REF" = "${{ env.FORGEJO_HEAD_REF }}" + test "$FORGEJO_HEAD_REF" = "${{ github.HEAD_REF }}" + test "$FORGEJO_HEAD_REF" = "${{ forge.HEAD_REF }}" + test "$FORGEJO_HEAD_REF" = "${{ forgejo.HEAD_REF }}" + test "$FORGEJO_HEAD_REF" = "$GITHUB_HEAD_REF" - - name: GITHUB_ENV + - name: FORGEJO_ENV run: | set -x - test -f "$GITHUB_ENV" - test "$GITHUB_ENV" = "${{ env.GITHUB_ENV }}" + test -f "$FORGEJO_ENV" + test "$FORGEJO_ENV" = "${{ env.FORGEJO_ENV }}" + test "$FORGEJO_ENV" = "$GITHUB_ENV" - - name: GITHUB_EVENT_NAME + - name: FORGEJO_EVENT_NAME run: | set -x - test "$GITHUB_EVENT_NAME" = push - test "$GITHUB_EVENT_NAME" = "${{ env.GITHUB_EVENT_NAME }}" - test "$GITHUB_EVENT_NAME" = "${{ github.EVENT_NAME }}" + test "$FORGEJO_EVENT_NAME" = push + test "$FORGEJO_EVENT_NAME" = "${{ env.FORGEJO_EVENT_NAME }}" + test "$FORGEJO_EVENT_NAME" = "${{ github.EVENT_NAME }}" + test "$FORGEJO_EVENT_NAME" = "${{ forge.EVENT_NAME }}" + test "$FORGEJO_EVENT_NAME" = "${{ forgejo.EVENT_NAME }}" + test "$FORGEJO_EVENT_NAME" = "$GITHUB_EVENT_NAME" - - name: GITHUB_JOB + - name: FORGEJO_JOB run: | set -x - test "$GITHUB_JOB" = test - test "$GITHUB_JOB" = "${{ env.GITHUB_JOB }}" - test "$GITHUB_JOB" = "${{ github.JOB }}" + test "$FORGEJO_JOB" = test + test "$FORGEJO_JOB" = "${{ env.FORGEJO_JOB }}" + test "$FORGEJO_JOB" = "${{ github.JOB }}" + test "$FORGEJO_JOB" = "${{ forge.JOB }}" + test "$FORGEJO_JOB" = "${{ forgejo.JOB }}" + test "$FORGEJO_JOB" = "$GITHUB_JOB" - - name: GITHUB_OUTPUT + - name: FORGEJO_OUTPUT run: | set -x - test -f "$GITHUB_OUTPUT" - test "$GITHUB_OUTPUT" = "${{ env.GITHUB_OUTPUT }}" + test -f "$FORGEJO_OUTPUT" + test "$FORGEJO_OUTPUT" = "${{ env.FORGEJO_OUTPUT }}" + test "$FORGEJO_OUTPUT" = "$GITHUB_OUTPUT" - - name: GITHUB_PATH + - name: FORGEJO_PATH run: | set -x - test -f "$GITHUB_PATH" - test "$GITHUB_PATH" = "${{ env.GITHUB_PATH }}" + test -f "$FORGEJO_PATH" + test "$FORGEJO_PATH" = "${{ env.FORGEJO_PATH }}" + test "$FORGEJO_PATH" = "$GITHUB_PATH" - - name: GITHUB_REF + - name: FORGEJO_REF shell: bash run: | set -x - [[ "$GITHUB_REF" =~ ^refs/ ]] - test "$GITHUB_REF" = "${{ env.GITHUB_REF }}" - test "$GITHUB_REF" = "${{ github.REF }}" + [[ "$FORGEJO_REF" =~ ^refs/ ]] + test "$FORGEJO_REF" = "${{ env.FORGEJO_REF }}" + test "$FORGEJO_REF" = "${{ github.REF }}" + test "$FORGEJO_REF" = "${{ forge.REF }}" + test "$FORGEJO_REF" = "${{ forgejo.REF }}" + test "$FORGEJO_REF" = "$GITHUB_REF" - - name: GITHUB_REF_NAME + - name: FORGEJO_REF_NAME shell: bash run: | set -x - ! [[ "$GITHUB_REF_NAME" =~ ^refs/ ]] - test "$GITHUB_REF_NAME" = "${{ env.GITHUB_REF_NAME }}" - test "$GITHUB_REF_NAME" = "${{ github.REF_NAME }}" + ! [[ "$FORGEJO_REF_NAME" =~ ^refs/ ]] + test "$FORGEJO_REF_NAME" = "${{ env.FORGEJO_REF_NAME }}" + test "$FORGEJO_REF_NAME" = "${{ github.REF_NAME }}" + test "$FORGEJO_REF_NAME" = "${{ forge.REF_NAME }}" + test "$FORGEJO_REF_NAME" = "${{ forgejo.REF_NAME }}" + test "$FORGEJO_REF_NAME" = "$GITHUB_REF_NAME" - - name: GITHUB_REPOSITORY + - name: FORGEJO_REPOSITORY run: | set -x - test "$GITHUB_REPOSITORY" = root/example-context - test "$GITHUB_REPOSITORY" = "${{ env.GITHUB_REPOSITORY }}" - test "$GITHUB_REPOSITORY" = "${{ github.REPOSITORY }}" + test "$FORGEJO_REPOSITORY" = root/example-context + test "$FORGEJO_REPOSITORY" = "${{ env.FORGEJO_REPOSITORY }}" + test "$FORGEJO_REPOSITORY" = "${{ github.REPOSITORY }}" + test "$FORGEJO_REPOSITORY" = "${{ forge.REPOSITORY }}" + test "$FORGEJO_REPOSITORY" = "${{ forgejo.REPOSITORY }}" + test "$FORGEJO_REPOSITORY" = "$GITHUB_REPOSITORY" - - name: GITHUB_REPOSITORY_OWNER + - name: FORGEJO_REPOSITORY_OWNER run: | set -x - test "$GITHUB_REPOSITORY_OWNER" = root - test "$GITHUB_REPOSITORY_OWNER" = "${{ env.GITHUB_REPOSITORY_OWNER }}" - test "$GITHUB_REPOSITORY_OWNER" = "${{ github.REPOSITORY_OWNER }}" + test "$FORGEJO_REPOSITORY_OWNER" = root + test "$FORGEJO_REPOSITORY_OWNER" = "${{ env.FORGEJO_REPOSITORY_OWNER }}" + test "$FORGEJO_REPOSITORY_OWNER" = "${{ github.REPOSITORY_OWNER }}" + test "$FORGEJO_REPOSITORY_OWNER" = "${{ forge.REPOSITORY_OWNER }}" + test "$FORGEJO_REPOSITORY_OWNER" = "${{ forgejo.REPOSITORY_OWNER }}" + test "$FORGEJO_REPOSITORY_OWNER" = "$GITHUB_REPOSITORY_OWNER" - - name: GITHUB_RUN_NUMBER + - name: FORGEJO_RUN_NUMBER run: | set -x - echo "$GITHUB_RUN_NUMBER" | grep -E '^[0-9]+$' - test "$GITHUB_RUN_NUMBER" = "${{ env.GITHUB_RUN_NUMBER }}" - test "$GITHUB_RUN_NUMBER" = "${{ github.RUN_NUMBER }}" + echo "$FORGEJO_RUN_NUMBER" | grep -E '^[0-9]+$' + test "$FORGEJO_RUN_NUMBER" = "${{ env.FORGEJO_RUN_NUMBER }}" + test "$FORGEJO_RUN_NUMBER" = "${{ github.RUN_NUMBER }}" + test "$FORGEJO_RUN_NUMBER" = "${{ forge.RUN_NUMBER }}" + test "$FORGEJO_RUN_NUMBER" = "${{ forgejo.RUN_NUMBER }}" + test "$FORGEJO_RUN_NUMBER" = "$GITHUB_RUN_NUMBER" - - name: GITHUB_SERVER_URL + - name: FORGEJO_RUN_ID + run: | + set -x + echo "$FORGEJO_RUN_ID" | grep -E '^[0-9]+$' + test "$FORGEJO_RUN_ID" = "${{ env.FORGEJO_RUN_ID }}" + test "$FORGEJO_RUN_ID" = "${{ github.RUN_ID }}" + test "$FORGEJO_RUN_ID" = "${{ forge.RUN_ID }}" + test "$FORGEJO_RUN_ID" = "${{ forgejo.RUN_ID }}" + test "$FORGEJO_RUN_ID" = "$GITHUB_RUN_ID" + + - name: FORGEJO_SERVER_URL shell: bash run: | set -x - [[ "$GITHUB_SERVER_URL" =~ ^http ]] - test "$GITHUB_SERVER_URL" = "${{ env.GITHUB_SERVER_URL }}" - test "$GITHUB_SERVER_URL" = "${{ github.SERVER_URL }}" + [[ "$FORGEJO_SERVER_URL" =~ ^http ]] + test "$FORGEJO_SERVER_URL" = "${{ env.FORGEJO_SERVER_URL }}" + test "$FORGEJO_SERVER_URL" = "${{ github.SERVER_URL }}" + test "$FORGEJO_SERVER_URL" = "${{ forge.SERVER_URL }}" + test "$FORGEJO_SERVER_URL" = "${{ forgejo.SERVER_URL }}" + test "$FORGEJO_SERVER_URL" = "$GITHUB_SERVER_URL" - - name: GITHUB_SHA + - name: FORGEJO_SHA run: | set -x - test "$GITHUB_SHA" - test "$GITHUB_SHA" = "${{ env.GITHUB_SHA }}" - test "$GITHUB_SHA" = "${{ github.SHA }}" + test "$FORGEJO_SHA" + test "$FORGEJO_SHA" = "${{ env.FORGEJO_SHA }}" + test "$FORGEJO_SHA" = "${{ github.SHA }}" + test "$FORGEJO_SHA" = "${{ forge.SHA }}" + test "$FORGEJO_SHA" = "${{ forgejo.SHA }}" + test "$FORGEJO_SHA" = "$GITHUB_SHA" - - name: GITHUB_STEP_SUMMARY + - name: FORGEJO_STEP_SUMMARY run: | set -x - test -f "$GITHUB_STEP_SUMMARY" - test "$GITHUB_STEP_SUMMARY" = "${{ env.GITHUB_STEP_SUMMARY }}" + test -f "$FORGEJO_STEP_SUMMARY" + test "$FORGEJO_STEP_SUMMARY" = "${{ env.FORGEJO_STEP_SUMMARY }}" + test "$FORGEJO_STEP_SUMMARY" = "$GITHUB_STEP_SUMMARY" # See also actions/example-pull-request/.forgejo/workflows/test.yml - - name: GITHUB_TOKEN + - name: FORGEJO_TOKEN run: | set -x - test "$GITHUB_TOKEN" - test "$GITHUB_TOKEN" = "${{ env.GITHUB_TOKEN }}" - test "$GITHUB_TOKEN" = "${{ github.TOKEN }}" + test "$FORGEJO_TOKEN" + test "$FORGEJO_TOKEN" = "${{ env.FORGEJO_TOKEN }}" + test "$FORGEJO_TOKEN" = "${{ github.TOKEN }}" + test "$FORGEJO_TOKEN" = "${{ forge.TOKEN }}" + test "$FORGEJO_TOKEN" = "${{ forgejo.TOKEN }}" + test "$FORGEJO_TOKEN" = "$GITHUB_TOKEN" - - name: GITHUB_WORKSPACE + - name: FORGEJO_WORKSPACE run: | set -x - test -d "$GITHUB_WORKSPACE" - test "$GITHUB_WORKSPACE" = "${{ env.GITHUB_WORKSPACE }}" - test "$GITHUB_WORKSPACE" = "${{ github.WORKSPACE }}" + test -d "$FORGEJO_WORKSPACE" + test "$FORGEJO_WORKSPACE" = "${{ env.FORGEJO_WORKSPACE }}" + test "$FORGEJO_WORKSPACE" = "${{ github.WORKSPACE }}" + test "$FORGEJO_WORKSPACE" = "${{ forge.WORKSPACE }}" + test "$FORGEJO_WORKSPACE" = "${{ forgejo.WORKSPACE }}" + test "$FORGEJO_WORKSPACE" = "$GITHUB_WORKSPACE" - name: RUNNER_ARCH run: | @@ -194,11 +260,10 @@ jobs: set -x test "$RUNNER_OS" = Linux - # runner 3.3.0 $RUNNER_TOOL_CACHE is not an existing directory - # - name: RUNNER_TOOL_CACHE - # run: | - # set -x - # test -d "$RUNNER_TOOL_CACHE" + - name: RUNNER_TOOL_CACHE + run: | + set -x + test "$RUNNER_TOOL_CACHE" - name: RUNNER_TEMP run: | diff --git a/actions/example-context/action-for-context/action.yml b/actions/example-context/action-for-context/action.yml index dcb8f2b7..e675d6ca 100644 --- a/actions/example-context/action-for-context/action.yml +++ b/actions/example-context/action-for-context/action.yml @@ -6,18 +6,27 @@ inputs: runs: using: "composite" steps: - - name: GITHUB_ACTION_REPOSITORY + - name: FORGEJO_ACTION_REPOSITORY run: | set -x - test "$GITHUB_ACTION_REPOSITORY" = root/action-for-context - test "$GITHUB_ACTION_REPOSITORY" = "${{ env.GITHUB_ACTION_REPOSITORY }}" - test "$GITHUB_ACTION_REPOSITORY" = "${{ github.ACTION_REPOSITORY }}" - touch /srv/example/example-context/GITHUB_ACTION_REPOSITORY + test "$FORGEJO_ACTION_REPOSITORY" = root/action-for-context + test "$FORGEJO_ACTION_REPOSITORY" = "${{ env.FORGEJO_ACTION_REPOSITORY }}" + test "$FORGEJO_ACTION_REPOSITORY" = "${{ github.ACTION_REPOSITORY }}" + test "$FORGEJO_ACTION_REPOSITORY" = "${{ forge.ACTION_REPOSITORY }}" + test "$FORGEJO_ACTION_REPOSITORY" = "${{ forgejo.ACTION_REPOSITORY }}" + test "$FORGEJO_ACTION_REPOSITORY" = "$GITHUB_ACTION_REPOSITORY" + touch /srv/example/example-context/FORGEJO_ACTION_REPOSITORY - - name: GITHUB_ACTION_PATH + - name: FORGEJO_ACTION_PATH shell: bash run: | set -x - [[ "$GITHUB_ACTION_PATH" =~ action-for-context@main$ ]] - test "$GITHUB_ACTION_PATH" = "${{ github.ACTION_PATH }}" - touch /srv/example/example-context/GITHUB_ACTION_PATH + # prior to Forgejo runner 8.0.0 the action path is built out of the file path. + # with Forgejo runner 8.0.0 and above is it a 64 character hash string + # e.g. /var/run/act/actions/1b/5c1802fa47e35716c2a0977bc907049d31aef29191cba400011c0b38b52d12 + [[ "$FORGEJO_ACTION_PATH" =~ action-for-context@main$ ]] || [[ "$FORGEJO_ACTION_PATH" =~ /[0-9a-f]{2}/[0-9a-f]{62}$ ]] + test "$FORGEJO_ACTION_PATH" = "${{ github.ACTION_PATH }}" + test "$FORGEJO_ACTION_PATH" = "${{ forge.ACTION_PATH }}" + test "$FORGEJO_ACTION_PATH" = "${{ forgejo.ACTION_PATH }}" + test "$FORGEJO_ACTION_PATH" = "$GITHUB_ACTION_PATH" + touch /srv/example/example-context/FORGEJO_ACTION_PATH diff --git a/actions/example-create-runner-file/.forgejo/workflows/test.yaml b/actions/example-create-runner-file/.forgejo/workflows/test.yaml new file mode 100644 index 00000000..e44397dd --- /dev/null +++ b/actions/example-create-runner-file/.forgejo/workflows/test.yaml @@ -0,0 +1,9 @@ +on: + push: + +jobs: + test: + runs-on: create-runner-file + steps: + - run: | + echo "OK" diff --git a/actions/example-create-runner-file/run.sh b/actions/example-create-runner-file/run.sh new file mode 100644 index 00000000..637132e5 --- /dev/null +++ b/actions/example-create-runner-file/run.sh @@ -0,0 +1,40 @@ +source "lib/lib.sh" + +api="$url/api/v1" + +function main() { + local repo + repo="root/example-$example" + + secret="$(openssl rand -hex 20)" + runner_name="runner-$(openssl rand -hex 5)" + + create_offline_registration_token "$runner_name" root "$secret" + + # Changing to $DIR is necessary so that `.runner` gets created there. Otherwise, `forgejo-runner` would not pick it up. + pushd "$DIR" || exit 1 + ./forgejo-runner -c "$EXAMPLE_DIR/runner-config.yaml" create-runner-file --instance "http://$IP:3000" --name "$runner_name" --secret "$secret" --connect + popd || exit 1 + + FORGEJO_RUNNER_CONFIG="$EXAMPLE_DIR/runner-config.yaml" forgejo-runner.sh reload + + label_count=$(jq '.labels | length ' "$DIR/.runner") + if [[ "$label_count" != "1" ]] ; then + echo "Unexpected number of labels in .runner file: $label_count instead of 1" >&2 + exit 1 + fi + + runner_label=$(jq -r '.labels[0]' "$DIR/.runner") + if [[ "$runner_label" != "create-runner-file:docker://code.forgejo.org/oci/node:24-trixie" ]] ; then + echo "Unexpected runner label: '$runner_label' instead of create-runner-file:docker://code.forgejo.org/oci/node:24-trixie" >&2 + exit 1 + fi + + forgejo-test-helper.sh push_workflow "actions/example-$example" "$url" root "example-$example" setup-forgejo "$token" + + local sha + sha="$(forgejo-test-helper.sh branch_tip "$url" "$repo" main)" + forgejo-test-helper.sh wait_success "$url" "$repo" "$sha" +} + +main diff --git a/actions/example-create-runner-file/runner-config.yaml b/actions/example-create-runner-file/runner-config.yaml new file mode 100644 index 00000000..7096728f --- /dev/null +++ b/actions/example-create-runner-file/runner-config.yaml @@ -0,0 +1,31 @@ + +log: + level: debug + +runner: + file: .runner + capacity: 1 + env_file: .env + timeout: 3h + insecure: false + fetch_timeout: 5s + fetch_interval: 2s + labels: + - "create-runner-file:docker://code.forgejo.org/oci/node:24-trixie" + +cache: + enabled: true + dir: "/srv/example/cache" + host: "" + port: 0 + +container: + network: "bridge" + privileged: false + options: + workdir_parent: + valid_volumes: ["/srv/example"] + docker_host: "" + +host: + workdir_parent: diff --git a/actions/example-cron/.forgejo/workflows/test.yml b/actions/example-cron/.forgejo/workflows/test.yml index e2748f8a..58ae70a6 100644 --- a/actions/example-cron/.forgejo/workflows/test.yml +++ b/actions/example-cron/.forgejo/workflows/test.yml @@ -6,13 +6,13 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/debian:bookworm + image: data.forgejo.org/oci/debian:trixie options: "--volume /srv/example:/srv/example" steps: - name: save context run: | - d=/srv/example/cron/contexts/$GITHUB_EVENT_NAME + d=/srv/example/cron/contexts/$FORGEJO_EVENT_NAME mkdir -p $d cat > $d/github <<'EOF' ${{ toJSON(github) }} diff --git a/actions/example-docker-action/.forgejo/workflows/test.yml b/actions/example-docker-action/.forgejo/workflows/test.yml index 6bc63c6d..d7ff2b98 100644 --- a/actions/example-docker-action/.forgejo/workflows/test.yml +++ b/actions/example-docker-action/.forgejo/workflows/test.yml @@ -7,13 +7,13 @@ jobs: # # This Docker action creates the file SOMEFILE ... # - - uses: https://data.forgejo.org/forgejo/test-setup-forgejo-docker@main + - uses: https://code.forgejo.org/forgejo/test-setup-forgejo-docker@main with: - args: ${{ github.workspace }}/SOMEFILE + args: ${{ forgejo.workspace }}/SOMEFILE # # ... which then also exists in the job workspace # because both docker containers are automatically # sharing the volume that contains it. # - run: | - test -f ${{ github.workspace }}/SOMEFILE + test -f ${{ forgejo.workspace }}/SOMEFILE diff --git a/actions/example-expression/.forgejo/workflows/test.yml b/actions/example-expression/.forgejo/workflows/test.yml index ab4bb646..ba37759e 100644 --- a/actions/example-expression/.forgejo/workflows/test.yml +++ b/actions/example-expression/.forgejo/workflows/test.yml @@ -23,7 +23,7 @@ jobs: if: ${{ env.KEY1 == 'nogood' }} - name: if does not skip id: conditional - run: echo 'check=good' >> $GITHUB_OUTPUT + run: echo 'check=good' >> $FORGEJO_OUTPUT if: env.KEY1 == 'value1' - name: verify if did not skip run: test ${{ steps.conditional.outputs.check }} = good @@ -98,10 +98,11 @@ jobs: set -x test "${{ fromJSON('["one","two"]')[0] }}" = 'one' - # As of act v1.13.0 this fails for real (before it pretended to work but did not) - # - name: hashFiles - # run: | - # set -x - # hash="bd52020371c038c4ad38a8d2df05dfa1a220d40fbe1ae83b63d6010cb527e531" - # test "${{ hashFiles('actions/example-expression/.forgejo/fileone.txt') }}" = $hash - # test "${{ hashFiles('actions/example-expression/.forgejo/fileone.*') }}" = $hash + - uses: actions/checkout@v4 + + - name: hashFiles + run: | + set -x + hash="aea6ca2329c852f5b480ec35e1fe09d39a6bd1b50f4f9cc38fbd4fef870dc107" + test "${{ hashFiles('.forgejo/fileone.txt') }}" = $hash + test "${{ hashFiles('.forgejo/fileone.*') }}" = $hash diff --git a/actions/example-force-rebuild/.forgejo/local-docker-action/Dockerfile b/actions/example-force-rebuild/.forgejo/local-docker-action/Dockerfile deleted file mode 100644 index 2339a39d..00000000 --- a/actions/example-force-rebuild/.forgejo/local-docker-action/Dockerfile +++ /dev/null @@ -1,5 +0,0 @@ -FROM code.forgejo.org/oci/debian:bookworm -COPY entrypoint.sh /run/entrypoint.sh -# if we rebuild, we should notice this file change -COPY input.txt /run/input.txt -ENTRYPOINT [ "/run/entrypoint.sh" ] diff --git a/actions/example-force-rebuild/.forgejo/local-docker-action/action.yml b/actions/example-force-rebuild/.forgejo/local-docker-action/action.yml deleted file mode 100644 index e53d6279..00000000 --- a/actions/example-force-rebuild/.forgejo/local-docker-action/action.yml +++ /dev/null @@ -1,6 +0,0 @@ -name: local docker action -description: local docker action, build depends on "input.txt" - -runs: - using: 'docker' - image: 'Dockerfile' diff --git a/actions/example-force-rebuild/.forgejo/local-docker-action/entrypoint.sh b/actions/example-force-rebuild/.forgejo/local-docker-action/entrypoint.sh deleted file mode 100755 index e2ee36ad..00000000 --- a/actions/example-force-rebuild/.forgejo/local-docker-action/entrypoint.sh +++ /dev/null @@ -1,3 +0,0 @@ -#! /usr/bin/env bash -set -x -exit "$(< /run/input.txt)" \ No newline at end of file diff --git a/actions/example-force-rebuild/.forgejo/local-docker-action/input.txt b/actions/example-force-rebuild/.forgejo/local-docker-action/input.txt deleted file mode 100644 index 5a944794..00000000 --- a/actions/example-force-rebuild/.forgejo/local-docker-action/input.txt +++ /dev/null @@ -1 +0,0 @@ -this file will be filled by the test \ No newline at end of file diff --git a/actions/example-force-rebuild/.forgejo/workflows/test.yml b/actions/example-force-rebuild/.forgejo/workflows/test.yml index 41510651..d6f8b3e9 100644 --- a/actions/example-force-rebuild/.forgejo/workflows/test.yml +++ b/actions/example-force-rebuild/.forgejo/workflows/test.yml @@ -1,10 +1,11 @@ ---- -on: - push: +on: [push] + jobs: - test: + ls: runs-on: docker steps: - - name: Checkout repository - uses: actions/checkout@v4 - - uses: ./.forgejo/local-docker-action + - uses: https://code.forgejo.org/forgejo/test-setup-forgejo-docker@main + with: + args: ${{ forgejo.workspace }}/SOMEFILE + - run: | + test -f ${{ forgejo.workspace }}/SOMEFILE diff --git a/actions/example-force-rebuild/run.sh b/actions/example-force-rebuild/run.sh index d82890a3..b783b3a2 100755 --- a/actions/example-force-rebuild/run.sh +++ b/actions/example-force-rebuild/run.sh @@ -19,24 +19,51 @@ function run() { forgejo-test-helper.sh wait_$expected $url $repo $sha } +function get_remote_image() { + docker image ls --format='{{ .Repository }}' | grep '^runner-remote-docker-action' +} + +function remove_remote_images() { + docker image ls --format='{{ .Repository }}' | grep '^runner-remote-docker-action' | while read image; do + docker rmi $image + done +} + +function was_built() { + grep --quiet 'docker build -t runner-remote-docker-action' $FORGEJO_RUNNER_LOGS +} + function main() { local dir=$TMPDIR/repository cp -a $EXAMPLE_DIR $dir - # set up passing docker action - echo "0" >$dir/.forgejo/local-docker-action/input.txt - setup_with_rebuild - run $dir success + remove_remote_images - # change docker action to fail - echo "1" >$dir/.forgejo/local-docker-action/input.txt - # ... but without a rebuild, it should still pass + : + : Run one + : setup_without_rebuild run $dir success + local image="$(get_remote_image)" + test "$image" + was_built - # now the action should fail + : + : Run two: verify the image was not rebuilt + : + setup_without_rebuild # resets the logs + run $dir success + test "$image" = "$(get_remote_image)" + ! was_built + + : + : Run two: verify the image was rebuilt and + : the image name stayed the same + : setup_with_rebuild - run $dir failure + run $dir success + test "$image" = "$(get_remote_image)" + was_built } main diff --git a/actions/example-force-rebuild/runner-config-with-rebuild.yml b/actions/example-force-rebuild/runner-config-with-rebuild.yml index c99a2300..6dee7b32 100644 --- a/actions/example-force-rebuild/runner-config-with-rebuild.yml +++ b/actions/example-force-rebuild/runner-config-with-rebuild.yml @@ -1,5 +1,6 @@ log: - level: debug + level: trace + job_level: trace runner: file: .runner diff --git a/actions/example-force-rebuild/runner-config-without-rebuild.yml b/actions/example-force-rebuild/runner-config-without-rebuild.yml index 793fbcd6..8d9f71bb 100644 --- a/actions/example-force-rebuild/runner-config-without-rebuild.yml +++ b/actions/example-force-rebuild/runner-config-without-rebuild.yml @@ -1,5 +1,6 @@ log: - level: debug + level: trace + job_level: trace runner: file: .runner diff --git a/actions/example-id-tokens/.forgejo/workflows/test.yml b/actions/example-id-tokens/.forgejo/workflows/test.yml new file mode 100644 index 00000000..31c49156 --- /dev/null +++ b/actions/example-id-tokens/.forgejo/workflows/test.yml @@ -0,0 +1,78 @@ +on: [push] + +env: + JWT_CLI_VERSION: 6.2.0 # renovate: datasource=github-releases depName=jwt-cli packageName=mike-engel/jwt-cli + +jobs: + generation-allowed: + enable-openid-connect: true + runs-on: docker + container: + image: data.forgejo.org/oci/ci:1 + steps: + - run: curl -L -o jwt-linux.tar.gz https://github.com/mike-engel/jwt-cli/releases/download/${{ env.JWT_CLI_VERSION }}/jwt-linux-musl.tar.gz && tar -xvzf ./jwt-linux.tar.gz && chmod a+x ./jwt + - name: validate token generation works + run: | + RAW_JWT=$(curl -H "Authorization: Bearer $ACTIONS_ID_TOKEN_REQUEST_TOKEN" "$ACTIONS_ID_TOKEN_REQUEST_URL&audience=exampleAudience" | jq -r ".value") + if [[ -z "RAW_JWT" ]]; then + echo "Error: RAW_JWT should be set" + exit 1 + fi + + DECODED_JWT_BODY=$(echo $RAW_JWT | jq -R 'split(".") | .[1] | @base64d | fromjson') + if [[ -z "$DECODED_JWT_BODY" ]]; then + echo "Error: DECODED_JWT_BODY should be set" + exit 1 + fi + + ISS=$(echo $DECODED_JWT_BODY | jq -r '.iss') + if [[ -z "$ISS" ]]; then + echo "Error: ISS should be set" + exit 1 + fi + + curl "$ISS/.well-known/keys" > jwks.json + JWKS=$(cat ./jwks.json) + if [[ -z "$JWKS" ]]; then + echo "Error: JWKS should be set" + exit 1 + fi + + # Verify that the JWT decodes with the JWKS data + ./jwt decode -S @./jwks.json -A RS256 $RAW_JWT || (echo "Error: failed signature validation" && exit 1) + + WORKFLOW=$(echo $DECODED_JWT_BODY | jq -r '.workflow') + AUD=$(echo $DECODED_JWT_BODY | jq -r '.aud') + EVENT_NAME=$(echo $DECODED_JWT_BODY | jq -r '.event_name') + SUB=$(echo $DECODED_JWT_BODY | jq -r '.sub') + if [[ "$WORKFLOW" != "test.yml" ]]; then + echo "Error: WORKFLOW should be test.yml but is $WORKFLOW" + exit 1 + fi + if [[ "$AUD" != "exampleAudience" ]]; then + echo "Error: AUD should be exampleAudience but is $AUD" + exit 1 + fi + if [[ "$EVENT_NAME" != "push" ]]; then + echo "Error: EVENT_NAME should be push but is $EVENT_NAME" + exit 1 + fi + if [[ "$SUB" != "repo:root/example-id-tokens:ref:refs/heads/main" ]]; then + echo "Error: SUB should be repo:root/example-id-tokens:ref:refs/heads/main but is $SUB" + exit 1 + fi + + generation-not-allowed: + enable-openid-connect: false + runs-on: docker + steps: + - name: check variables are unset + run: | + if [[ -n "$ACTIONS_ID_TOKEN_REQUEST_TOKEN" ]]; then + echo "Error: ACTIONS_ID_TOKEN_REQUEST_TOKEN should be unset" + exit 1 + fi + if [[ -n "$ACTIONS_ID_TOKEN_REQUEST_URL" ]]; then + echo "Error: ACTIONS_ID_TOKEN_REQUEST_TOKEN should be unset" + exit 1 + fi diff --git a/actions/example-if/.forgejo/workflows/test.yml b/actions/example-if/.forgejo/workflows/test.yml index cc9401ce..355d9f20 100644 --- a/actions/example-if/.forgejo/workflows/test.yml +++ b/actions/example-if/.forgejo/workflows/test.yml @@ -8,7 +8,7 @@ jobs: - name: if true if: true id: if_true - run: echo 'check=good' >> $GITHUB_OUTPUT + run: echo 'check=good' >> $FORGEJO_OUTPUT - name: verify if true was run run: test ${{ steps.if_true.outputs.check }} = good diff --git a/actions/example-local-action/.forgejo/local-action/action.yml b/actions/example-local-action/.forgejo/local-action/action.yml index 79637578..900bc1c1 100644 --- a/actions/example-local-action/.forgejo/local-action/action.yml +++ b/actions/example-local-action/.forgejo/local-action/action.yml @@ -13,10 +13,10 @@ outputs: runs: using: "composite" steps: - - name: GITHUB_ACTION_PATH + - name: FORGEJO_ACTION_PATH run: | set -x - test "$(basename $GITHUB_ACTION_PATH)" = local-action - test "$GITHUB_ACTION_PATH" = "${{ env.GITHUB_ACTION_PATH }}" + test -e "$FORGEJO_ACTION_PATH" + test "$FORGEJO_ACTION_PATH" = "${{ env.FORGEJO_ACTION_PATH }}" - - run: echo key=${{ inputs.input-two-required }} >> $GITHUB_OUTPUT + - run: echo key=${{ inputs.input-two-required }} >> $FORGEJO_OUTPUT diff --git a/actions/example-lxc/.forgejo/workflows/test.yml b/actions/example-lxc/.forgejo/workflows/test.yml index 5e466e72..e7aa3fd9 100644 --- a/actions/example-lxc/.forgejo/workflows/test.yml +++ b/actions/example-lxc/.forgejo/workflows/test.yml @@ -1,8 +1,16 @@ on: [push] jobs: - build: + job1: runs-on: lxc steps: - uses: https://data.forgejo.org/actions/checkout@v4 - run: systemctl --no-pager list-units + job2: + runs-on: lxc + steps: + - run: echo OK2 + job3: + runs-on: lxc + steps: + - run: echo OK3 diff --git a/actions/example-lxc/runner-config.yaml b/actions/example-lxc/runner-config.yaml index 6698ed20..617b3920 100644 --- a/actions/example-lxc/runner-config.yaml +++ b/actions/example-lxc/runner-config.yaml @@ -11,7 +11,7 @@ runner: insecure: false fetch_timeout: 5s fetch_interval: 2s - labels: ["lxc:lxc://debian:bookworm:docker"] + labels: ["lxc:lxc://debian:bookworm"] cache: enabled: false diff --git a/actions/example-matrix-dynamic/.forgejo/workflows/test.yml b/actions/example-matrix-dynamic/.forgejo/workflows/test.yml new file mode 100644 index 00000000..170a009b --- /dev/null +++ b/actions/example-matrix-dynamic/.forgejo/workflows/test.yml @@ -0,0 +1,49 @@ +on: [push] +jobs: + define-matrix: + runs-on: docker + outputs: + scalar-value: ${{ steps.define.outputs.scalar }} + array-value: ${{ steps.define.outputs.array }} + matrix-value: ${{ steps.define.outputs.matrix }} + steps: + - id: define + run: | + echo 'scalar=scalar value' >> "$FORGEJO_OUTPUT" + echo 'array=["value 1", "value 2"]' >> "$FORGEJO_OUTPUT" + echo 'matrix={"dimension-1": ["d1 v1", "d1 v2"], "dimension-2": ["d2 v1", "d2 v2"]}' >> "$GITHUB_OUTPUT" + + scalar-job: + runs-on: docker + needs: define-matrix + strategy: + matrix: + scalar: + - "${{ needs.define-matrix.outputs.scalar-value }}" + - hard-coded value + steps: + - run: | + set -x + [ "${{ matrix.scalar }}" = "scalar value" ] || [ "${{ matrix.scalar }}" = "hard-coded value" ] || exit 1 + + array-job: + runs-on: docker + needs: define-matrix + strategy: + matrix: + array: ${{ fromJSON(needs.define-matrix.outputs.array-value) }} + steps: + - run: | + set -x + [ "${{ matrix.array }}" = "value 1" ] || [ "${{ matrix.array }}" = "value 2" ] || exit 1 + + matrix-job: + runs-on: docker + needs: define-matrix + strategy: + matrix: ${{ fromJSON(needs.define-matrix.outputs.matrix-value) }} + steps: + - run: | + set -x + [ "${{ matrix.dimension-1 }}" = "d1 v1" ] || [ "${{ matrix.dimension-1 }}" = "d1 v2" ] || exit 1 + [ "${{ matrix.dimension-2 }}" = "d2 v1" ] || [ "${{ matrix.dimension-2 }}" = "d2 v2" ] || exit 1 diff --git a/actions/example-matrix-dynamic/run.sh b/actions/example-matrix-dynamic/run.sh new file mode 100644 index 00000000..18b8fc05 --- /dev/null +++ b/actions/example-matrix-dynamic/run.sh @@ -0,0 +1,10 @@ +forgejo-test-helper.sh run_workflow actions/example-$example $url root example-$example setup-forgejo $token + +# Verify that the matrix in the job was expanded correctly by checking that +# there are 9 completed jobs, by their commit statuses being present on the +# main branch's HEAD. +api=$url/api/v1 +sha=$(forgejo-curl.sh api_json $api/repos/root/example-matrix-dynamic/branches/main | jq -r ".commit.id") +num_runs=$(forgejo-curl.sh api_json $api/repos/root/example-matrix-dynamic/commits/$sha/status | jq ".total_count") +echo "Expecting 9 commit statuses, found $num_runs commit statuses" +test $num_runs = 9 diff --git a/actions/example-matrix/.forgejo/workflows/test.yml b/actions/example-matrix/.forgejo/workflows/test.yml new file mode 100644 index 00000000..34de0a59 --- /dev/null +++ b/actions/example-matrix/.forgejo/workflows/test.yml @@ -0,0 +1,12 @@ +on: [push] +jobs: + test: + runs-on: docker + name: name-${{ matrix.version }} + strategy: + matrix: + version: [1.18, 1.19] + steps: + - run: | + set -x + test "${{ matrix.version }}" diff --git a/actions/example-needs/.forgejo/workflows/test.yml b/actions/example-needs/.forgejo/workflows/test.yml new file mode 100644 index 00000000..d38a1e75 --- /dev/null +++ b/actions/example-needs/.forgejo/workflows/test.yml @@ -0,0 +1,19 @@ +on: [push] +jobs: + job1: + runs-on: docker + outputs: + job1output: ${{ steps.step1.outputs.value }} + steps: + - id: step1 + run: | + set -x + echo "value=value1" >> $FORGEJO_OUTPUT + + job2: + needs: [job1] + runs-on: docker + steps: + - run: | + set -x + test "${{ needs.job1.outputs.job1output }}" = "value1" diff --git a/actions/example-post-7-0-schedule/.forgejo/workflows/test.yml b/actions/example-post-7-0-schedule/.forgejo/workflows/test.yml index 135364aa..94eb4961 100644 --- a/actions/example-post-7-0-schedule/.forgejo/workflows/test.yml +++ b/actions/example-post-7-0-schedule/.forgejo/workflows/test.yml @@ -6,13 +6,13 @@ jobs: test: runs-on: ${{ vars.TEST_SCHEDULE_RUNSON }} container: - image: code.forgejo.org/oci/debian:bookworm + image: data.forgejo.org/oci/debian:trixie options: "--volume /srv/example:/srv/example" steps: - name: save context run: | - d=/srv/example/post-7-0-schedule/contexts/$GITHUB_EVENT_NAME + d=/srv/example/post-7-0-schedule/contexts/$FORGEJO_EVENT_NAME mkdir -p $d cat > $d/github <<'EOF' ${{ toJSON(github) }} diff --git a/actions/example-private-workflow-call/.forgejo/workflows/reusable.yaml b/actions/example-private-workflow-call/.forgejo/workflows/reusable.yaml new file mode 100644 index 00000000..48832449 --- /dev/null +++ b/actions/example-private-workflow-call/.forgejo/workflows/reusable.yaml @@ -0,0 +1,10 @@ +on: + workflow_call: + +jobs: + build: + runs-on: "docker" + container: + image: data.forgejo.org/oci/node:24-trixie + steps: + - run: echo 'OK' diff --git a/actions/example-private-workflow-call/.forgejo/workflows/test.yaml b/actions/example-private-workflow-call/.forgejo/workflows/test.yaml new file mode 100644 index 00000000..9bb279b3 --- /dev/null +++ b/actions/example-private-workflow-call/.forgejo/workflows/test.yaml @@ -0,0 +1,11 @@ +on: + push: + +jobs: + test: + # `runs-on` disables workflow expansion. We want that in this case, because then Forgejo Runner has to authenticate + # itself to access the reusable workflow. + runs-on: docker + container: + image: data.forgejo.org/oci/node:24-trixie + uses: ./.forgejo/workflows/reusable.yaml diff --git a/actions/example-private-workflow-call/run.sh b/actions/example-private-workflow-call/run.sh new file mode 100644 index 00000000..e71dc991 --- /dev/null +++ b/actions/example-private-workflow-call/run.sh @@ -0,0 +1,42 @@ +api="$url/api/v1" +export d=/srv/example/private-workflow-call + +function main() { + mkdir -p "$d" + + local repo + repo="root/example-$example" + + forgejo-test-helper.sh push_workflow "actions/example-$example" "$url" root "example-$example" setup-forgejo "$token" + + # push_workflow creates the repository and triggers a first workflow run. Wait for it to succeed. Ensures that the + # workflow is valid. + local sha + sha="$(forgejo-test-helper.sh branch_tip "$url" "$repo" main)" + forgejo-test-helper.sh wait_success "$url" "$repo" "$sha" + + # Make the repository private. That is necessary to verify that Forgejo Runner includes the correct credentials when + # cloning the workflow. + forgejo-curl.sh api_json -X PATCH --data-raw '{"private":true}' "$api/repos/root/example-$example" + + # Create a new commit that triggers a new workflow run that can be identified uniquely. + ( + cd "$d" || exit 1 + git clone "$url/root/example-$example" + cd "example-$example" || exit 1 + git config user.email root@example.com + git config user.name username + echo "A new file" > test.txt + git add . + git commit -m 'Commit a new file' + git push + ) + + # Wait for the workflow pulled from the private repository to succeed. + local new_sha + new_sha="$(forgejo-test-helper.sh branch_tip "$url" "$repo" main)" + [[ "$new_sha" != "$sha" ]] || exit 1 + forgejo-test-helper.sh wait_success "$url" "$repo" "$new_sha" +} + +main diff --git a/actions/example-private-workflow-call/setup.sh b/actions/example-private-workflow-call/setup.sh new file mode 100644 index 00000000..fd443948 --- /dev/null +++ b/actions/example-private-workflow-call/setup.sh @@ -0,0 +1 @@ +mkdir -p /srv/example/private-workflow-call diff --git a/actions/example-pull-request/.forgejo/workflows/test.yml b/actions/example-pull-request/.forgejo/workflows/test.yml index 829d9221..34a915a0 100644 --- a/actions/example-pull-request/.forgejo/workflows/test.yml +++ b/actions/example-pull-request/.forgejo/workflows/test.yml @@ -9,7 +9,7 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm options: "--volume /srv/example:/srv/example" steps: @@ -17,45 +17,45 @@ jobs: shell: bash run: | set -x - test $GITHUB_TOKEN = ${{ env.GITHUB_TOKEN }} - test $GITHUB_TOKEN = ${{ github.token }} + test $FORGEJO_TOKEN = ${{ env.FORGEJO_TOKEN }} + test $FORGEJO_TOKEN = ${{ forgejo.token }} export DEBIAN_FRONTEND=noninteractive ; apt-get -qq update ; apt-get install -y -qq curl git >& /dev/null curl -sS -o /usr/local/bin/forgejo-curl.sh https://code.forgejo.org/forgejo/forgejo-curl/raw/branch/main/forgejo-curl.sh && chmod +x /usr/local/bin/forgejo-curl.sh - forgejo-curl.sh --token "$GITHUB_TOKEN" login $GITHUB_SERVER_URL - forgejo-curl.sh api_json $GITHUB_SERVER_URL/api/v1/user + forgejo-curl.sh --token "$FORGEJO_TOKEN" login $FORGEJO_SERVER_URL + forgejo-curl.sh api_json $FORGEJO_SERVER_URL/api/v1/user - name: determine if the PR is from a fork id: forked run: | - if test ${{ github.event.pull_request.base.repo.full_name }} = ${{ github.event.pull_request.head.repo.full_name }} ; then - echo value=false >> $GITHUB_OUTPUT + if test ${{ forgejo.event.pull_request.base.repo.full_name }} = ${{ forge.event.pull_request.head.repo.full_name }} ; then + echo value=false >> $FORGEJO_OUTPUT else - echo value=true >> $GITHUB_OUTPUT + echo value=true >> $FORGEJO_OUTPUT fi # See also actions/example-context/.forgejo/workflows/test.yml - - name: env.GITHUB_BASE_REF + - name: env.FORGEJO_BASE_REF run: | set -x - test "$GITHUB_BASE_REF" = main - test "$GITHUB_BASE_REF" = "${{ env.GITHUB_BASE_REF }}" + test "$FORGEJO_BASE_REF" = main + test "$FORGEJO_BASE_REF" = "${{ env.FORGEJO_BASE_REF }}" # See also actions/example-context/.forgejo/workflows/test.yml - - name: env.GITHUB_HEAD_REF + - name: env.FORGEJO_HEAD_REF run: | set -x if ${{ steps.forked.outputs.value }} ; then - test "$GITHUB_HEAD_REF" = main + test "$FORGEJO_HEAD_REF" = main else - test "$GITHUB_HEAD_REF" = other + test "$FORGEJO_HEAD_REF" = other fi - test "$GITHUB_HEAD_REF" = "${{ env.GITHUB_HEAD_REF }}" + test "$FORGEJO_HEAD_REF" = "${{ env.FORGEJO_HEAD_REF }}" - name: secrets shell: bash run: | set -x - case $GITHUB_EVENT_NAME in + case $FORGEJO_EVENT_NAME in pull_request_target) # # all PRs: secrets @@ -76,7 +76,7 @@ jobs: fi ;; *) - echo unexpected event $GITHUB_EVENT_NAME + echo unexpected event $FORGEJO_EVENT_NAME false ;; esac @@ -95,9 +95,9 @@ jobs: # # create an issue # - base_repo=${{ github.event.pull_request.base.repo.full_name }} - forgejo-curl.sh api_json --data-raw '{"title":"ISSUE"}' $GITHUB_SERVER_URL/api/v1/repos/$base_repo/issues - url=$(echo $GITHUB_SERVER_URL | sed -e "s|://|://$GITHUB_TOKEN@|") + base_repo=${{ forgejo.event.pull_request.base.repo.full_name }} + forgejo-curl.sh api_json --data-raw '{"title":"ISSUE"}' $FORGEJO_SERVER_URL/api/v1/repos/$base_repo/issues + url=$(echo $FORGEJO_SERVER_URL | sed -e "s|://|://$FORGEJO_TOKEN@|") git clone $url/$base_repo base branch=B$RANDOM ( @@ -108,7 +108,7 @@ jobs: echo CHANGE >> README git add . git commit -m 'change' - case $GITHUB_EVENT_NAME in + case $FORGEJO_EVENT_NAME in pull_request_target|pull_request) # # repository write scope via http git passthrough @@ -117,15 +117,15 @@ jobs: # # repository write scope via the API # - assert_fail_if_forked forgejo-curl.sh api_json --data-raw '{"title":"PR","base":"main","head":"'$branch'"}' $GITHUB_SERVER_URL/api/v1/repos/$base_repo/pulls - assert_fail_if_forked forgejo-curl.sh api_json --data-raw '{"color":"#ffffff","name":"labelname"}' $GITHUB_SERVER_URL/api/v1/repos/$base_repo/labels + assert_fail_if_forked forgejo-curl.sh api_json --data-raw '{"title":"PR","base":"main","head":"'$branch'"}' $FORGEJO_SERVER_URL/api/v1/repos/$base_repo/pulls + assert_fail_if_forked forgejo-curl.sh api_json --data-raw '{"color":"#ffffff","name":"labelname"}' $FORGEJO_SERVER_URL/api/v1/repos/$base_repo/labels # # See https://codeberg.org/forgejo/forgejo/issues/1525 # - ! forgejo-curl.sh api_json --data-raw '{"new_branch_name":"B'$RANDOM'"}' $GITHUB_SERVER_URL/api/v1/repos/$base_repo/branches + ! forgejo-curl.sh api_json --data-raw '{"new_branch_name":"B'$RANDOM'"}' $FORGEJO_SERVER_URL/api/v1/repos/$base_repo/branches ;; *) - echo unexpected event $GITHUB_EVENT_NAME + echo unexpected event $FORGEJO_EVENT_NAME false ;; esac @@ -133,7 +133,7 @@ jobs: - name: save event run: | - d=/srv/example/pull-request/contexts/${{ github.event.pull_request.head.repo.owner.username }}/$GITHUB_EVENT_NAME + d=/srv/example/pull-request/contexts/${{ forgejo.event.pull_request.head.repo.owner.username }}/$FORGEJO_EVENT_NAME mkdir -p $d cat > $d/github <<'EOF' ${{ toJSON(github) }} @@ -143,7 +143,7 @@ jobs: - name: checkout the default branch if pull_request_target run: | set -x - case $GITHUB_EVENT_NAME in + case $FORGEJO_EVENT_NAME in pull_request_target) ! test -f file-unique-to-the-pr-branch ;; @@ -151,7 +151,7 @@ jobs: test -f file-unique-to-the-pr-branch ;; *) - echo unexpected event $GITHUB_EVENT_NAME + echo unexpected event $FORGEJO_EVENT_NAME false ;; esac diff --git a/actions/example-push/.forgejo/workflows/test.yml b/actions/example-push/.forgejo/workflows/test.yml index 89763f29..ebf53d1b 100644 --- a/actions/example-push/.forgejo/workflows/test.yml +++ b/actions/example-push/.forgejo/workflows/test.yml @@ -9,14 +9,14 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm volumes: - /srv/example:/srv/example steps: - name: save event run: | - d=/srv/example/push/contexts/$GITHUB_EVENT_NAME + d=/srv/example/push/contexts/$FORGEJO_EVENT_NAME mkdir -p $d cat > $d/github <<'EOF' ${{ toJSON(github) }} diff --git a/actions/example-schedule-noncancel/.forgejo/workflows/schedule_continue.yml b/actions/example-schedule-noncancel/.forgejo/workflows/schedule_continue.yml index 58156ea3..7cc5bdb3 100644 --- a/actions/example-schedule-noncancel/.forgejo/workflows/schedule_continue.yml +++ b/actions/example-schedule-noncancel/.forgejo/workflows/schedule_continue.yml @@ -5,7 +5,7 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/debian:bookworm + image: data.forgejo.org/oci/debian:trixie volumes: - /srv/example:/srv/example steps: diff --git a/actions/example-service/.forgejo/workflows/test.yml b/actions/example-service/.forgejo/workflows/test.yml index 014653aa..11132c96 100644 --- a/actions/example-service/.forgejo/workflows/test.yml +++ b/actions/example-service/.forgejo/workflows/test.yml @@ -8,7 +8,7 @@ jobs: runs-on: docker services: pgsql: - image: code.forgejo.org/oci/postgres:15 + image: data.forgejo.org/oci/postgres:15 env: POSTGRES_DB: test POSTGRES_PASSWORD: postgres @@ -23,11 +23,11 @@ jobs: simple: runs-on: docker container: - image: code.forgejo.org/oci/debian:bookworm + image: data.forgejo.org/oci/debian:trixie services: pgsql: - image: code.forgejo.org/oci/postgres:15 + image: data.forgejo.org/oci/postgres:15 env: POSTGRES_DB: test POSTGRES_PASSWORD: postgres @@ -43,7 +43,7 @@ jobs: needs: [simple] runs-on: docker container: - image: code.forgejo.org/oci/debian:bookworm + image: data.forgejo.org/oci/debian:trixie options: "--volume /srv/example-service-volume-valid:/srv/example-service-volume-valid --volume /srv/example-service-volume-invalid:/srv/example-service-volume-invalid" steps: @@ -58,12 +58,12 @@ jobs: needs: [volume-on-step] runs-on: docker container: - image: code.forgejo.org/oci/debian:bookworm + image: data.forgejo.org/oci/debian:trixie options: "--volume /srv/example-service-volume-valid:/srv/example-service-volume-valid" services: myservice: - image: code.forgejo.org/oci/debian:bookworm + image: data.forgejo.org/oci/debian:trixie options: "--volume /srv/example-service-volume-valid:/srv/example-service-volume-valid" cmd: ["bash", "-c", "echo -n SUCCESS > /srv/example-service-volume-valid ; sleep infinity"] diff --git a/actions/example-shell/.forgejo/workflows/test.yml b/actions/example-shell/.forgejo/workflows/test.yml new file mode 100644 index 00000000..5dad0b6e --- /dev/null +++ b/actions/example-shell/.forgejo/workflows/test.yml @@ -0,0 +1,87 @@ +on: [push] + +env: + ASSERT_SHELL: 'set -x ; readlink /proc/$$/exe ; readlink /proc/$$/exe | grep ' + +jobs: + default: + # docker:docker://code.forgejo.org/oci/node:22-bookworm + runs-on: docker + steps: + - name: default is bash + run: | + ${{ env.ASSERT_SHELL }} /bash + + sh-fallback: + needs: [default] + # alpine:docker://code.forgejo.org/oci/alpine:latest + runs-on: alpine + steps: + - name: default is bash but with a fallback to sh in case it does not exist + run: | + ${{ env.ASSERT_SHELL }} /busybox + + sh-fallback-with-container: + needs: [sh-fallback] + runs-on: docker + container: + image: data.forgejo.org/oci/alpine:latest + steps: + - name: default is bash but with a fallback to sh in case it does not exist + run: | + ${{ env.ASSERT_SHELL }} /busybox + + defaults-run: + needs: [sh-fallback-with-container] + # alpine:docker://code.forgejo.org/oci/alpine:latest + runs-on: alpine + defaults: + run: + shell: sh + steps: + - name: default is sh which is an alias for busybox in alpine + run: | + ${{ env.ASSERT_SHELL }} /busybox + + python: + needs: [alpine] + runs-on: docker + container: + image: data.forgejo.org/oci/python:slim + steps: + - name: python => python {0} + shell: python + run: | + print("something") + + other: + needs: [python] + runs-on: docker + container: + image: data.forgejo.org/oci/node:22-bookworm + steps: + - name: default is bash + run: | + ${{ env.ASSERT_SHELL }} /bash + + - name: bash => bash --noprofile --norc -e -o pipefail {0} + shell: bash + run: | + ${{ env.ASSERT_SHELL }} /bash + shopt -o + shopt -o | grep --quiet 'pipefail.*on' + + - name: sh => sh -e {0} + shell: sh + run: | + ${{ env.ASSERT_SHELL }} /dash + + - name: node => node {0} + shell: node + run: | + console.log("something") + + - name: dash -e {0} + shell: dash -e {0} + run: | + ${{ env.ASSERT_SHELL }} /dash diff --git a/actions/example-shell/runner-config.yaml b/actions/example-shell/runner-config.yaml new file mode 100644 index 00000000..4e4974d2 --- /dev/null +++ b/actions/example-shell/runner-config.yaml @@ -0,0 +1,32 @@ + +log: + level: debug + +runner: + file: .runner + capacity: 1 + env_file: .env + timeout: 3h + insecure: false + fetch_timeout: 5s + fetch_interval: 2s + labels: + - docker:docker://code.forgejo.org/oci/node:22-bookworm + - alpine:docker://code.forgejo.org/oci/alpine:latest + +cache: + enabled: false + dir: "" + host: "" + port: 0 + +container: + network: "" + privileged: false + options: + workdir_parent: + valid_volumes: [] + docker_host: "" + +host: + workdir_parent: diff --git a/actions/example-shell/setup.sh b/actions/example-shell/setup.sh new file mode 100755 index 00000000..9c1f5adf --- /dev/null +++ b/actions/example-shell/setup.sh @@ -0,0 +1 @@ +FORGEJO_RUNNER_CONFIG=$EXAMPLE_DIR/runner-config.yaml forgejo-runner.sh reload diff --git a/actions/example-shell/teardown.sh b/actions/example-shell/teardown.sh new file mode 100755 index 00000000..b410c513 --- /dev/null +++ b/actions/example-shell/teardown.sh @@ -0,0 +1 @@ +forgejo-runner.sh reload diff --git a/actions/example-tag/.forgejo/workflows/test.yml b/actions/example-tag/.forgejo/workflows/test.yml index c7e13570..1a2e4b91 100644 --- a/actions/example-tag/.forgejo/workflows/test.yml +++ b/actions/example-tag/.forgejo/workflows/test.yml @@ -7,14 +7,14 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm volumes: - /srv/example:/srv/example steps: - name: save event run: | - d=/srv/example/tag/contexts/$GITHUB_EVENT_NAME + d=/srv/example/tag/contexts/$FORGEJO_EVENT_NAME mkdir -p $d cat > $d/github <<'EOF' ${{ toJSON(github) }} diff --git a/actions/example-with-docker-host/.forgejo/workflows/test.yml b/actions/example-with-docker-host/.forgejo/workflows/test.yml index 6089092f..454a10da 100644 --- a/actions/example-with-docker-host/.forgejo/workflows/test.yml +++ b/actions/example-with-docker-host/.forgejo/workflows/test.yml @@ -4,7 +4,7 @@ jobs: build: runs-on: docker container: - image: code.forgejo.org/oci/docker:cli + image: data.forgejo.org/oci/docker:28-cli steps: - run: ls -l /var/run/docker.sock - run: docker ps diff --git a/actions/example-with-docker-socket/.forgejo/workflows/test.yml b/actions/example-with-docker-socket/.forgejo/workflows/test.yml index 6089092f..454a10da 100644 --- a/actions/example-with-docker-socket/.forgejo/workflows/test.yml +++ b/actions/example-with-docker-socket/.forgejo/workflows/test.yml @@ -4,7 +4,7 @@ jobs: build: runs-on: docker container: - image: code.forgejo.org/oci/docker:cli + image: data.forgejo.org/oci/docker:28-cli steps: - run: ls -l /var/run/docker.sock - run: docker ps diff --git a/actions/example-with-docker-tcp/.forgejo/workflows/test.yml b/actions/example-with-docker-tcp/.forgejo/workflows/test.yml index c33c2e7a..c4388ae8 100644 --- a/actions/example-with-docker-tcp/.forgejo/workflows/test.yml +++ b/actions/example-with-docker-tcp/.forgejo/workflows/test.yml @@ -4,7 +4,7 @@ jobs: build: runs-on: docker container: - image: code.forgejo.org/oci/node:20-bookworm + image: data.forgejo.org/oci/node:20-bookworm steps: - run: | ! test -e /var/run/docker.sock diff --git a/actions/example-workflow-call-expansion/.forgejo/workflows/reusable-layer-1.yml b/actions/example-workflow-call-expansion/.forgejo/workflows/reusable-layer-1.yml new file mode 100644 index 00000000..649392c1 --- /dev/null +++ b/actions/example-workflow-call-expansion/.forgejo/workflows/reusable-layer-1.yml @@ -0,0 +1,74 @@ +on: + workflow_call: + inputs: + input1: + required: true + type: string + input3: + required: true + type: string + outputs: + output1: + value: ${{ jobs.callee-1.outputs.job-output }} + output2: + value: ${{ jobs.callee-2.outputs.job-output }} + output3: + value: ${{ jobs.layer-2.outputs.output3 }} + output4: + value: ${{ jobs.layer-2.outputs.output4 }} + +jobs: + callee-1: + runs-on: docker + outputs: + job-output: callee-1-output + container: + image: data.forgejo.org/oci/node:22-bookworm + volumes: + - /srv/example:/srv/example + steps: + - name: verify workflow inputs + run: | + set -x + test "top-level-input1" = "${{ inputs.input1 }}" + test "dynamic output" = "${{ inputs.input3 }}" + - name: verify workflow secrets + run: | + set -x + test "AAAA" = "${{ secrets.secret1 }}" + test "BBBB1234" = "${{ secrets.secret2 }}" + test "" = "${{ secrets.secret3 }}" # wasn't specified to the workflow, should be absent + - name: indicate callee-1 hit + run: touch /srv/example/callee-1 + + layer-2: + needs: [callee-1] + uses: ./.forgejo/workflows/reusable-layer-2.yml + with: + input1: ${{ inputs.input1 }} + input2: mid-level-input2 + input3: ${{ inputs.input3 }} + input4: ${{ needs.callee-1.outputs.job-output }} + secrets: inherit + + callee-2: + needs: [callee-1, layer-2] + runs-on: docker + outputs: + job-output: callee-2-output + container: + image: data.forgejo.org/oci/node:22-bookworm + volumes: + - /srv/example:/srv/example + steps: + - name: verify callee-1 completed + run: | + set -x + test -f /srv/example/callee-1 + - name: verify layer-2 completed + run: | + set -x + test -f /srv/example/callee-3 + test -f /srv/example/callee-4 + - name: indicate callee-2 hit + run: touch /srv/example/callee-2 diff --git a/actions/example-workflow-call-expansion/.forgejo/workflows/reusable-layer-2.yml b/actions/example-workflow-call-expansion/.forgejo/workflows/reusable-layer-2.yml new file mode 100644 index 00000000..3b633ebd --- /dev/null +++ b/actions/example-workflow-call-expansion/.forgejo/workflows/reusable-layer-2.yml @@ -0,0 +1,63 @@ +on: + workflow_call: + inputs: + input1: + required: true + type: string + input2: + required: true + type: string + input3: + required: true + type: string + input4: + required: true + type: string + outputs: + output3: + value: ${{ jobs.callee-3.outputs.job-output }} + output4: + value: ${{ jobs.callee-4.outputs.job-output }} + +jobs: + callee-3: + runs-on: docker + outputs: + job-output: callee-3-output + container: + image: data.forgejo.org/oci/node:22-bookworm + volumes: + - /srv/example:/srv/example + steps: + - name: verify workflow inputs + run: | + set -x + test "top-level-input1" = "${{ inputs.input1 }}" + test "mid-level-input2" = "${{ inputs.input2 }}" + test "dynamic output" = "${{ inputs.input3 }}" + test "callee-1-output" = "${{ inputs.input4 }}" + - name: verify workflow secrets inherited + run: | + set -x + test "AAAA" = "${{ secrets.secret1 }}" + test "BBBB1234" = "${{ secrets.secret2 }}" + test "" = "${{ secrets.secret3 }}" # wasn't specified to the workflow, should be absent + - name: indicate callee-3 hit + run: touch /srv/example/callee-3 + + callee-4: + needs: callee-3 + runs-on: docker + outputs: + job-output: callee-4-output + container: + image: data.forgejo.org/oci/node:22-bookworm + volumes: + - /srv/example:/srv/example + steps: + - name: verify callee-3 completed + run: | + set -x + test -f /srv/example/callee-3 + - name: indicate callee-4 hit + run: touch /srv/example/callee-4 diff --git a/actions/example-workflow-call-expansion/.forgejo/workflows/test.yml b/actions/example-workflow-call-expansion/.forgejo/workflows/test.yml new file mode 100644 index 00000000..cd9290a2 --- /dev/null +++ b/actions/example-workflow-call-expansion/.forgejo/workflows/test.yml @@ -0,0 +1,53 @@ +on: + push: + +jobs: + pre-job: + runs-on: docker + container: + image: data.forgejo.org/oci/node:22-bookworm + outputs: + dynamic: "${{ steps.dynamic-step.outputs.dynamic }}" + steps: + - id: dynamic-step + run: echo "dynamic=dynamic output" >> $FORGEJO_OUTPUT + + layer-1: + needs: [pre-job] + uses: ./.forgejo/workflows/reusable-layer-1.yml + with: + input1: top-level-input1 + input3: ${{ needs.pre-job.outputs.dynamic }} + secrets: + secret1: AAAA + secret2: BBBB1234 + + verify: + needs: [layer-1] + runs-on: docker + container: + image: data.forgejo.org/oci/node:22-bookworm + volumes: + - /srv/example:/srv/example + steps: + - name: verify test config secret + run: | + set -x + # SECRET3 is set on the repo, but not passed into `reusable-layer-1.yml` so that we can test secrets don't + # leak into the workflow if they're not explicitly defined. This check verifies that the test environment has + # that secret, otherwise the test assertions that it isn't present within the workflow would be meaningless. + test "CCCC" = "${{ secrets.secret3 }}" + - name: verify callee-[0-4] completed + run: | + set -x + test -f /srv/example/callee-1 + test -f /srv/example/callee-2 + test -f /srv/example/callee-3 + test -f /srv/example/callee-4 + - name: verify workflow outputs + run: | + set -x + test "callee-1-output" = "${{ needs.layer-1.outputs.output1 }}" + test "callee-2-output" = "${{ needs.layer-1.outputs.output2 }}" + test "callee-3-output" = "${{ needs.layer-1.outputs.output3 }}" + test "callee-4-output" = "${{ needs.layer-1.outputs.output4 }}" diff --git a/actions/example-workflow-call-expansion/run.sh b/actions/example-workflow-call-expansion/run.sh new file mode 100644 index 00000000..07ca4cb7 --- /dev/null +++ b/actions/example-workflow-call-expansion/run.sh @@ -0,0 +1,12 @@ +repo=root/example-$example +api=$url/api/v1 + +# Prepare test repo +forgejo-test-helper.sh push_workflow actions/example-$example $url root example-$example setup-forgejo $token +sha=$(forgejo-test-helper.sh branch_tip $url $repo main) + +# Install a repo secret +forgejo-curl.sh api_json -X PUT --data-raw '{"data":"CCCC"}' $api/repos/$repo/actions/secrets/SECRET3 + +# Wait for action to complete +forgejo-test-helper.sh wait_success $url root/example-$example $sha diff --git a/actions/example-workflow-call/.forgejo/workflows/reusable.yml b/actions/example-workflow-call/.forgejo/workflows/reusable.yml new file mode 100644 index 00000000..6181aff6 --- /dev/null +++ b/actions/example-workflow-call/.forgejo/workflows/reusable.yml @@ -0,0 +1,35 @@ +on: + workflow_call: + inputs: + parameter1: + required: true + type: string + outputs: + output1: + value: ${{ jobs.callee.outputs.job-output }} + +jobs: + callee: + runs-on: docker + container: + image: data.forgejo.org/oci/node:22-bookworm + volumes: + - /srv/example:/srv/example + outputs: + job-output: ${{ steps.stepwithoutput.outputs.myvalue }} + steps: + + - id: stepwithoutput + run: | + set -x + test "${{ inputs.parameter1 }}" = "value1" + test "${{ secrets.secret }}" = "keep_it_private" + echo "myvalue=outputvalue1" >> $FORGEJO_OUTPUT + + - name: save event + run: | + d=/srv/example/push/contexts/$FORGEJO_EVENT_NAME + mkdir -p $d + cat > $d/github <<'EOF' + ${{ toJSON(github) }} + EOF diff --git a/actions/example-workflow-call/.forgejo/workflows/test.yml b/actions/example-workflow-call/.forgejo/workflows/test.yml new file mode 100644 index 00000000..fef61667 --- /dev/null +++ b/actions/example-workflow-call/.forgejo/workflows/test.yml @@ -0,0 +1,23 @@ +on: + push: + +jobs: + caller: + runs-on: docker + container: + image: data.forgejo.org/oci/node:22-bookworm + uses: ./.forgejo/workflows/reusable.yml + with: + parameter1: value1 + secrets: + secret: keep_it_private + + verify: + needs: [caller] + runs-on: docker + container: + image: data.forgejo.org/oci/node:22-bookworm + steps: + - run: | + set -x + test "${{ needs.caller.outputs.output1 }}" = "outputvalue1" diff --git a/actions/example-workflow-dispatch/.forgejo/workflows/test.yml b/actions/example-workflow-dispatch/.forgejo/workflows/test.yml index 186fe563..3839f7b5 100644 --- a/actions/example-workflow-dispatch/.forgejo/workflows/test.yml +++ b/actions/example-workflow-dispatch/.forgejo/workflows/test.yml @@ -44,13 +44,13 @@ jobs: test: runs-on: docker container: - image: code.forgejo.org/oci/debian:bookworm + image: data.forgejo.org/oci/debian:trixie options: "--volume /srv/example:/srv/example" steps: - name: save and display context run: | - d=/srv/example/workflow-dispatch/contexts/$GITHUB_EVENT_NAME + d=/srv/example/workflow-dispatch/contexts/$FORGEJO_EVENT_NAME mkdir -p $d tee $d/github <<'EOF' ${{ toJSON(github) }} diff --git a/actions/runner-config.yaml b/actions/runner-config.yaml index 7d9e7642..5859b08e 100644 --- a/actions/runner-config.yaml +++ b/actions/runner-config.yaml @@ -1,5 +1,6 @@ log: - level: debug + level: trace + job_level: trace runner: file: .runner diff --git a/end-to-end.sh b/end-to-end.sh index 3b3a702a..e57c8b1b 100755 --- a/end-to-end.sh +++ b/end-to-end.sh @@ -1,4 +1,4 @@ -#!/bin/bash +#!/usr/bin/env bash # SPDX-License-Identifier: MIT SELF_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" diff --git a/federation/federation.sh b/federation/federation.sh index 35a03f79..4d7c09a5 100755 --- a/federation/federation.sh +++ b/federation/federation.sh @@ -74,15 +74,23 @@ function test_federation() { local versions="${1:-$RELEASE_NUMBERS}" for version in $versions; do + # name, minimum version + # NOTE: newline seperated, not comma :> + scenarios=( + "star 7.1" + "mastodon 14.0" + "gotosocial 14.0" + ) - if dpkg --compare-versions $version lt 7.1; then - continue - fi + for scenario_version_str in "${scenarios[@]}"; do + IFS=' ' declare -a scenario_version="($scenario_version_str)" - federation_setup $version + if dpkg --compare-versions "$version" lt "${scenario_version[1]}"; then + continue + fi - for scenario in star; do - run federation_verify_scenario $scenario + federation_setup "$version" + run federation_verify_scenario "${scenario_version[0]}" done done } diff --git a/federation/scenario-gotosocial/.gitignore b/federation/scenario-gotosocial/.gitignore new file mode 100644 index 00000000..e69de29b diff --git a/federation/scenario-gotosocial/run.sh b/federation/scenario-gotosocial/run.sh new file mode 100644 index 00000000..9fd57a7b --- /dev/null +++ b/federation/scenario-gotosocial/run.sh @@ -0,0 +1,16 @@ +#!/usr/bin/env bash + +source "$DIR/federation_scenario-$scenario-env" + +if [[ -z "$password" ]]; then + exit 1 +fi + +if [[ -z "$port" ]]; then + exit 1 +fi + +status_code="$(curl -o /dev/null -w '%{http_code}' "http://localhost:$port/")" +if [[ "$status_code" != "200" ]]; then + exit 1 +fi diff --git a/federation/scenario-gotosocial/setup.sh b/federation/scenario-gotosocial/setup.sh new file mode 100644 index 00000000..fcf9a432 --- /dev/null +++ b/federation/scenario-gotosocial/setup.sh @@ -0,0 +1,58 @@ +#!/usr/bin/env bash + +source $SCENARIO_DIR/../../lib/lib.sh + +GTS_VERSION="0.20.0" # renovate: datasource=docker depName=data.forgejo.org/oci/gotosocial + +echo "setting up gotosocial" + +tmpdir="$(mktemp --tmpdir -d gts.XXXXXXXXXX)" +cat << EOF > "$tmpdir/config.yaml" +host: "localhost:8080" +protocol: http +db-type: sqlite +db-address: /mount/gts.db3 + +http-client: + allow-ips: ["0.0.0.0/0", "::/0"] + insecure-outgoing: true +EOF + +podman unshare \ + chown 1000:1000 -R $tmpdir + +container_id="$( + podman run \ + -d \ + --env "GTS_CONFIG_PATH=/mount/config.yaml" \ + -v "$tmpdir:/mount" \ + -p "8080:8080" \ + --network=host \ + "data.forgejo.org/oci/gotosocial:$GTS_VERSION" \ + server start +)" + +function wait_gts_ready() { + http_status=$(curl -s -w \ + "%{http_code}" -o /dev/null \ + "http://localhost:8080/" + ) + + [[ "$http_status" == 200 ]] && echo "ready" +} + +retry wait_gts_ready + +password="verysecurepassword" +podman exec -it "$container_id" /gotosocial/gotosocial admin \ + account create \ + --username "test" \ + --email "test@localhost" \ + --password "$password" + +cat << EOF > "$DIR/federation_scenario-gotosocial-env" +password="$password" +port="8080" +container_id="$container_id" +EOF + diff --git a/federation/scenario-gotosocial/teardown.sh b/federation/scenario-gotosocial/teardown.sh new file mode 100644 index 00000000..6e6d556a --- /dev/null +++ b/federation/scenario-gotosocial/teardown.sh @@ -0,0 +1,12 @@ +#!/usr/bin/env bash + +source "$DIR/federation_scenario-gotosocial-env" + +if [[ -z "$container_id" ]]; then + echo "gotosocial container ID not found, container may not be stopped" + exit 1 +fi + +podman stop "$container_id" +rm "$DIR/federation_scenario-gotosocial-env" + diff --git a/federation/scenario-mastodon/.gitignore b/federation/scenario-mastodon/.gitignore new file mode 100644 index 00000000..041e9d6f --- /dev/null +++ b/federation/scenario-mastodon/.gitignore @@ -0,0 +1,3 @@ +/resources/certs/forgejo* +/forgejo/certs/* +!/forgejo/certs/.gitkeep diff --git a/federation/scenario-mastodon/TEST_INSTRUCTION.md b/federation/scenario-mastodon/TEST_INSTRUCTION.md new file mode 100644 index 00000000..82d957b0 --- /dev/null +++ b/federation/scenario-mastodon/TEST_INSTRUCTION.md @@ -0,0 +1,38 @@ +# Manual testing + +1. compile forgejo binary to test on a debian/ubuntu system +2. start applications + * local forgejo: + ```sh + cd federation/scenario-mastodon + # create cert & startup & create test accounts + SCENARIO_DIR="." ./setup.sh + # Mastodon password in "/tmp/forgejo-end-to-end/federation_scenario-mastodon-env" + # Bind forgejo to localhost:3003 and set the domain to `forgejo` + ``` + * containerized forgejo: + ```sh + cd federation/scenario-mastodon + # Generate self-signed certs on first run + source ./functions.sh + generate_certs forgejo "./resources/certs" + mv "./resources/certs/forgejo"* "forgejo/certs" + + # Setup container + export FORGEJO_PATH="/path/to/forgejo/binary" + export COMPOSE_PROFILES="forgejo_container" + export MASTODON_HOST="mastodon-app" + + podman-compose up -d + podman-compose exec forgejo-app bash -c "/init/create_test_account.sh" + # Mastodon password is the last line of the output + podman-compose exec mastodon-app bash -c "/init/create_test_account.sh" + ``` +3. login to mastodon: http://localhost:4000 + 1. test@localhost - password from start app. +4. search for forgejo user: `https://forgejo/api/v1/activitypub/user-id/1` +5. Press follow +6. FYI: + 1. login to forgejo: http://localhost:3003/ + 2. me - me + 3. swagger-uri: http://localhost:3003/api/swagger#/activitypub diff --git a/federation/scenario-mastodon/compose.yaml b/federation/scenario-mastodon/compose.yaml new file mode 100644 index 00000000..ea7c28a6 --- /dev/null +++ b/federation/scenario-mastodon/compose.yaml @@ -0,0 +1,95 @@ +networks: + external_network: + internal_network: + internal: true + +services: + forgejo: + image: data.forgejo.org/oci/alpine:latest + volumes: + - ./forgejo/certs/:/usr/local/share/ca-certificates/ + - ./forgejo/init/:/init/ + - ./forgejo/etc/lighttpd.conf:/etc/lighttpd.conf + restart: unless-stopped + entrypoint: "sh /init/init.sh" + networks: + - external_network + - internal_network + + forgejo-app: + profiles: + - forgejo_container + # built from https://code.forgejo.org/federation/build-mastodon/src/branch/main/debian-containerfile + image: data.forgejo.org/federation/debian:trixie-cacerts + tmpfs: + - /data + volumes: + - ./forgejo-app/init/:/init/ + - ./forgejo-app/config/:/config/ + - ./resources/certs/:/usr/local/share/ca-certificates/ + - "${FORGEJO_PATH}:/usr/local/bin/forgejo" + ports: + - 3003:3003 + entrypoint: "sh /init/init.sh" + networks: + - external_network + - internal_network + + postgres: + image: data.forgejo.org/oci/postgres:14 + tmpfs: + - /var/lib/postgresql/data + environment: + POSTGRES_USER: postgres + POSTGRES_DB: postgres + POSTGRES_PASSWORD: postgres + POSTGRES_HOST_AUTH_METHOD: trust + networks: + - internal_network + + redis: + image: data.forgejo.org/oci/redis:7.2 + tmpfs: + - /var/lib/redis/ + networks: + - internal_network + + mastodon-app: + # built from https://code.forgejo.org/federation/build-mastodon/src/branch/main/mastodon-containerfile + image: data.forgejo.org/federation/mastodon:v4.5-test + volumes: + - ./resources/certs:/usr/local/share/ca-certificates/ + - ./mastodon-app/init/:/init/ + environment: &mastodon_env + DB_HOST: postgres + DB_USER: postgres + DB_PASS: postgres + REDIS_HOST: redis + PORT: 4000 + LOCAL_DOMAIN: ${MASTODON_HOST}:4000 + ALTERNATE_DOMAINS: ${MASTODON_HOST},localhost + EMAIL_DOMAIN_ALLOWLIST: localhost + AUTHORIZED_FETCH: "true" + ALLOWED_PRIVATE_ADDRESSES: 0.0.0.0/0,::/0 + SECRET_KEY_BASE: bc1bdb4d3d57a2c292a8f145d5d3c921 + ACTIVE_RECORD_ENCRYPTION_DETERMINISTIC_KEY: fkSxKD2bF396kdQbrP1EJ7WbU7ZgNokR + ACTIVE_RECORD_ENCRYPTION_KEY_DERIVATION_SALT: r0hvVmzBVsjxC7AMlwhOzmtc36ZCOS1E + ACTIVE_RECORD_ENCRYPTION_PRIMARY_KEY: PhdFyyfy5xJ7WVd2lWBpcPScRQHzRTNr + ports: + - "4000:4000" + entrypoint: "sh /init/init.sh" + networks: + - external_network + - internal_network + + mastodon-sidekiq: + # built from https://code.forgejo.org/federation/build-mastodon/src/branch/main/mastodon-containerfile + image: data.forgejo.org/federation/mastodon:v4.5-test + volumes: + - ./resources/certs:/usr/local/share/ca-certificates/ + - ./mastodon-sidekiq/init/:/init/ + restart: unless-stopped + environment: *mastodon_env + entrypoint: "sh /init/init.sh" + networks: + - internal_network diff --git a/federation/scenario-mastodon/forgejo-app/config/app.ini b/federation/scenario-mastodon/forgejo-app/config/app.ini new file mode 100644 index 00000000..55ef4f61 --- /dev/null +++ b/federation/scenario-mastodon/forgejo-app/config/app.ini @@ -0,0 +1,32 @@ +RUN_MODE = prod + +[server] +APP_DATA_PATH = /data +DOMAIN = forgejo +ROOT_URL = https://forgejo/ +HTTP_PORT = 3003 +PROTOCOL = http + +[queue] +TYPE = immediate + +[database] +DB_TYPE = sqlite3 +PATH = /data/forgejo.db + +[log] +MODE = console +LEVEL = debug + +[security] +INSTALL_LOCK = true + +[repository] +ENABLE_PUSH_CREATE_USER = true +DEFAULT_PUSH_CREATE_PRIVATE = false + +[federation] +ENABLED = true + +[session] +COOKIE_SECURE = false diff --git a/federation/scenario-mastodon/forgejo-app/init/create_test_account.sh b/federation/scenario-mastodon/forgejo-app/init/create_test_account.sh new file mode 100755 index 00000000..33fc4807 --- /dev/null +++ b/federation/scenario-mastodon/forgejo-app/init/create_test_account.sh @@ -0,0 +1,7 @@ +#!/usr/bin/env bash + +sleep 10 + +/usr/local/bin/forgejo -c /etc/forgejo/app.ini admin user create --username me --password me --email "me@example.com" --admin --must-change-password=false +/usr/local/bin/forgejo -c /etc/forgejo/app.ini admin user create --username to-be-followd --password to-be-followd --email "to-be-followd@example.com" --admin --must-change-password=false +/usr/local/bin/forgejo -c /etc/forgejo/app.ini admin user generate-access-token -u me -t token --scopes write:activitypub,write:repository,write:user diff --git a/federation/scenario-mastodon/forgejo-app/init/init.sh b/federation/scenario-mastodon/forgejo-app/init/init.sh new file mode 100755 index 00000000..3848fa53 --- /dev/null +++ b/federation/scenario-mastodon/forgejo-app/init/init.sh @@ -0,0 +1,10 @@ +#!/usr/bin/env bash + +sudo update-ca-certificates + +sudo mkdir -p /data/forgejo +sudo chown forgejo:forgejo /data/forgejo +sudo install -D -o forgejo -g forgejo /config/app.ini /etc/forgejo/app.ini + +/usr/local/bin/forgejo -c /etc/forgejo/app.ini + diff --git a/federation/scenario-mastodon/forgejo/certs/.gitkeep b/federation/scenario-mastodon/forgejo/certs/.gitkeep new file mode 100644 index 00000000..e69de29b diff --git a/federation/scenario-mastodon/forgejo/etc/lighttpd.conf b/federation/scenario-mastodon/forgejo/etc/lighttpd.conf new file mode 100644 index 00000000..325779ad --- /dev/null +++ b/federation/scenario-mastodon/forgejo/etc/lighttpd.conf @@ -0,0 +1,22 @@ +server.document-root = "/var/www" + +server.modules = ( + "mod_openssl", + "mod_proxy" +) + +$SERVER["socket"] == ":443" { + ssl.engine = "enable" + ssl.pemfile = "/usr/local/share/ca-certificates/forgejo-snakeoil.crt" + ssl.privkey = "/usr/local/share/ca-certificates/forgejo-snakeoil.key" +} + +proxy.server = ( + "" => ( + "forgejo" => ( + "host" => "host.containers.internal", + "port" => 3003, + ) + ) +) + diff --git a/federation/scenario-mastodon/forgejo/init/init.sh b/federation/scenario-mastodon/forgejo/init/init.sh new file mode 100755 index 00000000..6660768d --- /dev/null +++ b/federation/scenario-mastodon/forgejo/init/init.sh @@ -0,0 +1,6 @@ +#!/usr/bin/env sh + +apk add lighttpd + +lighttpd -D -f /etc/lighttpd.conf + diff --git a/federation/scenario-mastodon/functions.sh b/federation/scenario-mastodon/functions.sh new file mode 100644 index 00000000..507131cc --- /dev/null +++ b/federation/scenario-mastodon/functions.sh @@ -0,0 +1,32 @@ +function generate_certs() { + + host=${1} + cert_location=${2} + + rootCertificate="${cert_location}/custom-snakeoil-rootCA.crt" + rootCertKey="${cert_location}/custom-snakeoil-rootCA.key" + extensionFile="${cert_location}/${host}-snakeoil.ext" + keyFile="${cert_location}/${host}-snakeoil.key" + csrFile="${cert_location}/${host}-snakeoil.csr" + crtAltSubFile="${cert_location}/${host}-snakeoil.crt" + + cat << EOF > ${extensionFile} +authorityKeyIdentifier=keyid,issuer +basicConstraints=CA:FALSE +subjectAltName = @alt_names +[alt_names] +DNS.1 = ${host} +DNS.2 = localhost +EOF + + # Create CSR + openssl req -newkey rsa:2048 -nodes -keyout ${keyFile} \ + -out ${csrFile} -subj "/CN=${host}" -addext "subjectAltName=DNS:localhost" + + # Sign Our CSR with the root CA cert + openssl x509 -req -CA ${rootCertificate} \ + -CAkey ${rootCertKey} \ + -in ${csrFile} \ + -out ${crtAltSubFile} \ + -days 3650 -CAcreateserial -extfile ${extensionFile} +} \ No newline at end of file diff --git a/federation/scenario-mastodon/mastodon-app/init/create_test_account.sh b/federation/scenario-mastodon/mastodon-app/init/create_test_account.sh new file mode 100755 index 00000000..283000fb --- /dev/null +++ b/federation/scenario-mastodon/mastodon-app/init/create_test_account.sh @@ -0,0 +1,14 @@ +#!/usr/bin/env bash + +account_create="$(tootctl accounts create test --email test@localhost --role Owner --confirmed)" +tootctl account modify test --approve + +echo "${account_create}" + +password=$(echo "${account_create}" | + tail -n 1 | + sed 's/New password: //' | + sed 's/\r//' +) + +echo "$password" diff --git a/federation/scenario-mastodon/mastodon-app/init/init.sh b/federation/scenario-mastodon/mastodon-app/init/init.sh new file mode 100755 index 00000000..731aa55d --- /dev/null +++ b/federation/scenario-mastodon/mastodon-app/init/init.sh @@ -0,0 +1,8 @@ +#!/usr/bin/env bash + +sudo update-ca-certificates +sudo touch /opt/mastodon/log/prod.log +sudo chown mastodon: /opt/mastodon/log/prod.log +rails db:setup +bundle exec puma -C config/puma.rb +#sleep 2h diff --git a/federation/scenario-mastodon/mastodon-sidekiq/init/init.sh b/federation/scenario-mastodon/mastodon-sidekiq/init/init.sh new file mode 100755 index 00000000..af9c5190 --- /dev/null +++ b/federation/scenario-mastodon/mastodon-sidekiq/init/init.sh @@ -0,0 +1,7 @@ +#!/usr/bin/env bash + +sudo update-ca-certificates +sudo touch /opt/mastodon/log/prod.log +sudo chown mastodon: /opt/mastodon/log/prod.log +bundle exec sidekiq +#sleep 2h diff --git a/federation/scenario-mastodon/resources/certs/custom-snakeoil-rootCA.crt b/federation/scenario-mastodon/resources/certs/custom-snakeoil-rootCA.crt new file mode 100644 index 00000000..91a0d144 --- /dev/null +++ b/federation/scenario-mastodon/resources/certs/custom-snakeoil-rootCA.crt @@ -0,0 +1,19 @@ +-----BEGIN CERTIFICATE----- +MIIDGTCCAgGgAwIBAgIUU+o53CfULAHTgPuCq/Ua8JRTWLIwDQYJKoZIhvcNAQEL +BQAwGzEZMBcGA1UEAwwQY29kZS5mb3JnZWpvLm9yZzAgFw0yNTEwMjMwODI2NTVa +GA8yMTI1MDkyOTA4MjY1NVowGzEZMBcGA1UEAwwQY29kZS5mb3JnZWpvLm9yZzCC +ASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAKJl1YjGLoYK5J7wCbgL7WCZ +DGznwmp2SxpxJx/9Y6Pldt1QXTp0/VrR/H8iu3bNh13jmupXTKyGHU94MTNHER1T +/jbGw8LRPWCIYNjpYFZU17glTGs/DOieh7acuuvu+imoamk1oRLVaaHDewz09Tc2 +wkklCH+2ME2TC6mHIqpHOLO//ESEU0Glo+/mVMEcTJf9zdDhSGhZPKhXEaWgrLMo +EV3r0hpxHCE21OeaRrOKjMtOfp6/v0yKAsJ0QbLHXw1JDauiMWHUxp1H3jIHGgtc +0ALdiS1fhYi8zX3bkbMfctjREVtbhO0Aqps5pvDjhjTNyTmSQ3dkkU37W7Mz+WkC +AwEAAaNTMFEwHQYDVR0OBBYEFKXOSikliKVL6VYbbcaOR3k3khKyMB8GA1UdIwQY +MBaAFKXOSikliKVL6VYbbcaOR3k3khKyMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZI +hvcNAQELBQADggEBADE4RGzIXT3LsLGxqRiuOPrXnOTy6izD0sXraJGPWOTEm0MB +H+MnV1YmqRiafwCTbKyiTfzF50JX0zwa6NnkK7k7tyht7O2B0/1VfsrIaXGBP05B +pZMC1bMSaDEu+zvRUDFvNiE5Oxkw0LGy44o36e3SNCEXMCYU3fiTX/5IxfB/a1Bk ++5tNfpK4CKwyk2/pb8ClgBldYGxfp/hyzTVh7y4c5bSRzoawGxq2ipfmJbSBYEme +vyySFXJI1W9ih8utE2sQKbRS7YrwxSNS9Uj6qwixTlHB5a/MzlFmD630VkmkI1qq +5VkQxq7dJSTlVHX8qiQqvGoPPIp5ucbBDmyj2A8= +-----END CERTIFICATE----- diff --git a/federation/scenario-mastodon/resources/certs/custom-snakeoil-rootCA.key b/federation/scenario-mastodon/resources/certs/custom-snakeoil-rootCA.key new file mode 100644 index 00000000..b4b13057 --- /dev/null +++ b/federation/scenario-mastodon/resources/certs/custom-snakeoil-rootCA.key @@ -0,0 +1,28 @@ +-----BEGIN PRIVATE KEY----- +MIIEvwIBADANBgkqhkiG9w0BAQEFAASCBKkwggSlAgEAAoIBAQCiZdWIxi6GCuSe +8Am4C+1gmQxs58JqdksacScf/WOj5XbdUF06dP1a0fx/Irt2zYdd45rqV0yshh1P +eDEzRxEdU/42xsPC0T1giGDY6WBWVNe4JUxrPwzonoe2nLrr7vopqGppNaES1Wmh +w3sM9PU3NsJJJQh/tjBNkwuphyKqRzizv/xEhFNBpaPv5lTBHEyX/c3Q4UhoWTyo +VxGloKyzKBFd69IacRwhNtTnmkaziozLTn6ev79MigLCdEGyx18NSQ2rojFh1Mad +R94yBxoLXNAC3YktX4WIvM1925GzH3LY0RFbW4TtAKqbOabw44Y0zck5kkN3ZJFN ++1uzM/lpAgMBAAECggEAAdGmR0j0k/ISyfhYnFJfFAfBN+x0a1wl7rOjDP/Tg7r9 +Ln21yzYTJJcfnu5TaOfLH84KrRwrT6JhhfaYn64PC8PmH/rXDftPsFSOt/DZo2+B +vaSgGyWcMVqdnNOOep6IXq36rr3krwQra14Rmbbm36AYihh+iuzbB4w0vPvpwDwv +G9DITTLrIwDRbXReZ13FjqphP5dqT6jG7BnRLe7vyQ7CJwYdUDLkg2YLykwbHvco +DISS3IoYgF5R7KaGpwH2iFmeHYwXaVH9Y0RyjEvxp87iK8Awvm4yn7hWBx9NsMm2 +of7107TlFBU81JbG09KQZ+mS3S4C9XfQScqBoP66tQKBgQDYS4QhwkYFNusN8z+U +63IGMxJXMF0bvF1zqjhrfkdX16jDD7v8cMbZAjk80obmRdhFpNiuaCT7dbnXpt7L +Ppfu6IkcJsAJc32lbWGc56XzfzDnNecvQbCbMnRYI5GDzcTTY+ObgyhJv4SwuD3E +kdHhxOFPuxlLFey9eg9vC6ADnQKBgQDANX5oEqvVty8gn+cOU3fEiqQ+ZqvcgMcL +CUQYIAUDvXjZuXTbU0cSzgZnZi3JwtEVwj0u+0eXXlju6AVgKC/yd4aIpQ2f6hXO +UlODWIqiNq3lVgjatO6zQ2CXuBeV7crX6odNrhkvSwSPNlC2Ra7QZ8Uk0PpX0sTm +JyuMA/WBPQKBgQCkqulPYj44nhTZrAUN9Sn7+knOQy2/feqPsln9zEe4YqFCz+nI +SHu6nuzAl27IRQhgDR5BuVvebUQtIAeiKGc3JaWs3vt4topDtUCJWfqHpJ+whuMY +oSQ5I3Jb38ha1f8xCG0x6ep0KvB0MfAkhPeKsH7wWnrpJSn1HsY9PlZ2KQKBgQCS +/xZKb6UdEDipocDqkukw1bsgwhLD03TmOtLqBGrxXlFzacM2DW14sznwkBOKj0Sq +eF+kc6Zf3Fb1d1rNHE73B3RLQre1yiedIBcgh3GW92xszSx+XwuC64+O2Mqo7jBI +iuOpg/Fc2umEwUxe6dH1Lrd2HaCn09ikD+bc8RYsHQKBgQDXfAiAf3MdzG8+4zgD +kzfZsUXRUm3ACqrkhlUOzPsh2y5yGO0gxkrUR4ps2+wn0aapwYi+JdbEHpDqI4Ze +vE3d8ZgLF4ER+uuiayuItMIFa8T0AiH1oJMptUY4kgj1AaG0b3+ZxU/uGXjpciyA +a7/psxJ+in3AQ005JGir8rx+gA== +-----END PRIVATE KEY----- diff --git a/federation/scenario-mastodon/run.sh b/federation/scenario-mastodon/run.sh new file mode 100644 index 00000000..7e07a1b8 --- /dev/null +++ b/federation/scenario-mastodon/run.sh @@ -0,0 +1,17 @@ +#!/usr/bin/env bash + +source "$DIR/federation_scenario-$scenario-env" + +if [[ -z "$password" ]]; then + exit 1 +fi + +if [[ -z "$port" ]]; then + exit 1 +fi + +status_code="$(curl -o /dev/null -w '%{http_code}' "http://localhost:$port/")" +if [[ "$status_code" != "200" ]]; then + exit 1 +fi + diff --git a/federation/scenario-mastodon/setup.sh b/federation/scenario-mastodon/setup.sh new file mode 100755 index 00000000..cb9efb98 --- /dev/null +++ b/federation/scenario-mastodon/setup.sh @@ -0,0 +1,48 @@ +#!/usr/bin/env bash + +source "$SCENARIO_DIR/../../lib/lib.sh" +source "$SCENARIO_DIR/functions.sh" + +echo "Setting up Forgejo x Mastodon" + +if [[ ! -d "$DIR" ]]; then + mkdir -p "$DIR" +fi + +echo "Generating forgejo & mastodon self-signed certificate" + +generate_certs forgejo "$SCENARIO_DIR/resources/certs" + +mv "$SCENARIO_DIR/resources/certs/forgejo"* "$SCENARIO_DIR/forgejo/certs/" + +export MASTODON_HOST="localhost" + +podman-compose \ + -f "$SCENARIO_DIR/compose.yaml" \ + up -d + +function wait_up() { + command="$(podman-compose \ + -f "$SCENARIO_DIR/compose.yaml" \ + exec mastodon-app \ + bin/tootctl accounts + )" + + first="$(head -n 1 <<< "$command")" + [[ "$first" == *"Commands:"* ]] && echo "ready" +} + +retry wait_up + +password="$(podman-compose \ + -f "$SCENARIO_DIR/compose.yaml" \ + exec mastodon-app \ + bash -c "/init/create_test_account.sh" | \ + tail -n 1 | \ + sed 's/\r//' +)" + +cat << EOF > "$DIR/federation_scenario-mastodon-env" +password="$password" +port="4000" +EOF diff --git a/federation/scenario-mastodon/teardown.sh b/federation/scenario-mastodon/teardown.sh new file mode 100644 index 00000000..5e5d35f4 --- /dev/null +++ b/federation/scenario-mastodon/teardown.sh @@ -0,0 +1,8 @@ +#!/usr/bin/env bash + +podman-compose \ + -f "$SCENARIO_DIR/compose.yaml" \ + down + +rm "$DIR/federation_scenario-mastodon-env" + diff --git a/forgejo/sources/13.0 b/forgejo/sources/13.0 new file mode 100644 index 00000000..24bcca16 --- /dev/null +++ b/forgejo/sources/13.0 @@ -0,0 +1 @@ +https://codeberg.org/forgejo/forgejo forgejo 13.0.0 diff --git a/forgejo/sources/14.0 b/forgejo/sources/14.0 new file mode 100644 index 00000000..84203a1b --- /dev/null +++ b/forgejo/sources/14.0 @@ -0,0 +1 @@ +https://codeberg.org/forgejo/forgejo forgejo 14.0.0 diff --git a/forgejo/sources/15.0 b/forgejo/sources/15.0 new file mode 100644 index 00000000..595283d3 --- /dev/null +++ b/forgejo/sources/15.0 @@ -0,0 +1 @@ +https://codeberg.org/forgejo/forgejo forgejo 15.0.0 diff --git a/lib/build.sh b/lib/build.sh index bbef73eb..8fac7201 100755 --- a/lib/build.sh +++ b/lib/build.sh @@ -36,7 +36,7 @@ done git fetch --update-head-ok origin +$ref:$ref git switch --force-create $v $ref -export TAGS="bindata sqlite sqlite_unlock_notify" FORGEJO_VERSION=$semver +export TAGS="bindata sqlite sqlite_unlock_notify" FORGEJO_VERSION=$semver EXTRA_GOFLAGS="-cover" make deps-backend backend make generate forgejo cp -a forgejo $dir_binaries/forgejo-$v-dev diff --git a/lib/lib.sh b/lib/lib.sh index 1130a5bd..b1e9409f 100644 --- a/lib/lib.sh +++ b/lib/lib.sh @@ -26,11 +26,12 @@ IP=$(hostname -I | cut -f1 -d' ') # # Forgejo releases for which a branch exists (7.0/forgejo etc.) # -RELEASE_NUMBERS="7.0 11.0 12.0" +RELEASE_NUMBERS="11.0 14.0 15.0" PREFIX=============== export DIR=/tmp/forgejo-end-to-end DIR_BINARIES=/srv/forgejo-binaries +COVERAGE_DIR="$DIR/coverage" export DOT_FORGEJO_CURL=$DIR/forgejo-curl export DOT=$DOT_FORGEJO_CURL # for backward compatibility with forgejo-curl.sh 1.0.0 : ${FORGEJO_USER:=root} @@ -49,9 +50,9 @@ function dependencies() { $SUDO chmod +x /usr/local/bin/forgejo-curl.sh fi - if ! which make curl daemon git-lfs jq sqlite3 skopeo >/dev/null; then + if ! which make curl daemon git-lfs jq sqlite3 skopeo podman podman-compose pup >/dev/null; then $SUDO apt-get update -qq - $SUDO apt-get install -y -qq make curl daemon git-lfs jq sqlite3 skopeo + $SUDO apt-get install -y -qq make curl daemon git-lfs jq sqlite3 skopeo podman podman-compose pup fi if ! test -f /usr/local/bin/mc || ! test -f /usr/local/bin/minio; then @@ -262,7 +263,8 @@ function start_forgejo_daemon() { local base=$(work_path_base $config) local work_path=$DIR/$base - daemon --chdir=$DIR --unsafe --env="TERM=$TERM" --env="HOME=$HOME" --env="PATH=$PATH" --pidfile=$DIR/$base-pid --errlog=$DIR/$base-err.log --output=$DIR/$base-out.log -- $binary --config $work_path/app.ini --work-path $work_path + mkdir -p $COVERAGE_DIR + daemon --chdir=$DIR --unsafe --env="TERM=$TERM" --env="HOME=$HOME" --env="PATH=$PATH" --env="GOCOVERDIR=$COVERAGE_DIR" --pidfile=$DIR/$base-pid --errlog=$DIR/$base-err.log --output=$DIR/$base-out.log -- $binary --config $work_path/app.ini --work-path $work_path if ! retry grep --no-messages --quiet 'Starting server on' $work_path/log/forgejo.log; then grep '' $DIR/$base*.log grep '' $work_path/log/*.log 2>/dev/null @@ -413,6 +415,17 @@ EOF cp -a $DOT_FORGEJO_CURL $work_path/forgejo-curl } +function create_offline_registration_token() { + local name="$1" + local scope="$2" + local secret="$3" + + local work_path + work_path="$DIR/$(work_path_base "$config")" + + "$work_path/forgejocli" forgejo-cli actions register --name "$name" --scope "$scope" --secret "$secret" +} + function stop_daemon() { local daemon=$1 diff --git a/packages/alpine-10.0 b/packages/alpine-10.0 deleted file mode 120000 index b34295a0..00000000 --- a/packages/alpine-10.0 +++ /dev/null @@ -1 +0,0 @@ -alpine-7.0 \ No newline at end of file diff --git a/packages/alpine.sh b/packages/alpine.sh index c8679a51..ce5c4ac8 100644 --- a/packages/alpine.sh +++ b/packages/alpine.sh @@ -7,7 +7,7 @@ function test_packages_alpine_version() { reset_forgejo $PACKAGES_DIR/alpine-app.ini start_forgejo $forgejo_version - local d=$PACKAGES_DIR/alpine-$forgejo_version + local d=$PACKAGES_DIR/alpine local token=$(cat $DIR/forgejo-curl/token) local url=http://${HOST_PORT} @@ -16,8 +16,10 @@ function test_packages_alpine_version() { } function test_packages_alpine() { - for alpine_version in 3.20 3.21; do - for forgejo_version in 7.0 10.0; do + local forgejo_versions="${1:-$RELEASE_NUMBERS}" + + for alpine_version in 3.22 3.23; do + for forgejo_version in $forgejo_versions; do test_packages_alpine_version $alpine_version $forgejo_version done done diff --git a/packages/alpine-7.0/package-source/forgejo-2173/APKBUILD b/packages/alpine/package-source/forgejo-2173/APKBUILD similarity index 100% rename from packages/alpine-7.0/package-source/forgejo-2173/APKBUILD rename to packages/alpine/package-source/forgejo-2173/APKBUILD diff --git a/packages/alpine-7.0/package-source/forgejo-2173/forgejo_2173 b/packages/alpine/package-source/forgejo-2173/forgejo_2173 similarity index 100% rename from packages/alpine-7.0/package-source/forgejo-2173/forgejo_2173 rename to packages/alpine/package-source/forgejo-2173/forgejo_2173 diff --git a/packages/alpine-7.0/package-source/forgejo-2173/forgejo_2173.init b/packages/alpine/package-source/forgejo-2173/forgejo_2173.init similarity index 100% rename from packages/alpine-7.0/package-source/forgejo-2173/forgejo_2173.init rename to packages/alpine/package-source/forgejo-2173/forgejo_2173.init diff --git a/packages/alpine-7.0/package-source/forgejo-2174/APKBUILD b/packages/alpine/package-source/forgejo-2174/APKBUILD similarity index 100% rename from packages/alpine-7.0/package-source/forgejo-2174/APKBUILD rename to packages/alpine/package-source/forgejo-2174/APKBUILD diff --git a/packages/alpine-7.0/package-source/forgejo-2174/forgejo_2174 b/packages/alpine/package-source/forgejo-2174/forgejo_2174 similarity index 100% rename from packages/alpine-7.0/package-source/forgejo-2174/forgejo_2174 rename to packages/alpine/package-source/forgejo-2174/forgejo_2174 diff --git a/packages/alpine-7.0/package-source/forgejo-2174/forgejo_2174.init b/packages/alpine/package-source/forgejo-2174/forgejo_2174.init similarity index 100% rename from packages/alpine-7.0/package-source/forgejo-2174/forgejo_2174.init rename to packages/alpine/package-source/forgejo-2174/forgejo_2174.init diff --git a/packages/alpine-7.0/test.sh b/packages/alpine/test.sh similarity index 100% rename from packages/alpine-7.0/test.sh rename to packages/alpine/test.sh diff --git a/packages/packages.sh b/packages/packages.sh index 002ed796..4fc9c6a4 100644 --- a/packages/packages.sh +++ b/packages/packages.sh @@ -7,5 +7,7 @@ PACKAGES_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" source $PACKAGES_DIR/alpine.sh function test_packages() { - run test_packages_alpine + local forgejo_versions="${1:-$RELEASE_NUMBERS}" + + run test_packages_alpine $forgejo_versions } diff --git a/renovate.json b/renovate.json index cd7ea572..6b4cadc2 100644 --- a/renovate.json +++ b/renovate.json @@ -2,5 +2,13 @@ "$schema": "https://docs.renovatebot.com/renovate-schema.json", "extends": [ "local>forgejo/renovate-config" + ], + "packageRules": [ + { + "description": "Separate test actions", + "matchFileNames": ["actions/**"], + "additionalBranchPrefix": "actions", + "commitMessageTopic": "{{depName}} (test actions)" + } ] } diff --git a/run.sh b/run.sh new file mode 100755 index 00000000..92a91611 --- /dev/null +++ b/run.sh @@ -0,0 +1,11 @@ +#!/usr/bin/env bash + +podman build -t forgejo-e2e . +patchelf ../forgejo/forgejo --set-interpreter /lib64/ld-linux-x86-64.so.2 +podman run \ + -it --privileged \ + -v ../forgejo/gitea:/srv/forgejo-binaries/forgejo-14.0 \ + -p 3001-3003:3001-3003 \ + -p 4000:4000 \ + -p 8080:8080 \ + forgejo-e2e