diff --git a/Dockerfile b/Dockerfile index d1a46a30..26dc0051 100644 --- a/Dockerfile +++ b/Dockerfile @@ -34,7 +34,6 @@ FROM balenalib/amd64-node:6-build as i386-nlp-node-build FROM $ARCH-node-build as node-build -ARG NPM_VERSION WORKDIR /usr/src/app @@ -51,6 +50,7 @@ RUN apt-get update \ COPY package.json package-lock.json /usr/src/app/ +ARG NPM_VERSION # We first ensure that every architecture has an npm version # which can do an npm ci, then we perform the ci using this # temporary version @@ -73,8 +73,6 @@ RUN npm test \ # Build nodejs dependencies FROM $ARCH-node-base as node-deps -ARG ARCH -ARG NPM_VERSION RUN [ "cross-build-start" ] @@ -96,6 +94,7 @@ RUN mkdir -p rootfs-overlay && \ COPY package.json package-lock.json /usr/src/app/ +ARG NPM_VERSION # Install only the production modules that have C extensions RUN curl -LOJ https://www.npmjs.com/install.sh && \ npm config set unsafe-perm true && \ @@ -125,9 +124,6 @@ RUN [ "cross-build-end" ] # Minimal runtime image FROM balena/$ARCH-supervisor-base:v1.4.7 -ARG ARCH -ARG VERSION=master -ARG DEFAULT_MIXPANEL_TOKEN=bananasbananas WORKDIR /usr/src/app @@ -140,6 +136,9 @@ COPY avahi-daemon.conf /etc/avahi/avahi-daemon.conf VOLUME /data +ARG ARCH +ARG VERSION=master +ARG DEFAULT_MIXPANEL_TOKEN=bananasbananas ENV CONFIG_MOUNT_POINT=/boot/config.json \ LED_FILE=/dev/null \ SUPERVISOR_IMAGE=resin/$ARCH-supervisor \ diff --git a/Dockerfile.debug b/Dockerfile.debug index 1e4111bd..cdb0dafd 100644 --- a/Dockerfile.debug +++ b/Dockerfile.debug @@ -3,41 +3,47 @@ ARG NPM_VERSION=6.9.0 # The node version here should match the version of the runtime image which is # specified in the base-image subdirectory in the project -FROM balenalib/raspberry-pi-node:10-run as rpi-base -FROM balenalib/armv7hf-node:10-run as armv7hf-base -FROM balenalib/aarch64-node:10-run as aarch64-base +FROM balenalib/raspberry-pi-node:10-run as rpi-node-base +FROM balenalib/armv7hf-node:10-run as armv7hf-node-base +FROM balenalib/aarch64-node:10-run as aarch64-node-base RUN [ "cross-build-start" ] RUN sed -i '/security.debian.org jessie/d' /etc/apt/sources.list RUN [ "cross-build-end" ] -FROM balenalib/amd64-node:10-run as amd64-base +FROM balenalib/amd64-node:10-run as amd64-node-base RUN echo '#!/bin/sh\nexit 0' > /usr/bin/cross-build-start && chmod +x /usr/bin/cross-build-start \ && echo '#!/bin/sh\nexit 0' > /usr/bin/cross-build-end && chmod +x /usr/bin/cross-build-end -FROM balenalib/i386-node:10-run as i386-base +FROM balenalib/i386-node:10-run as i386-node-base RUN echo '#!/bin/sh\nexit 0' > /usr/bin/cross-build-start && chmod +x /usr/bin/cross-build-start \ && echo '#!/bin/sh\nexit 0' > /usr/bin/cross-build-end && chmod +x /usr/bin/cross-build-end -FROM balenalib/i386-nlp-node:6-jessie as i386-nlp-base +FROM balenalib/i386-nlp-node:6-jessie as i386-nlp-node-base RUN echo '#!/bin/sh\nexit 0' > /usr/bin/cross-build-start && chmod +x /usr/bin/cross-build-start \ && echo '#!/bin/sh\nexit 0' > /usr/bin/cross-build-end && chmod +x /usr/bin/cross-build-end -# A little hack to make this work with the makefile -FROM $ARCH-base AS node-build -FROM $ARCH-base AS node-deps - -ARG ARCH -ARG VERSION=master -ARG DEFAULT_MIXPANEL_TOKEN=bananasbananas +FROM $ARCH-node-base AS node-deps RUN [ "cross-build-start" ] WORKDIR /usr/src/app -RUN apt-get update && apt-get install ca-certificates \ - iptables libnss-mdns nodejs rsync git python make curl g++ \ - kmod vim +RUN apt-get update \ + && apt-get install -y \ + ca-certificates \ + g++ \ + git \ + kmod \ + iptables \ + libnss-mdns \ + make \ + nodejs \ + python \ + rsync \ + curl \ + vim +ARG NPM_VERSION # We first ensure that every architecture has an npm version # which can do an npm ci, then we perform the ci using this # temporary version @@ -62,6 +68,9 @@ COPY entry.sh . RUN mkdir -p rootfs-overlay && \ (([ ! -d rootfs-overlay/lib64 ] && ln -s /lib rootfs-overlay/lib64) || true) +ARG ARCH +ARG VERSION=master +ARG DEFAULT_MIXPANEL_TOKEN=bananasbananas ENV CONFIG_MOUNT_POINT=/boot/config.json \ LED_FILE=/dev/null \ SUPERVISOR_IMAGE=resin/$ARCH-supervisor \ diff --git a/Makefile b/Makefile index 3282984b..e9ff16e7 100644 --- a/Makefile +++ b/Makefile @@ -154,7 +154,7 @@ endif --build-arg ARCH=$(ARCH) \ --build-arg VERSION=$(shell jq -r .version package.json) \ --build-arg DEFAULT_MIXPANEL_TOKEN=$(MIXPANEL_TOKEN) \ - `if [ -z "$$DEBUG" ]; then echo ''; else echo '-f Dockerfile.debug'; fi` \ + `if [ -n "$$DEBUG" ]; then echo '-f Dockerfile.debug'; fi` \ -t $(IMAGE) . supervisor: diff --git a/automation/build.sh b/automation/build.sh index 0dc9e94b..e7d1aeba 100755 --- a/automation/build.sh +++ b/automation/build.sh @@ -38,10 +38,6 @@ if [ -z "$ARCH" ] || [ -z "$TAG" ]; then exit 1 fi -function tryRemove() { - docker rmi $1 || true -} - # This is the supervisor image we will produce TARGET_IMAGE=balena/$ARCH-supervisor:$TAG$DEBUG @@ -49,45 +45,58 @@ TARGET_IMAGE=balena/$ARCH-supervisor:$TAG$DEBUG NODE_IMAGE=balena/$ARCH-supervisor-node:$TAG$DEBUG NODE_BUILD_IMAGE=balena/$ARCH-supervisor-node:$TAG-build$DEBUG -TARGET_CACHE=$TARGET_IMAGE -NODE_CACHE=$NODE_IMAGE -NODE_BUILD_CACHE=$NODE_BUILD_IMAGE - TARGET_CACHE_MASTER=balena/$ARCH-supervisor:master$DEBUG NODE_CACHE_MASTER=balena/$ARCH-supervisor-node:master$DEBUG NODE_BUILD_CACHE_MASTER=balena/$ARCH-supervisor-node:master-build$DEBUG CACHE_FROM="" -function tryPullForCache() { +function useCache() { image=$1 - docker pull $image && { - CACHE_FROM="$CACHE_FROM --cache-from $image" - } || true + # Always add the cache because we can't do it from + # a subshell and specifying a missing image is fine + CACHE_FROM="$CACHE_FROM --cache-from $image" + # Pull in parallel for speed + docker pull $image & } -# Attempt to pull images for cache -# Only if the pull succeeds we add a --cache-from option -tryPullForCache $TARGET_CACHE & -tryPullForCache $TARGET_CACHE_MASTER & -tryPullForCache $NODE_CACHE & -tryPullForCache $NODE_CACHE_MASTER & -tryPullForCache $NODE_BUILD_CACHE & -tryPullForCache $NODE_BUILD_CACHE_MASTER & +useCache $TARGET_IMAGE +useCache $TARGET_CACHE_MASTER +useCache $NODE_IMAGE +useCache $NODE_CACHE_MASTER +# Debug images don't include nodebuild or use the supervisor-base image +if [ -z "$DEBUG" ]; then + useCache $NODE_BUILD_IMAGE + useCache $NODE_BUILD_CACHE_MASTER + + docker pull balenalib/amd64-node:6-build & + docker pull balena/$ARCH-supervisor-base:v1.4.7 & +fi +# Pull images we depend on in parallel to avoid needing +# to do it in serial during the build +docker pull balenalib/raspberry-pi-node:10-run & +docker pull balenalib/armv7hf-node:10-run & +docker pull balenalib/aarch64-node:10-run & +docker pull balenalib/amd64-node:10-run & +docker pull balenalib/i386-node:10-run & +docker pull balenalib/i386-nlp-node:6-jessie & wait export DOCKER_BUILD_OPTIONS=${CACHE_FROM} export ARCH export MIXPANEL_TOKEN -make IMAGE=$NODE_BUILD_IMAGE nodebuild -if [ "$PUSH_IMAGES" = "true" ]; then - make IMAGE=$NODE_BUILD_IMAGE deploy || true +# Debug images don't include nodebuild +if [ -z "$DEBUG" ]; then + make IMAGE=$NODE_BUILD_IMAGE nodebuild + if [ "$PUSH_IMAGES" = "true" ]; then + make IMAGE=$NODE_BUILD_IMAGE deploy & + fi + export DOCKER_BUILD_OPTIONS="${DOCKER_BUILD_OPTIONS} --cache-from ${NODE_BUILD_IMAGE}" fi -export DOCKER_BUILD_OPTIONS="${DOCKER_BUILD_OPTIONS} --cache-from ${NODE_BUILD_IMAGE}" make IMAGE=$NODE_IMAGE nodedeps if [ "$PUSH_IMAGES" = "true" ]; then - make IMAGE=$NODE_IMAGE deploy || true + make IMAGE=$NODE_IMAGE deploy & fi export DOCKER_BUILD_OPTIONS="${DOCKER_BUILD_OPTIONS} --cache-from ${NODE_IMAGE}" @@ -103,13 +112,12 @@ if [ "$PUSH_IMAGES" = "true" ]; then fi fi +# Wait for any ongoing deploys +wait if [ "$CLEANUP" = "true" ]; then - tryRemove $TARGET_IMAGE - - tryRemove $NODE_IMAGE - tryRemove $NODE_BUILD_IMAGE - - tryRemove $TARGET_CACHE - tryRemove $NODE_BUILD_CACHE - tryRemove $NODE_CACHE + docker rmi \ + $TARGET_IMAGE \ + $NODE_IMAGE \ + $NODE_BUILD_IMAGE \ + $TARGET_CACHE fi