Skip to content

Commit f72a56b

Browse files
committed
build(contracts): build contracts individually.
Building contracts individually produces more reproducible bytecode. Due to a bug in the 0.6.10 compiler (ethereum/solidity/issues/9573)
1 parent 77773b7 commit f72a56b

File tree

2 files changed

+90
-10
lines changed

2 files changed

+90
-10
lines changed

hardhat.config.ts

Lines changed: 88 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,21 @@ require("dotenv").config();
22
require("hardhat-contract-sizer");
33

44
import chalk from "chalk";
5-
import { HardhatUserConfig } from "hardhat/config";
5+
import { HardhatUserConfig, task } from "hardhat/config";
66
import { privateKeys } from "./utils/wallets";
77

88
import "@nomiclabs/hardhat-waffle";
99
import "@typechain/hardhat";
1010
import "solidity-coverage";
1111
import "hardhat-deploy";
12+
import {
13+
TASK_COMPILE_SOLIDITY_GET_COMPILATION_JOB_FOR_FILE,
14+
TASK_COMPILE_SOLIDITY_GET_DEPENDENCY_GRAPH,
15+
TASK_COMPILE_SOLIDITY_COMPILE_JOB,
16+
} from "hardhat/builtin-tasks/task-names";
17+
18+
import type { DependencyGraph, CompilationJob } from "hardhat/types/builtin-tasks";
19+
1220
import "./tasks";
1321

1422
const forkingConfig = {
@@ -104,15 +112,87 @@ function getHardhatPrivateKeys() {
104112
}
105113

106114
function checkForkedProviderEnvironment() {
107-
if (process.env.FORK &&
108-
(!process.env.ALCHEMY_TOKEN || process.env.ALCHEMY_TOKEN === "fake_alchemy_token")
109-
) {
110-
console.log(chalk.red(
111-
"You are running forked provider tests with invalid Alchemy credentials.\n" +
112-
"Update your ALCHEMY_TOKEN settings in the `.env` file."
113-
));
115+
if (
116+
process.env.FORK &&
117+
(!process.env.ALCHEMY_TOKEN || process.env.ALCHEMY_TOKEN === "fake_alchemy_token")
118+
) {
119+
console.log(
120+
chalk.red(
121+
"You are running forked provider tests with invalid Alchemy credentials.\n" +
122+
"Update your ALCHEMY_TOKEN settings in the `.env` file.",
123+
),
124+
);
114125
process.exit(1);
115126
}
116127
}
117128

129+
task("index:compile:one", "Compiles a single contract in isolation")
130+
.addPositionalParam("contractName")
131+
.setAction(async function (args, env) {
132+
const sourceName = env.artifacts.readArtifactSync(args.contractName).sourceName;
133+
134+
const dependencyGraph: DependencyGraph = await env.run(
135+
TASK_COMPILE_SOLIDITY_GET_DEPENDENCY_GRAPH,
136+
{ sourceNames: [sourceName] },
137+
);
138+
139+
const resolvedFiles = dependencyGraph.getResolvedFiles().filter(resolvedFile => {
140+
return resolvedFile.sourceName === sourceName;
141+
});
142+
143+
const compilationJob: CompilationJob = await env.run(
144+
TASK_COMPILE_SOLIDITY_GET_COMPILATION_JOB_FOR_FILE,
145+
{
146+
dependencyGraph,
147+
file: resolvedFiles[0],
148+
},
149+
);
150+
151+
await env.run(TASK_COMPILE_SOLIDITY_COMPILE_JOB, {
152+
compilationJob,
153+
compilationJobs: [compilationJob],
154+
compilationJobIndex: 0,
155+
emitsArtifacts: true,
156+
quiet: true,
157+
});
158+
159+
await env.run("typechain");
160+
});
161+
162+
task("index:compile:all", "Compiles all contracts in isolation").setAction(async function (
163+
_args,
164+
env,
165+
) {
166+
const allArtifacts = await env.artifacts.getAllFullyQualifiedNames();
167+
for (const contractName of allArtifacts) {
168+
const sourceName = env.artifacts.readArtifactSync(contractName).sourceName;
169+
170+
const dependencyGraph: DependencyGraph = await env.run(
171+
TASK_COMPILE_SOLIDITY_GET_DEPENDENCY_GRAPH,
172+
{
173+
sourceNames: [sourceName],
174+
},
175+
);
176+
177+
const resolvedFiles = dependencyGraph.getResolvedFiles().filter(resolvedFile => {
178+
return resolvedFile.sourceName === sourceName;
179+
});
180+
181+
const compilationJob: CompilationJob = await env.run(
182+
TASK_COMPILE_SOLIDITY_GET_COMPILATION_JOB_FOR_FILE,
183+
{
184+
dependencyGraph,
185+
file: resolvedFiles[0],
186+
},
187+
);
188+
189+
await env.run(TASK_COMPILE_SOLIDITY_COMPILE_JOB, {
190+
compilationJob,
191+
compilationJobs: [compilationJob],
192+
compilationJobIndex: 0,
193+
emitsArtifacts: true,
194+
quiet: true,
195+
});
196+
}
197+
});
118198
export default config;

package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -54,8 +54,8 @@
5454
"build:ts:hardhat": "yarn typechain && yarn transpile:dist:hardhat",
5555
"chain": "npx hardhat node",
5656
"clean": "./scripts/clean.sh",
57-
"compile": "npx hardhat compile",
58-
"compile:latest": "SKIP_ABI_GAS_MODS=true npx hardhat compile",
57+
"compile": "npx hardhat compile && npx hardhat index:compile:all",
58+
"compile:latest": "SKIP_ABI_GAS_MODS=true npx hardhat compile && npx hardhat index:compile:all",
5959
"coverage": "yarn clean && yarn build && yarn cov:command",
6060
"cov:command": "COVERAGE=true node --max-old-space-size=4096 ./node_modules/.bin/hardhat coverage",
6161
"etherscan:verify": "hardhat --network kovan etherscan-verify --solc-input --license 'None'",

0 commit comments

Comments
 (0)