forked from rust-secure-code/cargo-supply-chain
-
Notifications
You must be signed in to change notification settings - Fork 0
/
release_checks
executable file
·116 lines (95 loc) · 4.1 KB
/
release_checks
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
#!/bin/bash
determine_new_version() {
grep "version = " Cargo.toml | sed -Ee 's/version = "(.*)"/\1/' | head -1
}
determine_crate_name() {
grep "name = " Cargo.toml | sed -Ee 's/name = "(.*)"/\1/' | head -1
}
check_published_version() {
cirrus_agent="${CIRRUS_CI/?*/(Cirrus-CI)}"
final_agent="Release-Script/1.0 ${cirrus_agent:-(local)} (for $crate) (author:HeroicKatora)"
echo $final_agent
# Does the api information start with: '{"errors":'
[[ $(wget -U "$final_agent" --content-on-error "https://crates.io/api/v1/crates/$crate/$new_version" -qO -) == "{\"errors\":"* ]] || {
published_commit=$(wget -U "$final_agent" "https://crates.io/api/v1/crates/$crate/$new_version/download" -qO - | tar xOzf - "$crate-$new_version/.cargo_vcs_info.json")
published_commit=$(sed 's/\"sha1\": \"\(.*\)\"/\1/;T0;p;:0;d' <<< "$published_commit")
echo "Already published at" "$published_commit"
}
}
git_considered_clean() {
[[ -z $(git status -s) ]]
}
count_wip_marker() {
# WIP alone is not a marker
[[ -z $(grep "\[WIP\]" Changes.md Readme.md) ]]
}
check_release_changes() {
[[ -z $(grep "# v$new_version" Changes.md) ]]
}
make_git_tag() {
tag_edit_msg="../.git/TAG_MSG_$(uuidgen)"
touch "$tag_edit_msg"
function cleanup() {
rm "$tag_edit_msg"
}
trap cleanup EXIT
# Extract the verion specific section from Changes.md
# Delete lines until $new_version header
# Delete lines starting from the next header
# Delete all empty lines at the start
# Use as the initial message for a signed tag, but open edit anyways
echo $(pwd)
sed -e '0,/'"$new_version"'/d;/\#/,$d;/./,$!d' Changes.md >> "$tag_edit_msg"
echo >> "$tag_edit_msg"
# Sign the package content by including its hash in the tag
sha256sum "../target/package/${crate}-${new_version}.crate" >> "$tag_edit_msg"
git tag -s -F "$tag_edit_msg" -e "${crate}-v${new_version}" $published_commit
}
is_force=""
do_tag=""
for param in $@
do
case "$param" in
-f) is_force="-f";;
--tag) do_tag="yes";;
--help) ;&
-h) { cat << EOF
usage: release [-f] [-h|--help] <version>
Automates checks and tagging of new releases. Encourages a workflow where
planned changes are integrated into readme and migration documentation early,
with WIP markers to help produce complete logs.
-f Force usage of version, even if such a tag already exists.
-h, --help Display this help
<version> A semantic version number matching [0-9a-zA-Z.-]*
EOF
exit 1; } ;;
esac
done
new_version="$(determine_new_version)"
crate="$(determine_crate_name)"
# check it is a sane version number
[[ -z $(grep -vE '[0-9a-zA-Z.-]*' <<< "$new_version" ) ]] || { echo "Fail: Check version number: ${new_version}"; exit 1; }
# check we identified the crate
[[ -z "$crate" ]] && { echo "Couldn't determine crate name"; exit 1; }
# Check that the working dir is clean. May comment this out if it produces problems.
git_considered_clean || { echo "Fail: Working directory is not clean"; exit 1; }
# Check that for every author, we have at least name or mail recorded in Contributors.txt
# For each commit author, checks that either his/her name or respective mail
# address appears in the contributors file. Note that a .mailcap file could be
# introduced to canonicalize these names in the output of git-shortlog already.
# Since this needs GNU parallel, the check is optional.
if [[ -f Contributors.txt ]]; then
if which parallel 2>/dev/null; then
{ (git shortlog -se | parallel -C '\t|<' grep -Fq -e '{2}' -e '\<{3}' Contributors.txt) || { echo "Fail: contributor not listed"; exit 1; }; }
else
{ echo "Checking contributors needs GNU parallel, please make sure manually." 1>&2; }
fi
fi
check_published_version || { echo "Version $new_version appears already published"; exit 1; }
# Check there are no more [WIP] markers in Migrate and Readme
count_wip_marker || { echo "Fail: Work in progress in documentation"; exit 1; }
# Find a matching header in the changelog
check_release_changes && { echo "Fail: No changelog regarding this release"; exit 1; }
# Packaging works. Note: does not publish the version.
cargo package || { echo "Fail: cargo could not package successfully"; exit 1; }
[[ -z $do_tag ]] || make_git_tag