-
Notifications
You must be signed in to change notification settings - Fork 52
/
Copy pathadd-workflow-file-to-repositories.sh
executable file
·101 lines (83 loc) · 3.45 KB
/
add-workflow-file-to-repositories.sh
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
#!/bin/bash
# Adds a workflow file to the default branch in a CSV list of repositories
# Usage:
# Step 1: Run ./generate-repositories-list.sh <org> > repos.csv
# - Or create a list of repos in a csv file, 1 per line, with a trailing empty line at the end of the file
# - DO NOT REMOVE TRAILING NEW LINE IN THE INPUT CSV FILE
# Step 2: ./add-workflow-file-to-repositories.sh repos.csv ./docker-image.yml true 390793 41851701 ./my-app.2023-09-15.private-key.pem
#
# Overwrite or append:
# - Defaults to append
# - If you want to overwrite the workflow file, pass true as the 3rd argument, otherwise, it will skip
#
# Prerequisites:
# 1. Install gh (brew install gh)
# 2. Authenticate with gh (gh auth login)
# 3. Have the following extension installed: gh extension install lindluni/gh-token
# 4. Create a GitHub App, grab its App ID, Installation ID, and generate a private key
# - App will need "administration: read & write", "contents: read & write", "workflow: read & write", and be installed in the repo(s) you want to add the workflow file to
# - TODO: If Pull Request functionality is added, will also need "pull requests: read & write"
# 5. Run the script
#
set -e
if [ $# -lt "6" ]; then
echo "Usage: $0 <repos-list-file> <workflow-file> <overwrite: true|false> <app-id> <installation-id> <private-key-path>"
exit 1
fi
if [ ! -f "$1" ]; then
echo "Repo import file $1 does not exist"
exit 1
fi
if [ ! -f "$2" ]; then
echo "Workflow file $2 does not exist"
exit 1
fi
filename="$1"
workflow_file="$2"
overwrite="$3"
app_id="$4"
installation_id="$5"
private_key_path="$6"
echo "..." && echo ""
# get the friendly name of $filename
workflow_file_basename=$(basename -- "$workflow_file")
token=$(gh token generate --app-id $app_id --installation-id $installation_id --key "$private_key_path" --token-only)
while read -r repofull ;
do
IFS='/' read -ra data <<< "$repofull"
org=${data[0]}
repo=${data[1]}
echo "Checking $org/$repo ..."
# check if it exists first
if file=$(GH_TOKEN=$token gh api /repos/$org/$repo/contents/.github/workflows/$workflow_file_basename 2>/dev/null); then
exists=1
message="Replacing workflow $workflow_file_basename"
else
exists=0
message="Adding workflow $workflow_file_basename"
fi
if [ $exists=1 ]; then
sha=$(echo $file | jq -r '.sha')
echo " ... workflow $workflow_file_basename already exists"
# if $overwrite is true, then delete the workflow file
if [ "$overwrite" != true ] ; then
echo " ... replacing workflow $workflow_file_basename"
fi
else
echo " ... workflow $workflow_file_basename doesn't exist"
sha=""
fi
# Commit the workflow file
echo " ... comitting .github/workflows/$workflow_file_basename to $org/$repo"
if response=$(GH_TOKEN=$token gh api -X PUT /repos/$org/$repo/contents/.github/workflows/$workflow_file_basename -f message="$message" -f content="$(base64 -i $workflow_file)" -f sha=$sha 2>/dev/null); then
path=$(echo $response | jq -r '.content.path')
sha=$(echo $response | jq -r '.content.sha')
date=$(echo $response | jq -r '.commit.committer.date')
echo " ... committed $path with sha $sha on $date"
else
error=$(echo $response | jq -r ".message")
echo " ... failed to commit $path; $error"
# TODO: Create PR if error is "Changes must be made through a pull request."
fi
echo ""
done < "$filename"