Repository navigation
142 lines (139 loc) · 6.52 KB
/
Copy pathCompatHelper.yml
File metadata and controls
142 lines (139 loc) · 6.52 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
name: "CompatHelper"
on:
workflow_call:
inputs:
julia-version:
description: "Julia version"
default: "1"
required: false
type: string
localregistry:
description: 'URLs of registries besides General to use. Specified by providing the url (https/ssh) to the Github
repositories as a newline (\n) seperated list.'
default: ""
required: false
type: string
subdir:
description: "Subdirectory containing the package's Project.toml. When set, CompatHelper bumps `<subdir>/Project.toml` plus `<subdir>/{docs,examples,test}/Project.toml` if present. Empty (default) uses repo root."
default: ""
required: false
type: string
jobs:
compathelper:
name: "CompatHelper"
runs-on: ubuntu-latest
permissions:
contents: write
pull-requests: write
steps:
- name: "Checkout repository"
# CompatHelper.main clones the repo internally, but we also need the
# source on the runner so we can filter the `subdirs` list against
# which Project.tomls actually exist before passing it in.
# CompatHelper otherwise crashes on the first missing subdir and
# silently drops every later subdir in the list.
uses: actions/checkout@v7
- name: "Check if Julia is already available in the PATH"
id: julia_in_path
run: which julia
continue-on-error: true
- name: "Install Julia, but only if it is not already available in the PATH"
uses: julia-actions/setup-julia@v3
with:
version: "${{ inputs.julia-version }}"
arch: "${{ runner.arch }}"
if: steps.julia_in_path.outcome != 'success'
- name: "Add the General registry via Git"
run: |
import Pkg
ENV["JULIA_PKG_SERVER"] = ""
Pkg.Registry.add("General")
shell: julia --color=yes {0}
- name: "Install CompatHelper"
run: |
import Pkg
name = "CompatHelper"
uuid = "aa819f21-2bde-4658-8897-bab36330d9b7"
version = "3"
Pkg.add(; name, uuid, version)
shell: julia --color=yes {0}
- name: "Detect token owner"
# CompatHelper dedups open PRs by filtering on a fixed username
# ("github-actions[bot]" by default). When COMPATHELPER_PAT is used so
# pushes trigger CI, PRs are attributed to the PAT owner instead, so
# that filter silently drops its own PRs and every scheduled run opens
# a fresh duplicate. Detect the actual token owner and pass it through
# as the ci_cfg username so dedup works.
#
# `gh api user` requires a user-scoped token; the built-in GITHUB_TOKEN
# is an installation token and will return 403. In that case we fall
# through to an empty value, and the Run step below leaves
# GitHubActions() at its `github-actions[bot]` default.
id: token-owner
run: |
login=$(gh api user --jq .login 2>/dev/null || echo "")
echo "login=$login" >> "$GITHUB_OUTPUT"
env:
GH_TOKEN: ${{ secrets.COMPATHELPER_PAT || secrets.GITHUB_TOKEN }}
- name: "Run CompatHelper"
shell: julia --color=yes {0}
env:
# Use COMPATHELPER_PAT if available so that pushes trigger CI workflows.
# The built-in GITHUB_TOKEN can't trigger other workflows
# (see https://docs.github.com/en/actions/security-for-github-actions/security-guides/automatic-token-authentication#using-the-github_token-in-a-workflow).
GITHUB_TOKEN: ${{ secrets.COMPATHELPER_PAT || secrets.GITHUB_TOKEN }}
LOCALREGISTRY: ${{ inputs.localregistry }}
SUBDIR: ${{ inputs.subdir }}
TOKEN_OWNER: ${{ steps.token-owner.outputs.login }}
run: |
import CompatHelper
import LibGit2
import Pkg
import TOML
function registry_info_from_url(url::AbstractString)
return mktempdir() do tmp_path
# Retry to help spurious connection issues, particularly on CI.
# See https://github.com/JuliaLang/Pkg.jl/blob/v1.11.0/src/Registry/Registry.jl#L246-L248.
repo = retry(LibGit2.clone; delays=fill(1.0, 5), check=(s, e) -> e isa LibGit2.GitError)(url, tmp_path)
LibGit2.close(repo)
return TOML.parsefile(joinpath(tmp_path, "Registry.toml"))
end
end
registry_name_from_url(url::AbstractString) = registry_info_from_url(url)["name"]
registries = [
Pkg.RegistrySpec(;
url = "https://github.com/JuliaRegistries/General.git",
name = "General",
)
]
localregistry = get(ENV, "LOCALREGISTRY", "")
if !isempty(localregistry)
registry_urls = split(localregistry, "\n") .|> string
for registry_url in registry_urls
isempty(registry_url) && continue
registry_name = registry_name_from_url(registry_url)
# `CompatHelper.main` requires both the URL and the name.
# TODO: Raise an issue about that in CompatHelper.jl.
push!(registries, Pkg.RegistrySpec(; url=registry_url, name=registry_name))
end
end
subdir = get(ENV, "SUBDIR", "")
subdirs = ["", "docs", "examples", "test"]
isempty(subdir) || (subdirs = joinpath.(subdir, subdirs))
# Drop subdirs that don't actually have a Project.toml. Without
# this, CompatHelper throws `LoadError: ".../Project.toml": No
# such file` on the first missing one and silently skips every
# later subdir, dropping PRs it should have opened. The
# `actions/checkout` step above puts the source on the runner
# so we can do this check.
workspace = ENV["GITHUB_WORKSPACE"]
filter!(d -> isfile(joinpath(workspace, d, "Project.toml")), subdirs)
token_owner = get(ENV, "TOKEN_OWNER", "")
# If TOKEN_OWNER contains a JSON error body (happens when only GITHUB_TOKEN
# is available, e.g. in private repos without COMPATHELPER_PAT), treat it as
# empty so CompatHelper falls back to the default "github-actions[bot]" username.
startswith(token_owner, '{') && (token_owner = "")
ci_cfg = isempty(token_owner) ?
CompatHelper.GitHubActions() :
CompatHelper.GitHubActions(; username=token_owner)
CompatHelper.main(ENV, ci_cfg; registries, subdirs, bump_version=true)