Skip to content

Commit a7b1c85

Browse files
committed
test: cache nitro contracts docker image
1 parent 2f4418b commit a7b1c85

File tree

6 files changed

+62
-48
lines changed

6 files changed

+62
-48
lines changed

.github/workflows/build-test.yml

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -226,10 +226,25 @@ jobs:
226226
test-integration-anvil:
227227
name: Test (Integration Anvil)
228228
runs-on: ubuntu-latest
229+
env:
230+
NITRO_CONTRACTS_IMAGE_REF: v3.2.0-2f747c7
229231
steps:
230232
- name: Checkout
231233
uses: actions/checkout@v4
232234

235+
- name: Set up Docker Buildx
236+
uses: docker/setup-buildx-action@v3
237+
238+
- name: Build nitro contracts image
239+
uses: docker/build-push-action@v6
240+
with:
241+
context: ./nitro-contracts
242+
file: ./nitro-contracts/Dockerfile
243+
tags: chain-sdk-nitro-contracts:${{ env.NITRO_CONTRACTS_IMAGE_REF }}
244+
load: true
245+
cache-from: type=gha,scope=chain-sdk-nitro-contracts-${{ env.NITRO_CONTRACTS_IMAGE_REF }}
246+
cache-to: type=gha,mode=max,scope=chain-sdk-nitro-contracts-${{ env.NITRO_CONTRACTS_IMAGE_REF }}
247+
233248
- name: Setup pnpm
234249
uses: pnpm/action-setup@v4
235250
with:

nitro-contracts/Dockerfile

Lines changed: 27 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,37 @@
11
FROM ghcr.io/foundry-rs/foundry:v1.3.1 AS foundry
22

3-
FROM node:20-bullseye-slim
3+
FROM node:20-bullseye-slim AS builder
4+
5+
ARG NITRO_CONTRACTS_REPO_URL=https://github.com/OffchainLabs/nitro-contracts.git
6+
ARG NITRO_CONTRACTS_GIT_COMMIT=2f747c722d98d5fd662bfda08cd86aa534b22be2
47

58
COPY --from=foundry /usr/local/bin/forge /usr/local/bin/forge
69

10+
RUN apt-get update && apt-get install -y git && rm -rf /var/lib/apt/lists/*
11+
712
WORKDIR /workspace
8-
COPY . /workspace
13+
14+
RUN git init . \
15+
&& git remote add origin "${NITRO_CONTRACTS_REPO_URL}" \
16+
&& git fetch --depth 1 origin "${NITRO_CONTRACTS_GIT_COMMIT}" \
17+
&& git checkout --detach FETCH_HEAD \
18+
&& git submodule update --init --recursive --depth 1
19+
920
RUN cp scripts/config.example.ts scripts/config.ts
10-
RUN yarn install
21+
RUN yarn install --frozen-lockfile
1122
RUN yarn build:all
1223

24+
FROM node:20-bullseye-slim
25+
26+
WORKDIR /workspace
27+
COPY --from=builder /workspace/package.json /workspace/package.json
28+
COPY --from=builder /workspace/yarn.lock /workspace/yarn.lock
29+
COPY --from=builder /workspace/hardhat.config.ts /workspace/hardhat.config.ts
30+
COPY --from=builder /workspace/tsconfig.json /workspace/tsconfig.json
31+
COPY --from=builder /workspace/scripts /workspace/scripts
32+
COPY --from=builder /workspace/test/contract /workspace/test/contract
33+
COPY --from=builder /workspace/build /workspace/build
34+
COPY --from=builder /workspace/out /workspace/out
35+
COPY --from=builder /workspace/node_modules /workspace/node_modules
36+
1337
ENTRYPOINT ["yarn"]

src/integrationTestHelpers/anvilHarness.ts

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -30,9 +30,9 @@ import {
3030
cleanupCurrentHarnessResources,
3131
cleanupStaleHarnessContainers,
3232
cleanupStaleHarnessNetworks,
33-
createSourceDockerNetwork,
34-
startSourceL1AnvilContainer,
35-
startSourceL2NitroContainer,
33+
createDockerNetwork,
34+
startL1AnvilContainer,
35+
startL2NitroContainer,
3636
waitForRpc,
3737
} from './dockerHelpers';
3838
import {
@@ -105,7 +105,7 @@ export async function setupAnvilTestStack(): Promise<AnvilTestStack> {
105105
runtimeDir = mkdtempSync(join(tmpdir(), 'chain-sdk-int-test'));
106106
prepareNitroRuntimeDir(runtimeDir);
107107
dockerNetworkName = `chain-sdk-int-test-net-${Date.now()}`;
108-
createSourceDockerNetwork(dockerNetworkName);
108+
createDockerNetwork(dockerNetworkName);
109109

110110
const l2ChainId = testConstants.DEFAULT_L2_CHAIN_ID;
111111
const l1RpcPort = testConstants.DEFAULT_L1_RPC_PORT;
@@ -143,7 +143,7 @@ export async function setupAnvilTestStack(): Promise<AnvilTestStack> {
143143
l1ContainerName = `chain-sdk-int-test-l1-${Date.now()}`;
144144
console.log('Starting L1 Anvil node...');
145145

146-
startSourceL1AnvilContainer({
146+
startL1AnvilContainer({
147147
containerName: l1ContainerName,
148148
networkName: dockerNetworkName,
149149
l1RpcPort,
@@ -225,16 +225,17 @@ export async function setupAnvilTestStack(): Promise<AnvilTestStack> {
225225
if (l2ChainConfig.arbitrum.DataAvailabilityCommittee) {
226226
delete l2NodeConfig.node?.['data-availability']?.['rpc-aggregator'];
227227
}
228+
228229
l2NodeConfig.node!['batch-poster']!.enable = false;
229230
l2NodeConfig.node!.staker!.enable = false;
230-
const nodeConfigPath = join(runtimeDir, 'source-l2-node-config.json');
231+
const nodeConfigPath = join(runtimeDir, 'l2-node-config.json');
231232
writeFileSync(nodeConfigPath, JSON.stringify(l2NodeConfig, null, 2), { mode: 0o644 });
232233

233234
// Starting L2 node (Nitro)
234235
console.log('Starting L2 Nitro node...');
235236
l2ContainerName = `chain-sdk-int-test-l2-${Date.now()}`;
236237

237-
startSourceL2NitroContainer({
238+
startL2NitroContainer({
238239
containerName: l2ContainerName,
239240
networkName: dockerNetworkName,
240241
l2RpcPort,

src/integrationTestHelpers/anvilHarnessHelpers.ts

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,10 @@ function getRollupCreatorDockerArgs(
9494
'-e',
9595
'IGNORE_MAX_DATA_SIZE_WARNING=true',
9696
nitroContractsImage,
97-
'deploy-factory',
97+
'hardhat',
98+
'run',
99+
'--no-compile',
100+
'scripts/deployment.ts',
98101
'--network',
99102
'custom',
100103
];

src/integrationTestHelpers/constants.ts

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,7 @@ import { ethers } from 'ethers';
44
export const testConstants = {
55
DEFAULT_ANVIL_IMAGE: 'ghcr.io/foundry-rs/foundry:v1.3.1',
66
DEFAULT_NITRO_IMAGE: 'offchainlabs/nitro-node:v3.9.5-66e42c4',
7-
DEFAULT_NITRO_CONTRACTS_REF: 'v3.2.0',
8-
DEFAULT_NITRO_CONTRACTS_REPO_URL: 'https://github.com/OffchainLabs/nitro-contracts.git',
9-
DEFAULT_NITRO_CONTRACTS_BRANCH: 'feat/add-polling-interval',
7+
DEFAULT_NITRO_CONTRACTS_REF: 'v3.2.0-2f747c7',
108
DEFAULT_L2_CHAIN_ID: 421_337,
119
DEFAULT_L1_RPC_PORT: 9645,
1210
DEFAULT_L2_RPC_PORT: 8747,

src/integrationTestHelpers/dockerHelpers.ts

Lines changed: 7 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,11 @@
11
import { execFile, execFileSync } from 'node:child_process';
2-
import { mkdtempSync, rmSync } from 'node:fs';
3-
import { tmpdir } from 'node:os';
2+
import { rmSync } from 'node:fs';
43
import { join } from 'node:path';
54

65
import { createPublicClient, http } from 'viem';
76

87
import { testConstants } from './constants';
98

10-
const cachedNitroContractsImageByTag: Record<string, string> = {};
11-
129
function sleep(ms: number) {
1310
return new Promise((resolve) => setTimeout(resolve, ms));
1411
}
@@ -47,43 +44,19 @@ export function getNitroContractsImage(): string {
4744
const imageTag = `chain-sdk-nitro-contracts:${sanitizeDockerTagPart(
4845
testConstants.DEFAULT_NITRO_CONTRACTS_REF,
4946
)}`;
50-
const cachedImage = cachedNitroContractsImageByTag[imageTag];
51-
if (cachedImage) {
52-
return cachedImage;
53-
}
5447

5548
try {
5649
docker(['image', 'inspect', imageTag]);
5750
} catch {
58-
const tempDir = mkdtempSync(join(tmpdir(), 'chain-sdk-nitro-contracts-'));
59-
const repoDir = join(tempDir, 'repo');
51+
const nitroContractsDir = join(process.cwd(), 'nitro-contracts');
6052
const dockerfilePath = join(process.cwd(), 'nitro-contracts', 'Dockerfile');
61-
62-
try {
63-
runCommand('git', [
64-
'clone',
65-
'--recurse-submodules',
66-
'--shallow-submodules',
67-
'--depth',
68-
'1',
69-
'--branch',
70-
testConstants.DEFAULT_NITRO_CONTRACTS_BRANCH,
71-
'--single-branch',
72-
testConstants.DEFAULT_NITRO_CONTRACTS_REPO_URL,
73-
repoDir,
74-
]);
75-
76-
docker(['build', '-f', dockerfilePath, '-t', imageTag, repoDir]);
77-
} finally {
78-
rmSync(tempDir, { recursive: true, force: true });
79-
}
53+
docker(['build', '-f', dockerfilePath, '-t', imageTag, nitroContractsDir]);
8054
}
8155

82-
cachedNitroContractsImageByTag[imageTag] = imageTag;
8356
return imageTag;
8457
}
8558

86-
export function createSourceDockerNetwork(networkName: string) {
59+
export function createDockerNetwork(networkName: string) {
8760
docker(['network', 'create', networkName]);
8861
}
8962

@@ -237,7 +210,7 @@ export function cleanupStaleHarnessNetworks() {
237210
}
238211
}
239212

240-
export function startSourceL1AnvilContainer(params: {
213+
export function startL1AnvilContainer(params: {
241214
containerName: string;
242215
networkName: string;
243216
l1RpcPort: number;
@@ -275,7 +248,7 @@ export function startSourceL1AnvilContainer(params: {
275248
]);
276249
}
277250

278-
export function startSourceL2NitroContainer(params: {
251+
export function startL2NitroContainer(params: {
279252
containerName: string;
280253
networkName: string;
281254
l2RpcPort: number;
@@ -295,7 +268,7 @@ export function startSourceL2NitroContainer(params: {
295268
`${params.runtimeDir}:/runtime`,
296269
params.nitroImage,
297270
'--conf.file',
298-
'/runtime/source-l2-node-config.json',
271+
'/runtime/l2-node-config.json',
299272
'--persistent.chain',
300273
'/runtime/nitro-data',
301274
'--ensure-rollup-deployment=false',

0 commit comments

Comments
 (0)