1- # SPDX-FileCopyrightText: 2026 LibreCode Coop and LibreCode contributors
1+ # This workflow is provided via the organization template repository
22#
3- # SPDX-License-Identifier: AGPL-3.0-or-later
3+ # https://github.com/nextcloud/.github
4+ # https://docs.github.com/en/actions/learn-github-actions/sharing-workflows-with-your-organization
5+ #
6+ # SPDX-FileCopyrightText: 2021-2024 Nextcloud GmbH and Nextcloud contributors
7+ # SPDX-License-Identifier: MIT
48
59name : Build and publish app release
610
1014
1115permissions :
1216 contents : write
13- actions : write
1417
1518jobs :
1619 build_and_publish :
1720 runs-on : ubuntu-latest
18- env :
19- APP_NAME : profile_fields
21+
22+ # Only allowed to be run on nextcloud-releases repositories
23+ # if: ${{ github.repository_owner == 'nextcloud-releases' }}
2024
2125 steps :
2226 - name : Check actor permission
@@ -26,22 +30,16 @@ jobs:
2630
2731 - name : Set app env
2832 run : |
29- [ "${GITHUB_REPOSITORY##*/}" = "${APP_NAME}" ]
30- echo "APP_VERSION=${GITHUB_REF##*/}" >> "$GITHUB_ENV"
33+ # Split and keep last
34+ echo "APP_NAME=${GITHUB_REPOSITORY##*/}" >> $GITHUB_ENV
35+ echo "APP_VERSION=${GITHUB_REF##*/}" >> $GITHUB_ENV
3136
3237 - name : Checkout
3338 uses : actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
3439 with :
3540 persist-credentials : false
36- submodules : true
3741 path : ${{ env.APP_NAME }}
3842
39- - name : Validate signing secret
40- env :
41- APP_PRIVATE_KEY : ${{ secrets.APP_PRIVATE_KEY }}
42- run : |
43- test -n "${APP_PRIVATE_KEY}"
44-
4543 - name : Get app version number
4644 id : app-version
4745 uses : skjnldsv/xpath-action@f5b036e9d973f42c86324833fd00be90665fbf77 # v1.0.0
5149
5250 - name : Validate app version against tag
5351 run : |
54- [ "${{ github.ref_name }}" = "v${{ fromJSON(steps.app-version.outputs.result).version }}" ]
52+ [ "${{ env.APP_VERSION }}" = "v${{ fromJSON(steps.app-version.outputs.result).version }}" ]
5553
5654 - name : Get appinfo data
5755 id : appinfo
@@ -63,19 +61,22 @@ jobs:
6361 - name : Read package.json node and npm engines version
6462 uses : skjnldsv/read-package-engines-version-actions@06d6baf7d8f41934ab630e97d9e6c0bc9c9ac5e4 # v3
6563 id : versions
64+ # Continue if no package.json
6665 continue-on-error : true
6766 with :
6867 path : ${{ env.APP_NAME }}
6968 fallbackNode : ' ^24'
7069 fallbackNpm : ' ^11.3'
7170
7271 - name : Set up node ${{ steps.versions.outputs.nodeVersion }}
72+ # Skip if no package.json
7373 if : ${{ steps.versions.outputs.nodeVersion }}
7474 uses : actions/setup-node@53b83947a5a98c8d113130e565377fae1a50d02f # v6.3.0
7575 with :
7676 node-version : ${{ steps.versions.outputs.nodeVersion }}
7777
7878 - name : Set up npm ${{ steps.versions.outputs.npmVersion }}
79+ # Skip if no package.json
7980 if : ${{ steps.versions.outputs.npmVersion }}
8081 run : npm i -g 'npm@${{ steps.versions.outputs.npmVersion }}'
8182
@@ -93,19 +94,65 @@ jobs:
9394 env :
9495 GITHUB_TOKEN : ${{ secrets.GITHUB_TOKEN }}
9596
97+ - name : Check composer.json
98+ id : check_composer
99+ uses : andstor/file-existence-action@076e0072799f4942c8bc574a82233e1e4d13e9d6 # v3.0.0
100+ with :
101+ files : " ${{ env.APP_NAME }}/composer.json"
102+
103+ - name : Install composer dependencies
104+ if : steps.check_composer.outputs.files_exists == 'true'
105+ run : |
106+ cd ${{ env.APP_NAME }}
107+ composer install --no-dev
108+
109+ - name : Build ${{ env.APP_NAME }}
110+ # Skip if no package.json
111+ if : ${{ steps.versions.outputs.nodeVersion }}
112+ env :
113+ CYPRESS_INSTALL_BINARY : 0
114+ run : |
115+ cd ${{ env.APP_NAME }}
116+ npm ci
117+ npm run build --if-present
118+
119+ - name : Check Krankerl config
120+ id : krankerl
121+ uses : andstor/file-existence-action@076e0072799f4942c8bc574a82233e1e4d13e9d6 # v3.0.0
122+ with :
123+ files : ${{ env.APP_NAME }}/krankerl.toml
124+
125+ - name : Install Krankerl
126+ if : steps.krankerl.outputs.files_exists == 'true'
127+ run : |
128+ wget https://github.com/ChristophWurst/krankerl/releases/download/v0.14.0/krankerl_0.14.0_amd64.deb
129+ sudo dpkg -i krankerl_0.14.0_amd64.deb
130+
131+ - name : Package ${{ env.APP_NAME }} ${{ env.APP_VERSION }} with krankerl
132+ if : steps.krankerl.outputs.files_exists == 'true'
133+ run : |
134+ cd ${{ env.APP_NAME }}
135+ krankerl package
136+
137+ - name : Package ${{ env.APP_NAME }} ${{ env.APP_VERSION }} with makefile
138+ if : steps.krankerl.outputs.files_exists != 'true'
139+ run : |
140+ cd ${{ env.APP_NAME }}
141+ make appstore
142+
96143 - name : Check server download link for ${{ fromJSON(steps.appinfo.outputs.result).nextcloud.min-version }}
97- id : server-url
98144 run : |
99145 NCVERSION='${{ fromJSON(steps.appinfo.outputs.result).nextcloud.min-version }}'
100146 DOWNLOAD_URL=$(curl -s "https://updates.nextcloud.com/updater_server/latest?channel=beta&version=$NCVERSION" | jq -r '.downloads.zip[0]')
101- echo "url =$DOWNLOAD_URL" >> "$GITHUB_OUTPUT"
147+ echo "DOWNLOAD_URL =$DOWNLOAD_URL" >> $GITHUB_ENV
102148
103149 - name : Download server ${{ fromJSON(steps.appinfo.outputs.result).nextcloud.min-version }}
104150 continue-on-error : true
105151 id : server-download
106- if : steps.server-url.outputs.url != 'null'
152+ if : ${{ env.DOWNLOAD_URL != 'null' }}
107153 run : |
108- wget "${{ steps.server-url.outputs.url }}" -O nextcloud.zip
154+ echo "Downloading release tarball from $DOWNLOAD_URL"
155+ wget $DOWNLOAD_URL -O nextcloud.zip
109156 unzip nextcloud.zip
110157
111158 - name : Checkout server master fallback
@@ -117,50 +164,36 @@ jobs:
117164 repository : nextcloud/server
118165 path : nextcloud
119166
120- - name : Package ${{ env.APP_NAME }} ${{ github.ref_name }} with makefile
121- run : |
122- cd "${{ env.APP_NAME }}"
123- mkdir -p build/tools/certificates/
124- printf '%s' '${{ secrets.APP_PRIVATE_KEY }}' > "build/tools/certificates/${{ env.APP_NAME }}.key"
125- chmod 600 "build/tools/certificates/${{ env.APP_NAME }}.key"
126- make appstore verify-appstore-package
127167
128- - name : Attach tarball to GitHub release
168+ - name : Sign app
169+ run : |
170+ # Extracting release
171+ cd ${{ env.APP_NAME }}/build/artifacts
172+ tar -xvf ${{ env.APP_NAME }}.tar.gz
173+ cd ../../../
174+ # Setting up keys
175+ echo '${{ secrets.APP_PRIVATE_KEY }}' > ${{ env.APP_NAME }}.key # zizmor: ignore[secrets-outside-env]
176+ wget --quiet "https://github.com/nextcloud/app-certificate-requests/raw/master/${{ env.APP_NAME }}/${{ env.APP_NAME }}.crt"
177+ # Signing
178+ php nextcloud/occ integrity:sign-app --privateKey=../${{ env.APP_NAME }}.key --certificate=../${{ env.APP_NAME }}.crt --path=../${{ env.APP_NAME }}/build/artifacts/${{ env.APP_NAME }}
179+ # Rebuilding archive
180+ cd ${{ env.APP_NAME }}/build/artifacts
181+ tar -zcvf ${{ env.APP_NAME }}.tar.gz ${{ env.APP_NAME }}
182+
183+ - name : Attach tarball to github release
129184 uses : svenstaro/upload-release-action@29e53e917877a24fad85510ded594ab3c9ca12de # v2.11.5
130185 id : attach_to_release
131186 with :
132187 repo_token : ${{ secrets.GITHUB_TOKEN }}
133188 file : ${{ env.APP_NAME }}/build/artifacts/${{ env.APP_NAME }}.tar.gz
134- asset_name : ${{ env.APP_NAME }}-${{ github.ref_name }}.tar.gz
189+ asset_name : ${{ env.APP_NAME }}-${{ env.APP_VERSION }}.tar.gz
135190 tag : ${{ github.ref }}
136191 overwrite : true
137192
138193 - name : Upload app to Nextcloud appstore
139- env :
140- APPSTORE_TOKEN : ${{ secrets.APPSTORE_TOKEN }}
141- APP_PRIVATE_KEY : ${{ secrets.APP_PRIVATE_KEY }}
142- DOWNLOAD_URL : ${{ steps.attach_to_release.outputs.browser_download_url }}
143- run : |
144- APPSTORE_TOKEN="$(printf '%s' "$APPSTORE_TOKEN" | tr -d '\r\n')"
145- KEY_FILE="$RUNNER_TEMP/${{ env.APP_NAME }}.key"
146- APP_TGZ="$RUNNER_TEMP/${{ env.APP_NAME }}.tar.gz"
147- RESPONSE_FILE="$RUNNER_TEMP/appstore-response.json"
148-
149- printf '%s' "$APP_PRIVATE_KEY" > "$KEY_FILE"
150- wget "$DOWNLOAD_URL" -O "$APP_TGZ"
151-
152- SIGNATURE="$(openssl dgst -sha512 -sign "$KEY_FILE" "$APP_TGZ" | openssl base64 -A)"
153- PAYLOAD="$(jq -nc --arg download "$DOWNLOAD_URL" --arg signature "$SIGNATURE" '{download:$download, signature:$signature, nightly:false}')"
154-
155- HTTP_STATUS="$(curl -sS -o "$RESPONSE_FILE" -w '%{http_code}' -X POST https://apps.nextcloud.com/api/v1/apps/releases \
156- -H "Authorization: Token ${APPSTORE_TOKEN}" \
157- -H 'Content-Type: application/json' \
158- --data "$PAYLOAD")"
159-
160- echo "App Store response status: $HTTP_STATUS"
161- cat "$RESPONSE_FILE"
162-
163- if [ "$HTTP_STATUS" -lt 200 ] || [ "$HTTP_STATUS" -ge 300 ]; then
164- echo "::error::App Store upload failed with HTTP $HTTP_STATUS"
165- exit 1
166- fi
194+ uses : nextcloud-releases/nextcloud-appstore-push-action@a011fe619bcf6e77ddebc96f9908e1af4071b9c1 # v1.0.3
195+ with :
196+ app_name : ${{ env.APP_NAME }}
197+ appstore_token : ${{ secrets.APPSTORE_TOKEN }} # zizmor: ignore[secrets-outside-env]
198+ download_url : ${{ steps.attach_to_release.outputs.browser_download_url }}
199+ app_private_key : ${{ secrets.APP_PRIVATE_KEY }} # zizmor: ignore[secrets-outside-env]
0 commit comments