0
# Contract Verification
1
2
Core contract verification functionality that submits smart contract source code to block explorers like Etherscan for public verification and audit.
3
4
## Capabilities
5
6
### Main Verify Task
7
8
The primary verification task that orchestrates the entire verification workflow.
9
10
```typescript { .api }
11
/**
12
* Main contract verification task
13
* Verifies a deployed contract on the configured network's block explorer
14
*/
15
interface VerifyTaskArgs {
16
/** Contract address to verify */
17
address?: string;
18
/** Constructor arguments provided as command line parameters */
19
constructorArgsParams: string[];
20
/** Path to file containing constructor arguments */
21
constructorArgs?: string;
22
/** Fully qualified contract name (e.g., "contracts/Token.sol:Token") */
23
contract?: string;
24
/** Path to file containing library addresses */
25
libraries?: string;
26
/** Flag to list all supported networks */
27
listNetworks: boolean;
28
/** Flag to skip compilation before verification */
29
noCompile: boolean;
30
}
31
```
32
33
**Usage Examples:**
34
35
```bash
36
# Basic verification with constructor arguments
37
npx hardhat verify --network mainnet 0x1234...5678 "Initial Supply" "Token Name"
38
39
# Verify specific contract when multiple contracts match bytecode
40
npx hardhat verify --network mainnet --contract contracts/Token.sol:MyToken 0x1234...5678
41
42
# Verify with constructor arguments from file
43
npx hardhat verify --network mainnet --constructor-args arguments.js 0x1234...5678
44
45
# Verify with library addresses from file
46
npx hardhat verify --network mainnet --libraries libraries.js 0x1234...5678
47
48
# List all supported networks
49
npx hardhat verify --list-networks
50
```
51
52
### Verify Subtask
53
54
Internal subtask that performs the actual verification logic.
55
56
```typescript { .api }
57
/**
58
* Internal verification subtask with processed arguments
59
* Handles the core verification workflow including bytecode matching
60
*/
61
interface VerificationSubtaskArgs {
62
/** Contract address to verify */
63
address: string;
64
/** Processed constructor arguments array */
65
constructorArguments: any[];
66
/** Fully qualified contract name */
67
contract?: string;
68
/** Processed library addresses */
69
libraries: Libraries;
70
/** Skip compilation flag */
71
noCompile: boolean;
72
}
73
```
74
75
### Verification Response Handling
76
77
```typescript { .api }
78
class EtherscanResponse {
79
/** Response status code */
80
readonly status: number;
81
/** Response message from Etherscan */
82
readonly message: string;
83
84
constructor(response: any);
85
86
/** Check if verification is pending in queue */
87
isPending(): boolean;
88
/** Check if verification was successful */
89
isVerificationSuccess(): boolean;
90
/** Check if verification failed */
91
isVerificationFailure(): boolean;
92
/** Check if response is OK (status === 1) */
93
isOk(): boolean;
94
/** Check for bytecode missing error */
95
isBytecodeMissingInNetworkError(): boolean;
96
}
97
```
98
99
### Verification Status Polling
100
101
```typescript { .api }
102
/**
103
* Get verification status from Etherscan
104
* @param url - Etherscan API URL
105
* @param req - Status check request
106
* @returns Promise resolving to verification status
107
*/
108
function getVerificationStatus(
109
url: string,
110
req: EtherscanCheckStatusRequest
111
): Promise<EtherscanResponse>;
112
113
/**
114
* Check if contract is already verified
115
* @param apiURL - Etherscan API URL
116
* @param apiKey - Etherscan API key
117
* @param address - Contract address
118
* @returns Promise resolving to verification status
119
*/
120
function isAlreadyVerified(
121
apiURL: string,
122
apiKey: string,
123
address: string
124
): Promise<boolean>;
125
```
126
127
### Verification Request Submission
128
129
```typescript { .api }
130
/**
131
* Submit contract verification request to Etherscan
132
* @param url - Etherscan API URL
133
* @param req - Verification request parameters
134
* @returns Promise resolving to Etherscan response
135
*/
136
function verifyContract(
137
url: string,
138
req: EtherscanVerifyRequest
139
): Promise<EtherscanResponse>;
140
141
interface EtherscanRequest {
142
apikey: string;
143
module: "contract";
144
action: string;
145
}
146
147
interface EtherscanVerifyRequest extends EtherscanRequest {
148
action: "verifysourcecode";
149
contractaddress: string;
150
sourceCode: string;
151
codeformat: "solidity-standard-json-input";
152
contractname: string;
153
compilerversion: string;
154
// Note: This is misspelt in Etherscan's actual API parameters
155
constructorArguements: string;
156
}
157
158
interface EtherscanCheckStatusRequest extends EtherscanRequest {
159
action: "checkverifystatus";
160
guid: string;
161
}
162
```
163
164
### Bytecode Analysis and Matching
165
166
```typescript { .api }
167
/**
168
* Analyze deployed bytecode to infer Solidity version
169
*/
170
class Bytecode {
171
constructor(bytecodeHex: string);
172
/** Get inferred Solidity version from bytecode metadata */
173
getInferredSolcVersion(): string;
174
/** Check if bytecode appears to be OVM bytecode */
175
isOvmInferred(): boolean;
176
}
177
178
/**
179
* Extract contract information matching deployed bytecode
180
* @param sourceName - Source file name
181
* @param contractName - Contract name
182
* @param buildInfo - Hardhat build information
183
* @param deployedBytecode - Deployed bytecode to match
184
* @returns Contract information or null if no match
185
*/
186
function extractMatchingContractInformation(
187
sourceName: string,
188
contractName: string,
189
buildInfo: BuildInfo,
190
deployedBytecode: Bytecode
191
): Promise<ContractInformation | null>;
192
193
/**
194
* Find contracts with bytecode matching deployed contract
195
* @param artifacts - Hardhat artifacts manager
196
* @param matchingCompilerVersions - Compatible compiler versions
197
* @param deployedBytecode - Deployed bytecode to match
198
* @returns Array of matching contract information
199
*/
200
function lookupMatchingBytecode(
201
artifacts: Artifacts,
202
matchingCompilerVersions: string[],
203
deployedBytecode: Bytecode
204
): Promise<ContractInformation[]>;
205
206
/**
207
* Compare two bytecode instances for matching
208
* @param builtin - Built contract bytecode
209
* @param deployed - Deployed contract bytecode
210
* @returns Promise resolving to true if bytecodes match
211
*/
212
function compareBytecode(
213
builtin: Bytecode,
214
deployed: Bytecode
215
): Promise<boolean>;
216
217
/**
218
* Normalize bytecode by removing metadata and variable sections
219
* @param artifacts - Hardhat artifacts manager
220
* @param matchingCompilerVersions - Compatible compiler versions
221
* @param deployedBytecode - Deployed bytecode to normalize
222
* @returns Promise resolving to normalized bytecode
223
*/
224
function normalizeBytecode(
225
artifacts: Artifacts,
226
matchingCompilerVersions: string[],
227
deployedBytecode: Bytecode
228
): Promise<string>;
229
```
230
231
### Utility Functions
232
233
```typescript { .api }
234
/**
235
* Add delay for verification polling
236
* @param ms - Milliseconds to delay
237
*/
238
function delay(ms: number): Promise<void>;
239
240
/**
241
* Build contract URL for block explorer
242
* @param browserURL - Block explorer browser URL
243
* @param contractAddress - Contract address
244
* @returns Complete URL to contract page
245
*/
246
function buildContractUrl(
247
browserURL: string,
248
contractAddress: string
249
): string;
250
251
/**
252
* Get full Solidity compiler version from short version
253
* @param shortVersion - Short version like "0.8.19"
254
* @returns Promise resolving to full version like "v0.8.19+commit.7dd6d404"
255
*/
256
function getLongVersion(shortVersion: string): Promise<string>;
257
258
/**
259
* Get list of available Solidity compiler versions
260
* @returns Promise resolving to compiler list from solc-bin
261
*/
262
function getVersions(): Promise<CompilersList>;
263
264
interface CompilersList {
265
releases: {
266
[version: string]: string;
267
};
268
latestRelease: string;
269
}
270
271
/**
272
* Send GET request using undici
273
* @param url - URL to send request to
274
* @returns Promise resolving to response data
275
*/
276
function sendGetRequest(url: URL): Promise<Dispatcher.ResponseData>;
277
278
/**
279
* Send POST request using undici
280
* @param url - URL to send request to
281
* @param body - Request body
282
* @returns Promise resolving to response data
283
*/
284
function sendPostRequest(url: URL, body: string): Promise<Dispatcher.ResponseData>;
285
286
/**
287
* Build verification request for Etherscan API
288
* @param params - Verification request parameters
289
* @returns Formatted request object for Etherscan API
290
*/
291
function toVerifyRequest(params: {
292
apiKey: string;
293
contractAddress: string;
294
sourceCode: string;
295
sourceName: string;
296
contractName: string;
297
compilerVersion: string;
298
constructorArguments: string;
299
}): EtherscanVerifyRequest;
300
301
/**
302
* Build status check request for Etherscan API
303
* @param params - Status check request parameters
304
* @returns Formatted request object for Etherscan API
305
*/
306
function toCheckStatusRequest(params: {
307
apiKey: string;
308
guid: string;
309
}): EtherscanCheckStatusRequest;
310
```
311
312
### Metadata Analysis
313
314
```typescript { .api }
315
/**
316
* Infer Solidity compiler version from contract bytecode metadata
317
* @param bytecode - Contract bytecode buffer
318
* @returns Metadata description with inferred version and size information
319
*/
320
function inferSolcVersion(bytecode: Buffer): MetadataDescription;
321
322
/**
323
* Decode Solidity metadata from contract bytecode
324
* @param bytecode - Contract bytecode buffer
325
* @returns Decoded metadata object and size information
326
*/
327
function decodeSolcMetadata(bytecode: Buffer): {
328
decoded: any;
329
metadataSectionSizeInBytes: number;
330
};
331
332
/**
333
* Get the size of the metadata section in bytecode
334
* @param bytecode - Contract bytecode buffer
335
* @returns Size of metadata section in bytes
336
*/
337
function getSolcMetadataSectionLength(bytecode: Buffer): number;
338
339
/**
340
* Measure the size of the executable section without metadata
341
* @param bytecode - Contract bytecode hex string
342
* @returns Length of executable section in characters
343
*/
344
function measureExecutableSectionLength(bytecode: string): number;
345
346
interface MetadataDescription {
347
/** Inferred Solidity compiler version or version range */
348
solcVersion: string;
349
/** Size of metadata section in bytes */
350
metadataSectionSizeInBytes: number;
351
}
352
```