diff --git a/.gitignore b/.gitignore index d5b3b197..39a6c8a6 100644 --- a/.gitignore +++ b/.gitignore @@ -7,6 +7,5 @@ target *.env !*/.sample.env *types/* -*/contracts.json -contracts.json -deploy-scripts/vesting/fluid_vesting_team_and_investors_test.csv +*contracts.json +deploy-scripts/vesting/**/*.csv diff --git a/Cargo.lock b/Cargo.lock index 2d806382..f86c4664 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -239,9 +239,9 @@ checksum = "155a5a185e42c6b77ac7b88a15143d930a9e9727a5b7b77eed417404ab15c247" [[package]] name = "async-graphql" -version = "7.0.7" +version = "7.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b76aba2f176af685c2229633881a3adeae51f87ae1811781e73910b7001c93e" +checksum = "0ba6d24703c5adc5ba9116901b92ee4e4c0643c01a56c4fd303f3818638d7449" dependencies = [ "async-graphql-derive", "async-graphql-parser", @@ -251,6 +251,7 @@ dependencies = [ "base64 0.22.1", "bytes", "fnv", + "futures-timer", "futures-util", "http 1.1.0", "indexmap 2.2.6", @@ -271,9 +272,9 @@ dependencies = [ [[package]] name = "async-graphql-derive" -version = "7.0.7" +version = "7.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "72e2e26a6b44bc61df3ca8546402cf9204c28e30c06084cc8e75cd5e34d4f150" +checksum = "a94c2d176893486bd37cd1b6defadd999f7357bf5804e92f510c08bcf16c538f" dependencies = [ "Inflector", "async-graphql-parser", @@ -288,9 +289,9 @@ dependencies = [ [[package]] name = "async-graphql-parser" -version = "7.0.7" +version = "7.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f801451484b4977d6fe67b29030f81353cabdcbb754e5a064f39493582dac0cf" +checksum = "79272bdbf26af97866e149f05b2b546edb5c00e51b5f916289931ed233e208ad" dependencies = [ "async-graphql-value", "pest", @@ -300,9 +301,9 @@ dependencies = [ [[package]] name = "async-graphql-value" -version = "7.0.7" +version = "7.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69117c43c01d81a69890a9f5dd6235f2f027ca8d1ec62d6d3c5e01ca0edb4f2b" +checksum = "ef5ec94176a12a8cbe985cd73f2e54dc9c702c88c766bdef12f1f3a67cedbee1" dependencies = [ "bytes", "indexmap 2.2.6", @@ -451,7 +452,7 @@ dependencies = [ "sync_wrapper", "tokio", "tower", - "tower-http", + "tower-http 0.3.5", "tower-layer", "tower-service", ] @@ -530,21 +531,6 @@ version = "0.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d86b93f97252c47b41663388e6d155714a9d0c398b99f1005cbc5f978b29f445" -[[package]] -name = "bit-set" -version = "0.5.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0700ddab506f33b20a03b13996eccd309a48e5ff77d0d95926aa0210fb4e95f1" -dependencies = [ - "bit-vec", -] - -[[package]] -name = "bit-vec" -version = "0.6.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "349f9b6a179ed607305526ca489b34ad0a41aed5f7980fa90eb03160b69598fb" - [[package]] name = "bitflags" version = "1.3.2" @@ -1155,6 +1141,27 @@ dependencies = [ "subtle", ] +[[package]] +name = "csv" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac574ff4d437a7b5ad237ef331c17ccca63c46479e5b5453eb8e10bb99a759fe" +dependencies = [ + "csv-core", + "itoa", + "ryu", + "serde", +] + +[[package]] +name = "csv-core" +version = "0.1.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5efa2b3d7902f4b634a20cae3c9c4e6209dc4779feb6863329607560143efa70" +dependencies = [ + "memchr", +] + [[package]] name = "ctr" version = "0.9.2" @@ -1340,6 +1347,7 @@ dependencies = [ name = "deploy-scripts" version = "0.0.0" dependencies = [ + "csv", "dotenv", "fuels", "futures", @@ -1347,6 +1355,7 @@ dependencies = [ "pbr", "serde", "serde_json", + "tai64", "test-utils", "tokio", ] @@ -1670,9 +1679,9 @@ dependencies = [ [[package]] name = "eventsource-client" -version = "0.12.2" +version = "0.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c80c6714d1a380314fcb11a22eeff022e1e1c9642f0bb54e15dc9cb29f37b29" +checksum = "43ddc25e1ad2cc0106d5e2d967397b4fb2068a66677ee9b0eea4600e5cfe8fb4" dependencies = [ "futures", "hyper", @@ -1721,6 +1730,12 @@ dependencies = [ "static_assertions", ] +[[package]] +name = "fixedbitset" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ce7134b9999ecaf8bcd65542e436736ef32ddca1b3e06094cb6ec5755203b80" + [[package]] name = "float-cmp" version = "0.9.0" @@ -1793,25 +1808,50 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "122c27ab46707017063bf1c6e0b4f3de881e22e81b4059750a0dc95033d9cc26" dependencies = [ "bitflags 2.6.0", - "fuel-types", + "fuel-types 0.56.0", + "serde", + "strum 0.24.1", +] + +[[package]] +name = "fuel-asm" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f325971bf9047ec70004f80a989e03456316bc19cbef3ff3a39a38b192ab56e" +dependencies = [ + "bitflags 2.6.0", + "fuel-types 0.58.2", "serde", "strum 0.24.1", ] +[[package]] +name = "fuel-compression" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "24e42841f56f76ed759b3f516e5188d5c42de47015bee951651660c13b6dfa6c" +dependencies = [ + "fuel-derive 0.58.2", + "fuel-types 0.58.2", + "serde", +] + [[package]] name = "fuel-core" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "023265fe375de17c0ad26ae5d01feb4841653524deab82cbc70979ea5d346b94" +checksum = "9d5873aa1178f6fafdd967ddee2214a78be8be0c612a9c695889d31b5c1ede44" dependencies = [ "anyhow", "async-graphql", + "async-graphql-value", "async-trait", "axum", "clap", "derive_more", "enum-iterator", "fuel-core-chain-config", + "fuel-core-compression", "fuel-core-consensus-module", "fuel-core-database", "fuel-core-executor", @@ -1824,14 +1864,14 @@ dependencies = [ "fuel-core-services", "fuel-core-storage", "fuel-core-txpool", - "fuel-core-types", + "fuel-core-types 0.40.0", "fuel-core-upgradable-executor", "futures", "hex", "hyper", "indicatif", "itertools 0.12.1", - "postcard", + "paste", "rand", "serde", "serde_json", @@ -1842,22 +1882,23 @@ dependencies = [ "tokio-rayon", "tokio-stream", "tokio-util", - "tower-http", + "tower", + "tower-http 0.4.4", "tracing", "uuid 1.10.0", ] [[package]] name = "fuel-core-chain-config" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "318a5a9733255cffac64a4b5acf6a7f41e438bec3ead506fc9f74730ce956528" +checksum = "990db3029efd3766c4ae7c92a53c159ae66abf6f568ac6a3d58354f11400e6e2" dependencies = [ "anyhow", "bech32", "derivative", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", "itertools 0.12.1", "postcard", "rand", @@ -1869,15 +1910,16 @@ dependencies = [ [[package]] name = "fuel-core-client" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "03ad219bde52b072a2d828f27072982047a77cc02c953ea7e83c23de586d466d" +checksum = "f09b3a35e82226d77b10653829beb508dc4bcf698fbdaa96610faf894e794444" dependencies = [ "anyhow", + "base64 0.22.1", "cynic", "derive_more", "eventsource-client", - "fuel-core-types", + "fuel-core-types 0.40.0", "futures", "hex", "hyper-rustls", @@ -1891,40 +1933,55 @@ dependencies = [ "tracing", ] +[[package]] +name = "fuel-core-compression" +version = "0.40.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b6ed44f8fcd0f1ff5983510e49835149b39afb8226257f6397db17a0ca0558d" +dependencies = [ + "anyhow", + "fuel-core-types 0.40.0", + "paste", + "rand", + "serde", + "strum 0.25.0", + "strum_macros 0.25.3", +] + [[package]] name = "fuel-core-consensus-module" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e43c7a168ee26efee5fa2fc54e4ba003b386f8f6d1f407db3e5c98bcdec6d0a2" +checksum = "61161b1016ffb1a4f0d629534dd0b165bdaf146ce5037ccd5c8e8c9ec740d52f" dependencies = [ "anyhow", "fuel-core-chain-config", "fuel-core-poa", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", ] [[package]] name = "fuel-core-database" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8e7c0e04807ec39d71910ee1cab9c1f9eb27ee9bf05a3d8788c3db6801c6ac27" +checksum = "ceae011a49cbccb0e9b043c67f7e64dfd2f4d41233de34aff11d23646e98f5d8" dependencies = [ "anyhow", "derive_more", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", ] [[package]] name = "fuel-core-executor" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "061f43f469181ac6991e83458147e3d07a503a23f48e1cedc10ea83e8700d6d8" +checksum = "db57f06af045fafa81b76ca11318d47579e41babb0839fb0955ae7cf32e58a1f" dependencies = [ "anyhow", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", "hex", "parking_lot", "serde", @@ -1933,19 +1990,21 @@ dependencies = [ [[package]] name = "fuel-core-gas-price-service" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "50015fb2a24f21c441a59e4e81e2a5eee3626285784119cf9346be6e37bfe199" +checksum = "eea974f842be1ca7783df7eec770b5865c3babd50a10a5d8f107bdac65419c45" dependencies = [ "anyhow", "async-trait", "enum-iterator", "fuel-core-services", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", "fuel-gas-price-algorithm", "futures", "num_enum", + "parking_lot", + "reqwest", "serde", "strum 0.25.0", "strum_macros 0.25.3", @@ -1957,15 +2016,15 @@ dependencies = [ [[package]] name = "fuel-core-importer" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69fd6d1c72316511bd7c00084f2d8684a736dd57f97f912564d9af8ea13929c9" +checksum = "2a6a75d87da09380dc6f706ec0eb4171cb1309fef6a4c8b709025769a1903235" dependencies = [ "anyhow", "derive_more", "fuel-core-metrics", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", "parking_lot", "rayon", "tokio", @@ -1974,22 +2033,25 @@ dependencies = [ [[package]] name = "fuel-core-metrics" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "88eb1bd81016b49493181b8bc29526678229350a780d4d04db137415028db179" +checksum = "94a1c3eb92040d95d27f7c658801bb5c04ad4aaf67de380cececbeed5aab6e61" dependencies = [ + "once_cell", "parking_lot", "pin-project-lite", "prometheus-client", "regex", + "strum 0.25.0", + "strum_macros 0.25.3", "tracing", ] [[package]] name = "fuel-core-p2p" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fd4d69e535e914be87cb92843d4ac6b7b8b60110364f88efe8e509052368aaa3" +checksum = "db5c996b4d392a5f1991b4d2fcc2fe570dc846f8a763a30105cd7b3c8d08e747" dependencies = [ "anyhow", "async-trait", @@ -1997,9 +2059,10 @@ dependencies = [ "fuel-core-metrics", "fuel-core-services", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", "futures", "hex", + "hickory-resolver", "ip_network", "libp2p", "libp2p-mplex", @@ -2020,16 +2083,16 @@ dependencies = [ [[package]] name = "fuel-core-poa" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ef478ff684ee6c2eac57070322ba05525842670576328414da7fd6c40af4e25" +checksum = "2f6f78fa31dc56b9458e3ca9a7058b4bea381e16e49fcab0db49923be8a30f9c" dependencies = [ "anyhow", "async-trait", "fuel-core-chain-config", "fuel-core-services", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", "serde", "serde_json", "tokio", @@ -2039,15 +2102,15 @@ dependencies = [ [[package]] name = "fuel-core-producer" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "43d09fa42cdfe3c72fe325043e6b7860586d7f34c60baaef9f4a18a13bdcc6f4" +checksum = "7739b2019df5b9d5042ba2d9f7036c6feee105a0e441d8bcfd933221da5be635" dependencies = [ "anyhow", "async-trait", "derive_more", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", "tokio", "tokio-rayon", "tracing", @@ -2055,30 +2118,32 @@ dependencies = [ [[package]] name = "fuel-core-services" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "064b31213ea0b56f6558a0493b264cbd79e060a56de2bd35f8a10d7e78f526fa" +checksum = "8312b598da4b9a6503c9263c1c2a7ea58d34ab1f86e7f345490e12d309fb29bb" dependencies = [ "anyhow", "async-trait", "fuel-core-metrics", "futures", "parking_lot", + "pin-project-lite", + "rayon", "tokio", "tracing", ] [[package]] name = "fuel-core-storage" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f06320744b7d53bc7928d1a40a28fd697191a5b6938a353164231a3423ebdcd9" +checksum = "bda9242ebc9e8ef3251b9eae85f4ce5cdb376348baa30925606f3ce602db7ec5" dependencies = [ "anyhow", "derive_more", "enum-iterator", - "fuel-core-types", - "fuel-vm", + "fuel-core-types 0.40.0", + "fuel-vm 0.58.2", "impl-tools", "itertools 0.12.1", "mockall", @@ -2094,22 +2159,21 @@ dependencies = [ [[package]] name = "fuel-core-txpool" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9deaa3a9b5a2d49bf12fba5af16cc29142d58318eeb5ec8e67258d2dc1ec66ff" +checksum = "34cde90da8d814046018c5341129bffdbc51e6721e69ada9a393b3d4c16be14b" dependencies = [ "anyhow", "async-trait", "derive_more", - "fuel-core-metrics", "fuel-core-services", "fuel-core-storage", - "fuel-core-types", - "mockall", + "fuel-core-types 0.40.0", + "futures", "num-rational", "parking_lot", + "petgraph", "tokio", - "tokio-rayon", "tokio-stream", "tracing", ] @@ -2119,12 +2183,28 @@ name = "fuel-core-types" version = "0.35.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "84fda0c6dc7b3bd24a993b3902f55862b8db0fa6de5b0f1d45f5942bc59792eb" +dependencies = [ + "anyhow", + "derivative", + "derive_more", + "fuel-vm 0.56.0", + "secrecy", + "serde", + "tai64", + "zeroize", +] + +[[package]] +name = "fuel-core-types" +version = "0.40.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ee3a95b189bf729d21354a761862bb481298cbd883550adc3fef1bc7beb0b67" dependencies = [ "anyhow", "bs58", "derivative", "derive_more", - "fuel-vm", + "fuel-vm 0.58.2", "rand", "secrecy", "serde", @@ -2134,15 +2214,15 @@ dependencies = [ [[package]] name = "fuel-core-upgradable-executor" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5c104eb427f63ab720ffa2cd08e35df3064753648ff5dace9853a68f7ae98e1b" +checksum = "620b671cd011ee14c846628ca0d913b770923b36fd87d44dd7ba70f1a8db0eec" dependencies = [ "anyhow", "derive_more", "fuel-core-executor", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.40.0", "fuel-core-wasm-executor", "parking_lot", "postcard", @@ -2152,16 +2232,18 @@ dependencies = [ [[package]] name = "fuel-core-wasm-executor" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5e2277ef1637329cb879d9cf370dae9fa3b23f28031eb59800f39e552b81aefe" +checksum = "b44366541d35be9ea11ed88ed54629c64e91c309ca5fbf861fd909d443ca7575" dependencies = [ "anyhow", "fuel-core-executor", "fuel-core-storage", - "fuel-core-types", + "fuel-core-types 0.35.0", + "fuel-core-types 0.40.0", "postcard", "serde", + "serde_json", ] [[package]] @@ -2169,12 +2251,28 @@ name = "fuel-crypto" version = "0.56.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "33548590131674e8f272a3e056be4dbaa1de7cb364eab2b17987cd5c0dc31cb0" +dependencies = [ + "ecdsa", + "ed25519-dalek", + "fuel-types 0.56.0", + "k256", + "p256", + "serde", + "sha2 0.10.8", + "zeroize", +] + +[[package]] +name = "fuel-crypto" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "65e318850ca64890ff123a99b6b866954ef49da94ab9bc6827cf6ee045568585" dependencies = [ "coins-bip32", "coins-bip39", "ecdsa", "ed25519-dalek", - "fuel-types", + "fuel-types 0.58.2", "k256", "lazy_static", "p256", @@ -2197,13 +2295,24 @@ dependencies = [ "synstructure", ] +[[package]] +name = "fuel-derive" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ab0bc46a3552964bae5169e79b383761a54bd115ea66951a1a7a229edcefa55a" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.71", + "synstructure", +] + [[package]] name = "fuel-gas-price-algorithm" -version = "0.35.0" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9cca4572eaa61de46ba3e78c90b27bc16d13af2da165273bee66e3ac034513e2" +checksum = "7b51715a07bb4a099ca4c658796c7a732f3edb3dfb2cec3407769081c949dc0b" dependencies = [ - "proptest", "serde", "thiserror", ] @@ -2216,7 +2325,22 @@ checksum = "cf17ce8ee5e8b573ea584c223635ff09f1288ad022bcf662954fdccb907602eb" dependencies = [ "derive_more", "digest 0.10.7", - "fuel-storage", + "fuel-storage 0.56.0", + "hashbrown 0.13.2", + "hex", + "serde", + "sha2 0.10.8", +] + +[[package]] +name = "fuel-merkle" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c79eca6a452311c70978a5df796c0f99f27e474b69719e0db4c1d82e68800d07" +dependencies = [ + "derive_more", + "digest 0.10.7", + "fuel-storage 0.58.2", "hashbrown 0.13.2", "hex", "serde", @@ -2229,6 +2353,12 @@ version = "0.56.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4c1b711f28553ddc5f3546711bd220e144ce4c1af7d9e9a1f70b2f20d9f5b791" +[[package]] +name = "fuel-storage" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2d0c46b5d76b3e11197bd31e036cd8b1cb46c4d822cacc48836638080c6d2b76" + [[package]] name = "fuel-tx" version = "0.56.0" @@ -2238,27 +2368,60 @@ dependencies = [ "bitflags 2.6.0", "derivative", "derive_more", - "fuel-asm", - "fuel-crypto", - "fuel-merkle", - "fuel-types", + "fuel-asm 0.56.0", + "fuel-crypto 0.56.0", + "fuel-merkle 0.56.0", + "fuel-types 0.56.0", "hashbrown 0.14.5", "itertools 0.10.5", "postcard", - "rand", "serde", "serde_json", "strum 0.24.1", "strum_macros 0.24.3", ] +[[package]] +name = "fuel-tx" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6723bb8710ba2b70516ac94d34459593225870c937670fb3afaf82e0354667ac" +dependencies = [ + "bitflags 2.6.0", + "derivative", + "derive_more", + "fuel-asm 0.58.2", + "fuel-compression", + "fuel-crypto 0.58.2", + "fuel-merkle 0.58.2", + "fuel-types 0.58.2", + "hashbrown 0.14.5", + "itertools 0.10.5", + "postcard", + "rand", + "serde", + "strum 0.24.1", + "strum_macros 0.24.3", +] + [[package]] name = "fuel-types" version = "0.56.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5b6fb26bcb408b6897e603f68cf60bbbaf6d15381c99f54a69ea743a58235ac1" dependencies = [ - "fuel-derive", + "fuel-derive 0.56.0", + "hex", + "serde", +] + +[[package]] +name = "fuel-types" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "982265415a99b5bd6277bc24194a233bb2e18764df11c937b3dbb11a02c9e545" +dependencies = [ + "fuel-derive 0.58.2", "hex", "rand", "serde", @@ -2269,6 +2432,37 @@ name = "fuel-vm" version = "0.56.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "64fc4695efac9207276f6229f2dd9811848b328a13604a698f7bce1d452bd986" +dependencies = [ + "async-trait", + "backtrace", + "bitflags 2.6.0", + "derivative", + "derive_more", + "ethnum", + "fuel-asm 0.56.0", + "fuel-crypto 0.56.0", + "fuel-merkle 0.56.0", + "fuel-storage 0.56.0", + "fuel-tx 0.56.0", + "fuel-types 0.56.0", + "hashbrown 0.14.5", + "itertools 0.10.5", + "libm", + "paste", + "percent-encoding", + "primitive-types", + "serde", + "serde_with", + "sha3", + "static_assertions", + "strum 0.24.1", +] + +[[package]] +name = "fuel-vm" +version = "0.58.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "54b5362d7d072c72eec20581f67fc5400090c356a7f3ae77c79880b3b177b667" dependencies = [ "anyhow", "async-trait", @@ -2277,12 +2471,13 @@ dependencies = [ "derivative", "derive_more", "ethnum", - "fuel-asm", - "fuel-crypto", - "fuel-merkle", - "fuel-storage", - "fuel-tx", - "fuel-types", + "fuel-asm 0.58.2", + "fuel-compression", + "fuel-crypto 0.58.2", + "fuel-merkle 0.58.2", + "fuel-storage 0.58.2", + "fuel-tx 0.58.2", + "fuel-types 0.58.2", "hashbrown 0.14.5", "itertools 0.10.5", "libm", @@ -2300,13 +2495,13 @@ dependencies = [ [[package]] name = "fuels" -version = "0.66.4" +version = "0.66.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9699101cadc9ad3f1eff2a71532d755ab5526419414b99702e89c1d8b92b5938" +checksum = "6ed08053e72bdb285d5a167c27a7a0d10f1dc4e27d1e6e5296dd2a67813bd13f" dependencies = [ "fuel-core-client", - "fuel-crypto", - "fuel-tx", + "fuel-crypto 0.58.2", + "fuel-tx 0.58.2", "fuels-accounts", "fuels-core", "fuels-macros", @@ -2316,19 +2511,20 @@ dependencies = [ [[package]] name = "fuels-accounts" -version = "0.66.4" +version = "0.66.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a3e97cf3bb16c8b6436dd6e3a6f9cea5c1ffda8daf7cdb335c60b74c31572f57" +checksum = "49fee90e8f3a4fc9392a6cde3010c561fa50da0f805d66fdb659eaa4d5d8a504" dependencies = [ "async-trait", "chrono", + "cynic", "elliptic-curve", "eth-keystore", "fuel-core-client", - "fuel-core-types", - "fuel-crypto", - "fuel-tx", - "fuel-types", + "fuel-core-types 0.40.0", + "fuel-crypto 0.58.2", + "fuel-tx 0.58.2", + "fuel-types 0.58.2", "fuels-core", "itertools 0.12.1", "rand", @@ -2341,9 +2537,9 @@ dependencies = [ [[package]] name = "fuels-code-gen" -version = "0.66.4" +version = "0.66.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "47552a5e8b6935595131ef38b14ef4eee8db870174ea62c8db804dbfa02f57d6" +checksum = "f857b7ff658400506ca6be57bb84fedda44b566e78f5f0a8d0782242f41615c0" dependencies = [ "Inflector", "fuel-abi-types", @@ -2357,37 +2553,38 @@ dependencies = [ [[package]] name = "fuels-core" -version = "0.66.4" +version = "0.66.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b687c021466238851b07e2d39f974a614ffafc7e57dc9be00840d74c74c5febd" +checksum = "baccbdd81e624f57950dcb136b32b853c520dd954badf26b9f58de33f3d71c7e" dependencies = [ "async-trait", "bech32", "chrono", "fuel-abi-types", - "fuel-asm", + "fuel-asm 0.58.2", "fuel-core-chain-config", "fuel-core-client", - "fuel-core-types", - "fuel-crypto", - "fuel-tx", - "fuel-types", - "fuel-vm", + "fuel-core-types 0.40.0", + "fuel-crypto 0.58.2", + "fuel-tx 0.58.2", + "fuel-types 0.58.2", + "fuel-vm 0.58.2", "fuels-macros", "hex", "itertools 0.12.1", "postcard", "serde", "serde_json", + "sha2 0.10.8", "thiserror", "uint", ] [[package]] name = "fuels-macros" -version = "0.66.4" +version = "0.66.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b9dd9359ca6c0e7ad300d487e59babe03f64c6b7b169a0743d13f5c58837b589" +checksum = "5da75294c5e9da312bdc49239736699ee84ea9c5bfbc19a61a8ee588a1247aa1" dependencies = [ "fuels-code-gen", "itertools 0.12.1", @@ -2398,15 +2595,15 @@ dependencies = [ [[package]] name = "fuels-programs" -version = "0.66.4" +version = "0.66.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3288fc4b64e8f93a39b8ffa36fcaef8753232ffda5399662d28e24c172a7d00c" +checksum = "32675ed1c08edd28ddb648dfae0c60a1946d4368a69ddfa6434f2316e33f0520" dependencies = [ "async-trait", "fuel-abi-types", - "fuel-asm", - "fuel-tx", - "fuel-types", + "fuel-asm 0.58.2", + "fuel-tx 0.58.2", + "fuel-types 0.58.2", "fuels-accounts", "fuels-core", "itertools 0.12.1", @@ -2417,19 +2614,19 @@ dependencies = [ [[package]] name = "fuels-test-helpers" -version = "0.66.4" +version = "0.66.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "11e18f84f11543ab29e787e2170eeed7f390b791f16ef8be363e3700ea21833d" +checksum = "02176c0fb1bf8cf58b8a9e5372efb650324740abcd4847b45bd0b041a0f133a2" dependencies = [ "fuel-core", "fuel-core-chain-config", "fuel-core-client", "fuel-core-poa", "fuel-core-services", - "fuel-core-types", - "fuel-crypto", - "fuel-tx", - "fuel-types", + "fuel-core-types 0.40.0", + "fuel-crypto 0.58.2", + "fuel-tx 0.58.2", + "fuel-types 0.58.2", "fuels-accounts", "fuels-core", "futures", @@ -4184,7 +4381,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "071dfc062690e90b734c0b2273ce72ad0ffa95f0c74596bc250dcfd960262841" dependencies = [ "autocfg", - "libm", ] [[package]] @@ -4376,6 +4572,16 @@ dependencies = [ "ucd-trie", ] +[[package]] +name = "petgraph" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4c5cc86750666a3ed20bdaf5ca2a0344f9c67674cae0515bec2da16fbaa47db" +dependencies = [ + "fixedbitset", + "indexmap 2.2.6", +] + [[package]] name = "pin-project" version = "1.1.5" @@ -4615,27 +4821,16 @@ dependencies = [ ] [[package]] -name = "proptest" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b4c2511913b88df1637da85cc8d96ec8e43a3f8bb8ccb71ee1ac240d6f3df58d" +name = "protocol-manager-contract" +version = "0.1.0" dependencies = [ - "bit-set", - "bit-vec", - "bitflags 2.6.0", - "lazy_static", - "num-traits", - "rand", - "rand_chacha", - "rand_xorshift", - "regex-syntax", - "rusty-fork", - "tempfile", - "unarray", + "fuels", + "test-utils", + "tokio", ] [[package]] -name = "protocol-manager-contract" +name = "proxy-contract" version = "0.1.0" dependencies = [ "fuels", @@ -4789,15 +4984,6 @@ dependencies = [ "getrandom", ] -[[package]] -name = "rand_xorshift" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d25bf25ec5ae4a3f1b92f929810509a2f53d7dca2f50b794ff57e3face536c8f" -dependencies = [ - "rand_core", -] - [[package]] name = "rayon" version = "1.10.0" @@ -5132,18 +5318,6 @@ version = "1.0.17" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "955d28af4278de8121b7ebeb796b6a45735dc01436d898801014aced2773a3d6" -[[package]] -name = "rusty-fork" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cb3dcc6e454c328bb824492db107ab7c0ae8fcffe4ad210136ef014458c1bc4f" -dependencies = [ - "fnv", - "quick-error", - "tempfile", - "wait-timeout", -] - [[package]] name = "rw-stream-sink" version = "0.4.0" @@ -5249,9 +5423,9 @@ dependencies = [ [[package]] name = "secp256k1" -version = "0.26.0" +version = "0.29.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4124a35fe33ae14259c490fd70fa199a32b9ce9502f2ee6bc4f81ec06fa65894" +checksum = "9465315bc9d4566e1724f0fffcbcc446268cb522e60f9a27bcded6b19c108113" dependencies = [ "rand", "secp256k1-sys", @@ -5259,9 +5433,9 @@ dependencies = [ [[package]] name = "secp256k1-sys" -version = "0.8.1" +version = "0.10.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "70a129b9e9efbfb223753b9163c4ab3b13cff7fd9c7f010fbac25ab4099fa07e" +checksum = "d4387882333d3aa8cb20530a17c69a3752e97837832f34f6dccc760e715001d9" dependencies = [ "cc", ] @@ -5781,6 +5955,7 @@ checksum = "3369f5ac52d5eb6ab48c6b4ffdc8efbcad6b89c765749064ba298f2c68a16a76" name = "test-utils" version = "0.0.0" dependencies = [ + "csv", "dotenv", "fuels", "futures", @@ -5788,6 +5963,7 @@ dependencies = [ "rand", "serde", "serde_json", + "tai64", "tokio", ] @@ -6006,6 +6182,7 @@ dependencies = [ "pin-project", "pin-project-lite", "tokio", + "tokio-util", "tower-layer", "tower-service", "tracing", @@ -6025,10 +6202,28 @@ dependencies = [ "http-body", "http-range-header", "pin-project-lite", - "tokio", "tower", "tower-layer", "tower-service", +] + +[[package]] +name = "tower-http" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "61c5bb1d698276a2443e5ecfabc1008bf15a36c12e6a7176e7bf089ea9131140" +dependencies = [ + "bitflags 2.6.0", + "bytes", + "futures-core", + "futures-util", + "http 0.2.12", + "http-body", + "http-range-header", + "pin-project-lite", + "tokio", + "tower-layer", + "tower-service", "tracing", ] @@ -6127,12 +6322,6 @@ dependencies = [ "static_assertions", ] -[[package]] -name = "unarray" -version = "0.1.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eaea85b334db583fe3274d12b4cd1880032beab409c0d774be044d4480ab9a94" - [[package]] name = "unicode-bidi" version = "0.3.15" @@ -6279,15 +6468,6 @@ version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6a02e4885ed3bc0f2de90ea6dd45ebcbb66dacffe03547fadbb0eeae2770887d" -[[package]] -name = "wait-timeout" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9f200f5b12eb75f8c1ed65abd4b2db8a6e1b138a20de009dacee265a2498f3f6" -dependencies = [ - "libc", -] - [[package]] name = "want" version = "0.3.1" diff --git a/Cargo.toml b/Cargo.toml index 714d5bbd..fe9ba90a 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -9,6 +9,7 @@ members = [ "./contracts/borrow-operations-contract", "./contracts/protocol-manager-contract", "./contracts/token-contract", + "./contracts/proxy-contract", "./contracts/usdf-token-contract", "./contracts/active-pool-contract", "./contracts/coll-surplus-pool-contract", @@ -25,13 +26,15 @@ members = [ ] [workspace.dependencies] +csv = "1.1.0" dotenv = "0.15.0" -fuels = { version = "0.66.4", features = ["fuel-core-lib"] } +fuels = { version = "0.66.9", features = ["fuel-core-lib"] } futures = "0.3.17" hex = "0.4.3" pbr = "1.1.1" rand = { version = "0.8.5", features = ["std_rng", "getrandom"] } serde = { version = "1.0.92", features = ["derive"] } serde_json = "1.0.92" +tai64 = "4.0.0" tokio = { version = "1.21.0", features = ["rt", "macros"] } test-utils = { path = "./test-utils" } diff --git a/Forc.toml b/Forc.toml index 9f5538cb..4d864e3b 100644 --- a/Forc.toml +++ b/Forc.toml @@ -21,5 +21,6 @@ members = [ "./contracts/hint-helper-contract", "./contracts/tests-artifacts-sorted-troves-contract", "./contracts/tests-artifacts-stability-pool-contract", + "./contracts/proxy-contract", "./libraries", ] diff --git a/Makefile b/Makefile index 29dbfd72..70a1638d 100644 --- a/Makefile +++ b/Makefile @@ -3,7 +3,7 @@ include .env export $(shell sed 's/=.*//' .env) ############################# HELP MESSAGE ############################# # Make sure the help command stays first, so that it's printed by default when `make` is called without arguments -.PHONY: help tests build-and-test generate-types deploy add-asset pause unpause sanity-check +.PHONY: help tests build-and-test generate-types deploy add-asset pause unpause sanity-check transfer-owner help: @grep -E '^[a-zA-Z0-9_-]+:.*?## .*$$' $(MAKEFILE_LIST) | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m%-30s\033[0m %s\n", $$1, $$2}' @@ -20,17 +20,20 @@ format: ## Format the code -------Deployer Scripts-------: -deploy: ## Run the deployment script for core contracts - @forc build && cd deploy-scripts && RPC=$(RPC) SECRET=$(SECRET) cargo run deploy +deploy: ## Run the deployment script for core contracts (usage: make deploy NETWORK=) + @forc build && cd deploy-scripts && NETWORK=$(NETWORK) SECRET=$(SECRET) cargo run deploy -add-asset: ## Run the script to add assets to the protocol - @cd deploy-scripts && RPC=$(RPC) SECRET=$(SECRET) cargo run add-asset +add-asset: ## Run the script to add assets to the protocol (usage: make add-asset NETWORK= ASSET=ETH) + @forc build && cd deploy-scripts && NETWORK=$(NETWORK) SECRET=$(SECRET) cargo run add-asset $(ASSET) -pause: ## Pause the protocol - @cd deploy-scripts && RPC=$(RPC) SECRET=$(SECRET) cargo run pause +pause: ## Pause the protocol (usage: make pause NETWORK=) + @cd deploy-scripts && NETWORK=$(NETWORK) SECRET=$(SECRET) cargo run pause -unpause: ## Unpause the protocol - @cd deploy-scripts && RPC=$(RPC) SECRET=$(SECRET) cargo run unpause +unpause: ## Unpause the protocol (usage: make unpause NETWORK=) + @cd deploy-scripts && NETWORK=$(NETWORK) SECRET=$(SECRET) cargo run unpause -sanity-check: ## Run the sanity check script - @cd deploy-scripts && RPC=$(RPC) SECRET=$(SECRET) cargo run sanity-check +sanity-check: ## Run the sanity check script (usage: make sanity-check NETWORK=) + @cd deploy-scripts && NETWORK=$(NETWORK) SECRET=$(SECRET) cargo run sanity-check + +transfer-owner: ## Transfer ownership of the protocol (usage: make transfer-owner NETWORK= ADDRESS=) + @cd deploy-scripts && NETWORK=$(NETWORK) SECRET=$(SECRET) cargo run transfer-owner $(ADDRESS) diff --git a/contracts/active-pool-contract/Forc.toml b/contracts/active-pool-contract/Forc.toml index efbf94cc..83d39b65 100644 --- a/contracts/active-pool-contract/Forc.toml +++ b/contracts/active-pool-contract/Forc.toml @@ -6,3 +6,6 @@ name = "active-pool-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/active-pool-contract/tests/harness.rs b/contracts/active-pool-contract/tests/harness.rs index eb71aefb..b5e261a2 100644 --- a/contracts/active-pool-contract/tests/harness.rs +++ b/contracts/active-pool-contract/tests/harness.rs @@ -1,12 +1,15 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - interfaces::active_pool::{active_pool_abi, ActivePool}, - interfaces::token::{token_abi, Token}, + data_structures::ContractInstance, + interfaces::{ + active_pool::{active_pool_abi, ActivePool}, + token::{token_abi, Token}, + }, setup::common::{deploy_active_pool, deploy_default_pool, deploy_token}, }; async fn get_contract_instance() -> ( - ActivePool, + ContractInstance>, Token, WalletUnlocked, ) { @@ -43,7 +46,7 @@ async fn get_contract_instance() -> ( &instance, Identity::Address(wallet.address().into()), Identity::Address(wallet.address().into()), - default_pool.contract_id().into(), + default_pool.contract.contract_id().into(), Identity::Address(wallet.address().into()), ) .await diff --git a/contracts/borrow-operations-contract/Forc.toml b/contracts/borrow-operations-contract/Forc.toml index f010e5dd..6453d01c 100644 --- a/contracts/borrow-operations-contract/Forc.toml +++ b/contracts/borrow-operations-contract/Forc.toml @@ -7,4 +7,7 @@ name = "borrow-operations-contract" [dependencies] libraries = { path = "../../libraries" } standards = { git = "https://github.com/FuelLabs/sway-standards", tag = "v0.6.1" } -sway_libs = { git = "https://github.com/FuelLabs/sway-libs", tag = "v0.23.1" } +sway_libs = { git = "https://github.com/FuelLabs/sway-libs", tag = "v0.24.0" } + +[proxy] +enabled = true diff --git a/contracts/borrow-operations-contract/tests/events.rs b/contracts/borrow-operations-contract/tests/events.rs index 62001052..0c92ed5b 100644 --- a/contracts/borrow-operations-contract/tests/events.rs +++ b/contracts/borrow-operations-contract/tests/events.rs @@ -1,7 +1,7 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ borrow_operations::{borrow_operations_abi, BorrowOperations}, oracle::oracle_abi, @@ -152,9 +152,12 @@ async fn test_trove_events() { ) .await; - let borrow_operations_second_wallet = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - second_wallet.clone(), + let borrow_operations_second_wallet = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + second_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( diff --git a/contracts/borrow-operations-contract/tests/failure.rs b/contracts/borrow-operations-contract/tests/failure.rs index f7fa2b3a..7100d7da 100644 --- a/contracts/borrow-operations-contract/tests/failure.rs +++ b/contracts/borrow-operations-contract/tests/failure.rs @@ -84,6 +84,7 @@ async fn fails_open_two_troves_of_same_coll_type() { admin.address().into(), contracts .usdf + .contract .contract_id() .asset_id(&AssetId::zeroed().into()) .into(), @@ -517,7 +518,7 @@ async fn fails_incorrect_token_as_collateral_or_repayment() { usdf_token_abi::initialize( &fake_usdf_token, - fake_usdf_token.contract_id().into(), + fake_usdf_token.contract.contract_id().into(), Identity::Address(admin.address().into()), Identity::Address(admin.address().into()), ) diff --git a/contracts/borrow-operations-contract/tests/harness.rs b/contracts/borrow-operations-contract/tests/harness.rs index 66a3c0c8..17ac912f 100644 --- a/contracts/borrow-operations-contract/tests/harness.rs +++ b/contracts/borrow-operations-contract/tests/harness.rs @@ -1,2 +1,4 @@ +pub mod events; pub mod failure; +pub mod pausing; pub mod success; diff --git a/contracts/borrow-operations-contract/tests/pausing.rs b/contracts/borrow-operations-contract/tests/pausing.rs index 581305fa..19e84a91 100644 --- a/contracts/borrow-operations-contract/tests/pausing.rs +++ b/contracts/borrow-operations-contract/tests/pausing.rs @@ -1,7 +1,7 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ borrow_operations::{borrow_operations_abi, BorrowOperations}, oracle::oracle_abi, @@ -22,17 +22,23 @@ async fn test_permissions() { Identity::Address(new_pauser.address().into()), ) .await; - let borrow_operations_new_pauser = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - new_pauser.clone(), + let borrow_operations_new_pauser = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + new_pauser.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); assert!(result.is_ok(), "Admin should be able to set a new pauser"); // Verify unauthorized set_pauser let unauthorized_wallet = wallets.pop().unwrap(); - let unauthorized_borrow_operations = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - unauthorized_wallet.clone(), + let unauthorized_borrow_operations = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + unauthorized_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let result = borrow_operations_abi::set_pauser( &unauthorized_borrow_operations, @@ -65,9 +71,12 @@ async fn test_permissions() { ); // Test renounce_owner - let new_borrow_operations = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - new_owner.clone(), + let new_borrow_operations = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + new_owner.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let result = borrow_operations_abi::renounce_owner(&new_borrow_operations).await; assert!( @@ -115,9 +124,12 @@ async fn test_permissions() { assert!(!status.value, "Failed to set pause status to false"); let unauthorized_wallet = wallets.pop().unwrap(); - let unauthorized_borrow_operations = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - unauthorized_wallet.clone(), + let unauthorized_borrow_operations = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + unauthorized_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); // Try to set pause status with unauthorized wallet diff --git a/contracts/borrow-operations-contract/tests/success.rs b/contracts/borrow-operations-contract/tests/success.rs index 8858b037..9109f1b7 100644 --- a/contracts/borrow-operations-contract/tests/success.rs +++ b/contracts/borrow-operations-contract/tests/success.rs @@ -1,7 +1,7 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ active_pool::active_pool_abi, borrow_operations::{borrow_operations_abi, BorrowOperations}, @@ -63,6 +63,7 @@ async fn proper_creating_trove() { admin.address().into(), contracts .usdf + .contract .contract_id() .asset_id(&AssetId::zeroed().into()) .into(), @@ -439,11 +440,7 @@ async fn proper_increase_debt() { let provider = admin.provider().unwrap(); - let usdf_asset_id: AssetId = contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let usdf_asset_id: AssetId = contracts.usdf_asset_id; let deposit_amount = 1200 * PRECISION; let borrow_amount = 600 * PRECISION; @@ -596,11 +593,7 @@ async fn proper_decrease_debt() { let provider = admin.provider().unwrap(); - let usdf_asset_id = contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let usdf_asset_id = contracts.usdf_asset_id; let deposit_amount = 1200 * PRECISION; let borrow_amount = 800 * PRECISION; @@ -764,14 +757,20 @@ async fn proper_open_multiple_troves() { ) .await; - let borrow_operations_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet1.clone(), + let borrow_operations_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet2.clone(), + let borrow_operations_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let deposit_amount1 = 3000 * PRECISION; @@ -893,14 +892,20 @@ async fn proper_close_trove() { ) .await; - let borrow_operations_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet1.clone(), + let borrow_operations_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet2.clone(), + let borrow_operations_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let deposit_amount1 = 3000 * PRECISION; @@ -933,11 +938,7 @@ async fn proper_close_trove() { .unwrap(); // Transfering to cover the fee - let usdf_asset_id: AssetId = contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let usdf_asset_id: AssetId = contracts.usdf_asset_id; let amount = borrow_amount1 / 200; let tx_parms = TxPolicies::default() .with_tip(1) @@ -1111,14 +1112,7 @@ async fn proper_creating_trove_with_2nd_asset() { .unwrap(); let usdf_balance = provider - .get_asset_balance( - admin.address().into(), - contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(), - ) + .get_asset_balance(admin.address().into(), contracts.usdf_asset_id) .await .unwrap(); @@ -1214,8 +1208,13 @@ async fn proper_creating_trove_with_2nd_asset() { ) .await; - let borrow_operations_wallet2 = - BorrowOperations::new(contracts.borrow_operations.contract_id().clone(), wallet2); + let borrow_operations_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), + ); let deposit_amount2 = 1200 * PRECISION; let borrow_amount2 = 600 * PRECISION; @@ -1268,14 +1267,7 @@ async fn proper_creating_trove_with_2nd_asset() { .unwrap(); let usdf_balance = provider - .get_asset_balance( - admin.address().into(), - contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(), - ) + .get_asset_balance(admin.address().into(), contracts.usdf_asset_id) .await .unwrap(); @@ -1352,13 +1344,7 @@ async fn proper_creating_trove_with_2nd_asset() { // println!("{:?}", hex_string); - println!( - "Expected: {:?}", - contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - ); + println!("Expected: {:?}", contracts.usdf_asset_id); let _res = borrow_operations_abi::close_trove( &contracts.borrow_operations, diff --git a/contracts/coll-surplus-pool-contract/Forc.toml b/contracts/coll-surplus-pool-contract/Forc.toml index 448943cd..dd15dc44 100644 --- a/contracts/coll-surplus-pool-contract/Forc.toml +++ b/contracts/coll-surplus-pool-contract/Forc.toml @@ -6,3 +6,6 @@ name = "coll-surplus-pool-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/coll-surplus-pool-contract/tests/harness.rs b/contracts/coll-surplus-pool-contract/tests/harness.rs index 4fed99c3..dcfe4376 100644 --- a/contracts/coll-surplus-pool-contract/tests/harness.rs +++ b/contracts/coll-surplus-pool-contract/tests/harness.rs @@ -1,6 +1,6 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ borrow_operations::{borrow_operations_abi, BorrowOperations}, coll_surplus_pool::{coll_surplus_pool_abi, CollSurplusPool}, @@ -35,9 +35,12 @@ async fn test_collateral_surplus_workflow_after_liquidation() { ) .await; - let borrow_operations = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let borrow_operations = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id, ); borrow_operations_abi::open_trove( @@ -61,9 +64,12 @@ async fn test_collateral_surplus_workflow_after_liquidation() { // At least one healthy trove needed for liquidation let healthy_wallet = wallets.pop().unwrap(); - let healthy_wallet_borrow_operations = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet.clone(), + let healthy_wallet_borrow_operations = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet.clone(), + ), + contracts.borrow_operations.implementation_id, ); token_abi::mint_to_id( @@ -171,18 +177,26 @@ async fn test_collateral_surplus_workflow_after_liquidation() { #[tokio::test] async fn test_coll_surplus_pool_access_control() { let (contracts, admin, mut wallets) = setup_protocol(3, false, false).await; - let coll_surplus_pool = CollSurplusPool::new( - contracts.coll_surplus_pool.contract_id().clone(), - admin.clone(), + let coll_surplus_pool = ContractInstance::new( + CollSurplusPool::new( + contracts.coll_surplus_pool.contract.contract_id().clone(), + admin.clone(), + ), + contracts.coll_surplus_pool.implementation_id, ); let unauthorized_wallet = wallets.pop().unwrap(); - // Test initialize access control - let result = coll_surplus_pool_abi::initialize( - &CollSurplusPool::new( - coll_surplus_pool.contract_id().clone(), + let coll_surplus_unauthorized = ContractInstance::new( + CollSurplusPool::new( + contracts.coll_surplus_pool.contract.contract_id().clone(), unauthorized_wallet.clone(), ), + contracts.coll_surplus_pool.implementation_id, + ); + + // Test initialize access control + let result = coll_surplus_pool_abi::initialize( + &coll_surplus_unauthorized, ContractId::from([0u8; 32]), Identity::Address(unauthorized_wallet.address().into()), ) @@ -194,10 +208,7 @@ async fn test_coll_surplus_pool_access_control() { // Test add_asset access control let result = coll_surplus_pool_abi::add_asset( - &CollSurplusPool::new( - coll_surplus_pool.contract_id().clone(), - unauthorized_wallet.clone(), - ), + &coll_surplus_unauthorized, AssetId::default(), Identity::Address(unauthorized_wallet.address().into()), ) @@ -209,10 +220,7 @@ async fn test_coll_surplus_pool_access_control() { // Test claim_coll access control let result = coll_surplus_pool_abi::claim_coll( - &CollSurplusPool::new( - coll_surplus_pool.contract_id().clone(), - unauthorized_wallet.clone(), - ), + &coll_surplus_unauthorized, Identity::Address(unauthorized_wallet.address().into()), &contracts.active_pool, AssetId::default(), @@ -225,10 +233,7 @@ async fn test_coll_surplus_pool_access_control() { // Test account_surplus access control let result = coll_surplus_pool_abi::account_surplus( - &CollSurplusPool::new( - coll_surplus_pool.contract_id().clone(), - unauthorized_wallet.clone(), - ), + &coll_surplus_unauthorized, Identity::Address(unauthorized_wallet.address().into()), 100, AssetId::default(), diff --git a/contracts/community-issuance-contract/Forc.toml b/contracts/community-issuance-contract/Forc.toml index 403936e2..3a08dc1b 100644 --- a/contracts/community-issuance-contract/Forc.toml +++ b/contracts/community-issuance-contract/Forc.toml @@ -7,4 +7,7 @@ name = "community-issuance-contract" [dependencies] libraries = { path = "../../libraries" } standards = { git = "https://github.com/FuelLabs/sway-standards", tag = "v0.6.1" } -sway_libs = { git = "https://github.com/FuelLabs/sway-libs", tag = "v0.23.1" } +sway_libs = { git = "https://github.com/FuelLabs/sway-libs", tag = "v0.24.0" } + +[proxy] +enabled = true diff --git a/contracts/community-issuance-contract/tests/harness.rs b/contracts/community-issuance-contract/tests/harness.rs index 8e9c6da8..ea55620d 100644 --- a/contracts/community-issuance-contract/tests/harness.rs +++ b/contracts/community-issuance-contract/tests/harness.rs @@ -1,7 +1,7 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ borrow_operations::{borrow_operations_abi, BorrowOperations}, community_issuance::{community_issuance_abi, CommunityIssuance}, @@ -26,17 +26,13 @@ fn abs_dif(a: u64, b: u64) -> u64 { async fn test_emissions() { let (contracts, admin, _wallets) = setup_protocol(4, false, false).await; let provider = admin.provider().unwrap(); - let fpt_asset_id = contracts - .fpt_token - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let fpt_asset_id = contracts.fpt_asset_id; community_issuance_abi::set_current_time(&contracts.community_issuance, 0).await; let total_emissions = provider .get_contract_asset_balance( - contracts.community_issuance.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), fpt_asset_id, ) .await @@ -108,7 +104,7 @@ async fn test_emissions() { let fpt_balance_community_issuance = provider .get_contract_asset_balance( - contracts.community_issuance.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), fpt_asset_id, ) .await @@ -161,17 +157,13 @@ async fn test_emissions() { async fn test_admin_start_rewards_increase_transition() { let (contracts, admin, mut _wallets) = setup_protocol(4, false, false).await; let provider = admin.provider().unwrap(); - let fpt_asset_id = contracts - .fpt_token - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let fpt_asset_id = contracts.fpt_asset_id; community_issuance_abi::set_current_time(&contracts.community_issuance, 0).await; let total_emissions = provider .get_contract_asset_balance( - contracts.community_issuance.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), fpt_asset_id, ) .await @@ -227,7 +219,8 @@ async fn test_admin_start_rewards_increase_transition() { &contracts.community_issuance, 604800 + 1, ) - .await; + .await + .unwrap(); community_issuance_abi::set_current_time( &contracts.community_issuance, @@ -249,7 +242,7 @@ async fn test_admin_start_rewards_increase_transition() { let fpt_balance_community_issuance = provider .get_contract_asset_balance( - contracts.community_issuance.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), fpt_asset_id, ) .await @@ -279,11 +272,7 @@ async fn test_admin_start_rewards_increase_transition() { async fn test_public_start_rewards_increase_transition_after_deadline() { let (contracts, admin, mut wallets) = setup_protocol(4, false, false).await; let provider = admin.provider().unwrap(); - let fpt_asset_id = contracts - .fpt_token - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let fpt_asset_id = contracts.fpt_asset_id; let wallet1 = wallets.pop().unwrap(); @@ -291,7 +280,7 @@ async fn test_public_start_rewards_increase_transition_after_deadline() { let total_emissions = provider .get_contract_asset_balance( - contracts.community_issuance.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), fpt_asset_id, ) .await @@ -343,9 +332,12 @@ async fn test_public_start_rewards_increase_transition_after_deadline() { let deadline = 31_536_000 + 1; community_issuance_abi::set_current_time(&contracts.community_issuance, deadline).await; - let community_issuance_wallet1 = CommunityIssuance::new( - contracts.community_issuance.contract_id().clone(), - wallet1.clone(), + let community_issuance_wallet1 = ContractInstance::new( + CommunityIssuance::new( + contracts.community_issuance.contract.contract_id().clone(), + wallet1.clone(), + ), + contracts.community_issuance.implementation_id, ); // this is to test that anyone can call this function community_issuance_abi::public_start_rewards_increase_transition_after_deadline( @@ -373,7 +365,7 @@ async fn test_public_start_rewards_increase_transition_after_deadline() { let fpt_balance_community_issuance = provider .get_contract_asset_balance( - contracts.community_issuance.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), fpt_asset_id, ) .await @@ -404,17 +396,13 @@ async fn test_emissions_multiple_deposits() { let (contracts, admin, mut wallets) = setup_protocol(4, false, false).await; let provider = admin.provider().unwrap(); - let fpt_asset_id = contracts - .fpt_token - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let fpt_asset_id = contracts.fpt_asset_id; community_issuance_abi::set_current_time(&contracts.community_issuance, 0).await; let total_emissions = provider .get_contract_asset_balance( - contracts.community_issuance.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), fpt_asset_id, ) .await @@ -443,17 +431,26 @@ async fn test_emissions_multiple_deposits() { ) .await; - let borrow_operations_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet1.clone(), + let borrow_operations_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet1.clone(), + ), + contracts.borrow_operations.implementation_id, ); - let borrow_operations_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet2.clone(), + let borrow_operations_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet2.clone(), + ), + contracts.borrow_operations.implementation_id, ); - let borrow_operations_wallet3 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet3.clone(), + let borrow_operations_wallet3 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet3.clone(), + ), + contracts.borrow_operations.implementation_id, ); oracle_abi::set_debug_timestamp(&contracts.asset_contracts[0].oracle, PYTH_TIMESTAMP).await; @@ -520,17 +517,26 @@ async fn test_emissions_multiple_deposits() { .await .unwrap(); - let stability_pool_wallet1 = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - wallet1.clone(), + let stability_pool_wallet1 = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + wallet1.clone(), + ), + contracts.stability_pool.implementation_id, ); - let stability_pool_wallet2 = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - wallet2.clone(), + let stability_pool_wallet2 = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + wallet2.clone(), + ), + contracts.stability_pool.implementation_id, ); - let stability_pool_wallet3 = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - wallet3.clone(), + let stability_pool_wallet3 = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + wallet3.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::provide_to_stability_pool( &stability_pool_wallet1, @@ -634,16 +640,19 @@ async fn test_emissions_multiple_deposits() { #[tokio::test] async fn test_only_owner_can_start_rewards_increase_transition() { - let (contracts, admin, mut wallets) = setup_protocol(4, false, false).await; + let (contracts, _admin, mut wallets) = setup_protocol(4, false, false).await; let attacker = wallets.pop().unwrap(); community_issuance_abi::set_current_time(&contracts.community_issuance, 31104000 + 1).await; // Create a CommunityIssuance instance for the attacker - let community_issuance_attacker = CommunityIssuance::new( - contracts.community_issuance.contract_id().clone(), - attacker.clone(), + let community_issuance_attacker = ContractInstance::new( + CommunityIssuance::new( + contracts.community_issuance.contract.contract_id().clone(), + attacker.clone(), + ), + contracts.community_issuance.implementation_id, ); // Attempt to start the rewards increase transition as the attacker diff --git a/contracts/default-pool-contract/Forc.toml b/contracts/default-pool-contract/Forc.toml index c265e6d2..5bcd6b41 100644 --- a/contracts/default-pool-contract/Forc.toml +++ b/contracts/default-pool-contract/Forc.toml @@ -6,3 +6,6 @@ name = "default-pool-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/default-pool-contract/tests/harness.rs b/contracts/default-pool-contract/tests/harness.rs index 96e967d4..4205732b 100644 --- a/contracts/default-pool-contract/tests/harness.rs +++ b/contracts/default-pool-contract/tests/harness.rs @@ -1,12 +1,13 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ + data_structures::ContractInstance, interfaces::usdf_token::{usdf_token_abi, USDFToken}, setup::common::deploy_usdf_token, }; async fn get_contract_instance() -> ( - USDFToken, + ContractInstance>, WalletUnlocked, Vec, ) { @@ -28,7 +29,7 @@ async fn get_contract_instance() -> ( usdf_token_abi::initialize( &asset, - asset.contract_id().into(), + asset.contract.contract_id().into(), Identity::Address(wallet.address().into()), Identity::Address(wallet.address().into()), ) @@ -87,7 +88,10 @@ async fn fails_to_mint_unauthorized() { let wallet = wallets.pop().unwrap(); - let unauthorized_usdf = USDFToken::new(usdf.contract_id().clone(), wallet.clone()); + let unauthorized_usdf = ContractInstance::new( + USDFToken::new(usdf.contract.contract_id(), wallet.clone()), + usdf.implementation_id.clone(), + ); usdf_token_abi::mint( &unauthorized_usdf, @@ -108,7 +112,10 @@ async fn fails_to_burn_unauthorized() { .await .unwrap(); - let unauthorized_usdf = USDFToken::new(usdf.contract_id().clone(), wallet.clone()); + let unauthorized_usdf = ContractInstance::new( + USDFToken::new(usdf.contract.contract_id(), wallet.clone()), + usdf.implementation_id.clone(), + ); usdf_token_abi::burn(&unauthorized_usdf, 100) .await diff --git a/contracts/fpt-staking-contract/Forc.toml b/contracts/fpt-staking-contract/Forc.toml index ccb755b3..0fa8dd94 100644 --- a/contracts/fpt-staking-contract/Forc.toml +++ b/contracts/fpt-staking-contract/Forc.toml @@ -6,3 +6,6 @@ name = "fpt-staking-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/fpt-staking-contract/tests/events.rs b/contracts/fpt-staking-contract/tests/events.rs index a741552a..d7627626 100644 --- a/contracts/fpt-staking-contract/tests/events.rs +++ b/contracts/fpt-staking-contract/tests/events.rs @@ -15,7 +15,7 @@ async fn test_staking_events() { // Setup initial conditions let mock_token = Token::new( - contracts.fpt_token.contract_id().clone(), + contracts.fpt_token.contract.contract_id().clone(), wallets.pop().unwrap().clone(), ); diff --git a/contracts/fpt-staking-contract/tests/failure.rs b/contracts/fpt-staking-contract/tests/failure.rs index bcd924cf..f21dd79f 100644 --- a/contracts/fpt-staking-contract/tests/failure.rs +++ b/contracts/fpt-staking-contract/tests/failure.rs @@ -13,7 +13,7 @@ async fn fails_unstake_wrong_amount() { let (contracts, admin, mut _wallets) = setup_protocol(4, false, true).await; let mock_token = Token::new( - contracts.fpt_token.contract_id().clone(), + contracts.fpt_token.contract.contract_id().clone(), _wallets.pop().unwrap().clone(), ); token_abi::mint_to_id( @@ -24,7 +24,9 @@ async fn fails_unstake_wrong_amount() { .await; let mock_token_asset_id = mock_token.contract_id().asset_id(&AssetId::zeroed().into()); - fpt_staking_abi::stake(&contracts.fpt_staking, mock_token_asset_id, 1 * PRECISION).await; + fpt_staking_abi::stake(&contracts.fpt_staking, mock_token_asset_id, 1 * PRECISION) + .await + .unwrap(); fpt_staking_abi::unstake( &contracts.fpt_staking, diff --git a/contracts/fpt-staking-contract/tests/harness.rs b/contracts/fpt-staking-contract/tests/harness.rs index 66a3c0c8..72d8e66b 100644 --- a/contracts/fpt-staking-contract/tests/harness.rs +++ b/contracts/fpt-staking-contract/tests/harness.rs @@ -1,2 +1,3 @@ +pub mod events; pub mod failure; pub mod success; diff --git a/contracts/fpt-staking-contract/tests/success.rs b/contracts/fpt-staking-contract/tests/success.rs index a0a2dc33..6410c897 100644 --- a/contracts/fpt-staking-contract/tests/success.rs +++ b/contracts/fpt-staking-contract/tests/success.rs @@ -1,6 +1,6 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ borrow_operations::{borrow_operations_abi, BorrowOperations}, fpt_staking::{fpt_staking_abi, FPTStaking}, @@ -47,14 +47,10 @@ async fn proper_staking_deposit() { let provider = admin.provider().unwrap(); - let fpt_asset_id = contracts - .fpt_token - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let fpt_asset_id = contracts.fpt_asset_id; let mock_token = Token::new( - contracts.fpt_token.contract_id().clone(), + contracts.fpt_token.contract.contract_id().clone(), _wallets.pop().unwrap().clone(), ); token_abi::mint_to_id( @@ -66,7 +62,9 @@ async fn proper_staking_deposit() { let mock_token_asset_id = mock_token.contract_id().asset_id(&AssetId::zeroed().into()); - fpt_staking_abi::stake(&contracts.fpt_staking, mock_token_asset_id, 1 * PRECISION).await; + fpt_staking_abi::stake(&contracts.fpt_staking, mock_token_asset_id, 1 * PRECISION) + .await + .unwrap(); let fpt_balance = provider .get_asset_balance(admin.address().into(), fpt_asset_id) @@ -82,23 +80,16 @@ async fn proper_staking_multiple_positions() { let provider = admin.provider().unwrap(); - let fpt_asset_id = contracts - .fpt_token - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); - let usdf_asset_id = contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let fpt_asset_id = contracts.fpt_asset_id; + + let usdf_asset_id = contracts.usdf_asset_id; let healthy_wallet1 = wallets.pop().unwrap(); let healthy_wallet2 = wallets.pop().unwrap(); let healthy_wallet3 = wallets.pop().unwrap(); let mock_token = Token::new( - contracts.fpt_token.contract_id().clone(), + contracts.fpt_token.contract.contract_id().clone(), healthy_wallet1.clone(), ); @@ -116,14 +107,20 @@ async fn proper_staking_multiple_positions() { ) .await; - let fpt_staking_healthy_wallet1 = FPTStaking::new( - contracts.fpt_staking.contract_id().clone(), - healthy_wallet1.clone(), + let fpt_staking_healthy_wallet1 = ContractInstance::new( + FPTStaking::new( + contracts.fpt_staking.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.fpt_staking.implementation_id, ); - let fpt_staking_healthy_wallet2 = FPTStaking::new( - contracts.fpt_staking.contract_id().clone(), - healthy_wallet2.clone(), + let fpt_staking_healthy_wallet2 = ContractInstance::new( + FPTStaking::new( + contracts.fpt_staking.contract.contract_id().clone(), + healthy_wallet2.clone(), + ), + contracts.fpt_staking.implementation_id, ); let mock_token_asset_id = mock_token.contract_id().asset_id(&AssetId::zeroed().into()); @@ -133,14 +130,16 @@ async fn proper_staking_multiple_positions() { mock_token_asset_id, 1 * PRECISION, ) - .await; + .await + .unwrap(); fpt_staking_abi::stake( &fpt_staking_healthy_wallet2, mock_token_asset_id, 1 * PRECISION, ) - .await; + .await + .unwrap(); let fpt_balance_user1 = provider .get_asset_balance(healthy_wallet1.address().into(), fpt_asset_id) @@ -172,9 +171,12 @@ async fn proper_staking_multiple_positions() { // println!("Asset balance user {}", asset_user_balance); - let borrow_operations_healthy_wallet3 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet3.clone(), + let borrow_operations_healthy_wallet3 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet3.clone(), + ), + contracts.borrow_operations.implementation_id, ); oracle_abi::set_debug_timestamp(&contracts.asset_contracts[0].oracle, PYTH_TIMESTAMP).await; @@ -204,7 +206,7 @@ async fn proper_staking_multiple_positions() { .unwrap(); let usdf_in_staking_balance = provider - .get_contract_asset_balance(&contracts.fpt_staking.contract_id(), usdf_asset_id) + .get_contract_asset_balance(&contracts.fpt_staking.contract.contract_id(), usdf_asset_id) .await .unwrap(); @@ -226,9 +228,12 @@ async fn proper_staking_multiple_positions() { let redeem_amount = 10_000 * PRECISION; - let protocol_manager_healthy_wallet3 = ProtocolManager::new( - contracts.protocol_manager.contract_id().clone(), - healthy_wallet3.clone(), + let protocol_manager_healthy_wallet3 = ContractInstance::new( + ProtocolManager::new( + contracts.protocol_manager.contract.contract_id().clone(), + healthy_wallet3.clone(), + ), + contracts.protocol_manager.implementation_id, ); protocol_manager_abi::redeem_collateral( &protocol_manager_healthy_wallet3, @@ -249,7 +254,7 @@ async fn proper_staking_multiple_positions() { let asset_in_staking_balance = provider .get_contract_asset_balance( - &contracts.fpt_staking.contract_id(), + &contracts.fpt_staking.contract.contract_id(), contracts.asset_contracts[0].asset_id, ) .await diff --git a/contracts/fpt-token-contract/Forc.toml b/contracts/fpt-token-contract/Forc.toml index e9087442..bcc4ab3f 100644 --- a/contracts/fpt-token-contract/Forc.toml +++ b/contracts/fpt-token-contract/Forc.toml @@ -7,3 +7,6 @@ name = "fpt-token-contract" [dependencies] libraries = { path = "../../libraries" } standards = { git = "https://github.com/FuelLabs/sway-standards", tag = "v0.6.1" } + +[proxy] +enabled = true diff --git a/contracts/fpt-token-contract/tests/harness.rs b/contracts/fpt-token-contract/tests/harness.rs index 0618e152..1dc783fa 100644 --- a/contracts/fpt-token-contract/tests/harness.rs +++ b/contracts/fpt-token-contract/tests/harness.rs @@ -8,11 +8,7 @@ use test_utils::{ async fn proper_intialize() { let (contracts, admin, _wallets) = setup_protocol(4, false, false).await; let provider = admin.provider().unwrap(); - let fpt_asset_id = contracts - .fpt_token - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let fpt_asset_id = contracts.fpt_asset_id; let vesting_contract = fpt_token_abi::get_vesting_contract(&contracts.fpt_token) .await @@ -20,12 +16,12 @@ async fn proper_intialize() { assert_eq!( vesting_contract, - contracts.vesting_contract.contract_id().into() + contracts.vesting_contract.contract.contract_id().into() ); let fpt_balance_vesting = provider .get_contract_asset_balance( - contracts.vesting_contract.contract_id().into(), + contracts.vesting_contract.contract.contract_id().into(), fpt_asset_id, ) .await @@ -39,7 +35,7 @@ async fn proper_intialize() { let fpt_balance_community_issuance = provider .get_contract_asset_balance( - contracts.community_issuance.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), fpt_asset_id, ) .await diff --git a/contracts/hint-helper-contract/Forc.toml b/contracts/hint-helper-contract/Forc.toml index 434cc299..da49b864 100644 --- a/contracts/hint-helper-contract/Forc.toml +++ b/contracts/hint-helper-contract/Forc.toml @@ -6,3 +6,6 @@ name = "hint-helper-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/hint-helper-contract/tests/harness.rs b/contracts/hint-helper-contract/tests/harness.rs index 4b3580bc..001073b4 100644 --- a/contracts/hint-helper-contract/tests/harness.rs +++ b/contracts/hint-helper-contract/tests/harness.rs @@ -1,4 +1,4 @@ -use fuels::{prelude::*, types::Identity}; +use fuels::types::Identity; use test_utils::interfaces::borrow_operations::borrow_operations_utils; use test_utils::interfaces::oracle::oracle_abi; use test_utils::interfaces::pyth_oracle::{pyth_oracle_abi, pyth_price_feed, PYTH_TIMESTAMP}; @@ -17,9 +17,12 @@ async fn proper_hint_generations() { let hint_helper = deploy_hint_helper(&wallet).await; - hint_helper_abi::initialize(&hint_helper, contracts.sorted_troves.contract_id().into()) - .await - .unwrap(); + hint_helper_abi::initialize( + &hint_helper, + contracts.sorted_troves.contract.contract_id().into(), + ) + .await + .unwrap(); // create 15 troves each with 600 USDF debt and n * 1000 collateral let mut target_address = Identity::Address(wallet.address().into()); diff --git a/contracts/mock-pyth-contract/Forc.toml b/contracts/mock-pyth-contract/Forc.toml index 48a23320..46b8877e 100644 --- a/contracts/mock-pyth-contract/Forc.toml +++ b/contracts/mock-pyth-contract/Forc.toml @@ -7,3 +7,6 @@ name = "mock-pyth-contract" [dependencies] libraries = { path = "../../libraries" } pyth_interface = { git = "https://github.com/pyth-network/pyth-crosschain", rev = "04280eae6822b6d52d9f3502f1038b638381b37f" } + +[proxy] +enabled = true diff --git a/contracts/mock-redstone-contract/Forc.toml b/contracts/mock-redstone-contract/Forc.toml index 03e69dcc..23e56396 100644 --- a/contracts/mock-redstone-contract/Forc.toml +++ b/contracts/mock-redstone-contract/Forc.toml @@ -6,3 +6,6 @@ name = "mock-redstone-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/multi-trove-getter-contract/Forc.toml b/contracts/multi-trove-getter-contract/Forc.toml index 2ede25f4..8e61bb14 100644 --- a/contracts/multi-trove-getter-contract/Forc.toml +++ b/contracts/multi-trove-getter-contract/Forc.toml @@ -6,3 +6,6 @@ name = "multi-trove-getter-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/multi-trove-getter-contract/tests/harness.rs b/contracts/multi-trove-getter-contract/tests/harness.rs index 39a4068f..d8e92486 100644 --- a/contracts/multi-trove-getter-contract/tests/harness.rs +++ b/contracts/multi-trove-getter-contract/tests/harness.rs @@ -12,8 +12,11 @@ async fn test_get_multiple_sorted_troves() { let (contracts, _admin, mut wallets) = setup_protocol(20, false, false).await; let wallet = wallets.pop().unwrap(); - let multi_trove_getter = - deploy_multi_trove_getter(&wallet, &contracts.sorted_troves.contract_id().into()).await; + let multi_trove_getter = deploy_multi_trove_getter( + &wallet, + &contracts.sorted_troves.contract.contract_id().into(), + ) + .await; // create 10 troves each with 600 USDF debt and n * 1000 collateral oracle_abi::set_debug_timestamp(&contracts.asset_contracts[0].oracle, PYTH_TIMESTAMP).await; diff --git a/contracts/oracle-contract/Forc.toml b/contracts/oracle-contract/Forc.toml index a3afec59..f538e466 100644 --- a/contracts/oracle-contract/Forc.toml +++ b/contracts/oracle-contract/Forc.toml @@ -7,3 +7,6 @@ name = "oracle-contract" [dependencies] libraries = { path = "../../libraries" } pyth_interface = { git = "https://github.com/pyth-network/pyth-crosschain", rev = "04280eae6822b6d52d9f3502f1038b638381b37f" } + +[proxy] +enabled = true diff --git a/contracts/oracle-contract/tests/authorization.rs b/contracts/oracle-contract/tests/authorization.rs index 11f52149..51b41622 100644 --- a/contracts/oracle-contract/tests/authorization.rs +++ b/contracts/oracle-contract/tests/authorization.rs @@ -1,5 +1,6 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ + data_structures::ContractInstance, interfaces::{ oracle::{oracle_abi, Oracle, RedstoneConfig}, pyth_oracle::{pyth_oracle_abi, Price, PythCore, DEFAULT_PYTH_PRICE_ID}, @@ -8,7 +9,7 @@ use test_utils::{ }; async fn setup() -> ( - Oracle, + ContractInstance>, PythCore, WalletUnlocked, WalletUnlocked, @@ -57,7 +58,14 @@ async fn test_set_redstone_config_authorization() { ); // Test 2: Unauthorized set_redstone_config - let oracle_attacker = Oracle::new(oracle.contract_id().clone(), attacker_wallet.clone()); + let oracle_attacker = ContractInstance::new( + Oracle::new( + oracle.contract.contract_id().clone(), + attacker_wallet.clone(), + ), + oracle.implementation_id, + ); + let result = oracle_abi::set_redstone_config(&oracle_attacker, &redstone, redstone_config.clone()).await; diff --git a/contracts/oracle-contract/tests/harness.rs b/contracts/oracle-contract/tests/harness.rs index 2a052f74..df88e53b 100644 --- a/contracts/oracle-contract/tests/harness.rs +++ b/contracts/oracle-contract/tests/harness.rs @@ -1,5 +1,6 @@ use fuels::types::U256; use fuels::{prelude::*, types::Identity}; +use test_utils::data_structures::ContractInstance; use test_utils::{ data_structures::PRECISION, interfaces::{ @@ -22,7 +23,7 @@ async fn setup( fuel_vm_decimals: u32, initialize_redstone: bool, ) -> ( - Oracle, + ContractInstance>, PythCore, Option>, ) { @@ -66,7 +67,8 @@ async fn setup( precision: redstone_precision, }, ) - .await; + .await + .unwrap(); return (oracle, pyth, Some(redstone)); } diff --git a/contracts/protocol-manager-contract/Forc.toml b/contracts/protocol-manager-contract/Forc.toml index f1ed2d32..5999b2a0 100644 --- a/contracts/protocol-manager-contract/Forc.toml +++ b/contracts/protocol-manager-contract/Forc.toml @@ -7,4 +7,7 @@ name = "protocol-manager-contract" [dependencies] libraries = { path = "../../libraries" } standards = { git = "https://github.com/FuelLabs/sway-standards", tag = "v0.6.1" } -sway_libs = { git = "https://github.com/FuelLabs/sway-libs", tag = "v0.23.1" } +sway_libs = { git = "https://github.com/FuelLabs/sway-libs", tag = "v0.24.0" } + +[proxy] +enabled = true diff --git a/contracts/protocol-manager-contract/tests/authorization.rs b/contracts/protocol-manager-contract/tests/authorization.rs index 1424a13d..58a98e1e 100644 --- a/contracts/protocol-manager-contract/tests/authorization.rs +++ b/contracts/protocol-manager-contract/tests/authorization.rs @@ -1,4 +1,5 @@ use test_utils::{ + data_structures::{ContractInstance, ExistingAssetContracts}, interfaces::protocol_manager::{protocol_manager_abi, ProtocolManager}, setup::common::{deploy_asset_contracts, initialize_asset, setup_protocol}, }; @@ -11,9 +12,12 @@ async fn test_authorizations() { let attacker = wallets.pop().unwrap(); // Test 1: Unauthorized renounce_admin - let protocol_manager_attacker = ProtocolManager::new( - contracts.protocol_manager.contract_id().clone(), - attacker.clone(), + let protocol_manager_attacker = ContractInstance::new( + ProtocolManager::new( + contracts.protocol_manager.contract.contract_id().clone(), + attacker.clone(), + ), + contracts.protocol_manager.implementation_id, ); let result = protocol_manager_abi::renounce_admin(&protocol_manager_attacker).await; @@ -30,7 +34,19 @@ async fn test_authorizations() { ); } // Test 2: Unauthorized register_asset - let asset_contracts = deploy_asset_contracts(&protocol_manager_owner, &None).await; + let existing_asset_to_initialize: ExistingAssetContracts = ExistingAssetContracts { + symbol: "".to_string(), + asset: None, + pyth_oracle: None, + redstone_oracle: None, + }; + let asset_contracts = deploy_asset_contracts( + &protocol_manager_owner, + &existing_asset_to_initialize, + true, + true, + ) + .await; contracts.protocol_manager = protocol_manager_attacker.clone(); let result = initialize_asset(&contracts, &asset_contracts).await; @@ -46,14 +62,30 @@ async fn test_authorizations() { ); } - let protocol_manager_owner_contract = ProtocolManager::new( - contracts.protocol_manager.contract_id().clone(), - protocol_manager_owner.clone(), + let protocol_manager_owner_contract = ContractInstance::new( + ProtocolManager::new( + contracts.protocol_manager.contract.contract_id().clone(), + protocol_manager_owner.clone(), + ), + contracts.protocol_manager.implementation_id, ); // Test 3: Authorized register_asset contracts.protocol_manager = protocol_manager_owner_contract.clone(); - let asset_contracts_owner = deploy_asset_contracts(&protocol_manager_owner, &None).await; + let existing_asset_to_initialize: ExistingAssetContracts = ExistingAssetContracts { + symbol: "".to_string(), + asset: None, + pyth_oracle: None, + redstone_oracle: None, + }; + + let asset_contracts_owner = deploy_asset_contracts( + &protocol_manager_owner, + &existing_asset_to_initialize, + true, + true, + ) + .await; let result = initialize_asset(&contracts, &asset_contracts_owner).await; assert!( @@ -65,8 +97,12 @@ async fn test_authorizations() { let result = protocol_manager_abi::register_asset( &protocol_manager_owner_contract, asset_contracts_owner.asset_id, - asset_contracts_owner.trove_manager.contract_id().into(), - asset_contracts_owner.oracle.contract_id().into(), + asset_contracts_owner + .trove_manager + .contract + .contract_id() + .into(), + asset_contracts_owner.oracle.contract.contract_id().into(), &contracts.borrow_operations, &contracts.stability_pool, &contracts.usdf, @@ -111,7 +147,19 @@ async fn test_authorizations() { ); // Verify old owner can't perform admin actions - let asset_contracts = deploy_asset_contracts(&protocol_manager_owner, &None).await; + let existing_asset_to_initialize: ExistingAssetContracts = ExistingAssetContracts { + symbol: "".to_string(), + asset: None, + pyth_oracle: None, + redstone_oracle: None, + }; + let asset_contracts = deploy_asset_contracts( + &protocol_manager_owner, + &existing_asset_to_initialize, + true, + true, + ) + .await; let result = initialize_asset(&contracts, &asset_contracts).await; assert!( result.is_err(), @@ -125,9 +173,12 @@ async fn test_authorizations() { ); } - let new_protocol_manager_owner = ProtocolManager::new( - contracts.protocol_manager.contract_id().clone(), - new_owner.clone(), + let new_protocol_manager_owner = ContractInstance::new( + ProtocolManager::new( + contracts.protocol_manager.contract.contract_id().clone(), + new_owner.clone(), + ), + contracts.protocol_manager.implementation_id, ); // Test 5: Authorized renounce_admin let result = protocol_manager_abi::renounce_admin(&new_protocol_manager_owner).await; @@ -138,7 +189,19 @@ async fn test_authorizations() { ); // Test 6: Unauthorized register_asset after renouncement - let unauthorized_asset_contracts = deploy_asset_contracts(&protocol_manager_owner, &None).await; + let existing_asset_to_initialize: ExistingAssetContracts = ExistingAssetContracts { + symbol: "".to_string(), + asset: None, + pyth_oracle: None, + redstone_oracle: None, + }; + let unauthorized_asset_contracts = deploy_asset_contracts( + &protocol_manager_owner, + &existing_asset_to_initialize, + true, + true, + ) + .await; let result = initialize_asset(&contracts, &unauthorized_asset_contracts).await; assert!( diff --git a/contracts/protocol-manager-contract/tests/success_redemptions.rs b/contracts/protocol-manager-contract/tests/success_redemptions.rs index e9eeea22..027834b4 100644 --- a/contracts/protocol-manager-contract/tests/success_redemptions.rs +++ b/contracts/protocol-manager-contract/tests/success_redemptions.rs @@ -1,5 +1,5 @@ use fuels::{prelude::*, types::Identity}; -use test_utils::data_structures::PRECISION; +use test_utils::data_structures::{ContractInstance, PRECISION}; use test_utils::interfaces::oracle::oracle_abi; use test_utils::interfaces::protocol_manager::ProtocolManager; use test_utils::interfaces::pyth_oracle::PYTH_TIMESTAMP; @@ -49,9 +49,12 @@ async fn proper_redemption_from_partially_closed() { ) .await; - let borrow_operations_healthy_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet1.clone(), + let borrow_operations_healthy_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); oracle_abi::set_debug_timestamp(&contracts.asset_contracts[0].oracle, PYTH_TIMESTAMP).await; @@ -80,9 +83,12 @@ async fn proper_redemption_from_partially_closed() { .await .unwrap(); - let borrow_operations_healthy_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet2.clone(), + let borrow_operations_healthy_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( @@ -104,9 +110,12 @@ async fn proper_redemption_from_partially_closed() { .await .unwrap(); - let borrow_operations_healthy_wallet3 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet3.clone(), + let borrow_operations_healthy_wallet3 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet3.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( @@ -130,9 +139,12 @@ async fn proper_redemption_from_partially_closed() { let redemption_amount: u64 = 3_000 * PRECISION; - let protocol_manager_health1 = ProtocolManager::new( - contracts.protocol_manager.contract_id().clone(), - healthy_wallet1.clone(), + let protocol_manager_health1 = ContractInstance::new( + ProtocolManager::new( + contracts.protocol_manager.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.protocol_manager.implementation_id, ); let pre_redemption_active_pool_debt = active_pool_abi::get_usdf_debt( @@ -224,7 +236,7 @@ async fn proper_redemption_from_partially_closed() { .unwrap(); let staking_balance = provider - .get_contract_asset_balance(contracts.fpt_staking.contract_id(), mock_asset_id) + .get_contract_asset_balance(&contracts.fpt_staking.contract.contract_id(), mock_asset_id) .await .unwrap(); @@ -280,9 +292,12 @@ async fn proper_redemption_with_a_trove_closed_fully() { ) .await; - let borrow_operations_healthy_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet1.clone(), + let borrow_operations_healthy_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let coll1 = 12_000 * PRECISION; @@ -314,9 +329,12 @@ async fn proper_redemption_with_a_trove_closed_fully() { .await .unwrap(); - let borrow_operations_healthy_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet2.clone(), + let borrow_operations_healthy_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let coll2: u64 = 9_000 * PRECISION; @@ -340,9 +358,12 @@ async fn proper_redemption_with_a_trove_closed_fully() { .await .unwrap(); - let borrow_operations_healthy_wallet3 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet3.clone(), + let borrow_operations_healthy_wallet3 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet3.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let coll3: u64 = 8_000 * PRECISION; @@ -371,9 +392,12 @@ async fn proper_redemption_with_a_trove_closed_fully() { let redemption_amount: u64 = 6_000 * PRECISION; - let protocol_manager_health1 = ProtocolManager::new( - contracts.protocol_manager.contract_id().clone(), - healthy_wallet1.clone(), + let protocol_manager_health1 = ContractInstance::new( + ProtocolManager::new( + contracts.protocol_manager.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.protocol_manager.implementation_id, ); oracle_abi::set_debug_timestamp(&contracts.asset_contracts[1].oracle, PYTH_TIMESTAMP).await; @@ -435,7 +459,7 @@ async fn proper_redemption_with_a_trove_closed_fully() { .unwrap(); let staking_balance = provider - .get_contract_asset_balance(&contracts.fpt_staking.contract_id(), mock_asset_id) + .get_contract_asset_balance(&contracts.fpt_staking.contract.contract_id(), mock_asset_id) .await .unwrap(); diff --git a/contracts/protocol-manager-contract/tests/success_redemptions_many.rs b/contracts/protocol-manager-contract/tests/success_redemptions_many.rs index 1da876a4..c66f519d 100644 --- a/contracts/protocol-manager-contract/tests/success_redemptions_many.rs +++ b/contracts/protocol-manager-contract/tests/success_redemptions_many.rs @@ -1,5 +1,5 @@ -use fuels::{prelude::*, types::Identity}; -use test_utils::data_structures::PRECISION; +use fuels::types::Identity; +use test_utils::data_structures::{ContractInstance, PRECISION}; use test_utils::interfaces::borrow_operations::borrow_operations_utils; use test_utils::interfaces::oracle::oracle_abi; use test_utils::interfaces::protocol_manager::ProtocolManager; @@ -115,9 +115,12 @@ async fn proper_multi_collateral_redemption_from_partially_closed() { let redemption_amount: u64 = 8_000 * PRECISION; - let protocol_manager_health1 = ProtocolManager::new( - contracts.protocol_manager.contract_id().clone(), - healthy_wallet1.clone(), + let protocol_manager_health1 = ContractInstance::new( + ProtocolManager::new( + contracts.protocol_manager.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.protocol_manager.implementation_id, ); let pre_redemption_active_pool_debt = active_pool_abi::get_usdf_debt( @@ -187,12 +190,15 @@ async fn proper_multi_collateral_redemption_from_partially_closed() { .unwrap(); let staking_balance = provider - .get_contract_asset_balance(&contracts.fpt_staking.contract_id(), mock_asset_id) + .get_contract_asset_balance(&contracts.fpt_staking.contract.contract_id(), mock_asset_id) .await .unwrap(); let fees2 = provider - .get_contract_asset_balance(&contracts.fpt_staking.contract_id(), st_mock_asset_id) + .get_contract_asset_balance( + &contracts.fpt_staking.contract.contract_id(), + st_mock_asset_id, + ) .await .unwrap(); diff --git a/contracts/proxy-contract/Cargo.toml b/contracts/proxy-contract/Cargo.toml new file mode 100644 index 00000000..79c65515 --- /dev/null +++ b/contracts/proxy-contract/Cargo.toml @@ -0,0 +1,17 @@ +[package] +name = "proxy-contract" +version = "0.1.0" +authors = ["hydrogen-labs"] +edition = "2021" +license = "Apache-2.0" + +[dependencies] +fuels = { workspace = true } +tokio = { workspace = true } +test-utils = { workspace = true } +# Not the latest version because of indexer bug o.o + +[[test]] +harness = true +name = "tests" +path = "tests/harness.rs" diff --git a/contracts/proxy-contract/Forc.toml b/contracts/proxy-contract/Forc.toml new file mode 100644 index 00000000..adced75f --- /dev/null +++ b/contracts/proxy-contract/Forc.toml @@ -0,0 +1,9 @@ +[project] +authors = ["hydrogen-labs"] +entry = "main.sw" +license = "Apache-2.0" +name = "proxy-contract" + +[dependencies] +standards = { git = "https://github.com/FuelLabs/sway-standards", tag = "v0.6.1" } +sway_libs = { git = "https://github.com/FuelLabs/sway-libs", tag = "v0.24.0" } diff --git a/contracts/proxy-contract/src/main.sw b/contracts/proxy-contract/src/main.sw new file mode 100644 index 00000000..7f0d4904 --- /dev/null +++ b/contracts/proxy-contract/src/main.sw @@ -0,0 +1,69 @@ +contract; + +use sway_libs::upgradability::{ + _proxy_owner, + _proxy_target, + _set_proxy_owner, + _set_proxy_target, + only_proxy_owner, +}; +use standards::{src14::{SRC14, SRC14Extension}, src5::State}; +use std::execution::run_external; + +storage { + SRC14 { + /// The [ContractId] of the target contract. + /// + /// # Additional Information + /// + /// `target` is stored at sha256("storage_SRC14_0") + target in 0x7bb458adc1d118713319a5baa00a2d049dd64d2916477d2688d76970c898cd55: Option = None, + /// The [State] of the proxy owner. + /// + /// # Additional Information + /// + /// `proxy_owner` is stored at sha256("storage_SRC14_1") + proxy_owner in 0xbb79927b15d9259ea316f2ecb2297d6cc8851888a98278c0a2e03e1a091ea754: State = State::Uninitialized, + }, +} + +abi ProxyOwner { + #[storage(read, write)] + fn set_proxy_owner(new_proxy_owner: State); +} + +impl SRC14 for Contract { + #[storage(read, write)] + fn set_proxy_target(new_target: ContractId) { + only_proxy_owner(); + _set_proxy_target(new_target); + } + + #[storage(read)] + fn proxy_target() -> Option { + _proxy_target() + } +} + +impl ProxyOwner for Contract { + #[storage(read, write)] + fn set_proxy_owner(new_proxy_owner: State) { + // checking twice because don't control sway_libs + only_proxy_owner(); + _set_proxy_owner(new_proxy_owner); + } +} + +impl SRC14Extension for Contract { + #[storage(read)] + fn proxy_owner() -> State { + _proxy_owner() + } +} + +#[fallback] +#[storage(read)] +fn fallback() { + // pass through any other method call to the target + run_external(_proxy_target().unwrap()) +} diff --git a/contracts/proxy-contract/tests/harness.rs b/contracts/proxy-contract/tests/harness.rs new file mode 100644 index 00000000..392617b7 --- /dev/null +++ b/contracts/proxy-contract/tests/harness.rs @@ -0,0 +1,100 @@ +use fuels::{prelude::*, types::Identity}; +use test_utils::{ + interfaces::proxy::{proxy_abi, Proxy, State}, + setup::common::deploy_proxy, +}; + +const DEFAULT_TARGET_CONTRACT_ID: [u8; 32] = [1u8; 32]; + +async fn get_contract_instance() -> (Proxy, WalletUnlocked, WalletUnlocked) { + // Launch a local network and deploy the contract + let mut wallets = launch_custom_provider_and_get_wallets( + WalletsConfig::new( + Some(2), /* Two wallets */ + Some(1), /* Single coin (UTXO) */ + Some(1_000_000_000), /* Amount per coin */ + ), + None, + None, + ) + .await + .unwrap(); + + let wallet2 = wallets.pop().unwrap(); + let wallet = wallets.pop().unwrap(); + + let instance = deploy_proxy( + ContractId::from(DEFAULT_TARGET_CONTRACT_ID), + wallet.clone(), + None, + ) + .await; + + (instance, wallet, wallet2) +} + +#[tokio::test] +async fn test_initial_state() { + let (proxy, _wallet, _wallet2) = get_contract_instance().await; + + let target = proxy_abi::get_proxy_target(&proxy).await.unwrap().value; + assert_eq!(target, Some(ContractId::from(DEFAULT_TARGET_CONTRACT_ID))); + + let owner = proxy_abi::get_proxy_owner(&proxy).await.unwrap().value; + assert_eq!( + owner, + State::Initialized(Identity::Address(_wallet.address().into())) + ); +} + +#[tokio::test] +async fn test_unauthorized_set_target() { + let (proxy, _wallet, wallet2) = get_contract_instance().await; + + // Try to set target with unauthorized wallet + let result = + proxy_abi::set_proxy_target(&proxy.with_account(wallet2), ContractId::from([2u8; 32])) + .await; + + assert!(result.is_err()); +} + +#[tokio::test] +async fn test_unauthorized_set_owner() { + let (proxy, _wallet, wallet2) = get_contract_instance().await; + + // Try to set owner with unauthorized wallet + let result = proxy_abi::set_proxy_owner( + &proxy.with_account(wallet2.clone()), + State::Initialized(Identity::Address(wallet2.address().into())), + ) + .await; + + assert!(result.is_err()); +} + +#[tokio::test] +async fn test_authorized_operations() { + let (proxy, wallet, _wallet2) = get_contract_instance().await; + + // Set initial owner + proxy_abi::set_proxy_owner( + &proxy, + State::Initialized(Identity::Address(wallet.address().into())), + ) + .await + .unwrap(); + + let owner = proxy_abi::get_proxy_owner(&proxy).await.unwrap().value; + assert_eq!( + owner, + State::Initialized(Identity::Address(wallet.address().into())) + ); + + // Set target + let target = ContractId::from([3u8; 32]); + proxy_abi::set_proxy_target(&proxy, target).await.unwrap(); + + let stored_target = proxy_abi::get_proxy_target(&proxy).await.unwrap().value; + assert_eq!(stored_target, Some(target)); +} diff --git a/contracts/proxy-contract/tests/sanity.rs b/contracts/proxy-contract/tests/sanity.rs new file mode 100644 index 00000000..27155c8b --- /dev/null +++ b/contracts/proxy-contract/tests/sanity.rs @@ -0,0 +1,362 @@ +use fuels::prelude::*; + +use test_utils::{ + interfaces::proxy::{proxy_abi, Proxy}, + setup::common::setup_protocol, +}; + +#[tokio::test] +async fn sanity_testing_setup() { + // Setup protocol with initial contracts + let (contracts, admin, mut other) = setup_protocol(2, false, false).await; + + let attacker = other.pop().unwrap(); + // Try to upgrade each contract with unauthorized wallet + let new_target = ContractId::from([3u8; 32]); + + let attacker_proxy_usdf = Proxy::new( + contracts.usdf.contract.contract_id().clone(), + attacker.clone(), + ); + // Test USDF token proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_usdf, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade USDF token" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_usdf = Proxy::new(contracts.usdf.contract.contract_id().clone(), admin.clone()); + // Verify admin can still upgrade (testing one contract as example) + let res = proxy_abi::set_proxy_target(&admin_proxy_usdf, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_borrow_operations = Proxy::new( + contracts.borrow_operations.contract.contract_id().clone(), + attacker.clone(), + ); + + // Test Borrow Operations proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_borrow_operations, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Borrow Operations" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + // verify admin can upgrade + let admin_proxy_sorted_troves = Proxy::new( + contracts.sorted_troves.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_sorted_troves, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_sorted_troves = Proxy::new( + contracts.sorted_troves.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Sorted Troves proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_sorted_troves, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Sorted Troves" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_active_pool = Proxy::new( + contracts.active_pool.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_active_pool, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_active_pool = Proxy::new( + contracts.active_pool.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Active Pool proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_active_pool, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Active Pool" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_default_pool = Proxy::new( + contracts.default_pool.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_default_pool, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_default_pool = Proxy::new( + contracts.default_pool.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Default Pool proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_default_pool, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Default Pool" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_fpt_staking = Proxy::new( + contracts.fpt_staking.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_fpt_staking, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_fpt_staking = Proxy::new( + contracts.fpt_staking.contract.contract_id().clone(), + attacker.clone(), + ); + // Test FPT Staking proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_fpt_staking, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade FPT Staking" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_fpt_token = Proxy::new( + contracts.fpt_token.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_fpt_token, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + // Test each asset contract's components + for asset_contract in &contracts.asset_contracts { + let attacker_proxy_trove_manager = Proxy::new( + asset_contract.trove_manager.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Trove Manager proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_trove_manager, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Trove Manager" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_oracle = Proxy::new( + asset_contract.oracle.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_oracle, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_oracle = Proxy::new( + asset_contract.oracle.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Oracle proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_oracle, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Oracle" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_oracle = Proxy::new( + asset_contract.oracle.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_oracle, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + } + + let admin_proxy_stability_pool = Proxy::new( + contracts.stability_pool.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_stability_pool, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_stability_pool = Proxy::new( + contracts.stability_pool.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Stability Pool proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_stability_pool, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Stability Pool" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let attacker_proxy_coll_surplus_pool = Proxy::new( + contracts.coll_surplus_pool.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Collateral Surplus Pool proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_coll_surplus_pool, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Collateral Surplus Pool" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_community_issuance = Proxy::new( + contracts.community_issuance.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_community_issuance, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_community_issuance = Proxy::new( + contracts.community_issuance.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Community Issuance proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_community_issuance, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Community Issuance" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_vesting = Proxy::new( + contracts.vesting_contract.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_vesting, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_vesting = Proxy::new( + contracts.vesting_contract.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Vesting proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_vesting, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Vesting" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_protocol_manager = Proxy::new( + contracts.protocol_manager.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_protocol_manager, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_protocol_manager = Proxy::new( + contracts.protocol_manager.contract.contract_id().clone(), + attacker.clone(), + ); + // Test Protocol Manager proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_protocol_manager, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade Protocol Manager" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } + + let admin_proxy_fpt_token = Proxy::new( + contracts.fpt_token.contract.contract_id().clone(), + admin.clone(), + ); + let res = proxy_abi::set_proxy_target(&admin_proxy_fpt_token, new_target).await; + assert!(res.is_ok(), "Admin should be able to upgrade contracts"); + + let attacker_proxy_fpt_token = Proxy::new( + contracts.fpt_token.contract.contract_id().clone(), + attacker.clone(), + ); + // Test FPT Token proxy + let res = proxy_abi::set_proxy_target(&attacker_proxy_fpt_token, new_target).await; + assert!( + res.is_err(), + "Unauthorized wallet should not be able to upgrade FPT Token" + ); + if let Err(error) = res { + assert!( + error.to_string().contains("NotOwner"), + "Unexpected error message: {}", + error + ); + } +} diff --git a/contracts/sorted-troves-contract/Forc.toml b/contracts/sorted-troves-contract/Forc.toml index fc6071f9..823e99a6 100644 --- a/contracts/sorted-troves-contract/Forc.toml +++ b/contracts/sorted-troves-contract/Forc.toml @@ -6,3 +6,6 @@ name = "sorted-troves-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/sorted-troves-contract/tests/functions/sort.rs b/contracts/sorted-troves-contract/tests/functions/sort.rs index 8a25fd0d..b7fc31bd 100644 --- a/contracts/sorted-troves-contract/tests/functions/sort.rs +++ b/contracts/sorted-troves-contract/tests/functions/sort.rs @@ -6,6 +6,7 @@ use fuels::types::AssetId; use fuels::{prelude::*, types::Identity}; use rand::{self, Rng}; use test_utils::interfaces::sorted_troves::sorted_troves_abi; +use test_utils::interfaces::trove_manager::TroveManagerContract; #[tokio::test] async fn proper_initialization() { @@ -16,28 +17,18 @@ async fn proper_initialization() { let _ = initialize_st_and_tm(&sorted_troves, &trove_manager, max_size, asset).await; // Get the current value of the counter - let result = sorted_troves.methods().get_max_size().call().await.unwrap(); + let result = sorted_troves_abi::get_max_size(&sorted_troves).await; assert_eq!(result.value, max_size); - let result_size = sorted_troves - .methods() - .get_size(asset.into()) - .call() - .await - .unwrap(); + let result_size = sorted_troves_abi::get_size(&sorted_troves, asset).await; assert_eq!(result_size.value, 0); let first = sorted_troves_abi::get_first(&sorted_troves, asset).await; assert_eq!(first.value, Identity::Address(Address::zeroed())); - let last = sorted_troves - .methods() - .get_last(asset.into()) - .call() - .await - .unwrap(); + let last = sorted_troves_abi::get_last(&sorted_troves, asset).await; assert_eq!(last.value, Identity::Address(Address::zeroed())); } @@ -49,32 +40,29 @@ async fn proper_head_and_tails_after_insert() { // Increment the counter let _ = initialize_st_and_tm(&sorted_troves, &trove_manager, max_size, asset.into()).await; + let trove_manager_wrapped = + TroveManagerContract::new(trove_manager.contract_id(), wallet2.clone()); + // Get the current value of the counter // check if contains - let result = sorted_troves - .methods() - .contains(Identity::Address(wallet.address().into()), asset.into()) - .call() - .await - .unwrap(); + let result = sorted_troves_abi::contains( + &sorted_troves, + Identity::Address(wallet.address().into()), + asset.into(), + ) + .await; assert_eq!(result.value, false); - let tx_params = TxPolicies::default().with_tip(1); - - let result = sorted_troves - .methods() - .find_insert_position( - 100, - Identity::Address(Address::zeroed()), - Identity::Address(Address::zeroed()), - asset.into(), - ) - .with_contracts(&[&trove_manager]) - .with_tx_policies(tx_params) - .simulate(Execution::Realistic) - .await - .unwrap(); + let result = sorted_troves_abi::find_insert_position( + &sorted_troves, + &trove_manager_wrapped, + 100, + Identity::Address(Address::zeroed()), + Identity::Address(Address::zeroed()), + asset.into(), + ) + .await; assert_eq!( result.value, @@ -99,12 +87,7 @@ async fn proper_head_and_tails_after_insert() { // State: // (100, wallet) - let result_size = sorted_troves - .methods() - .get_size(asset.into()) - .call() - .await - .unwrap(); + let result_size = sorted_troves_abi::get_size(&sorted_troves, asset).await; assert_eq!(result_size.value, 1); let first = sorted_troves_abi::get_first(&sorted_troves, asset).await; @@ -114,12 +97,8 @@ async fn proper_head_and_tails_after_insert() { "first should be wallet" ); - let last = sorted_troves - .methods() - .get_last(asset.into()) - .call() - .await - .unwrap(); + let last = sorted_troves_abi::get_last(&sorted_troves, asset).await; + assert_eq!(last.value, Identity::Address(wallet.address().into())); let _res = set_nominal_icr_and_insert( @@ -136,12 +115,7 @@ async fn proper_head_and_tails_after_insert() { // State: // (200, wallet2) -> (100, wallet) - let result_size = sorted_troves - .methods() - .get_size(asset.into()) - .call() - .await - .unwrap(); + let result_size = sorted_troves_abi::get_size(&sorted_troves, asset).await; assert_eq!(result_size.value, 2); let first = sorted_troves_abi::get_first(&sorted_troves, asset).await; @@ -151,12 +125,8 @@ async fn proper_head_and_tails_after_insert() { "First should be wallet2" ); - let last = sorted_troves - .methods() - .get_last(asset.into()) - .call() - .await - .unwrap(); + let last = sorted_troves_abi::get_last(&sorted_troves, asset).await; + assert_eq!( last.value, Identity::Address(wallet.address().into()), @@ -177,12 +147,7 @@ async fn proper_head_and_tails_after_insert() { // State: // (300, trove_manager) -> (200, wallet2) -> (100, wallet) - let result_size = sorted_troves - .methods() - .get_size(asset.into()) - .call() - .await - .unwrap(); + let result_size = sorted_troves_abi::get_size(&sorted_troves, asset).await; assert_eq!(result_size.value, 3); let first = sorted_troves_abi::get_first(&sorted_troves, asset).await; @@ -192,12 +157,7 @@ async fn proper_head_and_tails_after_insert() { "First should be trove manager" ); - let last = sorted_troves - .methods() - .get_last(asset.into()) - .call() - .await - .unwrap(); + let last = sorted_troves_abi::get_last(&sorted_troves, asset).await; assert_eq!( last.value, Identity::Address(wallet.address().into()), @@ -207,7 +167,7 @@ async fn proper_head_and_tails_after_insert() { let _res = set_nominal_icr_and_insert( &trove_manager, &sorted_troves, - Identity::ContractId(sorted_troves.contract_id().into()), + Identity::ContractId(sorted_troves.contract.contract_id().into()), 150, Identity::Address(Address::zeroed()), Identity::Address(Address::zeroed()), @@ -217,12 +177,7 @@ async fn proper_head_and_tails_after_insert() { // State: // (300, trove_manager) -> (200, wallet2) -> (150, sorted_troves) -> (100, wallet) - let result_size = sorted_troves - .methods() - .get_size(asset.into()) - .call() - .await - .unwrap(); + let result_size = sorted_troves_abi::get_size(&sorted_troves, asset).await; assert_eq!(result_size.value, 4); let first = sorted_troves_abi::get_first(&sorted_troves, asset).await; @@ -233,12 +188,7 @@ async fn proper_head_and_tails_after_insert() { "First should be trove manager" ); - let last = sorted_troves - .methods() - .get_last(asset.into()) - .call() - .await - .unwrap(); + let last = sorted_troves_abi::get_last(&sorted_troves, asset).await; assert_eq!( last.value, Identity::Address(wallet.address().into()), @@ -324,7 +274,7 @@ async fn proper_node_neighbors() { let _res = set_nominal_icr_and_insert( &trove_manager, &sorted_troves, - Identity::ContractId(sorted_troves.contract_id().into()), + Identity::ContractId(sorted_troves.contract.contract_id().into()), 150, Identity::Address(Address::zeroed()), Identity::Address(Address::zeroed()), @@ -337,7 +287,7 @@ async fn proper_node_neighbors() { let _ = assert_neighbors( &sorted_troves, - Identity::ContractId(sorted_troves.contract_id().into()), + Identity::ContractId(sorted_troves.contract.contract_id().into()), Identity::Address(wallet2.address().into()), Identity::Address(wallet.address().into()), asset, diff --git a/contracts/sorted-troves-contract/tests/utils/setup.rs b/contracts/sorted-troves-contract/tests/utils/setup.rs index 9fcfc52e..b2c4c962 100644 --- a/contracts/sorted-troves-contract/tests/utils/setup.rs +++ b/contracts/sorted-troves-contract/tests/utils/setup.rs @@ -2,6 +2,7 @@ use fuels::prelude::*; use fuels::programs::responses::CallResponse; use fuels::types::Identity; use rand::{self, Rng}; +use test_utils::data_structures::ContractInstance; use test_utils::interfaces::sorted_troves::{sorted_troves_abi::initialize, SortedTroves}; use test_utils::setup::common::{deploy_sorted_troves, get_absolute_path_from_relative}; @@ -34,7 +35,7 @@ pub async fn deploy_mock_trove_manager_contract( pub async fn set_nominal_icr_and_insert( trove_manager: &MockTroveManagerContract, - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, new_id: Identity, new_icr: u64, prev_id: Identity, @@ -46,7 +47,11 @@ pub async fn set_nominal_icr_and_insert( trove_manager .methods() .set_nominal_icr_and_insert(new_id, new_icr, prev_id, next_id, asset.into()) - .with_contracts(&[sorted_troves]) + .with_contracts(&[&sorted_troves.contract]) + .with_contract_ids(&[ + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -67,7 +72,7 @@ pub async fn get_nominal_icr( pub async fn remove( trove_manager: &MockTroveManagerContract, - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, id: Identity, asset: AssetId, ) -> CallResponse<()> { @@ -76,7 +81,11 @@ pub async fn remove( trove_manager .methods() .remove(id, asset.into()) - .with_contracts(&[sorted_troves]) + .with_contracts(&[&sorted_troves.contract]) + .with_contract_ids(&[ + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -86,7 +95,7 @@ pub async fn remove( pub async fn setup( num_wallets: Option, ) -> ( - SortedTroves, + ContractInstance>, MockTroveManagerContract, WalletUnlocked, WalletUnlocked, @@ -122,7 +131,7 @@ pub async fn setup( } pub async fn initialize_st_and_tm( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, trove_manager: &MockTroveManagerContract, max_size: u64, asset: AssetId, @@ -139,14 +148,14 @@ pub async fn initialize_st_and_tm( trove_manager .methods() .initialize( - sorted_troves.contract_id(), - sorted_troves.contract_id(), - sorted_troves.contract_id(), - sorted_troves.contract_id(), - sorted_troves.contract_id(), - sorted_troves.contract_id(), - sorted_troves.contract_id(), - sorted_troves.contract_id(), + sorted_troves.contract.contract_id(), + sorted_troves.contract.contract_id(), + sorted_troves.contract.contract_id(), + sorted_troves.contract.contract_id(), + sorted_troves.contract.contract_id(), + sorted_troves.contract.contract_id(), + sorted_troves.contract.contract_id(), + sorted_troves.contract.contract_id(), ) .call() .await @@ -155,7 +164,11 @@ pub async fn initialize_st_and_tm( trove_manager .methods() .add_asset(asset.into(), trove_manager.contract_id()) - .with_contracts(&[sorted_troves]) + .with_contracts(&[&sorted_troves.contract]) + .with_contract_ids(&[ + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + ]) .call() .await .unwrap(); diff --git a/contracts/sorted-troves-contract/tests/utils/sorted_troves.rs b/contracts/sorted-troves-contract/tests/utils/sorted_troves.rs index 9f1a8bbe..c385e5a8 100644 --- a/contracts/sorted-troves-contract/tests/utils/sorted_troves.rs +++ b/contracts/sorted-troves-contract/tests/utils/sorted_troves.rs @@ -10,13 +10,14 @@ pub mod sorted_troves_utils { types::{Address, AssetId}, }; use rand::{self, Rng}; + use test_utils::data_structures::ContractInstance; use crate::utils::setup::{get_nominal_icr, set_nominal_icr_and_insert}; use super::*; pub async fn assert_neighbors( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, current: Identity, prev_id: Identity, next_id: Identity, @@ -30,7 +31,7 @@ pub mod sorted_troves_utils { } pub async fn assert_in_order_from_head( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, trove_manager: &MockTroveManagerContract, asset: AssetId, ) { @@ -72,7 +73,7 @@ pub mod sorted_troves_utils { } pub async fn assert_in_order_from_tail( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, trove_manager: &MockTroveManagerContract, asset: AssetId, ) { @@ -109,7 +110,7 @@ pub mod sorted_troves_utils { pub async fn generate_random_nodes( trove_manager: &MockTroveManagerContract, - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, max_size: u64, asset: AssetId, ) -> (Vec<(Identity, u64)>, u64) { diff --git a/contracts/stability-pool-contract/Forc.toml b/contracts/stability-pool-contract/Forc.toml index c5e2c31c..4dd5e39f 100644 --- a/contracts/stability-pool-contract/Forc.toml +++ b/contracts/stability-pool-contract/Forc.toml @@ -7,3 +7,6 @@ name = "stability-pool-contract" [dependencies] libraries = { path = "../../libraries" } standards = { git = "https://github.com/FuelLabs/sway-standards", tag = "v0.6.1" } + +[proxy] +enabled = true diff --git a/contracts/stability-pool-contract/tests/functions/failure.rs b/contracts/stability-pool-contract/tests/functions/failure.rs index 9ec4a62f..fccc49cd 100644 --- a/contracts/stability-pool-contract/tests/functions/failure.rs +++ b/contracts/stability-pool-contract/tests/functions/failure.rs @@ -1,6 +1,6 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ borrow_operations::borrow_operations_utils, oracle::oracle_abi, @@ -53,9 +53,12 @@ async fn fails_unauthorized() { let attacker = wallets.pop().unwrap(); - let stability_pool_attacker = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - attacker.clone(), + let stability_pool_attacker = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + attacker.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::initialize( diff --git a/contracts/stability-pool-contract/tests/functions/success.rs b/contracts/stability-pool-contract/tests/functions/success.rs index 7ff6238e..153ec6fd 100644 --- a/contracts/stability-pool-contract/tests/functions/success.rs +++ b/contracts/stability-pool-contract/tests/functions/success.rs @@ -1,7 +1,7 @@ use crate::utils::setup::setup; use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ borrow_operations::{borrow_operations_abi, borrow_operations_utils, BorrowOperations}, oracle::oracle_abi, @@ -14,7 +14,7 @@ use test_utils::{ trove_manager::trove_manager_abi, }, setup::common::{add_asset, assert_within_threshold, setup_protocol}, - utils::{print_response, with_min_borrow_fee}, + utils::with_min_borrow_fee, }; #[tokio::test] @@ -284,9 +284,12 @@ async fn proper_one_sp_depositor_position() { .await .unwrap(); - let liq_borrow_operations = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let liq_borrow_operations = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( @@ -480,9 +483,12 @@ async fn proper_many_depositors_distribution() { .await .unwrap(); - let liq_borrow_operations = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let liq_borrow_operations = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( @@ -514,11 +520,7 @@ async fn proper_many_depositors_distribution() { .await .unwrap(); - let usdf_asset_id: AssetId = contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let usdf_asset_id: AssetId = contracts.usdf_asset_id; let tx_params = TxPolicies::default().with_tip(1); admin @@ -541,14 +543,20 @@ async fn proper_many_depositors_distribution() { .await .unwrap(); - let depositor_2_sp = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - depositor_2.clone(), + let depositor_2_sp = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + depositor_2.clone(), + ), + contracts.stability_pool.implementation_id, ); - let depositor_3_sp = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - depositor_3.clone(), + let depositor_3_sp = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + depositor_3.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::provide_to_stability_pool( @@ -703,9 +711,12 @@ async fn proper_no_reward_when_depositing_and_rewards_already_distributed() { .await .unwrap(); - let liq_borrow_operations = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let liq_borrow_operations = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( @@ -737,11 +748,7 @@ async fn proper_no_reward_when_depositing_and_rewards_already_distributed() { .await .unwrap(); - let usdf_asset_id: AssetId = contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(); + let usdf_asset_id: AssetId = contracts.usdf_asset_id; let tx_params = TxPolicies::default().with_tip(1); oracle_abi::set_debug_timestamp(&contracts.asset_contracts[0].oracle, PYTH_TIMESTAMP + 1).await; @@ -780,9 +787,12 @@ async fn proper_no_reward_when_depositing_and_rewards_already_distributed() { .await .unwrap(); - let depositor_2_sp = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - depositor_2.clone(), + let depositor_2_sp = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + depositor_2.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::provide_to_stability_pool( diff --git a/contracts/stability-pool-contract/tests/utils/setup.rs b/contracts/stability-pool-contract/tests/utils/setup.rs index 228458f0..1f8d16d4 100644 --- a/contracts/stability-pool-contract/tests/utils/setup.rs +++ b/contracts/stability-pool-contract/tests/utils/setup.rs @@ -3,7 +3,8 @@ use rand::{self, Rng}; use fuels::programs::responses::CallResponse; use fuels::types::Identity; -use test_utils::interfaces::sorted_troves::{self, SortedTroves}; +use test_utils::data_structures::ContractInstance; +use test_utils::interfaces::sorted_troves::SortedTroves; use test_utils::interfaces::stability_pool::{stability_pool_abi, StabilityPool}; use test_utils::interfaces::token::{token_abi, Token}; use test_utils::setup::common::{ @@ -133,7 +134,7 @@ pub async fn remove( pub async fn setup( num_wallets: Option, ) -> ( - StabilityPool, + ContractInstance>, MockTroveManagerContract, Token, WalletUnlocked, @@ -195,9 +196,9 @@ pub async fn setup( stability_pool_abi::initialize( &stability_pool, usdf_token.contract_id().into(), - stability_pool.contract_id().into(), + stability_pool.contract.contract_id().into(), mock_token.contract_id().into(), - active_pool.contract_id().into(), + active_pool.contract.contract_id().into(), sorted_troves.contract_id().into(), ) .await @@ -205,9 +206,9 @@ pub async fn setup( initialize( &trove_instance, - stability_pool.contract_id().into(), - stability_pool.contract_id().into(), - stability_pool.contract_id().into(), + stability_pool.contract.contract_id().into(), + stability_pool.contract.contract_id().into(), + stability_pool.contract.contract_id().into(), ) .await .unwrap(); diff --git a/contracts/tests-artifacts-sorted-troves-contract/Forc.toml b/contracts/tests-artifacts-sorted-troves-contract/Forc.toml index cd8df578..f7237ead 100644 --- a/contracts/tests-artifacts-sorted-troves-contract/Forc.toml +++ b/contracts/tests-artifacts-sorted-troves-contract/Forc.toml @@ -6,3 +6,6 @@ name = "mock-trove-manager-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/tests-artifacts-stability-pool-contract/Forc.toml b/contracts/tests-artifacts-stability-pool-contract/Forc.toml index 6b4fb608..81f2fe53 100644 --- a/contracts/tests-artifacts-stability-pool-contract/Forc.toml +++ b/contracts/tests-artifacts-stability-pool-contract/Forc.toml @@ -6,3 +6,6 @@ name = "mock-trove-manager-sp-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/token-contract/Forc.toml b/contracts/token-contract/Forc.toml index 4ccedeea..f24f900e 100644 --- a/contracts/token-contract/Forc.toml +++ b/contracts/token-contract/Forc.toml @@ -6,3 +6,6 @@ name = "token-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/trove-manager-contract/Forc.toml b/contracts/trove-manager-contract/Forc.toml index d57a50d5..5ab6b939 100644 --- a/contracts/trove-manager-contract/Forc.toml +++ b/contracts/trove-manager-contract/Forc.toml @@ -7,3 +7,6 @@ name = "trove-manager-contract" [dependencies] libraries = { path = "../../libraries" } standards = { git = "https://github.com/FuelLabs/sway-standards", tag = "v0.6.1" } + +[proxy] +enabled = true diff --git a/contracts/trove-manager-contract/tests/failure.rs b/contracts/trove-manager-contract/tests/failure.rs index 45c50fd8..a430251c 100644 --- a/contracts/trove-manager-contract/tests/failure.rs +++ b/contracts/trove-manager-contract/tests/failure.rs @@ -1,6 +1,6 @@ use fuels::types::{Address, Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ borrow_operations::{borrow_operations_abi, BorrowOperations}, oracle::oracle_abi, @@ -32,9 +32,12 @@ async fn fails_to_liquidate_trove_not_under_mcr() { ) .await; - let borrow_operations_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet1.clone(), + let borrow_operations_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( diff --git a/contracts/trove-manager-contract/tests/success_batch_liquidations.rs b/contracts/trove-manager-contract/tests/success_batch_liquidations.rs index 30591658..a77d0245 100644 --- a/contracts/trove-manager-contract/tests/success_batch_liquidations.rs +++ b/contracts/trove-manager-contract/tests/success_batch_liquidations.rs @@ -1,7 +1,7 @@ use fuels::prelude::*; use fuels::types::Identity; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ active_pool::active_pool_abi, borrow_operations::borrow_operations_utils, @@ -76,9 +76,12 @@ async fn proper_batch_liquidations_enough_usdf_in_sp() { ) .await; - let stability_pool_healthy_wallet1 = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - healthy_wallet1.clone(), + let stability_pool_healthy_wallet1 = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::provide_to_stability_pool( diff --git a/contracts/trove-manager-contract/tests/success_full_liquidations.rs b/contracts/trove-manager-contract/tests/success_full_liquidations.rs index 650040c1..a74b91b6 100644 --- a/contracts/trove-manager-contract/tests/success_full_liquidations.rs +++ b/contracts/trove-manager-contract/tests/success_full_liquidations.rs @@ -3,13 +3,13 @@ use std::cmp::min; use fuels::prelude::*; use fuels::types::Identity; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ active_pool::active_pool_abi, borrow_operations::{borrow_operations_abi, BorrowOperations}, coll_surplus_pool::coll_surplus_pool_abi, default_pool::default_pool_abi, - multi_trove_getter::{multi_trove_getter_abi, multi_trove_getter_utils}, + multi_trove_getter::multi_trove_getter_utils, oracle::oracle_abi, pyth_oracle::{ pyth_oracle_abi, pyth_price_feed, pyth_price_feed_with_time, PYTH_PRECISION, @@ -52,14 +52,20 @@ async fn proper_full_liquidation_enough_usdf_in_sp() { ) .await; - let borrow_operations_liquidated_wallet = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let borrow_operations_liquidated_wallet = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet1.clone(), + let borrow_operations_healthy_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let usdf_deposit_to_be_liquidated = 1_000 * PRECISION; @@ -103,9 +109,12 @@ async fn proper_full_liquidation_enough_usdf_in_sp() { .await .unwrap(); - let stability_pool_healthy_wallet1 = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - healthy_wallet1.clone(), + let stability_pool_healthy_wallet1 = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::provide_to_stability_pool( @@ -308,19 +317,28 @@ async fn proper_full_liquidation_partial_usdf_in_sp() { ) .await; - let borrow_operations_liquidated_wallet = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let borrow_operations_liquidated_wallet = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet1.clone(), + let borrow_operations_healthy_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet2.clone(), + let borrow_operations_healthy_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( @@ -382,9 +400,12 @@ async fn proper_full_liquidation_partial_usdf_in_sp() { .await .unwrap(); - let stability_pool_healthy_wallet1 = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - healthy_wallet1.clone(), + let stability_pool_healthy_wallet1 = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::provide_to_stability_pool( @@ -604,19 +625,28 @@ async fn proper_full_liquidation_empty_sp() { ) .await; - let borrow_operations_liquidated_wallet = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let borrow_operations_liquidated_wallet = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet1.clone(), + let borrow_operations_healthy_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet2.clone(), + let borrow_operations_healthy_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( @@ -844,8 +874,11 @@ async fn proper_full_liquidation_empty_sp() { async fn test_trove_sorting_after_liquidation_and_rewards() { let (contracts, admin, mut wallets) = setup_protocol(5, false, false).await; - let multi_trove_getter = - deploy_multi_trove_getter(&admin, &contracts.sorted_troves.contract_id().into()).await; + let multi_trove_getter = deploy_multi_trove_getter( + &admin, + &contracts.sorted_troves.contract.contract_id().into(), + ) + .await; oracle_abi::set_debug_timestamp(&contracts.asset_contracts[0].oracle, PYTH_TIMESTAMP).await; pyth_oracle_abi::update_price_feeds( @@ -868,17 +901,26 @@ async fn test_trove_sorting_after_liquidation_and_rewards() { .await; } - let borrow_operations_a = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet_a.clone(), + let borrow_operations_a = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet_a.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_b = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet_b.clone(), + let borrow_operations_b = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet_b.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_c = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet_c.clone(), + let borrow_operations_c = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet_c.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); // Open troveA diff --git a/contracts/trove-manager-contract/tests/success_partial_liquidations.rs b/contracts/trove-manager-contract/tests/success_partial_liquidations.rs index 6a627354..450e014d 100644 --- a/contracts/trove-manager-contract/tests/success_partial_liquidations.rs +++ b/contracts/trove-manager-contract/tests/success_partial_liquidations.rs @@ -1,7 +1,7 @@ use fuels::prelude::*; use fuels::types::Identity; use test_utils::{ - data_structures::{POST_LIQUIDATION_COLLATERAL_RATIO, PRECISION}, + data_structures::{ContractInstance, POST_LIQUIDATION_COLLATERAL_RATIO, PRECISION}, interfaces::{ active_pool::active_pool_abi, borrow_operations::{borrow_operations_abi, BorrowOperations}, @@ -49,14 +49,20 @@ async fn proper_partial_liquidation_enough_usdf_in_sp() { ) .await; - let borrow_operations_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet1.clone(), + let borrow_operations_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - wallet2.clone(), + let borrow_operations_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); borrow_operations_abi::open_trove( @@ -98,9 +104,12 @@ async fn proper_partial_liquidation_enough_usdf_in_sp() { .await .unwrap(); - let stability_pool_wallet2 = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - wallet2.clone(), + let stability_pool_wallet2 = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + wallet2.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::provide_to_stability_pool( @@ -271,19 +280,28 @@ async fn proper_partial_liquidation_partial_usdf_in_sp() { ) .await; - let borrow_operations_liquidated_wallet = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let borrow_operations_liquidated_wallet = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet1.clone(), + let borrow_operations_healthy_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet2.clone(), + let borrow_operations_healthy_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let starting_col: u64 = 12_000 * PRECISION; @@ -348,9 +366,12 @@ async fn proper_partial_liquidation_partial_usdf_in_sp() { .await .unwrap(); - let stability_pool_healthy_wallet1 = StabilityPool::new( - contracts.stability_pool.contract_id().clone(), - healthy_wallet1.clone(), + let stability_pool_healthy_wallet1 = ContractInstance::new( + StabilityPool::new( + contracts.stability_pool.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.stability_pool.implementation_id, ); stability_pool_abi::provide_to_stability_pool( @@ -613,19 +634,28 @@ async fn proper_partial_liquidation_empty_sp() { ) .await; - let borrow_operations_liquidated_wallet = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - liquidated_wallet.clone(), + let borrow_operations_liquidated_wallet = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + liquidated_wallet.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet1 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet1.clone(), + let borrow_operations_healthy_wallet1 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet1.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); - let borrow_operations_healthy_wallet2 = BorrowOperations::new( - contracts.borrow_operations.contract_id().clone(), - healthy_wallet2.clone(), + let borrow_operations_healthy_wallet2 = ContractInstance::new( + BorrowOperations::new( + contracts.borrow_operations.contract.contract_id().clone(), + healthy_wallet2.clone(), + ), + contracts.borrow_operations.implementation_id.clone(), ); let starting_col: u64 = 12_000 * PRECISION; diff --git a/contracts/usdf-token-contract/Forc.toml b/contracts/usdf-token-contract/Forc.toml index a6a058fd..87ed9442 100644 --- a/contracts/usdf-token-contract/Forc.toml +++ b/contracts/usdf-token-contract/Forc.toml @@ -7,3 +7,6 @@ name = "usdf-token-contract" [dependencies] libraries = { path = "../../libraries" } standards = { git = "https://github.com/FuelLabs/sway-standards", tag = "v0.6.1" } + +[proxy] +enabled = true diff --git a/contracts/usdf-token-contract/tests/harness.rs b/contracts/usdf-token-contract/tests/harness.rs index b700f2e2..ff9f079d 100644 --- a/contracts/usdf-token-contract/tests/harness.rs +++ b/contracts/usdf-token-contract/tests/harness.rs @@ -1,7 +1,7 @@ use fuels::{prelude::*, types::Identity}; use test_utils::{ - data_structures::PRECISION, + data_structures::{ContractInstance, PRECISION}, interfaces::{ active_pool::{active_pool_abi, ActivePool}, default_pool::{default_pool_abi, DefaultPool}, @@ -12,10 +12,10 @@ use test_utils::{ }; async fn get_contract_instance() -> ( - DefaultPool, + ContractInstance>, Token, WalletUnlocked, - ActivePool, + ContractInstance>, ) { // Launch a local network and deploy the contract let mut wallets = launch_custom_provider_and_get_wallets( @@ -31,7 +31,7 @@ async fn get_contract_instance() -> ( .unwrap(); let wallet = wallets.pop().unwrap(); - let instance = deploy_default_pool(&wallet).await; + let default_pool = deploy_default_pool(&wallet).await; let active_pool = deploy_active_pool(&wallet).await; let asset = deploy_token(&wallet).await; @@ -47,9 +47,9 @@ async fn get_contract_instance() -> ( .unwrap(); default_pool_abi::initialize( - &instance, + &default_pool, Identity::Address(wallet.address().into()), - active_pool.contract_id().into(), + active_pool.contract.contract_id().into(), ) .await .unwrap(); @@ -58,7 +58,7 @@ async fn get_contract_instance() -> ( &active_pool, Identity::Address(wallet.address().into()), Identity::Address(wallet.address().into()), - instance.contract_id().into(), + default_pool.contract.contract_id().into(), Identity::Address(wallet.address().into()), ) .await @@ -75,7 +75,7 @@ async fn get_contract_instance() -> ( .await; default_pool_abi::add_asset( - &instance, + &default_pool, asset .contract_id() .asset_id(&AssetId::zeroed().into()) @@ -84,7 +84,7 @@ async fn get_contract_instance() -> ( ) .await; - (instance, asset, wallet, active_pool) + (default_pool, asset, wallet, active_pool) } #[tokio::test] @@ -224,8 +224,10 @@ async fn fails_unauthorized_usdf_operations() { let attacker = wallets.pop().unwrap(); // Create a new instance of the USDF token contract with the attacker's wallet - let usdf_token_attacker = - USDFToken::new(contracts.usdf.contract_id().clone(), attacker.clone()); + let usdf_token_attacker = ContractInstance::new( + USDFToken::new(contracts.usdf.contract.contract_id(), attacker.clone()), + contracts.usdf.implementation_id, + ); // Try to add a trove manager using the attacker's wallet let result = @@ -247,8 +249,10 @@ async fn fails_unauthorized_usdf_operations() { } // Create a new instance of the USDF token contract with the attacker's wallet - let usdf_token_attacker = - USDFToken::new(contracts.usdf.contract_id().clone(), attacker.clone()); + let usdf_token_attacker = ContractInstance::new( + USDFToken::new(contracts.usdf.contract.contract_id(), attacker.clone()), + contracts.usdf.implementation_id, + ); // Test 1: Unauthorized add_trove_manager let result = diff --git a/contracts/vesting-contract/Forc.toml b/contracts/vesting-contract/Forc.toml index 309cf5a5..b94a48fd 100644 --- a/contracts/vesting-contract/Forc.toml +++ b/contracts/vesting-contract/Forc.toml @@ -6,3 +6,6 @@ name = "vesting-contract" [dependencies] libraries = { path = "../../libraries" } + +[proxy] +enabled = true diff --git a/contracts/vesting-contract/tests/functions/vesting_calculations.rs b/contracts/vesting-contract/tests/functions/vesting_calculations.rs index 0c9217b2..e61872fc 100644 --- a/contracts/vesting-contract/tests/functions/vesting_calculations.rs +++ b/contracts/vesting-contract/tests/functions/vesting_calculations.rs @@ -1,13 +1,19 @@ use crate::utils::setup::setup; use fuels::prelude::*; -use fuels::types::transaction_builders::VariableOutputPolicy; use fuels::types::Identity; mod success { - use test_utils::interfaces::vesting::{ - get_vesting_schedule, instantiate_vesting_contract, load_vesting_schedules_from_json_file, - set_timestamp, VestingContract, + use test_utils::{ + data_structures::ContractInstance, + interfaces::vesting::{ + get_vesting_schedule, load_vesting_schedules_from_json_file, + vesting_abi::{ + claim_vested_tokens, get_redeemable_amount, get_vesting_schedule_call, + instantiate_vesting_contract, set_timestamp, + }, + VestingContract, + }, }; use crate::utils::setup::test_helpers::init_and_mint_to_vesting; @@ -16,41 +22,33 @@ mod success { #[tokio::test] async fn create_vesting_contract() { - let (vest, admin, recipient, asset) = setup(10000).await; + let (vest, _admin, recipient, asset) = setup(10000).await; + let recipient_identity = Identity::Address(recipient.address().into()); let vesting_schedule = [get_vesting_schedule( 3000, 1000, 2000, 0, 10000, - Identity::Address(recipient.address().into()), + recipient_identity, )]; - let _ = instantiate_vesting_contract( + instantiate_vesting_contract( &vest, &asset .contract_id() .asset_id(&AssetId::zeroed().into()) .into(), vesting_schedule.to_vec(), + true, ) - .await; + .await + .unwrap(); - let res = vest - .methods() - .get_vesting_schedule(Identity::Address(recipient.address().into())) - .call() - .await - .unwrap(); + let res = get_vesting_schedule_call(&vest, recipient_identity).await; - assert_eq!(res.value, vesting_schedule[0]); - - vest.methods() - .get_vesting_schedule(Identity::Address(admin.address().into())) - .call() - .await - .unwrap_err(); + assert_eq!(res.unwrap().value, vesting_schedule[0]); // fails to initialize twice let res = instantiate_vesting_contract( @@ -60,6 +58,7 @@ mod success { .asset_id(&AssetId::zeroed().into()) .into(), vesting_schedule.to_vec(), + true, ) .await; @@ -73,6 +72,7 @@ mod success { let end_timestamp = 10000; let total_amount = 10000; let cliff_amount = 3000; + let recipient_identity = Identity::Address(recipient.address().into()); let vesting_schedule = [get_vesting_schedule( cliff_amount, @@ -80,7 +80,7 @@ mod success { end_timestamp, 0, total_amount, - Identity::Address(recipient.address().into()), + recipient_identity, )]; let _ = instantiate_vesting_contract( @@ -90,10 +90,11 @@ mod success { .asset_id(&AssetId::zeroed().into()) .into(), vesting_schedule.to_vec(), + true, ) .await; - let _ = init_and_mint_to_vesting(&asset, &vest, total_amount, &admin).await; + let _ = init_and_mint_to_vesting(&asset, &vest.contract, total_amount, &admin).await; let asset_id = asset .contract_id() @@ -103,46 +104,32 @@ mod success { let provider = admin.provider().unwrap(); let vest_balance = provider - .get_contract_asset_balance(&vest.id(), asset_id) + .get_contract_asset_balance(&vest.contract.id(), asset_id) .await .unwrap(); assert_eq!(vest_balance, total_amount); // Time before cliff, no tokens should be redeemable - let res = vest - .methods() - .get_redeemable_amount( - cliff_timestamp - 1, - Identity::Address(recipient.address().into()), - ) - .call() + let res = get_redeemable_amount(&vest, cliff_timestamp - 1, recipient_identity) .await .unwrap(); assert_eq!(res.value, 0); // Time after end of vesting, all tokens should be redeemable - let res = vest - .methods() - .get_redeemable_amount( - end_timestamp + 1, - Identity::Address(recipient.address().into()), - ) - .call() + let res = get_redeemable_amount(&vest, end_timestamp + 1, recipient_identity) .await .unwrap(); assert_eq!(res.value, total_amount); // Midway through vesting, cliff + half of the remaining tokens should be redeemable - let res = vest - .methods() - .get_redeemable_amount( - cliff_timestamp + (end_timestamp - cliff_timestamp) / 2, - Identity::Address(recipient.address().into()), - ) - .call() - .await - .unwrap(); + let res = get_redeemable_amount( + &vest, + cliff_timestamp + (end_timestamp - cliff_timestamp) / 2, + recipient_identity, + ) + .await + .unwrap(); assert_eq!(res.value, cliff_amount + (total_amount - cliff_amount) / 2); } @@ -157,7 +144,10 @@ mod success { let total_amount = 10000; let cliff_amount = 3000; - let recpient_vesting = VestingContract::new(vest.contract_id().clone(), recipient.clone()); + let recpient_vesting = + VestingContract::new(vest.contract.contract_id().clone(), recipient.clone()); + + let recpient_vesting = ContractInstance::new(recpient_vesting, vest.implementation_id); let vesting_schedule = [get_vesting_schedule( cliff_amount, @@ -175,10 +165,11 @@ mod success { .asset_id(&AssetId::zeroed().into()) .into(), vesting_schedule.to_vec(), + true, ) .await; - let _ = init_and_mint_to_vesting(&asset, &vest, total_amount, &admin).await; + let _ = init_and_mint_to_vesting(&asset, &vest.contract, total_amount, &admin).await; let asset_id = asset .contract_id() @@ -195,20 +186,17 @@ mod success { assert_eq!(starting_balance, 0); let vest_balance = provider - .get_contract_asset_balance(&vest.id(), asset_id) + .get_contract_asset_balance(&vest.contract.id(), asset_id) .await .unwrap(); assert_eq!(vest_balance, total_amount); - let _ = set_timestamp(&vest, 20).await; + // Time before cliff, no tokens should be redeemable + let _ = set_timestamp(&vest, 20).await.unwrap(); - let _res = recpient_vesting - .methods() - .claim_vested_tokens() - .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) - .call() - .await; + let res = claim_vested_tokens(&recpient_vesting).await; + assert!(res.is_err()); let rec_balance = provider .get_asset_balance(&recipient.address(), asset_id) @@ -217,15 +205,12 @@ mod success { assert_eq!(rec_balance, 0); - let _ = set_timestamp(&vest, cliff_timestamp).await; + let _ = set_timestamp(&recpient_vesting, cliff_timestamp) + .await + .unwrap(); // Block produced then claim vested tokens happens in the next block - let _res = recpient_vesting - .methods() - .claim_vested_tokens() - .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) - .call() - .await; + let _res = claim_vested_tokens(&recpient_vesting).await.unwrap(); let rec_balance = provider .get_asset_balance(&recipient.address(), asset_id) @@ -237,12 +222,7 @@ mod success { let _ = set_timestamp(&vest, end_timestamp - (end_timestamp - cliff_timestamp) / 2).await; // Block produced then claim vested tokens happens in the next block - let _res = recpient_vesting - .methods() - .claim_vested_tokens() - .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) - .call() - .await; + let _res = claim_vested_tokens(&recpient_vesting).await.unwrap(); let rec_balance = provider .get_asset_balance(&recipient.address(), asset_id) @@ -257,12 +237,7 @@ mod success { let _ = set_timestamp(&vest, end_timestamp).await; // Block produced then claim vested tokens happens in the next block - let _res = recpient_vesting - .methods() - .claim_vested_tokens() - .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) - .call() - .await; + let _res = claim_vested_tokens(&recpient_vesting).await.unwrap(); let rec_balance = provider .get_asset_balance(&recipient.address(), asset_id) @@ -271,15 +246,11 @@ mod success { assert_eq!(total_amount, rec_balance); - set_timestamp(&vest, end_timestamp + 10).await; + let _ = set_timestamp(&vest, end_timestamp + 10).await.unwrap(); // Tries to claim after all tokens have been claimed - let _res = recpient_vesting - .methods() - .claim_vested_tokens() - .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) - .call() - .await; + let res = claim_vested_tokens(&recpient_vesting).await; + assert!(res.is_err()); let rec_balance = provider .get_asset_balance(&recipient.address(), asset_id) @@ -312,7 +283,7 @@ mod success { mod failure { use test_utils::interfaces::vesting::{ - get_vesting_schedule, instantiate_vesting_contract, VestingContract, + get_vesting_schedule, vesting_abi::instantiate_vesting_contract, }; use super::*; @@ -338,6 +309,7 @@ mod failure { .asset_id(&AssetId::zeroed().into()) .into(), vesting_schedule.to_vec(), + true, ) .await; diff --git a/contracts/vesting-contract/tests/utils/setup.rs b/contracts/vesting-contract/tests/utils/setup.rs index d397f39d..f3fa2d9e 100644 --- a/contracts/vesting-contract/tests/utils/setup.rs +++ b/contracts/vesting-contract/tests/utils/setup.rs @@ -1,4 +1,5 @@ use fuels::prelude::*; +use test_utils::data_structures::ContractInstance; use test_utils::interfaces::vesting::VestingContract; use test_utils::setup::common::deploy_vesting_contract; use test_utils::{interfaces::token::Token, setup::common::deploy_token}; @@ -6,16 +7,11 @@ use test_utils::{interfaces::token::Token, setup::common::deploy_token}; pub async fn setup( total_amount: u64, ) -> ( - VestingContract, + ContractInstance>, WalletUnlocked, WalletUnlocked, Token, ) { - // let config = Config { - // manual_blocks_enabled: true, // Necessary so the `produce_blocks` API can be used locally - // ..Config::local_node() - // }; - let mut wallets = launch_custom_provider_and_get_wallets( WalletsConfig::new( Some(2), /* Single wallet */ @@ -31,11 +27,12 @@ pub async fn setup( let wallet = wallets.pop().unwrap(); let wallet2 = wallets.pop().unwrap(); - let instance = deploy_vesting_contract(&wallet.clone(), total_amount).await; + // First deploy the target contract + let vesting = deploy_vesting_contract(&wallet.clone(), total_amount).await; let asset = deploy_token(&wallet).await; - (instance, wallet, wallet2, asset) + (vesting, wallet, wallet2, asset) } pub mod test_helpers { @@ -77,6 +74,7 @@ pub mod test_helpers { asset_id, TxPolicies::default(), ) - .await; + .await + .unwrap(); } } diff --git a/deploy-scripts/Cargo.toml b/deploy-scripts/Cargo.toml index 9aa22aff..7627eff9 100644 --- a/deploy-scripts/Cargo.toml +++ b/deploy-scripts/Cargo.toml @@ -15,7 +15,8 @@ serde = { workspace = true } serde_json = { workspace = true } test-utils = { workspace = true } tokio = { workspace = true } - +csv = { workspace = true } +tai64 = { workspace = true } [lib] doctest = false diff --git a/deploy-scripts/src/add_asset.rs b/deploy-scripts/src/add_asset.rs index 5039b8da..dfee7df1 100644 --- a/deploy-scripts/src/add_asset.rs +++ b/deploy-scripts/src/add_asset.rs @@ -1,52 +1,85 @@ +use crate::constants::{self}; use crate::utils::utils::*; use dotenv::dotenv; use fuels::prelude::*; -use fuels::types::{Bits256, U256}; -use serde_json::json; - -use std::{fs::File, io::Write}; -use test_utils::data_structures::{AssetContracts, ExistingAssetContracts}; -use test_utils::interfaces::oracle::oracle_abi; -use test_utils::interfaces::pyth_oracle::pyth_oracle_abi; -use test_utils::interfaces::redstone_oracle::redstone_oracle_abi; - +use fuels::types::Bits256; +use std::str::FromStr; +use test_utils::data_structures::{AssetConfig, ExistingAssetContracts, PythConfig}; use test_utils::setup::common::*; -pub async fn add_asset() { + +pub async fn add_asset(symbol: &str) { dotenv().ok(); let wallet = setup_wallet().await; - let address = wallet.address(); + let network_name = wallet.provider().unwrap().chain_info().await.unwrap().name; + let is_testnet = is_testnet(wallet.clone()).await; + let address: Address = wallet.address().into(); println!("🔑 Wallet address: {}", address); - - let core_contracts = load_core_contracts(wallet.clone()); - - // you will need to set the existing asset contracts here manually and uncomment the below line - let mut existing_asset_to_initialize: Option = - Some(ExistingAssetContracts { - asset: ContractId::zeroed(), - asset_id: AssetId::zeroed(), - pyth_oracle: ContractId::zeroed(), - pyth_precision: 9, - pyth_price_id: Bits256::zeroed(), - redstone_oracle: ContractId::zeroed(), - redstone_price_id: U256::zero(), - redstone_precision: 9, - fuel_vm_decimals: 9, - }); - existing_asset_to_initialize = None; - - match existing_asset_to_initialize { - Some(_) => { - println!("Existing asset to initialize"); - } - None => { - println!("Initializing new asset"); + println!("Network name: {}", network_name); + println!("Is testnet: {}", is_testnet); + + let core_contracts = load_core_contracts(wallet.clone(), is_testnet); + + // Get asset constants based on symbol and network type + let asset_constants = match (symbol.to_uppercase().as_str(), is_testnet) { + // Testnet + ("ETH", true) => &constants::TESTNET_ETH_CONSTANTS, + ("WSTETH", true) => &constants::TESTNET_WSTETH_CONSTANTS, + ("EZETH", true) => &constants::TESTNET_EZETH_CONSTANTS, + ("WEETH", true) => &constants::TESTNET_WEETH_CONSTANTS, + ("RSETH", true) => &constants::TESTNET_RSETH_CONSTANTS, + ("METH", true) => &constants::TESTNET_METH_CONSTANTS, + // Mainnet + ("ETH", false) => &constants::MAINNET_ETH_CONSTANTS, + ("WSTETH", false) => &constants::MAINNET_WSTETH_CONSTANTS, + ("EZETH", false) => &constants::MAINNET_EZETH_CONSTANTS, + ("WEETH", false) => &constants::MAINNET_WEETH_CONSTANTS, + ("RSETH", false) => &constants::MAINNET_RSETH_CONSTANTS, + ("METH", false) => &constants::MAINNET_METH_CONSTANTS, + // Add more assets as needed + (symbol, is_testnet) => panic!( + "Unsupported asset symbol '{}' for {} network", + symbol, + if is_testnet { "testnet" } else { "mainnet" } + ), + }; + + let existing_asset_to_initialize: ExistingAssetContracts = ExistingAssetContracts { + symbol: symbol.to_string(), + asset: match is_testnet { + true => None, + false => Some(AssetConfig { + asset: ContractId::from_str(asset_constants.asset_contract_id.unwrap()).unwrap(), + asset_id: AssetId::from_str(asset_constants.asset_id.unwrap()).unwrap(), + fuel_vm_decimals: asset_constants.decimals, + }), + }, + pyth_oracle: Some(PythConfig { + contract: ContractId::from_str(asset_constants.pyth_contract_id).unwrap(), + price_id: Bits256::from_hex_str(asset_constants.pyth_price_id).unwrap(), + }), + redstone_oracle: None, // TODO: Add redstone oracle when it's ready + }; + + // Redstone oracle is not required for initialization + if existing_asset_to_initialize.asset.is_none() + || existing_asset_to_initialize.pyth_oracle.is_none() + { + // If testnet then cause a failure so it's obvious + if !is_testnet { + panic!("Mainnet assets must have an asset and pyth oracle"); } + + println!("Initializing new asset"); + } else { + println!("Existing asset to register"); } + // Deploy the asset contracts - let asset_contracts = deploy_asset_contracts(&wallet, &existing_asset_to_initialize).await; + let asset_contracts = + deploy_asset_contracts(&wallet, &existing_asset_to_initialize, false, false).await; - query_oracles(&asset_contracts).await; + query_oracles(&asset_contracts, wallet.clone()).await; println!("Are you sure you want to initialize the asset? (y/n)"); let mut input = String::new(); @@ -58,82 +91,11 @@ pub async fn add_asset() { return; } - initialize_asset(&core_contracts, &asset_contracts).await; + initialize_asset(&core_contracts, &asset_contracts) + .await + .unwrap(); - write_asset_contracts_to_file(vec![asset_contracts]); + write_asset_contracts_to_file(vec![asset_contracts], is_testnet); println!("Asset contracts added successfully"); } - -fn write_asset_contracts_to_file(asset_contracts: Vec>) { - // Read existing contracts.json - let mut contracts: serde_json::Value = serde_json::from_str( - &std::fs::read_to_string("contracts.json").expect("Failed to read contracts.json"), - ) - .expect("Failed to parse contracts.json"); - - // Update asset_contracts field - contracts["asset_contracts"] = - json!(asset_contracts.iter().map(|asset_contract| { - json!({ - "oracle": asset_contract.oracle.contract_id().to_string(), - "trove_manager": asset_contract.trove_manager.contract_id().to_string(), - "asset_contract": asset_contract.asset.contract_id().to_string(), - "asset_id": format!("0x{}", asset_contract.asset_id.to_string()), - "pyth_price_id": to_hex_str(&asset_contract.pyth_price_id), - "pyth_contract": asset_contract.mock_pyth_oracle.contract_id().to_string(), - "redstone_contract": asset_contract.mock_redstone_oracle.contract_id().to_string(), - "redstone_price_id": asset_contract.redstone_price_id.to_string(), - "redstone_precision": asset_contract.redstone_precision, - "fuel_vm_decimals": asset_contract.fuel_vm_decimals, - }) - }).collect::>()); - - // Write updated contracts back to file - let mut file = - File::create("contracts.json").expect("Failed to open contracts.json for writing"); - file.write_all(serde_json::to_string_pretty(&contracts).unwrap().as_bytes()) - .expect("Failed to write to contracts.json"); -} - -async fn query_oracles(asset_contracts: &AssetContracts) { - let current_price = oracle_abi::get_price( - &asset_contracts.oracle, - &asset_contracts.mock_pyth_oracle, - &Some(asset_contracts.mock_redstone_oracle.clone()), - ) - .await - .value; - - let current_pyth_price = pyth_oracle_abi::price_unsafe( - &asset_contracts.mock_pyth_oracle, - &asset_contracts.pyth_price_id, - ) - .await - .value - .price; - - let current_redstone_price = redstone_oracle_abi::read_prices( - &asset_contracts.mock_redstone_oracle, - vec![asset_contracts.redstone_price_id], - ) - .await - .value[0] - .as_u64(); - - println!( - "Current oracle proxy price: {:.9}", - current_price as f64 / 1_000_000_000.0 - ); - println!( - "Current pyth price: {:.9}", - current_pyth_price as f64 / 1_000_000_000.0 - ); - println!( - "Current redstone price: {:.9}", - current_redstone_price as f64 / 1_000_000_000.0 - ); -} -pub fn to_hex_str(bits: &Bits256) -> String { - format!("0x{}", hex::encode(bits.0)) -} diff --git a/deploy-scripts/src/constants.rs b/deploy-scripts/src/constants.rs new file mode 100644 index 00000000..ed518b0c --- /dev/null +++ b/deploy-scripts/src/constants.rs @@ -0,0 +1,195 @@ +// References: +// https://docs.pyth.network/price-feeds/contract-addresses/fuel +// https://github.com/FuelLabs/verified-assets/blob/main/ASSETS.md + +pub const TESTNET_CONTRACTS_FILE: &str = "testnet.contracts.json"; +pub const MAINNET_CONTRACTS_FILE: &str = "mainnet.contracts.json"; + +pub const TESTNET_RPC: &str = "https://testnet.fuel.network/v1/playground"; +pub const MAINNET_RPC: &str = "https://mainnet.fuel.network/v1/playground"; + +pub const TESTNET_TREASURY_IDENTITY: &str = + "0xa5ac02c203dde9b52cb2ab29bdd0dfee1e7a17f97339ff2ead92de4eebb62305"; +pub const MAINNET_TREASURY_IDENTITY: &str = + "0x8c365ce492a296a851c1a68dc2fcf667766396a47dc441d9cd0f9d26756525f7"; + +pub const TESTNET_PYTH_CONTRACT_ID: &str = + "0x25146735b29d4216639f7f8b1d7b921ff87a1d3051de62d6cceaacabeb33b8e7"; +pub const MAINNET_PYTH_CONTRACT_ID: &str = + "0x1c86fdd9e0e7bc0d2ae1bf6817ef4834ffa7247655701ee1b031b52a24c523da"; + +// Testnet +pub const TESTNET_ETH_ASSET_CONTRACT_ID: &str = + "0x4ea6ccef1215d9479f1024dff70fc055ca538215d2c8c348beddffd54583d0e8"; +pub const TESTNET_ETH_ASSET_ID: &str = + "f8f8b6283d7fa5b672b530cbb84fcccb4ff8dc40f8176ef4544ddb1f1952ad07"; + +// Mainnet +// https://github.com/FuelLabs/verified-assets/blob/main/ASSETS.md +pub const MAINNET_ASSET_CONTRACT_ID: &str = + "0x4ea6ccef1215d9479f1024dff70fc055ca538215d2c8c348beddffd54583d0e8"; +pub const MAINNET_ETH_ASSET_ID: &str = + "0xf8f8b6283d7fa5b672b530cbb84fcccb4ff8dc40f8176ef4544ddb1f1952ad07"; +pub const MAINNET_ETH_DECIMALS: u32 = 9; +pub const MAINNET_WSTETH_ASSET_ID: &str = + "0x1a7815cc9f75db5c24a5b0814bfb706bb9fe485333e98254015de8f48f84c67b"; +pub const MAINNET_WSTETH_DECIMALS: u32 = 9; +pub const MAINNET_EZETH_ASSET_ID: &str = + "0x91b3559edb2619cde8ffb2aa7b3c3be97efd794ea46700db7092abeee62281b0"; +pub const MAINNET_EZETH_DECIMALS: u32 = 9; +pub const MAINNET_PZETH_ASSET_ID: &str = + "0x1493d4ec82124de8f9b625682de69dcccda79e882b89a55a8c737b12de67bd68"; +pub const MAINNET_PZETH_DECIMALS: u32 = 9; +pub const MAINNET_WEETH_ASSET_ID: &str = + "0x239ed6e12b7ce4089ee245244e3bf906999a6429c2a9a445a1e1faf56914a4ab"; +pub const MAINNET_WEETH_DECIMALS: u32 = 9; +pub const MAINNET_RSETH_ASSET_ID: &str = + "0xbae80f7fb8aa6b90d9b01ef726ec847cc4f59419c4d5f2ea88fec785d1b0e849"; +pub const MAINNET_RSETH_DECIMALS: u32 = 9; +pub const MAINNET_METH_ASSET_ID: &str = + "0xafd219f513317b1750783c6581f55530d6cf189a5863fd18bd1b3ffcec1714b4"; +pub const MAINNET_METH_DECIMALS: u32 = 9; + +// pyth price ids +// https://www.pyth.network/developers/price-feed-ids#pyth-evm-stable +pub const PYTH_ETH_PRICE_ID: &str = + "ff61491a931112ddf1bd8147cd1b641375f79f5825126d665480874634fd0ace"; +pub const PYTH_WSTETH_PRICE_ID: &str = + "6df640f3b8963d8f8358f791f352b8364513f6ab1cca5ed3f1f7b5448980e784"; +pub const PYTH_EZETH_PRICE_ID: &str = + "06c217a791f5c4f988b36629af4cb88fad827b2485400a358f3b02886b54de92"; +pub const PYTH_WEETH_PRICE_ID: &str = + "9ee4e7c60b940440a261eb54b6d8149c23b580ed7da3139f7f08f4ea29dad395"; +pub const PYTH_RSETH_PRICE_ID: &str = + "0caec284d34d836ca325cf7b3256c078c597bc052fbd3c0283d52b581d68d71f"; +pub const PYTH_METH_PRICE_ID: &str = + "fbc9c3a716650b6e24ab22ab85b1c0ef4141b18f4590cc0b986e2f9064cf73d6"; +pub const PYTH_PZETH_PRICE_ID: &str = ""; // Waiting for Pyth price feed + +pub struct AssetConstants { + pub symbol: &'static str, + pub asset_contract_id: Option<&'static str>, + pub asset_id: Option<&'static str>, + pub pyth_contract_id: &'static str, + pub pyth_price_id: &'static str, + pub decimals: u32, +} + +// Asset-specific constants +pub const TESTNET_ETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "ETH", + asset_contract_id: None, + asset_id: None, + pyth_contract_id: TESTNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_ETH_PRICE_ID, + decimals: 9, +}; + +pub const TESTNET_WSTETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "WSTETH", + asset_contract_id: None, + asset_id: None, + pyth_contract_id: TESTNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_WSTETH_PRICE_ID, + decimals: 9, +}; + +pub const TESTNET_EZETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "EZETH", + asset_contract_id: None, + asset_id: None, + pyth_contract_id: TESTNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_EZETH_PRICE_ID, + decimals: 9, +}; + +pub const TESTNET_WEETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "WEETH", + asset_contract_id: None, + asset_id: None, + pyth_contract_id: TESTNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_WEETH_PRICE_ID, + decimals: 9, +}; + +pub const TESTNET_RSETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "RSETH", + asset_contract_id: None, + asset_id: None, + pyth_contract_id: TESTNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_RSETH_PRICE_ID, + decimals: 9, +}; + +pub const TESTNET_METH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "METH", + asset_contract_id: None, + asset_id: None, + pyth_contract_id: TESTNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_METH_PRICE_ID, + decimals: 9, +}; + +// Mainnet +pub const MAINNET_ETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "ETH", + asset_contract_id: Some(MAINNET_ASSET_CONTRACT_ID), + asset_id: Some(MAINNET_ETH_ASSET_ID), + pyth_contract_id: MAINNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_ETH_PRICE_ID, + decimals: MAINNET_ETH_DECIMALS, +}; + +pub const MAINNET_WSTETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "WSTETH", + asset_contract_id: Some(MAINNET_ASSET_CONTRACT_ID), + asset_id: Some(MAINNET_WSTETH_ASSET_ID), + pyth_contract_id: MAINNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_WSTETH_PRICE_ID, + decimals: MAINNET_WSTETH_DECIMALS, +}; + +pub const MAINNET_EZETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "EZETH", + asset_contract_id: Some(MAINNET_ASSET_CONTRACT_ID), + asset_id: Some(MAINNET_EZETH_ASSET_ID), + pyth_contract_id: MAINNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_EZETH_PRICE_ID, + decimals: MAINNET_EZETH_DECIMALS, +}; + +pub const MAINNET_WEETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "WEETH", + asset_contract_id: Some(MAINNET_ASSET_CONTRACT_ID), + asset_id: Some(MAINNET_WEETH_ASSET_ID), + pyth_contract_id: MAINNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_WEETH_PRICE_ID, + decimals: MAINNET_WEETH_DECIMALS, +}; + +pub const MAINNET_RSETH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "RSETH", + asset_contract_id: Some(MAINNET_ASSET_CONTRACT_ID), + asset_id: Some(MAINNET_RSETH_ASSET_ID), + pyth_contract_id: MAINNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_RSETH_PRICE_ID, + decimals: MAINNET_RSETH_DECIMALS, +}; + +pub const MAINNET_METH_CONSTANTS: AssetConstants = AssetConstants { + symbol: "METH", + asset_contract_id: Some(MAINNET_ASSET_CONTRACT_ID), + asset_id: Some(MAINNET_METH_ASSET_ID), + pyth_contract_id: MAINNET_PYTH_CONTRACT_ID, + pyth_price_id: PYTH_METH_PRICE_ID, + decimals: MAINNET_METH_DECIMALS, +}; + +// pub const MAINNET_PZETH_CONSTANTS: AssetConstants = AssetConstants { +// symbol: "PZETH", +// asset_contract_id: Some(MAINNET_ASSET_CONTRACT_ID), +// asset_id: Some(MAINNET_PZETH_ASSET_ID), +// pyth_contract_id: MAINNET_PYTH_CONTRACT_ID, +// pyth_price_id: PYTH_PZETH_PRICE_ID, +// decimals: MAINNET_PZETH_DECIMALS, +// }; diff --git a/deploy-scripts/src/deploy.rs b/deploy-scripts/src/deploy.rs index 0690ff27..cef65fd7 100644 --- a/deploy-scripts/src/deploy.rs +++ b/deploy-scripts/src/deploy.rs @@ -2,57 +2,89 @@ use std::{fs::File, io::Write}; use dotenv::dotenv; use fuels::prelude::*; +use fuels::types::{Bits256, Identity}; use serde_json::json; +use std::str::FromStr; +use test_utils::data_structures::ProtocolContracts; +use test_utils::interfaces::hint_helper::HintHelper; +use test_utils::interfaces::multi_trove_getter::MultiTroveGetter; +use test_utils::interfaces::vesting; -pub mod deployment { - const VESTING_SCHEDULE_PATH: &str = "deploy-scripts/vesting/test_vesting.json"; - use fuels::types::Bits256; - use test_utils::data_structures::ProtocolContracts; - use test_utils::interfaces::hint_helper::HintHelper; - use test_utils::interfaces::multi_trove_getter::MultiTroveGetter; - use test_utils::interfaces::vesting::{self, load_vesting_schedules_from_json_file}; +use crate::constants::{MAINNET_CONTRACTS_FILE, TESTNET_CONTRACTS_FILE}; +use crate::utils::utils::{is_testnet, load_vesting_schedules_from_csv, setup_wallet}; - use crate::utils::utils::setup_wallet; +use test_utils::setup::common::{ + deploy_core_contracts, deploy_hint_helper, deploy_multi_trove_getter, initialize_core_contracts, +}; - use super::*; +const VESTING_SCHEDULE_PATH: &str = "deploy-scripts/vesting/vesting.csv"; +const CLIFF_PERCENTAGE: f64 = 0.0; // 0% cliff +const SECONDS_TO_CLIFF: u64 = 7 * 24 * 60 * 60; // 7 days +const SECONDS_VESTING_DURATION: u64 = 2 * 365 * 24 * 60 * 60; // 2 years - use test_utils::setup::common::{ - deploy_core_contracts, deploy_hint_helper, deploy_multi_trove_getter, - initialize_core_contracts, - }; +pub mod deployment { + use crate::constants::{MAINNET_TREASURY_IDENTITY, TESTNET_TREASURY_IDENTITY}; + use super::*; pub async fn deploy() { //--------------- Deploy --------------- dotenv().ok(); - //--------------- WALLET --------------- let wallet = setup_wallet().await; - let address = wallet.address(); - println!("🔑 Wallet address: {}", address); - + let network_name = wallet.provider().unwrap().chain_info().await.unwrap().name; + let address: Address = wallet.address().into(); + let is_testnet = is_testnet(wallet.clone()).await; + //--------------- WALLET --------------- + println!("🔑 Wallet address: 0x{}", address); + println!("🔑 Is testnet: {}", is_testnet); + println!("🔑 Network name: {}", network_name); + println!( + "🔑 Treasury identity: {}", + match is_testnet { + true => TESTNET_TREASURY_IDENTITY, + false => MAINNET_TREASURY_IDENTITY, + } + ); //--------------- Deploy --------------- - let core_contracts = deploy_and_initialize_all_core_contracts(wallet.clone()).await; + let core_contracts = + deploy_and_initialize_all_core_contracts(wallet.clone(), is_testnet).await; let (hint_helper, multi_trove_getter) = deploy_frontend_helper_contracts(wallet.clone(), &core_contracts).await; //--------------- Write to file --------------- - write_contracts_to_file(core_contracts, hint_helper, multi_trove_getter); + write_contracts_to_file(core_contracts, hint_helper, multi_trove_getter, is_testnet); } pub async fn deploy_and_initialize_all_core_contracts( wallet: WalletUnlocked, + is_testnet: bool, ) -> ProtocolContracts { - let vesting_schedules = load_vesting_schedules_from_json_file(VESTING_SCHEDULE_PATH); - - let mut core_contracts = deploy_core_contracts(&wallet, false).await; + let treasury_identity = Identity::Address( + Address::from_str(match is_testnet { + true => TESTNET_TREASURY_IDENTITY, + false => MAINNET_TREASURY_IDENTITY, + }) + .unwrap(), + ); + + let vesting_schedules = load_vesting_schedules_from_csv( + VESTING_SCHEDULE_PATH, + CLIFF_PERCENTAGE, + SECONDS_TO_CLIFF, + SECONDS_VESTING_DURATION, + treasury_identity, + ); + let mut core_contracts = deploy_core_contracts(&wallet, false, true).await; initialize_core_contracts(&mut core_contracts, &wallet, false, false, true).await; - let _ = vesting::instantiate_vesting_contract( + vesting::vesting_abi::instantiate_vesting_contract( &core_contracts.vesting_contract, &core_contracts.fpt_asset_id, vesting_schedules, + false, ) - .await; + .await + .unwrap(); return core_contracts; } @@ -62,9 +94,11 @@ pub mod deployment { core_contracts: &ProtocolContracts, ) -> (HintHelper, MultiTroveGetter) { let hint_helper = deploy_hint_helper(&wallet).await; - let multi_trove_getter = - deploy_multi_trove_getter(&wallet, &core_contracts.sorted_troves.contract_id().into()) - .await; + let multi_trove_getter = deploy_multi_trove_getter( + &wallet, + &core_contracts.sorted_troves.contract.contract_id().into(), + ) + .await; return (hint_helper, multi_trove_getter); } @@ -73,30 +107,49 @@ pub mod deployment { contracts: ProtocolContracts, hint_helper: HintHelper, multi_trove_getter: MultiTroveGetter, + is_testnet: bool, ) { - let mut file = File::create("contracts.json").unwrap(); + let mut file = File::create(match is_testnet { + true => TESTNET_CONTRACTS_FILE, + false => MAINNET_CONTRACTS_FILE, + }) + .unwrap(); let json = json!({ - "borrow_operations": contracts.borrow_operations.contract_id().to_string(), - "usdf": contracts.usdf.contract_id().to_string(), + "borrow_operations": contracts.borrow_operations.contract.contract_id().to_string(), + "borrow_operations_implementation_id": format!("0x{}", contracts.borrow_operations.implementation_id.to_string()), + "usdf": contracts.usdf.contract.contract_id().to_string(), + "usdf_implementation_id": format!("0x{}", contracts.usdf.implementation_id.to_string()), "usdf_asset_id": format!("0x{}", contracts.usdf_asset_id.to_string()), - "stability_pool": contracts.stability_pool.contract_id().to_string(), - "protocol_manager": contracts.protocol_manager.contract_id().to_string(), - "fpt_staking": contracts.fpt_staking.contract_id().to_string(), - "fpt_token": contracts.fpt_token.contract_id().to_string(), + "stability_pool": contracts.stability_pool.contract.contract_id().to_string(), + "stability_pool_implementation_id": format!("0x{}", contracts.stability_pool.implementation_id.to_string()), + "protocol_manager": contracts.protocol_manager.contract.contract_id().to_string(), + "protocol_manager_implementation_id": format!("0x{}", contracts.protocol_manager.implementation_id.to_string()), + "fpt_staking": contracts.fpt_staking.contract.contract_id().to_string(), + "fpt_staking_implementation_id": format!("0x{}", contracts.fpt_staking.implementation_id.to_string()), + "fpt_token": contracts.fpt_token.contract.contract_id().to_string(), + "fpt_token_implementation_id": format!("0x{}", contracts.fpt_token.implementation_id.to_string()), "fpt_asset_id": format!("0x{}", contracts.fpt_asset_id.to_string()), - "community_issuance": contracts.community_issuance.contract_id().to_string(), - "coll_surplus_pool": contracts.coll_surplus_pool.contract_id().to_string(), - "default_pool": contracts.default_pool.contract_id().to_string(), - "active_pool": contracts.active_pool.contract_id().to_string(), - "sorted_troves": contracts.sorted_troves.contract_id().to_string(), - "vesting_contract": contracts.vesting_contract.contract_id().to_string(), + "community_issuance": contracts.community_issuance.contract.contract_id().to_string(), + "community_issuance_implementation_id": format!("0x{}", contracts.community_issuance.implementation_id.to_string()), + "coll_surplus_pool": contracts.coll_surplus_pool.contract.contract_id().to_string(), + "coll_surplus_pool_implementation_id": format!("0x{}", contracts.coll_surplus_pool.implementation_id.to_string()), + "default_pool": contracts.default_pool.contract.contract_id().to_string(), + "default_pool_implementation_id": format!("0x{}", contracts.default_pool.implementation_id.to_string()), + "active_pool": contracts.active_pool.contract.contract_id().to_string(), + "active_pool_implementation_id": format!("0x{}", contracts.active_pool.implementation_id.to_string()), + "sorted_troves": contracts.sorted_troves.contract.contract_id().to_string(), + "sorted_troves_implementation_id": format!("0x{}", contracts.sorted_troves.implementation_id.to_string()), + "vesting_contract": contracts.vesting_contract.contract.contract_id().to_string(), + "vesting_contract_implementation_id": format!("0x{}", contracts.vesting_contract.implementation_id.to_string()), "hint_helper": hint_helper.contract_id().to_string(), "multi_trove_getter": multi_trove_getter.contract_id().to_string(), "asset_contracts": contracts.asset_contracts.iter().map(|asset_contracts| { json!({ - "oracle": asset_contracts.oracle.contract_id().to_string(), - "trove_manager": asset_contracts.trove_manager.contract_id().to_string(), + "oracle": asset_contracts.oracle.contract.contract_id().to_string(), + "oracle_implementation_id": format!("0x{}", asset_contracts.oracle.implementation_id.to_string()), + "trove_manager": asset_contracts.trove_manager.contract.contract_id().to_string(), + "trove_manager_implementation_id": format!("0x{}", asset_contracts.trove_manager.implementation_id.to_string()), "asset_contract": asset_contracts.asset.contract_id().to_string(), "asset_id": format!("0x{}", asset_contracts.asset_id.to_string()), }) diff --git a/deploy-scripts/src/lib.rs b/deploy-scripts/src/lib.rs index 56de46cb..c844221a 100644 --- a/deploy-scripts/src/lib.rs +++ b/deploy-scripts/src/lib.rs @@ -1,5 +1,7 @@ pub mod add_asset; +pub mod constants; pub mod deploy; pub mod pause; pub mod sanity_check; +pub mod transfer_ownership; pub mod utils; diff --git a/deploy-scripts/src/main.rs b/deploy-scripts/src/main.rs index c42c6124..2a4a026e 100644 --- a/deploy-scripts/src/main.rs +++ b/deploy-scripts/src/main.rs @@ -3,24 +3,40 @@ use deploy_scripts::{ deploy::deployment::deploy, pause::{pause_protocol, unpause_protocol}, sanity_check::sanity_check, + transfer_ownership::transfer_owner, }; #[tokio::main] pub async fn main() { let args: Vec = std::env::args().collect(); if args.len() < 2 { - println!("Please specify 'deploy', 'add-asset', 'pause', 'unpause', or 'sanity-check'"); + println!( + "Please specify 'deploy', 'add-asset ', 'pause', 'unpause', 'sanity-check', or 'transfer-owner
'" + ); return; } match args[1].as_str() { "deploy" => deploy().await, - "add-asset" => add_asset().await, + "add-asset" => { + if args.len() < 3 { + println!("Please specify an asset symbol (e.g., 'add-asset ETH')"); + return; + } + add_asset(&args[2]).await + }, "pause" => pause_protocol().await, "unpause" => unpause_protocol().await, "sanity-check" => sanity_check().await, + "transfer-owner" => { + if args.len() < 3 { + println!("Please specify the new owner address"); + return; + } + transfer_owner(&args[2]).await + }, _ => println!( - "Invalid argument. Use 'deploy', 'add-asset', 'pause', 'unpause', or 'sanity-check'" + "Invalid argument. Use 'deploy', 'add-asset ', 'pause', 'unpause', 'sanity-check', or 'transfer-owner
'" ), } } diff --git a/deploy-scripts/src/pause.rs b/deploy-scripts/src/pause.rs index 7f9428a6..6143acd4 100644 --- a/deploy-scripts/src/pause.rs +++ b/deploy-scripts/src/pause.rs @@ -1,4 +1,4 @@ -use crate::utils::utils::{load_core_contracts, setup_wallet}; +use crate::utils::utils::{is_testnet, load_core_contracts, setup_wallet}; use dotenv::dotenv; use test_utils::interfaces::borrow_operations::borrow_operations_abi; @@ -10,7 +10,8 @@ pub async fn pause_protocol() { let address = wallet.address(); println!("🔑 Wallet address: {}", address); - let core_contracts = load_core_contracts(wallet.clone()); + let is_testnet = is_testnet(wallet.clone()).await; + let core_contracts = load_core_contracts(wallet.clone(), is_testnet); println!("Are you sure you want to pause the protocol? (y/n)"); let mut input = String::new(); @@ -36,7 +37,8 @@ pub async fn unpause_protocol() { let address = wallet.address(); println!("🔑 Wallet address: {}", address); - let core_contracts = load_core_contracts(wallet.clone()); + let is_testnet = is_testnet(wallet.clone()).await; + let core_contracts = load_core_contracts(wallet.clone(), is_testnet); println!("Are you sure you want to unpause the protocol? (y/n)"); let mut input = String::new(); diff --git a/deploy-scripts/src/sanity_check.rs b/deploy-scripts/src/sanity_check.rs index da9e62c9..3011bb83 100644 --- a/deploy-scripts/src/sanity_check.rs +++ b/deploy-scripts/src/sanity_check.rs @@ -12,20 +12,21 @@ use test_utils::data_structures::PRECISION; pub async fn sanity_check() { dotenv().ok(); - let collateral_amount = 4000 * PRECISION; + let collateral_amount = 4 * PRECISION; let debt = 1000 * PRECISION; let wallet = setup_wallet().await; let address = wallet.address(); println!("🔑 Wallet address: {}", address); - let core_contracts = load_core_contracts(wallet.clone()); + let is_testnet = is_testnet(wallet.clone()).await; + let core_contracts = load_core_contracts(wallet.clone(), is_testnet); let provider = wallet.provider().unwrap(); let community_issuance_balance = provider .get_contract_asset_balance( - core_contracts.community_issuance.contract_id(), + core_contracts.community_issuance.contract.contract_id(), core_contracts.fpt_asset_id.into(), ) .await @@ -38,7 +39,7 @@ pub async fn sanity_check() { let vesting_contract_balance = provider .get_contract_asset_balance( - core_contracts.vesting_contract.contract_id(), + core_contracts.vesting_contract.contract.contract_id(), core_contracts.fpt_asset_id.into(), ) .await @@ -136,23 +137,6 @@ pub async fn sanity_check() { .await .unwrap(); - println!("Waiting 30 seconds to accumulate rewards"); - sleep(Duration::from_secs(30)); - stability_pool_abi::withdraw_from_stability_pool( - &core_contracts.stability_pool, - &core_contracts.community_issuance, - &core_contracts.usdf, - &core_contracts.asset_contracts[0].asset, - &core_contracts.sorted_troves, - &core_contracts.asset_contracts[0].oracle, - &core_contracts.asset_contracts[0].mock_pyth_oracle, - &core_contracts.asset_contracts[0].mock_redstone_oracle, - &core_contracts.asset_contracts[0].trove_manager, - stability_pool_balance / 3, - ) - .await - .unwrap(); - let fpt_balance = provider .get_asset_balance(wallet.address().into(), core_contracts.fpt_asset_id.into()) .await @@ -166,6 +150,7 @@ pub async fn sanity_check() { core_contracts.fpt_asset_id, fpt_balance, ) - .await; + .await + .unwrap(); println!("Staked FPT"); } diff --git a/deploy-scripts/src/transfer_ownership.rs b/deploy-scripts/src/transfer_ownership.rs new file mode 100644 index 00000000..304e174d --- /dev/null +++ b/deploy-scripts/src/transfer_ownership.rs @@ -0,0 +1,47 @@ +use crate::utils::utils::{is_testnet, load_core_contracts, setup_wallet}; +use dotenv::dotenv; +use fuels::types::Identity; +use test_utils::interfaces::{ + borrow_operations::borrow_operations_abi, protocol_manager::protocol_manager_abi, +}; + +pub async fn transfer_owner(new_owner: &str) { + dotenv().ok(); + + let wallet = setup_wallet().await; + let address = wallet.address(); + println!("🔑 Wallet address: {}", address); + + let is_testnet = is_testnet(wallet.clone()).await; + let core_contracts = load_core_contracts(wallet.clone(), is_testnet); + + println!( + "Are you sure you want to transfer ownership to {}? (y/n)", + new_owner + ); + let mut input = String::new(); + std::io::stdin() + .read_line(&mut input) + .expect("Failed to read line"); + if input.trim().to_lowercase() != "y" { + println!("Operation cancelled."); + return; + } + + // Convert string address to Identity + let new_owner_identity = Identity::Address(new_owner.parse().expect("Invalid address format")); + + let _ = borrow_operations_abi::transfer_owner( + &core_contracts.borrow_operations, + new_owner_identity, + ) + .await + .unwrap(); + + let _ = + protocol_manager_abi::transfer_owner(&core_contracts.protocol_manager, new_owner_identity) + .await + .unwrap(); + + println!("Ownership transferred successfully to {}", new_owner); +} diff --git a/deploy-scripts/src/utils.rs b/deploy-scripts/src/utils.rs index d503db07..35ddea0e 100644 --- a/deploy-scripts/src/utils.rs +++ b/deploy-scripts/src/utils.rs @@ -1,11 +1,21 @@ pub mod utils { + use csv::ReaderBuilder; use fuels::accounts::{provider::Provider, wallet::WalletUnlocked}; use fuels::prelude::*; use fuels::types::bech32::Bech32ContractId; - use fuels::types::{Bits256, U256}; + use fuels::types::{Bits256, Identity, U256}; + use serde_json::json; + use std::fs::File; + use std::io::Write; use std::str::FromStr; - use test_utils::data_structures::AssetContracts; - + use test_utils::data_structures::{ + AssetContracts, AssetContractsOptionalRedstone, ContractInstance, PRECISION, + }; + use test_utils::interfaces::oracle::oracle_abi; + use test_utils::interfaces::pyth_oracle::pyth_oracle_abi; + use test_utils::interfaces::redstone_oracle::redstone_oracle_abi; + use test_utils::interfaces::vesting::{VestingSchedule, TOTAL_AMOUNT_VESTED}; + use test_utils::setup::common::get_absolute_path_from_relative; use test_utils::{ data_structures::ProtocolContracts, interfaces::{ @@ -18,12 +28,19 @@ pub mod utils { vesting::VestingContract, }, }; + + use crate::constants::{ + MAINNET_CONTRACTS_FILE, MAINNET_RPC, TESTNET_CONTRACTS_FILE, TESTNET_RPC, + }; pub async fn setup_wallet() -> WalletUnlocked { - let rpc = match std::env::var("RPC") { - Ok(s) => s, - Err(error) => panic!("❌ Cannot find .env file: {:#?}", error), + let network = + std::env::var("NETWORK").expect("NETWORK must be set to 'mainnet' or 'testnet'"); + + let rpc: String = match network.as_str() { + "mainnet" => MAINNET_RPC.to_string(), + "testnet" => TESTNET_RPC.to_string(), + _ => panic!("❌ NETWORK must be 'mainnet' or 'testnet'"), }; - println!("RPC: {}", rpc); let provider = match Provider::connect(rpc).await { Ok(p) => p, @@ -43,8 +60,15 @@ pub mod utils { .unwrap() } - pub fn load_core_contracts(wallet: WalletUnlocked) -> ProtocolContracts { - let json = std::fs::read_to_string("contracts.json").unwrap(); + pub fn load_core_contracts( + wallet: WalletUnlocked, + is_testnet: bool, + ) -> ProtocolContracts { + let json = std::fs::read_to_string(match is_testnet { + true => TESTNET_CONTRACTS_FILE, + false => MAINNET_CONTRACTS_FILE, + }) + .unwrap(); let contracts: serde_json::Value = serde_json::from_str(&json).unwrap(); let borrow_operations_contract_id: Bech32ContractId = contracts["borrow_operations"] @@ -52,72 +76,172 @@ pub mod utils { .unwrap() .parse() .unwrap(); - let borrow_operations = - BorrowOperations::new(borrow_operations_contract_id, wallet.clone()); - + let borrow_operations_implementation_id: ContractId = contracts + ["borrow_operations_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let borrow_operations = ContractInstance::new( + BorrowOperations::new(borrow_operations_contract_id.clone(), wallet.clone()), + borrow_operations_implementation_id.into(), + ); let usdf_contract_id: Bech32ContractId = contracts["usdf"].as_str().unwrap().parse().unwrap(); - let usdf = - test_utils::interfaces::usdf_token::USDFToken::new(usdf_contract_id, wallet.clone()); + let usdf_implementation_id: ContractId = contracts["usdf_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let usdf = ContractInstance::new( + test_utils::interfaces::usdf_token::USDFToken::new(usdf_contract_id, wallet.clone()), + usdf_implementation_id.into(), + ); let stability_pool_contract_id: Bech32ContractId = contracts["stability_pool"] .as_str() .unwrap() .parse() .unwrap(); - let stability_pool = StabilityPool::new(stability_pool_contract_id, wallet.clone()); + let stability_pool_implementation_id: ContractId = contracts + ["stability_pool_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let stability_pool = ContractInstance::new( + StabilityPool::new(stability_pool_contract_id.clone(), wallet.clone()), + stability_pool_implementation_id.into(), + ); let protocol_manager_contract_id: Bech32ContractId = contracts["protocol_manager"] .as_str() .unwrap() .parse() .unwrap(); - let protocol_manager = ProtocolManager::new(protocol_manager_contract_id, wallet.clone()); + let protocol_manager_implementation_id: ContractId = contracts + ["protocol_manager_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let protocol_manager = ContractInstance::new( + ProtocolManager::new(protocol_manager_contract_id.clone(), wallet.clone()), + protocol_manager_implementation_id.into(), + ); let fpt_staking_contract_id: Bech32ContractId = contracts["fpt_staking"].as_str().unwrap().parse().unwrap(); - let fpt_staking = FPTStaking::new(fpt_staking_contract_id, wallet.clone()); + let fpt_staking_implementation_id: ContractId = contracts["fpt_staking_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let fpt_staking = ContractInstance::new( + FPTStaking::new(fpt_staking_contract_id.clone(), wallet.clone()), + fpt_staking_implementation_id.into(), + ); let fpt_token_contract_id: Bech32ContractId = contracts["fpt_token"].as_str().unwrap().parse().unwrap(); - let fpt_token = FPTToken::new(fpt_token_contract_id.clone(), wallet.clone()); + let fpt_token_implementation_id: ContractId = contracts["fpt_token_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let fpt_token = ContractInstance::new( + FPTToken::new(fpt_token_contract_id.clone(), wallet.clone()), + fpt_token_implementation_id.into(), + ); let community_issuance_contract_id: Bech32ContractId = contracts["community_issuance"] .as_str() .unwrap() .parse() .unwrap(); - let community_issuance = - CommunityIssuance::new(community_issuance_contract_id, wallet.clone()); + let community_issuance_implementation_id: ContractId = contracts + ["community_issuance_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let community_issuance = ContractInstance::new( + CommunityIssuance::new(community_issuance_contract_id.clone(), wallet.clone()), + community_issuance_implementation_id.into(), + ); let coll_surplus_pool_contract_id: Bech32ContractId = contracts["coll_surplus_pool"] .as_str() .unwrap() .parse() .unwrap(); - let coll_surplus_pool = CollSurplusPool::new(coll_surplus_pool_contract_id, wallet.clone()); + let coll_surplus_pool_implementation_id: ContractId = contracts + ["coll_surplus_pool_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let coll_surplus_pool = ContractInstance::new( + CollSurplusPool::new(coll_surplus_pool_contract_id.clone(), wallet.clone()), + coll_surplus_pool_implementation_id.into(), + ); let default_pool_contract_id: Bech32ContractId = contracts["default_pool"].as_str().unwrap().parse().unwrap(); - let default_pool = DefaultPool::new(default_pool_contract_id, wallet.clone()); + let default_pool_implementation_id: ContractId = contracts + ["default_pool_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let default_pool = ContractInstance::new( + DefaultPool::new(default_pool_contract_id.clone(), wallet.clone()), + default_pool_implementation_id.into(), + ); let active_pool_contract_id: Bech32ContractId = contracts["active_pool"].as_str().unwrap().parse().unwrap(); - let active_pool = ActivePool::new(active_pool_contract_id, wallet.clone()); + let active_pool_implementation_id: ContractId = contracts["active_pool_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let active_pool = ContractInstance::new( + ActivePool::new(active_pool_contract_id.clone(), wallet.clone()), + active_pool_implementation_id.into(), + ); let sorted_troves_contract_id: Bech32ContractId = contracts["sorted_troves"] .as_str() .unwrap() .parse() .unwrap(); - let sorted_troves = SortedTroves::new(sorted_troves_contract_id, wallet.clone()); + let sorted_troves_implementation_id: ContractId = contracts + ["sorted_troves_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let sorted_troves = ContractInstance::new( + SortedTroves::new(sorted_troves_contract_id.clone(), wallet.clone()), + sorted_troves_implementation_id.into(), + ); let vesting_contract_id: Bech32ContractId = contracts["vesting_contract"] .as_str() .unwrap() .parse() .unwrap(); - let vesting_contract = VestingContract::new(vesting_contract_id, wallet.clone()); + let vesting_contract_implementation_id: ContractId = contracts + ["vesting_contract_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); + let vesting_contract = ContractInstance::new( + VestingContract::new(vesting_contract_id.clone(), wallet.clone()), + vesting_contract_implementation_id.into(), + ); let fpt_asset_id: AssetId = AssetId::from_str(contracts["fpt_asset_id"].as_str().unwrap()).unwrap(); @@ -139,32 +263,50 @@ pub mod utils { AssetId::from_str(asset_contract["asset_id"].as_str().unwrap()).unwrap(); let oracle_contract_id: Bech32ContractId = asset_contract["oracle"].as_str().unwrap().parse().unwrap(); + let oracle_implementation_id: ContractId = asset_contract + ["oracle_implementation_id"] + .as_str() + .unwrap() + .parse() + .unwrap(); let trove_manager_contract_id: Bech32ContractId = asset_contract["trove_manager"] .as_str() .unwrap() .parse() .unwrap(); - let pyth_contract_id: Bech32ContractId = asset_contract["pyth_contract"] + let trove_manager_implementation_id: ContractId = asset_contract + ["trove_manager_implementation_id"] .as_str() .unwrap() .parse() .unwrap(); - let redstone_contract_id: Bech32ContractId = asset_contract["redstone_contract"] + let pyth_contract_id: Bech32ContractId = asset_contract["pyth_contract"] .as_str() .unwrap() .parse() .unwrap(); + let redstone_contract_id: Bech32ContractId = asset_contract["redstone_contract"] + .as_str() + .unwrap_or("0") + .parse() + .unwrap_or(Bech32ContractId::default()); AssetContracts { asset: Token::new(asset_contract_id, wallet.clone()), asset_id, - oracle: test_utils::interfaces::oracle::Oracle::new( - oracle_contract_id, - wallet.clone(), + oracle: ContractInstance::new( + test_utils::interfaces::oracle::Oracle::new( + oracle_contract_id.clone(), + wallet.clone(), + ), + oracle_implementation_id.into(), ), - trove_manager: TroveManagerContract::new( - trove_manager_contract_id, - wallet.clone(), + trove_manager: ContractInstance::new( + TroveManagerContract::new( + trove_manager_contract_id.clone(), + wallet.clone(), + ), + trove_manager_implementation_id.into(), ), fuel_vm_decimals: asset_contract["fuel_vm_decimals"].as_u64().unwrap() as u32, mock_pyth_oracle: PythCore::new(pyth_contract_id, wallet.clone()), @@ -173,10 +315,10 @@ pub mod utils { asset_contract["pyth_price_id"].as_str().unwrap(), ) .unwrap(), - redstone_precision: asset_contract["redstone_precision"].as_u64().unwrap() + redstone_precision: asset_contract["redstone_precision"].as_u64().unwrap_or(9) as u32, redstone_price_id: U256::from_str( - asset_contract["redstone_price_id"].as_str().unwrap(), + asset_contract["redstone_price_id"].as_str().unwrap_or("0"), ) .unwrap(), } @@ -203,4 +345,208 @@ pub mod utils { protocol_contracts } + + pub async fn is_testnet(wallet: WalletUnlocked) -> bool { + let network_name = wallet.provider().unwrap().chain_info().await.unwrap().name; + network_name.to_lowercase().contains("testnet") + } + + pub fn write_asset_contracts_to_file( + asset_contracts: Vec>, + is_testnet: bool, + ) { + // Read existing contracts.json + let mut contracts: serde_json::Value = serde_json::from_str( + &std::fs::read_to_string(match is_testnet { + true => TESTNET_CONTRACTS_FILE, + false => MAINNET_CONTRACTS_FILE, + }) + .expect("Failed to read contracts.json"), + ) + .expect("Failed to parse contracts.json"); + + // Get existing asset_contracts or create an empty array if it doesn't exist + let mut existing_asset_contracts = contracts["asset_contracts"] + .as_array() + .cloned() + .unwrap_or_else(Vec::new); + + // Add new asset_contracts to the existing ones + for asset_contract in asset_contracts { + existing_asset_contracts.push(json!({ + "symbol": asset_contract.symbol, + "oracle": asset_contract.oracle.contract.contract_id().to_string(), + "oracle_implementation_id": format!("0x{}", asset_contract.oracle.implementation_id.to_string()), + "trove_manager": asset_contract.trove_manager.contract.contract_id().to_string(), + "trove_manager_implementation_id": format!("0x{}", asset_contract.trove_manager.implementation_id.to_string()), + "asset_contract": asset_contract.asset.contract_id().to_string(), + "asset_id": format!("0x{}", asset_contract.asset_id.to_string()), + "pyth_price_id": to_hex_str(&asset_contract.pyth_price_id), + "pyth_contract": asset_contract.mock_pyth_oracle.contract_id().to_string(), + "redstone": match &asset_contract.redstone_config { + Some(redstone_config) => { + json!({ + "redstone_contract": redstone_config.contract.to_string(), + "redstone_price_id": redstone_config.price_id.to_string(), + "redstone_precision": redstone_config.precision, + }) + }, + None => json!(null), + }, + "fuel_vm_decimals": asset_contract.fuel_vm_decimals, + })); + } + + // Update asset_contracts field with the combined list + contracts["asset_contracts"] = json!(existing_asset_contracts); + + // Write updated contracts back to file + let mut file = File::create(match is_testnet { + true => TESTNET_CONTRACTS_FILE, + false => MAINNET_CONTRACTS_FILE, + }) + .expect("Failed to open contracts.json for writing"); + file.write_all(serde_json::to_string_pretty(&contracts).unwrap().as_bytes()) + .expect("Failed to write to contracts.json"); + } + + pub async fn query_oracles( + asset_contracts: &AssetContractsOptionalRedstone, + wallet: WalletUnlocked, + ) { + let current_pyth_price = pyth_oracle_abi::price_unsafe( + &asset_contracts.mock_pyth_oracle, + &asset_contracts.pyth_price_id, + ) + .await + .value; + + let pyth_precision = current_pyth_price.exponent as usize; + println!( + "Current pyth price: {:.precision$}", + current_pyth_price.price as f64 / 10f64.powi(pyth_precision.try_into().unwrap()), + precision = pyth_precision + ); + let mut redstone_contract: Option> = None; + match &asset_contracts.redstone_config { + Some(redstone_config) => { + redstone_contract = + Some(RedstoneCore::new(redstone_config.contract, wallet.clone())); + } + None => {} + } + + let current_price = oracle_abi::get_price( + &asset_contracts.oracle, + &asset_contracts.mock_pyth_oracle, + &redstone_contract, + ) + .await + .value; + + println!( + "Current oracle proxy price: {:.9}", + current_price as f64 / 1_000_000_000.0 + ); + match &asset_contracts.redstone_config { + Some(redstone_config) => { + let redstone_precision = redstone_config.precision as usize; + let current_redstone_price = redstone_oracle_abi::read_prices( + &redstone_contract.unwrap(), + vec![redstone_config.price_id], + ) + .await + .value[0] + .as_u64(); + + println!( + "Current redstone price: {:.precision$}", + current_redstone_price as f64 + / 10f64.powi(redstone_precision.try_into().unwrap()), + precision = redstone_precision + ); + } + None => {} + } + } + pub fn to_hex_str(bits: &Bits256) -> String { + format!("0x{}", hex::encode(bits.0)) + } + + pub fn load_vesting_schedules_from_csv( + path: &str, + cliff_percentage: f64, + seconds_to_cliff: u64, + seconds_vesting_duration: u64, + treasury_identity: Identity, + ) -> Vec { + let absolute_path = get_absolute_path_from_relative(path); + let file = File::open(&absolute_path).expect("Failed to open file"); + let mut reader = ReaderBuilder::new() + .flexible(true) + .trim(csv::Trim::All) + .has_headers(false) + .from_reader(file); + + let now_unix = std::time::SystemTime::now() + .duration_since(std::time::UNIX_EPOCH) + .expect("Time went backwards") + .as_secs(); + + let cliff_timestamp = now_unix + seconds_to_cliff; + let end_timestamp = cliff_timestamp + seconds_vesting_duration; + let now_unix_and_5_minutes = now_unix + 5 * 60; + + let now_and_5_minutes = tai64::Tai64::from_unix(now_unix_and_5_minutes.try_into().unwrap()); + let cliff_timestamp = tai64::Tai64::from_unix(cliff_timestamp.try_into().unwrap()); + let end_timestamp = tai64::Tai64::from_unix(end_timestamp.try_into().unwrap()); + + let mut schedules = Vec::new(); + + for result in reader.records() { + let record = result.expect("Failed to read CSV record"); + if record.len() < 5 || record[1].is_empty() { + panic!("Invalid row found in CSV: {:?}", record); + } + + // println!("record: {:?}", record); + + let total_amount = (record[1].replace([',', '"'], "").parse::().unwrap() + * PRECISION as f64) as u64; + let recipient = if !record[2].is_empty() { + Identity::Address(Address::from_str(&record[2]).unwrap()) + } else if !record[3].is_empty() { + panic!("ETH addresses are not supported yet: {:?}", record); + } else { + panic!("No valid wallet address found in row: {:?}", record); + }; + + let schedule = VestingSchedule { + cliff_amount: (total_amount as f64 * cliff_percentage) as u64, + cliff_timestamp: cliff_timestamp.0, + end_timestamp: end_timestamp.0, + claimed_amount: 0, + total_amount, + recipient, + }; + + schedules.push(schedule); + } + // take the sum of all total_amounts + let total_sum: u64 = schedules.iter().map(|s| s.total_amount).sum(); + println!("Total sum of all vesting amounts: {}", total_sum); + // add one more schedule with the remaining amount + let remaining_amount = TOTAL_AMOUNT_VESTED - total_sum; + println!("Remaining amount: {}", remaining_amount); + // treasury vesting schedule + schedules.push(VestingSchedule { + cliff_amount: remaining_amount, + cliff_timestamp: now_and_5_minutes.0, // cliff timestamp is now + 5 minutes + end_timestamp: end_timestamp.0, + claimed_amount: 0, + total_amount: remaining_amount, + recipient: treasury_identity, + }); + schedules + } } diff --git a/fuel-toolchain.toml b/fuel-toolchain.toml index d23fef00..9cbb98d3 100644 --- a/fuel-toolchain.toml +++ b/fuel-toolchain.toml @@ -2,4 +2,4 @@ channel = "latest-aarch64-apple-darwin" [components] -forc = "0.63.5" +forc = "0.66.4" diff --git a/libraries/src/fluid_math.sw b/libraries/src/fluid_math.sw index 2311a8a4..6c9c5320 100644 --- a/libraries/src/fluid_math.sw +++ b/libraries/src/fluid_math.sw @@ -20,7 +20,7 @@ pub const MCR: u64 = 1_350_000_000; // 10 USDF pub const USDF_GAS_COMPENSATION: u64 = 10_000_000; -// min debt is 500 USDF +// min debt is 500 USDF for staging pub const MIN_NET_DEBT: u64 = 500_000_000_000; /* */ pub const PERCENT_DIVERSOR = 200; pub const POST_COLLATERAL_RATIO: u64 = 1_500_000_000; diff --git a/test-utils/Cargo.toml b/test-utils/Cargo.toml index 27f09a7c..704964ff 100644 --- a/test-utils/Cargo.toml +++ b/test-utils/Cargo.toml @@ -6,6 +6,7 @@ edition = "2021" license = "Apache-2.0" [dependencies] +csv = { workspace = true } dotenv = { workspace = true } fuels = { workspace = true } futures = { workspace = true } @@ -13,6 +14,7 @@ pbr = { workspace = true } rand = { workspace = true } serde = { workspace = true } serde_json = { workspace = true } +tai64 = { workspace = true } tokio = { workspace = true } [lib] diff --git a/test-utils/src/data_structures.rs b/test-utils/src/data_structures.rs index ea37bb60..4d947c1d 100644 --- a/test-utils/src/data_structures.rs +++ b/test-utils/src/data_structures.rs @@ -13,45 +13,182 @@ use fuels::{ pub const PRECISION: u64 = 1_000_000_000; pub const POST_LIQUIDATION_COLLATERAL_RATIO: u64 = 1_500_000_000; +pub struct ContractInstance { + pub contract: C, + pub implementation_id: ContractId, +} + +impl ContractInstance { + pub fn new(contract: C, implementation_id: ContractId) -> Self { + Self { + contract, + implementation_id, + } + } +} + +impl Clone for ContractInstance { + fn clone(&self) -> Self { + Self { + contract: self.contract.clone(), + implementation_id: self.implementation_id.clone(), + } + } +} + pub struct ProtocolContracts { - pub borrow_operations: BorrowOperations, - pub usdf: USDFToken, - pub stability_pool: StabilityPool, - pub protocol_manager: ProtocolManager, - pub asset_contracts: Vec>, - pub fpt_staking: FPTStaking, - pub coll_surplus_pool: CollSurplusPool, - pub sorted_troves: SortedTroves, - pub default_pool: DefaultPool, - pub active_pool: ActivePool, - pub fpt_token: FPTToken, - pub community_issuance: CommunityIssuance, - pub vesting_contract: VestingContract, + pub borrow_operations: ContractInstance>, + pub usdf: ContractInstance>, + pub stability_pool: ContractInstance>, + pub protocol_manager: ContractInstance>, + pub asset_contracts: Vec>, // TODO: Change to AssetContractsOptionalRedstone but it's a big refactor + pub fpt_staking: ContractInstance>, + pub coll_surplus_pool: ContractInstance>, + pub sorted_troves: ContractInstance>, + pub default_pool: ContractInstance>, + pub active_pool: ContractInstance>, + pub fpt_token: ContractInstance>, + pub community_issuance: ContractInstance>, + pub vesting_contract: ContractInstance>, pub fpt_asset_id: AssetId, pub usdf_asset_id: AssetId, } pub struct AssetContracts { pub asset: Token, - pub oracle: Oracle, + pub oracle: ContractInstance>, pub mock_pyth_oracle: PythCore, pub mock_redstone_oracle: RedstoneCore, - pub trove_manager: TroveManagerContract, + pub trove_manager: ContractInstance>, pub asset_id: AssetId, pub pyth_price_id: Bits256, pub redstone_price_id: U256, pub redstone_precision: u32, pub fuel_vm_decimals: u32, } +pub struct AssetContractsOptionalRedstone { + pub symbol: String, + pub asset: Token, + pub oracle: ContractInstance>, + pub mock_pyth_oracle: PythCore, + pub trove_manager: ContractInstance>, + pub asset_id: AssetId, + pub pyth_price_id: Bits256, + pub fuel_vm_decimals: u32, + pub redstone_config: Option, +} pub struct ExistingAssetContracts { + pub symbol: String, + pub asset: Option, + pub pyth_oracle: Option, + pub redstone_oracle: Option, +} + +pub struct AssetConfig { pub asset: ContractId, pub asset_id: AssetId, - pub pyth_oracle: ContractId, - pub pyth_price_id: Bits256, - pub pyth_precision: u8, - pub redstone_oracle: ContractId, - pub redstone_price_id: U256, - pub redstone_precision: u32, pub fuel_vm_decimals: u32, } + +pub struct PythConfig { + pub contract: ContractId, + pub price_id: Bits256, +} + +pub struct RedstoneConfig { + pub contract: ContractId, + pub price_id: U256, + pub precision: u32, +} + +impl ProtocolContracts { + pub fn print_contract_ids(&self) { + println!( + "Borrow Operations Contract ID: {:?}", + self.borrow_operations.contract.contract_id() + ); + println!( + "Borrow Operations Implementation ID: {:?}", + self.borrow_operations.implementation_id + ); + println!( + "USDF Token Contract ID: {:?}", + self.usdf.contract.contract_id() + ); + println!( + "USDF Token Implementation ID: {:?}", + self.usdf.implementation_id + ); + println!( + "Stability Pool Contract ID: {:?}", + self.stability_pool.contract.contract_id() + ); + println!( + "Protocol Manager Contract ID: {:?}", + self.protocol_manager.contract.contract_id() + ); + for asset_contract in &self.asset_contracts { + println!( + "Asset Contract ID: {:?}", + asset_contract.asset.contract_id() + ); + println!( + "Oracle Contract ID: {:?}", + asset_contract.oracle.contract.contract_id() + ); + println!( + "Mock Pyth Oracle Contract ID: {:?}", + asset_contract.mock_pyth_oracle.contract_id() + ); + println!( + "Mock Redstone Oracle Contract ID: {:?}", + asset_contract.mock_redstone_oracle.contract_id() + ); + println!( + "Trove Manager Contract ID: {:?}", + asset_contract.trove_manager.contract.contract_id() + ); + } + println!( + "FPT Staking Contract ID: {:?}", + self.fpt_staking.contract.contract_id() + ); + println!( + "Coll Surplus Pool Contract ID: {:?}", + self.coll_surplus_pool.contract.contract_id() + ); + println!( + "Sorted Troves Contract ID: {:?}", + self.sorted_troves.contract.contract_id() + ); + println!( + "Sorted Troves Implementation ID: {:?}", + self.sorted_troves.implementation_id + ); + println!( + "Default Pool Contract ID: {:?}", + self.default_pool.contract.contract_id() + ); + println!( + "Active Pool Contract ID: {:?}", + self.active_pool.contract.contract_id() + ); + println!( + "FPT Token Contract ID: {:?}", + self.fpt_token.contract.contract_id() + ); + println!( + "Community Issuance Contract ID: {:?}", + self.community_issuance.contract.contract_id() + ); + println!( + "Vesting Contract ID: {:?}", + self.vesting_contract.contract.contract_id() + ); + println!( + "Vesting Implementation ID: {:?}", + self.vesting_contract.implementation_id + ); + } +} diff --git a/test-utils/src/interfaces/active_pool.rs b/test-utils/src/interfaces/active_pool.rs index 821a0bb0..53e3bd71 100644 --- a/test-utils/src/interfaces/active_pool.rs +++ b/test-utils/src/interfaces/active_pool.rs @@ -8,6 +8,7 @@ abigen!(Contract( pub mod active_pool_abi { use super::*; + use crate::data_structures::ContractInstance; use crate::interfaces::default_pool::DefaultPool; use crate::interfaces::token::Token; use fuels::prelude::Account; @@ -18,7 +19,7 @@ pub mod active_pool_abi { }; pub async fn initialize( - active_pool: &ActivePool, + active_pool: &ContractInstance>, borrow_operations: Identity, stability_pool: Identity, default_pool: ContractId, @@ -27,6 +28,7 @@ pub mod active_pool_abi { let tx_params = TxPolicies::default().with_tip(1); let res = active_pool + .contract .methods() .initialize( borrow_operations.clone(), @@ -34,6 +36,10 @@ pub mod active_pool_abi { default_pool, protocol_manager, ) + .with_contract_ids(&[ + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await; @@ -42,39 +48,54 @@ pub mod active_pool_abi { } pub async fn get_usdf_debt( - active_pool: &ActivePool, + active_pool: &ContractInstance>, asset_id: AssetId, ) -> CallResponse { active_pool + .contract .methods() .get_usdf_debt(asset_id.into()) + .with_contract_ids(&[ + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn get_asset( - active_pool: &ActivePool, + active_pool: &ContractInstance>, asset_id: AssetId, ) -> CallResponse { active_pool + .contract .methods() .get_asset(asset_id.into()) + .with_contract_ids(&[ + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn increase_usdf_debt( - active_pool: &ActivePool, + active_pool: &ContractInstance>, amount: u64, asset_id: AssetId, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); active_pool + .contract .methods() .increase_usdf_debt(amount, asset_id.into()) + .with_contract_ids(&[ + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -82,15 +103,20 @@ pub mod active_pool_abi { } pub async fn decrease_usdf_debt( - active_pool: &ActivePool, + active_pool: &ContractInstance>, amount: u64, asset_id: AssetId, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); active_pool + .contract .methods() .decrease_usdf_debt(amount, asset_id.into()) + .with_contract_ids(&[ + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -98,15 +124,20 @@ pub mod active_pool_abi { } pub async fn add_asset( - active_pool: &ActivePool, + active_pool: &ContractInstance>, asset_id: AssetId, trove_manager: Identity, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); active_pool + .contract .methods() .add_asset(asset_id.into(), trove_manager) + .with_contract_ids(&[ + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -114,7 +145,7 @@ pub mod active_pool_abi { } pub async fn recieve( - active_pool: &ActivePool, + active_pool: &ContractInstance>, token: &Token, amount: u64, ) -> CallResponse<()> { @@ -128,11 +159,16 @@ pub mod active_pool_abi { .with_asset_id(mock_asset_id); active_pool + .contract .methods() .recieve() .call_params(call_params) .unwrap() .with_contracts(&[token]) + .with_contract_ids(&[ + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(2)) .call() .await @@ -140,14 +176,19 @@ pub mod active_pool_abi { } pub async fn send_asset( - active_pool: &ActivePool, + active_pool: &ContractInstance>, recipient: Identity, amount: u64, asset_id: AssetId, ) -> CallResponse<()> { active_pool + .contract .methods() .send_asset(recipient, amount, asset_id.into()) + .with_contract_ids(&[ + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .call() .await @@ -155,12 +196,13 @@ pub mod active_pool_abi { } pub async fn send_asset_to_default_pool( - active_pool: &ActivePool, - default_pool: &DefaultPool, + active_pool: &ContractInstance>, + default_pool: &ContractInstance>, asset: &Token, amount: u64, ) -> Result, Error> { active_pool + .contract .methods() .send_asset_to_default_pool( amount, @@ -169,7 +211,13 @@ pub mod active_pool_abi { .asset_id(&AssetId::zeroed().into()) .into(), ) - .with_contracts(&[default_pool, asset]) + .with_contracts(&[&default_pool.contract, asset]) + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .call() .await diff --git a/test-utils/src/interfaces/borrow_operations.rs b/test-utils/src/interfaces/borrow_operations.rs index 0cb2e164..47cff623 100644 --- a/test-utils/src/interfaces/borrow_operations.rs +++ b/test-utils/src/interfaces/borrow_operations.rs @@ -8,6 +8,7 @@ abigen!(Contract( pub mod borrow_operations_abi { use super::*; + use crate::data_structures::ContractInstance; use crate::interfaces::active_pool::ActivePool; use crate::interfaces::coll_surplus_pool::CollSurplusPool; use crate::interfaces::default_pool::DefaultPool; @@ -25,7 +26,7 @@ pub mod borrow_operations_abi { use fuels::types::{AssetId, Identity}; pub async fn initialize( - borrow_operations: &BorrowOperations, + borrow_operations: &ContractInstance>, usdf_contract: ContractId, fpt_staking_contract: ContractId, protocol_manager_contract: ContractId, @@ -38,6 +39,7 @@ pub mod borrow_operations_abi { .with_script_gas_limit(2000000); borrow_operations + .contract .methods() .initialize( usdf_contract, @@ -48,22 +50,23 @@ pub mod borrow_operations_abi { sorted_troves_contract, ) .with_tx_policies(tx_params) + .with_contract_ids(&[borrow_operations.implementation_id.into()]) .call() .await .unwrap() } pub async fn open_trove( - borrow_operations: &BorrowOperations, - oracle: &Oracle, + borrow_operations: &ContractInstance>, + oracle: &ContractInstance>, mock_pyth: &PythCore, - mock_redstone: &RedstoneCore, + _mock_redstone: &RedstoneCore, asset_token: &Token, - usdf_token: &USDFToken, - fpt_staking: &FPTStaking, - sorted_troves: &SortedTroves, - trove_manager: &TroveManagerContract, - active_pool: &ActivePool, + usdf_token: &ContractInstance>, + fpt_staking: &ContractInstance>, + sorted_troves: &ContractInstance>, + trove_manager: &ContractInstance>, + active_pool: &ContractInstance>, collateral_amount_deposit: u64, usdf_amount_withdrawn: u64, upper_hint: Identity, @@ -81,19 +84,37 @@ pub mod borrow_operations_abi { .with_asset_id(asset_id); return borrow_operations + .contract .methods() .open_trove(usdf_amount_withdrawn, upper_hint, lower_hint) .call_params(call_params) .unwrap() .with_contracts(&[ - oracle, + &oracle.contract, mock_pyth, - mock_redstone, - active_pool, - usdf_token, - sorted_troves, - trove_manager, - fpt_staking, + //mock_redstone, + &active_pool.contract, + &usdf_token.contract, + &sorted_troves.contract, + &trove_manager.contract, + &fpt_staking.contract, + ]) + .with_contract_ids(&[ + borrow_operations.contract.contract_id().into(), + borrow_operations.implementation_id.into(), + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + mock_pyth.contract_id().into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + usdf_token.contract.contract_id().into(), + usdf_token.implementation_id.into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(3)) .with_tx_policies(tx_params) @@ -102,15 +123,15 @@ pub mod borrow_operations_abi { } pub async fn add_coll( - borrow_operations: &BorrowOperations, - oracle: &Oracle, + borrow_operations: &ContractInstance>, + oracle: &ContractInstance>, pyth: &PythCore, redstone: &RedstoneCore, mock_token: &Token, - usdf_token: &USDFToken, - sorted_troves: &SortedTroves, - trove_manager: &TroveManagerContract, - active_pool: &ActivePool, + usdf_token: &ContractInstance>, + sorted_troves: &ContractInstance>, + trove_manager: &ContractInstance>, + active_pool: &ContractInstance>, amount: u64, lower_hint: Identity, upper_hint: Identity, @@ -129,19 +150,37 @@ pub mod borrow_operations_abi { .with_asset_id(mock_asset_id); borrow_operations + .contract .methods() .add_coll(lower_hint, upper_hint) .call_params(call_params) .unwrap() .with_contracts(&[ - oracle, + &oracle.contract, pyth, redstone, mock_token, - sorted_troves, - trove_manager, - active_pool, - usdf_token, + &sorted_troves.contract, + &trove_manager.contract, + &active_pool.contract, + &usdf_token.contract, + ]) + .with_contract_ids(&[ + borrow_operations.contract.contract_id().into(), + borrow_operations.implementation_id.into(), + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + pyth.contract_id().into(), + redstone.contract_id().into(), + mock_token.contract_id().into(), + usdf_token.contract.contract_id().into(), + usdf_token.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .with_tx_policies(tx_params) @@ -150,14 +189,14 @@ pub mod borrow_operations_abi { } pub async fn withdraw_coll( - borrow_operations: &BorrowOperations, - oracle: &Oracle, + borrow_operations: &ContractInstance>, + oracle: &ContractInstance>, pyth: &PythCore, redstone: &RedstoneCore, mock_token: &Token, - sorted_troves: &SortedTroves, - trove_manager: &TroveManagerContract, - active_pool: &ActivePool, + sorted_troves: &ContractInstance>, + trove_manager: &ContractInstance>, + active_pool: &ContractInstance>, amount: u64, lower_hint: Identity, upper_hint: Identity, @@ -172,16 +211,32 @@ pub mod borrow_operations_abi { .into(); borrow_operations + .contract .methods() .withdraw_coll(amount, lower_hint, upper_hint, mock_asset_id.into()) .with_contracts(&[ - oracle, + &oracle.contract, pyth, redstone, mock_token, - sorted_troves, - trove_manager, - active_pool, + &sorted_troves.contract, + &trove_manager.contract, + &active_pool.contract, + ]) + .with_contract_ids(&[ + borrow_operations.contract.contract_id().into(), + borrow_operations.implementation_id.into(), + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + pyth.contract_id().into(), + redstone.contract_id().into(), + mock_token.contract_id().into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .with_tx_policies(tx_params) @@ -190,16 +245,16 @@ pub mod borrow_operations_abi { } pub async fn withdraw_usdf( - borrow_operations: &BorrowOperations, - oracle: &Oracle, + borrow_operations: &ContractInstance>, + oracle: &ContractInstance>, pyth: &PythCore, redstone: &RedstoneCore, mock_token: &Token, - usdf_token: &USDFToken, - fpt_staking: &FPTStaking, - sorted_troves: &SortedTroves, - trove_manager: &TroveManagerContract, - active_pool: &ActivePool, + usdf_token: &ContractInstance>, + fpt_staking: &ContractInstance>, + sorted_troves: &ContractInstance>, + trove_manager: &ContractInstance>, + active_pool: &ContractInstance>, amount: u64, lower_hint: Identity, upper_hint: Identity, @@ -214,18 +269,38 @@ pub mod borrow_operations_abi { .into(); borrow_operations + .contract .methods() .withdraw_usdf(amount, lower_hint, upper_hint, mock_asset_id.into()) .with_contracts(&[ - oracle, + &oracle.contract, pyth, redstone, mock_token, - sorted_troves, - trove_manager, - active_pool, - usdf_token, - fpt_staking, + &sorted_troves.contract, + &trove_manager.contract, + &active_pool.contract, + &usdf_token.contract, + &fpt_staking.contract, + ]) + .with_contract_ids(&[ + borrow_operations.contract.contract_id().into(), + borrow_operations.implementation_id.into(), + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + pyth.contract_id().into(), + redstone.contract_id().into(), + mock_token.contract_id().into(), + usdf_token.contract.contract_id().into(), + usdf_token.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .with_tx_policies(tx_params) @@ -234,16 +309,16 @@ pub mod borrow_operations_abi { } pub async fn repay_usdf( - borrow_operations: &BorrowOperations, - oracle: &Oracle, + borrow_operations: &ContractInstance>, + oracle: &ContractInstance>, pyth: &PythCore, redstone: &RedstoneCore, mock_token: &Token, - usdf_token: &USDFToken, - sorted_troves: &SortedTroves, - trove_manager: &TroveManagerContract, - active_pool: &ActivePool, - default_pool: &DefaultPool, + usdf_token: &ContractInstance>, + sorted_troves: &ContractInstance>, + trove_manager: &ContractInstance>, + active_pool: &ContractInstance>, + default_pool: &ContractInstance>, amount: u64, lower_hint: Identity, upper_hint: Identity, @@ -252,6 +327,7 @@ pub mod borrow_operations_abi { .with_tip(1) .with_script_gas_limit(2000000); let usdf_asset_id = usdf_token + .contract .contract_id() .asset_id(&AssetId::zeroed().into()) .into(); @@ -266,18 +342,38 @@ pub mod borrow_operations_abi { .into(); borrow_operations + .contract .methods() .repay_usdf(lower_hint, upper_hint, mock_asset_id.into()) .with_contracts(&[ - oracle, + &oracle.contract, pyth, redstone, mock_token, - sorted_troves, - trove_manager, - active_pool, - usdf_token, - default_pool, + &sorted_troves.contract, + &trove_manager.contract, + &active_pool.contract, + &usdf_token.contract, + &default_pool.contract, + ]) + .with_contract_ids(&[ + borrow_operations.contract.contract_id().into(), + borrow_operations.implementation_id.into(), + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + pyth.contract_id().into(), + redstone.contract_id().into(), + mock_token.contract_id().into(), + usdf_token.contract.contract_id().into(), + usdf_token.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .with_tx_policies(tx_params) @@ -288,22 +384,23 @@ pub mod borrow_operations_abi { } pub async fn close_trove( - borrow_operations: &BorrowOperations, - oracle: &Oracle, + borrow_operations: &ContractInstance>, + oracle: &ContractInstance>, pyth: &PythCore, redstone: &RedstoneCore, mock_token: &Token, - usdf_token: &USDFToken, - fpt_staking: &FPTStaking, - sorted_troves: &SortedTroves, - trove_manager: &TroveManagerContract, - active_pool: &ActivePool, + usdf_token: &ContractInstance>, + fpt_staking: &ContractInstance>, + sorted_troves: &ContractInstance>, + trove_manager: &ContractInstance>, + active_pool: &ContractInstance>, amount: u64, ) -> Result, Error> { let tx_params = TxPolicies::default() .with_tip(1) .with_script_gas_limit(2000000); let usdf_asset_id: AssetId = usdf_token + .contract .contract_id() .asset_id(&AssetId::zeroed().into()) .into(); @@ -320,18 +417,38 @@ pub mod borrow_operations_abi { .into(); borrow_operations + .contract .methods() .close_trove(mock_asset_id.into()) .with_contracts(&[ - oracle, + &oracle.contract, pyth, redstone, mock_token, - sorted_troves, - trove_manager, - active_pool, - usdf_token, - fpt_staking, + &sorted_troves.contract, + &trove_manager.contract, + &active_pool.contract, + &usdf_token.contract, + &fpt_staking.contract, + ]) + .with_contract_ids(&[ + borrow_operations.contract.contract_id().into(), + borrow_operations.implementation_id.into(), + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + pyth.contract_id().into(), + redstone.contract_id().into(), + mock_token.contract_id().into(), + usdf_token.contract.contract_id().into(), + usdf_token.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(3)) .with_tx_policies(tx_params) @@ -342,7 +459,7 @@ pub mod borrow_operations_abi { } pub async fn add_asset( - borrow_operations: BorrowOperations, + borrow_operations: &ContractInstance>, oracle: ContractId, trove_manager: ContractId, asset: AssetId, @@ -352,6 +469,7 @@ pub mod borrow_operations_abi { .with_script_gas_limit(2000000); return borrow_operations + .contract .methods() .add_asset(asset.into(), trove_manager, oracle) .with_tx_policies(tx_params) @@ -360,7 +478,7 @@ pub mod borrow_operations_abi { } pub async fn set_pause_status( - borrow_operations: &BorrowOperations, + borrow_operations: &ContractInstance>, is_paused: bool, ) -> Result, Error> { let tx_params = TxPolicies::default() @@ -368,54 +486,69 @@ pub mod borrow_operations_abi { .with_script_gas_limit(2000000); borrow_operations + .contract .methods() .set_pause_status(is_paused) + .with_contract_ids(&[borrow_operations.implementation_id.into()]) .with_tx_policies(tx_params) .call() .await } pub async fn get_pauser( - borrow_operations: &BorrowOperations, + borrow_operations: &ContractInstance>, ) -> Result, Error> { let tx_params = TxPolicies::default() .with_tip(1) .with_script_gas_limit(2000000); borrow_operations + .contract .methods() .get_pauser() + .with_contract_ids(&[borrow_operations.implementation_id.into()]) .with_tx_policies(tx_params) .call() .await } pub async fn get_is_paused( - borrow_operations: &BorrowOperations, + borrow_operations: &ContractInstance>, ) -> Result, Error> { let tx_params = TxPolicies::default() .with_tip(1) .with_script_gas_limit(2000000); borrow_operations + .contract .methods() .get_is_paused() + .with_contract_ids(&[borrow_operations.implementation_id.into()]) .with_tx_policies(tx_params) .call() .await } pub async fn claim_coll( - borrow_operations: &BorrowOperations, - active_pool: &ActivePool, - coll_surplus_pool: &CollSurplusPool, + borrow_operations: &ContractInstance>, + active_pool: &ContractInstance>, + coll_surplus_pool: &ContractInstance>, asset: AssetId, ) -> CallResponse<()> { borrow_operations + .contract .methods() .claim_collateral(asset.into()) - .with_contracts(&[active_pool, coll_surplus_pool]) + .with_contracts(&[&active_pool.contract, &coll_surplus_pool.contract]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) + .with_contract_ids(&[ + borrow_operations.contract.contract_id().into(), + borrow_operations.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + ]) .call() .await .unwrap() @@ -423,7 +556,7 @@ pub mod borrow_operations_abi { // Add these new functions to the module pub async fn set_pauser( - borrow_operations: &BorrowOperations, + borrow_operations: &ContractInstance>, pauser: Identity, ) -> Result, Error> { let tx_params = TxPolicies::default() @@ -431,15 +564,17 @@ pub mod borrow_operations_abi { .with_script_gas_limit(2000000); borrow_operations + .contract .methods() .set_pauser(pauser) + .with_contract_ids(&[borrow_operations.implementation_id.into()]) .with_tx_policies(tx_params) .call() .await } pub async fn transfer_owner( - borrow_operations: &BorrowOperations, + borrow_operations: &ContractInstance>, new_owner: Identity, ) -> Result, Error> { let tx_params = TxPolicies::default() @@ -447,23 +582,27 @@ pub mod borrow_operations_abi { .with_script_gas_limit(2000000); borrow_operations + .contract .methods() .transfer_owner(new_owner) + .with_contract_ids(&[borrow_operations.implementation_id.into()]) .with_tx_policies(tx_params) .call() .await } pub async fn renounce_owner( - borrow_operations: &BorrowOperations, + borrow_operations: &ContractInstance>, ) -> Result, Error> { let tx_params = TxPolicies::default() .with_tip(1) .with_script_gas_limit(2000000); borrow_operations + .contract .methods() .renounce_owner() + .with_contract_ids(&[borrow_operations.implementation_id.into()]) .with_tx_policies(tx_params) .call() .await @@ -475,7 +614,8 @@ pub mod borrow_operations_utils { use fuels::types::{Address, Identity}; use super::*; - use crate::interfaces::active_pool; + use crate::data_structures::ContractInstance; + use crate::interfaces::active_pool::ActivePool; use crate::interfaces::fpt_staking::FPTStaking; use crate::interfaces::sorted_troves::SortedTroves; use crate::interfaces::usdf_token::USDFToken; @@ -484,11 +624,11 @@ pub mod borrow_operations_utils { pub async fn mint_token_and_open_trove( wallet: WalletUnlocked, asset_contracts: &AssetContracts, - borrow_operations: &BorrowOperations, - usdf: &USDFToken, - fpt_staking: &FPTStaking, - active_pool: &active_pool::ActivePool, - sorted_troves: &SortedTroves, + borrow_operations: &ContractInstance>, + usdf: &ContractInstance>, + fpt_staking: &ContractInstance>, + active_pool: &ContractInstance>, + sorted_troves: &ContractInstance>, amount: u64, usdf_amount: u64, ) { @@ -499,8 +639,13 @@ pub mod borrow_operations_utils { ) .await; - let borrow_operations_healthy_wallet1 = - BorrowOperations::new(borrow_operations.contract_id().clone(), wallet.clone()); + let borrow_operations_healthy_wallet1 = ContractInstance::new( + BorrowOperations::new( + borrow_operations.contract.contract_id().clone(), + wallet.clone(), + ), + borrow_operations.implementation_id.into(), + ); borrow_operations_abi::open_trove( &borrow_operations_healthy_wallet1, diff --git a/test-utils/src/interfaces/coll_surplus_pool.rs b/test-utils/src/interfaces/coll_surplus_pool.rs index 6c926644..5e925804 100644 --- a/test-utils/src/interfaces/coll_surplus_pool.rs +++ b/test-utils/src/interfaces/coll_surplus_pool.rs @@ -8,6 +8,7 @@ abigen!(Contract( pub mod coll_surplus_pool_abi { use super::*; + use crate::data_structures::ContractInstance; use crate::interfaces::active_pool::ActivePool; use fuels::prelude::Error; use fuels::types::transaction_builders::VariableOutputPolicy; @@ -18,15 +19,20 @@ pub mod coll_surplus_pool_abi { }; pub async fn initialize( - coll_surplus_pool: &CollSurplusPool, + coll_surplus_pool: &ContractInstance>, borrow_operations: ContractId, protocol_manager: Identity, ) -> Result, Error> { let tx_params = TxPolicies::default().with_tip(1); let res = coll_surplus_pool + .contract .methods() .initialize(borrow_operations, protocol_manager) + .with_contract_ids(&[ + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await; @@ -35,60 +41,91 @@ pub mod coll_surplus_pool_abi { } pub async fn get_asset( - default_pool: &CollSurplusPool, + coll_surplus_pool: &ContractInstance>, asset: AssetId, ) -> Result, Error> { - default_pool.methods().get_asset(asset.into()).call().await + coll_surplus_pool + .contract + .methods() + .get_asset(asset.into()) + .with_contract_ids(&[ + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + ]) + .call() + .await } pub async fn claim_coll( - default_pool: &CollSurplusPool, + coll_surplus_pool: &ContractInstance>, acount: Identity, - active_pool: &ActivePool, + active_pool: &ContractInstance>, asset: AssetId, ) -> Result, Error> { - default_pool + coll_surplus_pool + .contract .methods() .claim_coll(acount, asset.into()) - .with_contracts(&[active_pool]) + .with_contracts(&[&active_pool.contract]) + .with_contract_ids(&[ + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .call() .await } pub async fn get_collateral( - default_pool: &CollSurplusPool, + coll_surplus_pool: &ContractInstance>, acount: Identity, asset: AssetId, ) -> Result, Error> { - default_pool + coll_surplus_pool + .contract .methods() .get_collateral(acount, asset.into()) + .with_contract_ids(&[ + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + ]) .call() .await } pub async fn add_asset( - default_pool: &CollSurplusPool, + coll_surplus_pool: &ContractInstance>, asset: AssetId, trove_manager: Identity, ) -> Result, Error> { - default_pool + coll_surplus_pool + .contract .methods() .add_asset(asset.into(), trove_manager) + .with_contract_ids(&[ + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + ]) .call() .await } pub async fn account_surplus( - default_pool: &CollSurplusPool, + coll_surplus_pool: &ContractInstance>, account: Identity, amount: u64, asset: AssetId, ) -> Result, Error> { - default_pool + coll_surplus_pool + .contract .methods() .account_surplus(account, amount, asset.into()) + .with_contract_ids(&[ + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + ]) .call() .await } diff --git a/test-utils/src/interfaces/community_issuance.rs b/test-utils/src/interfaces/community_issuance.rs index cbd9dd0d..bcedc3db 100644 --- a/test-utils/src/interfaces/community_issuance.rs +++ b/test-utils/src/interfaces/community_issuance.rs @@ -11,9 +11,11 @@ pub mod community_issuance_abi { use fuels::{prelude::ContractId, prelude::Error, types::AssetId, types::Identity}; + use crate::data_structures::ContractInstance; + use super::*; pub async fn initialize( - instance: &CommunityIssuance, + instance: &ContractInstance>, stability_pool_contract: ContractId, fpt_token_asset_id: AssetId, admin: &Identity, @@ -22,6 +24,7 @@ pub mod community_issuance_abi { let tx_params = TxPolicies::default().with_tip(1); let res = instance + .contract .methods() .initialize( stability_pool_contract, @@ -29,6 +32,10 @@ pub mod community_issuance_abi { admin.clone(), debugging, ) + .with_contract_ids(&[ + instance.contract.contract_id().into(), + instance.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await; @@ -37,14 +44,19 @@ pub mod community_issuance_abi { } pub async fn set_current_time( - instance: &CommunityIssuance, + instance: &ContractInstance>, time: u64, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); let res = instance + .contract .methods() .set_current_time(time) + .with_contract_ids(&[ + instance.contract.contract_id().into(), + instance.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await; @@ -53,13 +65,18 @@ pub mod community_issuance_abi { } pub async fn public_start_rewards_increase_transition_after_deadline( - instance: &CommunityIssuance, + instance: &ContractInstance>, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); let res = instance + .contract .methods() .public_start_rewards_increase_transition_after_deadline() + .with_contract_ids(&[ + instance.contract.contract_id().into(), + instance.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await; @@ -68,14 +85,19 @@ pub mod community_issuance_abi { } pub async fn start_rewards_increase_transition( - instance: &CommunityIssuance, + instance: &ContractInstance>, transition_time: u64, ) -> Result, Error> { let tx_params = TxPolicies::default().with_tip(1); let res = instance + .contract .methods() .start_rewards_increase_transition(transition_time) + .with_contract_ids(&[ + instance.contract.contract_id().into(), + instance.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await; diff --git a/test-utils/src/interfaces/default_pool.rs b/test-utils/src/interfaces/default_pool.rs index a853b9ea..091d3cda 100644 --- a/test-utils/src/interfaces/default_pool.rs +++ b/test-utils/src/interfaces/default_pool.rs @@ -8,6 +8,7 @@ abigen!(Contract( pub mod default_pool_abi { use super::*; + use crate::data_structures::ContractInstance; use crate::interfaces::active_pool::ActivePool; use crate::interfaces::token::Token; use fuels::prelude::Account; @@ -18,15 +19,20 @@ pub mod default_pool_abi { }; pub async fn initialize( - default_pool: &DefaultPool, + default_pool: &ContractInstance>, protocol_manager: Identity, active_pool: ContractId, ) -> Result, Error> { let tx_params = TxPolicies::default().with_tip(1); let res = default_pool + .contract .methods() .initialize(protocol_manager.clone(), active_pool) + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await; @@ -35,52 +41,72 @@ pub mod default_pool_abi { } pub async fn get_usdf_debt( - default_pool: &DefaultPool, + default_pool: &ContractInstance>, asset_id: AssetId, ) -> CallResponse { default_pool + .contract .methods() .get_usdf_debt(asset_id.into()) + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn get_asset( - default_pool: &DefaultPool, + default_pool: &ContractInstance>, asset_id: AssetId, ) -> CallResponse { default_pool + .contract .methods() .get_asset(asset_id.into()) + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn increase_usdf_debt( - default_pool: &DefaultPool, + default_pool: &ContractInstance>, amount: u64, asset_id: AssetId, ) -> CallResponse<()> { default_pool + .contract .methods() .increase_usdf_debt(amount, asset_id.into()) + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn add_asset( - default_pool: &DefaultPool, + default_pool: &ContractInstance>, asset_id: AssetId, trove_manager: Identity, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); default_pool + .contract .methods() .add_asset(asset_id.into(), trove_manager) + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -88,20 +114,25 @@ pub mod default_pool_abi { } pub async fn decrease_usdf_debt( - default_pool: &DefaultPool, + default_pool: &ContractInstance>, amount: u64, asset_id: AssetId, ) -> CallResponse<()> { default_pool + .contract .methods() .decrease_usdf_debt(amount, asset_id.into()) + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn recieve( - default_pool: &DefaultPool, + default_pool: &ContractInstance>, token: &Token, amount: u64, ) -> CallResponse<()> { @@ -114,12 +145,17 @@ pub mod default_pool_abi { let tx_params = TxPolicies::default().with_tip(1); default_pool + .contract .methods() .recieve() .with_tx_policies(tx_params) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .call_params(call_params) .unwrap() + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + ]) .with_contracts(&[token]) .call() .await @@ -127,15 +163,22 @@ pub mod default_pool_abi { } pub async fn send_asset_to_active_pool( - default_pool: &DefaultPool, - active_pool: &ActivePool, + default_pool: &ContractInstance>, + active_pool: &ContractInstance>, amount: u64, asset_id: AssetId, ) -> CallResponse<()> { default_pool + .contract .methods() .send_asset_to_active_pool(amount, asset_id.into()) - .with_contracts(&[active_pool]) + .with_contracts(&[&active_pool.contract]) + .with_contract_ids(&[ + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .call() .await diff --git a/test-utils/src/interfaces/fpt_staking.rs b/test-utils/src/interfaces/fpt_staking.rs index 13550ab3..a90f6955 100644 --- a/test-utils/src/interfaces/fpt_staking.rs +++ b/test-utils/src/interfaces/fpt_staking.rs @@ -9,6 +9,7 @@ abigen!(Contract( pub mod fpt_staking_abi { use super::*; + use crate::data_structures::ContractInstance; use crate::interfaces::token::Token; use crate::interfaces::usdf_token::USDFToken; use fuels::prelude::{Account, AssetId, CallParameters, Error}; @@ -16,22 +17,27 @@ pub mod fpt_staking_abi { use fuels::{prelude::ContractId, types::Identity}; pub async fn initialize( - fpt_staking: &FPTStaking, + fpt_staking: &ContractInstance>, protocol_manager_address: ContractId, borrower_operations_address: ContractId, - fpt_address: AssetId, - usdf_address: AssetId, + fpt_asset_id: AssetId, + usdf_asset_id: AssetId, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); fpt_staking + .contract .methods() .initialize( protocol_manager_address, borrower_operations_address, - fpt_address.into(), - usdf_address.into(), + fpt_asset_id.into(), + usdf_asset_id.into(), ) + .with_contract_ids(&[ + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -39,13 +45,18 @@ pub mod fpt_staking_abi { } pub async fn get_storage( - fpt_staking: &FPTStaking, + fpt_staking: &ContractInstance>, ) -> CallResponse { let tx_params = TxPolicies::default().with_tip(1); fpt_staking + .contract .methods() .get_storage() + .with_contract_ids(&[ + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -53,7 +64,7 @@ pub mod fpt_staking_abi { } pub async fn stake( - fpt_staking: &FPTStaking, + fpt_staking: &ContractInstance>, fpt_asset_id: AssetId, fpt_deposit_amount: u64, ) -> Result, Error> { @@ -66,8 +77,13 @@ pub mod fpt_staking_abi { .with_asset_id(fpt_asset_id); fpt_staking + .contract .methods() .stake() + .with_contract_ids(&[ + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call_params(call_params) .unwrap() @@ -76,8 +92,8 @@ pub mod fpt_staking_abi { } pub async fn unstake( - fpt_staking: &FPTStaking, - usdf_token: &USDFToken, + fpt_staking: &ContractInstance>, + usdf_token: &ContractInstance>, mock_token: &Token, fpt_token: &Token, amount: u64, @@ -88,82 +104,116 @@ pub mod fpt_staking_abi { .with_script_gas_limit(2000000); fpt_staking + .contract .methods() .unstake(amount) .with_tx_policies(tx_params) - .with_contracts(&[usdf_token, mock_token, fpt_token]) + .with_contracts(&[&usdf_token.contract, mock_token, fpt_token]) + .with_contract_ids(&[ + usdf_token.contract.contract_id().into(), + usdf_token.implementation_id.into(), + mock_token.contract_id().into(), + fpt_token.contract_id().into(), + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(10)) .call() .await } pub async fn add_asset( - fpt_staking: &FPTStaking, + fpt_staking: &ContractInstance>, asset_address: AssetId, ) -> CallResponse<()> { // let tx_params = TxPolicies::default().with_tip(1); fpt_staking + .contract .methods() .add_asset(asset_address.into()) + .with_contract_ids(&[ + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn get_pending_asset_gain( - fpt_staking: &FPTStaking, + fpt_staking: &ContractInstance>, id: Identity, asset_address: AssetId, ) -> CallResponse { // let tx_params = TxPolicies::default().with_tip(1); fpt_staking + .contract .methods() .get_pending_asset_gain(id, asset_address.into()) + .with_contract_ids(&[ + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn get_pending_usdf_gain( - fpt_staking: &FPTStaking, + fpt_staking: &ContractInstance>, id: Identity, ) -> CallResponse { // let tx_params = TxPolicies::default().with_tip(1); fpt_staking + .contract .methods() .get_pending_usdf_gain(id) + .with_contract_ids(&[ + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn increase_f_usdf( - fpt_staking: &FPTStaking, + fpt_staking: &ContractInstance>, usdf_fee_amount: u64, ) -> CallResponse<()> { // let tx_params = TxPolicies::default().with_tip(1); fpt_staking + .contract .methods() .increase_f_usdf(usdf_fee_amount) + .with_contract_ids(&[ + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn increase_f_asset( - fpt_staking: &FPTStaking, + fpt_staking: &ContractInstance>, asset_fee_amount: u64, asset_address: AssetId, ) -> CallResponse<()> { // let tx_params = TxPolicies::default().with_tip(1); fpt_staking + .contract .methods() .increase_f_asset(asset_fee_amount, asset_address.into()) + .with_contract_ids(&[ + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + ]) .call() .await .unwrap() diff --git a/test-utils/src/interfaces/fpt_token.rs b/test-utils/src/interfaces/fpt_token.rs index 394db557..a9f783cc 100644 --- a/test-utils/src/interfaces/fpt_token.rs +++ b/test-utils/src/interfaces/fpt_token.rs @@ -6,25 +6,35 @@ abigen!(Contract( )); pub mod fpt_token_abi { - use crate::interfaces::community_issuance::CommunityIssuance; use crate::interfaces::vesting::VestingContract; + use crate::{ + data_structures::ContractInstance, interfaces::community_issuance::CommunityIssuance, + }; use fuels::{prelude::*, types::ContractId}; use super::*; pub async fn initialize( - instance: &FPTToken, + instance: &ContractInstance>, vesting_contract: &VestingContract, - community_issuance_contract: &CommunityIssuance, + community_issuance_contract: &ContractInstance>, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); let res = instance + .contract .methods() .initialize( vesting_contract.contract_id(), - community_issuance_contract.contract_id(), + community_issuance_contract.contract.contract_id(), ) - .with_contracts(&[vesting_contract, community_issuance_contract]) + .with_contracts(&[vesting_contract, &community_issuance_contract.contract]) + .with_contract_ids(&[ + community_issuance_contract.contract.contract_id().into(), + community_issuance_contract.implementation_id.into(), + vesting_contract.contract_id().into(), + instance.contract.contract_id().into(), + instance.implementation_id.into(), + ]) .with_tx_policies(tx_params) .with_variable_output_policy(VariableOutputPolicy::Exactly(10)) .call() @@ -33,26 +43,39 @@ pub mod fpt_token_abi { return res.unwrap(); } - pub async fn total_supply(instance: &FPTToken) -> CallResponse> { + pub async fn total_supply( + instance: &ContractInstance>, + ) -> CallResponse> { let fpt_token_asset_id = instance + .contract .contract_id() .asset_id(&AssetId::zeroed().into()) .into(); instance + .contract .methods() .total_supply(fpt_token_asset_id) + .with_contract_ids(&[ + instance.contract.contract_id().into(), + instance.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn get_vesting_contract( - instance: &FPTToken, + instance: &ContractInstance>, ) -> CallResponse { instance + .contract .methods() .get_vesting_contract() + .with_contract_ids(&[ + instance.contract.contract_id().into(), + instance.implementation_id.into(), + ]) .call() .await .unwrap() diff --git a/test-utils/src/interfaces/hint_helper.rs b/test-utils/src/interfaces/hint_helper.rs index 743dc92c..81e17ddd 100644 --- a/test-utils/src/interfaces/hint_helper.rs +++ b/test-utils/src/interfaces/hint_helper.rs @@ -8,6 +8,7 @@ abigen!(Contract( pub mod hint_helper_abi { use super::*; + use crate::data_structures::ContractInstance; use crate::interfaces::sorted_troves::SortedTroves; use crate::interfaces::trove_manager::TroveManagerContract; use fuels::prelude::Account; @@ -35,8 +36,8 @@ pub mod hint_helper_abi { pub async fn get_approx_hint( hint_helper: &HintHelper, - trove_manager: &TroveManagerContract, - sorted_troves: &SortedTroves, + trove_manager: &ContractInstance>, + sorted_troves: &ContractInstance>, asset_id: &AssetId, cr: u64, num_itterations: u64, @@ -46,12 +47,18 @@ pub mod hint_helper_abi { .methods() .get_approx_hint( asset_id.clone(), - trove_manager.contract_id(), + trove_manager.contract.contract_id(), cr, num_itterations, random_seed, ) - .with_contracts(&[sorted_troves, trove_manager]) + .with_contracts(&[&sorted_troves.contract, &trove_manager.contract]) + .with_contract_ids(&[ + sorted_troves.contract.contract_id().into(), + sorted_troves.implementation_id.into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .call() .await .unwrap() diff --git a/test-utils/src/interfaces/mod.rs b/test-utils/src/interfaces/mod.rs index 319d163a..8bff2d58 100644 --- a/test-utils/src/interfaces/mod.rs +++ b/test-utils/src/interfaces/mod.rs @@ -9,6 +9,7 @@ pub mod hint_helper; pub mod multi_trove_getter; pub mod oracle; pub mod protocol_manager; +pub mod proxy; pub mod pyth_oracle; pub mod redstone_oracle; pub mod sorted_troves; diff --git a/test-utils/src/interfaces/multi_trove_getter.rs b/test-utils/src/interfaces/multi_trove_getter.rs index bafce8ac..c1f091a6 100644 --- a/test-utils/src/interfaces/multi_trove_getter.rs +++ b/test-utils/src/interfaces/multi_trove_getter.rs @@ -8,14 +8,15 @@ abigen!(Contract( pub mod multi_trove_getter_abi { use super::*; + use crate::data_structures::ContractInstance; use crate::interfaces::{sorted_troves::SortedTroves, trove_manager::TroveManagerContract}; use fuels::prelude::Account; use fuels::types::AssetId; pub async fn get_multiple_sorted_troves( multi_trove_getter: &MultiTroveGetter, - trove_manager: &TroveManagerContract, - sorted_troves: &SortedTroves, + trove_manager: &ContractInstance>, + sorted_troves: &ContractInstance>, asset_id: &AssetId, start_indx: u64, count: u8, @@ -23,12 +24,18 @@ pub mod multi_trove_getter_abi { multi_trove_getter .methods() .get_multiple_sorted_troves( - trove_manager.contract_id(), + trove_manager.contract.contract_id(), asset_id.clone(), start_indx, count, ) - .with_contracts(&[sorted_troves, trove_manager]) + .with_contracts(&[&sorted_troves.contract, &trove_manager.contract]) + .with_contract_ids(&[ + sorted_troves.contract.contract_id().into(), + sorted_troves.implementation_id.into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .call() .await .unwrap() @@ -37,7 +44,7 @@ pub mod multi_trove_getter_abi { pub mod multi_trove_getter_utils { use super::*; - use crate::data_structures::PRECISION; + use crate::data_structures::{ContractInstance, PRECISION}; use crate::interfaces::sorted_troves::SortedTroves; use crate::interfaces::trove_manager::TroveManagerContract; use fuels::prelude::Account; @@ -45,8 +52,8 @@ pub mod multi_trove_getter_utils { pub async fn print_troves_cr( multi_trove_getter: &MultiTroveGetter, - trove_manager: &TroveManagerContract, - sorted_troves: &SortedTroves, + trove_manager: &ContractInstance>, + sorted_troves: &ContractInstance>, asset_id: &AssetId, ) { let troves_after_rewards = multi_trove_getter_abi::get_multiple_sorted_troves( @@ -74,8 +81,8 @@ pub mod multi_trove_getter_utils { pub async fn assert_sorted_troves_by_cr( multi_trove_getter: &MultiTroveGetter, - trove_manager: &TroveManagerContract, - sorted_troves: &SortedTroves, + trove_manager: &ContractInstance>, + sorted_troves: &ContractInstance>, asset_id: &AssetId, ) { let troves = multi_trove_getter_abi::get_multiple_sorted_troves( diff --git a/test-utils/src/interfaces/oracle.rs b/test-utils/src/interfaces/oracle.rs index ec1993f2..71bf43a0 100644 --- a/test-utils/src/interfaces/oracle.rs +++ b/test-utils/src/interfaces/oracle.rs @@ -12,15 +12,17 @@ pub const ORACLE_TIMEOUT: u64 = 600; pub mod oracle_abi { + use crate::data_structures::ContractInstance; + use super::*; use fuels::{ prelude::{Account, TxPolicies}, programs::calls::ContractDependency, - types::errors::Error, + types::{bech32::Bech32ContractId, errors::Error}, }; pub async fn get_price( - oracle: &Oracle, + oracle: &ContractInstance>, pyth: &PythCore, redstone: &Option>, ) -> CallResponse { @@ -32,22 +34,40 @@ pub mod oracle_abi { with_contracts.push(redstone); } + let mut with_contract_ids: Vec = Vec::new(); + with_contract_ids.push(pyth.contract_id().into()); + with_contract_ids.push(oracle.implementation_id.into()); + with_contract_ids.push(oracle.contract.contract_id().into()); + if let Some(redstone) = redstone { + with_contract_ids.push(redstone.contract_id().into()); + } + oracle + .contract .methods() .get_price() .with_contracts(&with_contracts) + .with_contract_ids(&with_contract_ids) .with_tx_policies(tx_params) .call() .await .unwrap() } - pub async fn set_debug_timestamp(oracle: &Oracle, timestamp: u64) { + pub async fn set_debug_timestamp( + oracle: &ContractInstance>, + timestamp: u64, + ) { let tx_params = TxPolicies::default().with_tip(1); oracle + .contract .methods() .set_debug_timestamp(timestamp) + .with_contract_ids(&[ + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -55,16 +75,21 @@ pub mod oracle_abi { } pub async fn set_redstone_config( - oracle: &Oracle, + oracle: &ContractInstance>, redstone: &RedstoneCore, config: RedstoneConfig, ) -> Result, Error> { let tx_params = TxPolicies::default().with_tip(1); oracle + .contract .methods() .set_redstone_config(config) .with_contracts(&[redstone]) + .with_contract_ids(&[ + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await diff --git a/test-utils/src/interfaces/protocol_manager.rs b/test-utils/src/interfaces/protocol_manager.rs index 1654bd4d..486393ac 100644 --- a/test-utils/src/interfaces/protocol_manager.rs +++ b/test-utils/src/interfaces/protocol_manager.rs @@ -8,7 +8,7 @@ abigen!(Contract( pub mod protocol_manager_abi { use super::*; - use crate::data_structures; + use crate::data_structures::{self, ContractInstance}; use crate::interfaces::active_pool::ActivePool; use crate::interfaces::borrow_operations::BorrowOperations; use crate::interfaces::coll_surplus_pool::CollSurplusPool; @@ -19,6 +19,7 @@ pub mod protocol_manager_abi { use crate::interfaces::usdf_token::USDFToken; use data_structures::AssetContracts; use fuels::prelude::{Account, CallParameters, ContractDependency}; + use fuels::types::bech32::Bech32ContractId; use fuels::types::errors::Error; use fuels::types::transaction_builders::VariableOutputPolicy; use fuels::types::{Address, AssetId}; @@ -28,7 +29,7 @@ pub mod protocol_manager_abi { }; pub async fn initialize( - protocol_manager: &ProtocolManager, + protocol_manager: &ContractInstance>, borrow_operations: ContractId, stability_pool: ContractId, fpt_staking: ContractId, @@ -42,6 +43,7 @@ pub mod protocol_manager_abi { let tx_params = TxPolicies::default().with_tip(1); let res = protocol_manager + .contract .methods() .initialize( borrow_operations, @@ -55,6 +57,10 @@ pub mod protocol_manager_abi { admin, ) .with_tx_policies(tx_params) + .with_contract_ids(&[ + protocol_manager.contract.contract_id().into(), + protocol_manager.implementation_id.into(), + ]) .call() .await .unwrap(); @@ -63,52 +69,72 @@ pub mod protocol_manager_abi { } pub async fn register_asset( - protocol_manager: &ProtocolManager, + protocol_manager: &ContractInstance>, asset: AssetId, trove_manager: ContractId, oracle: ContractId, - borrow_operations: &BorrowOperations, - stability_pool: &StabilityPool, - usdf: &USDFToken, - fpt_staking: &FPTStaking, - coll_surplus_pool: &CollSurplusPool, - default_pool: &DefaultPool, - active_pool: &ActivePool, - sorted_troves: &SortedTroves, + borrow_operations: &ContractInstance>, + stability_pool: &ContractInstance>, + usdf: &ContractInstance>, + fpt_staking: &ContractInstance>, + coll_surplus_pool: &ContractInstance>, + default_pool: &ContractInstance>, + active_pool: &ContractInstance>, + sorted_troves: &ContractInstance>, ) -> Result, Error> { let tx_params = TxPolicies::default().with_tip(1); - protocol_manager + .contract .methods() .register_asset(asset.into(), trove_manager, oracle) .with_tx_policies(tx_params) .with_contracts(&[ - borrow_operations, - stability_pool, - usdf, - fpt_staking, - coll_surplus_pool, - default_pool, - active_pool, - sorted_troves, + &borrow_operations.contract, + &stability_pool.contract, + &usdf.contract, + &fpt_staking.contract, + &coll_surplus_pool.contract, + &default_pool.contract, + &active_pool.contract, + &sorted_troves.contract, + ]) + .with_contract_ids(&[ + protocol_manager.contract.contract_id().into(), + protocol_manager.implementation_id.into(), + borrow_operations.contract.contract_id().into(), + borrow_operations.implementation_id.into(), + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + fpt_staking.contract.contract_id().into(), + fpt_staking.implementation_id.into(), + usdf.contract.contract_id().into(), + usdf.implementation_id.into(), + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), ]) .call() .await } pub async fn redeem_collateral( - protocol_manager: &ProtocolManager, + protocol_manager: &ContractInstance>, amount: u64, max_iterations: u64, partial_redemption_hint: u64, upper_partial_hint: Option, lower_partial_hint: Option, - usdf: &USDFToken, - fpt_staking: &FPTStaking, - coll_surplus_pool: &CollSurplusPool, - default_pool: &DefaultPool, - active_pool: &ActivePool, - sorted_troves: &SortedTroves, + usdf: &ContractInstance>, + fpt_staking: &ContractInstance>, + coll_surplus_pool: &ContractInstance>, + default_pool: &ContractInstance>, + active_pool: &ContractInstance>, + sorted_troves: &ContractInstance>, aswith_contracts: &Vec>, ) -> CallResponse<()> { let tx_params = TxPolicies::default() @@ -116,6 +142,7 @@ pub mod protocol_manager_abi { .with_witness_limit(2000000) .with_script_gas_limit(2000000); let usdf_asset_id = usdf + .contract .contract_id() .asset_id(&AssetId::zeroed().into()) .into(); @@ -127,20 +154,48 @@ pub mod protocol_manager_abi { let mut with_contracts: Vec<&dyn ContractDependency> = Vec::new(); for contracts in aswith_contracts.iter() { - with_contracts.push(&contracts.trove_manager); - with_contracts.push(&contracts.oracle); + with_contracts.push(&contracts.trove_manager.contract); + with_contracts.push(&contracts.oracle.contract); with_contracts.push(&contracts.mock_pyth_oracle); with_contracts.push(&contracts.mock_redstone_oracle); } - with_contracts.push(fpt_staking); - with_contracts.push(coll_surplus_pool); - with_contracts.push(default_pool); - with_contracts.push(active_pool); - with_contracts.push(usdf); - with_contracts.push(sorted_troves); + with_contracts.push(&fpt_staking.contract); + with_contracts.push(&coll_surplus_pool.contract); + with_contracts.push(&default_pool.contract); + with_contracts.push(&active_pool.contract); + with_contracts.push(&usdf.contract); + with_contracts.push(&sorted_troves.contract); + + let mut with_contract_ids: Vec = Vec::new(); + with_contract_ids.push(sorted_troves.contract.contract_id().into()); + with_contract_ids.push(sorted_troves.implementation_id.into()); + with_contract_ids.push(fpt_staking.contract.contract_id().into()); + with_contract_ids.push(fpt_staking.implementation_id.into()); + with_contract_ids.push(coll_surplus_pool.contract.contract_id().into()); + with_contract_ids.push(coll_surplus_pool.implementation_id.into()); + with_contract_ids.push(default_pool.contract.contract_id().into()); + with_contract_ids.push(default_pool.implementation_id.into()); + with_contract_ids.push(active_pool.contract.contract_id().into()); + with_contract_ids.push(active_pool.implementation_id.into()); + with_contract_ids.push(usdf.contract.contract_id().into()); + with_contract_ids.push(usdf.implementation_id.into()); + with_contract_ids.push(sorted_troves.contract.contract_id().into()); + with_contract_ids.push(sorted_troves.implementation_id.into()); + with_contract_ids.push(protocol_manager.contract.contract_id().into()); + with_contract_ids.push(protocol_manager.implementation_id.into()); + + for contracts in aswith_contracts.iter() { + with_contract_ids.push(contracts.trove_manager.contract.contract_id().into()); + with_contract_ids.push(contracts.trove_manager.implementation_id.into()); + with_contract_ids.push(contracts.oracle.contract.contract_id().into()); + with_contract_ids.push(contracts.oracle.implementation_id.into()); + with_contract_ids.push(contracts.mock_pyth_oracle.contract_id().into()); + with_contract_ids.push(contracts.mock_redstone_oracle.contract_id().into()); + } protocol_manager + .contract .methods() .redeem_collateral( max_iterations, @@ -152,21 +207,29 @@ pub mod protocol_manager_abi { .call_params(call_params) .unwrap() .with_contracts(&with_contracts) + .with_contract_ids(&with_contract_ids.to_vec()) .with_variable_output_policy(VariableOutputPolicy::Exactly(10)) .call() .await .unwrap() } - pub async fn owner(protocol_manager: &ProtocolManager) -> CallResponse { + pub async fn owner( + protocol_manager: &ContractInstance>, + ) -> CallResponse { let tx_params = TxPolicies::default() .with_tip(1) .with_witness_limit(2000000) .with_script_gas_limit(2000000); protocol_manager + .contract .methods() .owner() + .with_contract_ids(&[ + protocol_manager.contract.contract_id().into(), + protocol_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -174,7 +237,7 @@ pub mod protocol_manager_abi { } pub async fn renounce_admin( - protocol_manager: &ProtocolManager, + protocol_manager: &ContractInstance>, ) -> Result, Error> { let tx_params = TxPolicies::default() .with_tip(1) @@ -182,22 +245,32 @@ pub mod protocol_manager_abi { .with_script_gas_limit(2000000); protocol_manager + .contract .methods() .renounce_admin() + .with_contract_ids(&[ + protocol_manager.contract.contract_id().into(), + protocol_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await } pub async fn transfer_owner( - protocol_manager: &ProtocolManager, + protocol_manager: &ContractInstance>, new_owner: Identity, ) -> Result, Error> { let tx_params = TxPolicies::default().with_tip(1); protocol_manager + .contract .methods() .transfer_owner(new_owner) + .with_contract_ids(&[ + protocol_manager.contract.contract_id().into(), + protocol_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await diff --git a/test-utils/src/interfaces/proxy.rs b/test-utils/src/interfaces/proxy.rs new file mode 100644 index 00000000..ee11d173 --- /dev/null +++ b/test-utils/src/interfaces/proxy.rs @@ -0,0 +1,52 @@ +use fuels::prelude::abigen; +use fuels::programs::responses::CallResponse; + +abigen!(Contract( + name = "Proxy", + abi = "contracts/proxy-contract/out/debug/proxy-contract-abi.json" +)); + +pub mod proxy_abi { + use super::*; + use fuels::prelude::{Account, ContractId, Error, TxPolicies}; + + pub async fn set_proxy_target( + proxy: &Proxy, + new_target: ContractId, + ) -> Result, Error> { + let tx_params = TxPolicies::default().with_tip(1); + + proxy + .methods() + .set_proxy_target(new_target) + .with_tx_policies(tx_params) + .call() + .await + } + + pub async fn get_proxy_target( + proxy: &Proxy, + ) -> Result>, Error> { + proxy.methods().proxy_target().call().await + } + + pub async fn set_proxy_owner( + proxy: &Proxy, + new_proxy_owner: State, + ) -> Result, Error> { + let tx_params = TxPolicies::default().with_tip(1); + + proxy + .methods() + .set_proxy_owner(new_proxy_owner) + .with_tx_policies(tx_params) + .call() + .await + } + + pub async fn get_proxy_owner( + proxy: &Proxy, + ) -> Result, Error> { + proxy.methods().proxy_owner().call().await + } +} diff --git a/test-utils/src/interfaces/sorted_troves.rs b/test-utils/src/interfaces/sorted_troves.rs index bde94fa6..b59c932c 100644 --- a/test-utils/src/interfaces/sorted_troves.rs +++ b/test-utils/src/interfaces/sorted_troves.rs @@ -8,6 +8,10 @@ abigen!(Contract( )); pub mod sorted_troves_abi { + use crate::{ + data_structures::ContractInstance, interfaces::trove_manager::TroveManagerContract, + }; + use super::*; use fuels::{ @@ -16,7 +20,7 @@ pub mod sorted_troves_abi { }; pub async fn initialize( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, max_size: u64, protocol_manager: ContractId, borrow_opperations: ContractId, @@ -24,8 +28,10 @@ pub mod sorted_troves_abi { let tx_params = TxPolicies::default().with_tip(1); let res = sorted_troves + .contract .methods() .set_params(max_size, protocol_manager, borrow_opperations) + .with_contract_ids(&[sorted_troves.implementation_id.into()]) .with_tx_policies(tx_params) .call() .await; @@ -34,7 +40,7 @@ pub mod sorted_troves_abi { } pub async fn insert( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, id: Identity, icr: u64, prev_id: Identity, @@ -42,83 +48,151 @@ pub mod sorted_troves_abi { asset: AssetId, ) -> CallResponse<()> { sorted_troves + .contract .methods() .insert(id, icr, prev_id, next_id, asset.into()) + .with_contract_ids(&[sorted_troves.implementation_id.into()]) .call() .await .unwrap() } pub async fn add_asset( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, asset: AssetId, trove_manager: ContractId, ) -> CallResponse<()> { sorted_troves + .contract .methods() .add_asset(asset.into(), trove_manager) + .with_contract_ids(&[sorted_troves.implementation_id.into()]) .call() .await .unwrap() } pub async fn get_first( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, asset: AssetId, ) -> CallResponse { sorted_troves + .contract .methods() .get_first(asset.into()) + .with_contract_ids(&[sorted_troves.implementation_id.into()]) .call() .await .unwrap() } pub async fn get_last( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, asset: AssetId, ) -> CallResponse { sorted_troves + .contract .methods() .get_last(asset.into()) + .with_contract_ids(&[sorted_troves.implementation_id.into()]) .call() .await .unwrap() } pub async fn get_size( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, asset: AssetId, ) -> CallResponse { sorted_troves + .contract .methods() .get_size(asset.into()) + .with_contract_ids(&[sorted_troves.implementation_id.into()]) .call() .await .unwrap() } pub async fn get_next( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, id: Identity, asset: AssetId, ) -> CallResponse { sorted_troves + .contract .methods() .get_next(id, asset.into()) + .with_contract_ids(&[sorted_troves.implementation_id.into()]) .call() .await .unwrap() } pub async fn get_prev( - sorted_troves: &SortedTroves, + sorted_troves: &ContractInstance>, id: Identity, asset: AssetId, ) -> CallResponse { sorted_troves + .contract .methods() .get_prev(id, asset.into()) + .with_contract_ids(&[sorted_troves.implementation_id.into()]) + .call() + .await + .unwrap() + } + + pub async fn get_max_size( + sorted_troves: &ContractInstance>, + ) -> CallResponse { + sorted_troves + .contract + .methods() + .get_max_size() + .with_contract_ids(&[sorted_troves.implementation_id.into()]) + .call() + .await + .unwrap() + } + + pub async fn contains( + sorted_troves: &ContractInstance>, + id: Identity, + asset: AssetId, + ) -> CallResponse { + sorted_troves + .contract + .methods() + .contains(id, asset.into()) + .with_contract_ids(&[ + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + ]) + .call() + .await + .unwrap() + } + + pub async fn find_insert_position( + sorted_troves: &ContractInstance>, + trove_manager: &TroveManagerContract, + icr: u64, + prev_id: Identity, + next_id: Identity, + asset: AssetId, + ) -> CallResponse<(Identity, Identity)> { + sorted_troves + .contract + .methods() + .find_insert_position(icr, prev_id, next_id, asset.into()) + .with_contracts(&[trove_manager]) + .with_contract_ids(&[ + sorted_troves.implementation_id.into(), + sorted_troves.contract.contract_id().into(), + trove_manager.contract_id().into(), + ]) .call() .await .unwrap() diff --git a/test-utils/src/interfaces/stability_pool.rs b/test-utils/src/interfaces/stability_pool.rs index a30ea3c8..7b8af22b 100644 --- a/test-utils/src/interfaces/stability_pool.rs +++ b/test-utils/src/interfaces/stability_pool.rs @@ -16,16 +16,17 @@ abigen!(Contract( pub mod stability_pool_abi { + use crate::data_structures::ContractInstance; + use super::*; use fuels::{ - prelude::{Account, CallParameters, Error, TxPolicies, WalletUnlocked}, + prelude::{Account, CallParameters, Error, TxPolicies}, programs::responses::CallResponse, types::{transaction_builders::VariableOutputPolicy, AssetId, ContractId, Identity}, }; pub async fn initialize( - stability_pool: &StabilityPool, - + stability_pool: &ContractInstance>, usdf_address: ContractId, community_issuance_address: ContractId, protocol_manager_contract: ContractId, @@ -35,6 +36,7 @@ pub mod stability_pool_abi { let tx_params = TxPolicies::default().with_tip(1); stability_pool + .contract .methods() .initialize( usdf_address, @@ -43,13 +45,17 @@ pub mod stability_pool_abi { active_pool, sorted_troves, ) + .with_contract_ids(&[ + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await } pub async fn add_asset( - stability_pool: &StabilityPool, + stability_pool: &ContractInstance>, trove_manager: ContractId, asset_address: AssetId, oracle_address: ContractId, @@ -57,105 +63,152 @@ pub mod stability_pool_abi { let tx_params = TxPolicies::default().with_tip(1); stability_pool + .contract .methods() .add_asset(trove_manager, asset_address.into(), oracle_address) .with_tx_policies(tx_params) + .with_contract_ids(&[ + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + ]) .call() .await } pub async fn provide_to_stability_pool( - stability_pool: &StabilityPool, - community_issuance: &CommunityIssuance, - usdf_token: &USDFToken, + stability_pool: &ContractInstance>, + community_issuance: &ContractInstance>, + usdf_token: &ContractInstance>, mock_token: &Token, amount: u64, ) -> Result, Error> { let tx_params = TxPolicies::default().with_tip(1); - let usdf_asset_id = usdf_token.contract_id().asset_id(&AssetId::zeroed().into()); + let usdf_asset_id = usdf_token + .contract + .contract_id() + .asset_id(&AssetId::zeroed().into()); let call_params: CallParameters = CallParameters::default() .with_amount(amount) .with_asset_id(usdf_asset_id); stability_pool + .contract .methods() .provide_to_stability_pool() .with_tx_policies(tx_params) .call_params(call_params) .unwrap() .with_variable_output_policy(VariableOutputPolicy::Exactly(2)) - .with_contracts(&[usdf_token, mock_token, community_issuance]) + .with_contracts(&[ + &usdf_token.contract, + mock_token, + &community_issuance.contract, + ]) + .with_contract_ids(&[ + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + usdf_token.contract.contract_id().into(), + usdf_token.implementation_id.into(), + mock_token.contract_id().into(), + community_issuance.contract.contract_id().into(), + community_issuance.implementation_id.into(), + ]) .call() .await } pub async fn get_asset( - stability_pool: &StabilityPool, + stability_pool: &ContractInstance>, asset_address: AssetId, ) -> Result, Error> { stability_pool + .contract .methods() .get_asset(asset_address) + .with_contract_ids(&[ + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + ]) .call() .await } pub async fn get_total_usdf_deposits( - stability_pool: &StabilityPool, + stability_pool: &ContractInstance>, ) -> Result, Error> { stability_pool + .contract .methods() .get_total_usdf_deposits() + .with_contract_ids(&[ + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + ]) .call() .await } pub async fn get_depositor_asset_gain( - stability_pool: &StabilityPool, + stability_pool: &ContractInstance>, depositor: Identity, asset_id: AssetId, ) -> Result, Error> { stability_pool + .contract .methods() .get_depositor_asset_gain(depositor, asset_id.into()) + .with_contract_ids(&[ + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + ]) .call() .await } - pub async fn get_compounded_usdf_deposit( - stability_pool: &StabilityPool, + pub async fn get_compounded_usdf_deposit( + stability_pool: &ContractInstance>, depositor: Identity, ) -> Result, Error> { stability_pool + .contract .methods() .get_compounded_usdf_deposit(depositor) + .with_contract_ids(&[ + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + ]) .call() .await } pub async fn get_depositor_fpt_gain( - stability_pool: &StabilityPool, + stability_pool: &ContractInstance>, depositor: Identity, ) -> Result, Error> { stability_pool + .contract .methods() .get_depositor_fpt_gain(depositor) + .with_contract_ids(&[ + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + ]) .call() .await } pub async fn withdraw_from_stability_pool( - stability_pool: &StabilityPool, - community_issuance: &CommunityIssuance, - usdf_token: &USDFToken, + stability_pool: &ContractInstance>, + community_issuance: &ContractInstance>, + usdf_token: &ContractInstance>, mock_token: &Token, - sorted_troves: &SortedTroves, - oracle: &Oracle, + sorted_troves: &ContractInstance>, + oracle: &ContractInstance>, pyth_oracle: &PythCore, - redstone_oracle: &RedstoneCore, - trove_manager: &TroveManagerContract, + _redstone_oracle: &RedstoneCore, + trove_manager: &ContractInstance>, amount: u64, ) -> Result, Error> { let tx_params = TxPolicies::default() @@ -163,19 +216,37 @@ pub mod stability_pool_abi { .with_script_gas_limit(2000000); stability_pool + .contract .methods() .withdraw_from_stability_pool(amount) .with_tx_policies(tx_params) .with_variable_output_policy(VariableOutputPolicy::Exactly(2)) .with_contracts(&[ - usdf_token, + &usdf_token.contract, mock_token, - community_issuance, - sorted_troves, - oracle, + &community_issuance.contract, + &sorted_troves.contract, + &oracle.contract, pyth_oracle, - redstone_oracle, - trove_manager, + // redstone_oracle, + &trove_manager.contract, + ]) + .with_contract_ids(&[ + sorted_troves.contract.contract_id().into(), + sorted_troves.implementation_id.into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + pyth_oracle.contract_id().into(), + // redstone_oracle.contract_id().into(), + usdf_token.contract.contract_id().into(), + usdf_token.implementation_id.into(), + mock_token.contract_id().into(), + community_issuance.contract.contract_id().into(), + community_issuance.implementation_id.into(), + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), ]) .call() .await @@ -184,16 +255,16 @@ pub mod stability_pool_abi { pub mod stability_pool_utils { use fuels::{ - prelude::{Account, WalletUnlocked}, + prelude::Account, types::{AssetId, Identity}, }; - use crate::setup::common::assert_within_threshold; + use crate::{data_structures::ContractInstance, setup::common::assert_within_threshold}; use super::*; pub async fn assert_pool_asset( - stability_pool: &StabilityPool, + stability_pool: &ContractInstance>, expected_asset_amount: u64, asset_address: AssetId, ) { @@ -206,7 +277,7 @@ pub mod stability_pool_utils { } pub async fn assert_total_usdf_deposits( - stability_pool: &StabilityPool, + stability_pool: &ContractInstance>, expected_usdf_amount: u64, ) { let total_usdf_deposits = @@ -219,7 +290,7 @@ pub mod stability_pool_utils { } pub async fn assert_depositor_asset_gain( - stability_pool: &StabilityPool, + stability_pool: &ContractInstance>, depositor: Identity, expected_asset_gain: u64, asset_address: AssetId, @@ -243,8 +314,8 @@ pub mod stability_pool_utils { ); } - pub async fn assert_compounded_usdf_deposit( - stability_pool: &StabilityPool, + pub async fn assert_compounded_usdf_deposit( + stability_pool: &ContractInstance>, depositor: Identity, expected_compounded_usdf_deposit: u64, ) { diff --git a/test-utils/src/interfaces/trove_manager.rs b/test-utils/src/interfaces/trove_manager.rs index c096921c..728359db 100644 --- a/test-utils/src/interfaces/trove_manager.rs +++ b/test-utils/src/interfaces/trove_manager.rs @@ -23,32 +23,39 @@ pub mod trove_manager_abi { types::{transaction_builders::VariableOutputPolicy, AssetId, ContractId, Identity}, }; + use crate::data_structures::ContractInstance; + use super::*; pub async fn get_nominal_icr( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, ) -> CallResponse { trove_manager + .contract .methods() .get_nominal_icr(id) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn batch_liquidate_troves( - trove_manager: &TroveManagerContract, - community_issuance: &CommunityIssuance, - stability_pool: &StabilityPool, - oracle: &Oracle, + trove_manager: &ContractInstance>, + community_issuance: &ContractInstance>, + stability_pool: &ContractInstance>, + oracle: &ContractInstance>, pyth: &PythCore, redstone: &RedstoneCore, - sorted_troves: &SortedTroves, - active_pool: &ActivePool, - default_pool: &DefaultPool, - coll_surplus_pool: &CollSurplusPool, - usdf: &USDFToken, + sorted_troves: &ContractInstance>, + active_pool: &ContractInstance>, + default_pool: &ContractInstance>, + coll_surplus_pool: &ContractInstance>, + usdf: &ContractInstance>, ids: Vec, upper_hint: Identity, lower_hint: Identity, @@ -56,20 +63,43 @@ pub mod trove_manager_abi { let tx_params = TxPolicies::default().with_tip(1); trove_manager + .contract .methods() .batch_liquidate_troves(ids, upper_hint, lower_hint) .with_tx_policies(tx_params) .with_contracts(&[ - stability_pool, - oracle, + &stability_pool.contract, + &oracle.contract, pyth, redstone, - sorted_troves, - active_pool, - default_pool, - coll_surplus_pool, - usdf, - community_issuance, + &sorted_troves.contract, + &active_pool.contract, + &default_pool.contract, + &coll_surplus_pool.contract, + &usdf.contract, + &community_issuance.contract, + ]) + .with_contract_ids(&[ + sorted_troves.contract.contract_id().into(), + sorted_troves.implementation_id.into(), + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + pyth.contract_id().into(), + redstone.contract_id().into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + usdf.contract.contract_id().into(), + usdf.implementation_id.into(), + community_issuance.contract.contract_id().into(), + community_issuance.implementation_id.into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(3)) .call() @@ -77,17 +107,17 @@ pub mod trove_manager_abi { } pub async fn liquidate( - trove_manager: &TroveManagerContract, - community_issuance: &CommunityIssuance, - stability_pool: &StabilityPool, - oracle: &Oracle, + trove_manager: &ContractInstance>, + community_issuance: &ContractInstance>, + stability_pool: &ContractInstance>, + oracle: &ContractInstance>, pyth: &PythCore, redstone: &RedstoneCore, - sorted_troves: &SortedTroves, - active_pool: &ActivePool, - default_pool: &DefaultPool, - coll_surplus_pool: &CollSurplusPool, - usdf: &USDFToken, + sorted_troves: &ContractInstance>, + active_pool: &ContractInstance>, + default_pool: &ContractInstance>, + coll_surplus_pool: &ContractInstance>, + usdf: &ContractInstance>, id: Identity, upper_hint: Identity, lower_hint: Identity, @@ -95,20 +125,43 @@ pub mod trove_manager_abi { let tx_params = TxPolicies::default().with_tip(1); trove_manager + .contract .methods() .liquidate(id, upper_hint, lower_hint) .with_tx_policies(tx_params) .with_contracts(&[ - stability_pool, - oracle, + &stability_pool.contract, + &oracle.contract, pyth, redstone, - sorted_troves, - active_pool, - default_pool, - coll_surplus_pool, - usdf, - community_issuance, + &sorted_troves.contract, + &active_pool.contract, + &default_pool.contract, + &coll_surplus_pool.contract, + &usdf.contract, + &community_issuance.contract, + ]) + .with_contract_ids(&[ + sorted_troves.contract.contract_id().into(), + sorted_troves.implementation_id.into(), + stability_pool.contract.contract_id().into(), + stability_pool.implementation_id.into(), + oracle.contract.contract_id().into(), + oracle.implementation_id.into(), + pyth.contract_id().into(), + redstone.contract_id().into(), + active_pool.contract.contract_id().into(), + active_pool.implementation_id.into(), + default_pool.contract.contract_id().into(), + default_pool.implementation_id.into(), + coll_surplus_pool.contract.contract_id().into(), + coll_surplus_pool.implementation_id.into(), + usdf.contract.contract_id().into(), + usdf.implementation_id.into(), + community_issuance.contract.contract_id().into(), + community_issuance.implementation_id.into(), + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(3)) .call() @@ -116,15 +169,20 @@ pub mod trove_manager_abi { } pub async fn increase_trove_coll( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, amount: u64, ) -> CallResponse { let tx_params = TxPolicies::default().with_tip(1); trove_manager + .contract .methods() .increase_trove_coll(id, amount) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -132,15 +190,20 @@ pub mod trove_manager_abi { } pub async fn increase_trove_debt( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, amount: u64, ) -> CallResponse { let tx_params = TxPolicies::default().with_tip(1); trove_manager + .contract .methods() .increase_trove_debt(id, amount) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -148,15 +211,20 @@ pub mod trove_manager_abi { } pub async fn set_trove_status( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, status: Status, ) -> CallResponse<()> { let tx_params = TxPolicies::default().with_tip(1); trove_manager + .contract .methods() .set_trove_status(id, status) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -164,7 +232,7 @@ pub mod trove_manager_abi { } pub async fn initialize( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, borrow_operations: ContractId, sorted_troves_id: ContractId, oracle_id: ContractId, @@ -179,6 +247,7 @@ pub mod trove_manager_abi { let tx_params = TxPolicies::default().with_tip(1); let res = trove_manager + .contract .methods() .initialize( borrow_operations, @@ -192,6 +261,10 @@ pub mod trove_manager_abi { asset.into(), protocol_manager, ) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await; @@ -200,14 +273,19 @@ pub mod trove_manager_abi { } pub async fn get_trove_coll( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, ) -> CallResponse { let tx_params = TxPolicies::default().with_tip(1); trove_manager + .contract .methods() .get_trove_coll(id) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -215,14 +293,19 @@ pub mod trove_manager_abi { } pub async fn get_entire_debt_and_coll( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, ) -> CallResponse<(u64, u64, u64, u64)> { let tx_params = TxPolicies::default().with_tip(1); trove_manager + .contract .methods() .get_entire_debt_and_coll(id) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .with_tx_policies(tx_params) .call() .await @@ -230,43 +313,67 @@ pub mod trove_manager_abi { } pub async fn get_trove_debt( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, ) -> CallResponse { trove_manager + .contract .methods() .get_trove_debt(id) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn get_trove_status( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, ) -> Result, Error> { - trove_manager.methods().get_trove_status(id).call().await + trove_manager + .contract + .methods() + .get_trove_status(id) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) + .call() + .await } pub async fn get_pending_asset_reward( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, ) -> CallResponse { trove_manager + .contract .methods() .get_pending_asset_rewards(id) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .call() .await .unwrap() } pub async fn get_pending_usdf_reward( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, ) -> CallResponse { trove_manager + .contract .methods() .get_pending_usdf_rewards(id) + .with_contract_ids(&[ + trove_manager.contract.contract_id().into(), + trove_manager.implementation_id.into(), + ]) .call() .await .unwrap() @@ -284,14 +391,15 @@ pub mod trove_manager_utils { }; use crate::{ - interfaces::sorted_troves::sorted_troves_abi, setup::common::assert_within_threshold, + data_structures::ContractInstance, interfaces::sorted_troves::sorted_troves_abi, + setup::common::assert_within_threshold, }; use super::*; pub async fn set_coll_and_debt_insert( - trove_manager: &TroveManagerContract, - sorted_troves: &SortedTroves, + trove_manager: &ContractInstance>, + sorted_troves: &ContractInstance>, id: Identity, coll: u64, debt: u64, @@ -306,7 +414,7 @@ pub mod trove_manager_utils { } pub async fn assert_trove_coll( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, expected_coll: u64, ) { @@ -318,7 +426,7 @@ pub mod trove_manager_utils { } pub async fn assert_trove_debt( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, expected_debt: u64, ) { @@ -330,7 +438,7 @@ pub mod trove_manager_utils { } pub async fn assert_trove_status( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, expected_status: Status, ) { @@ -343,7 +451,7 @@ pub mod trove_manager_utils { } pub async fn assert_pending_asset_rewards( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, expected_rewards: u64, ) { @@ -362,7 +470,7 @@ pub mod trove_manager_utils { } pub async fn assert_pending_usdf_rewards( - trove_manager: &TroveManagerContract, + trove_manager: &ContractInstance>, id: Identity, expected_rewards: u64, ) { diff --git a/test-utils/src/interfaces/usdf_token.rs b/test-utils/src/interfaces/usdf_token.rs index c117b126..a68dc36b 100644 --- a/test-utils/src/interfaces/usdf_token.rs +++ b/test-utils/src/interfaces/usdf_token.rs @@ -10,6 +10,8 @@ abigen!(Contract( )); pub mod usdf_token_abi { + use crate::data_structures::ContractInstance; + use super::*; use fuels::{ prelude::{Account, CallParameters, Error, TxPolicies}, @@ -17,7 +19,7 @@ pub mod usdf_token_abi { }; pub async fn initialize( - instance: &USDFToken, + instance: &ContractInstance>, protocol_manager: ContractId, stability_pool: Identity, borrow_operations: Identity, @@ -25,38 +27,49 @@ pub mod usdf_token_abi { let tx_params = TxPolicies::default().with_tip(1); instance + .contract .methods() .initialize( protocol_manager, stability_pool.clone(), borrow_operations.clone(), ) + .with_contract_ids(&[ + instance.implementation_id.into(), + instance.contract.contract_id().into(), + ]) .with_tx_policies(tx_params) .call() .await } pub async fn mint( - instance: &USDFToken, + instance: &ContractInstance>, amount: u64, address: Identity, ) -> Result, Error> { instance + .contract .methods() .mint(address, None, amount) + .with_contract_ids(&[ + instance.implementation_id.into(), + instance.contract.contract_id().into(), + ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) .call() .await } pub async fn burn( - usdf_token: &USDFToken, + instance: &ContractInstance>, amount: u64, ) -> Result, Error> { let tx_params = TxPolicies::default() .with_tip(1) .with_script_gas_limit(200000); - let usdf_asset_id = usdf_token + let usdf_asset_id = instance + .contract .contract_id() .asset_id(&AssetId::zeroed().into()) .into(); @@ -65,9 +78,14 @@ pub mod usdf_token_abi { .with_amount(amount) .with_asset_id(usdf_asset_id); - let call_handler = usdf_token + let call_handler = instance + .contract .methods() .burn(Bits256::zeroed(), amount) + .with_contract_ids(&[ + instance.implementation_id.into(), + instance.contract.contract_id().into(), + ]) .with_variable_output_policy(VariableOutputPolicy::Exactly(1)); call_handler @@ -78,29 +96,42 @@ pub mod usdf_token_abi { .await } - pub async fn total_supply(instance: &USDFToken) -> CallResponse> { + pub async fn total_supply( + instance: &ContractInstance>, + ) -> CallResponse> { let usdf_asset_id = instance + .contract .contract_id() .asset_id(&AssetId::zeroed().into()) .into(); instance + .contract .methods() .total_supply(usdf_asset_id) + .with_contract_ids(&[ + instance.implementation_id.into(), + instance.contract.contract_id().into(), + ]) .call() .await .unwrap() } pub async fn add_trove_manager( - instance: &USDFToken, + instance: &ContractInstance>, trove_manager: ContractId, ) -> Result, Error> { let tx_params = TxPolicies::default().with_tip(1); instance + .contract .methods() .add_trove_manager(trove_manager) + .with_contract_ids(&[ + instance.implementation_id.into(), + instance.contract.contract_id().into(), + ]) .with_tx_policies(tx_params) .call() .await diff --git a/test-utils/src/interfaces/vesting.rs b/test-utils/src/interfaces/vesting.rs index e1dc674e..75ff97b6 100644 --- a/test-utils/src/interfaces/vesting.rs +++ b/test-utils/src/interfaces/vesting.rs @@ -1,5 +1,3 @@ -use std::{fs::File, io::BufReader, str::FromStr}; - use fuels::prelude::{Address, Bech32Address}; use fuels::types::errors::Error; use fuels::types::AssetId; @@ -9,7 +7,9 @@ use fuels::{ types::Identity, }; use serde::Deserialize; +use std::{fs::File, io::BufReader, str::FromStr}; +use crate::data_structures::PRECISION; use crate::setup::common::get_absolute_path_from_relative; abigen!(Contract( @@ -17,30 +17,81 @@ abigen!(Contract( abi = "contracts/vesting-contract/out/debug/vesting-contract-abi.json" )); -pub async fn instantiate_vesting_contract( - contract: &VestingContract, - asset_contract: &AssetId, - schedules: Vec, -) -> Result, Error> { - contract - .methods() - .constructor(asset_contract.clone().into(), schedules, true) - .call() - .await -} +pub const TOTAL_AMOUNT_VESTED: u64 = 100_000_000 * 68 / 100 * PRECISION; -pub async fn set_timestamp( - contract: &VestingContract, - timestamp: u64, -) -> CallResponse<()> { - contract - .methods() - .set_current_time(timestamp) - .call() - .await - .unwrap() -} +pub mod vesting_abi { + use fuels::types::transaction_builders::VariableOutputPolicy; + + use crate::data_structures::ContractInstance; + + use super::*; + pub async fn instantiate_vesting_contract( + contract: &ContractInstance>, + asset_contract: &AssetId, + schedules: Vec, + debug: bool, + ) -> Result, Error> { + contract + .contract + .methods() + .constructor(asset_contract.clone().into(), schedules, debug) + .with_contract_ids(&[contract.implementation_id.into()]) + .call() + .await + } + pub async fn set_timestamp( + contract: &ContractInstance>, + timestamp: u64, + ) -> Result, Error> { + contract + .contract + .methods() + .set_current_time(timestamp) + .with_contract_ids(&[contract.implementation_id.into()]) + .call() + .await + } + pub async fn get_vesting_schedule_call( + contract: &ContractInstance>, + recipient: Identity, + ) -> Result, Error> { + contract + .contract + .methods() + .get_vesting_schedule(recipient) + .with_contract_ids(&[contract.implementation_id.into()]) + .call() + .await + } + + pub async fn get_redeemable_amount( + contract: &ContractInstance>, + timestamp: u64, + recipient: Identity, + ) -> Result, Error> { + contract + .contract + .methods() + .get_redeemable_amount(timestamp, recipient) + .with_contract_ids(&[contract.implementation_id.into()]) + .call() + .await + } + + pub async fn claim_vested_tokens( + contract: &ContractInstance>, + ) -> Result, Error> { + contract + .contract + .methods() + .claim_vested_tokens() + .with_contract_ids(&[contract.implementation_id.into()]) + .with_variable_output_policy(VariableOutputPolicy::Exactly(1)) + .call() + .await + } +} pub fn load_vesting_schedules_from_json_file(path: &str) -> Vec { let absolute_path = get_absolute_path_from_relative(path); diff --git a/test-utils/src/lib.rs b/test-utils/src/lib.rs index 05e82516..ef17a125 100644 --- a/test-utils/src/lib.rs +++ b/test-utils/src/lib.rs @@ -2,5 +2,4 @@ pub mod data_structures; pub mod interfaces; pub mod paths; pub mod setup; -pub mod testing_query_manual; pub mod utils; diff --git a/test-utils/src/paths.rs b/test-utils/src/paths.rs index f49a5915..37d34d0f 100644 --- a/test-utils/src/paths.rs +++ b/test-utils/src/paths.rs @@ -66,6 +66,8 @@ pub const FPT_TOKEN_CONTRACT_STORAGE_PATH: &str = pub const FPT_STAKING_CONTRACT_BINARY_PATH: &str = "contracts/fpt-staking-contract/out/debug/fpt-staking-contract.bin"; +pub const FPT_STAKING_CONTRACT_STORAGE_PATH: &str = + "contracts/fpt-staking-contract/out/debug/fpt-staking-contract-storage_slots.json"; pub const PROTCOL_MANAGER_CONTRACT_BINARY_PATH: &str = "contracts/protocol-manager-contract/out/debug/protocol-manager-contract.bin"; @@ -86,3 +88,8 @@ pub const MULTI_TROVE_GETTER_CONTRACT_BINARY_PATH: &str = "contracts/multi-trove-getter-contract/out/debug/multi-trove-getter-contract.bin"; pub const MULTI_TROVE_GETTER_CONTRACT_STORAGE_PATH: &str = "contracts/multi-trove-getter-contract/out/debug/multi-trove-getter-contract-storage_slots.json"; + +pub const PROXY_CONTRACT_BINARY_PATH: &str = + "contracts/proxy-contract/out/debug/proxy-contract.bin"; +pub const PROXY_CONTRACT_STORAGE_PATH: &str = + "contracts/proxy-contract/out/debug/proxy-contract-storage_slots.json"; diff --git a/test-utils/src/setup.rs b/test-utils/src/setup.rs index 7fa4aa28..2227ccd6 100644 --- a/test-utils/src/setup.rs +++ b/test-utils/src/setup.rs @@ -24,7 +24,10 @@ use fuels::prelude::{Contract, TxPolicies, WalletUnlocked}; pub mod common { use super::*; use crate::{ - data_structures::{AssetContracts, ExistingAssetContracts, ProtocolContracts, PRECISION}, + data_structures::{ + AssetContracts, AssetContractsOptionalRedstone, ContractInstance, + ExistingAssetContracts, ProtocolContracts, RedstoneConfig, PRECISION, + }, interfaces::{ active_pool::active_pool_abi, borrow_operations::borrow_operations_abi, @@ -35,6 +38,7 @@ pub mod common { fpt_token::fpt_token_abi, oracle::oracle_abi, protocol_manager::protocol_manager_abi, + proxy::Proxy, pyth_oracle::{pyth_oracle_abi, pyth_price_feed}, redstone_oracle::{redstone_oracle_abi, redstone_price_feed_with_id}, sorted_troves::sorted_troves_abi, @@ -49,12 +53,13 @@ pub mod common { // accounts::rand::{self, Rng}, prelude::*, programs::responses::CallResponse, - types::{Bits256, ContractId, Identity, U256}, + tx::StorageSlot, + types::{Bits256, Bytes32, ContractId, Identity, U256}, }; use pbr::ProgressBar; // use pbr::ProgressBar; use rand::Rng; - use std::env; + use std::{env, str::FromStr}; pub async fn setup_protocol( num_wallets: u64, @@ -79,7 +84,7 @@ pub mod common { .unwrap(); let wallet = wallets.pop().unwrap(); - let mut contracts = deploy_core_contracts(&wallet, use_test_fpt).await; + let mut contracts = deploy_core_contracts(&wallet, use_test_fpt, false).await; initialize_core_contracts(&mut contracts, &wallet, use_test_fpt, true, false).await; // Add the first asset (Fuel) @@ -110,28 +115,73 @@ pub mod common { pub async fn deploy_core_contracts( wallet: &WalletUnlocked, use_test_fpt: bool, + verbose: bool, ) -> ProtocolContracts { println!("Deploying core contracts..."); + let mut pb = ProgressBar::new(13); let borrow_operations = deploy_borrow_operations(wallet).await; + + if verbose { + pb.inc(); + } let usdf = deploy_usdf_token(wallet).await; + if verbose { + pb.inc(); + } let stability_pool = deploy_stability_pool(wallet).await; + if verbose { + pb.inc(); + } let fpt_staking = deploy_fpt_staking(wallet).await; + if verbose { + pb.inc(); + } let community_issuance = deploy_community_issuance(wallet).await; + if verbose { + pb.inc(); + } let fpt_token = if use_test_fpt { deploy_test_fpt_token(wallet).await } else { deploy_fpt_token(wallet).await }; + if verbose { + pb.inc(); + } let protocol_manager = deploy_protocol_manager(wallet).await; + if verbose { + pb.inc(); + } let coll_surplus_pool = deploy_coll_surplus_pool(wallet).await; + if verbose { + pb.inc(); + } let default_pool = deploy_default_pool(wallet).await; + if verbose { + pb.inc(); + } let active_pool = deploy_active_pool(wallet).await; + if verbose { + pb.inc(); + } let sorted_troves = deploy_sorted_troves(wallet).await; let vesting_contract = deploy_vesting_contract(wallet, 68_000_000 * PRECISION).await; - let fpt_asset_id = fpt_token.contract_id().asset_id(&AssetId::zeroed().into()); - let usdf_asset_id = usdf.contract_id().asset_id(&AssetId::zeroed().into()); + let fpt_asset_id = fpt_token + .contract + .contract_id() + .asset_id(&AssetId::zeroed().into()); + if verbose { + pb.inc(); + } + let usdf_asset_id = usdf + .contract + .contract_id() + .asset_id(&AssetId::zeroed().into()); + if verbose { + pb.inc(); + } ProtocolContracts { borrow_operations, @@ -160,11 +210,12 @@ pub mod common { verbose: bool, ) { println!("Initializing core contracts..."); + // contracts.print_contract_ids(); let mut pb = ProgressBar::new(11); if !use_test_fpt { fpt_token_abi::initialize( &contracts.fpt_token, - &contracts.vesting_contract, + &contracts.vesting_contract.contract, &contracts.community_issuance, ) .await; @@ -175,7 +226,7 @@ pub mod common { community_issuance_abi::initialize( &contracts.community_issuance, - contracts.stability_pool.contract_id().into(), + contracts.stability_pool.contract.contract_id().into(), contracts.fpt_asset_id, &Identity::Address(wallet.address().into()), debug, @@ -188,9 +239,9 @@ pub mod common { usdf_token_abi::initialize( &contracts.usdf, - contracts.protocol_manager.contract_id().into(), - Identity::ContractId(contracts.stability_pool.contract_id().into()), - Identity::ContractId(contracts.borrow_operations.contract_id().into()), + contracts.protocol_manager.contract.contract_id().into(), + Identity::ContractId(contracts.stability_pool.contract.contract_id().into()), + Identity::ContractId(contracts.borrow_operations.contract.contract_id().into()), ) .await .unwrap(); @@ -200,12 +251,12 @@ pub mod common { borrow_operations_abi::initialize( &contracts.borrow_operations, - contracts.usdf.contract_id().into(), - contracts.fpt_staking.contract_id().into(), - contracts.protocol_manager.contract_id().into(), - contracts.coll_surplus_pool.contract_id().into(), - contracts.active_pool.contract_id().into(), - contracts.sorted_troves.contract_id().into(), + contracts.usdf.contract.contract_id().into(), + contracts.fpt_staking.contract.contract_id().into(), + contracts.protocol_manager.contract.contract_id().into(), + contracts.coll_surplus_pool.contract.contract_id().into(), + contracts.active_pool.contract.contract_id().into(), + contracts.sorted_troves.contract.contract_id().into(), ) .await; if verbose { @@ -214,11 +265,11 @@ pub mod common { stability_pool_abi::initialize( &contracts.stability_pool, - contracts.usdf.contract_id().into(), - contracts.community_issuance.contract_id().into(), - contracts.protocol_manager.contract_id().into(), - contracts.active_pool.contract_id().into(), - contracts.sorted_troves.contract_id().into(), + contracts.usdf.contract.contract_id().into(), + contracts.community_issuance.contract.contract_id().into(), + contracts.protocol_manager.contract.contract_id().into(), + contracts.active_pool.contract.contract_id().into(), + contracts.sorted_troves.contract.contract_id().into(), ) .await .unwrap(); @@ -228,14 +279,10 @@ pub mod common { fpt_staking_abi::initialize( &contracts.fpt_staking, - contracts.protocol_manager.contract_id().into(), - contracts.borrow_operations.contract_id().into(), + contracts.protocol_manager.contract.contract_id().into(), + contracts.borrow_operations.contract.contract_id().into(), contracts.fpt_asset_id, - contracts - .usdf - .contract_id() - .asset_id(&AssetId::zeroed().into()) - .into(), + contracts.usdf_asset_id, ) .await; if verbose { @@ -244,14 +291,14 @@ pub mod common { protocol_manager_abi::initialize( &contracts.protocol_manager, - contracts.borrow_operations.contract_id().into(), - contracts.stability_pool.contract_id().into(), - contracts.fpt_staking.contract_id().into(), - contracts.usdf.contract_id().into(), - contracts.coll_surplus_pool.contract_id().into(), - contracts.default_pool.contract_id().into(), - contracts.active_pool.contract_id().into(), - contracts.sorted_troves.contract_id().into(), + contracts.borrow_operations.contract.contract_id().into(), + contracts.stability_pool.contract.contract_id().into(), + contracts.fpt_staking.contract.contract_id().into(), + contracts.usdf.contract.contract_id().into(), + contracts.coll_surplus_pool.contract.contract_id().into(), + contracts.default_pool.contract.contract_id().into(), + contracts.active_pool.contract.contract_id().into(), + contracts.sorted_troves.contract.contract_id().into(), Identity::Address(wallet.address().into()), ) .await; @@ -261,8 +308,8 @@ pub mod common { coll_surplus_pool_abi::initialize( &contracts.coll_surplus_pool, - contracts.borrow_operations.contract_id().into(), - Identity::ContractId(contracts.protocol_manager.contract_id().into()), + contracts.borrow_operations.contract.contract_id().into(), + Identity::ContractId(contracts.protocol_manager.contract.contract_id().into()), ) .await .unwrap(); @@ -272,8 +319,8 @@ pub mod common { default_pool_abi::initialize( &contracts.default_pool, - Identity::ContractId(contracts.protocol_manager.contract_id().into()), - contracts.active_pool.contract_id().into(), + Identity::ContractId(contracts.protocol_manager.contract.contract_id().into()), + contracts.active_pool.contract.contract_id().into(), ) .await .unwrap(); @@ -283,10 +330,10 @@ pub mod common { active_pool_abi::initialize( &contracts.active_pool, - Identity::ContractId(contracts.borrow_operations.contract_id().into()), - Identity::ContractId(contracts.stability_pool.contract_id().into()), - contracts.default_pool.contract_id().into(), - Identity::ContractId(contracts.protocol_manager.contract_id().into()), + Identity::ContractId(contracts.borrow_operations.contract.contract_id().into()), + Identity::ContractId(contracts.stability_pool.contract.contract_id().into()), + contracts.default_pool.contract.contract_id().into(), + Identity::ContractId(contracts.protocol_manager.contract.contract_id().into()), ) .await .unwrap(); @@ -297,8 +344,8 @@ pub mod common { sorted_troves_abi::initialize( &contracts.sorted_troves, 100_000_000, - contracts.protocol_manager.contract_id().into(), - contracts.borrow_operations.contract_id().into(), + contracts.protocol_manager.contract.contract_id().into(), + contracts.borrow_operations.contract.contract_id().into(), ) .await .unwrap(); @@ -307,7 +354,9 @@ pub mod common { } } - async fn deploy_test_fpt_token(wallet: &WalletUnlocked) -> FPTToken { + async fn deploy_test_fpt_token( + wallet: &WalletUnlocked, + ) -> ContractInstance> { let mock_fpt_token = deploy_token(wallet).await; token_abi::initialize( @@ -320,7 +369,10 @@ pub mod common { .await .unwrap(); - FPTToken::new(mock_fpt_token.contract_id().clone(), wallet.clone()) + ContractInstance::new( + FPTToken::new(mock_fpt_token.contract_id().clone(), wallet.clone()), + mock_fpt_token.contract_id().into(), + ) } pub async fn deploy_token(wallet: &WalletUnlocked) -> Token { @@ -354,7 +406,9 @@ pub mod common { } } - pub async fn deploy_fpt_token(wallet: &WalletUnlocked) -> FPTToken { + pub async fn deploy_fpt_token( + wallet: &WalletUnlocked, + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -372,29 +426,25 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => return FPTToken::new(id, wallet.clone()), - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(FPT_TOKEN_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_configurables(configurables.clone()) - .with_salt(salt), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(FPT_TOKEN_CONTRACT_STORAGE_PATH), + ) + .await; - return FPTToken::new(id, wallet.clone()); - } - } + ContractInstance::new( + FPTToken::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } - pub async fn deploy_sorted_troves(wallet: &WalletUnlocked) -> SortedTroves { + pub async fn deploy_sorted_troves( + wallet: &WalletUnlocked, + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -412,31 +462,25 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => return SortedTroves::new(id, wallet.clone()), - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(SORTED_TROVES_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_configurables(configurables) - .with_salt(salt), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(SORTED_TROVES_CONTRACT_STORAGE_PATH), + ) + .await; - return SortedTroves::new(id, wallet.clone()); - } - } + ContractInstance::new( + SortedTroves::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } pub async fn deploy_trove_manager_contract( wallet: &WalletUnlocked, - ) -> TroveManagerContract { + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -454,32 +498,26 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => return TroveManagerContract::new(id, wallet.clone()), - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(TROVE_MANAGER_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_configurables(configurables) - .with_salt(salt), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(TROVE_MANAGER_CONTRACT_STORAGE_PATH), + ) + .await; - return TroveManagerContract::new(id, wallet.clone()); - } - } + ContractInstance::new( + TroveManagerContract::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } pub async fn deploy_vesting_contract( wallet: &WalletUnlocked, total_amount: u64, - ) -> VestingContract { + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -499,25 +537,20 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => return VestingContract::new(id, wallet.clone()), - Err(_) => { - let id = Contract::load_from( - &get_absolute_path_from_relative(VESTING_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_configurables(configurables) - .with_salt(salt), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(VESTING_CONTRACT_STORAGE_PATH), + ) + .await; - return VestingContract::new(id, wallet.clone()); - } - } + ContractInstance::new( + VestingContract::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } pub async fn deploy_mock_pyth_oracle(wallet: &WalletUnlocked) -> PythCore { @@ -593,7 +626,7 @@ pub mod common { fuel_vm_decimals: u32, debug: bool, initializer: Identity, - ) -> Oracle { + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -618,32 +651,22 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return Oracle::new(id, wallet.clone()); - } - Err(_) => { - let id = Contract::load_from( - &get_absolute_path_from_relative(ORACLE_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_salt(salt) - .with_configurables(configurables), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(ORACLE_CONTRACT_STORAGE_PATH), + ) + .await; - return Oracle::new(id, wallet.clone()); - } - } + ContractInstance::new(Oracle::new(proxy.contract_id(), wallet.clone()), id.into()) } pub async fn deploy_protocol_manager( wallet: &WalletUnlocked, - ) -> ProtocolManager { + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -664,12 +687,22 @@ pub mod common { .await .unwrap(); - ProtocolManager::new(id, wallet.clone()) + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(PROTCOL_MANAGER_CONTRACT_STORAGE_PATH), + ) + .await; + + ContractInstance::new( + ProtocolManager::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } pub async fn deploy_borrow_operations( wallet: &WalletUnlocked, - ) -> BorrowOperations { + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -687,28 +720,20 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return BorrowOperations::new(id, wallet.clone()); - } - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(BORROW_OPERATIONS_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_configurables(configurables) - .with_salt(salt), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(BORROW_OPERATIONS_CONTRACT_STORAGE_PATH), + ) + .await; - return BorrowOperations::new(id, wallet.clone()); - } - } + ContractInstance::new( + BorrowOperations::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } pub fn get_absolute_path_from_relative(relative_path: &str) -> String { @@ -729,43 +754,23 @@ pub mod common { pub async fn deploy_asset_contracts( wallet: &WalletUnlocked, - existing_contracts: &Option, - ) -> AssetContracts { + existing_contracts: &ExistingAssetContracts, + debug: bool, + deploy_redstone: bool, + ) -> AssetContractsOptionalRedstone { println!("Deploying asset contracts..."); let mut pb = ProgressBar::new(6); - let trove_manager = deploy_trove_manager_contract(&wallet).await; pb.inc(); - match existing_contracts { - Some(contracts) => { - pb.finish(); - - let oracle = deploy_oracle( - &wallet, - contracts.pyth_oracle, - contracts.pyth_price_id, - contracts.fuel_vm_decimals, - false, - Identity::Address(wallet.address().into()), + let (asset, asset_id, fuel_vm_decimals) = match &existing_contracts.asset { + Some(asset_contract) => { + pb.inc(); + ( + asset_contract.asset, + asset_contract.asset_id, + asset_contract.fuel_vm_decimals, ) - .await; - - return AssetContracts { - oracle, - mock_pyth_oracle: PythCore::new(contracts.pyth_oracle, wallet.clone()), - mock_redstone_oracle: RedstoneCore::new( - contracts.redstone_oracle, - wallet.clone(), - ), - trove_manager, - asset: Token::new(contracts.asset, wallet.clone()), - asset_id: contracts.asset_id, - pyth_price_id: contracts.pyth_price_id, - redstone_price_id: contracts.redstone_price_id, - redstone_precision: contracts.redstone_precision, - fuel_vm_decimals: contracts.fuel_vm_decimals, - }; } None => { let asset = deploy_token(&wallet).await; @@ -774,7 +779,6 @@ pub mod common { .contract_id() .asset_id(&AssetId::zeroed().into()) .into(); - token_abi::mint_to_id( &asset, 5000 * PRECISION, @@ -782,27 +786,7 @@ pub mod common { ) .await; - let pyth_price_id = Bits256::from(asset_id); - let redstone_price_id = U256::from(rand::thread_rng().gen_range(1..1_000_000)); - - let pyth = deploy_mock_pyth_oracle(&wallet).await; - let redstone = deploy_mock_redstone_oracle(&wallet).await; - let oracle = deploy_oracle( - &wallet, - pyth.contract_id().into(), - pyth_price_id, - 9, - true, - Identity::Address(wallet.address().into()), - ) - .await; - pb.inc(); - println!("Deploying asset contracts... Done"); - println!("Oracle: {}", oracle.contract_id()); - println!("Mock Pyth Oracle: {}", pyth.contract_id()); - println!("Mock Redstone Oracle: {}", redstone.contract_id()); - println!("Trove Manager: {}", trove_manager.contract_id()); println!("Asset: {}", asset.contract_id()); let _ = token_abi::initialize( @@ -812,7 +796,24 @@ pub mod common { "MOCK".to_string(), "MOCK".to_string(), ) - .await; + .await + .unwrap(); + (asset.contract_id().into(), asset_id, 9) // Default fuel_vm_decimals to 9 + } + }; + + // Deploy or use existing Pyth oracle + let (mock_pyth_oracle, pyth_price_id) = match &existing_contracts.pyth_oracle { + Some(pyth_config) => { + pb.inc(); + ( + PythCore::new(pyth_config.contract, wallet.clone()), + pyth_config.price_id, + ) + } + None => { + let pyth = deploy_mock_pyth_oracle(&wallet).await; + let pyth_price_id = Bits256::from(asset_id); pb.inc(); let pyth_feed = vec![( pyth_price_id, @@ -823,29 +824,88 @@ pub mod common { publish_time: PYTH_TIMESTAMP, }, )]; - let redstone_feed = redstone_price_feed_with_id(redstone_price_id, vec![1]); - - oracle_abi::set_debug_timestamp(&oracle, PYTH_TIMESTAMP).await; pyth_oracle_abi::update_price_feeds(&pyth, pyth_feed).await; - pb.inc(); + (pyth, pyth_price_id) + } + }; - redstone_oracle_abi::write_prices(&redstone, redstone_feed).await; - redstone_oracle_abi::set_timestamp(&redstone, PYTH_TIMESTAMP).await; + // Deploy or use existing Redstone oracle + let redstone_config: Option = match &existing_contracts.redstone_oracle { + Some(redstone_config) => { pb.inc(); + Some(RedstoneConfig { + contract: redstone_config.contract.into(), + price_id: redstone_config.price_id, + precision: redstone_config.precision, + }) + } + None => { + if deploy_redstone { + let redstone = deploy_mock_redstone_oracle(&wallet).await; + let redstone_price_id = U256::from(rand::thread_rng().gen_range(1..1_000_000)); + let redstone_feed = redstone_price_feed_with_id(redstone_price_id, vec![1]); + redstone_oracle_abi::write_prices(&redstone, redstone_feed).await; + redstone_oracle_abi::set_timestamp(&redstone, PYTH_TIMESTAMP).await; + pb.inc(); + Some(RedstoneConfig { + contract: redstone.contract_id().into(), + price_id: redstone_price_id, + precision: 9, + }) + } else { + None + } + } + }; - return AssetContracts { - oracle, - mock_pyth_oracle: pyth, - mock_redstone_oracle: redstone, - trove_manager, - asset, - asset_id, - pyth_price_id, - redstone_price_id, - redstone_precision: 9, - fuel_vm_decimals: 9, - }; + // Always deploy a new oracle and trove manager + let oracle = deploy_oracle( + &wallet, + mock_pyth_oracle.contract_id().into(), + pyth_price_id, + fuel_vm_decimals, + debug, + Identity::Address(wallet.address().into()), + ) + .await; + pb.inc(); + + let trove_manager = deploy_trove_manager_contract(&wallet).await; + pb.inc(); + + // Set up price feeds if we deployed new oracles + if debug { + oracle_abi::set_debug_timestamp(&oracle, PYTH_TIMESTAMP).await; + } + + println!("Deploying asset contracts... Done"); + println!("Oracle: {}", oracle.contract.contract_id()); + println!("Mock Pyth Oracle: {}", mock_pyth_oracle.contract_id()); + + println!("Trove Manager: {}", trove_manager.contract.contract_id()); + println!("Asset: {}", asset); + println!("Asset ID: {}", asset_id); + println!("Pyth Price ID: {:?}", pyth_price_id); + match &redstone_config { + Some(redstone_config) => { + println!("Redstone Oracle: {}", redstone_config.contract); + println!("Redstone Price ID: {}", redstone_config.price_id); + println!("Redstone Precision: {}", redstone_config.precision); } + None => println!("No Redstone Oracle"), + } + println!("Fuel VM Decimals: {}", fuel_vm_decimals); + + AssetContractsOptionalRedstone { + symbol: existing_contracts.symbol.clone(), + oracle, + mock_pyth_oracle, + redstone_config, + trove_manager, + asset: Token::new(asset, wallet.clone()), + asset_id, + pyth_price_id, + fuel_vm_decimals, } } @@ -881,19 +941,19 @@ pub mod common { trove_manager_abi::initialize( &trove_manager, - contracts.borrow_operations.contract_id().into(), - contracts.sorted_troves.contract_id().into(), - oracle.contract_id().into(), - contracts.stability_pool.contract_id().into(), - contracts.default_pool.contract_id().into(), - contracts.active_pool.contract_id().into(), - contracts.coll_surplus_pool.contract_id().into(), - contracts.usdf.contract_id().into(), + contracts.borrow_operations.contract.contract_id().into(), + contracts.sorted_troves.contract.contract_id().into(), + oracle.contract.contract_id().into(), + contracts.stability_pool.contract.contract_id().into(), + contracts.default_pool.contract.contract_id().into(), + contracts.active_pool.contract.contract_id().into(), + contracts.coll_surplus_pool.contract.contract_id().into(), + contracts.usdf.contract.contract_id().into(), asset .contract_id() .asset_id(&AssetId::zeroed().into()) .into(), - contracts.protocol_manager.contract_id().into(), + contracts.protocol_manager.contract.contract_id().into(), ) .await .unwrap(); @@ -906,8 +966,8 @@ pub mod common { .contract_id() .asset_id(&AssetId::zeroed().into()) .into(), - trove_manager.contract_id().into(), - oracle.contract_id().into(), + trove_manager.contract.contract_id().into(), + oracle.contract.contract_id().into(), &contracts.borrow_operations, &contracts.stability_pool, &contracts.usdf, @@ -941,7 +1001,7 @@ pub mod common { pub async fn initialize_asset( core_protocol_contracts: &ProtocolContracts, - asset_contracts: &AssetContracts, + asset_contracts: &AssetContractsOptionalRedstone, ) -> Result> { println!("Initializing asset contracts..."); let mut pb = ProgressBar::new(2); @@ -950,21 +1010,40 @@ pub mod common { &asset_contracts.trove_manager, core_protocol_contracts .borrow_operations + .contract + .contract_id() + .into(), + core_protocol_contracts + .sorted_troves + .contract + .contract_id() + .into(), + asset_contracts.oracle.contract.contract_id().into(), + core_protocol_contracts + .stability_pool + .contract + .contract_id() + .into(), + core_protocol_contracts + .default_pool + .contract + .contract_id() + .into(), + core_protocol_contracts + .active_pool + .contract .contract_id() .into(), - core_protocol_contracts.sorted_troves.contract_id().into(), - asset_contracts.oracle.contract_id().into(), - core_protocol_contracts.stability_pool.contract_id().into(), - core_protocol_contracts.default_pool.contract_id().into(), - core_protocol_contracts.active_pool.contract_id().into(), core_protocol_contracts .coll_surplus_pool + .contract .contract_id() .into(), - core_protocol_contracts.usdf.contract_id().into(), + core_protocol_contracts.usdf.contract.contract_id().into(), asset_contracts.asset_id, core_protocol_contracts .protocol_manager + .contract .contract_id() .into(), ) @@ -975,8 +1054,8 @@ pub mod common { protocol_manager_abi::register_asset( &core_protocol_contracts.protocol_manager, asset_contracts.asset_id, - asset_contracts.trove_manager.contract_id().into(), - asset_contracts.oracle.contract_id().into(), + asset_contracts.trove_manager.contract.contract_id().into(), + asset_contracts.oracle.contract.contract_id().into(), &core_protocol_contracts.borrow_operations, &core_protocol_contracts.stability_pool, &core_protocol_contracts.usdf, @@ -989,7 +1068,9 @@ pub mod common { .await } - pub async fn deploy_active_pool(wallet: &WalletUnlocked) -> ActivePool { + pub async fn deploy_active_pool( + wallet: &WalletUnlocked, + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -1007,31 +1088,25 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return ActivePool::new(id, wallet.clone()); - } - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(ACTIVE_POOL_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_configurables(configurables) - .with_salt(salt), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(ACTIVE_POOL_CONTRACT_STORAGE_PATH), + ) + .await; - return ActivePool::new(id, wallet.clone()); - } - } + ContractInstance::new( + ActivePool::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } - pub async fn deploy_stability_pool(wallet: &WalletUnlocked) -> StabilityPool { + pub async fn deploy_stability_pool( + wallet: &WalletUnlocked, + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -1049,31 +1124,25 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return StabilityPool::new(id, wallet.clone()); - } - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(STABILITY_POOL_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_salt(salt) - .with_configurables(configurables.clone()), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(STABILITY_POOL_CONTRACT_STORAGE_PATH), + ) + .await; - return StabilityPool::new(id, wallet.clone()); - } - } + ContractInstance::new( + StabilityPool::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } - pub async fn deploy_default_pool(wallet: &WalletUnlocked) -> DefaultPool { + pub async fn deploy_default_pool( + wallet: &WalletUnlocked, + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -1091,33 +1160,25 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return DefaultPool::new(id, wallet.clone()); - } - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(DEFAULT_POOL_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_salt(salt) - .with_configurables(configurables.clone()), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(DEFAULT_POOL_CONTRACT_STORAGE_PATH), + ) + .await; - return DefaultPool::new(id, wallet.clone()); - } - } + ContractInstance::new( + DefaultPool::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } pub async fn deploy_coll_surplus_pool( wallet: &WalletUnlocked, - ) -> CollSurplusPool { + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -1135,33 +1196,25 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return CollSurplusPool::new(id, wallet.clone()); - } - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(COLL_SURPLUS_POOL_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_salt(salt) - .with_configurables(configurables.clone()), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(COLL_SURPLUS_POOL_CONTRACT_STORAGE_PATH), + ) + .await; - return CollSurplusPool::new(id, wallet.clone()); - } - } + ContractInstance::new( + CollSurplusPool::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } pub async fn deploy_community_issuance( wallet: &WalletUnlocked, - ) -> CommunityIssuance { + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -1179,31 +1232,25 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return CommunityIssuance::new(id, wallet.clone()); - } - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(COMMUNITY_ISSUANCE_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_salt(salt) - .with_configurables(configurables.clone()), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(COMMUNITY_ISSUANCE_CONTRACT_STORAGE_PATH), + ) + .await; - return CommunityIssuance::new(id, wallet.clone()); - } - } + ContractInstance::new( + CommunityIssuance::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } - pub async fn deploy_fpt_staking(wallet: &WalletUnlocked) -> FPTStaking { + pub async fn deploy_fpt_staking( + wallet: &WalletUnlocked, + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -1221,31 +1268,25 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return FPTStaking::new(id, wallet.clone()); - } - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(FPT_STAKING_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_salt(salt) - .with_configurables(configurables.clone()), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(FPT_STAKING_CONTRACT_STORAGE_PATH), + ) + .await; - return FPTStaking::new(id, wallet.clone()); - } - } + ContractInstance::new( + FPTStaking::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } - pub async fn deploy_usdf_token(wallet: &WalletUnlocked) -> USDFToken { + pub async fn deploy_usdf_token( + wallet: &WalletUnlocked, + ) -> ContractInstance> { let mut rng = rand::thread_rng(); let salt = rng.gen::<[u8; 32]>(); let tx_policies = TxPolicies::default().with_tip(1); @@ -1263,28 +1304,20 @@ pub mod common { ) .unwrap() .deploy(&wallet.clone(), tx_policies) - .await; + .await + .unwrap(); - match id { - Ok(id) => { - return USDFToken::new(id, wallet.clone()); - } - Err(_) => { - wait(); - let id = Contract::load_from( - &get_absolute_path_from_relative(USDF_TOKEN_CONTRACT_BINARY_PATH), - LoadConfiguration::default() - .with_salt(salt) - .with_configurables(configurables.clone()), - ) - .unwrap() - .deploy(&wallet.clone(), tx_policies) - .await - .unwrap(); + let proxy = deploy_proxy( + id.clone().into(), + wallet.clone(), + Some(USDF_TOKEN_CONTRACT_STORAGE_PATH), + ) + .await; - return USDFToken::new(id, wallet.clone()); - } - } + ContractInstance::new( + USDFToken::new(proxy.contract_id(), wallet.clone()), + id.into(), + ) } pub async fn deploy_hint_helper(wallet: &WalletUnlocked) -> HintHelper { @@ -1350,4 +1383,94 @@ pub mod common { pub fn wait() { std::thread::sleep(std::time::Duration::from_secs(12)); } + + pub async fn deploy_proxy( + target: ContractId, + owner: WalletUnlocked, + additional_storage_path: Option<&str>, + ) -> Proxy { + let mut rng = rand::thread_rng(); + let salt = rng.gen::<[u8; 32]>(); + + // Storage keys for the proxy target contract + // These match the storage slots defined in the proxy contract's storage layout + // See contracts/proxy-contract/src/main.sw storage section + let target_key0 = + Bytes32::from_str("0x7bb458adc1d118713319a5baa00a2d049dd64d2916477d2688d76970c898cd55") + .unwrap(); + let target_key1 = + Bytes32::from_str("0x7bb458adc1d118713319a5baa00a2d049dd64d2916477d2688d76970c898cd56") + .unwrap(); + + // Convert target ContractId to storage value format + let target_value = Bytes32::new(target.into()); + let mut target_value0 = Bytes32::new([0u8; 32]); + let mut target_value1 = Bytes32::new([0u8; 32]); + + // Split target value across two storage slots + // First slot: Set flag byte and first part of target + target_value0[7] = 1; // Flag byte indicating initialized state + for n in 8..32 { + target_value0[n] = target_value[n - 8]; + } + // Second slot: Remaining bytes of target + for n in 0..8 { + target_value1[n] = target_value[n + 24]; + } + + // Storage keys for the proxy owner + // These match the storage slots for the proxy owner state + let owner_key0 = + Bytes32::from_str("bb79927b15d9259ea316f2ecb2297d6cc8851888a98278c0a2e03e1a091ea754") + .unwrap(); + let owner_key1 = + Bytes32::from_str("bb79927b15d9259ea316f2ecb2297d6cc8851888a98278c0a2e03e1a091ea755") + .unwrap(); + + // Convert owner address to storage value format + let owner_value = Bytes32::new(Address::from(owner.address()).into()); + let mut owner_value0 = Bytes32::new([0u8; 32]); + let mut owner_value1 = Bytes32::new([0u8; 32]); + + // Split owner value across two storage slots + // First slot: Set flag byte and first part of owner address + owner_value0[7] = 1; // Flag byte indicating initialized state + for n in 16..32 { + owner_value0[n] = owner_value[n - 16]; + } + // Second slot: Remaining bytes of owner address + for n in 0..16 { + owner_value1[n] = owner_value[n + 16]; + } + + // Create storage configuration with the initialized slots + let storage_slots = [ + StorageSlot::new(target_key0, target_value0), + StorageSlot::new(target_key1, target_value1), + StorageSlot::new(owner_key0, owner_value0), + StorageSlot::new(owner_key1, owner_value1), + ]; + let storage_configuration = match additional_storage_path { + Some(path) => StorageConfiguration::default() + .add_slot_overrides(storage_slots) + .add_slot_overrides_from_file(get_absolute_path_from_relative(path)) + .unwrap(), + None => StorageConfiguration::default().add_slot_overrides(storage_slots), + }; + // Deploy the proxy contract with the initialized storage + let contract_configuration = + LoadConfiguration::default().with_storage_configuration(storage_configuration); + + let contract_id = Contract::load_from( + &get_absolute_path_from_relative(PROXY_CONTRACT_BINARY_PATH), + contract_configuration, + ) + .unwrap() + .with_salt(salt) + .deploy(&owner, TxPolicies::default()) + .await + .unwrap(); + + Proxy::new(contract_id, owner) + } } diff --git a/test-utils/src/testing_query_manual.rs b/test-utils/src/testing_query_manual.rs deleted file mode 100644 index 36020ea2..00000000 --- a/test-utils/src/testing_query_manual.rs +++ /dev/null @@ -1,124 +0,0 @@ -use crate::data_structures::PRECISION; -use crate::interfaces::active_pool::ActivePool; -use crate::interfaces::borrow_operations::{borrow_operations_abi, BorrowOperations}; -use crate::interfaces::fpt_staking::FPTStaking; -use crate::interfaces::oracle::{oracle_abi, Oracle}; -use crate::interfaces::pyth_oracle::PythCore; -use crate::interfaces::redstone_oracle::RedstoneCore; -use crate::interfaces::sorted_troves::SortedTroves; -use crate::interfaces::token::Token; -use crate::interfaces::trove_manager::TroveManagerContract; -use crate::interfaces::usdf_token::USDFToken; -use dotenv::dotenv; -use fuels::prelude::{Bech32ContractId, Provider, WalletUnlocked}; -use fuels::types::{Address, Identity}; - -const RPC: &str = "beta-4.fuel.network"; - -// This is not a core part of the testing suite, meant to be a quick script for manking manual queries to the testnet - -#[tokio::main] -pub async fn testing_query() { - let provider = match Provider::connect(RPC).await { - Ok(p) => p, - Err(error) => panic!("❌ Problem creating provider: {:#?}", error), - }; - - dotenv().ok(); - let secret = match std::env::var("SECRET") { - Ok(s) => s, - Err(error) => panic!("❌ Cannot find .env file: {:#?}", error), - }; - - let wallet = WalletUnlocked::new_from_mnemonic_phrase_with_path( - &secret, - Some(provider.clone()), - "m/44'/1179993420'/0'/0/0", - ) - .unwrap(); - - println!("Wallet address: {}", wallet.address()); - let id: Bech32ContractId = "fuel129gw5u3rlacka3smhngevvgq4awllx8u4l5fktpr506yaxv8gx4qz6y4k3" - .parse() - .expect("Invalid ID"); - - let oracle = Oracle::new(id.clone(), wallet.clone()); - let pyth = PythCore::new(id.clone(), wallet.clone()); - let redstone = RedstoneCore::new(id, wallet.clone()); - - let res = oracle_abi::get_price(&oracle, &pyth, &Some(redstone.clone())).await; - - println!("Result: {:#?}", res.value); - - let borrow_operations_id: Bech32ContractId = - "fuel1wnys85mec9vna4y577r97w0u4egdpmnvuxv32cph8uqqzmx8694sd7wqtw" - .parse() - .expect("Invalid ID"); - - let borrow_operations = BorrowOperations::new(borrow_operations_id, wallet.clone()); - - let null_hint = Identity::Address(Address::default()); - - let asset_token_id: Bech32ContractId = - "fuel1ql6d5vjmuqs0v2tev7su73zjrpajffy9cjccvll38mxmamaeteuqml4pxl" - .parse() - .expect("Invalid ID"); - let asset_token = Token::new(asset_token_id, wallet.clone()); - - let usdf_token_id: Bech32ContractId = - "fuel1an59xymuwqj9r757agfcu0wetqadsl0lc6xw7xe3vka23d0z2tfqa8t7c5" - .parse() - .expect("Invalid ID"); - - let usdf_token = USDFToken::new(usdf_token_id, wallet.clone()); - - let fpt_staking_id: Bech32ContractId = - "fuel14a5zgt9yz04rwnt7z7dyxuhtdlzyjtu9nfxw7pl3ares0zd85svqwlntrm" - .parse() - .expect("Invalid ID"); - - let fpt_staking = FPTStaking::new(fpt_staking_id, wallet.clone()); - - let sorted_troves_id: Bech32ContractId = - "fuel17q7999tp3s55jk7ev9sj6kmzp3qfmr8rnwnf6dzg9df4z3jrh74qpg5x22" - .parse() - .expect("Invalid ID"); - - let sorted_troves = SortedTroves::new(sorted_troves_id, wallet.clone()); - - let trove_manager_id: Bech32ContractId = - "fuel17thhl04jewnftymwksgufgcsegea72a6pjfwgxg0nptvc0ys5yjq05arr4" - .parse() - .expect("Invalid ID"); - - let trove_manager = TroveManagerContract::new(trove_manager_id, wallet.clone()); - - let active_pool_id: Bech32ContractId = - "fuel12qxy3gk3wdm3cytlfsaegzth7cnn5de5q8hrg6cdukff2k0zhcws3rxqef" - .parse() - .expect("Invalid ID"); - - let active_pool = ActivePool::new(active_pool_id, wallet.clone()); - - let mock_amount_deposit = 2 * PRECISION; - let usdf_amount_withdrawn = 600 * PRECISION; - - let _res = borrow_operations_abi::open_trove( - &borrow_operations, - &oracle, - &pyth, - &redstone, - &asset_token, - &usdf_token, - &fpt_staking, - &sorted_troves, - &trove_manager, - &active_pool, - mock_amount_deposit, - usdf_amount_withdrawn, - null_hint.clone(), - null_hint.clone(), - ) - .await - .unwrap(); -}