Skip to content

Commit

Permalink
ci: create dependency cache layer of interop tests
Browse files Browse the repository at this point in the history
Currently, the Docker images for the HEAD branch of the pull-request get re-built completely every time we push a new commit to a branch. That is because the RUN caches use the local disk of the host system but those are ephemeral in GitHub actions.

To fix this, we rewrite the dockerfiles to use `cargo chef`, a tool developed to create a cached layer of built dependencies that doesn't get invalidated as the application source changes.

Normally, these layers are also cached on the local filesystem. To have them available across pull-requests and branches, we instruct buildkit to use the same S3 cache as we use in the interop tests already for docker layers. As a result, this should greatly speed up our CI.

Resolves: #3925.

Pull-Request: #4593.
  • Loading branch information
thomaseizinger authored Oct 5, 2023
1 parent 246acfd commit 7d1d67c
Show file tree
Hide file tree
Showing 3 changed files with 48 additions and 32 deletions.
16 changes: 15 additions & 1 deletion .github/workflows/interop-test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,23 @@ jobs:
flavour: [chromium, native]
steps:
- uses: actions/checkout@v4

- uses: docker/setup-buildx-action@v3

# This uses the same S3 cache as all test-plans images. Because we use `cargo-chef` in the Dockerfile, we have a layer available with all dependencies built.
- name: Build ${{ matrix.flavour }} image
run: docker buildx build --load -t ${{ matrix.flavour }}-rust-libp2p-head . -f interop-tests/Dockerfile.${{ matrix.flavour }}
run: |
docker buildx build \
--load \
--cache-to type=s3,mode=max,bucket=libp2p-by-tf-aws-bootstrap,region=us-east-1,prefix=buildCache,name=${{ matrix.flavour }}-rust-libp2p-head \
--cache-from type=s3,mode=max,bucket=libp2p-by-tf-aws-bootstrap,region=us-east-1,prefix=buildCache,name=${{ matrix.flavour }}-rust-libp2p-head \
-t ${{ matrix.flavour }}-rust-libp2p-head \
. \
-f interop-tests/Dockerfile.${{ matrix.flavour }}
env:
AWS_ACCESS_KEY_ID: ${{ vars.TEST_PLANS_BUILD_CACHE_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.TEST_PLANS_BUILD_CACHE_KEY }}

- name: Run ${{ matrix.flavour }} tests
uses: libp2p/test-plans/.github/actions/run-interop-ping-test@master
with:
Expand Down
40 changes: 19 additions & 21 deletions interop-tests/Dockerfile.chromium
Original file line number Diff line number Diff line change
@@ -1,28 +1,26 @@
FROM rust:1.67.0 as builder

# Run with access to the target cache to speed up builds
WORKDIR /workspace
ADD . .

# syntax=docker/dockerfile:1.5-labs
FROM rust:1.67.0 as chef
RUN rustup target add wasm32-unknown-unknown

RUN wget -q -O- https://github.com/rustwasm/wasm-pack/releases/download/v0.12.1/wasm-pack-v0.12.1-x86_64-unknown-linux-musl.tar.gz | tar -zx -C /usr/local/bin --strip-components 1 --wildcards "wasm-pack-*/wasm-pack"
RUN wget -q -O- https://github.com/WebAssembly/binaryen/releases/download/version_115/binaryen-version_115-x86_64-linux.tar.gz | tar -zx -C /usr/local/bin --strip-components 2 --wildcards "binaryen-version_*/bin/wasm-opt"

RUN --mount=type=cache,target=./target \
--mount=type=cache,target=/usr/local/cargo/registry \
wasm-pack build --target web interop-tests

RUN --mount=type=cache,target=./target \
--mount=type=cache,target=/usr/local/cargo/registry \
cargo build --release --package interop-tests --bin wasm_ping

RUN --mount=type=cache,target=./target \
mv ./target/release/wasm_ping /usr/local/bin/testplan
RUN wget -q -O- https://github.com/LukeMathWalker/cargo-chef/releases/download/v0.1.62/cargo-chef-x86_64-unknown-linux-gnu.tar.gz | tar -zx -C /usr/local/bin
WORKDIR /app

FROM chef AS planner
COPY . .
RUN cargo chef prepare --recipe-path recipe.json

FROM chef AS builder
COPY --from=planner /app/recipe.json recipe.json
# Build dependencies - this is the caching Docker layer!
RUN cargo chef cook --release --package interop-tests --target wasm32-unknown-unknown --recipe-path recipe.json
RUN cargo chef cook --release --package interop-tests --bin wasm_ping --recipe-path recipe.json
# Build application
COPY . .
RUN wasm-pack build --target web interop-tests
RUN cargo build --release --package interop-tests --bin wasm_ping

FROM selenium/standalone-chrome:115.0
COPY --from=builder /usr/local/bin/testplan /usr/local/bin/testplan

COPY --from=builder /app/target/release/wasm_ping /usr/local/bin/testplan
ENV RUST_BACKTRACE=1

ENTRYPOINT ["testplan"]
24 changes: 14 additions & 10 deletions interop-tests/Dockerfile.native
Original file line number Diff line number Diff line change
@@ -1,17 +1,21 @@
# syntax=docker/dockerfile:1.5-labs
FROM rust:1.67.0 as builder
FROM rust:1.67.0 as chef
RUN wget -q -O- https://github.com/LukeMathWalker/cargo-chef/releases/download/v0.1.62/cargo-chef-x86_64-unknown-linux-gnu.tar.gz | tar -zx -C /usr/local/bin
WORKDIR /app

# Run with access to the target cache to speed up builds
WORKDIR /workspace
ADD . .
RUN --mount=type=cache,target=./target \
--mount=type=cache,target=/usr/local/cargo/registry \
cargo build --release --package interop-tests --bin native_ping
FROM chef AS planner
COPY . .
RUN cargo chef prepare --recipe-path recipe.json

RUN --mount=type=cache,target=./target \
mv ./target/release/native_ping /usr/local/bin/testplan
FROM chef AS builder
COPY --from=planner /app/recipe.json recipe.json
# Build dependencies - this is the caching Docker layer!
RUN cargo chef cook --release --package interop-tests --bin native_ping --recipe-path recipe.json
# Build application
COPY . .
RUN cargo build --release --package interop-tests --bin native_ping

FROM gcr.io/distroless/cc
COPY --from=builder /usr/local/bin/testplan /usr/local/bin/testplan
COPY --from=builder /app/target/release/native_ping /usr/local/bin/testplan
ENV RUST_BACKTRACE=1
ENTRYPOINT ["testplan"]

0 comments on commit 7d1d67c

Please sign in to comment.