Add managed quote-push treasury workflows

This commit is contained in:
defiQUG
2026-04-13 21:37:33 -07:00
parent 2b52cc6e32
commit 7517869ea6
9 changed files with 429 additions and 39 deletions

View File

@@ -15,6 +15,7 @@ import {QuotePushTreasuryManager} from "../../contracts/flash/QuotePushTreasuryM
* QUOTE_PUSH_TREASURY_HARVEST optional; default 1
* QUOTE_PUSH_TREASURY_GAS_DISTRIBUTION_RAW optional; default 0
* QUOTE_PUSH_TREASURY_RECYCLE_DISTRIBUTION_RAW optional; default 0
* QUOTE_PUSH_TREASURY_TRANSFER_RECEIVER_OWNER_TO optional; when set, transfer receiver ownership
*/
contract ManageQuotePushTreasuryManager is Script {
function run() external {
@@ -23,6 +24,7 @@ contract ManageQuotePushTreasuryManager is Script {
bool harvest = vm.envOr("QUOTE_PUSH_TREASURY_HARVEST", uint256(1)) == 1;
uint256 gasAmount = vm.envOr("QUOTE_PUSH_TREASURY_GAS_DISTRIBUTION_RAW", uint256(0));
uint256 recycleAmount = vm.envOr("QUOTE_PUSH_TREASURY_RECYCLE_DISTRIBUTION_RAW", uint256(0));
address transferReceiverOwnerTo = vm.envOr("QUOTE_PUSH_TREASURY_TRANSFER_RECEIVER_OWNER_TO", address(0));
QuotePushTreasuryManager manager = QuotePushTreasuryManager(managerAddr);
@@ -30,6 +32,7 @@ contract ManageQuotePushTreasuryManager is Script {
console.log("harvest", harvest);
console.log("gasAmount", gasAmount);
console.log("recycleAmount", recycleAmount);
console.log("transferReceiverOwnerTo", transferReceiverOwnerTo);
console.log("quoteBalanceBefore", manager.quoteBalance());
console.log("availableBefore", manager.availableQuote());
console.log("receiverSweepableBefore", manager.receiverSweepableQuote());
@@ -42,6 +45,9 @@ contract ManageQuotePushTreasuryManager is Script {
if (gasAmount > 0 || recycleAmount > 0) {
manager.distributeToConfiguredRecipients(gasAmount, recycleAmount);
}
if (transferReceiverOwnerTo != address(0)) {
manager.transferManagedReceiverOwnership(transferReceiverOwnerTo);
}
vm.stopBroadcast();
console.log("quoteBalanceAfter", manager.quoteBalance());

View File

@@ -41,6 +41,10 @@ interface IDODOPMMPoolQuote {
* UNWIND_MODE=5 DODOToUniswapV3MultiHopExternalUnwinder:
* set UNWIND_DODO_POOL, UNWIND_INTERMEDIATE_TOKEN, UNWIND_MIN_INTERMEDIATE_OUT_RAW,
* UNWIND_V3_PATH_HEX (path starts at intermediate token and ends at tokenOut)
* UNWIND_MODE=6 TwoHopDodoToUniswapV3MultiHopExternalUnwinder:
* set UNWIND_TWO_HOP_POOL_A, UNWIND_TWO_HOP_POOL_B, UNWIND_TWO_HOP_MID_TOKEN,
* optional UNWIND_MIN_MID_OUT_RAW, then UNWIND_INTERMEDIATE_TOKEN,
* UNWIND_MIN_INTERMEDIATE_OUT_RAW, UNWIND_V3_PATH_HEX
*/
contract RunMainnetAaveCwusdcUsdcQuotePushOnce is Script {
address internal constant DEFAULT_POOL = 0x69776fc607e9edA8042e320e7e43f54d06c68f0E;
@@ -99,8 +103,18 @@ contract RunMainnetAaveCwusdcUsdcQuotePushOnce is Script {
string memory pathHex = vm.envString("UNWIND_V3_PATH_HEX");
bytes memory path = vm.parseBytes(pathHex);
unwindData = abi.encode(dodoPool, intermediateToken, minIntermediateOut, path);
} else if (unwindMode == 6) {
address poolA = vm.envAddress("UNWIND_TWO_HOP_POOL_A");
address poolB = vm.envAddress("UNWIND_TWO_HOP_POOL_B");
address midToken = vm.envAddress("UNWIND_TWO_HOP_MID_TOKEN");
uint256 minMidOut = vm.envOr("UNWIND_MIN_MID_OUT_RAW", uint256(1));
address intermediateToken = vm.envAddress("UNWIND_INTERMEDIATE_TOKEN");
uint256 minIntermediateOut = vm.envOr("UNWIND_MIN_INTERMEDIATE_OUT_RAW", uint256(1));
string memory pathHex = vm.envString("UNWIND_V3_PATH_HEX");
bytes memory path = vm.parseBytes(pathHex);
unwindData = abi.encode(poolA, poolB, midToken, minMidOut, intermediateToken, minIntermediateOut, path);
} else {
revert("UNWIND_MODE must be 0, 1, 2, 4, or 5");
revert("UNWIND_MODE must be 0, 1, 2, 4, 5, or 6");
}
AaveQuotePushFlashReceiver.QuotePushParams memory p = AaveQuotePushFlashReceiver.QuotePushParams({

View File

@@ -58,29 +58,13 @@ contract RunManagedMainnetAaveCwusdcUsdcQuotePushCycle is Script {
console.log("gasHoldbackTargetRaw", gasHoldbackTargetRaw);
vm.startBroadcast(pk);
AaveQuotePushFlashReceiver(receiver).flashQuotePush(usdc, amount, p);
uint256 harvested = 0;
if (harvest) {
uint256 receiverSweepableAfterFlash = manager.receiverSweepableQuote();
if (receiverSweepableAfterFlash > 0) {
harvested = manager.harvestReceiverSurplus();
}
console.log("receiverSweepableAfterFlash", receiverSweepableAfterFlash);
}
uint256 available = manager.availableQuote();
uint256 gasAmount = _min(available, gasHoldbackTargetRaw);
uint256 recycleAmount = available - gasAmount;
if (gasAmount > 0 || recycleAmount > 0) {
manager.distributeToConfiguredRecipients(gasAmount, recycleAmount);
}
(uint256 harvested, uint256 gasAmount, uint256 recycleAmount) =
manager.runManagedCycle(usdc, amount, p, harvest, gasHoldbackTargetRaw);
vm.stopBroadcast();
console.log("harvested", harvested);
console.log("gasDistributionRaw", gasAmount);
console.log("recycleDistributionRaw", recycleAmount);
console.log("managedCycleHarvestedRaw", harvested);
console.log("managedCycleGasDistributionRaw", gasAmount);
console.log("managedCycleRecycleDistributionRaw", recycleAmount);
console.log("managerQuoteAfter", manager.quoteBalance());
console.log("managerAvailableAfter", manager.availableQuote());
console.log("receiverSweepableAfter", manager.receiverSweepableQuote());
@@ -136,8 +120,18 @@ contract RunManagedMainnetAaveCwusdcUsdcQuotePushCycle is Script {
string memory pathHex = vm.envString("UNWIND_V3_PATH_HEX");
bytes memory path = vm.parseBytes(pathHex);
unwindData = abi.encode(dodoPool, intermediateToken, minIntermediateOut, path);
} else if (unwindMode == 6) {
address poolA = vm.envAddress("UNWIND_TWO_HOP_POOL_A");
address poolB = vm.envAddress("UNWIND_TWO_HOP_POOL_B");
address midToken = vm.envAddress("UNWIND_TWO_HOP_MID_TOKEN");
uint256 minMidOut = vm.envOr("UNWIND_MIN_MID_OUT_RAW", uint256(1));
address intermediateToken = vm.envAddress("UNWIND_INTERMEDIATE_TOKEN");
uint256 minIntermediateOut = vm.envOr("UNWIND_MIN_INTERMEDIATE_OUT_RAW", uint256(1));
string memory pathHex = vm.envString("UNWIND_V3_PATH_HEX");
bytes memory path = vm.parseBytes(pathHex);
unwindData = abi.encode(poolA, poolB, midToken, minMidOut, intermediateToken, minIntermediateOut, path);
} else {
revert("UNWIND_MODE must be 0, 1, 2, 4, or 5");
revert("UNWIND_MODE must be 0, 1, 2, 4, 5, or 6");
}
p = AaveQuotePushFlashReceiver.QuotePushParams({
@@ -166,8 +160,4 @@ contract RunManagedMainnetAaveCwusdcUsdcQuotePushCycle is Script {
console.log("minOutPmm", minOutPmm);
console.log("minOutUnwind", minOutUnwind);
}
function _min(uint256 a, uint256 b) internal pure returns (uint256) {
return a < b ? a : b;
}
}