D3759: packaging: replace dockerlib.sh with a Python script
indygreg (Gregory Szorc)
phabricator at mercurial-scm.org
Mon Jun 25 11:21:01 EDT 2018
This revision was automatically updated to reflect the committed changes.
Closed by commit rHGe5916f1236f3: packaging: replace dockerlib.sh with a Python script (authored by indygreg, committed by ).
CHANGED PRIOR TO COMMIT
https://phab.mercurial-scm.org/D3759?vs=9111&id=9285#toc
REPOSITORY
rHG Mercurial
CHANGES SINCE LAST UPDATE
https://phab.mercurial-scm.org/D3759?vs=9111&id=9285
REVISION DETAIL
https://phab.mercurial-scm.org/D3759
AFFECTED FILES
contrib/packaging/dockerdeb
contrib/packaging/dockerlib.sh
contrib/packaging/dockerrpm
contrib/packaging/hg-docker
tests/test-check-module-imports.t
CHANGE DETAILS
diff --git a/tests/test-check-module-imports.t b/tests/test-check-module-imports.t
--- a/tests/test-check-module-imports.t
+++ b/tests/test-check-module-imports.t
@@ -20,6 +20,7 @@
> -X setup.py \
> -X contrib/debugshell.py \
> -X contrib/hgweb.fcgi \
+ > -X contrib/packaging/hg-docker \
> -X contrib/python-zstandard/ \
> -X contrib/win32/hgwebdir_wsgi.py \
> -X doc/gendoc.py \
diff --git a/contrib/packaging/hg-docker b/contrib/packaging/hg-docker
new file mode 100755
--- /dev/null
+++ b/contrib/packaging/hg-docker
@@ -0,0 +1,111 @@
+#!/usr/bin/env python3
+#
+# Copyright 2018 Gregory Szorc <gregory.szorc at gmail.com>
+#
+# This software may be used and distributed according to the terms of the
+# GNU General Public License version 2 or any later version.
+
+import argparse
+import pathlib
+import shutil
+import subprocess
+import sys
+
+def get_docker() -> str:
+ docker = shutil.which('docker.io') or shutil.which('docker')
+ if not docker:
+ print('could not find docker executable')
+ return 1
+
+ try:
+ out = subprocess.check_output([docker, '-h'], stderr=subprocess.STDOUT)
+
+ if b'Jansens' in out:
+ print('%s is the Docking System Tray; try installing docker.io' %
+ docker)
+ sys.exit(1)
+ except subprocess.CalledProcessError as e:
+ print('error calling `%s -h`: %s' % (docker, e.output))
+ sys.exit(1)
+
+ out = subprocess.check_output([docker, 'version'],
+ stderr=subprocess.STDOUT)
+
+ lines = out.splitlines()
+ if not any(l.startswith((b'Client:', b'Client version:')) for l in lines):
+ print('`%s version` does not look like Docker' % docker)
+ sys.exit(1)
+
+ if not any(l.startswith((b'Server:', b'Server version:')) for l in lines):
+ print('`%s version` does not look like Docker' % docker)
+ sys.exit(1)
+
+ return docker
+
+def get_dockerfile(path: pathlib.Path, args: list) -> bytes:
+ with path.open('rb') as fh:
+ df = fh.read()
+
+ for k, v in args:
+ df = df.replace(b'%%%s%%' % k, v)
+
+ return df
+
+def build_docker_image(dockerfile: pathlib.Path, params: list, tag: str):
+ """Build a Docker image from a templatized Dockerfile."""
+ docker = get_docker()
+
+ dockerfile_path = pathlib.Path(dockerfile)
+
+ dockerfile = get_dockerfile(dockerfile_path, params)
+
+ print('building Dockerfile:')
+ print(dockerfile.decode('utf-8', 'replace'))
+
+ args = [
+ docker,
+ 'build',
+ '--build-arg', 'http_proxy',
+ '--build-arg', 'https_proxy',
+ '--tag', tag,
+ '-',
+ ]
+
+ print('executing: %r' % args)
+ subprocess.run(args, input=dockerfile, check=True)
+
+def command_build(args):
+ build_args = []
+ for arg in args.build_arg:
+ k, v = arg.split('=', 1)
+ build_args.append((k.encode('utf-8'), v.encode('utf-8')))
+
+ build_docker_image(pathlib.Path(args.dockerfile),
+ build_args,
+ args.tag)
+
+def command_docker(args):
+ print(get_docker())
+
+def main() -> int:
+ parser = argparse.ArgumentParser()
+
+ subparsers = parser.add_subparsers(title='subcommands')
+
+ build = subparsers.add_parser('build', help='Build a Docker image')
+ build.set_defaults(func=command_build)
+ build.add_argument('--build-arg', action='append', default=[],
+ help='Substitution to perform in Dockerfile; '
+ 'format: key=value')
+ build.add_argument('dockerfile', help='path to Dockerfile to use')
+ build.add_argument('tag', help='Tag to apply to created image')
+
+ docker = subparsers.add_parser('docker-path', help='Resolve path to Docker')
+ docker.set_defaults(func=command_docker)
+
+ args = parser.parse_args()
+
+ return args.func(args)
+
+if __name__ == '__main__':
+ sys.exit(main())
diff --git a/contrib/packaging/dockerrpm b/contrib/packaging/dockerrpm
--- a/contrib/packaging/dockerrpm
+++ b/contrib/packaging/dockerrpm
@@ -1,16 +1,16 @@
#!/bin/bash -e
-. $(dirname $0)/dockerlib.sh
-
BUILDDIR=$(dirname $0)
export ROOTDIR=$(cd $BUILDDIR/../..; pwd)
-checkdocker
-
PLATFORM="$1"
shift # extra params are passed to buildrpm
-initcontainer $PLATFORM
+DOCKER=$($BUILDDIR/hg-docker docker-path)
+
+CONTAINER=hg-docker-$PLATFORM
+
+$BUILDDIR/hg-docker build $BUILDDIR/docker/$PLATFORM $CONTAINER
RPMBUILDDIR=$ROOTDIR/packages/$PLATFORM
$ROOTDIR/contrib/packaging/buildrpm --rpmbuilddir $RPMBUILDDIR --prepare $*
diff --git a/contrib/packaging/dockerlib.sh b/contrib/packaging/dockerlib.sh
deleted file mode 100644
--- a/contrib/packaging/dockerlib.sh
+++ /dev/null
@@ -1,30 +0,0 @@
-#!/bin/sh -eu
-
-# This function exists to set up the DOCKER variable and verify that
-# it's the binary we expect. It also verifies that the docker service
-# is running on the system and we can talk to it.
-function checkdocker() {
- if which docker.io >> /dev/null 2>&1 ; then
- DOCKER=docker.io
- elif which docker >> /dev/null 2>&1 ; then
- DOCKER=docker
- else
- echo "Error: docker must be installed"
- exit 1
- fi
-
- $DOCKER -h 2> /dev/null | grep -q Jansens && { echo "Error: $DOCKER is the Docking System Tray - install docker.io instead"; exit 1; }
- $DOCKER version | grep -Eq "^Client( version)?:" || { echo "Error: unexpected output from \"$DOCKER version\""; exit 1; }
- $DOCKER version | grep -Eq "^Server( version)?:" || { echo "Error: could not get docker server version - check it is running and your permissions"; exit 1; }
-}
-
-# Construct a container and leave its name in $CONTAINER for future use.
-function initcontainer() {
- [ "$1" ] || { echo "Error: platform name must be specified"; exit 1; }
-
- DFILE="$ROOTDIR/contrib/packaging/docker/$1"
- [ -f "$DFILE" ] || { echo "Error: docker file $DFILE not found"; exit 1; }
-
- CONTAINER="hg-dockerrpm-$1"
- cat $DFILE | $DOCKER build --build-arg http_proxy --build-arg https_proxy --tag $CONTAINER -
-}
diff --git a/contrib/packaging/dockerdeb b/contrib/packaging/dockerdeb
--- a/contrib/packaging/dockerdeb
+++ b/contrib/packaging/dockerdeb
@@ -1,21 +1,21 @@
#!/bin/bash -eu
-. $(dirname $0)/dockerlib.sh
. $(dirname $0)/packagelib.sh
BUILDDIR=$(dirname $0)
export ROOTDIR=$(cd $BUILDDIR/../.. > /dev/null; pwd)
-checkdocker
-
DISTID="$1"
CODENAME="$2"
PLATFORM="$1-$2"
shift; shift # extra params are passed to build process
OUTPUTDIR=${OUTPUTDIR:=$ROOTDIR/packages/$PLATFORM}
+CONTAINER=hg-docker-$PLATFORM
-initcontainer $PLATFORM
+DOCKER=$($BUILDDIR/hg-docker docker-path)
+
+$BUILDDIR/hg-docker build $BUILDDIR/docker/$PLATFORM $CONTAINER
# debuild only appears to be able to save built debs etc to .., so we
# have to share the .. of the current directory with the docker
To: indygreg, #hg-reviewers, durin42
Cc: mercurial-devel
More information about the Mercurial-devel
mailing list