@solarity/hardhat-migrate
Version:
The simplest way to deploy smart contracts
238 lines • 12.7 kB
JavaScript
;
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var __importStar = (this && this.__importStar) || (function () {
var ownKeys = function(o) {
ownKeys = Object.getOwnPropertyNames || function (o) {
var ar = [];
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
return ar;
};
return ownKeys(o);
};
return function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
__setModuleDefault(result, mod);
return result;
};
})();
var Deployer_1;
Object.defineProperty(exports, "__esModule", { value: true });
exports.Deployer = void 0;
const ethers_1 = require("ethers");
const utils_1 = require("../utils");
const errors_1 = require("../errors");
const constants_1 = require("../constants");
const BytecodeAdapter_1 = require("./adapters/BytecodeAdapter");
const type_checks_1 = require("../types/type-checks");
const Stats_1 = require("../tools/Stats");
const Reporter_1 = require("../tools/reporters/Reporter");
const NetworkManager_1 = require("../tools/network/NetworkManager");
const TransactionRunner_1 = require("../tools/runners/TransactionRunner");
const TransactionProcessor_1 = require("../tools/storage/TransactionProcessor");
const VerificationProcessor_1 = require("../tools/storage/VerificationProcessor");
const EthersContractFactoryAdapter_1 = require("./adapters/EthersContractFactoryAdapter");
const TypechainContractFactoryAdapter_1 = require("./adapters/TypechainContractFactoryAdapter");
let Deployer = Deployer_1 = class Deployer {
_hre;
constructor(_hre) {
this._hre = _hre;
}
async deploy(contract, argsOrParameters = [], parameters = {}) {
if (!Array.isArray(argsOrParameters)) {
parameters = argsOrParameters;
argsOrParameters = [];
}
const adapter = Deployer_1.resolveAdapter(this._hre, contract);
const minimalContract = await adapter.fromInstance(contract, parameters);
const contractAddress = await minimalContract.deploy(argsOrParameters, parameters);
return adapter.toInstance(contract, contractAddress, parameters);
}
async deployERC1967Proxy(implementationFactory, constructorCalldata, argsOrParameters = [], parameters = {}) {
await this.validateConstructorCalldata(implementationFactory, parameters, constructorCalldata);
return this.deployProxy(implementationFactory, "ERC1967Proxy", (implementationAddress) => [implementationAddress, constructorCalldata], argsOrParameters, parameters);
}
async deployAdminableProxy(implementationFactory, constructorCalldata, argsOrParameters = [], parameters = {}) {
await this.validateConstructorCalldata(implementationFactory, parameters, constructorCalldata);
return this.deployProxy(implementationFactory, "AdminableProxy", (implementationAddress) => [implementationAddress, constructorCalldata], argsOrParameters, parameters);
}
async deployTransparentUpgradeableProxy(implementationFactory, proxyAdmin, constructorCalldata, argsOrParameters = [], parameters = {}) {
await this.validateConstructorCalldata(implementationFactory, parameters, constructorCalldata);
if (proxyAdmin === ethers_1.ZeroAddress) {
throw new errors_1.MigrateError("Proxy admin cannot be the zero address");
}
return this.deployProxy(implementationFactory, "TransparentUpgradeableProxy", (implementationAddress) => [implementationAddress, proxyAdmin, constructorCalldata], argsOrParameters, parameters);
}
async deployProxy(implementationFactory, proxyFactoryName, proxyArgs, argsOrParameters = [], parameters = {}) {
const { ethers, artifacts } = await Promise.resolve().then(() => __importStar(require("hardhat")));
let proxyFactory;
try {
proxyFactory = await ethers.getContractFactory(proxyFactoryName);
}
catch {
throw new errors_1.MigrateError(`Contract factory for ${proxyFactoryName} not found. Please add import of the proxy to one of the contracts in the project.`);
}
const adapter = Deployer_1.resolveAdapter(this._hre, implementationFactory);
let implementationArgs = [];
let implementationParameters = {};
if (argsOrParameters && Array.isArray(argsOrParameters)) {
implementationArgs = argsOrParameters;
}
else if (argsOrParameters && typeof argsOrParameters === "object") {
implementationParameters = argsOrParameters;
}
else {
implementationParameters = parameters;
}
let instanceName = adapter.getContractName(implementationFactory, implementationParameters);
const implementation = (await this.deploy(implementationFactory, implementationArgs, {
...implementationParameters,
name: `${instanceName} implementation`,
}));
VerificationProcessor_1.VerificationProcessor.saveVerificationFunction({
contractAddress: await implementation.getAddress(),
contractName: instanceName,
constructorArguments: implementationArgs,
chainId: Number(await (0, utils_1.getChainId)()),
});
let artifact = await artifacts.readArtifact(proxyFactoryName);
const proxy = await this.deploy(proxyFactory, proxyArgs(await implementation.getAddress()), {
name: `${instanceName} proxy`,
});
VerificationProcessor_1.VerificationProcessor.saveVerificationFunction({
contractAddress: await proxy.getAddress(),
contractName: `${artifact.sourceName}:${artifact.contractName}`,
constructorArguments: proxyArgs(await implementation.getAddress()),
chainId: Number(await (0, utils_1.getChainId)()),
});
return this.deployed(implementationFactory, `${instanceName} proxy`);
}
async validateConstructorCalldata(implementationFactory, parameters, constructorCalldata) {
if (!(0, type_checks_1.isTypechainFactoryClass)(implementationFactory) || constructorCalldata == "0x" || constructorCalldata == "") {
return;
}
const adapter = Deployer_1.resolveAdapter(this._hre, implementationFactory);
const contractInterface = adapter.getInterface(implementationFactory);
const functionFragment = contractInterface.parseTransaction({ data: constructorCalldata });
if (!functionFragment) {
throw new errors_1.MigrateError("Invalid constructor calldata. Correct it and use --continue flag to continue migration.");
}
Reporter_1.Reporter.notifyOfProxyConstructorUsage(adapter.getContractName(implementationFactory, parameters), functionFragment.name);
}
async deployed(contract, contractIdentifier) {
const adapter = Deployer_1.resolveAdapter(this._hre, contract);
const defaultContractName = adapter.getContractName(contract, {});
let contractAddress;
if (contractIdentifier === undefined) {
contractAddress = await TransactionProcessor_1.TransactionProcessor?.tryRestoreContractAddressByName(defaultContractName);
return adapter.toInstance(contract, contractAddress, {});
}
if ((0, ethers_1.isAddress)(contractIdentifier)) {
if (!(await (0, utils_1.isDeployedContractAddress)(contractIdentifier))) {
throw new errors_1.MigrateError(`Contract with address '${contractIdentifier}' is not deployed`);
}
return adapter.toInstance(contract, contractIdentifier, {});
}
contractAddress = await TransactionProcessor_1.TransactionProcessor?.tryRestoreContractAddressByName(contractIdentifier);
return adapter.toInstance(contract, contractAddress, {});
}
async save(contract, contractAddress, force = false) {
if (!(await (0, utils_1.isDeployedContractAddress)(contractAddress)) && !force) {
throw new errors_1.MigrateError(`Contract with address '${contractAddress}' is not deployed`);
}
const saveMetadata = {
migrationNumber: Stats_1.Stats.currentMigration,
};
if (typeof contract === "string") {
TransactionProcessor_1.TransactionProcessor?.saveContractAddress(contract, contractAddress, saveMetadata);
return;
}
const adapter = Deployer_1.resolveAdapter(this._hre, contract);
const defaultContractName = adapter.getContractName(contract, {});
TransactionProcessor_1.TransactionProcessor?.saveContractAddress(defaultContractName, contractAddress, saveMetadata);
}
async sendNative(to, value, name = constants_1.SEND_NATIVE_TX_NAME) {
const signer = await NetworkManager_1.networkManager.getSigner();
const tx = await this._buildSendTransaction(to, value, name);
const methodString = "sendNative";
if (this._hre.config.migrate.execution.continue) {
try {
const savedTx = TransactionProcessor_1.TransactionProcessor?.tryRestoreSavedTransaction(tx);
Reporter_1.Reporter.notifyTransactionRecovery(methodString, savedTx);
return savedTx;
}
catch {
Reporter_1.Reporter.notifyTransactionSendingInsteadOfRecovery(methodString);
}
}
const txResponse = await signer.sendTransaction(tx);
const [receipt] = await Promise.all([
txResponse.wait(this._hre.config.migrate.execution.wait),
TransactionRunner_1.TransactionRunner.reportTransactionResponse(txResponse, methodString),
]);
const saveMetadata = {
migrationNumber: Stats_1.Stats.currentMigration,
methodName: methodString,
};
const savedTx = TransactionProcessor_1.TransactionProcessor?.saveTransaction(tx, receipt, saveMetadata);
return savedTx;
}
async setSigner(from) {
await NetworkManager_1.networkManager.setSigner(from);
}
async getSigner(from) {
return NetworkManager_1.networkManager.getSigner(from);
}
async getChainId() {
return (0, utils_1.getChainId)();
}
async _buildSendTransaction(to, value, name) {
return {
to,
value,
chainId: await (0, utils_1.getChainId)(),
data: "0x",
from: await (await NetworkManager_1.networkManager.getSigner()).getAddress(),
name,
};
}
static resolveAdapter(hre, contract) {
if ((0, type_checks_1.isTypechainFactoryClass)(contract)) {
return new TypechainContractFactoryAdapter_1.TypechainContractFactoryAdapter(hre);
}
if ((0, type_checks_1.isEthersContractFactory)(contract)) {
return new EthersContractFactoryAdapter_1.EthersContractFactoryAdapter(hre);
}
if ((0, type_checks_1.isBytecodeFactory)(contract)) {
return new BytecodeAdapter_1.BytecodeAdapter(hre);
}
throw new errors_1.MigrateError("Unknown Contract Factory Type");
}
};
exports.Deployer = Deployer;
exports.Deployer = Deployer = Deployer_1 = __decorate([
utils_1.catchError
], Deployer);
//# sourceMappingURL=Deployer.js.map