From def6ca00b5c99b2da68ff033c7c8224379c39289 Mon Sep 17 00:00:00 2001 From: Curtis Vogt Date: Thu, 18 Apr 2024 23:37:59 -0500 Subject: [PATCH] Skip creating artifact update PR when up-to-date (#22) * Skip creating artifact update PR when up-to-date * Add keepalive job --- .github/workflows/Release.yaml | 1 + .github/workflows/Update.yaml | 48 +++++++++++++++++++++++++++------- gen/make.jl | 35 ++++++++++++++++++++----- 3 files changed, 68 insertions(+), 16 deletions(-) diff --git a/.github/workflows/Release.yaml b/.github/workflows/Release.yaml index 3b578a6..d335066 100644 --- a/.github/workflows/Release.yaml +++ b/.github/workflows/Release.yaml @@ -1,3 +1,4 @@ +--- name: Release on: push: diff --git a/.github/workflows/Update.yaml b/.github/workflows/Update.yaml index 5b722cb..726c4f0 100644 --- a/.github/workflows/Update.yaml +++ b/.github/workflows/Update.yaml @@ -1,6 +1,14 @@ --- +# Automatically builds new TZJData artifacts and creates a PR with the associated +# changes to the `Project.toml` and `Artifacts.toml`. Once the PR has been merged the +# `Release.yaml` workflow will generate a GitHub release with the assets to fufill the +# artifact URLs within the `Artifacts.toml`. + name: Update on: + pull_request: + paths: + - .github/workflows/Update.yaml schedule: - cron: "44 9 * * *" # Every day at 09:44 UTC workflow_dispatch: {} @@ -18,7 +26,7 @@ jobs: steps: - uses: actions/checkout@v4 with: - ref: ${{ github.event_name == 'pull_request' && github.event.pull_request.head.sha || 'main' }} + ref: ${{ github.event.pull_request.head.sha || 'main' }} - uses: julia-actions/setup-julia@v1 with: version: "1" @@ -33,25 +41,34 @@ jobs: shell: julia --color=yes {0} run: | include(joinpath(pwd(), "gen", "make.jl")) - (; tarball_path, tarball_sha256, new_version, commit_message) = update_tzdata() - key = basename(tarball_path) * "-" * tarball_sha256 - @show key tarball_path commit_message - open(ENV["GITHUB_OUTPUT"], "a") do io - println(io, "key=$key") - println(io, "tarball_path=$tarball_path") - println(io, "commit_message=$commit_message") + if is_pkg_tzdata_version_outdated() + (; tarball_path, tarball_sha256, new_version, commit_message) = update_tzdata() + key = basename(tarball_path) * "-" * tarball_sha256 + @show key tarball_path commit_message + open(ENV["GITHUB_OUTPUT"], "a") do io + println(io, "updated=true") + println(io, "key=$key") + println(io, "tarball_path=$tarball_path") + println(io, "commit_message=$commit_message") + end + else + open(ENV["GITHUB_OUTPUT"], "a") do io + println(io, "updated=false") + end end println("workflow_ref=${{ github.workflow_ref }}") - run: git diff # Store the Julia artifact tarball as a GitHub actions artifact. This will allow us to retrieve this # tarball from other workflows. - uses: actions/upload-artifact@v4 + if: ${{ steps.build.outputs.updated == 'true' }} id: action-artifact with: name: ${{ steps.build.outputs.key }} path: ${{ steps.build.outputs.tarball_path }} - name: Create Pull Request uses: peter-evans/create-pull-request@v5 + if: ${{ steps.build.outputs.updated == 'true' }} with: base: main # Shouldn't be required for `workflow_dispatch` title: ${{ steps.build.outputs.commit_message }} @@ -62,5 +79,18 @@ jobs: Artifacts.toml commit-message: ${{ steps.build.outputs.commit_message }} branch: gh/update-tzdata - delete-branch: ${{ github.event_name == 'pull_request' }} token: ${{ secrets.TZJDATA_UPDATE_TOKEN }} # TODO: Fine-grained token expires + + # Work around having GitHub suspend the scheduled workflow if there is no commit activity + # for the past 60 days. As this repo doesn't get much activity beyond artifact updates + # this can be quite annoying. + keepalive: + name: Keepalive + runs-on: ubuntu-latest + # These permissions are needed to: + # - Keep the workflow alive: https://github.com/marketplace/actions/keepalive-workflow#github-api-keepalive-workflow---default-for-github-actions-users + permissions: + actions: write + steps: + - uses: actions/checkout@v4 + - uses: gautamkrishnar/keepalive-workflow@v2 diff --git a/gen/make.jl b/gen/make.jl index 75ecf06..ac5cdda 100644 --- a/gen/make.jl +++ b/gen/make.jl @@ -109,7 +109,29 @@ function upload_to_github_release(owner, repo_name, commit, tag, path; token=ENV run(cmd) end -function update_tzdata() +function next_tzdata_version(tzdata_version::AbstractString) + # Always fetch the current list of tzdata versions (ignoring any caching). + tzdata_versions = TZData.tzdata_versions() + i = findfirst(==(tzdata_version), tzdata_versions) + if !isnothing(i) + return i < length(tzdata_versions) ? tzdata_versions[i + 1] : nothing + else + error("Unable to locate tzdata version $tzdata_version in list of tzdata versions") + end +end + +function is_pkg_tzdata_version_outdated() + repo_path = joinpath(@__DIR__, "..") + + # Read Project.toml + project_toml = joinpath(repo_path, "Project.toml") + project = read_project(project_toml) + tzdata_version = only(project.version.build) + + return !isnothing(next_tzdata_version(tzdata_version)) +end + +function update_tzdata(; force::Bool=false) repo_path = joinpath(@__DIR__, "..") pkg_url = remote_url(repo_path) @@ -119,14 +141,13 @@ function update_tzdata() old_version = project.version old_tzdata_version = only(old_version.build) - # Always fetch the current list of tzdata versions (ignoring any caching). - tzdata_versions = TZData.tzdata_versions() - i = findfirst(==(old_tzdata_version), tzdata_versions) - if i == length(tzdata_versions) - new_tzdata_version = tzdata_versions[i] + # If `old_tzdata_version` is already the latest version then `nothing` will be returned + # so we'll perform a rebuild of the current tzdata version. + new_tzdata_version = next_tzdata_version(old_tzdata_version) + if isnothing(new_tzdata_version) + new_tzdata_version = tzdata_version new_version = Base.nextpatch(old_version) else - new_tzdata_version = tzdata_versions[i + 1] new_version = Base.nextminor(old_version) end