Skip to content

Commit 2118843

Browse files
Fix no important files script (exercism#199)
1 parent ab845c4 commit 2118843

File tree

1 file changed

+52
-24
lines changed

1 file changed

+52
-24
lines changed

.github/workflows/check-no-important-files-changed.yml

Lines changed: 52 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -20,39 +20,67 @@ jobs:
2020
name: No important files changed
2121
runs-on: ubuntu-22.04
2222
steps:
23-
- name: Checkout code
24-
uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
25-
with:
26-
repository: ${{ inputs.repository }}
27-
ref: ${{ inputs.ref }}
28-
2923
- name: Check if important files changed
3024
id: check
31-
run: |
32-
set -exo pipefail
25+
uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea
26+
with:
27+
script: |
28+
const { owner, repo } = context.repo;
29+
const pull_number = context.issue.number
30+
31+
return github.rest.pulls.listFiles({ owner, repo, pull_number })
32+
.then(async ({ data: files }) => {
33+
const filenames = files.map(file => file.filename);
34+
console.log(`Files in PR: ${filenames}`);
35+
36+
// Cache the parsed exercise config file's invalidator files
37+
let exerciseInvalidatorFiles = {};
38+
39+
return filenames.some(async (filename) => {
40+
const match = /^exercises\/(?<type>practice|concept)\/(?<slug>[^\/]+)\/(?<path>.+)$/i.exec(filename);
41+
if (match?.groups === undefined) {
42+
console.log(`${filename}: skipped (can't invalidate test results)`);
43+
return false;
44+
}
45+
46+
const { type, slug, path } = match.groups;
47+
const configFile = `exercises/${type}/${slug}/.meta/config.json`;
3348
34-
git remote add upstream "https://github.com/${GITHUB_REPOSITORY}.git"
35-
git fetch --depth 1 upstream main
49+
const parseInvalidatorFiles = (path) => {
50+
return github.rest.repos
51+
.getContent({ owner, repo, path })
52+
.then(({ data: { content } }) => JSON.parse(Buffer.from(content, "base64").toString()))
53+
.then((config) => {
54+
const files = config.files;
55+
if (files === undefined) {
56+
return [];
57+
}
3658
37-
git diff --diff-filter=M --name-only upstream/main
59+
return [].concat(
60+
files["invalidator"] || [],
61+
files["test"] || [],
62+
files["editor"] || []
63+
);
64+
})
65+
.catch((err) => []);
66+
};
3867
39-
for changed_file in $(git diff --diff-filter=M --name-only upstream/main); do
40-
slug="$(echo "${changed_file}" | sed --regexp-extended 's#exercises/[^/]+/([^/]+)/.*#\1#' )"
41-
path_before_slug="$(echo "${changed_file}" | sed --regexp-extended "s#(.*)/${slug}/.*#\\1#" )"
42-
path_after_slug="$( echo "${changed_file}" | sed --regexp-extended "s#.*/${slug}/(.*)#\\1#" )"
43-
config_json_file="${path_before_slug}/${slug}/.meta/config.json"
68+
exerciseInvalidatorFiles[slug] ||= await parseInvalidatorFiles(configFile);
69+
const invalidatesTests = exerciseInvalidatorFiles[slug].includes(path)
4470
45-
if ! [ -f "${config_json_file}" ]; then
46-
# cannot determine if important files changed without .meta/config.json
47-
continue
48-
fi
71+
if (invalidatesTests) {
72+
console.log(`${filename}: invalidates test results`);
73+
} else {
74+
console.log(`${filename}: does not invalidate test results`);
75+
}
4976
50-
changed=$(jq --arg path "${path_after_slug}" '[.files.test, .files.invalidator, .files.editor] | flatten | index($path) != null' "${config_json_file}")
51-
echo "important_files_changed=${changed}" >> "$GITHUB_OUTPUT"
52-
done
77+
return invalidatesTests;
78+
});
79+
})
80+
.catch((err) => false);
5381
5482
- name: Suggest to add [no important files changed]
55-
if: steps.check.outputs.important_files_changed == 'true'
83+
if: steps.check.outputs.result == 'true'
5684
uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea
5785
with:
5886
script: |

0 commit comments

Comments
 (0)