Files
proxmox/scripts/verify/generate-contract-verification-publish-matrix.mjs
defiQUG dbd517b279 Sync workspace: config, docs, scripts, CI, operator rules, and submodule pointers.
- Update dbis_core, cross-chain-pmm-lps, explorer-monorepo, metamask-integration, pr-workspace/chains
- Omit embedded publish git dirs and empty placeholders from index

Made-with: Cursor
2026-04-12 06:12:20 -07:00

314 lines
12 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#!/usr/bin/env node
import fs from 'fs';
import path from 'path';
const repoRoot = path.resolve(path.dirname(new URL(import.meta.url).pathname), '..', '..');
const smartContractsPath = path.join(repoRoot, 'config', 'smart-contracts-master.json');
const deploymentStatusPath = path.join(repoRoot, 'cross-chain-pmm-lps', 'config', 'deployment-status.json');
const outputJsonPath = path.join(repoRoot, 'reports', 'status', 'contract_verification_publish_matrix.json');
const outputMdPath = path.join(repoRoot, 'docs', '11-references', 'CONTRACT_VERIFICATION_AND_PUBLICATION_MATRIX_ALL_NETWORKS.md');
const CHAIN_META = {
'1': {
name: 'Ethereum Mainnet',
explorer: 'https://etherscan.io',
verifierKind: 'etherscan',
publishSurface: 'Etherscan + repo inventory/token maps',
},
'10': {
name: 'Optimism',
explorer: 'https://optimistic.etherscan.io',
verifierKind: 'etherscan-family',
publishSurface: 'Optimism explorer + repo inventory/token maps',
},
'25': {
name: 'Cronos',
explorer: 'https://cronoscan.com',
verifierKind: 'etherscan-family',
publishSurface: 'Cronoscan + repo inventory/token maps',
},
'56': {
name: 'BSC',
explorer: 'https://bscscan.com',
verifierKind: 'etherscan-family',
publishSurface: 'BscScan + repo inventory/token maps',
},
'100': {
name: 'Gnosis',
explorer: 'https://gnosisscan.io',
verifierKind: 'etherscan-family',
publishSurface: 'Gnosis explorer + repo inventory/token maps',
},
'1111': {
name: 'Wemix',
explorer: 'https://explorer.wemix.com',
verifierKind: 'manual',
publishSurface: 'Wemix explorer + repo inventory/token maps',
},
'137': {
name: 'Polygon',
explorer: 'https://polygonscan.com',
verifierKind: 'etherscan-family',
publishSurface: 'PolygonScan + repo inventory/token maps',
},
'138': {
name: 'Chain 138',
explorer: 'https://blockscout.defi-oracle.io',
explorerAlt: 'https://explorer.d-bis.org',
verifierKind: 'blockscout',
publishSurface: 'Blockscout + repo inventory + explorer token/config surfaces',
verificationScript: 'bash scripts/verify/run-contract-verification-with-proxy.sh',
},
'42161': {
name: 'Arbitrum',
explorer: 'https://arbiscan.io',
verifierKind: 'etherscan-family',
publishSurface: 'Arbiscan + repo inventory/token maps',
},
'42220': {
name: 'Celo',
explorer: 'https://celoscan.io',
verifierKind: 'etherscan-family',
publishSurface: 'Celo explorer + repo inventory/token maps',
},
'43114': {
name: 'Avalanche',
explorer: 'https://snowtrace.io',
verifierKind: 'etherscan-family',
publishSurface: 'Snowtrace + repo inventory/token maps',
},
'8453': {
name: 'Base',
explorer: 'https://basescan.org',
verifierKind: 'etherscan-family',
publishSurface: 'Basescan + repo inventory/token maps',
},
'651940': {
name: 'ALL Mainnet',
explorer: 'https://alltra.global',
verifierKind: 'manual',
publishSurface: 'Alltra explorer/docs + repo inventory/token maps',
},
};
function loadJson(filePath) {
return JSON.parse(fs.readFileSync(filePath, 'utf8'));
}
function ensureDir(filePath) {
fs.mkdirSync(path.dirname(filePath), { recursive: true });
}
function chainMeta(chainId, fallbackName = '') {
const meta = CHAIN_META[String(chainId)] || {};
return {
chainId: String(chainId),
chainName: meta.name || fallbackName || `Chain ${chainId}`,
explorer: meta.explorer || '',
explorerAlt: meta.explorerAlt || '',
verifierKind: meta.verifierKind || 'manual',
publishSurface: meta.publishSurface || 'Explorer + repo inventory',
verificationScript: meta.verificationScript || '',
};
}
function pushEntry(target, entry) {
target.push({
verificationStatus: 'pending',
publicationStatus: 'pending',
publishRequirement: 'Verify source on chain explorer and keep repo inventories/token maps aligned',
...entry,
});
}
const smartContracts = loadJson(smartContractsPath);
const deploymentStatus = loadJson(deploymentStatusPath);
const entries = [];
for (const [chainId, chainData] of Object.entries(smartContracts.chains || {})) {
const meta = chainMeta(chainId);
for (const [label, address] of Object.entries(chainData.contracts || {})) {
pushEntry(entries, {
sourceRegistry: 'config/smart-contracts-master.json',
contractType: 'canonical_contract',
label,
address,
...meta,
automation: chainId === '138' ? 'repo-supported' : 'manual-or-external',
publishNotes: chainId === '138'
? 'Canonical Chain 138 contract; verify in Blockscout and keep reference docs current'
: 'Mainnet relay or non-138 canonical contract; verify on chain explorer and mirror in repo docs',
});
}
}
for (const [chainId, chainData] of Object.entries(deploymentStatus.chains || {})) {
const meta = chainMeta(chainId, chainData.name);
for (const [label, address] of Object.entries(chainData.cwTokens || {})) {
pushEntry(entries, {
sourceRegistry: 'cross-chain-pmm-lps/config/deployment-status.json',
contractType: 'cw_token',
label,
address,
...meta,
automation: 'inventory-only',
publishNotes: 'Cross-chain wrapped/canonical token; verify on explorer and keep PMM/token-mapping inventories aligned',
});
}
for (const [label, address] of Object.entries(chainData.gasMirrors || {})) {
pushEntry(entries, {
sourceRegistry: 'cross-chain-pmm-lps/config/deployment-status.json',
contractType: 'gas_mirror',
label,
address,
...meta,
automation: 'inventory-only',
publishNotes: 'Gas-family mirror token; verify on explorer and keep gas rollout inventory aligned',
});
}
for (const [label, address] of Object.entries(chainData.anchorAddresses || {})) {
pushEntry(entries, {
sourceRegistry: 'cross-chain-pmm-lps/config/deployment-status.json',
contractType: 'anchor_token',
label,
address,
...meta,
automation: 'reference-only',
publishNotes: 'Anchor/reference asset; confirm explorer address and keep mapping docs current',
});
}
for (const pool of chainData.pmmPools || []) {
pushEntry(entries, {
sourceRegistry: 'cross-chain-pmm-lps/config/deployment-status.json',
contractType: 'pmm_pool',
label: `${pool.base}/${pool.quote}`,
address: pool.poolAddress,
...meta,
automation: chainId === '138' ? 'partial' : 'inventory-only',
publishNotes: `PMM pool (${pool.role || 'unclassified'}); verify source if custom deployment and keep routing inventory aligned`,
});
}
for (const pool of chainData.pmmPoolsVolatile || []) {
pushEntry(entries, {
sourceRegistry: 'cross-chain-pmm-lps/config/deployment-status.json',
contractType: 'pmm_pool_volatile',
label: `${pool.base}/${pool.quote}`,
address: pool.poolAddress,
...meta,
automation: 'inventory-only',
publishNotes: `Volatile PMM pool (${pool.role || 'unclassified'}); verify source where repo owns deployment and keep routing inventory aligned`,
});
}
for (const venue of chainData.gasReferenceVenues || []) {
if (!venue.venueAddress) continue;
pushEntry(entries, {
sourceRegistry: 'cross-chain-pmm-lps/config/deployment-status.json',
contractType: 'reference_venue',
label: `${venue.protocol}:${venue.base}/${venue.quote}`,
address: venue.venueAddress,
...meta,
automation: 'inventory-only',
publishNotes: 'Reference venue entry; verify only if repo owns deployment, otherwise treat as external dependency',
});
}
}
entries.sort((a, b) => {
if (a.chainId !== b.chainId) return Number(a.chainId) - Number(b.chainId);
if (a.contractType !== b.contractType) return a.contractType.localeCompare(b.contractType);
return a.label.localeCompare(b.label);
});
const summaryByChain = new Map();
for (const entry of entries) {
const key = `${entry.chainId}:${entry.chainName}`;
const current = summaryByChain.get(key) || { total: 0, canonical: 0, cw: 0, pools: 0 };
current.total += 1;
if (entry.contractType === 'canonical_contract') current.canonical += 1;
if (entry.contractType === 'cw_token' || entry.contractType === 'gas_mirror') current.cw += 1;
if (entry.contractType.includes('pmm_pool')) current.pools += 1;
summaryByChain.set(key, current);
}
const generatedAt = new Date().toISOString();
const jsonPayload = {
generatedAt,
sources: [
'config/smart-contracts-master.json',
'cross-chain-pmm-lps/config/deployment-status.json',
],
entryCount: entries.length,
entries,
};
const summaryRows = [...summaryByChain.entries()]
.map(([key, value]) => {
const [chainId, chainName] = key.split(':');
const meta = chainMeta(chainId, chainName);
return `| ${chainId} | ${chainName} | ${value.total} | ${value.canonical} | ${value.cw} | ${value.pools} | ${meta.explorer || 'manual'} |`;
})
.join('\n');
const sampleRows = entries.slice(0, 80).map((entry) => {
const explorer = entry.explorer || 'manual';
return `| ${entry.chainId} | ${entry.chainName} | ${entry.contractType} | ${entry.label} | \`${entry.address}\` | ${entry.verifierKind} | ${entry.automation} | ${explorer} | ${entry.verificationStatus} | ${entry.publicationStatus} |`;
}).join('\n');
const md = `# Contract Verification And Publication Matrix (All Networks)
**Generated:** ${generatedAt}
**Authoritative sources:** \`config/smart-contracts-master.json\`, \`cross-chain-pmm-lps/config/deployment-status.json\`
This matrix is the canonical repo-level inventory for **what still needs explorer verification and publication coverage across every network currently tracked in the workspace**.
## Meaning
- **Verification** = source or deployment metadata is verified on the network explorer used for that chain.
- **Publication** = the deployment is also reflected in the repos public inventories, token mappings, PMM status, and explorer-facing docs/config where applicable.
- **Pending** means the repo knows the address, but does not yet have a machine-confirmed proof here that explorer verification/publication is complete.
## Chain Summary
| Chain ID | Chain | Total Entries | Canonical Contracts | cW / Gas Mirrors | PMM Pools | Explorer |
| --- | --- | ---: | ---: | ---: | ---: | --- |
${summaryRows}
## Required operator path
1. **Chain 138 canonical contracts**
- Run: \`bash scripts/verify/run-contract-verification-with-proxy.sh\`
- Recheck: \`bash scripts/verify/check-contracts-on-chain-138.sh\`
2. **Chain 138 DODO v3 pilot**
- Run: \`bash scripts/verify/verify-dodo-v3-chain138-blockscout.sh\`
3. **Other EVM chains**
- Verify on the chain explorer shown below.
- If the repo owns the deployment, keep token/pool/mapping docs updated after explorer verification.
4. **Publication closure**
- Update \`config/smart-contracts-master.json\`, \`cross-chain-pmm-lps/config/deployment-status.json\`, token lists, and any chain-specific runbooks after verification is confirmed.
## Inventory sample
The JSON report in \`reports/status/contract_verification_publish_matrix.json\` contains the full set. The first 80 rows are shown here for readability.
| Chain ID | Chain | Type | Label | Address | Verifier | Automation | Explorer | Verify | Publish |
| --- | --- | --- | --- | --- | --- | --- | --- | --- | --- |
${sampleRows}
## Notes
- Entries from \`smart-contracts-master.json\` are treated as the canonical deploy inventory.
- Entries from \`deployment-status.json\` are treated as required publication inventory, even when explorer verification may be external or manual.
- This matrix does **not** claim every address is already verified; it marks the repo-wide backlog explicitly so the status can be closed chain by chain instead of being lost in prose.
`;
ensureDir(outputJsonPath);
ensureDir(outputMdPath);
fs.writeFileSync(outputJsonPath, JSON.stringify(jsonPayload, null, 2) + '\n');
fs.writeFileSync(outputMdPath, md + '\n');
console.log(`Wrote ${entries.length} entries to:`);
console.log(`- ${outputJsonPath}`);
console.log(`- ${outputMdPath}`);