diff --git a/precise/docker-updater/README b/precise/docker-updater/README new file mode 100644 index 0000000..81eb76c --- /dev/null +++ b/precise/docker-updater/README @@ -0,0 +1,28 @@ + + +Unfinished because untested. But, the script docker-updater is +tested and used. + + +This LXC requires a kernel >3.8 at least. (to be able to run docker in +LXC) It requires also "aufs" capabilities (apparmor.d permission, but +also available in kernel) + +XXXvlab: we could run docker in LXC via a socket towards an host's +install of docker and remove this constraint. + + +It is meant to build image of applications based on a single git-sub +code. + +It provides an IMAGE that does not requires 'git' tool, and won't +contain any git history. + +Then, it'll be able to update this image by small "docker commits" +quite efficiently. + + +Currently the image produced can only be run on docker host that +support running aufs in the containers (this implies, that the docker +fs driver IS NOT aufs, that the host kernel support aufs, and that +permissions are set so that container can mount an aufs filesystem). diff --git a/precise/docker-updater/config b/precise/docker-updater/config new file mode 100644 index 0000000..de6f698 --- /dev/null +++ b/precise/docker-updater/config @@ -0,0 +1 @@ +lxc.aa_profile = unconfined diff --git a/precise/docker-updater/hooks/install b/precise/docker-updater/hooks/install new file mode 100755 index 0000000..aa7ba34 --- /dev/null +++ b/precise/docker-updater/hooks/install @@ -0,0 +1,10 @@ +#!/bin/bash + +set -eux # -x for verbose logging to juju debug-log + +## +## Init.d and defaults running options +## + +cp src/usr/local/sbin/* src/usr/local/sbin/ + diff --git a/precise/docker-updater/hooks/start b/precise/docker-updater/hooks/start new file mode 100755 index 0000000..9eb7853 --- /dev/null +++ b/precise/docker-updater/hooks/start @@ -0,0 +1,3 @@ +#!/bin/bash + +juju-log "Nothing to Start for base." diff --git a/precise/docker-updater/hooks/stop b/precise/docker-updater/hooks/stop new file mode 100755 index 0000000..170162b --- /dev/null +++ b/precise/docker-updater/hooks/stop @@ -0,0 +1,3 @@ +#!/bin/bash + +juju-log "Nothing to stop for base." diff --git a/precise/docker-updater/metadata.yaml b/precise/docker-updater/metadata.yaml new file mode 100644 index 0000000..f83b91f --- /dev/null +++ b/precise/docker-updater/metadata.yaml @@ -0,0 +1,9 @@ +name: docker-updater +summary: "Docker Updater" +maintainer: "Valentin Lab " +inherit: docker +description: | + Docker Updater +data-resources: + - /var/lib/docker + - /srv/docker-updates diff --git a/precise/docker-updater/revision b/precise/docker-updater/revision new file mode 100644 index 0000000..573541a --- /dev/null +++ b/precise/docker-updater/revision @@ -0,0 +1 @@ +0 diff --git a/precise/docker-updater/src/usr/local/bin/docker-update b/precise/docker-updater/src/usr/local/bin/docker-update new file mode 100755 index 0000000..f68d203 --- /dev/null +++ b/precise/docker-updater/src/usr/local/bin/docker-update @@ -0,0 +1,103 @@ +#!/bin/bash + + +#!- +. /etc/shlib +#!- + + +DOCKER_UPDATE_PATH=${DOCKER_UPDATE_PATH:-/srv/docker-updates} + + +include common +include pretty + +usage="$exname COMPONENT MASTER_IMAGE_NAME BRANCH UPDATED_IMAGE_NAME" + + +COMPONENT_NAME="$1" +MASTER_IMAGE_NAME="$2" +BRANCH="$3" +UPDATED_IMAGE_NAME="$4" + +## Note: we will need in the DOCKER_UPDATE_HOST: +## - git-sub + +## should we check for aufs ? + +mkdir -p "$DOCKER_UPDATE_PATH" +cd "$DOCKER_UPDATE_PATH" +if ! [ -d "$COMPONENT_NAME" ]; then + echo "ERROR: repository $DOCKER_UPDATE_PATH//$COMPONENT_NAME is not existent." + echo "You should build it on this host prior to run this hook." + echo "As a remainder: this host is supposed to keep the reference git that" + echo "was used to built the master image." + exit 1 +fi + +if [ -e "$COMPONENT_NAME.locked" ]; then + echo "Master is being updated." + echo "Or '$COMPONENT_NAME.locked' file was left dangling over." + exit 1 +fi + + +clean_all() { + cd / + mountpoint "$tmpdir_root" 2>/dev/null && umount "$tmpdir_root" + [ -d "$tmpdir_root" ] && rmdir "$tmpdir_root" + [ -d "$tmpdir_changes" ] && rm -rf "$tmpdir_changes" +} + +tmpdir_changes=$(mktemp -d /tmp/$COMPONENT_NAME.changes.XXXXXX) +tmpdir_root=$(mktemp -d /tmp/$COMPONENT_NAME.root.XXXXXX) + +trap "clean_all" EXIT +mount -t aufs -o br=$tmpdir_changes:$DOCKER_UPDATE_PATH/$COMPONENT_NAME -o udba=none none "$tmpdir_root" +cd "$tmpdir_root" + +## XXXvlab: We probably would need to: +## - fetch only the module concerned +## - fetch only the ref concerned +git fetch origin "$BRANCH" +git checkout "$BRANCH" +git sub update + +cd / && +umount "$tmpdir_root" && +rmdir "$tmpdir_root" +if [ "$?" != 0 ]; then + echo "Uh oh... could not umount aufs $tmpdir_root or delete it." + exit 1 +fi +cd "$tmpdir_changes" + +echo "Cleaning the change layer." +find . -name .git -type d -exec rm -rf {} \; -prune + +## XXXvlab: if we produced it we shouldn't have to pull it +echo "Pulling $MASTER_IMAGE_NAME" +docker pull "$MASTER_IMAGE_NAME" >/dev/null 2>&1 + +container_id=$(docker run -d \ + -v $tmpdir_changes:/mnt/changes \ + "$MASTER_IMAGE_NAME" \ + /bin/bash -c " + mkdir -p /srv/app/{root,changes} + cp -a /mnt/changes /srv/app/changes/0000 + ls /srv/app/changes/0000 + ") + +if [ "$(docker wait "$container_id")" != "0" ]; then + echo "Copy of changes to docker images failed !" + echo "Log of container:" + docker logs $container_id + exit 1 +fi + +docker commit --author "$exname" \ + --message "Automatic Updater" \ + "$container_id" \ + "$UPDATED_IMAGE_NAME" + +docker push "$UPDATED_IMAGE_NAME"