From 515c6292bf57a0a8433ba1edd30f33230ea1410c Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 27 Feb 2023 14:19:04 +0000 Subject: [PATCH 01/41] add assert ABi --- src/contracts/abis/Assert.json | 1 + 1 file changed, 1 insertion(+) create mode 100644 src/contracts/abis/Assert.json diff --git a/src/contracts/abis/Assert.json b/src/contracts/abis/Assert.json new file mode 100644 index 000000000..7133b1fe1 --- /dev/null +++ b/src/contracts/abis/Assert.json @@ -0,0 +1 @@ +[{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"address","name":"expectedTarget","type":"address"},{"internalType":"bytes","name":"expectedCalldata","type":"bytes"}],"name":"assertEq","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes","name":"actual","type":"bytes"},{"internalType":"bytes","name":"expected","type":"bytes"}],"name":"assertEq","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"uint256","name":"actual","type":"uint256"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertEq","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertEq","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bool","name":"actual","type":"bool"},{"internalType":"bool","name":"expected","type":"bool"}],"name":"assertEq","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"address","name":"expectedTarget","type":"address"},{"internalType":"bytes","name":"expectedCalldata","type":"bytes"},{"internalType":"uint256","name":"abs","type":"uint256"}],"name":"assertEqAbs","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"uint256","name":"expected","type":"uint256"},{"internalType":"uint256","name":"abs","type":"uint256"}],"name":"assertEqAbs","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"actual","type":"uint256"},{"internalType":"uint256","name":"expected","type":"uint256"},{"internalType":"uint256","name":"abs","type":"uint256"}],"name":"assertEqAbs","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"uint256","name":"expected","type":"uint256"},{"internalType":"uint256","name":"rel","type":"uint256"}],"name":"assertEqRel","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"actual","type":"uint256"},{"internalType":"uint256","name":"expected","type":"uint256"},{"internalType":"uint256","name":"rel","type":"uint256"}],"name":"assertEqRel","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"address","name":"expectedTarget","type":"address"},{"internalType":"bytes","name":"expectedCalldata","type":"bytes"},{"internalType":"uint256","name":"rel","type":"uint256"}],"name":"assertEqRel","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"address","name":"expectedTarget","type":"address"},{"internalType":"bytes","name":"expectedCalldata","type":"bytes"}],"name":"assertGe","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"actual","type":"uint256"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertGe","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertGe","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"address","name":"expectedTarget","type":"address"},{"internalType":"bytes","name":"expectedCalldata","type":"bytes"}],"name":"assertGt","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertGt","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"actual","type":"uint256"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertGt","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertLe","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"actual","type":"uint256"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertLe","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"address","name":"expectedTarget","type":"address"},{"internalType":"bytes","name":"expectedCalldata","type":"bytes"}],"name":"assertLe","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertLt","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"actual","type":"uint256"},{"internalType":"uint256","name":"expected","type":"uint256"}],"name":"assertLt","outputs":[],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"actualTarget","type":"address"},{"internalType":"bytes","name":"actualCalldata","type":"bytes"},{"internalType":"address","name":"expectedTarget","type":"address"},{"internalType":"bytes","name":"expectedCalldata","type":"bytes"}],"name":"assertLt","outputs":[],"stateMutability":"nonpayable","type":"function"}] \ No newline at end of file From 2df3f8eeeb8a216c1732e15eca74b048eb52d2dc Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 27 Feb 2023 14:19:19 +0000 Subject: [PATCH 02/41] build assert contract --- src/contracts/Assert.d.ts | 956 +++++++++++++++++++++ src/contracts/factories/Assert__factory.ts | 569 ++++++++++++ src/contracts/index.ts | 2 + 3 files changed, 1527 insertions(+) create mode 100644 src/contracts/Assert.d.ts create mode 100644 src/contracts/factories/Assert__factory.ts diff --git a/src/contracts/Assert.d.ts b/src/contracts/Assert.d.ts new file mode 100644 index 000000000..71a77d919 --- /dev/null +++ b/src/contracts/Assert.d.ts @@ -0,0 +1,956 @@ +/* Autogenerated file. Do not edit manually. */ +/* tslint:disable */ +/* eslint-disable */ + +import { + ethers, + EventFilter, + Signer, + BigNumber, + BigNumberish, + PopulatedTransaction, + BaseContract, + ContractTransaction, + Overrides, + CallOverrides, +} from "ethers"; +import { BytesLike } from "@ethersproject/bytes"; +import { Listener, Provider } from "@ethersproject/providers"; +import { FunctionFragment, EventFragment, Result } from "@ethersproject/abi"; +import type { TypedEventFilter, TypedEvent, TypedListener } from "./common"; + +interface AssertInterface extends ethers.utils.Interface { + functions: { + "assertEq(address,bytes,address,bytes)": FunctionFragment; + "assertEqAbs(address,bytes,address,bytes,uint256)": FunctionFragment; + "assertEqRel(address,bytes,uint256,uint256)": FunctionFragment; + "assertGe(address,bytes,address,bytes)": FunctionFragment; + "assertGt(address,bytes,address,bytes)": FunctionFragment; + "assertLe(address,bytes,uint256)": FunctionFragment; + "assertLt(address,bytes,uint256)": FunctionFragment; + }; + + encodeFunctionData( + functionFragment: "assertEq", + values: [string, BytesLike, string, BytesLike] + ): string; + encodeFunctionData( + functionFragment: "assertEqAbs", + values: [string, BytesLike, string, BytesLike, BigNumberish] + ): string; + encodeFunctionData( + functionFragment: "assertEqRel", + values: [string, BytesLike, BigNumberish, BigNumberish] + ): string; + encodeFunctionData( + functionFragment: "assertGe", + values: [string, BytesLike, string, BytesLike] + ): string; + encodeFunctionData( + functionFragment: "assertGt", + values: [string, BytesLike, string, BytesLike] + ): string; + encodeFunctionData( + functionFragment: "assertLe", + values: [string, BytesLike, BigNumberish] + ): string; + encodeFunctionData( + functionFragment: "assertLt", + values: [string, BytesLike, BigNumberish] + ): string; + + decodeFunctionResult(functionFragment: "assertEq", data: BytesLike): Result; + decodeFunctionResult( + functionFragment: "assertEqAbs", + data: BytesLike + ): Result; + decodeFunctionResult( + functionFragment: "assertEqRel", + data: BytesLike + ): Result; + decodeFunctionResult(functionFragment: "assertGe", data: BytesLike): Result; + decodeFunctionResult(functionFragment: "assertGt", data: BytesLike): Result; + decodeFunctionResult(functionFragment: "assertLe", data: BytesLike): Result; + decodeFunctionResult(functionFragment: "assertLt", data: BytesLike): Result; + + events: {}; +} + +export class Assert extends BaseContract { + connect(signerOrProvider: Signer | Provider | string): this; + attach(addressOrName: string): this; + deployed(): Promise; + + listeners, EventArgsObject>( + eventFilter?: TypedEventFilter + ): Array>; + off, EventArgsObject>( + eventFilter: TypedEventFilter, + listener: TypedListener + ): this; + on, EventArgsObject>( + eventFilter: TypedEventFilter, + listener: TypedListener + ): this; + once, EventArgsObject>( + eventFilter: TypedEventFilter, + listener: TypedListener + ): this; + removeListener, EventArgsObject>( + eventFilter: TypedEventFilter, + listener: TypedListener + ): this; + removeAllListeners, EventArgsObject>( + eventFilter: TypedEventFilter + ): this; + + listeners(eventName?: string): Array; + off(eventName: string, listener: Listener): this; + on(eventName: string, listener: Listener): this; + once(eventName: string, listener: Listener): this; + removeListener(eventName: string, listener: Listener): this; + removeAllListeners(eventName?: string): this; + + queryFilter, EventArgsObject>( + event: TypedEventFilter, + fromBlockOrBlockhash?: string | number | undefined, + toBlock?: string | number | undefined + ): Promise>>; + + interface: AssertInterface; + + functions: { + "assertEq(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEq(bytes,bytes)"( + actual: BytesLike, + expected: BytesLike, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertEq(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertEq(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEq(bool,bool)"( + actual: boolean, + expected: boolean, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertEqAbs(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + abs: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqAbs(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + abs: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqAbs(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + abs: BigNumberish, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertEqRel(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + rel: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqRel(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + rel: BigNumberish, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertEqRel(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + rel: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertGe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertLe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertLe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise<[void]>; + + "assertLt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + }; + + "assertEq(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEq(bytes,bytes)"( + actual: BytesLike, + expected: BytesLike, + overrides?: CallOverrides + ): Promise; + + "assertEq(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEq(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEq(bool,bool)"( + actual: boolean, + expected: boolean, + overrides?: CallOverrides + ): Promise; + + "assertEqAbs(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + abs: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqAbs(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + abs: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqAbs(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + abs: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + rel: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqRel(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + rel: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + rel: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertGe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + callStatic: { + "assertEq(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: CallOverrides + ): Promise; + + "assertEq(bytes,bytes)"( + actual: BytesLike, + expected: BytesLike, + overrides?: CallOverrides + ): Promise; + + "assertEq(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEq(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEq(bool,bool)"( + actual: boolean, + expected: boolean, + overrides?: CallOverrides + ): Promise; + + "assertEqAbs(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + abs: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqAbs(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + abs: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqAbs(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + abs: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + rel: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + rel: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + rel: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertGe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: CallOverrides + ): Promise; + + "assertGe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertGe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertGt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: CallOverrides + ): Promise; + + "assertGt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertGt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: CallOverrides + ): Promise; + + "assertLt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: CallOverrides + ): Promise; + }; + + filters: {}; + + estimateGas: { + "assertEq(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEq(bytes,bytes)"( + actual: BytesLike, + expected: BytesLike, + overrides?: CallOverrides + ): Promise; + + "assertEq(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEq(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEq(bool,bool)"( + actual: boolean, + expected: boolean, + overrides?: CallOverrides + ): Promise; + + "assertEqAbs(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + abs: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqAbs(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + abs: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqAbs(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + abs: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + rel: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqRel(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + rel: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + rel: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertGe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + }; + + populateTransaction: { + "assertEq(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEq(bytes,bytes)"( + actual: BytesLike, + expected: BytesLike, + overrides?: CallOverrides + ): Promise; + + "assertEq(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEq(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEq(bool,bool)"( + actual: boolean, + expected: boolean, + overrides?: CallOverrides + ): Promise; + + "assertEqAbs(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + abs: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqAbs(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + abs: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqAbs(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + abs: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(address,bytes,uint256,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + rel: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertEqRel(uint256,uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + rel: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertEqRel(address,bytes,address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + rel: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertGe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertGt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLe(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLe(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLt(address,bytes,uint256)"( + actualTarget: string, + actualCalldata: BytesLike, + expected: BigNumberish, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + + "assertLt(uint256,uint256)"( + actual: BigNumberish, + expected: BigNumberish, + overrides?: CallOverrides + ): Promise; + + "assertLt(address,bytes,address,bytes)"( + actualTarget: string, + actualCalldata: BytesLike, + expectedTarget: string, + expectedCalldata: BytesLike, + overrides?: Overrides & { from?: string | Promise } + ): Promise; + }; +} diff --git a/src/contracts/factories/Assert__factory.ts b/src/contracts/factories/Assert__factory.ts new file mode 100644 index 000000000..3b122e070 --- /dev/null +++ b/src/contracts/factories/Assert__factory.ts @@ -0,0 +1,569 @@ +/* Autogenerated file. Do not edit manually. */ +/* tslint:disable */ +/* eslint-disable */ + +import { Contract, Signer, utils } from "ethers"; +import { Provider } from "@ethersproject/providers"; +import type { Assert, AssertInterface } from "../Assert"; + +const _abi = [ + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "address", + name: "expectedTarget", + type: "address", + }, + { + internalType: "bytes", + name: "expectedCalldata", + type: "bytes", + }, + ], + name: "assertEq", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "bytes", + name: "actual", + type: "bytes", + }, + { + internalType: "bytes", + name: "expected", + type: "bytes", + }, + ], + name: "assertEq", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "uint256", + name: "actual", + type: "uint256", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertEq", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertEq", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "bool", + name: "actual", + type: "bool", + }, + { + internalType: "bool", + name: "expected", + type: "bool", + }, + ], + name: "assertEq", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "address", + name: "expectedTarget", + type: "address", + }, + { + internalType: "bytes", + name: "expectedCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "abs", + type: "uint256", + }, + ], + name: "assertEqAbs", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + { + internalType: "uint256", + name: "abs", + type: "uint256", + }, + ], + name: "assertEqAbs", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "uint256", + name: "actual", + type: "uint256", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + { + internalType: "uint256", + name: "abs", + type: "uint256", + }, + ], + name: "assertEqAbs", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + { + internalType: "uint256", + name: "rel", + type: "uint256", + }, + ], + name: "assertEqRel", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "uint256", + name: "actual", + type: "uint256", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + { + internalType: "uint256", + name: "rel", + type: "uint256", + }, + ], + name: "assertEqRel", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "address", + name: "expectedTarget", + type: "address", + }, + { + internalType: "bytes", + name: "expectedCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "rel", + type: "uint256", + }, + ], + name: "assertEqRel", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "address", + name: "expectedTarget", + type: "address", + }, + { + internalType: "bytes", + name: "expectedCalldata", + type: "bytes", + }, + ], + name: "assertGe", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "uint256", + name: "actual", + type: "uint256", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertGe", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertGe", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "address", + name: "expectedTarget", + type: "address", + }, + { + internalType: "bytes", + name: "expectedCalldata", + type: "bytes", + }, + ], + name: "assertGt", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertGt", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "uint256", + name: "actual", + type: "uint256", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertGt", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertLe", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "uint256", + name: "actual", + type: "uint256", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertLe", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "address", + name: "expectedTarget", + type: "address", + }, + { + internalType: "bytes", + name: "expectedCalldata", + type: "bytes", + }, + ], + name: "assertLe", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertLt", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, + { + inputs: [ + { + internalType: "uint256", + name: "actual", + type: "uint256", + }, + { + internalType: "uint256", + name: "expected", + type: "uint256", + }, + ], + name: "assertLt", + outputs: [], + stateMutability: "pure", + type: "function", + }, + { + inputs: [ + { + internalType: "address", + name: "actualTarget", + type: "address", + }, + { + internalType: "bytes", + name: "actualCalldata", + type: "bytes", + }, + { + internalType: "address", + name: "expectedTarget", + type: "address", + }, + { + internalType: "bytes", + name: "expectedCalldata", + type: "bytes", + }, + ], + name: "assertLt", + outputs: [], + stateMutability: "nonpayable", + type: "function", + }, +]; + +export class Assert__factory { + static readonly abi = _abi; + static createInterface(): AssertInterface { + return new utils.Interface(_abi) as AssertInterface; + } + static connect(address: string, signerOrProvider: Signer | Provider): Assert { + return new Contract(address, _abi, signerOrProvider) as Assert; + } +} diff --git a/src/contracts/index.ts b/src/contracts/index.ts index eb26a04ae..49a457801 100644 --- a/src/contracts/index.ts +++ b/src/contracts/index.ts @@ -2,6 +2,7 @@ /* tslint:disable */ /* eslint-disable */ export type { AccumulatorOracle } from "./AccumulatorOracle"; +export type { Assert } from "./Assert"; export type { Cauldron } from "./Cauldron"; export type { ChainlinkMultiOracle } from "./ChainlinkMultiOracle"; export type { ChainlinkUSDOracle } from "./ChainlinkUSDOracle"; @@ -28,6 +29,7 @@ export type { WrapEtherModule } from "./WrapEtherModule"; export type { YearnVaultMultiOracle } from "./YearnVaultMultiOracle"; export { AccumulatorOracle__factory } from "./factories/AccumulatorOracle__factory"; +export { Assert__factory } from "./factories/Assert__factory"; export { Cauldron__factory } from "./factories/Cauldron__factory"; export { ChainlinkMultiOracle__factory } from "./factories/ChainlinkMultiOracle__factory"; export { ChainlinkUSDOracle__factory } from "./factories/ChainlinkUSDOracle__factory"; From 242d8daea133955d9f99102865cc059700618ead Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 27 Feb 2023 14:19:36 +0000 Subject: [PATCH 03/41] add in useAssert hook --- src/hooks/actionHooks/useAssert.ts | 29 +++++++++++++++++++++++++++++ src/types/operations.ts | 3 +++ 2 files changed, 32 insertions(+) create mode 100644 src/hooks/actionHooks/useAssert.ts diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts new file mode 100644 index 000000000..064dd2570 --- /dev/null +++ b/src/hooks/actionHooks/useAssert.ts @@ -0,0 +1,29 @@ +import { BigNumber } from 'ethers'; +import { useAccount } from 'wagmi'; +import { ICallData, LadleActions } from '../../types'; +import { RoutedActions } from '../../types/operations'; +import { ZERO_BN } from '../../utils/constants'; +import useContracts, { ContractNames } from '../useContracts'; + +export const useAssert = () => { + const contracts = useContracts(); + const AssertContract = contracts.get(ContractNames.ASSERT); + + const assert = ( + + ): ICallData[] => + /* if there is a destination 'to' then use the ladle module (wrapEtherModule) */ + [ + { + operation: LadleActions.Fn.ROUTE, + args: [ + + + ] as RoutedActions.Args.ASSERT, + fnName: RoutedActions.Fn.ASSERT, + targetContract: AssertContract, + ignoreIf: false, + }, + ] + return { assert }; +}; \ No newline at end of file diff --git a/src/types/operations.ts b/src/types/operations.ts index fbaa89137..8a71145b4 100644 --- a/src/types/operations.ts +++ b/src/types/operations.ts @@ -95,6 +95,7 @@ export namespace RoutedActions { UNWRAP = 'unwrap', CHECKPOINT = 'checkpoint', // convex + ASSERT= 'assert' } export namespace Args { @@ -119,6 +120,8 @@ export namespace RoutedActions { export type UNWRAP = [receiver: string]; export type CHECKPOINT = [vaultOwner: string]; + + export type ASSERT = []; } } From 1d0bd8c1e20f97edc979aa57a6d74f1aa3c5dd89 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 27 Feb 2023 14:19:53 +0000 Subject: [PATCH 04/41] add assert contract adderss --- src/hooks/useContracts.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/src/hooks/useContracts.ts b/src/hooks/useContracts.ts index 8437702fb..8acc079ae 100644 --- a/src/hooks/useContracts.ts +++ b/src/hooks/useContracts.ts @@ -12,6 +12,7 @@ export enum ContractNames { LADLE = 'Ladle', WRAP_ETHER_MODULE = 'WrapEtherModule', CONVEX_LADLE_MODULE = 'ConvexLadleModule', + ASSERT = 'Assert' } const useContracts = () => { From 0974d297fc72b26829b94692666ec3cd5e7c6c00 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 27 Feb 2023 14:20:06 +0000 Subject: [PATCH 05/41] assert RPC tenderly --- .env.local | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/.env.local b/.env.local index 6ddb6f89b..44aea6ec4 100644 --- a/.env.local +++ b/.env.local @@ -4,10 +4,12 @@ REACT_APP_VERSION=$npm_package_version REACT_APP_RPC_URL_1='https://eth-mainnet.g.alchemy.com/v2/ZXDCq5iy0KrKR0XjsqC6E4QG7Z_FuXDv' REACT_APP_RPC_URL_42161='https://arb-mainnet.g.alchemy.com/v2/vtMM4_eLnOvkjkdckprVw3cIa64EVkDZ' -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/c6e7288b-fcc8-4ffd-a894-d0c933848df4' +REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/f24b59a8-db83-4d2c-a244-77b665a2b6ce' REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' + REACT_APP_RPC_URL_421611='https://arb-rinkeby.g.alchemy.com/v2/AY_Q_Uy-Kcfwmf5In5qwG636vaOIoA8L' -TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/d738b4fb-285e-480b-ac52-c05eb95386d5' + +TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/f24b59a8-db83-4d2c-a244-77b665a2b6ce' LOCALHOST_RPC_URL='http://127.0.0.1:8545' TENDERLY_USER='mmyield' From cb4590230b5f558e28240055de9193a84cd08e55 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 28 Feb 2023 10:12:42 +0000 Subject: [PATCH 06/41] feat/useAssert --- src/hooks/actionHooks/useAssert.ts | 91 +++++++++++++++++++++++++----- src/hooks/actionHooks/useBorrow.ts | 17 +++++- src/types/operations.ts | 5 +- 3 files changed, 95 insertions(+), 18 deletions(-) diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index 064dd2570..be12539de 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -1,29 +1,90 @@ -import { BigNumber } from 'ethers'; -import { useAccount } from 'wagmi'; -import { ICallData, LadleActions } from '../../types'; +import { BigNumber, BigNumberish, Contract, ethers } from 'ethers'; +import { erc20ABI, useAccount } from 'wagmi'; +import { IAsset, ICallData, LadleActions } from '../../types'; import { RoutedActions } from '../../types/operations'; import { ZERO_BN } from '../../utils/constants'; import useContracts, { ContractNames } from '../useContracts'; +export namespace AssertActions { + export enum Fn { + ASSERT_GT = 'assertGt', + ASSERT_LT = 'assertLt', + ASSERT_EQ_REL = 'assertEqRel', + ASSERT_EQ_ABS = 'assertEqAbs', + ASSERT_GE = 'assertGe', + ASSERT_LE = 'assertLe', + } + export namespace Args { + export type ASSERT_GT = [actualTarget: string, bytes: any, expected: BigNumberish]; + export type ASSERT_LT = [actualTarget: string, bytes: any, expected: BigNumberish]; + export type ASSERT_EQ_REL = [actualTarget: string, bytes: any, expected: BigNumberish, relative: BigNumberish]; + export type ASSERT_EQ_ABS = [actualTarget: string, bytes: any, expected: BigNumberish]; + export type ASSERT_GE = [actualTarget: string, bytes: any, expected: BigNumberish]; + export type ASSERT_LE = [actualTarget: string, bytes: any, expected: BigNumberish]; + } +} + export const useAssert = () => { const contracts = useContracts(); const AssertContract = contracts.get(ContractNames.ASSERT); + const { address: account } = useAccount(); - const assert = ( + const encodeBalanceCall = (address: string, tokenIdentifier: string | number | undefined = undefined) => { - ): ICallData[] => - /* if there is a destination 'to' then use the ladle module (wrapEtherModule) */ - [ + const mock = '0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE'; + if (address) { + const abi = tokenIdentifier ? erc1155ABI : erc20ABI; + const args = tokenIdentifier ? [account, tokenIdentifier] : [account]; + const assetContract = new Contract(address, abi); + return assetContract.interface.encodeFunctionData('balanceOf', args); + } + return '0x'; + }; + + const assert = ( + address: string, + encodedCallBytes: any, + assertFn: AssertActions.Fn, + expectedVal: BigNumber + ): ICallData[] => { + return [ { operation: LadleActions.Fn.ROUTE, - args: [ - - - ] as RoutedActions.Args.ASSERT, - fnName: RoutedActions.Fn.ASSERT, + args: [address, encodedCallBytes, expectedVal] as AssertActions.Args.ASSERT_GT, + fnName: assertFn, targetContract: AssertContract, ignoreIf: false, }, - ] - return { assert }; -}; \ No newline at end of file + ]; + }; + + /* if there is a destination 'to' then use the ladle module (wrapEtherModule) */ + return { assert, encodeBalanceCall }; +}; + +const erc1155ABI = [ + { + inputs: [ + { + internalType: 'address', + name: 'account', + type: 'address', + }, + { + internalType: 'uint256', + name: 'id', + type: 'uint256', + }, + ], + name: 'balanceOf', + outputs: [ + { + internalType: 'uint256', + name: '', + type: 'uint256', + }, + ], + stateMutability: 'view', + type: 'function', + }, +]; diff --git a/src/hooks/actionHooks/useBorrow.ts b/src/hooks/actionHooks/useBorrow.ts index cf49eb043..ef0a44f1c 100644 --- a/src/hooks/actionHooks/useBorrow.ts +++ b/src/hooks/actionHooks/useBorrow.ts @@ -13,7 +13,9 @@ import { CONVEX_BASED_ASSETS, ETH_BASED_ASSETS, WETH } from '../../config/assets import { useChain } from '../useChain'; import { useWrapUnwrapAsset } from './useWrapUnwrapAsset'; import { useAddRemoveEth } from './useAddRemoveEth'; -import { ModuleActions } from '../../types/operations'; +import { AssertActions, useAssert } from './useAssert'; + +import { ModuleActions, RoutedActions } from '../../types/operations'; import { ConvexLadleModule } from '../../contracts'; import useTimeTillMaturity from '../useTimeTillMaturity'; import { Address, useAccount, useBalance } from 'wagmi'; @@ -45,6 +47,8 @@ export const useBorrow = () => { const { sign, transact } = useChain(); const { getTimeTillMaturity } = useTimeTillMaturity(); + const { assert, encodeBalanceCall } = useAssert(); + const borrow = async (vault: IVault | undefined, input: string | undefined, collInput: string | undefined) => { /* generate the reproducible txCode for tx tracking and tracing */ const txCode = getTxCode(ActionCodes.BORROW, selectedSeries?.id!); @@ -117,6 +121,14 @@ export const useBorrow = () => { txCode ); + /* Add in an Assert call */ + const assertCallData: ICallData[] = assert( + base.address, + encodeBalanceCall(base.address, base.tokenIdentifier), + AssertActions.Fn.ASSERT_GE, + base.balance.add(_input) + ); + /* if ETH is being borrowed, send the borrowed tokens (WETH) to ladle for unwrapping */ const serveToAddress = () => { if (isEthBase) return ladleAddress; @@ -160,7 +172,10 @@ export const useBorrow = () => { args: [vaultId, serveToAddress(), _collInput, _input, _expectedFyTokenWithSlippage] as LadleActions.Args.SERVE, ignoreIf: false, }, + ...removeEthCallData, + + ...assertCallData, ]; /* finally, handle the transaction */ diff --git a/src/types/operations.ts b/src/types/operations.ts index 8a71145b4..64bf70a65 100644 --- a/src/types/operations.ts +++ b/src/types/operations.ts @@ -95,7 +95,8 @@ export namespace RoutedActions { UNWRAP = 'unwrap', CHECKPOINT = 'checkpoint', // convex - ASSERT= 'assert' + + // ASSERT = 'assert', } export namespace Args { @@ -121,7 +122,7 @@ export namespace RoutedActions { export type CHECKPOINT = [vaultOwner: string]; - export type ASSERT = []; + // export type ASSERT = []; } } From 1838a3bd072c5275f3c3c1bd183ded679c563288 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 28 Feb 2023 10:38:14 +0000 Subject: [PATCH 07/41] fork --- .env.local | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.env.local b/.env.local index 44aea6ec4..f199c0bbd 100644 --- a/.env.local +++ b/.env.local @@ -4,12 +4,12 @@ REACT_APP_VERSION=$npm_package_version REACT_APP_RPC_URL_1='https://eth-mainnet.g.alchemy.com/v2/ZXDCq5iy0KrKR0XjsqC6E4QG7Z_FuXDv' REACT_APP_RPC_URL_42161='https://arb-mainnet.g.alchemy.com/v2/vtMM4_eLnOvkjkdckprVw3cIa64EVkDZ' -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/f24b59a8-db83-4d2c-a244-77b665a2b6ce' +REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/419b6a25-238a-41b4-bb8a-d8d7fe0b0fd1' REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' REACT_APP_RPC_URL_421611='https://arb-rinkeby.g.alchemy.com/v2/AY_Q_Uy-Kcfwmf5In5qwG636vaOIoA8L' -TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/f24b59a8-db83-4d2c-a244-77b665a2b6ce' +TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/419b6a25-238a-41b4-bb8a-d8d7fe0b0fd1' LOCALHOST_RPC_URL='http://127.0.0.1:8545' TENDERLY_USER='mmyield' From f23b4f5280fe472f0c582ae3ed99cdebf761b399 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 28 Feb 2023 14:30:49 +0000 Subject: [PATCH 08/41] add in asert addresses --- src/contexts/yieldEnv.json | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/contexts/yieldEnv.json b/src/contexts/yieldEnv.json index 71724b42b..d2ece9a3b 100644 --- a/src/contexts/yieldEnv.json +++ b/src/contexts/yieldEnv.json @@ -16,7 +16,8 @@ "Transfer1155Module": "0x97f1d43A217aDD678bB6Dcd3C5D51F40b6729d06", "WrapEtherModule": "0x22768FCaFe7BB9F03e31cb49823d1Ece30C0b8eA", - "ConvexLadleModule": "0x9Bf195997581C99cef8be95a3a816Ca19Cf1A3e6" + "ConvexLadleModule": "0x9Bf195997581C99cef8be95a3a816Ca19Cf1A3e6", + "Assert": "0x41bf71A2109FbdF7e5064a7421EAEFeaBF7a12f7" }, "42161": { @@ -26,7 +27,8 @@ "AccumulatorOracle": "0x0ad9Ef93673B6081c0c3b753CcaaBDdd8d2e7848", "Witch": "0x08173D0885B00BDD640aaE57D05AbB74cd00d669", "WitchV2": "0x07c2c74811cb14a5003c3ccff7ec436d504fffb6", - "WrapEtherModule": "0x4cd01ed221d6d198e2656c16c32803bf78134568" + "WrapEtherModule": "0x4cd01ed221d6d198e2656c16c32803bf78134568", + "Assert": "0x3201161c97E6B3c6e0e565d8Cd17ae5d0BEDb5F7" } } } From 4a4446bbb6020688e03943edf1a359b3c7471bf0 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 28 Feb 2023 14:31:08 +0000 Subject: [PATCH 09/41] specify assert fns by params --- src/hooks/actionHooks/useAssert.ts | 36 +++++++++++++++++++----------- 1 file changed, 23 insertions(+), 13 deletions(-) diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index be12539de..8340501bc 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -7,18 +7,18 @@ import useContracts, { ContractNames } from '../useContracts'; export namespace AssertActions { export enum Fn { - ASSERT_GT = 'assertGt', - ASSERT_LT = 'assertLt', - ASSERT_EQ_REL = 'assertEqRel', - ASSERT_EQ_ABS = 'assertEqAbs', - ASSERT_GE = 'assertGe', - ASSERT_LE = 'assertLe', + ASSERT_GT = 'assertGt(address,bytes,uint)', + ASSERT_LT = 'assertLt(address,bytes,uint,uint256)', + ASSERT_EQ_REL = 'assertEqRel(address,bytes,uint,uint256)', + ASSERT_EQ_ABS = 'assertEqAbs(address,bytes,uint,uint256)', + ASSERT_GE = 'assertGe(address,bytes,uint)', + ASSERT_LE = 'assertLe(address,bytes,uint)', } export namespace Args { export type ASSERT_GT = [actualTarget: string, bytes: any, expected: BigNumberish]; export type ASSERT_LT = [actualTarget: string, bytes: any, expected: BigNumberish]; export type ASSERT_EQ_REL = [actualTarget: string, bytes: any, expected: BigNumberish, relative: BigNumberish]; - export type ASSERT_EQ_ABS = [actualTarget: string, bytes: any, expected: BigNumberish]; + export type ASSERT_EQ_ABS = [actualTarget: string, bytes: any, expected: BigNumberish, absolute: BigNumberish]; export type ASSERT_GE = [actualTarget: string, bytes: any, expected: BigNumberish]; export type ASSERT_LE = [actualTarget: string, bytes: any, expected: BigNumberish]; } @@ -30,15 +30,15 @@ export const useAssert = () => { const { address: account } = useAccount(); const encodeBalanceCall = (address: string, tokenIdentifier: string | number | undefined = undefined) => { - - const mock = '0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE'; if (address) { const abi = tokenIdentifier ? erc1155ABI : erc20ABI; const args = tokenIdentifier ? [account, tokenIdentifier] : [account]; - const assetContract = new Contract(address, abi); - return assetContract.interface.encodeFunctionData('balanceOf', args); + const assetContract_ = new Contract(address, abi); + return assetContract_.interface.encodeFunctionData('balanceOf', args); } - return '0x'; + /* if no address provided, assume the balance is the native balance and get the users ETH balance via a multicall2 contract */ + const contract_ = new Contract("0x5BA1e12693Dc8F9c48aAD8770482f4739bEeD696",multiCallFragment); + return contract_.interface.encodeFunctionData('getEthBalance', [account]); // this calls the helper contract -> because we are looking for an ETH/Native balance; }; const assert = ( @@ -50,7 +50,7 @@ export const useAssert = () => { return [ { operation: LadleActions.Fn.ROUTE, - args: [address, encodedCallBytes, expectedVal] as AssertActions.Args.ASSERT_GT, + args: [address, encodedCallBytes, expectedVal], fnName: assertFn, targetContract: AssertContract, ignoreIf: false, @@ -62,6 +62,16 @@ export const useAssert = () => { return { assert, encodeBalanceCall }; }; +const multiCallFragment = [ + { + inputs: [{ internalType: 'address', name: 'addr', type: 'address' }], + name: 'getEthBalance', + outputs: [{ internalType: 'uint256', name: 'balance', type: 'uint256' }], + stateMutability: 'view', + type: 'function', + }, +]; + const erc1155ABI = [ { inputs: [ From 5e0351fb51e50c0b032291d642c970fabe116e80 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 28 Feb 2023 14:35:59 +0000 Subject: [PATCH 10/41] handle arbitrum ethBalanceCall --- src/hooks/actionHooks/useAssert.ts | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index 8340501bc..7ffc0d776 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -3,6 +3,7 @@ import { erc20ABI, useAccount } from 'wagmi'; import { IAsset, ICallData, LadleActions } from '../../types'; import { RoutedActions } from '../../types/operations'; import { ZERO_BN } from '../../utils/constants'; +import useChainId from '../useChainId'; import useContracts, { ContractNames } from '../useContracts'; export namespace AssertActions { @@ -28,6 +29,7 @@ export const useAssert = () => { const contracts = useContracts(); const AssertContract = contracts.get(ContractNames.ASSERT); const { address: account } = useAccount(); + const chainId = useChainId(); const encodeBalanceCall = (address: string, tokenIdentifier: string | number | undefined = undefined) => { if (address) { @@ -37,7 +39,7 @@ export const useAssert = () => { return assetContract_.interface.encodeFunctionData('balanceOf', args); } /* if no address provided, assume the balance is the native balance and get the users ETH balance via a multicall2 contract */ - const contract_ = new Contract("0x5BA1e12693Dc8F9c48aAD8770482f4739bEeD696",multiCallFragment); + const contract_ = new Contract(chainId === 1 ? "0x5BA1e12693Dc8F9c48aAD8770482f4739bEeD696": "0x842eC2c7D803033Edf55E478F461FC547Bc54EB2", multiCallFragment); return contract_.interface.encodeFunctionData('getEthBalance', [account]); // this calls the helper contract -> because we are looking for an ETH/Native balance; }; From b542a84b933dc2f89b9a71138da7e0c7205dfbef Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 28 Feb 2023 14:37:10 +0000 Subject: [PATCH 11/41] cleanup assetSelector --- src/components/selectors/AssetSelector.tsx | 20 -------------------- 1 file changed, 20 deletions(-) diff --git a/src/components/selectors/AssetSelector.tsx b/src/components/selectors/AssetSelector.tsx index 830a59912..0d7deec5d 100644 --- a/src/components/selectors/AssetSelector.tsx +++ b/src/components/selectors/AssetSelector.tsx @@ -12,12 +12,6 @@ import AssetSelectModal from './AssetSelectModal'; import Logo from '../logos/Logo'; import { GA_Event, GA_Properties } from '../../types/analytics'; import useAnalytics from '../../hooks/useAnalytics'; -import useBalances from '../../hooks/useBalances'; - -import { TokenKind } from 'graphql/language/tokenKind'; - -import { ORACLE_INFO } from '../../config/oracles'; -import useChainId from '../../hooks/useChainId'; interface IAssetSelectorProps { selectCollateral?: boolean; @@ -48,20 +42,6 @@ function AssetSelector({ selectCollateral, isModal }: IAssetSelectorProps) { const [options, setOptions] = useState([]); const [modalOpen, toggleModal] = useState(false); const { logAnalyticsEvent } = useAnalytics(); - const chainId = useChainId(); - const oracleInfo = ORACLE_INFO.get(chainId); - - const { - data: assetsBalance, - isLoading: assetsLoading, - // status: assetsStatus, - refetch: refetchAssets, - } = useBalances( - Array.from(assetMap.values()), // assetRoot[] - !!selectCollateral // enabled boolean - ); - - // console.log( assetsBalance ) const optionText = (asset: IAsset | undefined) => asset ? ( From e7183edc7ee6603094d8fc9028d21fca1e0c635f Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 28 Feb 2023 14:41:08 +0000 Subject: [PATCH 12/41] repayAssertCAll --- src/hooks/actionHooks/useRepayDebt.ts | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) diff --git a/src/hooks/actionHooks/useRepayDebt.ts b/src/hooks/actionHooks/useRepayDebt.ts index b1a96a92d..d56910477 100644 --- a/src/hooks/actionHooks/useRepayDebt.ts +++ b/src/hooks/actionHooks/useRepayDebt.ts @@ -18,6 +18,7 @@ import useContracts, { ContractNames } from '../useContracts'; import { removeUndefined } from 'grommet/utils'; import useChainId from '../useChainId'; import useAccountPlus from '../useAccountPlus'; +import { AssertActions, useAssert } from './useAssert'; export const useRepayDebt = () => { const { @@ -37,7 +38,7 @@ export const useRepayDebt = () => { }); const { refetch: refetchBaseBal } = useBalance({ address: account, - token: selectedBase?.id === WETH ? undefined : selectedBase?.address as Address, + token: selectedBase?.id === WETH ? undefined : (selectedBase?.address as Address), }); const { addEth, removeEth } = useAddRemoveEth(); @@ -46,6 +47,8 @@ export const useRepayDebt = () => { const { getTimeTillMaturity, isMature } = useTimeTillMaturity(); const chainId = useChainId(); + const { assert, encodeBalanceCall } = useAssert(); + /** * REPAY FN * @param vault @@ -130,7 +133,7 @@ export const useRepayDebt = () => { // const wrapAssetCallData : ICallData[] = await wrapAsset(ilk, account!); const unwrapAssetCallData: ICallData[] = reclaimCollateral ? await unwrapAsset(ilk, account!) : []; - const approveAmount = base.id === USDT && chainId !== 42161 ? MAX_256 : amountToTransfer.mul(110).div(100) + const approveAmount = base.id === USDT && chainId !== 42161 ? MAX_256 : amountToTransfer.mul(110).div(100); const permitCallData: ICallData[] = await sign( [ { @@ -155,6 +158,14 @@ export const useRepayDebt = () => { return account; }; + /* Add in an Assert call : Ilk Balance increases by vault ilk (collateral) amount */ + const assertCallData: ICallData[] = assert( + ilk.address, + encodeBalanceCall(ilk.address, ilk.tokenIdentifier), + AssertActions.Fn.ASSERT_GE, + ilk.balance.add(vault.ink) + ); + const calls: ICallData[] = [ ...permitCallData, @@ -211,6 +222,8 @@ export const useRepayDebt = () => { }, ...removeEthCallData, ...unwrapAssetCallData, + + ...assertCallData, ]; await transact(calls, txCode); if (selectedBase?.proxyId !== WETH) refetchBaseBal(); From c88ea24023ba8f62e4c9cfa3ff4d50b3d8ff55dc Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 28 Feb 2023 15:04:48 +0000 Subject: [PATCH 13/41] useMulticall3 --- src/hooks/actionHooks/useAssert.ts | 8 ++++---- src/hooks/actionHooks/useRepayDebt.ts | 4 +--- 2 files changed, 5 insertions(+), 7 deletions(-) diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index 7ffc0d776..690d5f9b4 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -1,5 +1,5 @@ import { BigNumber, BigNumberish, Contract, ethers } from 'ethers'; -import { erc20ABI, useAccount } from 'wagmi'; +import { erc20ABI, useAccount, useNetwork } from 'wagmi'; import { IAsset, ICallData, LadleActions } from '../../types'; import { RoutedActions } from '../../types/operations'; import { ZERO_BN } from '../../utils/constants'; @@ -29,7 +29,7 @@ export const useAssert = () => { const contracts = useContracts(); const AssertContract = contracts.get(ContractNames.ASSERT); const { address: account } = useAccount(); - const chainId = useChainId(); + const {chain} = useNetwork(); const encodeBalanceCall = (address: string, tokenIdentifier: string | number | undefined = undefined) => { if (address) { @@ -38,8 +38,8 @@ export const useAssert = () => { const assetContract_ = new Contract(address, abi); return assetContract_.interface.encodeFunctionData('balanceOf', args); } - /* if no address provided, assume the balance is the native balance and get the users ETH balance via a multicall2 contract */ - const contract_ = new Contract(chainId === 1 ? "0x5BA1e12693Dc8F9c48aAD8770482f4739bEeD696": "0x842eC2c7D803033Edf55E478F461FC547Bc54EB2", multiCallFragment); + /* if no address provided, assume the balance is the native balance and get the users ETH balance via a multical3 contract */ + const contract_ = new Contract(chain?.contracts?.multicall3?.address!, multiCallFragment); return contract_.interface.encodeFunctionData('getEthBalance', [account]); // this calls the helper contract -> because we are looking for an ETH/Native balance; }; diff --git a/src/hooks/actionHooks/useRepayDebt.ts b/src/hooks/actionHooks/useRepayDebt.ts index d56910477..bb80ee850 100644 --- a/src/hooks/actionHooks/useRepayDebt.ts +++ b/src/hooks/actionHooks/useRepayDebt.ts @@ -13,9 +13,8 @@ import { ONE_BN, ZERO_BN } from '../../utils/constants'; import { useWrapUnwrapAsset } from './useWrapUnwrapAsset'; import { ConvexJoin__factory } from '../../contracts'; import useTimeTillMaturity from '../useTimeTillMaturity'; -import { Address, useAccount, useBalance, useNetwork, useProvider } from 'wagmi'; +import { Address, useBalance, useNetwork, useProvider } from 'wagmi'; import useContracts, { ContractNames } from '../useContracts'; -import { removeUndefined } from 'grommet/utils'; import useChainId from '../useChainId'; import useAccountPlus from '../useAccountPlus'; import { AssertActions, useAssert } from './useAssert'; @@ -168,7 +167,6 @@ export const useRepayDebt = () => { const calls: ICallData[] = [ ...permitCallData, - /* Reqd. when we have a wrappedBase */ // ...wrapAssetCallData From 1d0b719827df40bb569382c9bad736c6b7853864 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Thu, 2 Mar 2023 10:12:47 +0000 Subject: [PATCH 14/41] version bump --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index bbe269f46..cfb3546c3 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "app-v2", - "version": "2.5.4", + "version": "2.5.5", "private": true, "dependencies": { "@ethersproject/providers": "^5.6.8", From cfbbd804f8efde7863c73ced9661a42139b96d1b Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Thu, 2 Mar 2023 11:47:15 +0000 Subject: [PATCH 15/41] feat/ assert in actions --- src/hooks/actionHooks/useAddCollateral.ts | 25 +++++++++--- src/hooks/actionHooks/useAddLiquidity.ts | 24 +++++++++--- src/hooks/actionHooks/useAssert.ts | 40 ++++++++------------ src/hooks/actionHooks/useBorrow.ts | 6 +-- src/hooks/actionHooks/useClosePosition.ts | 40 +++++++++++++------- src/hooks/actionHooks/useLend.ts | 15 +++++++- src/hooks/actionHooks/useRemoveCollateral.ts | 14 ++++++- src/hooks/actionHooks/useRemoveLiquidity.ts | 27 ++++++++++++- src/hooks/actionHooks/useRepayDebt.ts | 30 ++++++++++----- src/hooks/actionHooks/useRollDebt.ts | 19 ++++++++++ src/hooks/actionHooks/useRollPosition.ts | 16 +++++++- 11 files changed, 190 insertions(+), 66 deletions(-) diff --git a/src/hooks/actionHooks/useAddCollateral.ts b/src/hooks/actionHooks/useAddCollateral.ts index c3f801241..4f6f131c2 100644 --- a/src/hooks/actionHooks/useAddCollateral.ts +++ b/src/hooks/actionHooks/useAddCollateral.ts @@ -16,6 +16,7 @@ import { HistoryContext } from '../../contexts/HistoryContext'; import { Address, useAccount, useBalance } from 'wagmi'; import useContracts, { ContractNames } from '../useContracts'; import useAccountPlus from '../useAccountPlus'; +import { useAssert, AssertActions } from './useAssert'; export const useAddCollateral = () => { const { userState, userActions } = useContext(UserContext); @@ -32,6 +33,8 @@ export const useAddCollateral = () => { const { wrapAsset } = useWrapUnwrapAsset(); const { addEth } = useAddRemoveEth(); + const { assert, encodeBalanceCall } = useAssert(); + const { refetch: refetchBaseBal } = useBalance({ address: account, token: selectedBase?.address as Address, @@ -46,7 +49,7 @@ export const useAddCollateral = () => { const vaultId = vault?.id || BLANK_VAULT; /* set the ilk based on if a vault has been selected or it's a new vault */ - const ilk: IAsset | null | undefined = vault ? assetMap?.get(vault.ilkId) : selectedIlk; + const ilk: IAsset | null | undefined = vault ? assetMap?.get(vault.ilkId)! : selectedIlk!; const base: IAsset | null | undefined = vault ? assetMap?.get(vault.baseId) : selectedBase; const ladleAddress = contracts.get(ContractNames.LADLE)?.address; @@ -59,6 +62,11 @@ export const useAddCollateral = () => { /* check if the ilk/asset is an eth asset variety, if so pour to Ladle */ const isEthCollateral = ETH_BASED_ASSETS.includes(ilk?.proxyId!); + /* pour destination based on ilk/asset is an eth asset variety */ + const pourToAddress = () => { + if (isEthCollateral) return ladleAddress; + return account; + }; /* is convex-type collateral */ const isConvexCollateral = CONVEX_BASED_ASSETS.includes(selectedIlk?.proxyId!); @@ -92,11 +100,13 @@ export const useAddCollateral = () => { selectedIlk?.proxyId ); - /* pour destination based on ilk/asset is an eth asset variety */ - const pourToAddress = () => { - if (isEthCollateral) return ladleAddress; - return account; - }; + /* Add in an Assert call : collateral(ilk) increases by input amount */ + const assertCallData: ICallData[] = assert( + ilk.address, + encodeBalanceCall(ilk.address, ilk.tokenIdentifier), + AssertActions.Fn.ASSERT_GE, + ilk.balance.add(_input) + ); /** * BUILD CALL DATA ARRAY @@ -132,6 +142,9 @@ export const useAddCollateral = () => { args: [vaultId, pourToAddress(), _input, ethers.constants.Zero] as LadleActions.Args.POUR, ignoreIf: false, // never ignore }, + + /* handle any assert at end of tx */ + ...assertCallData, ]; /* TRANSACT */ diff --git a/src/hooks/actionHooks/useAddLiquidity.ts b/src/hooks/actionHooks/useAddLiquidity.ts index 1ed31858d..1f9c93f18 100644 --- a/src/hooks/actionHooks/useAddLiquidity.ts +++ b/src/hooks/actionHooks/useAddLiquidity.ts @@ -1,6 +1,6 @@ import { BigNumber, ethers } from 'ethers'; import { useContext } from 'react'; -import { calcPoolRatios, calculateSlippage, fyTokenForMint, MAX_256, splitLiquidity } from '@yield-protocol/ui-math'; +import { calcPoolRatios, calculateSlippage, fyTokenForMint, MAX_256, splitLiquidity, WAD_BN } from '@yield-protocol/ui-math'; import { formatUnits } from 'ethers/lib/utils'; import { UserContext } from '../../contexts/UserContext'; @@ -29,10 +29,11 @@ import { Address, useAccount, useBalance } from 'wagmi'; import useContracts, { ContractNames } from '../useContracts'; import useChainId from '../useChainId'; import useAccountPlus from '../useAccountPlus'; +import { AssertActions, useAssert } from './useAssert'; export const useAddLiquidity = () => { const { - settingsState: { slippageTolerance }, + settingsState: { slippageTolerance, diagnostics }, } = useContext(SettingsContext); const { userState, userActions } = useContext(UserContext); @@ -49,6 +50,8 @@ export const useAddLiquidity = () => { } = useContext(HistoryContext); const { addEth } = useAddRemoveEth(); + const { assert, encodeBalanceCall } = useAssert(); + const { getTimeTillMaturity } = useTimeTillMaturity(); const { refetch: refetchBaseBal } = useBalance({ address: account, @@ -127,7 +130,8 @@ export const useAddLiquidity = () => { const baseToPool = _series.getBase(sharesToPool); /* DIAGNOSITCS */ - method === AddLiquidityType.BUY && + diagnostics && + method === AddLiquidityType.BUY && console.log( '\n', 'method: ', @@ -155,7 +159,8 @@ export const useAddLiquidity = () => { formatUnits(maxRatio, strategy.decimals) ); - method === AddLiquidityType.BORROW && + diagnostics && + method === AddLiquidityType.BORROW && console.log( '\n', 'method: ', @@ -214,7 +219,14 @@ export const useAddLiquidity = () => { return []; // sends back an empty array [] if not eth base }; - console.log('isEthBase', isEthBase); + /* Add in an Assert call : Strategy Tokens received within 10% of baseIn. */ + const assertCallData: ICallData[] = assert( + strategy.address, + encodeBalanceCall(strategy.address, undefined), + AssertActions.Fn.ASSERT_EQ_REL, + strategy.accountBalance!.add(_input), + WAD_BN.mul('10') // 10% relative tolerance + ); /** * BUILD CALL DATA ARRAY @@ -303,6 +315,8 @@ export const useAddLiquidity = () => { targetContract: strategy.strategyContract, ignoreIf: !strategy, }, + + ...assertCallData, ]; await transact(calls, txCode); diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index 690d5f9b4..17874f233 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -29,17 +29,17 @@ export const useAssert = () => { const contracts = useContracts(); const AssertContract = contracts.get(ContractNames.ASSERT); const { address: account } = useAccount(); - const {chain} = useNetwork(); + const { chain } = useNetwork(); - const encodeBalanceCall = (address: string, tokenIdentifier: string | number | undefined = undefined) => { - if (address) { + const encodeBalanceCall = (targetAddress: string, tokenIdentifier: string | number | undefined = undefined) => { + if (targetAddress) { const abi = tokenIdentifier ? erc1155ABI : erc20ABI; const args = tokenIdentifier ? [account, tokenIdentifier] : [account]; - const assetContract_ = new Contract(address, abi); + const assetContract_ = new Contract(targetAddress, abi); return assetContract_.interface.encodeFunctionData('balanceOf', args); } /* if no address provided, assume the balance is the native balance and get the users ETH balance via a multical3 contract */ - const contract_ = new Contract(chain?.contracts?.multicall3?.address!, multiCallFragment); + const contract_ = new Contract(chain?.contracts?.multicall3?.address!, multiCallFragment); return contract_.interface.encodeFunctionData('getEthBalance', [account]); // this calls the helper contract -> because we are looking for an ETH/Native balance; }; @@ -47,15 +47,19 @@ export const useAssert = () => { address: string, encodedCallBytes: any, assertFn: AssertActions.Fn, - expectedVal: BigNumber + expectedVal: BigNumber, + relOrAbsVal: BigNumber = ZERO_BN, + ignoreIf: boolean = false ): ICallData[] => { return [ { operation: LadleActions.Fn.ROUTE, - args: [address, encodedCallBytes, expectedVal], + args: relOrAbsVal.gt(ZERO_BN) + ? [address, encodedCallBytes, expectedVal, relOrAbsVal] + : [address, encodedCallBytes, expectedVal], fnName: assertFn, targetContract: AssertContract, - ignoreIf: false, + ignoreIf, }, ]; }; @@ -77,25 +81,11 @@ const multiCallFragment = [ const erc1155ABI = [ { inputs: [ - { - internalType: 'address', - name: 'account', - type: 'address', - }, - { - internalType: 'uint256', - name: 'id', - type: 'uint256', - }, + { internalType: 'address', name: 'account', type: 'address' }, + { internalType: 'uint256', name: 'id', type: 'uint256' }, ], name: 'balanceOf', - outputs: [ - { - internalType: 'uint256', - name: '', - type: 'uint256', - }, - ], + outputs: [{ internalType: 'uint256', name: '', type: 'uint256' }], stateMutability: 'view', type: 'function', }, diff --git a/src/hooks/actionHooks/useBorrow.ts b/src/hooks/actionHooks/useBorrow.ts index d6d01ddae..856b2c462 100644 --- a/src/hooks/actionHooks/useBorrow.ts +++ b/src/hooks/actionHooks/useBorrow.ts @@ -44,12 +44,12 @@ export const useBorrow = () => { const { addEth, removeEth } = useAddRemoveEth(); + const { assert, encodeBalanceCall } = useAssert(); + const { wrapAsset } = useWrapUnwrapAsset(); const { sign, transact } = useChain(); const { getTimeTillMaturity } = useTimeTillMaturity(); - const { assert, encodeBalanceCall } = useAssert(); - const borrow = async (vault: IVault | undefined, input: string | undefined, collInput: string | undefined) => { /* generate the reproducible txCode for tx tracking and tracing */ const txCode = getTxCode(ActionCodes.BORROW, selectedSeries?.id!); @@ -173,7 +173,7 @@ export const useBorrow = () => { args: [vaultId, serveToAddress(), _collInput, _input, _expectedFyTokenWithSlippage] as LadleActions.Args.SERVE, ignoreIf: false, }, - + ...removeEthCallData, ...assertCallData, diff --git a/src/hooks/actionHooks/useClosePosition.ts b/src/hooks/actionHooks/useClosePosition.ts index ad1ba6144..fb6eb0129 100644 --- a/src/hooks/actionHooks/useClosePosition.ts +++ b/src/hooks/actionHooks/useClosePosition.ts @@ -1,6 +1,6 @@ import { ethers } from 'ethers'; import { useContext } from 'react'; -import { buyBase, calculateSlippage } from '@yield-protocol/ui-math'; +import { buyBase, calculateSlippage, WAD_BN } from '@yield-protocol/ui-math'; import { ETH_BASED_ASSETS } from '../../config/assets'; import { HistoryContext } from '../../contexts/HistoryContext'; @@ -16,6 +16,7 @@ import useTimeTillMaturity from '../useTimeTillMaturity'; import { Address, useAccount, useBalance } from 'wagmi'; import useContracts, { ContractNames } from '../useContracts'; import useAccountPlus from '../useAccountPlus'; +import { AssertActions, useAssert } from './useAssert'; /* Lend Actions Hook */ export const useClosePosition = () => { @@ -44,6 +45,8 @@ export const useClosePosition = () => { const { removeEth } = useAddRemoveEth(); const { getTimeTillMaturity } = useTimeTillMaturity(); + const { assert, encodeBalanceCall } = useAssert(); + const closePosition = async ( input: string | undefined, series: ISeries, @@ -80,6 +83,19 @@ export const useClosePosition = () => { /* if ethBase */ const isEthBase = ETH_BASED_ASSETS.includes(series.baseId); + /* Set the transferTo address based on series maturity */ + const transferToAddress = () => { + if (seriesIsMature) return address; + return poolAddress; + }; + + /* receiver based on whether base is ETH (- or wrapped Base) */ + const receiverAddress = () => { + if (isEthBase) return ladleAddress; + // if ( unwrapping) return unwrapHandlerAddress; + return account; + }; + /* if approveMAx, check if signature is required */ const alreadyApproved = (await series.fyTokenContract.allowance(account!, ladleAddress!)).gte(_fyTokenValueOfInput); @@ -97,18 +113,14 @@ export const useClosePosition = () => { const removeEthCallData = isEthBase ? removeEth(ONE_BN) : []; - /* Set the transferTo address based on series maturity */ - const transferToAddress = () => { - if (seriesIsMature) return address; - return poolAddress; - }; - - /* receiver based on whether base is ETH (- or wrapped Base) */ - const receiverAddress = () => { - if (isEthBase) return ladleAddress; - // if ( unwrapping) return unwrapHandlerAddress; - return account; - }; + /* Add in an Assert call : base Balance increases up to 10% of fyToken balance */ + const assertCallData: ICallData[] = assert( + base.address, + encodeBalanceCall(base.address, base.tokenIdentifier), + AssertActions.Fn.ASSERT_EQ_REL, + base.balance.add(series.fyTokenBalance!), + WAD_BN.mul('10') // 10% relative tolerance + ); const calls: ICallData[] = [ ...permitCallData, @@ -139,6 +151,8 @@ export const useClosePosition = () => { }, ...removeEthCallData, // (exit_ether sweeps all the eth out the ladle, so exact amount is not importnat -> just greater than zero) + + ...assertCallData, ]; await transact(calls, txCode); refetchBaseBal(); diff --git a/src/hooks/actionHooks/useLend.ts b/src/hooks/actionHooks/useLend.ts index 9be3794fb..00e0cdd58 100644 --- a/src/hooks/actionHooks/useLend.ts +++ b/src/hooks/actionHooks/useLend.ts @@ -1,6 +1,6 @@ import { ethers } from 'ethers'; import { useContext } from 'react'; -import { calculateSlippage, MAX_256, sellBase } from '@yield-protocol/ui-math'; +import { calculateSlippage, MAX_256, sellBase, WAD_BN } from '@yield-protocol/ui-math'; import { ETH_BASED_ASSETS, USDT } from '../../config/assets'; import { HistoryContext } from '../../contexts/HistoryContext'; @@ -15,6 +15,7 @@ import { Address, useAccount, useBalance } from 'wagmi'; import useContracts, { ContractNames } from '../useContracts'; import useChainId from '../useChainId'; import useAccountPlus from '../useAccountPlus'; +import { AssertActions, useAssert } from './useAssert'; /* Lend Actions Hook */ export const useLend = () => { @@ -43,6 +44,8 @@ export const useLend = () => { const { getTimeTillMaturity } = useTimeTillMaturity(); const contracts = useContracts(); + const { assert, encodeBalanceCall } = useAssert(); + const lend = async (input: string | undefined, series: ISeries) => { /* generate the reproducible txCode for tx tracking and tracing */ const txCode = getTxCode(ActionCodes.LEND, series.id); @@ -90,6 +93,15 @@ export const useLend = () => { return []; }; + /* Add in an Assert call : fyToken balance is 10% higher than what they inputed (as fyTokens) */ + const assertCallData: ICallData[] = assert( + series.fyTokenContract.address, + encodeBalanceCall(series.fyTokenContract.address, undefined), + AssertActions.Fn.ASSERT_EQ_REL, + series.fyTokenBalance!.add(_inputAsFyToken), + WAD_BN.mul('10') // 10% relative tolerance + ); + const calls: ICallData[] = [ ...permitCallData, ...addEthCallData(), @@ -105,6 +117,7 @@ export const useLend = () => { targetContract: series.poolContract, ignoreIf: false, }, + ...assertCallData, ]; await transact(calls, txCode); diff --git a/src/hooks/actionHooks/useRemoveCollateral.ts b/src/hooks/actionHooks/useRemoveCollateral.ts index 2b596a813..c0eeaf4b6 100644 --- a/src/hooks/actionHooks/useRemoveCollateral.ts +++ b/src/hooks/actionHooks/useRemoveCollateral.ts @@ -13,6 +13,7 @@ import { HistoryContext } from '../../contexts/HistoryContext'; import { Address, useAccount, useBalance, useNetwork, useProvider } from 'wagmi'; import useContracts, { ContractNames } from '../useContracts'; import useAccountPlus from '../useAccountPlus'; +import { AssertActions, useAssert } from './useAssert'; export const useRemoveCollateral = () => { const { userState, userActions } = useContext(UserContext); @@ -24,7 +25,7 @@ export const useRemoveCollateral = () => { const { refetch: refetchIlkBal } = useBalance({ address: account, token: selectedIlk?.address as Address, - }); + }); const { historyActions: { updateVaultHistory }, @@ -34,6 +35,7 @@ export const useRemoveCollateral = () => { const { transact } = useChain(); const { removeEth } = useAddRemoveEth(); const { unwrapAsset } = useWrapUnwrapAsset(); + const { assert, encodeBalanceCall } = useAssert(); const removeCollateral = async (vault: IVault, input: string, unwrapOnRemove: boolean = true) => { /* generate the txCode for tx tracking and tracing */ @@ -66,6 +68,14 @@ export const useRemoveCollateral = () => { if (unwrapCallData.length) return unwrapHandlerAddress; // if there is something to unwrap return account; }; + + /* Add in an Assert call : collateral(ilk) decreases by input amount */ + const assertCallData: ICallData[] = assert( + ilk.address, + encodeBalanceCall(ilk.address, ilk.tokenIdentifier), + AssertActions.Fn.ASSERT_GE, + ilk.balance.sub(_input) + ); const calls: ICallData[] = [ /* convex-type collateral; ensure checkpoint before giving collateral back to account */ @@ -88,6 +98,8 @@ export const useRemoveCollateral = () => { }, ...removeEthCallData, ...unwrapCallData, + + ...assertCallData, ]; await transact(calls, txCode); diff --git a/src/hooks/actionHooks/useRemoveLiquidity.ts b/src/hooks/actionHooks/useRemoveLiquidity.ts index 4daa16e1b..d5d3667b4 100644 --- a/src/hooks/actionHooks/useRemoveLiquidity.ts +++ b/src/hooks/actionHooks/useRemoveLiquidity.ts @@ -8,6 +8,7 @@ import { calculateSlippage, newPoolState, sellFYToken, + WAD_BN, } from '@yield-protocol/ui-math'; import { formatUnits } from 'ethers/lib/utils'; @@ -27,6 +28,7 @@ import useContracts, { ContractNames } from '../useContracts'; import { Strategy__factory } from '../../contracts'; import { StrategyType } from '../../config/strategies'; import useAccountPlus from '../useAccountPlus'; +import { AssertActions, useAssert } from './useAssert'; /* +---------+ DEFUNCT PATH @@ -53,9 +55,8 @@ is Mature? N +--------+ */ export const useRemoveLiquidity = () => { - const provider = useProvider(); - const {address:account} = useAccountPlus(); + const { address: account } = useAccountPlus(); const { txActions } = useContext(TxContext); const { resetProcess } = txActions; @@ -68,6 +69,8 @@ export const useRemoveLiquidity = () => { const { removeEth } = useAddRemoveEth(); const { getTimeTillMaturity } = useTimeTillMaturity(); + const { assert, encodeBalanceCall } = useAssert(); + const contracts = useContracts(); const { refetch: refetchBaseBal } = useBalance({ address: account, @@ -290,6 +293,23 @@ export const useRemoveLiquidity = () => { txCode ); + /* Add in an Assert call : Base received + fyToken received within 10% of strategy tokens held. */ + const assertCallData_base: ICallData[] = assert( + _base.address, + encodeBalanceCall(_base.address, _base.tokenIdentifier), + AssertActions.Fn.ASSERT_EQ_REL, + _base.balance!.add( series.getBase(_sharesReceived) ), + WAD_BN.mul('10') // 10% relative tolerance + ); + /* Add in an Assert call : Base received + fyToken received within 10% of strategy tokens held. */ + const assertCallData_fyToken: ICallData[] = _fyTokenReceived.gt(ZERO_BN) ? assert( + series.address, + encodeBalanceCall(series.address, undefined), + AssertActions.Fn.ASSERT_EQ_REL, + series.fyTokenBalance!.add(_fyTokenReceived), + WAD_BN.mul('10') // 10% relative tolerance + ) : []; + // const unwrapping: ICallData[] = await unwrapAsset(_base, account) const calls: ICallData[] = [ ...permitCallData, @@ -448,6 +468,9 @@ export const useRemoveLiquidity = () => { }, ...removeEthCallData, + + ...assertCallData_base, + ...assertCallData_fyToken, ]; await transact(calls, txCode); diff --git a/src/hooks/actionHooks/useRepayDebt.ts b/src/hooks/actionHooks/useRepayDebt.ts index bb80ee850..11712daf0 100644 --- a/src/hooks/actionHooks/useRepayDebt.ts +++ b/src/hooks/actionHooks/useRepayDebt.ts @@ -1,6 +1,6 @@ import { ethers } from 'ethers'; import { useContext } from 'react'; -import { calculateSlippage, maxBaseIn, MAX_256, sellBase } from '@yield-protocol/ui-math'; +import { calculateSlippage, maxBaseIn, MAX_256, sellBase, WAD_BN } from '@yield-protocol/ui-math'; import { UserContext } from '../../contexts/UserContext'; import { ICallData, IVault, ISeries, ActionCodes, LadleActions, IAsset, RoutedActions } from '../../types'; @@ -11,7 +11,7 @@ import { SettingsContext } from '../../contexts/SettingsContext'; import { useAddRemoveEth } from './useAddRemoveEth'; import { ONE_BN, ZERO_BN } from '../../utils/constants'; import { useWrapUnwrapAsset } from './useWrapUnwrapAsset'; -import { ConvexJoin__factory } from '../../contracts'; +import { Cauldron, ConvexJoin__factory } from '../../contracts'; import useTimeTillMaturity from '../useTimeTillMaturity'; import { Address, useBalance, useNetwork, useProvider } from 'wagmi'; import useContracts, { ContractNames } from '../useContracts'; @@ -47,6 +47,7 @@ export const useRepayDebt = () => { const chainId = useChainId(); const { assert, encodeBalanceCall } = useAssert(); + const cauldron = contracts.get(ContractNames.CAULDRON) as Cauldron; /** * REPAY FN @@ -157,13 +158,24 @@ export const useRepayDebt = () => { return account; }; - /* Add in an Assert call : Ilk Balance increases by vault ilk (collateral) amount */ - const assertCallData: ICallData[] = assert( - ilk.address, - encodeBalanceCall(ilk.address, ilk.tokenIdentifier), - AssertActions.Fn.ASSERT_GE, - ilk.balance.add(vault.ink) - ); + /** Add in an Assert call : + * - Users ilk balance increases by ilk amount> if repaying all debt AND removing all collateral + * - vault debt reduced by input amount > if repaying part debt + */ + const assertCallData: ICallData[] = reclaimCollateral + ? assert( + ilk.address, + encodeBalanceCall(ilk.address, ilk.tokenIdentifier), + AssertActions.Fn.ASSERT_GE, + ilk.balance.add(vault.ink) + ) + : assert( + cauldron.address, + cauldron.interface.encodeFunctionData('balances', [vault.id]), + AssertActions.Fn.ASSERT_EQ_REL, + vault.accruedArt.sub(_input), + WAD_BN.mul('10') // 10% relative tolerance + ); const calls: ICallData[] = [ ...permitCallData, diff --git a/src/hooks/actionHooks/useRollDebt.ts b/src/hooks/actionHooks/useRollDebt.ts index a0ddec0e6..bffe0da09 100644 --- a/src/hooks/actionHooks/useRollDebt.ts +++ b/src/hooks/actionHooks/useRollDebt.ts @@ -1,10 +1,15 @@ +import { WAD_BN } from '@yield-protocol/ui-math'; +import { ethers } from 'ethers'; import { useContext } from 'react'; import { HistoryContext } from '../../contexts/HistoryContext'; import { UserContext } from '../../contexts/UserContext'; +import { Cauldron } from '../../contracts'; import { ICallData, IVault, ISeries, ActionCodes, LadleActions, IHistoryContext } from '../../types'; import { getTxCode } from '../../utils/appUtils'; import { MAX_128, ZERO_BN } from '../../utils/constants'; import { useChain } from '../useChain'; +import useContracts, { ContractNames } from '../useContracts'; +import { AssertActions, useAssert } from './useAssert'; /* Generic hook for chain transactions */ export const useRollDebt = () => { @@ -18,12 +23,25 @@ export const useRollDebt = () => { const { transact } = useChain(); + const { assert, encodeBalanceCall } = useAssert(); + const contracts = useContracts(); + const cauldron = contracts.get(ContractNames.CAULDRON) as Cauldron; + const rollDebt = async (vault: IVault, toSeries: ISeries) => { const txCode = getTxCode(ActionCodes.ROLL_DEBT, vault.id); const base = assetMap?.get(vault.baseId); const hasDebt = vault.accruedArt.gt(ZERO_BN); const fromSeries = seriesMap?.get(vault.seriesId); + /* Add in an Assert call : debt in new series within 10% of old debt */ + const assertCallData: ICallData[] = assert( + cauldron.address, + cauldron.interface.encodeFunctionData('balances', [vault.id]), + AssertActions.Fn.ASSERT_EQ_REL, + vault.accruedArt, + WAD_BN.mul('10'), // 10% relative tolerance + ); + const calls: ICallData[] = [ { // ladle.rollAction(vaultId: string, newSeriesId: string, max: BigNumberish) @@ -37,6 +55,7 @@ export const useRollDebt = () => { args: [vault.id, toSeries.id, vault.ilkId] as LadleActions.Args.TWEAK, ignoreIf: hasDebt, }, + // ...assertCallData, ]; await transact(calls, txCode); updateVaults([vault]); diff --git a/src/hooks/actionHooks/useRollPosition.ts b/src/hooks/actionHooks/useRollPosition.ts index 279754d0e..5399dfef9 100644 --- a/src/hooks/actionHooks/useRollPosition.ts +++ b/src/hooks/actionHooks/useRollPosition.ts @@ -1,6 +1,6 @@ import { ethers } from 'ethers'; import { useContext } from 'react'; -import { buyBase, calculateSlippage, sellBase } from '@yield-protocol/ui-math'; +import { buyBase, calculateSlippage, sellBase, WAD_BN } from '@yield-protocol/ui-math'; import { formatUnits } from 'ethers/lib/utils'; import { HistoryContext } from '../../contexts/HistoryContext'; @@ -14,6 +14,7 @@ import { useRouter } from 'next/router'; import { useAccount } from 'wagmi'; import useContracts, { ContractNames } from '../useContracts'; import useAccountPlus from '../useAccountPlus'; +import { AssertActions, useAssert } from './useAssert'; /* Roll Lend Position Action Hook */ export const useRollPosition = () => { @@ -36,6 +37,8 @@ export const useRollPosition = () => { const { sign, transact } = useChain(); const { getTimeTillMaturity } = useTimeTillMaturity(); + const { assert, encodeBalanceCall } = useAssert(); + /** * Transfer fyToken to the "from" pool to sell for base, then send base to "to" pool and sell base for fyToken * @param input in base (i.e.: 100 USDC) @@ -115,6 +118,15 @@ export const useRollPosition = () => { txCode ); + /* Add in an Assert call : new fyToken balance within 10% (up or down) of old position. */ + const assertCallData: ICallData[] = assert( + toSeries.address, + encodeBalanceCall(toSeries.address, undefined), + AssertActions.Fn.ASSERT_EQ_REL, + fromSeries.fyTokenBalance!, + WAD_BN.mul('10') // 10% relative tolerance + ); + /* Reciever of transfer (based on maturity) the series maturity */ const transferToAddress = () => { if (fromSeries.seriesIsMature) return fromSeries.address; @@ -161,6 +173,8 @@ export const useRollPosition = () => { targetContract: toSeries.poolContract, ignoreIf: !fromSeries.seriesIsMature, }, + + ...assertCallData, ]; const res = (await transact(calls, txCode)) as Promise | void; From c89a54a2d1ddd741fdd509c4263840878eeab07d Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Thu, 2 Mar 2023 14:17:35 +0000 Subject: [PATCH 16/41] new fork --- .env.local | 9 ++------- src/contexts/SettingsContext.tsx | 2 +- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/.env.local b/.env.local index 282d66e49..75c500214 100644 --- a/.env.local +++ b/.env.local @@ -4,17 +4,12 @@ REACT_APP_VERSION=$npm_package_version REACT_APP_RPC_URL_1='https://eth-mainnet.g.alchemy.com/v2/ZXDCq5iy0KrKR0XjsqC6E4QG7Z_FuXDv' REACT_APP_RPC_URL_42161='https://arb-mainnet.g.alchemy.com/v2/vtMM4_eLnOvkjkdckprVw3cIa64EVkDZ' -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/419b6a25-238a-41b4-bb8a-d8d7fe0b0fd1' +REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/ae439554-dd8b-4419-94f4-a9c91b876844' REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' -REACT_APP_RPC_URL_421611='https://arb-rinkeby.g.alchemy.com/v2/AY_Q_Uy-Kcfwmf5In5qwG636vaOIoA8L' - -TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/419b6a25-238a-41b4-bb8a-d8d7fe0b0fd1' +TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/ae439554-dd8b-4419-94f4-a9c91b876844' LOCALHOST_RPC_URL='http://127.0.0.1:8545' -TENDERLY_SIMULATION_1=' ' -TENDERLY_SIMULATION_42161=' ' - TENDERLY_USER='mmyield' TENDERLY_PROECT='Yield/v2' TENDERLY_ACCESS_KEY='780JYfoBZ7uF6TX9hoMe76n9YdEKGAHd' diff --git a/src/contexts/SettingsContext.tsx b/src/contexts/SettingsContext.tsx index d272a076a..9485627ae 100644 --- a/src/contexts/SettingsContext.tsx +++ b/src/contexts/SettingsContext.tsx @@ -41,7 +41,7 @@ const initState: ISettingsContextState = { /* development settings */ /* Always force transctions to the chain -> even if they will likely fail */ - forceTransactions: false, + forceTransactions: true, /* Show diagnostic messages in the console */ diagnostics: false, /* use a forked network */ From c1b99476b6169cc12dfac9a65c823c16b0ae4233 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 6 Mar 2023 10:23:11 +0000 Subject: [PATCH 17/41] WIP:placeholder --- .env.local | 4 ++-- src/components/selectors/AssetSelector.tsx | 2 +- src/contexts/SettingsContext.tsx | 3 ++- src/hooks/actionHooks/useBorrow.ts | 7 ++++--- 4 files changed, 9 insertions(+), 7 deletions(-) diff --git a/.env.local b/.env.local index 75c500214..8b2d17738 100644 --- a/.env.local +++ b/.env.local @@ -4,10 +4,10 @@ REACT_APP_VERSION=$npm_package_version REACT_APP_RPC_URL_1='https://eth-mainnet.g.alchemy.com/v2/ZXDCq5iy0KrKR0XjsqC6E4QG7Z_FuXDv' REACT_APP_RPC_URL_42161='https://arb-mainnet.g.alchemy.com/v2/vtMM4_eLnOvkjkdckprVw3cIa64EVkDZ' -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/ae439554-dd8b-4419-94f4-a9c91b876844' +REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/419b6a25-238a-41b4-bb8a-d8d7fe0b0fd1' REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' -TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/ae439554-dd8b-4419-94f4-a9c91b876844' +TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/419b6a25-238a-41b4-bb8a-d8d7fe0b0fd1' LOCALHOST_RPC_URL='http://127.0.0.1:8545' TENDERLY_USER='mmyield' diff --git a/src/components/selectors/AssetSelector.tsx b/src/components/selectors/AssetSelector.tsx index b006fcc99..4ae8521c9 100644 --- a/src/components/selectors/AssetSelector.tsx +++ b/src/components/selectors/AssetSelector.tsx @@ -80,7 +80,7 @@ function AssetSelector({ selectCollateral, isModal }: IAssetSelectorProps) { /* update options on any changes */ useEffect(() => { - const opts = (selectCollateral ? validIlks! : Array.from(assetMap.values())) + const opts = (selectCollateral && validIlks ? validIlks : Array.from(assetMap.values())) // if !validIlks, then we just return all assets ( for forked env ) .filter((a) => a.showToken) .filter((a) => (showWrappedTokens ? true : !a.isWrappedToken)); // filter based on whether wrapped tokens are shown or not diff --git a/src/contexts/SettingsContext.tsx b/src/contexts/SettingsContext.tsx index 9485627ae..ce512d65e 100644 --- a/src/contexts/SettingsContext.tsx +++ b/src/contexts/SettingsContext.tsx @@ -1,6 +1,7 @@ import { createContext, Dispatch, ReactNode, useEffect, useReducer } from 'react'; import { USDC } from '../config/assets'; import { ApprovalType } from '../types'; +import { BLANK_ADDRESS } from '../utils/constants'; import { ISettingsContextActions, ISettingsContextState, Settings, SettingsContextAction } from './types/settings'; const initState: ISettingsContextState = { @@ -51,7 +52,7 @@ const initState: ISettingsContextState = { /* Mock a particular user */ useMockedUser: false, - mockUserAddress: '0x1Bd3Abb6ef058408734EA01cA81D325039cd7bcA', + mockUserAddress: BLANK_ADDRESS, }; const initActions: ISettingsContextActions = { diff --git a/src/hooks/actionHooks/useBorrow.ts b/src/hooks/actionHooks/useBorrow.ts index 856b2c462..586c55f11 100644 --- a/src/hooks/actionHooks/useBorrow.ts +++ b/src/hooks/actionHooks/useBorrow.ts @@ -1,6 +1,6 @@ import { ethers } from 'ethers'; import { useContext } from 'react'; -import { buyBase, calculateSlippage } from '@yield-protocol/ui-math'; +import { buyBase, calculateSlippage, WAD_BN } from '@yield-protocol/ui-math'; import { SettingsContext } from '../../contexts/SettingsContext'; import { UserContext } from '../../contexts/UserContext'; @@ -126,8 +126,9 @@ export const useBorrow = () => { const assertCallData: ICallData[] = assert( base.address, encodeBalanceCall(base.address, base.tokenIdentifier), - AssertActions.Fn.ASSERT_GE, - base.balance.add(_input) + AssertActions.Fn.ASSERT_EQ_REL, // relative here + base.balance.add(_input), + WAD_BN ); /* if ETH is being borrowed, send the borrowed tokens (WETH) to ladle for unwrapping */ From 54f8c21aaf914f62f16eef2db843fea7d704972f Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 7 Mar 2023 14:46:30 +0000 Subject: [PATCH 18/41] vaultBalance before === vaultBalance after --- src/hooks/actionHooks/useRollDebt.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/hooks/actionHooks/useRollDebt.ts b/src/hooks/actionHooks/useRollDebt.ts index bffe0da09..f74df81f3 100644 --- a/src/hooks/actionHooks/useRollDebt.ts +++ b/src/hooks/actionHooks/useRollDebt.ts @@ -55,7 +55,7 @@ export const useRollDebt = () => { args: [vault.id, toSeries.id, vault.ilkId] as LadleActions.Args.TWEAK, ignoreIf: hasDebt, }, - // ...assertCallData, + ...assertCallData, ]; await transact(calls, txCode); updateVaults([vault]); From a7685daf2765fe09c8893e71592fb6437749c9f4 Mon Sep 17 00:00:00 2001 From: marcomariscal Date: Fri, 10 Mar 2023 14:39:28 -0800 Subject: [PATCH 19/41] feat: assert into new config --- src/config/contracts.ts | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/config/contracts.ts b/src/config/contracts.ts index e2d1679f9..cfeb4ec87 100644 --- a/src/config/contracts.ts +++ b/src/config/contracts.ts @@ -8,6 +8,7 @@ export enum ContractNames { WRAP_ETHER_MODULE = 'WrapEtherModule', CONVEX_LADLE_MODULE = 'ConvexLadleModule', TRANSFER_1155_MODULE = 'Transfer1155Module', + ASSERT = 'Assert', } export type ContractMap = Map; @@ -28,6 +29,7 @@ const contractAddresses: ContractAddresses = { [ContractNames.TRANSFER_1155_MODULE, '0x97f1d43A217aDD678bB6Dcd3C5D51F40b6729d06'], [ContractNames.WRAP_ETHER_MODULE, '0x22768FCaFe7BB9F03e31cb49823d1Ece30C0b8eA'], [ContractNames.CONVEX_LADLE_MODULE, '0x9Bf195997581C99cef8be95a3a816Ca19Cf1A3e6'], + [ContractNames.ASSERT, '0x41bf71A2109FbdF7e5064a7421EAEFeaBF7a12f7'], ]), ], [ @@ -38,6 +40,7 @@ const contractAddresses: ContractAddresses = { [ContractNames.WITCH, '0x08173D0885B00BDD640aaE57D05AbB74cd00d669'], [ContractNames.WITCHV2, '0x07c2c74811cb14a5003c3ccff7ec436d504fffb6'], [ContractNames.WRAP_ETHER_MODULE, '0x4cd01ed221d6d198e2656c16c32803bf78134568'], + [ContractNames.ASSERT, '0x3201161c97E6B3c6e0e565d8Cd17ae5d0BEDb5F7'], ]), ], ]), From 0d5d6ff8e013594931a61683ebddb769e2980dc5 Mon Sep 17 00:00:00 2001 From: marcomariscal Date: Fri, 10 Mar 2023 14:45:36 -0800 Subject: [PATCH 20/41] feat: make sure contracts exist --- src/hooks/actionHooks/useAssert.ts | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index 17874f233..d5467ceec 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -1,10 +1,11 @@ import { BigNumber, BigNumberish, Contract, ethers } from 'ethers'; import { erc20ABI, useAccount, useNetwork } from 'wagmi'; +import { ContractNames } from '../../config/contracts'; import { IAsset, ICallData, LadleActions } from '../../types'; import { RoutedActions } from '../../types/operations'; import { ZERO_BN } from '../../utils/constants'; import useChainId from '../useChainId'; -import useContracts, { ContractNames } from '../useContracts'; +import useContracts from '../useContracts'; export namespace AssertActions { export enum Fn { @@ -27,7 +28,6 @@ export namespace AssertActions { export const useAssert = () => { const contracts = useContracts(); - const AssertContract = contracts.get(ContractNames.ASSERT); const { address: account } = useAccount(); const { chain } = useNetwork(); @@ -51,6 +51,10 @@ export const useAssert = () => { relOrAbsVal: BigNumber = ZERO_BN, ignoreIf: boolean = false ): ICallData[] => { + if (!contracts) return []; + + const AssertContract = contracts.get(ContractNames.ASSERT); + return [ { operation: LadleActions.Fn.ROUTE, From 69aff1a1b69b6f32384823599b25d6600b263e39 Mon Sep 17 00:00:00 2001 From: marcomariscal Date: Fri, 10 Mar 2023 14:47:50 -0800 Subject: [PATCH 21/41] fix: make sure contracts exist --- src/hooks/actionHooks/useRollDebt.ts | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/src/hooks/actionHooks/useRollDebt.ts b/src/hooks/actionHooks/useRollDebt.ts index f74df81f3..7793e4b41 100644 --- a/src/hooks/actionHooks/useRollDebt.ts +++ b/src/hooks/actionHooks/useRollDebt.ts @@ -1,6 +1,6 @@ import { WAD_BN } from '@yield-protocol/ui-math'; -import { ethers } from 'ethers'; import { useContext } from 'react'; +import { ContractNames } from '../../config/contracts'; import { HistoryContext } from '../../contexts/HistoryContext'; import { UserContext } from '../../contexts/UserContext'; import { Cauldron } from '../../contracts'; @@ -8,7 +8,7 @@ import { ICallData, IVault, ISeries, ActionCodes, LadleActions, IHistoryContext import { getTxCode } from '../../utils/appUtils'; import { MAX_128, ZERO_BN } from '../../utils/constants'; import { useChain } from '../useChain'; -import useContracts, { ContractNames } from '../useContracts'; +import useContracts from '../useContracts'; import { AssertActions, useAssert } from './useAssert'; /* Generic hook for chain transactions */ @@ -25,9 +25,11 @@ export const useRollDebt = () => { const { assert, encodeBalanceCall } = useAssert(); const contracts = useContracts(); - const cauldron = contracts.get(ContractNames.CAULDRON) as Cauldron; const rollDebt = async (vault: IVault, toSeries: ISeries) => { + if (!contracts) return; + + const cauldron = contracts.get(ContractNames.CAULDRON) as Cauldron; const txCode = getTxCode(ActionCodes.ROLL_DEBT, vault.id); const base = assetMap?.get(vault.baseId); const hasDebt = vault.accruedArt.gt(ZERO_BN); @@ -39,7 +41,7 @@ export const useRollDebt = () => { cauldron.interface.encodeFunctionData('balances', [vault.id]), AssertActions.Fn.ASSERT_EQ_REL, vault.accruedArt, - WAD_BN.mul('10'), // 10% relative tolerance + WAD_BN.mul('10') // 10% relative tolerance ); const calls: ICallData[] = [ From dc7fd88885f00c077879bed5ba08449501185a62 Mon Sep 17 00:00:00 2001 From: marcomariscal Date: Fri, 10 Mar 2023 14:48:37 -0800 Subject: [PATCH 22/41] feat: bytesLike --- src/hooks/actionHooks/useAssert.ts | 24 +++++++++++++++++------- 1 file changed, 17 insertions(+), 7 deletions(-) diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index d5467ceec..929a040bb 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -1,4 +1,4 @@ -import { BigNumber, BigNumberish, Contract, ethers } from 'ethers'; +import { BigNumber, BigNumberish, Bytes, BytesLike, Contract, ethers } from 'ethers'; import { erc20ABI, useAccount, useNetwork } from 'wagmi'; import { ContractNames } from '../../config/contracts'; import { IAsset, ICallData, LadleActions } from '../../types'; @@ -17,12 +17,22 @@ export namespace AssertActions { ASSERT_LE = 'assertLe(address,bytes,uint)', } export namespace Args { - export type ASSERT_GT = [actualTarget: string, bytes: any, expected: BigNumberish]; - export type ASSERT_LT = [actualTarget: string, bytes: any, expected: BigNumberish]; - export type ASSERT_EQ_REL = [actualTarget: string, bytes: any, expected: BigNumberish, relative: BigNumberish]; - export type ASSERT_EQ_ABS = [actualTarget: string, bytes: any, expected: BigNumberish, absolute: BigNumberish]; - export type ASSERT_GE = [actualTarget: string, bytes: any, expected: BigNumberish]; - export type ASSERT_LE = [actualTarget: string, bytes: any, expected: BigNumberish]; + export type ASSERT_GT = [actualTarget: string, bytes: BytesLike, expected: BigNumberish]; + export type ASSERT_LT = [actualTarget: string, bytes: BytesLike, expected: BigNumberish]; + export type ASSERT_EQ_REL = [ + actualTarget: string, + bytes: BytesLike, + expected: BigNumberish, + relative: BigNumberish + ]; + export type ASSERT_EQ_ABS = [ + actualTarget: string, + bytes: BytesLike, + expected: BigNumberish, + absolute: BigNumberish + ]; + export type ASSERT_GE = [actualTarget: string, bytes: BytesLike, expected: BigNumberish]; + export type ASSERT_LE = [actualTarget: string, bytes: BytesLike, expected: BigNumberish]; } } From 2ddb11d04775c0483b88e778640edf9e2e483653 Mon Sep 17 00:00:00 2001 From: marcomariscal Date: Fri, 10 Mar 2023 15:18:12 -0800 Subject: [PATCH 23/41] feat: types --- src/hooks/actionHooks/useAssert.ts | 26 ++++++-------------------- 1 file changed, 6 insertions(+), 20 deletions(-) diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index 929a040bb..bb174fa61 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -1,10 +1,9 @@ -import { BigNumber, BigNumberish, Bytes, BytesLike, Contract, ethers } from 'ethers'; +import { BigNumber, BigNumberish, BytesLike, Contract } from 'ethers'; import { erc20ABI, useAccount, useNetwork } from 'wagmi'; import { ContractNames } from '../../config/contracts'; -import { IAsset, ICallData, LadleActions } from '../../types'; -import { RoutedActions } from '../../types/operations'; +import { Assert, ERC1155__factory } from '../../contracts'; +import { ICallData, LadleActions } from '../../types'; import { ZERO_BN } from '../../utils/constants'; -import useChainId from '../useChainId'; import useContracts from '../useContracts'; export namespace AssertActions { @@ -43,7 +42,7 @@ export const useAssert = () => { const encodeBalanceCall = (targetAddress: string, tokenIdentifier: string | number | undefined = undefined) => { if (targetAddress) { - const abi = tokenIdentifier ? erc1155ABI : erc20ABI; + const abi = tokenIdentifier ? ERC1155__factory.abi : erc20ABI; const args = tokenIdentifier ? [account, tokenIdentifier] : [account]; const assetContract_ = new Contract(targetAddress, abi); return assetContract_.interface.encodeFunctionData('balanceOf', args); @@ -55,7 +54,7 @@ export const useAssert = () => { const assert = ( address: string, - encodedCallBytes: any, + encodedCallBytes: string, assertFn: AssertActions.Fn, expectedVal: BigNumber, relOrAbsVal: BigNumber = ZERO_BN, @@ -63,7 +62,7 @@ export const useAssert = () => { ): ICallData[] => { if (!contracts) return []; - const AssertContract = contracts.get(ContractNames.ASSERT); + const AssertContract = contracts.get(ContractNames.ASSERT) as Assert; return [ { @@ -91,16 +90,3 @@ const multiCallFragment = [ type: 'function', }, ]; - -const erc1155ABI = [ - { - inputs: [ - { internalType: 'address', name: 'account', type: 'address' }, - { internalType: 'uint256', name: 'id', type: 'uint256' }, - ], - name: 'balanceOf', - outputs: [{ internalType: 'uint256', name: '', type: 'uint256' }], - stateMutability: 'view', - type: 'function', - }, -]; From a053020f9eeb9d83781611f69663f7fe1d18798c Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Wed, 12 Apr 2023 11:00:40 +0200 Subject: [PATCH 24/41] clean out .env --- .env.local | 15 +-------------- next.config.js | 4 +--- 2 files changed, 2 insertions(+), 17 deletions(-) diff --git a/.env.local b/.env.local index e67e8d5a0..aa2774956 100644 --- a/.env.local +++ b/.env.local @@ -1,26 +1,13 @@ REACT_APP_DEFAULT_CHAINID=42161 REACT_APP_VERSION=$npm_package_version -REACT_APP_RPC_URL_1='https://eth-mainnet.g.alchemy.com/v2/ZXDCq5iy0KrKR0XjsqC6E4QG7Z_FuXDv' -REACT_APP_RPC_URL_42161='https://arb-mainnet.g.alchemy.com/v2/vtMM4_eLnOvkjkdckprVw3cIa64EVkDZ' - -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/6fd873f9-62cb-44b7-a7ab-e871f8f3b764' -REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' - -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/419b6a25-238a-41b4-bb8a-d8d7fe0b0fd1' +REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/3856a2e6-7fa7-4eda-b38b-278b4df5156c' REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' -TENDERLY_JSON_RPC_URL='https://rpc.tenderly.co/fork/419b6a25-238a-41b4-bb8a-d8d7fe0b0fd1' -LOCALHOST_RPC_URL='http://127.0.0.1:8545' - -TENDERLY_SIMULATION_1=' ' -TENDERLY_SIMULATION_42161=' ' - TENDERLY_USER='Yield' TENDERLY_PROJECT='v2' TENDERLY_ACCESS_KEY='B4N3hpAhTmY09c3pyeC9zC8rMfto7ukj' - INFURA_KEY=2af222f674024a0f84b5f0aad0da72a2 ALCHEMY_ARBITRUM_KEY=vtMM4_eLnOvkjkdckprVw3cIa64EVkDZ ALCHEMY_MAINNET_KEY=ZXDCq5iy0KrKR0XjsqC6E4QG7Z_FuXDv diff --git a/next.config.js b/next.config.js index 5ccddd31b..9408bfb03 100644 --- a/next.config.js +++ b/next.config.js @@ -5,9 +5,6 @@ const nextConfig = { env: { REACT_APP_DEFAULT_CHAINID: process.env.REACT_APP_DEFAULT_CHAINID, REACT_APP_VERSION: process.env.REACT_APP_VERSION, - REACT_APP_INFURA_KEY_V1: process.env.REACT_APP_INFURA_KEY_V1, - REACT_APP_RPC_URL_1: process.env.TENDERLY_JSON_RPC_URL, - REACT_APP_RPC_URL_42161: process.env.REACT_APP_RPC_URL_42161, REACT_APP_DEFAULT_FORK_RPC_URL: process.env.REACT_APP_DEFAULT_FORK_RPC_URL, REACT_APP_LOCALHOST_RPC_URL: process.env.REACT_APP_LOCALHOST_RPC_URL, @@ -22,6 +19,7 @@ const nextConfig = { TENDERLY_ACCESS_KEY: process.env.TENDERLY_ACCESS_KEY, ALLOWED_SUPPORT_ADDRESSES: process.env.ALLOWED_SUPPORT_ADDRESSES, + KILLSWITCH_ACTIVE: process.env.KILLSWITCH_ACTIVE, KILLSWITCH_TEXT: process.env.KILLSWITCH_TEXT, KILLSWITCH_CHAIN: process.env.KILLSWITCH_CHAIN, From b67e2b1925f1553edf98f0dba57e65b6685c152e Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Wed, 12 Apr 2023 12:09:30 +0200 Subject: [PATCH 25/41] increase gaslimit --- src/hooks/useChain.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/hooks/useChain.ts b/src/hooks/useChain.ts index 6f9624db7..6fe13e9d1 100644 --- a/src/hooks/useChain.ts +++ b/src/hooks/useChain.ts @@ -97,7 +97,7 @@ export const useChain = () => { gasEst = await _contract.estimateGas.batch(encodedCalls, { value: batchValue } as PayableOverrides); console.log('Auto gas estimate:', gasEst.mul(135).div(100).toString()); } catch (e: any) { - gasEst = BigNumber.from(500000); + gasEst = BigNumber.from(5000000); /* handle if the tx if going to fail and transactions aren't forced */ if (!forceTransactions) return handleTxWillFail(e.error, txCode, e.transaction); } From 325948db4a4f71fe27df2d20f49f6a3d7b8e9c54 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Wed, 12 Apr 2023 12:09:41 +0200 Subject: [PATCH 26/41] add in availabel assert.sol --- .env.local | 2 +- src/config/contracts.ts | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/.env.local b/.env.local index aa2774956..45f6e78ac 100644 --- a/.env.local +++ b/.env.local @@ -1,7 +1,7 @@ REACT_APP_DEFAULT_CHAINID=42161 REACT_APP_VERSION=$npm_package_version -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/3856a2e6-7fa7-4eda-b38b-278b4df5156c' +REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/f6e50db3-ab83-44fb-a94a-68b5b49628ef' REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' TENDERLY_USER='Yield' diff --git a/src/config/contracts.ts b/src/config/contracts.ts index cfeb4ec87..004a2821b 100644 --- a/src/config/contracts.ts +++ b/src/config/contracts.ts @@ -29,7 +29,7 @@ const contractAddresses: ContractAddresses = { [ContractNames.TRANSFER_1155_MODULE, '0x97f1d43A217aDD678bB6Dcd3C5D51F40b6729d06'], [ContractNames.WRAP_ETHER_MODULE, '0x22768FCaFe7BB9F03e31cb49823d1Ece30C0b8eA'], [ContractNames.CONVEX_LADLE_MODULE, '0x9Bf195997581C99cef8be95a3a816Ca19Cf1A3e6'], - [ContractNames.ASSERT, '0x41bf71A2109FbdF7e5064a7421EAEFeaBF7a12f7'], + [ContractNames.ASSERT, '0x40f0b18c7a41c04f848c033ed7f9178d9c5a80d8'], ]), ], [ @@ -40,7 +40,7 @@ const contractAddresses: ContractAddresses = { [ContractNames.WITCH, '0x08173D0885B00BDD640aaE57D05AbB74cd00d669'], [ContractNames.WITCHV2, '0x07c2c74811cb14a5003c3ccff7ec436d504fffb6'], [ContractNames.WRAP_ETHER_MODULE, '0x4cd01ed221d6d198e2656c16c32803bf78134568'], - [ContractNames.ASSERT, '0x3201161c97E6B3c6e0e565d8Cd17ae5d0BEDb5F7'], + [ContractNames.ASSERT, '0x40f0b18c7a41c04f848c033ed7f9178d9c5a80d8'], ]), ], ]), From 5b62aca70cbdd8f5157c46e2071b23cf29941cfe Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Wed, 12 Apr 2023 14:11:37 +0200 Subject: [PATCH 27/41] assert closeLending input --- src/hooks/actionHooks/useClosePosition.ts | 4 ++-- src/hooks/actionHooks/useLend.ts | 2 +- src/hooks/viewHelperHooks/useBorrowHelpers.ts | 8 ++++---- 3 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/hooks/actionHooks/useClosePosition.ts b/src/hooks/actionHooks/useClosePosition.ts index 90124cc6e..dd433735e 100644 --- a/src/hooks/actionHooks/useClosePosition.ts +++ b/src/hooks/actionHooks/useClosePosition.ts @@ -123,8 +123,8 @@ export const useClosePosition = () => { base.address, encodeBalanceCall(base.address, base.tokenIdentifier), AssertActions.Fn.ASSERT_EQ_REL, - base.balance.add(series.fyTokenBalance!), - WAD_BN.mul('10') // 10% relative tolerance + base.balance.add(_input), + WAD_BN.div('10') // 10% relative tolerance ); const calls: ICallData[] = [ diff --git a/src/hooks/actionHooks/useLend.ts b/src/hooks/actionHooks/useLend.ts index 1ba391057..8bd1226e3 100644 --- a/src/hooks/actionHooks/useLend.ts +++ b/src/hooks/actionHooks/useLend.ts @@ -106,7 +106,7 @@ export const useLend = () => { encodeBalanceCall(series.fyTokenContract.address, undefined), AssertActions.Fn.ASSERT_EQ_REL, series.fyTokenBalance!.add(_inputAsFyToken), - WAD_BN.mul('10') // 10% relative tolerance + WAD_BN.div('10') // 10% relative tolerance ); const calls: ICallData[] = [ diff --git a/src/hooks/viewHelperHooks/useBorrowHelpers.ts b/src/hooks/viewHelperHooks/useBorrowHelpers.ts index 36a7d8a47..4fc34773d 100644 --- a/src/hooks/viewHelperHooks/useBorrowHelpers.ts +++ b/src/hooks/viewHelperHooks/useBorrowHelpers.ts @@ -163,12 +163,12 @@ export const useBorrowHelpers = ( futureSeries.mu ); - const _minCollat = calculateMinCollateral( - assetPairInfo?.pairPrice!, + const _minCollat = assetPairInfo ? calculateMinCollateral( + assetPairInfo.pairPrice, newDebt, - assetPairInfo?.minRatio.toString()!, + assetPairInfo.minRatio.toString()!, undefined - ); + ): ZERO_BN diagnostics && console.log('min Collat of roll to series', _minCollat.toString()); /* SET MAX ROLL */ From 7abed058e990e0ab3f4b544d9e6fecdc31315bef Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Wed, 12 Apr 2023 14:24:20 +0200 Subject: [PATCH 28/41] bugfix/AssertAddLiquidity --- src/hooks/actionHooks/useAddLiquidity.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/hooks/actionHooks/useAddLiquidity.ts b/src/hooks/actionHooks/useAddLiquidity.ts index 874f4eb04..fad57d264 100644 --- a/src/hooks/actionHooks/useAddLiquidity.ts +++ b/src/hooks/actionHooks/useAddLiquidity.ts @@ -239,7 +239,7 @@ export const useAddLiquidity = () => { encodeBalanceCall(strategy.address, undefined), AssertActions.Fn.ASSERT_EQ_REL, strategy.accountBalance!.add(_input), - WAD_BN.mul('10') // 10% relative tolerance + WAD_BN.div('10') // 10% relative tolerance ); /** From ddbbc5210623fdd44156d87bbd3adeec3127bdd3 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Wed, 12 Apr 2023 14:40:05 +0200 Subject: [PATCH 29/41] bugfix/ removeLiq div not mul --- src/hooks/actionHooks/useRemoveCollateral.ts | 1 - src/hooks/actionHooks/useRemoveLiquidity.ts | 4 ++-- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/src/hooks/actionHooks/useRemoveCollateral.ts b/src/hooks/actionHooks/useRemoveCollateral.ts index 11b3d669d..98d8db69a 100644 --- a/src/hooks/actionHooks/useRemoveCollateral.ts +++ b/src/hooks/actionHooks/useRemoveCollateral.ts @@ -44,7 +44,6 @@ export const useRemoveCollateral = () => { if (!contracts) return; if (!isActionAllowed(ActionCodes.REMOVE_COLLATERAL)) return; // return if action is not allowed - /* generate the txCode for tx tracking and tracing */ const txCode = getTxCode(ActionCodes.REMOVE_COLLATERAL, vault.id); diff --git a/src/hooks/actionHooks/useRemoveLiquidity.ts b/src/hooks/actionHooks/useRemoveLiquidity.ts index 26a198248..96af2a595 100644 --- a/src/hooks/actionHooks/useRemoveLiquidity.ts +++ b/src/hooks/actionHooks/useRemoveLiquidity.ts @@ -304,7 +304,7 @@ export const useRemoveLiquidity = () => { encodeBalanceCall(_base.address, _base.tokenIdentifier), AssertActions.Fn.ASSERT_EQ_REL, _base.balance!.add(series.getBase(_sharesReceived)), - WAD_BN.mul('10') // 10% relative tolerance + WAD_BN.div('10') // 10% relative tolerance ); /* Add in an Assert call : Base received + fyToken received within 10% of strategy tokens held. */ const assertCallData_fyToken: ICallData[] = _fyTokenReceived.gt(ZERO_BN) @@ -313,7 +313,7 @@ export const useRemoveLiquidity = () => { encodeBalanceCall(series.address, undefined), AssertActions.Fn.ASSERT_EQ_REL, series.fyTokenBalance!.add(_fyTokenReceived), - WAD_BN.mul('10') // 10% relative tolerance + WAD_BN.div('10') // 10% relative tolerance ) : []; From 5a8b9b649f37c5badbc1a562f3c4ff5695e0b1f4 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Wed, 12 Apr 2023 15:25:06 +0200 Subject: [PATCH 30/41] bugfix/useRepayAssert --- src/hooks/actionHooks/useRepayDebt.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/hooks/actionHooks/useRepayDebt.ts b/src/hooks/actionHooks/useRepayDebt.ts index d6b5ca7f5..acb7ea0bb 100644 --- a/src/hooks/actionHooks/useRepayDebt.ts +++ b/src/hooks/actionHooks/useRepayDebt.ts @@ -171,7 +171,7 @@ export const useRepayDebt = () => { * - Users ilk balance increases by ilk amount> if repaying all debt AND removing all collateral * - vault debt reduced by input amount > if repaying part debt */ - const assertCallData: ICallData[] = reclaimCollateral + const assertCallData: ICallData[] = _collateralToRemove !== ZERO_BN ? assert( ilk.address, encodeBalanceCall(ilk.address, ilk.tokenIdentifier), @@ -183,7 +183,7 @@ export const useRepayDebt = () => { cauldron.interface.encodeFunctionData('balances', [vault.id]), AssertActions.Fn.ASSERT_EQ_REL, vault.accruedArt.sub(_input), - WAD_BN.mul('10') // 10% relative tolerance + WAD_BN.div('10') // 10% relative tolerance ); const calls: ICallData[] = [ From 45267471d6158442b9518ca6bf2763732faa3fcc Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Wed, 12 Apr 2023 15:33:46 +0200 Subject: [PATCH 31/41] bugfix/swap out div for mul --- src/hooks/actionHooks/useRollDebt.ts | 2 +- src/hooks/actionHooks/useRollPosition.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/hooks/actionHooks/useRollDebt.ts b/src/hooks/actionHooks/useRollDebt.ts index fdf530b35..f812491ab 100644 --- a/src/hooks/actionHooks/useRollDebt.ts +++ b/src/hooks/actionHooks/useRollDebt.ts @@ -46,7 +46,7 @@ export const useRollDebt = () => { cauldron.interface.encodeFunctionData('balances', [vault.id]), AssertActions.Fn.ASSERT_EQ_REL, vault.accruedArt, - WAD_BN.mul('10') // 10% relative tolerance + WAD_BN.div('10') // 10% relative tolerance ); const calls: ICallData[] = [ diff --git a/src/hooks/actionHooks/useRollPosition.ts b/src/hooks/actionHooks/useRollPosition.ts index 31b5087ce..073f38af3 100644 --- a/src/hooks/actionHooks/useRollPosition.ts +++ b/src/hooks/actionHooks/useRollPosition.ts @@ -129,7 +129,7 @@ export const useRollPosition = () => { encodeBalanceCall(toSeries.address, undefined), AssertActions.Fn.ASSERT_EQ_REL, fromSeries.fyTokenBalance!, - WAD_BN.mul('10') // 10% relative tolerance + WAD_BN.div('10') // 10% relative tolerance ); /* Reciever of transfer (based on maturity) the series maturity */ From b73958abf0d2a9e75cb4c24584099570e8b3fb96 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Tue, 18 Apr 2023 12:34:41 +0100 Subject: [PATCH 32/41] updated assert still --- src/hooks/actionHooks/useAddCollateral.ts | 20 ++++++++++++++------ src/hooks/actionHooks/useAssert.ts | 18 ++++++++++-------- src/hooks/useAccountPlus.ts | 6 ++++-- 3 files changed, 28 insertions(+), 16 deletions(-) diff --git a/src/hooks/actionHooks/useAddCollateral.ts b/src/hooks/actionHooks/useAddCollateral.ts index ac2eb386d..c1c747ec7 100644 --- a/src/hooks/actionHooks/useAddCollateral.ts +++ b/src/hooks/actionHooks/useAddCollateral.ts @@ -1,12 +1,12 @@ -import { ethers } from 'ethers'; +import { BigNumber, ethers } from 'ethers'; import { useContext } from 'react'; import { UserContext } from '../../contexts/UserContext'; -import { ICallData, IVault, ActionCodes, LadleActions, IAsset, IHistoryContext } from '../../types'; +import { ICallData, IVault, ActionCodes, LadleActions, IAsset, IHistoryContext, TokenType } from '../../types'; import { cleanValue, getTxCode } from '../../utils/appUtils'; import { BLANK_VAULT, ZERO_BN } from '../../utils/constants'; -import { CONVEX_BASED_ASSETS, ETH_BASED_ASSETS } from '../../config/assets'; +import { CONVEX_BASED_ASSETS, ETH_BASED_ASSETS, WETH } from '../../config/assets'; import { useChain } from '../useChain'; import { useWrapUnwrapAsset } from './useWrapUnwrapAsset'; import { useAddRemoveEth } from './useAddRemoveEth'; @@ -22,9 +22,9 @@ import useAllowAction from '../useAllowAction'; export const useAddCollateral = () => { const { userState, userActions } = useContext(UserContext); - const { selectedBase, selectedIlk, selectedSeries, assetMap } = userState; + const { selectedBase, selectedIlk, selectedSeries, assetMap, } = userState; const { updateAssets, updateVaults } = userActions; - const { address: account } = useAccountPlus(); + const { address: account, nativeBalance } = useAccountPlus(); const contracts = useContracts(); const { @@ -107,11 +107,19 @@ export const useAddCollateral = () => { ); /* Add in an Assert call : collateral(ilk) increases by input amount */ - const assertCallData: ICallData[] = assert( + const assertCallData: ICallData[] = ilk.id !== WETH + ? assert( ilk.address, encodeBalanceCall(ilk.address, ilk.tokenIdentifier), AssertActions.Fn.ASSERT_GE, ilk.balance.add(_input) + ) + : assert( + undefined, + encodeBalanceCall(undefined), + AssertActions.Fn.ASSERT_GE, + (nativeBalance?.value as BigNumber).add(input) + // ilk.balance.add(_input) ); /** diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index bb174fa61..6368afee6 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -40,7 +40,7 @@ export const useAssert = () => { const { address: account } = useAccount(); const { chain } = useNetwork(); - const encodeBalanceCall = (targetAddress: string, tokenIdentifier: string | number | undefined = undefined) => { + const encodeBalanceCall = (targetAddress: string | undefined, tokenIdentifier: string | number | undefined = undefined) => { if (targetAddress) { const abi = tokenIdentifier ? ERC1155__factory.abi : erc20ABI; const args = tokenIdentifier ? [account, tokenIdentifier] : [account]; @@ -53,7 +53,7 @@ export const useAssert = () => { }; const assert = ( - address: string, + address: string | undefined, encodedCallBytes: string, assertFn: AssertActions.Fn, expectedVal: BigNumber, @@ -61,17 +61,19 @@ export const useAssert = () => { ignoreIf: boolean = false ): ICallData[] => { if (!contracts) return []; - - const AssertContract = contracts.get(ContractNames.ASSERT) as Assert; - + /* if address == undefined, then use the appropriate multicall contract for the connected chain as the defualt */ + const defaultAddress = chain?.contracts?.multicall3?.address! + + const assertContract = contracts.get(ContractNames.ASSERT) as Assert; + return [ { operation: LadleActions.Fn.ROUTE, args: relOrAbsVal.gt(ZERO_BN) - ? [address, encodedCallBytes, expectedVal, relOrAbsVal] - : [address, encodedCallBytes, expectedVal], + ? [address || defaultAddress, encodedCallBytes, expectedVal, relOrAbsVal] + : [address || defaultAddress, encodedCallBytes, expectedVal], fnName: assertFn, - targetContract: AssertContract, + targetContract: assertContract, ignoreIf, }, ]; diff --git a/src/hooks/useAccountPlus.ts b/src/hooks/useAccountPlus.ts index 5296c8a0c..f4cf63518 100644 --- a/src/hooks/useAccountPlus.ts +++ b/src/hooks/useAccountPlus.ts @@ -1,5 +1,5 @@ import { useContext, useMemo } from 'react'; -import { useAccount } from 'wagmi'; +import { useAccount, useBalance } from 'wagmi'; import { SettingsContext } from '../contexts/SettingsContext'; /** @@ -7,13 +7,15 @@ import { SettingsContext } from '../contexts/SettingsContext'; * @returns mockUserAddress input when using mocked data, else simply the wagmi useAccount hook address */ const useAccountPlus = () => { + const { settingsState: { useMockedUser, mockUserAddress }, } = useContext(SettingsContext); const { address } = useAccount(); + const {data:nativeBalance} = useBalance({address}); return useMemo( - () => (useMockedUser ? { address: mockUserAddress } : { address }), + () => (useMockedUser ? { address: mockUserAddress, nativeBalance } : { address, nativeBalance }), [address, mockUserAddress, useMockedUser] ); }; From 43bf3180eef7eed9c6d3e3838fea44a5a982a1d5 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 09:46:02 +0100 Subject: [PATCH 33/41] number of tweaks:temp remove addCollateral assert --- .env.local | 4 ++-- src/config/assets.ts | 1 - src/hooks/actionHooks/useAddCollateral.ts | 23 ++++++++--------------- src/hooks/actionHooks/useAssert.ts | 4 +++- 4 files changed, 13 insertions(+), 19 deletions(-) diff --git a/.env.local b/.env.local index 45f6e78ac..20d00a582 100644 --- a/.env.local +++ b/.env.local @@ -1,7 +1,7 @@ REACT_APP_DEFAULT_CHAINID=42161 REACT_APP_VERSION=$npm_package_version -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/f6e50db3-ab83-44fb-a94a-68b5b49628ef' +REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/9fef86c8-29d0-448e-8c7a-a430b4429a71' REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' TENDERLY_USER='Yield' @@ -18,4 +18,4 @@ ALLOWED_SUPPORT_ADDRESSES='0x1Bd3Abb6ef058408734EA01cA81D325039cd7bcA, ' KILLSWITCH_ACTIVE=false KILLSWITCH_CHAIN=1 -KILLSWITCH_TEXT='Due to an Euler Finance security incident, we are suspending UI interaction with the Yield Protocol until we have fully assessed the implications of the breach' +KILLSWITCH_TEXT='Due to an incident, we are suspending UI interaction with the Yield Protocol until we have fully assessed the implications of the breach' diff --git a/src/config/assets.ts b/src/config/assets.ts index 290ef7d24..d226c4d8a 100644 --- a/src/config/assets.ts +++ b/src/config/assets.ts @@ -12,7 +12,6 @@ export interface AssetStaticInfo { digitFormat: number; // this is the 'reasonable' number of digits to show. accuracy equivalent to +- 1 us cent. tokenRoles: TokenRole[]; - // optionals // isYieldBase?: boolean; diff --git a/src/hooks/actionHooks/useAddCollateral.ts b/src/hooks/actionHooks/useAddCollateral.ts index c1c747ec7..344372ffe 100644 --- a/src/hooks/actionHooks/useAddCollateral.ts +++ b/src/hooks/actionHooks/useAddCollateral.ts @@ -107,20 +107,13 @@ export const useAddCollateral = () => { ); /* Add in an Assert call : collateral(ilk) increases by input amount */ - const assertCallData: ICallData[] = ilk.id !== WETH - ? assert( - ilk.address, - encodeBalanceCall(ilk.address, ilk.tokenIdentifier), - AssertActions.Fn.ASSERT_GE, - ilk.balance.add(_input) - ) - : assert( - undefined, - encodeBalanceCall(undefined), - AssertActions.Fn.ASSERT_GE, - (nativeBalance?.value as BigNumber).add(input) - // ilk.balance.add(_input) - ); + // const assertCallData: ICallData[] = assert( + // // ilk?.address, + // // // ilk.address, // if WETH, we don't pass address so that the native balance is read. + // // // encodeBalanceCall(ilk.address, ilk.tokenIdentifier), + // // // AssertActions.Fn.ASSERT_GE, + // // // ilk.balance.add(_input) + // ); /** * BUILD CALL DATA ARRAY @@ -158,7 +151,7 @@ export const useAddCollateral = () => { }, /* handle any assert at end of tx */ - ...assertCallData, + // ...assertCallData, ]; /* TRANSACT */ diff --git a/src/hooks/actionHooks/useAssert.ts b/src/hooks/actionHooks/useAssert.ts index 6368afee6..c38ed52d0 100644 --- a/src/hooks/actionHooks/useAssert.ts +++ b/src/hooks/actionHooks/useAssert.ts @@ -41,12 +41,14 @@ export const useAssert = () => { const { chain } = useNetwork(); const encodeBalanceCall = (targetAddress: string | undefined, tokenIdentifier: string | number | undefined = undefined) => { + if (targetAddress) { const abi = tokenIdentifier ? ERC1155__factory.abi : erc20ABI; const args = tokenIdentifier ? [account, tokenIdentifier] : [account]; const assetContract_ = new Contract(targetAddress, abi); return assetContract_.interface.encodeFunctionData('balanceOf', args); } + /* if no address provided, assume the balance is the native balance and get the users ETH balance via a multical3 contract */ const contract_ = new Contract(chain?.contracts?.multicall3?.address!, multiCallFragment); return contract_.interface.encodeFunctionData('getEthBalance', [account]); // this calls the helper contract -> because we are looking for an ETH/Native balance; @@ -61,9 +63,9 @@ export const useAssert = () => { ignoreIf: boolean = false ): ICallData[] => { if (!contracts) return []; + /* if address == undefined, then use the appropriate multicall contract for the connected chain as the defualt */ const defaultAddress = chain?.contracts?.multicall3?.address! - const assertContract = contracts.get(ContractNames.ASSERT) as Assert; return [ From cf7b5808418355460272008819407a87cc528bc5 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 09:57:12 +0100 Subject: [PATCH 34/41] bugfix: eth borrow --- src/hooks/actionHooks/useAddCollateral.ts | 5 ---- src/hooks/actionHooks/useBorrow.ts | 30 +++++++++++++++-------- 2 files changed, 20 insertions(+), 15 deletions(-) diff --git a/src/hooks/actionHooks/useAddCollateral.ts b/src/hooks/actionHooks/useAddCollateral.ts index 344372ffe..d0f34aca0 100644 --- a/src/hooks/actionHooks/useAddCollateral.ts +++ b/src/hooks/actionHooks/useAddCollateral.ts @@ -108,11 +108,6 @@ export const useAddCollateral = () => { /* Add in an Assert call : collateral(ilk) increases by input amount */ // const assertCallData: ICallData[] = assert( - // // ilk?.address, - // // // ilk.address, // if WETH, we don't pass address so that the native balance is read. - // // // encodeBalanceCall(ilk.address, ilk.tokenIdentifier), - // // // AssertActions.Fn.ASSERT_GE, - // // // ilk.balance.add(_input) // ); /** diff --git a/src/hooks/actionHooks/useBorrow.ts b/src/hooks/actionHooks/useBorrow.ts index 5dc3b28a4..1c8933d9a 100644 --- a/src/hooks/actionHooks/useBorrow.ts +++ b/src/hooks/actionHooks/useBorrow.ts @@ -32,7 +32,7 @@ export const useBorrow = () => { const { userState, userActions } = useContext(UserContext); const { selectedBase, selectedIlk, selectedSeries, seriesMap, assetMap } = userState; const { updateVaults, updateAssets, updateSeries } = userActions; - const { address: account } = useAccountPlus(); + const { address: account, nativeBalance } = useAccountPlus(); const contracts = useContracts(); const { refetch: refetchIlkBal } = useBalance({ @@ -52,13 +52,12 @@ export const useBorrow = () => { const { sign, transact } = useChain(); const { getTimeTillMaturity } = useTimeTillMaturity(); - const {isActionAllowed} = useAllowAction(); + const { isActionAllowed } = useAllowAction(); const borrow = async (vault: IVault | undefined, input: string | undefined, collInput: string | undefined) => { if (!contracts) return; if (!isActionAllowed(ActionCodes.BORROW)) return; // return if action is not allowed - /* generate the reproducible txCode for tx tracking and tracing */ const txCode = getTxCode(ActionCodes.BORROW, selectedSeries?.id!); /* use the vault id provided OR 0 if new/ not provided */ @@ -131,13 +130,24 @@ export const useBorrow = () => { ); /* Add in an Assert call */ - const assertCallData: ICallData[] = assert( - base.address, - encodeBalanceCall(base.address, base.tokenIdentifier), - AssertActions.Fn.ASSERT_EQ_REL, // relative here - base.balance.add(_input), - WAD_BN - ); + const assertCallData: ICallData[] = + base.id === WETH && nativeBalance + ? assert( + // if base is WETH, check the native balance increase + undefined, + encodeBalanceCall(undefined), + AssertActions.Fn.ASSERT_EQ_REL, // relative here + nativeBalance.value.add(_input), + WAD_BN + ) + : assert( + // else check the token balance + base.address, + encodeBalanceCall(base.address, base.tokenIdentifier), + AssertActions.Fn.ASSERT_EQ_REL, // relative here + base.balance.add(_input), + WAD_BN + ); /* if ETH is being borrowed, send the borrowed tokens (WETH) to ladle for unwrapping */ const serveToAddress = () => { From ec372b4cdbf52bf8c5477967f47e09e43e12f9ef Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 09:58:56 +0100 Subject: [PATCH 35/41] arbitrum fork --- .env.local | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.env.local b/.env.local index 20d00a582..f6f6c776c 100644 --- a/.env.local +++ b/.env.local @@ -1,7 +1,7 @@ REACT_APP_DEFAULT_CHAINID=42161 REACT_APP_VERSION=$npm_package_version -REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/9fef86c8-29d0-448e-8c7a-a430b4429a71' +REACT_APP_DEFAULT_FORK_RPC_URL='https://rpc.tenderly.co/fork/90a229c1-7aef-4d13-a897-24e14b070508' REACT_APP_LOCALHOST_RPC_URL='http://127.0.0.1:8545' TENDERLY_USER='Yield' From d1b36a966366ab0a507e4124a4ddbefeb1f8294b Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 10:01:06 +0100 Subject: [PATCH 36/41] bugfix: close handle ETH --- src/hooks/actionHooks/useClosePosition.ts | 28 +++++++++++++++-------- 1 file changed, 19 insertions(+), 9 deletions(-) diff --git a/src/hooks/actionHooks/useClosePosition.ts b/src/hooks/actionHooks/useClosePosition.ts index dd433735e..7f46f7418 100644 --- a/src/hooks/actionHooks/useClosePosition.ts +++ b/src/hooks/actionHooks/useClosePosition.ts @@ -2,7 +2,7 @@ import { ethers } from 'ethers'; import { useContext } from 'react'; import { buyBase, calculateSlippage, WAD_BN } from '@yield-protocol/ui-math'; -import { ETH_BASED_ASSETS } from '../../config/assets'; +import { ETH_BASED_ASSETS, WETH } from '../../config/assets'; import { HistoryContext } from '../../contexts/HistoryContext'; import { SettingsContext } from '../../contexts/SettingsContext'; import { UserContext } from '../../contexts/UserContext'; @@ -28,7 +28,7 @@ export const useClosePosition = () => { const { userState, userActions } = useContext(UserContext); const { assetMap, selectedSeries, selectedBase } = userState; - const { address: account } = useAccountPlus(); + const { address: account, nativeBalance } = useAccountPlus(); const { refetch: refetchFyTokenBal } = useBalance({ address: account, token: selectedSeries?.address as Address, @@ -119,13 +119,23 @@ export const useClosePosition = () => { const removeEthCallData = isEthBase ? removeEth(ONE_BN) : []; /* Add in an Assert call : base Balance increases up to 10% of fyToken balance */ - const assertCallData: ICallData[] = assert( - base.address, - encodeBalanceCall(base.address, base.tokenIdentifier), - AssertActions.Fn.ASSERT_EQ_REL, - base.balance.add(_input), - WAD_BN.div('10') // 10% relative tolerance - ); + const assertCallData: ICallData[] = + base.id === WETH && nativeBalance + ? assert( + // if base is WETH, check the native balance increase + undefined, + encodeBalanceCall(undefined), + AssertActions.Fn.ASSERT_EQ_REL, // relative here + nativeBalance.value.add(_input), + WAD_BN.div('10') + ) + : assert( + base.address, + encodeBalanceCall(base.address, base.tokenIdentifier), + AssertActions.Fn.ASSERT_EQ_REL, + base.balance.add(_input), + WAD_BN.div('10') // 10% relative tolerance + ); const calls: ICallData[] = [ ...permitCallData, From 03ab05286aa5da96864b2d0631fb04d98546c933 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 10:03:44 +0100 Subject: [PATCH 37/41] remove assert from remove collateral --- src/hooks/actionHooks/useRemoveCollateral.ts | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/src/hooks/actionHooks/useRemoveCollateral.ts b/src/hooks/actionHooks/useRemoveCollateral.ts index 98d8db69a..cfe886762 100644 --- a/src/hooks/actionHooks/useRemoveCollateral.ts +++ b/src/hooks/actionHooks/useRemoveCollateral.ts @@ -20,7 +20,7 @@ import useAllowAction from '../useAllowAction'; export const useRemoveCollateral = () => { const { userState, userActions } = useContext(UserContext); const { selectedIlk, assetMap } = userState; - const { address: account } = useAccountPlus(); + const { address: account, nativeBalance } = useAccountPlus(); const { chain } = useNetwork(); const provider = useProvider(); const contracts = useContracts(); @@ -76,12 +76,12 @@ export const useRemoveCollateral = () => { }; /* Add in an Assert call : collateral(ilk) decreases by input amount */ - const assertCallData: ICallData[] = assert( - ilk.address, - encodeBalanceCall(ilk.address, ilk.tokenIdentifier), - AssertActions.Fn.ASSERT_GE, - ilk.balance.sub(_input) - ); + // const assertCallData: ICallData[] = assert( + // ilk.address, + // encodeBalanceCall(ilk.address, ilk.tokenIdentifier), + // AssertActions.Fn.ASSERT_GE, + // ilk.balance.sub(_input) + // ); const calls: ICallData[] = [ /* convex-type collateral; ensure checkpoint before giving collateral back to account */ @@ -105,7 +105,7 @@ export const useRemoveCollateral = () => { ...removeEthCallData, ...unwrapCallData, - ...assertCallData, + // ...assertCallData, ]; await transact(calls, txCode); From 0c39222e7ca035395baf2d62654499779f5593b4 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 10:20:59 +0100 Subject: [PATCH 38/41] refactor: collate all possible asserts --- src/hooks/actionHooks/useAddCollateral.ts | 11 +++++++++-- src/hooks/actionHooks/useAddLiquidity.ts | 1 - src/hooks/actionHooks/useBorrow.ts | 2 +- src/hooks/actionHooks/useClosePosition.ts | 2 +- src/hooks/actionHooks/useRemoveCollateral.ts | 9 +++++---- src/hooks/actionHooks/useRemoveLiquidity.ts | 1 + 6 files changed, 17 insertions(+), 9 deletions(-) diff --git a/src/hooks/actionHooks/useAddCollateral.ts b/src/hooks/actionHooks/useAddCollateral.ts index d0f34aca0..927f0e509 100644 --- a/src/hooks/actionHooks/useAddCollateral.ts +++ b/src/hooks/actionHooks/useAddCollateral.ts @@ -10,7 +10,7 @@ import { CONVEX_BASED_ASSETS, ETH_BASED_ASSETS, WETH } from '../../config/assets import { useChain } from '../useChain'; import { useWrapUnwrapAsset } from './useWrapUnwrapAsset'; import { useAddRemoveEth } from './useAddRemoveEth'; -import { ConvexLadleModule } from '../../contracts'; +import { Cauldron, ConvexLadleModule } from '../../contracts'; import { ModuleActions } from '../../types/operations'; import { HistoryContext } from '../../contexts/HistoryContext'; import { Address, useBalance } from 'wagmi'; @@ -35,7 +35,7 @@ export const useAddCollateral = () => { const { wrapAsset } = useWrapUnwrapAsset(); const { addEth } = useAddRemoveEth(); - const { assert, encodeBalanceCall } = useAssert(); + const { assert } = useAssert(); const {isActionAllowed} = useAllowAction(); const { refetch: refetchBaseBal } = useBalance({ @@ -57,7 +57,9 @@ export const useAddCollateral = () => { /* set the ilk based on if a vault has been selected or it's a new vault */ const ilk: IAsset | null | undefined = vault ? assetMap?.get(vault.ilkId)! : selectedIlk!; const base: IAsset | null | undefined = vault ? assetMap?.get(vault.baseId) : selectedBase; + const ladleAddress = contracts.get(ContractNames.LADLE)?.address; + const cauldron = contracts.get(ContractNames.CAULDRON) as Cauldron; /* generate the reproducible txCode for tx tracking and tracing */ const txCode = getTxCode(ActionCodes.ADD_COLLATERAL, vaultId); @@ -108,6 +110,11 @@ export const useAddCollateral = () => { /* Add in an Assert call : collateral(ilk) increases by input amount */ // const assertCallData: ICallData[] = assert( + // cauldron.address, + // cauldron.interface.encodeFunctionData('balances', [vaultId]), + // AssertActions.Fn.ASSERT_EQ_REL, + // currentArt.add(input), + // WAD_BN.div('10') // 10% relative tolerance // ); /** diff --git a/src/hooks/actionHooks/useAddLiquidity.ts b/src/hooks/actionHooks/useAddLiquidity.ts index fad57d264..e859b8c4a 100644 --- a/src/hooks/actionHooks/useAddLiquidity.ts +++ b/src/hooks/actionHooks/useAddLiquidity.ts @@ -249,7 +249,6 @@ export const useAddLiquidity = () => { ...permitCallData, /* addETh calldata */ - ...addEthCallData(), /** diff --git a/src/hooks/actionHooks/useBorrow.ts b/src/hooks/actionHooks/useBorrow.ts index 1c8933d9a..7e056de23 100644 --- a/src/hooks/actionHooks/useBorrow.ts +++ b/src/hooks/actionHooks/useBorrow.ts @@ -131,7 +131,7 @@ export const useBorrow = () => { /* Add in an Assert call */ const assertCallData: ICallData[] = - base.id === WETH && nativeBalance + isEthBase && nativeBalance ? assert( // if base is WETH, check the native balance increase undefined, diff --git a/src/hooks/actionHooks/useClosePosition.ts b/src/hooks/actionHooks/useClosePosition.ts index 7f46f7418..6836d403c 100644 --- a/src/hooks/actionHooks/useClosePosition.ts +++ b/src/hooks/actionHooks/useClosePosition.ts @@ -120,7 +120,7 @@ export const useClosePosition = () => { /* Add in an Assert call : base Balance increases up to 10% of fyToken balance */ const assertCallData: ICallData[] = - base.id === WETH && nativeBalance + isEthBase && nativeBalance ? assert( // if base is WETH, check the native balance increase undefined, diff --git a/src/hooks/actionHooks/useRemoveCollateral.ts b/src/hooks/actionHooks/useRemoveCollateral.ts index cfe886762..8ff4ff50b 100644 --- a/src/hooks/actionHooks/useRemoveCollateral.ts +++ b/src/hooks/actionHooks/useRemoveCollateral.ts @@ -77,10 +77,11 @@ export const useRemoveCollateral = () => { /* Add in an Assert call : collateral(ilk) decreases by input amount */ // const assertCallData: ICallData[] = assert( - // ilk.address, - // encodeBalanceCall(ilk.address, ilk.tokenIdentifier), - // AssertActions.Fn.ASSERT_GE, - // ilk.balance.sub(_input) + // cauldron.address, + // cauldron.interface.encodeFunctionData('balances', [vaultId]), + // AssertActions.Fn.ASSERT_EQ_REL, + // currentIlk.balance.sub(_input), + // WAD_BN.div('10') // ); const calls: ICallData[] = [ diff --git a/src/hooks/actionHooks/useRemoveLiquidity.ts b/src/hooks/actionHooks/useRemoveLiquidity.ts index 96af2a595..49dd24181 100644 --- a/src/hooks/actionHooks/useRemoveLiquidity.ts +++ b/src/hooks/actionHooks/useRemoveLiquidity.ts @@ -306,6 +306,7 @@ export const useRemoveLiquidity = () => { _base.balance!.add(series.getBase(_sharesReceived)), WAD_BN.div('10') // 10% relative tolerance ); + /* Add in an Assert call : Base received + fyToken received within 10% of strategy tokens held. */ const assertCallData_fyToken: ICallData[] = _fyTokenReceived.gt(ZERO_BN) ? assert( From e6edea65255ed3386260ab7d7bdcf84e450dd837 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 10:47:54 +0100 Subject: [PATCH 39/41] addRemovalCollateral remove assert.sol :( --- src/hooks/actionHooks/useAddCollateral.ts | 11 ++++++----- src/hooks/actionHooks/useRemoveCollateral.ts | 17 ++++++++++------- 2 files changed, 16 insertions(+), 12 deletions(-) diff --git a/src/hooks/actionHooks/useAddCollateral.ts b/src/hooks/actionHooks/useAddCollateral.ts index 927f0e509..506d0105f 100644 --- a/src/hooks/actionHooks/useAddCollateral.ts +++ b/src/hooks/actionHooks/useAddCollateral.ts @@ -5,7 +5,7 @@ import { UserContext } from '../../contexts/UserContext'; import { ICallData, IVault, ActionCodes, LadleActions, IAsset, IHistoryContext, TokenType } from '../../types'; import { cleanValue, getTxCode } from '../../utils/appUtils'; -import { BLANK_VAULT, ZERO_BN } from '../../utils/constants'; +import { BLANK_VAULT, WAD_BN, ZERO_BN } from '../../utils/constants'; import { CONVEX_BASED_ASSETS, ETH_BASED_ASSETS, WETH } from '../../config/assets'; import { useChain } from '../useChain'; import { useWrapUnwrapAsset } from './useWrapUnwrapAsset'; @@ -109,13 +109,14 @@ export const useAddCollateral = () => { ); /* Add in an Assert call : collateral(ilk) increases by input amount */ - // const assertCallData: ICallData[] = assert( + const assertCallData: ICallData[] = [] ; + // vault ? assert( // cauldron.address, // cauldron.interface.encodeFunctionData('balances', [vaultId]), // AssertActions.Fn.ASSERT_EQ_REL, - // currentArt.add(input), + // vault.ink.add(input), // WAD_BN.div('10') // 10% relative tolerance - // ); + // ) : []; /** * BUILD CALL DATA ARRAY @@ -153,7 +154,7 @@ export const useAddCollateral = () => { }, /* handle any assert at end of tx */ - // ...assertCallData, + ...assertCallData, ]; /* TRANSACT */ diff --git a/src/hooks/actionHooks/useRemoveCollateral.ts b/src/hooks/actionHooks/useRemoveCollateral.ts index 8ff4ff50b..e48c162ae 100644 --- a/src/hooks/actionHooks/useRemoveCollateral.ts +++ b/src/hooks/actionHooks/useRemoveCollateral.ts @@ -7,8 +7,8 @@ import { CONVEX_BASED_ASSETS, ETH_BASED_ASSETS, WETH } from '../../config/assets import { useChain } from '../useChain'; import { useWrapUnwrapAsset } from './useWrapUnwrapAsset'; import { useAddRemoveEth } from './useAddRemoveEth'; -import { ONE_BN, ZERO_BN } from '../../utils/constants'; -import { ConvexJoin__factory } from '../../contracts'; +import { ONE_BN, WAD_BN, ZERO_BN } from '../../utils/constants'; +import { Cauldron, ConvexJoin__factory } from '../../contracts'; import { HistoryContext } from '../../contexts/HistoryContext'; import { Address, useBalance, useNetwork, useProvider } from 'wagmi'; import useContracts from '../useContracts'; @@ -50,6 +50,8 @@ export const useRemoveCollateral = () => { /* get associated series and ilk */ const ilk = assetMap?.get(vault.ilkId)!; const ladleAddress = contracts.get(ContractNames.LADLE)?.address; + const cauldron = contracts.get(ContractNames.CAULDRON) as Cauldron; + /* get unwrap handler if required */ const unwrapHandlerAddress = ilk.unwrapHandlerAddresses?.get(chain?.id!); /* check if the ilk/asset is an eth asset variety OR if it is wrapped token, if so pour to Ladle */ @@ -76,13 +78,14 @@ export const useRemoveCollateral = () => { }; /* Add in an Assert call : collateral(ilk) decreases by input amount */ - // const assertCallData: ICallData[] = assert( + const assertCallData: ICallData[] = []; + // vault ? assert( // cauldron.address, - // cauldron.interface.encodeFunctionData('balances', [vaultId]), + // cauldron.interface.encodeFunctionData('balances', [vault.id]), // AssertActions.Fn.ASSERT_EQ_REL, - // currentIlk.balance.sub(_input), + // vault.ink.sub(_input), // WAD_BN.div('10') - // ); + // ): []; const calls: ICallData[] = [ /* convex-type collateral; ensure checkpoint before giving collateral back to account */ @@ -106,7 +109,7 @@ export const useRemoveCollateral = () => { ...removeEthCallData, ...unwrapCallData, - // ...assertCallData, + ...assertCallData, ]; await transact(calls, txCode); From 5b5edf1b851e6bb07d28ee359bf0593e194c26ee Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 11:16:28 +0100 Subject: [PATCH 40/41] bugfix: repay ETH ilk --- src/hooks/actionHooks/useRepayDebt.ts | 24 ++++++++++++++---------- 1 file changed, 14 insertions(+), 10 deletions(-) diff --git a/src/hooks/actionHooks/useRepayDebt.ts b/src/hooks/actionHooks/useRepayDebt.ts index acb7ea0bb..f4df1ff78 100644 --- a/src/hooks/actionHooks/useRepayDebt.ts +++ b/src/hooks/actionHooks/useRepayDebt.ts @@ -29,7 +29,7 @@ export const useRepayDebt = () => { const { userState, userActions } = useContext(UserContext); const { seriesMap, assetMap, selectedIlk, selectedBase } = userState; const { updateVaults, updateAssets, updateSeries } = userActions; - const { address: account } = useAccountPlus(); + const { address: account, nativeBalance } = useAccountPlus(); const { chain } = useNetwork(); const provider = useProvider(); const contracts = useContracts(); @@ -171,20 +171,24 @@ export const useRepayDebt = () => { * - Users ilk balance increases by ilk amount> if repaying all debt AND removing all collateral * - vault debt reduced by input amount > if repaying part debt */ - const assertCallData: ICallData[] = _collateralToRemove !== ZERO_BN - ? assert( + const assertCallData: ICallData[] = + _collateralToRemove !== ZERO_BN && nativeBalance ? + isEthCollateral + ? assert( + // if base is WETH, check the native balance increase + undefined, + encodeBalanceCall(undefined), + AssertActions.Fn.ASSERT_EQ_REL, // relative here + nativeBalance.value.add(vault.ink), + WAD_BN + ) : + assert( ilk.address, encodeBalanceCall(ilk.address, ilk.tokenIdentifier), AssertActions.Fn.ASSERT_GE, ilk.balance.add(vault.ink) ) - : assert( - cauldron.address, - cauldron.interface.encodeFunctionData('balances', [vault.id]), - AssertActions.Fn.ASSERT_EQ_REL, - vault.accruedArt.sub(_input), - WAD_BN.div('10') // 10% relative tolerance - ); + : []; // currently not handling asserts on partial debt repayments const calls: ICallData[] = [ ...permitCallData, From 017dd4d159ad5e5ee08915c3de56cccb24f0f2b3 Mon Sep 17 00:00:00 2001 From: brucedonovan Date: Mon, 8 May 2023 11:56:51 +0100 Subject: [PATCH 41/41] temp remove fyToken assert.sol --- src/hooks/actionHooks/useRemoveLiquidity.ts | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/src/hooks/actionHooks/useRemoveLiquidity.ts b/src/hooks/actionHooks/useRemoveLiquidity.ts index 49dd24181..f27d47490 100644 --- a/src/hooks/actionHooks/useRemoveLiquidity.ts +++ b/src/hooks/actionHooks/useRemoveLiquidity.ts @@ -57,7 +57,7 @@ is Mature? N +--------+ export const useRemoveLiquidity = () => { const provider = useProvider(); - const { address: account } = useAccountPlus(); + const { address: account, nativeBalance } = useAccountPlus(); const { txActions } = useContext(TxContext); const { resetProcess } = txActions; @@ -299,13 +299,22 @@ export const useRemoveLiquidity = () => { ); /* Add in an Assert call : Base received + fyToken received within 10% of strategy tokens held. */ - const assertCallData_base: ICallData[] = assert( + const assertCallData_base: ICallData[] = + isEthBase && nativeBalance + ? assert( + undefined, + encodeBalanceCall(undefined), + AssertActions.Fn.ASSERT_EQ_REL, + nativeBalance.value.add(series.getBase(_sharesReceived)), + WAD_BN.div('10') // 10% relative tolerance + ): + assert( _base.address, encodeBalanceCall(_base.address, _base.tokenIdentifier), AssertActions.Fn.ASSERT_EQ_REL, _base.balance!.add(series.getBase(_sharesReceived)), WAD_BN.div('10') // 10% relative tolerance - ); + ) /* Add in an Assert call : Base received + fyToken received within 10% of strategy tokens held. */ const assertCallData_fyToken: ICallData[] = _fyTokenReceived.gt(ZERO_BN) @@ -478,7 +487,8 @@ export const useRemoveLiquidity = () => { ...removeEthCallData, ...assertCallData_base, - ...assertCallData_fyToken, + // ...assertCallData_fyToken, temporarily remove fyToken check + ]; await transact(calls, txCode);