const { ethers, upgrades, run } = require("hardhat"); const fs = require("fs"); const path = require("path"); require('dotenv').config({ path: path.join(__dirname, '..', '.env') }); const deploymentFile = path.join(__dirname, "deployedAddresses.json"); async function main() { const privateKey = process.env.PRIVATE_KEY; const network = await hre.network.name; let deployer; if (network === "hardhat" || network === "localhost") { // Use default hardhat account for local testing [deployer] = await ethers.getSigners(); console.log(`Using default hardhat account: ${deployer.address}`); } else { const wallet = new ethers.Wallet(privateKey, ethers.provider); deployer = wallet.connect(ethers.provider); console.log(`Using private key for account: ${deployer.address}`); } console.log("Deploying contracts with the account:", deployer.address); let deploymentData = {}; if (fs.existsSync(deploymentFile)) { deploymentData = JSON.parse(fs.readFileSync(deploymentFile, "utf8")); } // Select contract and proxy address based on network let contractName; let proxyAddress; if (network === "base") { contractName = "PacaFinanceWithBoostAndScheduleBase"; proxyAddress = process.env.PROXY_ADDRESS_BASE; } else if (network === "sonic") { contractName = "PacaFinanceWithBoostAndScheduleSonic"; proxyAddress = process.env.PROXY_ADDRESS_SONIC || deploymentData.proxyAddress; } else if (network === "mainnet") { contractName = "PacaFinanceWithBoostAndScheduleBsc"; proxyAddress = process.env.PROXY_ADDRESS_BSC || deploymentData.proxyAddress; } else { // Default to BSC for other networks (like test networks) contractName = "PacaFinanceWithBoostAndScheduleBsc"; proxyAddress = deploymentData.proxyAddress; } if (!proxyAddress) { // Initial deployment console.log("Deploying proxy..."); const Paca = await ethers.getContractFactory(contractName, deployer); const proxy = await upgrades.deployProxy(Paca, [], { initializer: "initialize", }); await proxy.waitForDeployment(); proxyAddress = proxy.target; const implementationAddress = await upgrades.erc1967.getImplementationAddress(proxyAddress); console.log("Proxy deployed to:", proxyAddress); console.log("Implementation deployed to:", implementationAddress); deploymentData.proxyAddress = proxyAddress; deploymentData.implementationAddress = implementationAddress; fs.writeFileSync(deploymentFile, JSON.stringify(deploymentData, null, 2)); await verifyContract(implementationAddress, contractName); } else { // Upgrade console.log("Upgrading proxy..."); const Paca = await ethers.getContractFactory(contractName, deployer); // Get current implementation for comparison const oldImplementationAddress = await upgrades.erc1967.getImplementationAddress(proxyAddress); console.log("Current implementation:", oldImplementationAddress); // Perform the upgrade console.log("Performing upgrade..."); const upgraded = await upgrades.upgradeProxy(proxyAddress, Paca); // Wait for deployment to complete await upgraded.waitForDeployment(); console.log("Waiting 10 seconds before verification..."); await new Promise(resolve => setTimeout(resolve, 10000)); // Get the new implementation address after deployment is complete const newImplementationAddress = await upgrades.erc1967.getImplementationAddress(proxyAddress); // Double check we actually have a new address if (newImplementationAddress.toLowerCase() === oldImplementationAddress.toLowerCase()) { console.error("Warning: New implementation address is the same as the old one!"); } console.log("New implementation deployed to:", newImplementationAddress); // Save the new implementation address deploymentData.implementationAddress = newImplementationAddress; fs.writeFileSync(deploymentFile, JSON.stringify(deploymentData, null, 2)); // Verify the new implementation await verifyContract(newImplementationAddress, contractName); } } async function verifyContract(address, contractName) { if (!address) return; console.log(`Verifying contract at ${address}...`); // Wait a bit before verification console.log("Waiting 10 seconds before verification..."); await new Promise(resolve => setTimeout(resolve, 10000)); try { await run("verify:verify", { address: address, constructorArguments: [] }); console.log("Contract verified successfully."); } catch (err) { if (err.message.includes("already been verified")) { console.log("Contract is already verified."); } else { console.log("Attempting verification with explicit contract path..."); try { await run("verify:verify", { address: address, contract: `contracts/${contractName}.sol:${contractName}`, constructorArguments: [] }); console.log("Verification successful."); } catch (manualErr) { console.error("Verification failed:", manualErr.message); console.log("\nTo verify manually, run:"); console.log(`npx hardhat verify --network ${hre.network.name} ${address}`); } } } } main() .then(() => process.exit(0)) .catch((error) => { console.error(error); process.exit(1); });