diff --git a/contracts/adapters/OptimisticAuctionRebalanceExtensionV1.sol b/contracts/adapters/OptimisticAuctionRebalanceExtensionV1.sol index 0213c74a..9d3793b6 100644 --- a/contracts/adapters/OptimisticAuctionRebalanceExtensionV1.sol +++ b/contracts/adapters/OptimisticAuctionRebalanceExtensionV1.sol @@ -49,7 +49,7 @@ contract OptimisticAuctionRebalanceExtensionV1 is AuctionRebalanceExtension, As IERC20 indexed setToken, address indexed manager, OptimisticRebalanceParams optimisticParams, - bytes32 indexed rulesHash + string rules ); event RebalanceProposed( @@ -66,7 +66,7 @@ contract OptimisticAuctionRebalanceExtensionV1 is AuctionRebalanceExtension, As event AssertedClaim( IERC20 indexed setToken, address indexed _assertedBy, - bytes32 indexed rulesHash, + string rules, bytes32 _assertionId, bytes _claimData ); @@ -99,7 +99,7 @@ contract OptimisticAuctionRebalanceExtensionV1 is AuctionRebalanceExtension, As struct ProductSettings{ OptimisticRebalanceParams optimisticParams; // OptimisticRebalanceParams struct containing optimistic rebalance parameters. - bytes32 rulesHash; // IPFS hash of the rules for the product. + string rules; // Definition of rules for the product. (including ipfs hash pointing to full rules) } /* ============ State Variables ============ */ @@ -111,7 +111,7 @@ contract OptimisticAuctionRebalanceExtensionV1 is AuctionRebalanceExtension, As // Keys for assertion claim data. bytes public constant PROPOSAL_HASH_KEY = "proposalHash"; - bytes public constant RULES_KEY = "rulesIPFSHash"; + bytes public constant RULES_KEY = "rules"; /* ============ Constructor ============ */ @@ -178,21 +178,21 @@ contract OptimisticAuctionRebalanceExtensionV1 is AuctionRebalanceExtension, As /** * @dev OPERATOR ONLY: sets product settings for a given set token * @param _optimisticParams OptimisticRebalanceParams struct containing optimistic rebalance parameters. - * @param _rulesHash bytes32 containing the ipfs hash rules for the product. + * @param _rules string describing the rules of the rebalance (including IPFS hash pointing to full rules) */ function setProductSettings( OptimisticRebalanceParams memory _optimisticParams, - bytes32 _rulesHash + string memory _rules ) external onlyOperator { productSettings = ProductSettings({ optimisticParams: _optimisticParams, - rulesHash: _rulesHash + rules: _rules }); - emit ProductSettingsUpdated(setToken, setToken.manager(), _optimisticParams, _rulesHash); + emit ProductSettingsUpdated(setToken, setToken.manager(), _optimisticParams, _rules); } /** @@ -232,10 +232,10 @@ contract OptimisticAuctionRebalanceExtensionV1 is AuctionRebalanceExtension, As _positionMultiplier )); require(assertionIds[proposalHash] == bytes32(0), "Proposal already exists"); - require(productSettings.rulesHash != bytes32(""), "Rules not set"); + require(bytes(productSettings.rules).length > 0, "Rules not set"); require(address(productSettings.optimisticParams.optimisticOracleV3) != address(0), "Oracle not set"); - bytes memory claim = _constructClaim(proposalHash, productSettings.rulesHash); + bytes memory claim = _constructClaim(proposalHash, productSettings.rules); uint256 totalBond = _pullBond(productSettings.optimisticParams); bytes32 assertionId = productSettings.optimisticParams.optimisticOracleV3.assertTruth( @@ -254,7 +254,7 @@ contract OptimisticAuctionRebalanceExtensionV1 is AuctionRebalanceExtension, As assertionIdToProposalHash[assertionId] = proposalHash; emit RebalanceProposed( setToken, _quoteAsset, _oldComponents, _newComponents, _newComponentsAuctionParams, _oldComponentsAuctionParams, _rebalanceDuration, _positionMultiplier); - emit AssertedClaim(setToken, msg.sender, productSettings.rulesHash, assertionId, claim); + emit AssertedClaim(setToken, msg.sender, productSettings.rules, assertionId, claim); } /** @@ -369,14 +369,14 @@ contract OptimisticAuctionRebalanceExtensionV1 is AuctionRebalanceExtension, As // Constructs the claim that will be asserted at the Optimistic Oracle V3. // @dev Inspired by the equivalent function in the OptimisticGovernor: https://github.com/UMAprotocol/protocol/blob/96cf5be32a3f57ac761f004890dd3466c63e1fa5/packages/core/contracts/optimistic-governor/implementation/OptimisticGovernor.sol#L437 - function _constructClaim(bytes32 proposalHash, bytes32 rulesHash) internal pure returns (bytes memory) { + function _constructClaim(bytes32 proposalHash, string memory rules) internal pure returns (bytes memory) { return abi.encodePacked( AncillaryData.appendKeyValueBytes32("", PROPOSAL_HASH_KEY, proposalHash), ",", RULES_KEY, ":\"", - rulesHash, + rules, "\"" ); } diff --git a/test/adapters/optimisticAuctionRebalanceExtensionV1.spec.ts b/test/adapters/optimisticAuctionRebalanceExtensionV1.spec.ts index d2495cad..ed66125d 100644 --- a/test/adapters/optimisticAuctionRebalanceExtensionV1.spec.ts +++ b/test/adapters/optimisticAuctionRebalanceExtensionV1.spec.ts @@ -1,7 +1,6 @@ import "module-alias/register"; import { Address, Account } from "@utils/types"; -import { base58ToHexString } from "@utils/common"; import { ADDRESS_ZERO, ZERO } from "@utils/constants"; import { BaseManager, @@ -52,6 +51,8 @@ describe("OptimisticAuctionRebalanceExtensionV1", () => { let useAssetAllowlist: boolean; let allowedAssets: Address[]; + const ipfsHash = "Qmc5gCcjYypU7y28oCALwfSvxCBskLuPKWpK4qpterKC7z"; + before(async () => { [owner, methodologist, operator] = await getAccounts(); @@ -305,12 +306,10 @@ describe("OptimisticAuctionRebalanceExtensionV1", () => { }); context("when the product settings have been set", () => { - let rulesHash: Uint8Array; + let rules: string; let bondAmount: BigNumber; beforeEach(async () => { - rulesHash = utils.arrayify( - base58ToHexString("Qmc5gCcjYypU7y28oCALwfSvxCBskLuPKWpK4qpterKC7z"), - ); + rules = ipfsHash; bondAmount = ether(140); // 140 INDEX minimum bond await auctionRebalanceExtension.connect(operator.wallet).setProductSettings( { @@ -320,7 +319,7 @@ describe("OptimisticAuctionRebalanceExtensionV1", () => { identifier: utils.formatBytes32String(""), optimisticOracleV3: optimisticOracleV3Mock.address, }, - rulesHash, + rules, ); }); @@ -442,12 +441,7 @@ describe("OptimisticAuctionRebalanceExtensionV1", () => { ], ), ); - const firstPart = utils.toUtf8Bytes( - "proposalHash:" + proposalHash.slice(2) + ',rulesIPFSHash:"', - ); - const lastPart = utils.toUtf8Bytes('"'); - - return utils.hexlify(utils.concat([firstPart, rulesHash, lastPart])); + return `proposalHash:${proposalHash.slice(2)},rules:"${rules}"`; } context("when the extension is open for rebalance", () => { @@ -528,10 +522,10 @@ describe("OptimisticAuctionRebalanceExtensionV1", () => { expect(emittedSetToken).to.eq(setToken.address); const assertedBy = assertEvent.args._assertedBy; expect(assertedBy).to.eq(operator.wallet.address); - const emittedRulesHash = assertEvent.args.rulesHash; - expect(emittedRulesHash).to.eq(utils.hexlify(rulesHash)); + const emittedRules = assertEvent.args.rules; + expect(emittedRules).to.eq(rules); const claim = assertEvent.args._claimData; - expect(claim).to.eq(constructClaim()); + expect(utils.toUtf8String(claim)).to.eq(constructClaim()); }); context("when the same rebalance has been proposed already", () => { @@ -570,7 +564,7 @@ describe("OptimisticAuctionRebalanceExtensionV1", () => { const currentSettings = await auctionRebalanceExtension.productSettings(); await auctionRebalanceExtension.setProductSettings( currentSettings.optimisticParams, - constants.HashZero, + "", ); }); @@ -891,9 +885,7 @@ describe("OptimisticAuctionRebalanceExtensionV1", () => { identifier: utils.formatBytes32String(""), optimisticOracleV3: optimisticOracleV3MockUpgraded.address, }, - utils.arrayify( - base58ToHexString("Qmc5gCcjYypU7y28oCALwfSvxCBskLuPKWpK4qpterKC7z"), - ), + ipfsHash, ); const proposalHash = await auctionRebalanceExtension diff --git a/test/integration/ethereum/optimisticAuctionRebalanceExtenisonV1.spec.ts b/test/integration/ethereum/optimisticAuctionRebalanceExtenisonV1.spec.ts index 156ae3b4..53b2e2ae 100644 --- a/test/integration/ethereum/optimisticAuctionRebalanceExtenisonV1.spec.ts +++ b/test/integration/ethereum/optimisticAuctionRebalanceExtenisonV1.spec.ts @@ -3,7 +3,6 @@ import "module-alias/register"; import { Address, Account } from "@utils/types"; import { increaseTimeAsync } from "@utils/test"; import { setBlockNumber } from "@utils/test/testingUtils"; -import { base58ToHexString } from "@utils/common"; import { ONE_HOUR_IN_SECONDS, ZERO } from "@utils/constants"; import { OptimisticAuctionRebalanceExtensionV1 } from "@utils/contracts/index"; import { @@ -45,6 +44,7 @@ if (process.env.INTEGRATIONTEST) { describe("OptimisticAuctionRebalanceExtensionV1 - Integration Test dsEth", () => { const contractAddresses = PRODUCTION_ADDRESSES; + const rules = "Rules stored on ipfs under hash: Qmc5gCcjYypU7y28oCALwfSvxCBskLuPKWpK4qpterKC7z"; const liveness = BigNumber.from(60 * 60 * 24 * 2); // 2 days const minimumBond = ether(140); // 140 INDEX Minimum Bond @@ -154,7 +154,7 @@ if (process.env.INTEGRATIONTEST) { let identifier: string; beforeEach(async () => { - identifier = "0x4153534552545f54525554480000000000000000000000000000000000000000"; // ASSERT_TRUTH identifier + identifier = "0x4153534552545f54525554480000000000000000000000000000000000000000"; // ASSERT_TTH identifier productSettings = { collateral: collateralAssetAddress, @@ -166,10 +166,7 @@ if (process.env.INTEGRATIONTEST) { await auctionRebalanceExtension .connect(operator) - .setProductSettings( - productSettings, - utils.arrayify(base58ToHexString("Qmc5gCcjYypU7y28oCALwfSvxCBskLuPKWpK4qpterKC7z")), - ); + .setProductSettings(productSettings, rules); }); context("when the extension is open to rebalances", () => { @@ -198,9 +195,13 @@ if (process.env.INTEGRATIONTEST) { subjectOldComponents = await dsEth.getComponents(); - subjectNewComponents = [contractAddresses.tokens.swETH, contractAddresses.tokens.ETHx]; + subjectNewComponents = [ + contractAddresses.tokens.swETH, + contractAddresses.tokens.ETHx, + ]; subjectNewComponentsAuctionParams = [ - { // swETH: https://etherscan.io/address/0xf951E335afb289353dc249e82926178EaC7DEd78#readProxyContract#F6 + { + // swETH: https://etherscan.io/address/0xf951E335afb289353dc249e82926178EaC7DEd78#readProxyContract#F6 targetUnit: "155716754710815260", priceAdapterName: "BoundedStepwiseLinearPriceAdapter", priceAdapterConfigData: await priceAdapter.getEncodedData( @@ -212,7 +213,8 @@ if (process.env.INTEGRATIONTEST) { ether(1.043), ), }, - { // ETHx: https://etherscan.io/address/0xcf5ea1b38380f6af39068375516daf40ed70d299#readProxyContract#F5 + { + // ETHx: https://etherscan.io/address/0xcf5ea1b38380f6af39068375516daf40ed70d299#readProxyContract#F5 targetUnit: "162815732702576500", priceAdapterName: "BoundedStepwiseLinearPriceAdapter", priceAdapterConfigData: await priceAdapter.getEncodedData( @@ -287,17 +289,17 @@ if (process.env.INTEGRATIONTEST) { .add(effectiveBond) .toHexString(); - // set operator balance to effective bond + // set operator balance to effective bond await ethers.provider.send("hardhat_setBalance", [ await subjectCaller.getAddress(), quantity, ]); await getIndexTokens(await subjectCaller.getAddress(), effectiveBond); - await indexToken - .connect(subjectCaller) - .approve(auctionRebalanceExtension.address, effectiveBond); - }); + await indexToken + .connect(subjectCaller) + .approve(auctionRebalanceExtension.address, effectiveBond); + }); describe("#startRebalance", () => { async function subject(): Promise { @@ -450,7 +452,9 @@ if (process.env.INTEGRATIONTEST) { expect(proposalHash).to.not.eq(ethers.constants.HashZero); await getIndexTokens(await subjectCaller.getAddress(), effectiveBond); - await indexToken.connect(subjectCaller).approve(optimisticOracleV3.address, effectiveBond); + await indexToken + .connect(subjectCaller) + .approve(optimisticOracleV3.address, effectiveBond); await optimisticOracleV3 .connect(subjectCaller) .disputeAssertion(proposalId, owner.address); @@ -471,9 +475,7 @@ if (process.env.INTEGRATIONTEST) { identifier, optimisticOracleV3: optimisticOracleV3Mock.address, }, - utils.arrayify( - base58ToHexString("Qmc5gCcjYypU7y28oCALwfSvxCBskLuPKWpK4qpterKC7z"), - ), + rules, ); const proposalHash = await auctionRebalanceExtension @@ -506,9 +508,7 @@ if (process.env.INTEGRATIONTEST) { identifier, optimisticOracleV3: optimisticOracleV3Mock.address, }, - utils.arrayify( - base58ToHexString("Qmc5gCcjYypU7y28oCALwfSvxCBskLuPKWpK4qpterKC7z"), - ), + rules, ); const tx = await auctionRebalanceExtension .connect(subjectCaller)