Currently deployed, has vesting tracker
This commit is contained in:
@@ -36,7 +36,7 @@ error StakeNotInSellState();
|
|||||||
|
|
||||||
// File: paca.sol
|
// File: paca.sol
|
||||||
|
|
||||||
contract PacaFinanceWithBoostAndScheduleUSDC is Initializable, ReentrancyGuardUpgradeable {
|
contract PacaFinanceWithBoostAndScheduleBase is Initializable, ReentrancyGuardUpgradeable {
|
||||||
using SafeERC20 for IERC20;
|
using SafeERC20 for IERC20;
|
||||||
|
|
||||||
|
|
||||||
@@ -136,8 +136,6 @@ contract PacaFinanceWithBoostAndScheduleUSDC is Initializable, ReentrancyGuardUp
|
|||||||
uint256 public unlockDelay;
|
uint256 public unlockDelay;
|
||||||
uint256 public withdrawLiabilities;
|
uint256 public withdrawLiabilities;
|
||||||
mapping(address => WithdrawStake[]) public withdrawStake;
|
mapping(address => WithdrawStake[]) public withdrawStake;
|
||||||
mapping(address => WithdrawVesting[]) public withdrawVesting;
|
|
||||||
uint256 private withdrawVestingCounter;
|
|
||||||
uint256 public restakeBonus;
|
uint256 public restakeBonus;
|
||||||
mapping(address => uint256) public addressFixedRate;
|
mapping(address => uint256) public addressFixedRate;
|
||||||
mapping(address => mapping(uint256 => SellStake)) public sellStakes;
|
mapping(address => mapping(uint256 => SellStake)) public sellStakes;
|
||||||
@@ -147,6 +145,12 @@ contract PacaFinanceWithBoostAndScheduleUSDC is Initializable, ReentrancyGuardUp
|
|||||||
mapping(address => mapping(uint256 => uint256)) private sellStakeKeyIndex;
|
mapping(address => mapping(uint256 => uint256)) private sellStakeKeyIndex;
|
||||||
uint256 public sellMin;
|
uint256 public sellMin;
|
||||||
|
|
||||||
|
mapping(address => WithdrawVesting[]) private withdrawVestingActual;
|
||||||
|
uint256 private withdrawVestingCounterActual;
|
||||||
|
|
||||||
|
// Track total withdraw vesting liabilities by token address
|
||||||
|
mapping(address => uint256) public withdrawVestingLiabilities;
|
||||||
|
|
||||||
// Events
|
// Events
|
||||||
event Staked(address indexed user, uint256 amount);
|
event Staked(address indexed user, uint256 amount);
|
||||||
event RewardClaimed(address indexed user, uint256 reward);
|
event RewardClaimed(address indexed user, uint256 reward);
|
||||||
@@ -451,14 +455,14 @@ contract PacaFinanceWithBoostAndScheduleUSDC is Initializable, ReentrancyGuardUp
|
|||||||
dollarsVested[oldAddress] = 0;
|
dollarsVested[oldAddress] = 0;
|
||||||
|
|
||||||
// Migrate pending vesting withdrawals
|
// Migrate pending vesting withdrawals
|
||||||
WithdrawVesting[] storage oldWithdrawVestings = withdrawVesting[oldAddress];
|
WithdrawVesting[] storage oldWithdrawVestings = withdrawVestingActual[oldAddress];
|
||||||
uint256 withdrawVestingCount = oldWithdrawVestings.length;
|
uint256 withdrawVestingCount = oldWithdrawVestings.length;
|
||||||
if (withdrawVestingCount > 0) {
|
if (withdrawVestingCount > 0) {
|
||||||
WithdrawVesting[] storage newWithdrawVestings = withdrawVesting[newAddress];
|
WithdrawVesting[] storage newWithdrawVestings = withdrawVestingActual[newAddress];
|
||||||
for (uint256 i = 0; i < withdrawVestingCount; i++) {
|
for (uint256 i = 0; i < withdrawVestingCount; i++) {
|
||||||
newWithdrawVestings.push(oldWithdrawVestings[i]);
|
newWithdrawVestings.push(oldWithdrawVestings[i]);
|
||||||
}
|
}
|
||||||
delete withdrawVesting[oldAddress];
|
delete withdrawVestingActual[oldAddress];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -824,7 +828,7 @@ function withdraw(uint256 _stakeIndex) external nonReentrant {
|
|||||||
* @param _vestingId The vesting ID to withdraw
|
* @param _vestingId The vesting ID to withdraw
|
||||||
*/
|
*/
|
||||||
function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
||||||
WithdrawVesting[] storage userVestings = withdrawVesting[msg.sender];
|
WithdrawVesting[] storage userVestings = withdrawVestingActual[msg.sender];
|
||||||
if (userVestings.length == 0) revert NoStakesAvailable();
|
if (userVestings.length == 0) revert NoStakesAvailable();
|
||||||
|
|
||||||
for (uint256 i = 0; i < userVestings.length; ++i) {
|
for (uint256 i = 0; i < userVestings.length; ++i) {
|
||||||
@@ -842,6 +846,9 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
// Update state before external calls
|
// Update state before external calls
|
||||||
vestingWithdraw.amount = 0;
|
vestingWithdraw.amount = 0;
|
||||||
|
|
||||||
|
// Decrement withdraw vesting liabilities for this token
|
||||||
|
withdrawVestingLiabilities[_token] -= _amount;
|
||||||
|
|
||||||
// Transfer tokens
|
// Transfer tokens
|
||||||
IERC20(_token).safeTransfer(msg.sender, _amount);
|
IERC20(_token).safeTransfer(msg.sender, _amount);
|
||||||
emit StakeWithdrawn(msg.sender, _amount, _vestingId);
|
emit StakeWithdrawn(msg.sender, _amount, _vestingId);
|
||||||
@@ -849,7 +856,6 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Revert if no matching vesting with non-zero amount was found
|
|
||||||
revert StakeNotFound();
|
revert StakeNotFound();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1009,13 +1015,16 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
vestedTotal[vesting.token] -= amountToClaim;
|
vestedTotal[vesting.token] -= amountToClaim;
|
||||||
|
|
||||||
// Add vesting claims to cooldown queue
|
// Add vesting claims to cooldown queue
|
||||||
withdrawVesting[msg.sender].push(WithdrawVesting({
|
withdrawVestingActual[msg.sender].push(WithdrawVesting({
|
||||||
vestingId: withdrawVestingCounter++,
|
vestingId: withdrawVestingCounterActual++,
|
||||||
amount: amountToClaim,
|
amount: amountToClaim,
|
||||||
unlockTime: block.timestamp + unlockDelay,
|
unlockTime: block.timestamp + unlockDelay,
|
||||||
token: vesting.token
|
token: vesting.token
|
||||||
}));
|
}));
|
||||||
|
|
||||||
|
// Increment withdraw vesting liabilities for this token
|
||||||
|
withdrawVestingLiabilities[vesting.token] += amountToClaim;
|
||||||
|
|
||||||
emit VestingClaimed(msg.sender, amountToClaim, 0);
|
emit VestingClaimed(msg.sender, amountToClaim, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1062,13 +1071,16 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
vestedTotal[_token] -= totalReward;
|
vestedTotal[_token] -= totalReward;
|
||||||
|
|
||||||
// Add vesting claims to cooldown queue
|
// Add vesting claims to cooldown queue
|
||||||
withdrawVesting[msg.sender].push(WithdrawVesting({
|
withdrawVestingActual[msg.sender].push(WithdrawVesting({
|
||||||
vestingId: withdrawVestingCounter++,
|
vestingId: withdrawVestingCounterActual++,
|
||||||
amount: totalReward,
|
amount: totalReward,
|
||||||
unlockTime: block.timestamp + unlockDelay,
|
unlockTime: block.timestamp + unlockDelay,
|
||||||
token: _token
|
token: _token
|
||||||
}));
|
}));
|
||||||
|
|
||||||
|
// Increment withdraw vesting liabilities for this token
|
||||||
|
withdrawVestingLiabilities[_token] += totalReward;
|
||||||
|
|
||||||
emit RewardClaimed(msg.sender, totalReward);
|
emit RewardClaimed(msg.sender, totalReward);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1237,15 +1249,23 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
/// @param user The address to evaluate.
|
/// @param user The address to evaluate.
|
||||||
/// @return An array of WithdrawVesting for the given user.
|
/// @return An array of WithdrawVesting for the given user.
|
||||||
function getAllWithdrawVestings(address user) external view returns (WithdrawVesting[] memory) {
|
function getAllWithdrawVestings(address user) external view returns (WithdrawVesting[] memory) {
|
||||||
return withdrawVesting[user];
|
return withdrawVestingActual[user];
|
||||||
}
|
}
|
||||||
|
|
||||||
/// @notice Returns the current withdraw vesting counter value
|
/// @notice Returns the current withdraw vesting counter value
|
||||||
/// @return Current counter value for tracking unique withdrawal IDs
|
/// @return Current counter value for tracking unique withdrawal IDs
|
||||||
function getWithdrawVestingCounter() external view returns (uint256) {
|
function getWithdrawVestingCounter() external view returns (uint256) {
|
||||||
return withdrawVestingCounter;
|
return withdrawVestingCounterActual;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// @notice Test function for upgrade verification
|
||||||
|
/// @return Returns a constant value to verify upgrade worked
|
||||||
|
function testUpgradeFunction() external pure returns (uint256) {
|
||||||
|
return 888;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/// @notice Function to put a stake for sale.
|
/// @notice Function to put a stake for sale.
|
||||||
/// Sets the original stake amount to 0 to prevent any alterations while for sale.
|
/// Sets the original stake amount to 0 to prevent any alterations while for sale.
|
||||||
/// @param _stakeId The stake to sell.
|
/// @param _stakeId The stake to sell.
|
||||||
|
|||||||
@@ -36,7 +36,7 @@ error StakeNotInSellState();
|
|||||||
|
|
||||||
// File: paca.sol
|
// File: paca.sol
|
||||||
|
|
||||||
contract PacaFinanceWithBoostAndScheduleUSDT is Initializable, ReentrancyGuardUpgradeable {
|
contract PacaFinanceWithBoostAndScheduleBsc is Initializable, ReentrancyGuardUpgradeable {
|
||||||
using SafeERC20 for IERC20;
|
using SafeERC20 for IERC20;
|
||||||
|
|
||||||
|
|
||||||
@@ -136,8 +136,6 @@ contract PacaFinanceWithBoostAndScheduleUSDT is Initializable, ReentrancyGuardUp
|
|||||||
uint256 public unlockDelay;
|
uint256 public unlockDelay;
|
||||||
uint256 public withdrawLiabilities;
|
uint256 public withdrawLiabilities;
|
||||||
mapping(address => WithdrawStake[]) public withdrawStake;
|
mapping(address => WithdrawStake[]) public withdrawStake;
|
||||||
mapping(address => WithdrawVesting[]) public withdrawVesting;
|
|
||||||
uint256 private withdrawVestingCounter;
|
|
||||||
uint256 public restakeBonus;
|
uint256 public restakeBonus;
|
||||||
mapping(address => uint256) public addressFixedRate;
|
mapping(address => uint256) public addressFixedRate;
|
||||||
mapping(address => mapping(uint256 => SellStake)) public sellStakes;
|
mapping(address => mapping(uint256 => SellStake)) public sellStakes;
|
||||||
@@ -147,6 +145,12 @@ contract PacaFinanceWithBoostAndScheduleUSDT is Initializable, ReentrancyGuardUp
|
|||||||
mapping(address => mapping(uint256 => uint256)) private sellStakeKeyIndex;
|
mapping(address => mapping(uint256 => uint256)) private sellStakeKeyIndex;
|
||||||
uint256 public sellMin;
|
uint256 public sellMin;
|
||||||
|
|
||||||
|
mapping(address => WithdrawVesting[]) private withdrawVestingActual;
|
||||||
|
uint256 private withdrawVestingCounterActual;
|
||||||
|
|
||||||
|
// Track total withdraw vesting liabilities by token address
|
||||||
|
mapping(address => uint256) public withdrawVestingLiabilities;
|
||||||
|
|
||||||
// Events
|
// Events
|
||||||
event Staked(address indexed user, uint256 amount);
|
event Staked(address indexed user, uint256 amount);
|
||||||
event RewardClaimed(address indexed user, uint256 reward);
|
event RewardClaimed(address indexed user, uint256 reward);
|
||||||
@@ -207,6 +211,7 @@ contract PacaFinanceWithBoostAndScheduleUSDT is Initializable, ReentrancyGuardUp
|
|||||||
owners[_owner] = false;
|
owners[_owner] = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/// @notice Function to add a bot to the list (only callable by the contract owner)
|
/// @notice Function to add a bot to the list (only callable by the contract owner)
|
||||||
function addBot(address bot) external onlyOwner {
|
function addBot(address bot) external onlyOwner {
|
||||||
if (bot == address(0)) revert InvalidAddress();
|
if (bot == address(0)) revert InvalidAddress();
|
||||||
@@ -226,6 +231,7 @@ contract PacaFinanceWithBoostAndScheduleUSDT is Initializable, ReentrancyGuardUp
|
|||||||
emit PoolUpdated(_lockupPeriod, _dailyRewardRate);
|
emit PoolUpdated(_lockupPeriod, _dailyRewardRate);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
function depositRewards(uint256 _amount) external onlyOwner {
|
function depositRewards(uint256 _amount) external onlyOwner {
|
||||||
IERC20(pool.tokenAddress).safeTransferFrom(msg.sender, address(this), _amount);
|
IERC20(pool.tokenAddress).safeTransferFrom(msg.sender, address(this), _amount);
|
||||||
pool.totalRewards = pool.totalRewards + _amount;
|
pool.totalRewards = pool.totalRewards + _amount;
|
||||||
@@ -449,14 +455,14 @@ contract PacaFinanceWithBoostAndScheduleUSDT is Initializable, ReentrancyGuardUp
|
|||||||
dollarsVested[oldAddress] = 0;
|
dollarsVested[oldAddress] = 0;
|
||||||
|
|
||||||
// Migrate pending vesting withdrawals
|
// Migrate pending vesting withdrawals
|
||||||
WithdrawVesting[] storage oldWithdrawVestings = withdrawVesting[oldAddress];
|
WithdrawVesting[] storage oldWithdrawVestings = withdrawVestingActual[oldAddress];
|
||||||
uint256 withdrawVestingCount = oldWithdrawVestings.length;
|
uint256 withdrawVestingCount = oldWithdrawVestings.length;
|
||||||
if (withdrawVestingCount > 0) {
|
if (withdrawVestingCount > 0) {
|
||||||
WithdrawVesting[] storage newWithdrawVestings = withdrawVesting[newAddress];
|
WithdrawVesting[] storage newWithdrawVestings = withdrawVestingActual[newAddress];
|
||||||
for (uint256 i = 0; i < withdrawVestingCount; i++) {
|
for (uint256 i = 0; i < withdrawVestingCount; i++) {
|
||||||
newWithdrawVestings.push(oldWithdrawVestings[i]);
|
newWithdrawVestings.push(oldWithdrawVestings[i]);
|
||||||
}
|
}
|
||||||
delete withdrawVesting[oldAddress];
|
delete withdrawVestingActual[oldAddress];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -812,7 +818,7 @@ contract PacaFinanceWithBoostAndScheduleUSDT is Initializable, ReentrancyGuardUp
|
|||||||
* @param _vestingId The vesting ID to withdraw
|
* @param _vestingId The vesting ID to withdraw
|
||||||
*/
|
*/
|
||||||
function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
||||||
WithdrawVesting[] storage userVestings = withdrawVesting[msg.sender];
|
WithdrawVesting[] storage userVestings = withdrawVestingActual[msg.sender];
|
||||||
if (userVestings.length == 0) revert NoStakesAvailable();
|
if (userVestings.length == 0) revert NoStakesAvailable();
|
||||||
|
|
||||||
for (uint256 i = 0; i < userVestings.length; ++i) {
|
for (uint256 i = 0; i < userVestings.length; ++i) {
|
||||||
@@ -830,6 +836,9 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
// Update state before external calls
|
// Update state before external calls
|
||||||
vestingWithdraw.amount = 0;
|
vestingWithdraw.amount = 0;
|
||||||
|
|
||||||
|
// Decrement withdraw vesting liabilities for this token
|
||||||
|
withdrawVestingLiabilities[_token] -= _amount;
|
||||||
|
|
||||||
// Transfer tokens
|
// Transfer tokens
|
||||||
IERC20(_token).safeTransfer(msg.sender, _amount);
|
IERC20(_token).safeTransfer(msg.sender, _amount);
|
||||||
emit StakeWithdrawn(msg.sender, _amount, _vestingId);
|
emit StakeWithdrawn(msg.sender, _amount, _vestingId);
|
||||||
@@ -837,7 +846,6 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Revert if no matching vesting with non-zero amount was found
|
|
||||||
revert StakeNotFound();
|
revert StakeNotFound();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -997,13 +1005,16 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
vestedTotal[vesting.token] -= amountToClaim;
|
vestedTotal[vesting.token] -= amountToClaim;
|
||||||
|
|
||||||
// Add vesting claims to cooldown queue
|
// Add vesting claims to cooldown queue
|
||||||
withdrawVesting[msg.sender].push(WithdrawVesting({
|
withdrawVestingActual[msg.sender].push(WithdrawVesting({
|
||||||
vestingId: withdrawVestingCounter++,
|
vestingId: withdrawVestingCounterActual++,
|
||||||
amount: amountToClaim,
|
amount: amountToClaim,
|
||||||
unlockTime: block.timestamp + unlockDelay,
|
unlockTime: block.timestamp + unlockDelay,
|
||||||
token: vesting.token
|
token: vesting.token
|
||||||
}));
|
}));
|
||||||
|
|
||||||
|
// Increment withdraw vesting liabilities for this token
|
||||||
|
withdrawVestingLiabilities[vesting.token] += amountToClaim;
|
||||||
|
|
||||||
emit VestingClaimed(msg.sender, amountToClaim, 0);
|
emit VestingClaimed(msg.sender, amountToClaim, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1050,13 +1061,16 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
vestedTotal[_token] -= totalReward;
|
vestedTotal[_token] -= totalReward;
|
||||||
|
|
||||||
// Add vesting claims to cooldown queue
|
// Add vesting claims to cooldown queue
|
||||||
withdrawVesting[msg.sender].push(WithdrawVesting({
|
withdrawVestingActual[msg.sender].push(WithdrawVesting({
|
||||||
vestingId: withdrawVestingCounter++,
|
vestingId: withdrawVestingCounterActual++,
|
||||||
amount: totalReward,
|
amount: totalReward,
|
||||||
unlockTime: block.timestamp + unlockDelay,
|
unlockTime: block.timestamp + unlockDelay,
|
||||||
token: _token
|
token: _token
|
||||||
}));
|
}));
|
||||||
|
|
||||||
|
// Increment withdraw vesting liabilities for this token
|
||||||
|
withdrawVestingLiabilities[_token] += totalReward;
|
||||||
|
|
||||||
emit RewardClaimed(msg.sender, totalReward);
|
emit RewardClaimed(msg.sender, totalReward);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1225,15 +1239,22 @@ function withdrawVestingToken(uint256 _vestingId) external nonReentrant {
|
|||||||
/// @param user The address to evaluate.
|
/// @param user The address to evaluate.
|
||||||
/// @return An array of WithdrawVesting for the given user.
|
/// @return An array of WithdrawVesting for the given user.
|
||||||
function getAllWithdrawVestings(address user) external view returns (WithdrawVesting[] memory) {
|
function getAllWithdrawVestings(address user) external view returns (WithdrawVesting[] memory) {
|
||||||
return withdrawVesting[user];
|
return withdrawVestingActual[user];
|
||||||
}
|
}
|
||||||
|
|
||||||
/// @notice Returns the current withdraw vesting counter value
|
/// @notice Returns the current withdraw vesting counter value
|
||||||
/// @return Current counter value for tracking unique withdrawal IDs
|
/// @return Current counter value for tracking unique withdrawal IDs
|
||||||
function getWithdrawVestingCounter() external view returns (uint256) {
|
function getWithdrawVestingCounter() external view returns (uint256) {
|
||||||
return withdrawVestingCounter;
|
return withdrawVestingCounterActual;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// @notice Test function for upgrade verification
|
||||||
|
/// @return Returns a constant value to verify upgrade worked
|
||||||
|
function testUpgradeFunction() external pure returns (uint256) {
|
||||||
|
return 777;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/// @notice Function to put a stake for sale.
|
/// @notice Function to put a stake for sale.
|
||||||
/// Sets the original stake amount to 0 to prevent any alterations while for sale.
|
/// Sets the original stake amount to 0 to prevent any alterations while for sale.
|
||||||
/// @param _stakeId The stake to sell.
|
/// @param _stakeId The stake to sell.
|
||||||
|
|||||||
1435
contracts/sonic_paca.sol
Normal file
1435
contracts/sonic_paca.sol
Normal file
File diff suppressed because it is too large
Load Diff
@@ -1,11 +1,8 @@
|
|||||||
require("@openzeppelin/hardhat-upgrades");
|
require("@openzeppelin/hardhat-upgrades");
|
||||||
require("@nomicfoundation/hardhat-ignition-ethers");
|
require("@nomicfoundation/hardhat-ignition-ethers");
|
||||||
// require("@nomiclabs/hardhat-ethers");
|
|
||||||
// require("@nomiclabs/hardhat-etherscan");
|
|
||||||
require("hardhat-contract-sizer");
|
require("hardhat-contract-sizer");
|
||||||
// require("dotenv").config();
|
|
||||||
// require("hardhat-gas-reporter");
|
|
||||||
require("@nomicfoundation/hardhat-verify");
|
require("@nomicfoundation/hardhat-verify");
|
||||||
|
require("dotenv").config();
|
||||||
|
|
||||||
const env = process.env;
|
const env = process.env;
|
||||||
// This is a sample Hardhat task. To learn how to create your own go to
|
// This is a sample Hardhat task. To learn how to create your own go to
|
||||||
@@ -82,15 +79,8 @@ module.exports = {
|
|||||||
networks: {
|
networks: {
|
||||||
hardhat: {
|
hardhat: {
|
||||||
forking: {
|
forking: {
|
||||||
// MAINNET FORK
|
url: `https://rpc.soniclabs.com`,
|
||||||
url: `https://bsc-mainnet.nodereal.io/v1/f82aa3b8072a46ccadf3024a96f0cff4`,
|
blockNumber: 37000000,
|
||||||
// blockNumber: 30488174,
|
|
||||||
chainId: 56,
|
|
||||||
|
|
||||||
// TESTNET FORK
|
|
||||||
// url: `https://bsc-testnet.nodereal.io/v1/f82aa3b8072a46ccadf3024a96f0cff4`,
|
|
||||||
// blockNumber: 31828689,
|
|
||||||
// chainId: 97,
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
local: {
|
local: {
|
||||||
@@ -132,26 +122,32 @@ module.exports = {
|
|||||||
// gas: 2e9,
|
// gas: 2e9,
|
||||||
},
|
},
|
||||||
mainnet: {
|
mainnet: {
|
||||||
url: `https://bsc-dataseed1.binance.org`,
|
url: env.MAINNET_RPC_URL || `https://bsc-dataseed1.binance.org`,
|
||||||
chainId: 56,
|
chainId: 56,
|
||||||
|
accounts: env.PRIVATE_KEY ? [env.PRIVATE_KEY] : [],
|
||||||
},
|
},
|
||||||
base: {
|
base: {
|
||||||
url: `https://base-mainnet.public.blastapi.io`,
|
url: env.BASE_RPC_URL || `https://base-mainnet.public.blastapi.io`,
|
||||||
chainId: 8453,
|
chainId: 8453,
|
||||||
|
accounts: env.PRIVATE_KEY ? [env.PRIVATE_KEY] : [],
|
||||||
},
|
},
|
||||||
sonic: {
|
sonic: {
|
||||||
url: `https://rpc.soniclabs.com`,
|
url: env.SONIC_RPC_URL || `https://rpc.soniclabs.com`,
|
||||||
chainId: 146,
|
chainId: 146,
|
||||||
|
accounts: env.PRIVATE_KEY ? [env.PRIVATE_KEY] : [],
|
||||||
|
},
|
||||||
|
sonicfork: {
|
||||||
|
url: "http://127.0.0.1:8545",
|
||||||
|
forking: {
|
||||||
|
url: `https://rpc.soniclabs.com`,
|
||||||
|
blockNumber: 37513000, // Recent block
|
||||||
|
},
|
||||||
|
accounts: env.PRIVATE_KEY ? [env.PRIVATE_KEY] : [],
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
etherscan: {
|
etherscan: {
|
||||||
enable: true,
|
enable: true,
|
||||||
apiKey: {
|
apiKey: "JRKR5T93RQTKVERUJ2NVE4T994TD66QGFH",
|
||||||
bbsc: "verifyContract",
|
|
||||||
base: "GN555QYEWPDFZ47H1TR5ASK693D38A69GY",
|
|
||||||
mainnet: "1I15826QJ4HHY2UTGK3EZEA4TNBT68FB83",
|
|
||||||
sonic: "N6DMIQQNJ7634I1ETH527Z1WZQM2Q6GEW8"
|
|
||||||
},
|
|
||||||
customChains: [
|
customChains: [
|
||||||
{
|
{
|
||||||
network: "bbsc",
|
network: "bbsc",
|
||||||
|
|||||||
@@ -1,17 +1,24 @@
|
|||||||
const { ethers, upgrades, run } = require("hardhat");
|
const { ethers, upgrades, run } = require("hardhat");
|
||||||
const fs = require("fs");
|
const fs = require("fs");
|
||||||
const path = require("path");
|
const path = require("path");
|
||||||
require('dotenv').config();
|
require('dotenv').config({ path: path.join(__dirname, '..', '.env') });
|
||||||
|
|
||||||
const deploymentFile = path.join(__dirname, "deployedAddresses.json");
|
const deploymentFile = path.join(__dirname, "deployedAddresses.json");
|
||||||
|
|
||||||
async function main() {
|
async function main() {
|
||||||
const privateKey = process.env.pk;
|
const privateKey = process.env.PRIVATE_KEY;
|
||||||
const network = await hre.network.name;
|
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);
|
const wallet = new ethers.Wallet(privateKey, ethers.provider);
|
||||||
const deployer = wallet.connect(ethers.provider);
|
deployer = wallet.connect(ethers.provider);
|
||||||
console.log(`Using private key for account: ${deployer.address}`);
|
console.log(`Using private key for account: ${deployer.address}`);
|
||||||
|
}
|
||||||
console.log("Deploying contracts with the account:", deployer.address);
|
console.log("Deploying contracts with the account:", deployer.address);
|
||||||
|
|
||||||
let deploymentData = {};
|
let deploymentData = {};
|
||||||
@@ -19,12 +26,25 @@ async function main() {
|
|||||||
deploymentData = JSON.parse(fs.readFileSync(deploymentFile, "utf8"));
|
deploymentData = JSON.parse(fs.readFileSync(deploymentFile, "utf8"));
|
||||||
}
|
}
|
||||||
|
|
||||||
const contractName = network === "mainnet"
|
// Select contract and proxy address based on network
|
||||||
? "PacaFinanceWithBoostAndScheduleUSDT"
|
let contractName;
|
||||||
: "PacaFinanceWithBoostAndScheduleUSDC";
|
|
||||||
|
|
||||||
let proxyAddress;
|
let proxyAddress;
|
||||||
if (!deploymentData.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
|
// Initial deployment
|
||||||
console.log("Deploying proxy...");
|
console.log("Deploying proxy...");
|
||||||
const Paca = await ethers.getContractFactory(contractName, deployer);
|
const Paca = await ethers.getContractFactory(contractName, deployer);
|
||||||
@@ -46,12 +66,9 @@ async function main() {
|
|||||||
await verifyContract(implementationAddress, contractName);
|
await verifyContract(implementationAddress, contractName);
|
||||||
} else {
|
} else {
|
||||||
// Upgrade
|
// Upgrade
|
||||||
proxyAddress = deploymentData.proxyAddress;
|
|
||||||
console.log("Upgrading proxy...");
|
console.log("Upgrading proxy...");
|
||||||
|
|
||||||
const Paca = await ethers.getContractFactory(contractName, deployer);
|
const Paca = await ethers.getContractFactory(contractName, deployer);
|
||||||
// //commen tout for mainet
|
|
||||||
// await upgrades.forceImport(proxyAddress, Paca);
|
|
||||||
|
|
||||||
// Get current implementation for comparison
|
// Get current implementation for comparison
|
||||||
const oldImplementationAddress = await upgrades.erc1967.getImplementationAddress(proxyAddress);
|
const oldImplementationAddress = await upgrades.erc1967.getImplementationAddress(proxyAddress);
|
||||||
|
|||||||
112
scripts/manualUpgrade.js
Normal file
112
scripts/manualUpgrade.js
Normal file
@@ -0,0 +1,112 @@
|
|||||||
|
const { ethers } = 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") {
|
||||||
|
[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);
|
||||||
|
|
||||||
|
// Select contract based on network
|
||||||
|
let contractName;
|
||||||
|
if (network === "base") {
|
||||||
|
contractName = "PacaFinanceWithBoostAndScheduleBase";
|
||||||
|
} else if (network === "sonic") {
|
||||||
|
contractName = "PacaFinanceWithBoostAndScheduleSonic";
|
||||||
|
} else if (network === "mainnet") {
|
||||||
|
contractName = "PacaFinanceWithBoostAndScheduleBsc";
|
||||||
|
} else {
|
||||||
|
contractName = "PacaFinanceWithBoostAndScheduleBsc";
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log(`Deploying ${contractName} for network: ${network}`);
|
||||||
|
|
||||||
|
// Read deployment data
|
||||||
|
let deploymentData = {};
|
||||||
|
if (fs.existsSync(deploymentFile)) {
|
||||||
|
deploymentData = JSON.parse(fs.readFileSync(deploymentFile, "utf8"));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!deploymentData.proxyAddress) {
|
||||||
|
console.error("No proxy address found in deployment file!");
|
||||||
|
process.exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
const proxyAddress = deploymentData.proxyAddress;
|
||||||
|
console.log("Proxy address:", proxyAddress);
|
||||||
|
|
||||||
|
// Deploy new implementation contract
|
||||||
|
console.log("Deploying new implementation contract...");
|
||||||
|
const PacaFactory = await ethers.getContractFactory(contractName, deployer);
|
||||||
|
const newImplementation = await PacaFactory.deploy();
|
||||||
|
await newImplementation.waitForDeployment();
|
||||||
|
|
||||||
|
const newImplementationAddress = await newImplementation.getAddress();
|
||||||
|
console.log("New implementation deployed to:", newImplementationAddress);
|
||||||
|
|
||||||
|
// ProxyAdmin contract address
|
||||||
|
const proxyAdminAddress = "0x3459Fe72D4274d40d449aE1806F8E2149302F28B";
|
||||||
|
|
||||||
|
// ProxyAdmin ABI with upgradeAndCall function
|
||||||
|
const proxyAdminABI = [
|
||||||
|
"function upgradeAndCall(address proxy, address implementation, bytes data) external payable"
|
||||||
|
];
|
||||||
|
|
||||||
|
// Connect to ProxyAdmin contract
|
||||||
|
const proxyAdmin = new ethers.Contract(proxyAdminAddress, proxyAdminABI, deployer);
|
||||||
|
|
||||||
|
// Perform upgrade with empty call data
|
||||||
|
console.log("Performing upgrade via ProxyAdmin...");
|
||||||
|
console.log("ProxyAdmin address:", proxyAdminAddress);
|
||||||
|
const upgradeTx = await proxyAdmin.upgradeAndCall(proxyAddress, newImplementationAddress, "0x");
|
||||||
|
console.log("Upgrade transaction hash:", upgradeTx.hash);
|
||||||
|
|
||||||
|
// Wait for transaction confirmation
|
||||||
|
await upgradeTx.wait();
|
||||||
|
console.log("Upgrade completed successfully!");
|
||||||
|
|
||||||
|
// Update deployment data
|
||||||
|
deploymentData.implementationAddress = newImplementationAddress;
|
||||||
|
fs.writeFileSync(deploymentFile, JSON.stringify(deploymentData, null, 2));
|
||||||
|
console.log("Deployment data updated");
|
||||||
|
|
||||||
|
// Verify the new implementation
|
||||||
|
console.log("Waiting 10 seconds before verification...");
|
||||||
|
await new Promise(resolve => setTimeout(resolve, 10000));
|
||||||
|
|
||||||
|
try {
|
||||||
|
await hre.run("verify:verify", {
|
||||||
|
address: newImplementationAddress,
|
||||||
|
constructorArguments: []
|
||||||
|
});
|
||||||
|
console.log("Contract verified successfully.");
|
||||||
|
} catch (err) {
|
||||||
|
if (err.message.includes("already been verified")) {
|
||||||
|
console.log("Contract is already verified.");
|
||||||
|
} else {
|
||||||
|
console.log("Verification failed:", err.message);
|
||||||
|
console.log(`\nTo verify manually, run:`);
|
||||||
|
console.log(`npx hardhat verify --network ${network} ${newImplementationAddress}`);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
main()
|
||||||
|
.then(() => process.exit(0))
|
||||||
|
.catch((error) => {
|
||||||
|
console.error(error);
|
||||||
|
process.exit(1);
|
||||||
|
});
|
||||||
Reference in New Issue
Block a user