Skip to content

N8N-13 Add workflow to automate n8n updates #1

N8N-13 Add workflow to automate n8n updates

N8N-13 Add workflow to automate n8n updates #1

name: n8n Dependency Update
on:
pull_request:
branches:
- main
types:
- opened
env:
YQ_VERSION: v4.44.1
permissions:
contents: write
pull-requests: write
jobs:
determine-versions:
name: Determine node, n8n and types Versions
runs-on: ubuntu-latest
if: contains(github.event.pull_request.title, 'bump n8n from')
outputs:
target-node-version: ${{ steps.target-node-version.outputs.version }}
target-n8n-version: ${{ steps.target-n8n-version.outputs.version }}
target-n8n-nodes-base-version: ${{ steps.target-n8n-nodes-base-version.outputs.version }}
target-n8n-workflow-version: ${{ steps.target-n8n-workflow-version.outputs.version }}
target-types-node-version: ${{ steps.target-types-node-version.outputs.version }}
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Extract target n8n version
id: target-n8n-version
# yamllint disable-line rule:line-length
run: echo "version=$(jq --raw-output '.packages["node_modules/n8n"].version' package-lock.json)" >> "$GITHUB_OUTPUT"
- name: Extract target n8n-nodes-base version
id: target-n8n-nodes-base-version
# yamllint disable-line rule:line-length
run: echo "version=$(jq --raw-output '.packages["node_modules/n8n"].dependencies["n8n-nodes-base"]' package-lock.json)" >> "$GITHUB_OUTPUT"
- name: Extract target n8n-workflow version
id: target-n8n-workflow-version
# yamllint disable-line rule:line-length
run: echo "version=$(jq --raw-output '.packages["node_modules/n8n"].dependencies["n8n-workflow"]' package-lock.json)" >> "$GITHUB_OUTPUT"
- name: Retrieve Node.js version from n8n Docker Image
id: target-node-version
run: |
node_version=$(echo $(docker run --rm --entrypoint node n8nio/n8n:1.44.2 --version))
echo "version=${node_version#v}" >> "$GITHUB_OUTPUT"
- name: Find closest matching version of @types/node
id: target-types-node-version
# yamllint disable-line rule:line-length
run: echo "version=$(npm show @types/node versions --json | jq -r 'map(select(. <= "${{ steps.target-node-version.outputs.version }}")) | map(split(".") | map(tonumber)) | max_by(.) | join(".")')" >> "$GITHUB_OUTPUT"
update-common-dependencies:
name: Update Common Dependencies
runs-on: ubuntu-latest
if: contains(github.event.pull_request.title, 'bump n8n from')
needs: determine-versions
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Update node version in devcontainer.json
# yamllint disable rule:line-length
run: |
devcontainer_json='.devcontainer/devcontainer.json'
json_path='["features", "ghcr.io/devcontainers/features/node:1", "version"]'
target_node_version='${{ needs.determine-versions.outputs.target-node-version }}'
if [ "$(jq -r --argjson path "${json_path}" 'getpath($path)' ${devcontainer_json})" != "${target_node_version}" ]; then
jq \
--argjson path "${json_path}" \
--arg version "${target_node_version}" \
'setpath($path; $version)' ${devcontainer_json} > ${devcontainer_json}.new
mv ${devcontainer_json}.new ${devcontainer_json}
fi
# yamllint enable rule:line-length
- name: Commit node version update in devcontainer.json
uses: stefanzweifel/git-auto-commit-action@v5
with:
# yamllint disable-line rule:line-length
commit_message: 'chore: bump node version in devcontainer to ${{ needs.determine-versions.outputs.target-node-version }}'
skip_dirty_check: false
create_branch: false
- name: Update @types/node
# yamllint disable rule:line-length
run: |
npm install @types/node@~${{ needs.determine-versions.outputs.target-types-node-version }} \
--save-dev
# yamllint enable rule:line-length
- name: Commit @types/node update
uses: stefanzweifel/git-auto-commit-action@v5
with:
# yamllint disable-line rule:line-length
commit_message: 'chore: bump @types/node version to ${{ needs.determine-versions.outputs.target-types-node-version }}'
skip_dirty_check: false
create_branch: false
- name: Update n8n-nodes-base in root
# yamllint disable rule:line-length
run: |
npm install n8n-nodes-base@${{ needs.determine-versions.outputs.target-n8n-nodes-base-version }} \
--save-dev \
--save-exact
# yamllint enable rule:line-length
- name: Commit n8n-nodes-base update
uses: stefanzweifel/git-auto-commit-action@v5
with:
# yamllint disable-line rule:line-length
commit_message: 'chore: bump n8n-nodes-base version to ${{ needs.determine-versions.outputs.target-n8n-nodes-base-version }}'
skip_dirty_check: false
create_branch: false
- name: Update n8n-workflow in root
# yamllint disable rule:line-length
run: |
npm install n8n-workflow@${{ needs.determine-versions.outputs.target-n8n-workflow-version }} \
--save-dev \
--save-exact
# yamllint enable rule:line-length
- name: Commit n8n-workflow update
uses: stefanzweifel/git-auto-commit-action@v5
with:
# yamllint disable-line rule:line-length
commit_message: 'chore: bump n8n-workflow version to ${{ needs.determine-versions.outputs.target-n8n-workflow-version }}'
update-n8n-versions-in-nodes:
name: Update n8n versions in nodes
runs-on: ubuntu-latest
if: contains(github.event.pull_request.title, 'bump n8n from')
needs:
- determine-versions
- update-common-dependencies
strategy:
matrix:
node:
- test
max-parallel: 1
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Update n8n-nodes-base version
# yamllint disable rule:line-length
run: |
sed -i "s/\"n8n-nodes-base\": \".*\"/\"n8n-nodes-base\": \"${{ needs.determine-versions.outputs.target-n8n-nodes-base-version }}\"/g" nodes/${{matrix.node}}/package.json
# yamllint enable rule:line-length
- name: Commit n8n version updates in node
uses: stefanzweifel/git-auto-commit-action@v5
with:
# yamllint disable-line rule:line-length
commit_message: 'fix(${{matrix.node}}): bump n8n-nodes-base version to ${{ needs.determine-versions.outputs.target-n8n-nodes-base-version }}'
skip_dirty_check: false
create_branch: false
- name: Update n8n-workflow version
# yamllint disable rule:line-length
run: |
sed -i "s/\"n8n-workflow\": \".*\"/\"n8n-workflow\": \"${{ needs.determine-versions.outputs.target-n8n-workflow-version }}\"/g" nodes/${{matrix.node}}/package.json
# yamllint enable rule:line-length
- name: Commit n8n version updates in node
uses: stefanzweifel/git-auto-commit-action@v5
with:
# yamllint disable-line rule:line-length
commit_message: 'fix(${{matrix.node}}): bump n8n-workflow version to ${{ needs.determine-versions.outputs.target-n8n-workflow-version }}'
skip_dirty_check: false
create_branch: false
verify-workflow-node-version:
name: Verify matching version for GitHub Workflow Node.js
runs-on: ubuntu-latest
if: contains(github.event.pull_request.title, 'bump n8n from')
needs: determine-versions
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Setup YQ
uses: chrisdickinson/setup-yq@latest
with:
yq-version: ${{ env.YQ_VERSION }}
- name: Check Node.js version
id: check_node_version
# yamllint disable rule:line-length
run: |
workflow_file_urls=()
for workflow_file in ".github/workflows/"*.yaml; do
node_version=$(yq eval '.env.NODE_VERSION' "$workflow_file")
if [ "${node_version}" = "null" ] || [ "${node_version}" = "${{ needs.determine-versions.outputs.target-node-version }}" ] ; then
continue;
fi
line_number=$(yq eval '.env.NODE_VERSION | line' "$workflow_file")
url="[${workflow_file}](${{ github.server_url }}/${{ github.repository }}/blob/main/${workflow_file}#L${line_number})"
workflow_file_urls+=("$url")
done
if [ ${#workflow_file_urls[@]} -gt 0 ]; then
echo "workflow_file_urls=${workflow_file_urls[*]}" >> "$GITHUB_OUTPUT"
fi
# yamllint enable rule:line-length
- name: Request changes on PR
if: steps.check_node_version.outputs.workflow_file_urls
# yamllint disable rule:line-length
run: |
# Split the output by spaces into an array
IFS=' ' read -r -a files_array <<< "${{ steps.check_node_version.outputs.workflow_file_urls }}"
files_with_newlines=$(printf -- '- %s\n' "${files_array[@]}")
body=$(printf "The following Workflows have a different NODE_VERSION:\n%s\n\nPlease update the Node.js version to **${{ needs.determine-versions.outputs.target-node-version }}**." "${files_with_newlines}")
gh pr review ${{ github.event.pull_request.number }} \
--request-changes \
--body "${body}"
# yamllint enable rule:line-length
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}