Skip to content

Commit bf3b306

Browse files
committed
Initial introduction of a opam-release tool
This is a tool to generate a branch (and a pull-request manually) from the opam meta data local to the repository. Most of the arguments are inferred automatically if one: - has a unique file named <your-project>.opam - is using a github repository - has their github username configured in their global .gitconfig - has performed git remote update - the dev-repo is set in the opam file - opam is installed Arguments can be supplied to fix any of the default behavior (or their absence thereof). One can witness the inferred arguments by providing option `-s`
1 parent 6d0eada commit bf3b306

1 file changed

Lines changed: 257 additions & 0 deletions

File tree

opam-release.sh

Lines changed: 257 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,257 @@
1+
#!/usr/bin/env bash
2+
set -e
3+
4+
if [ "$DEBUG" = 1 ]; then
5+
set -x
6+
fi
7+
8+
show_help(){
9+
cat <<EOF
10+
Usage : opam-release (arguments)* (opam-files)*
11+
--
12+
Optional arguments:
13+
opam-files: one or many opam files to push to opam-coq-archive
14+
*if no argument is provided, it lists *.opam files in the current directory
15+
-u GITHUBUSER / --user GITHUBUSER:
16+
where GITHUBUSER is your github username,
17+
you must have a fork of coq/opam-coq-archive under
18+
https://github.com/$GITHUBUSER/opam-coq-archive
19+
for this command to work,
20+
* if not provided, tries "git config --get github.user"
21+
-p PROJECT / --project PROJECT:
22+
where PROJECT is a name of the project,
23+
without space, it is used solely for generating
24+
the name of the branch and PR,
25+
* automatically infered from the name of the opam file
26+
if only one was given,
27+
-e DEPTH / --depth DEPTH:
28+
sets the depth of the local clone of opam-coq-archive to $DEPTH
29+
* defaults to full clone,
30+
you may want to fix the DEPTH to save bandwidth and time
31+
-V VERSION / --version VERSION:
32+
where VERSION is the opam version number of
33+
the package to create,
34+
* if no version is provided, tries to find the latest tag,
35+
you may want to perform a "git remote update" to fetch all tags first
36+
-U URL / --url URL:
37+
where URL is the url of the archive associated
38+
with the version to release.
39+
* tries to infer it from the "dev-repo" section if one opam file is provided
40+
-x PREFIX / --version-prefix PREFIX: the tag of a version is equal to $PREFIX$VERSION
41+
* default is ""
42+
** this options is used only if URL is not provided
43+
-d / --dev: pushes an update to extra-dev instead of releases
44+
-C / --no-check-upstream: tells opam lint not to check the sum online
45+
-h / -? / --help: print this usage
46+
-s / --show-defaults: prints the default inferred setting and exists
47+
-v / --verbose: show debug information
48+
-L / --no-lint: do not run opam lint
49+
(not recommended but useful if you do not have opam installed)
50+
-n / --do-nothing: do not push anything
51+
EOF
52+
}
53+
54+
die() {
55+
printf '%s\n' "$1" >&2
56+
exit 1
57+
}
58+
59+
GITHUBUSER=$(git config --get github.user)
60+
VERSION=$(git describe --tags --abbrev=0 | sed -e "s/[^0-9]*\(\([0-9]+|\.\)\)*/\1/")
61+
PROJECT=
62+
URL=
63+
LINT=1
64+
NOTHING=0
65+
DEPTH=
66+
HDEPTH=
67+
TARGET="released"
68+
OPAM=()
69+
CHECKUPSTREAM="--check-upstream"
70+
VERSIONPREFIX=
71+
SHOWDEFAULTS=0
72+
73+
while :; do
74+
case $1 in
75+
-h|-\?|--help)
76+
show_help # Display a usage synopsis.
77+
exit 0
78+
;;
79+
-u|--user)
80+
if [ "$2" ]; then GITHUBUSER=$2; shift; shift
81+
else die 'ERROR: "--user" requires a non-empty argument, cf --help'
82+
fi
83+
;;
84+
-p|--project)
85+
if [ "$2" ]; then PROJECT=$2; shift; shift
86+
else die 'ERROR: "--name" requires a non-empty argument, cf --help'
87+
fi
88+
;;
89+
-V|--version)
90+
if [ "$2" ]; then VERSION=$2; shift; shift
91+
else die 'ERROR: "--name" requires a non-empty argument, cf --help'
92+
fi
93+
;;
94+
-U|--url)
95+
if [ "$2" ]; then URL=$2; shift; shift
96+
else die 'ERROR: "--name" requires a non-empty argument, cf --help'
97+
fi
98+
;;
99+
-e|--depth)
100+
if [ "$2" ]; then HDEPTH="$2"; DEPTH="--depth=$2"; shift; shift
101+
else die 'ERROR: "--name" requires a non-empty argument, cf --help'
102+
fi
103+
;;
104+
-x|--version-prefix)
105+
if [ "$2" ]; then VERSIONPREFIX=$2; shift; shift
106+
else die 'ERROR: "--name" requires a non-empty argument, cf --help'
107+
fi
108+
;;
109+
-L|--no-lint)
110+
LINT=0; shift
111+
;;
112+
-d|--dev)
113+
TARGET="extra-dev"
114+
VERSION="dev"
115+
CHECKUPSTREAM=
116+
shift
117+
;;
118+
-C|--no-check-upstream)
119+
CHECKUPSTREAM=
120+
shift
121+
;;
122+
-v|--verbose)
123+
VERBOSE=1; shift
124+
;;
125+
-s|--show-defaults)
126+
SHOWDEFAULTS=1; shift
127+
;;
128+
-n|--do-nothing)
129+
NOTHING=1; shift
130+
;;
131+
*) # unknown option
132+
if ! [ "$*" ]; then
133+
break
134+
elif [ -f "$1" ]; then
135+
OPAM+=("$1")
136+
shift
137+
else die 'ERROR: positional arguments must be a file'
138+
fi
139+
;;
140+
esac
141+
done
142+
143+
if ! [ "$OPAM" ]; then
144+
OPAM=(); for opam in *.opam; do OPAM+=("$opam"); done
145+
fi
146+
147+
eval set -- "${OPAM[@]}"
148+
149+
if ! [ "GITHUBUSER" ]; then
150+
die 'ERROR: -u / --user argument is required, cf --help'
151+
fi
152+
153+
if ! [ "VERSION" ]; then
154+
die 'ERROR: -V / --version argument is required, cf --help'
155+
fi
156+
157+
158+
case "${#OPAM[@]}" in
159+
0)
160+
die 'ERROR: no opam file provided or found cf --help'
161+
;;
162+
1)
163+
if ! [ "$PROJECT" ]; then
164+
PROJECT=$(basename "${OPAM[0]}" .opam)
165+
fi
166+
;;
167+
*)
168+
if ! [ "$PROJECT" ]; then
169+
die 'ERROR: -p / --project argument is required when more than one opam files are given, cf --help'
170+
fi
171+
;;
172+
esac
173+
174+
if ! [ "$URL" ]; then
175+
if [ "$TARGET" = "released" ]; then
176+
URL=$(opam show -f dev-repo --file "${OPAM[0]}" | sed -e "s/git+//" | sed -e "s+\.git+/archive/${VERSIONPREFIX}${VERSION}.tar.gz+")
177+
else
178+
URL="$(opam show -f dev-repo --file ${OPAM[0]})#master"
179+
fi
180+
fi
181+
182+
if [ "$VERBOSE" = 1 ] || [ "$SHOWDEFAULTS" = 1 ]; then
183+
echo "# this would call"
184+
echo "$0 \\"
185+
if [ "$VERBOSE" = 1 ]; then echo "-v \\"; fi
186+
echo "-u $GITHUBUSER \\"
187+
echo "-V $VERSION \\"
188+
echo "-p $PROJECT \\"
189+
echo "-U $URL \\"
190+
if [ "$LINT" = 0 ]; then echo "-L \\"; fi
191+
if [ "$NOTHING" = 1 ]; then echo "-n \\"; fi
192+
if [ "$HDEPTH" ]; then echo "-e $HDEPTH \\"; fi
193+
if [ "$TARGET" = "extra-dev" ]; then echo "--dev \\"; fi
194+
if ! [ "$CHECKUPSTREAM" ]; then echo "-C \\"; fi
195+
echo "${OPAM[@]}"
196+
197+
fi
198+
199+
if [ "$SHOWDEFAULTS" = 1 ]; then
200+
exit
201+
fi
202+
203+
COA=$(mktemp -d) # stands for Coq Opam Archive
204+
git clone $DEPTH git@github.com:coq/opam-coq-archive $COA -o upstream
205+
git -C $COA remote add origin git@github.com:$GITHUBUSER/opam-coq-archive
206+
BRANCH=$PROJECT.$VERSION
207+
git -C $COA checkout -b $BRANCH
208+
PKGS=$COA/$TARGET/packages
209+
210+
ARCHIVE=$(mktemp)
211+
if [ "$TARGET" = "released" ]; then
212+
curl -L $URL -o $ARCHIVE
213+
SUM=$(sha256sum $ARCHIVE | cut -d " " -f 1)
214+
fi
215+
216+
if [ "$VERBOSE" = 1 ]; then
217+
echo "COA=$COA"
218+
echo "BRANCH=$BRANCH"
219+
echo "PKGS=$PKGS"
220+
echo "ARCHIVE=$ARCHIVE"
221+
echo "SUM=$SUM"
222+
fi
223+
224+
for opam in ${OPAM[@]}; do
225+
B=$(basename $opam .opam)
226+
P=$PKGS/$B/$B.$VERSION
227+
mkdir -p $P
228+
sed "/^version:.*/d" $opam > $P/opam
229+
sed -i -e '/^[ \t]*#/d' $P/opam
230+
echo "" >> $P/opam
231+
echo "url {" >> $P/opam
232+
echo " src: \"$URL\"" >> $P/opam
233+
if [ "$TARGET" = "released" ]; then
234+
echo " checksum: \"sha256=$SUM\"" >> $P/opam
235+
fi
236+
echo "}" >> $P/opam
237+
if [ "$LINT" = 1 ]; then
238+
opam lint $CHECKUPSTREAM $P/opam
239+
else
240+
echo "linting disabled (not recommended)"
241+
fi
242+
git -C $COA add $P/opam
243+
done
244+
245+
if [ "$NOTHING" = 1 ]; then
246+
echo "Dry running!"
247+
echo git -C $COA commit -m "Release $PROJECT $VERSION"
248+
echo git -C $COA push origin -f $BRANCH
249+
else
250+
git -C $COA commit -m "Update $PROJECT $VERSION"
251+
git -C $COA push origin -f $BRANCH
252+
echo "**********************************************************************"
253+
echo "Create a pull request by visiting"
254+
echo "https://github.com/$GITHUBUSER/opam-coq-archive/pull/new/$BRANCH"
255+
echo "**** PLEASE CHECK CAREFULLY THE GENERATED CODE ***"
256+
echo "**********************************************************************"
257+
fi

0 commit comments

Comments
 (0)