refactor(substreams): improve logic to ignore updates (#96)
* refactor(substreams): ignore transaction if contracts update are ignored. There are some cases where we ignore contracts updates (for example if the old and new values are the same). In that case if the transaction only contains ignored updates we don't emit it. * refactor(substreams): ignore deletions for freshly created attributes. There are cases where an attribute can be created and deleted during the same transaction. To avoid sending a confusing deletion for something that was never created before, we just ignore the deletion in that particular case. * feat(substreams): Add uniswap V3 logs only module (#98) * feat(substreams): add uniswapV3 logs only Substreams module * refactor(substreams): encode everything as big endian * refactor(substreams): mark changes as creation when a tick liq is updated from 0 This will allow the SDK to detect cases where a tick is created and deleted in the same transaction and ignore it. * ci(substreams): ignore built files for uniswapv3 logs only module and clean code * refactor(substreams): update uniswapv3 substreams with new SDK interface * feat(subtreams): emit default token balances value for uniswapv3 --------- Co-authored-by: zizou <111426680+flopell@users.noreply.github.com> --------- Co-authored-by: zizou <111426680+flopell@users.noreply.github.com>
This commit is contained in:
92
substreams/Cargo.lock
generated
92
substreams/Cargo.lock
generated
@@ -347,6 +347,26 @@ dependencies = [
|
|||||||
"tycho-substreams",
|
"tycho-substreams",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "ethereum-uniswap-v3-logs-only"
|
||||||
|
version = "0.1.0"
|
||||||
|
dependencies = [
|
||||||
|
"anyhow",
|
||||||
|
"ethabi 18.0.0",
|
||||||
|
"getrandom",
|
||||||
|
"hex",
|
||||||
|
"hex-literal 0.4.1",
|
||||||
|
"itertools 0.13.0",
|
||||||
|
"num-bigint",
|
||||||
|
"prost 0.11.9",
|
||||||
|
"substreams",
|
||||||
|
"substreams-entity-change",
|
||||||
|
"substreams-ethereum",
|
||||||
|
"substreams-helper",
|
||||||
|
"tiny-keccak",
|
||||||
|
"tycho-substreams",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "fastrand"
|
name = "fastrand"
|
||||||
version = "2.0.1"
|
version = "2.0.1"
|
||||||
@@ -660,6 +680,51 @@ version = "2.3.1"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e"
|
checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pest"
|
||||||
|
version = "2.7.14"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "879952a81a83930934cbf1786752d6dedc3b1f29e8f8fb2ad1d0a36f377cf442"
|
||||||
|
dependencies = [
|
||||||
|
"memchr",
|
||||||
|
"thiserror",
|
||||||
|
"ucd-trie",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pest_derive"
|
||||||
|
version = "2.7.14"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "d214365f632b123a47fd913301e14c946c61d1c183ee245fa76eb752e59a02dd"
|
||||||
|
dependencies = [
|
||||||
|
"pest",
|
||||||
|
"pest_generator",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pest_generator"
|
||||||
|
version = "2.7.14"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "eb55586734301717aea2ac313f50b2eb8f60d2fc3dc01d190eefa2e625f60c4e"
|
||||||
|
dependencies = [
|
||||||
|
"pest",
|
||||||
|
"pest_meta",
|
||||||
|
"proc-macro2",
|
||||||
|
"quote",
|
||||||
|
"syn 2.0.52",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pest_meta"
|
||||||
|
version = "2.7.14"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "b75da2a70cf4d9cb76833c990ac9cd3923c9a8905a8929789ce347c84564d03d"
|
||||||
|
dependencies = [
|
||||||
|
"once_cell",
|
||||||
|
"pest",
|
||||||
|
"sha2",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "petgraph"
|
name = "petgraph"
|
||||||
version = "0.6.4"
|
version = "0.6.4"
|
||||||
@@ -968,6 +1033,17 @@ dependencies = [
|
|||||||
"thiserror",
|
"thiserror",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "sha2"
|
||||||
|
version = "0.10.8"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "793db75ad2bcafc3ffa7c68b215fee268f537982cd901d132f89c6343f3a3dc8"
|
||||||
|
dependencies = [
|
||||||
|
"cfg-if",
|
||||||
|
"cpufeatures",
|
||||||
|
"digest",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "sha3"
|
name = "sha3"
|
||||||
version = "0.10.8"
|
version = "0.10.8"
|
||||||
@@ -986,9 +1062,9 @@ checksum = "a2eb9349b6444b326872e140eb1cf5e7c522154d69e7a0ffb0fb81c06b37543f"
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "substreams"
|
name = "substreams"
|
||||||
version = "0.5.13"
|
version = "0.5.22"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "3520661f782c338f0e3c6cfc001ac790ed5e68d8f28515139e2aa674f8bb54da"
|
checksum = "92e47e531af83a3cbb78c627ee8232a0ac86604f11c89e34bd4b721ec41e03e5"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"anyhow",
|
"anyhow",
|
||||||
"bigdecimal",
|
"bigdecimal",
|
||||||
@@ -998,6 +1074,8 @@ dependencies = [
|
|||||||
"num-integer",
|
"num-integer",
|
||||||
"num-traits",
|
"num-traits",
|
||||||
"pad",
|
"pad",
|
||||||
|
"pest",
|
||||||
|
"pest_derive",
|
||||||
"prost 0.11.9",
|
"prost 0.11.9",
|
||||||
"prost-build",
|
"prost-build",
|
||||||
"prost-types 0.11.9",
|
"prost-types 0.11.9",
|
||||||
@@ -1141,9 +1219,9 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "substreams-macro"
|
name = "substreams-macro"
|
||||||
version = "0.5.13"
|
version = "0.5.22"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "c15595ceab80fece579e462d4823048fe85d67922584c681f5e94305727ad9ee"
|
checksum = "a4ac77f08d723dace35739d65df8ed122f6d04e2a3e47929831d4021e3339240"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"proc-macro2",
|
"proc-macro2",
|
||||||
"quote",
|
"quote",
|
||||||
@@ -1258,6 +1336,12 @@ version = "1.17.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "42ff0bf0c66b8238c6f3b578df37d0b7848e55df8577b3f74f92a69acceeb825"
|
checksum = "42ff0bf0c66b8238c6f3b578df37d0b7848e55df8577b3f74f92a69acceeb825"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "ucd-trie"
|
||||||
|
version = "0.1.7"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "2896d95c02a80c6d6a5d6e953d479f5ddf2dfdb6a244441010e373ac0fb88971"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "uint"
|
name = "uint"
|
||||||
version = "0.9.5"
|
version = "0.9.5"
|
||||||
|
|||||||
@@ -9,13 +9,14 @@ members = [
|
|||||||
"ethereum-uniswap-v3",
|
"ethereum-uniswap-v3",
|
||||||
"ethereum-sfrax",
|
"ethereum-sfrax",
|
||||||
"ethereum-sfraxeth",
|
"ethereum-sfraxeth",
|
||||||
|
"ethereum-uniswap-v3-logs-only",
|
||||||
]
|
]
|
||||||
resolver = "2"
|
resolver = "2"
|
||||||
|
|
||||||
|
|
||||||
[workspace.dependencies]
|
[workspace.dependencies]
|
||||||
substreams-ethereum = "0.9.9"
|
substreams-ethereum = "0.9.9"
|
||||||
substreams = "0.5"
|
substreams = "0.5.22"
|
||||||
prost = "0.11"
|
prost = "0.11"
|
||||||
prost-types = "0.12.3"
|
prost-types = "0.12.3"
|
||||||
hex-literal = "0.4.1"
|
hex-literal = "0.4.1"
|
||||||
|
|||||||
@@ -59,7 +59,7 @@ pub fn extract_contract_changes<F: Fn(&[u8]) -> bool>(
|
|||||||
changed_contracts
|
changed_contracts
|
||||||
.clone()
|
.clone()
|
||||||
.into_values()
|
.into_values()
|
||||||
.map(|change| change.into()),
|
.filter_map(|change| change.into()),
|
||||||
);
|
);
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
use std::collections::HashMap;
|
use std::collections::{HashMap, HashSet};
|
||||||
use substreams_ethereum::pb::eth::v2::{self as sf, StorageChange};
|
use substreams_ethereum::pb::eth::v2::{self as sf, StorageChange};
|
||||||
|
|
||||||
// re-export the protobuf types here.
|
// re-export the protobuf types here.
|
||||||
@@ -114,6 +114,13 @@ impl TransactionChangesBuilder {
|
|||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|a| (a.name.clone(), a))
|
.map(|a| (a.name.clone(), a))
|
||||||
.collect(),
|
.collect(),
|
||||||
|
created_attributes: change
|
||||||
|
.attributes
|
||||||
|
.clone()
|
||||||
|
.iter()
|
||||||
|
.filter(|&attr| (attr.change == i32::from(ChangeType::Creation)))
|
||||||
|
.map(|attr| attr.name.clone())
|
||||||
|
.collect(),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -141,34 +148,31 @@ impl TransactionChangesBuilder {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn build(self) -> Option<TransactionChanges> {
|
pub fn build(self) -> Option<TransactionChanges> {
|
||||||
if self.contract_changes.is_empty() &&
|
let tx_changes = TransactionChanges {
|
||||||
self.component_changes.is_empty() &&
|
tx: self.tx,
|
||||||
self.balance_changes.is_empty() &&
|
contract_changes: self
|
||||||
self.entity_changes.is_empty()
|
.contract_changes
|
||||||
{
|
.into_values()
|
||||||
|
.filter_map(|interim| interim.into())
|
||||||
|
.collect::<Vec<_>>(),
|
||||||
|
entity_changes: self
|
||||||
|
.entity_changes
|
||||||
|
.into_values()
|
||||||
|
.filter_map(|interim| interim.into())
|
||||||
|
.collect::<Vec<_>>(),
|
||||||
|
component_changes: self
|
||||||
|
.component_changes
|
||||||
|
.into_values()
|
||||||
|
.collect::<Vec<_>>(),
|
||||||
|
balance_changes: self
|
||||||
|
.balance_changes
|
||||||
|
.into_values()
|
||||||
|
.collect::<Vec<_>>(),
|
||||||
|
};
|
||||||
|
if tx_changes.is_empty() {
|
||||||
None
|
None
|
||||||
} else {
|
} else {
|
||||||
Some(TransactionChanges {
|
Some(tx_changes)
|
||||||
tx: self.tx,
|
|
||||||
contract_changes: self
|
|
||||||
.contract_changes
|
|
||||||
.into_values()
|
|
||||||
.map(|interim| interim.into())
|
|
||||||
.collect::<Vec<_>>(),
|
|
||||||
entity_changes: self
|
|
||||||
.entity_changes
|
|
||||||
.into_values()
|
|
||||||
.map(|interim| interim.into())
|
|
||||||
.collect::<Vec<_>>(),
|
|
||||||
component_changes: self
|
|
||||||
.component_changes
|
|
||||||
.into_values()
|
|
||||||
.collect::<Vec<_>>(),
|
|
||||||
balance_changes: self
|
|
||||||
.balance_changes
|
|
||||||
.into_values()
|
|
||||||
.collect::<Vec<_>>(),
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -389,6 +393,8 @@ impl ProtocolComponent {
|
|||||||
pub struct InterimEntityChanges {
|
pub struct InterimEntityChanges {
|
||||||
component_id: String,
|
component_id: String,
|
||||||
attributes: HashMap<String, Attribute>,
|
attributes: HashMap<String, Attribute>,
|
||||||
|
/// A set of created attributes during this transaction
|
||||||
|
created_attributes: HashSet<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl InterimEntityChanges {
|
impl InterimEntityChanges {
|
||||||
@@ -397,26 +403,45 @@ impl InterimEntityChanges {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_attribute(&mut self, attr: &Attribute) {
|
pub fn set_attribute(&mut self, attr: &Attribute) {
|
||||||
self.attributes
|
// Add any attribute creation to the map
|
||||||
.entry(attr.name.clone())
|
if attr.change == i32::from(ChangeType::Creation) {
|
||||||
.and_modify(|existing| *existing = attr.clone())
|
self.created_attributes
|
||||||
.or_insert(attr.clone());
|
.insert(attr.name.clone());
|
||||||
|
}
|
||||||
|
|
||||||
|
if attr.change == i32::from(ChangeType::Deletion) &&
|
||||||
|
self.created_attributes
|
||||||
|
.contains(&attr.name)
|
||||||
|
{
|
||||||
|
// If a freshly created attribute is deleted, remove the creation.
|
||||||
|
self.attributes.remove(&attr.name);
|
||||||
|
} else {
|
||||||
|
self.attributes
|
||||||
|
.entry(attr.name.clone())
|
||||||
|
.and_modify(|existing| *existing = attr.clone())
|
||||||
|
.or_insert(attr.clone());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<InterimEntityChanges> for EntityChanges {
|
impl From<InterimEntityChanges> for Option<EntityChanges> {
|
||||||
fn from(value: InterimEntityChanges) -> Self {
|
fn from(value: InterimEntityChanges) -> Self {
|
||||||
EntityChanges {
|
let changes = EntityChanges {
|
||||||
component_id: value.component_id.clone(),
|
component_id: value.component_id.clone(),
|
||||||
attributes: value
|
attributes: value
|
||||||
.attributes
|
.attributes
|
||||||
.into_values()
|
.into_values()
|
||||||
.collect::<Vec<_>>(),
|
.collect::<Vec<_>>(),
|
||||||
|
};
|
||||||
|
if changes.attributes.is_empty() {
|
||||||
|
None
|
||||||
|
} else {
|
||||||
|
Some(changes)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone, Debug)]
|
||||||
struct SlotValue {
|
struct SlotValue {
|
||||||
new_value: Vec<u8>,
|
new_value: Vec<u8>,
|
||||||
start_value: Vec<u8>,
|
start_value: Vec<u8>,
|
||||||
@@ -435,7 +460,7 @@ impl From<&StorageChange> for SlotValue {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Uses a map for slots, protobuf does not allow bytes in hashmap keys
|
// Uses a map for slots, protobuf does not allow bytes in hashmap keys
|
||||||
#[derive(Clone)]
|
#[derive(Clone, Debug)]
|
||||||
pub struct InterimContractChange {
|
pub struct InterimContractChange {
|
||||||
address: Vec<u8>,
|
address: Vec<u8>,
|
||||||
balance: Vec<u8>,
|
balance: Vec<u8>,
|
||||||
@@ -492,9 +517,9 @@ impl InterimContractChange {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<InterimContractChange> for ContractChange {
|
impl From<InterimContractChange> for Option<ContractChange> {
|
||||||
fn from(value: InterimContractChange) -> Self {
|
fn from(value: InterimContractChange) -> Self {
|
||||||
ContractChange {
|
let contract_change = ContractChange {
|
||||||
address: value.address,
|
address: value.address,
|
||||||
balance: value.balance,
|
balance: value.balance,
|
||||||
code: value.code,
|
code: value.code,
|
||||||
@@ -505,6 +530,87 @@ impl From<InterimContractChange> for ContractChange {
|
|||||||
.map(|(slot, value)| ContractSlot { slot, value: value.new_value })
|
.map(|(slot, value)| ContractSlot { slot, value: value.new_value })
|
||||||
.collect(),
|
.collect(),
|
||||||
change: value.change.into(),
|
change: value.change.into(),
|
||||||
|
};
|
||||||
|
if contract_change.is_empty() {
|
||||||
|
None
|
||||||
|
} else {
|
||||||
|
Some(contract_change)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl ContractChange {
|
||||||
|
fn is_empty(&self) -> bool {
|
||||||
|
self.balance.is_empty() &&
|
||||||
|
self.slots.is_empty() &&
|
||||||
|
self.code.is_empty() &&
|
||||||
|
self.change == i32::from(ChangeType::Update)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl TransactionChanges {
|
||||||
|
fn is_empty(&self) -> bool {
|
||||||
|
self.contract_changes.is_empty() &&
|
||||||
|
self.component_changes.is_empty() &&
|
||||||
|
self.balance_changes.is_empty() &&
|
||||||
|
self.entity_changes.is_empty()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod test {
|
||||||
|
use substreams_ethereum::pb::eth::v2::StorageChange;
|
||||||
|
|
||||||
|
use crate::models::{Attribute, ChangeType, EntityChanges};
|
||||||
|
|
||||||
|
use super::{InterimContractChange, TransactionChangesBuilder};
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_transaction_changes_builder_ignored_contract_changes() {
|
||||||
|
let mut builder = TransactionChangesBuilder::new(&super::Transaction::default());
|
||||||
|
let mut contract_changes = InterimContractChange::new(&[1], false);
|
||||||
|
contract_changes.upsert_slot(&StorageChange {
|
||||||
|
address: [1].to_vec(),
|
||||||
|
key: [0].to_vec(),
|
||||||
|
old_value: [1].to_vec(),
|
||||||
|
new_value: [1].to_vec(), //Same old and new value, must be ignored
|
||||||
|
ordinal: 1,
|
||||||
|
});
|
||||||
|
builder.add_contract_changes(&contract_changes);
|
||||||
|
|
||||||
|
let tx_changes = builder.build();
|
||||||
|
assert!(tx_changes.is_none());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_transaction_changes_builder_ignored_deletion() {
|
||||||
|
let mut builder = TransactionChangesBuilder::new(&super::Transaction::default());
|
||||||
|
|
||||||
|
// Create an attribute
|
||||||
|
let changes = EntityChanges {
|
||||||
|
component_id: "component".to_string(),
|
||||||
|
attributes: vec![Attribute {
|
||||||
|
name: "attribute".to_string(),
|
||||||
|
value: vec![1],
|
||||||
|
change: ChangeType::Creation.into(),
|
||||||
|
}],
|
||||||
|
};
|
||||||
|
|
||||||
|
builder.add_entity_change(&changes);
|
||||||
|
|
||||||
|
// Delete the attribute
|
||||||
|
let changes = EntityChanges {
|
||||||
|
component_id: "component".to_string(),
|
||||||
|
attributes: vec![Attribute {
|
||||||
|
name: "attribute".to_string(),
|
||||||
|
value: vec![0],
|
||||||
|
change: ChangeType::Deletion.into(),
|
||||||
|
}],
|
||||||
|
};
|
||||||
|
|
||||||
|
builder.add_entity_change(&changes);
|
||||||
|
|
||||||
|
let tx_changes = builder.build();
|
||||||
|
assert!(tx_changes.is_none());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
30
substreams/ethereum-uniswap-v3-logs-only/Cargo.toml
Normal file
30
substreams/ethereum-uniswap-v3-logs-only/Cargo.toml
Normal file
@@ -0,0 +1,30 @@
|
|||||||
|
[package]
|
||||||
|
name = "ethereum-uniswap-v3-logs-only"
|
||||||
|
version = "0.1.0"
|
||||||
|
edition = "2021"
|
||||||
|
|
||||||
|
[lib]
|
||||||
|
name = "ethereum_uniswap_v3_logs_only"
|
||||||
|
crate-type = ["cdylib"]
|
||||||
|
|
||||||
|
[dependencies]
|
||||||
|
substreams.workspace = true
|
||||||
|
substreams-ethereum.workspace = true
|
||||||
|
prost.workspace = true
|
||||||
|
ethabi.workspace = true
|
||||||
|
anyhow = { workspace = true, features = [] }
|
||||||
|
hex-literal.workspace = true
|
||||||
|
substreams-helper.workspace = true
|
||||||
|
tycho-substreams.workspace = true
|
||||||
|
num-bigint = "0.4.4"
|
||||||
|
hex.workspace = true
|
||||||
|
tiny-keccak = "2.0"
|
||||||
|
substreams-entity-change = "1.3"
|
||||||
|
itertools = "0.13.0"
|
||||||
|
|
||||||
|
[target.wasm32-unknown-unknown.dependencies]
|
||||||
|
getrandom = { version = "0.2", features = ["custom"] }
|
||||||
|
|
||||||
|
[build-dependencies]
|
||||||
|
anyhow.workspace = true
|
||||||
|
substreams-ethereum.workspace = true
|
||||||
2
substreams/ethereum-uniswap-v3-logs-only/Makefile
Normal file
2
substreams/ethereum-uniswap-v3-logs-only/Makefile
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
build:
|
||||||
|
cargo build --target wasm32-unknown-unknown --profile substreams
|
||||||
198
substreams/ethereum-uniswap-v3-logs-only/abi/Factory.json
Normal file
198
substreams/ethereum-uniswap-v3-logs-only/abi/Factory.json
Normal file
@@ -0,0 +1,198 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "uint24",
|
||||||
|
"name": "fee",
|
||||||
|
"type": "uint24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickSpacing",
|
||||||
|
"type": "int24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "FeeAmountEnabled",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "oldOwner",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "newOwner",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "OwnerChanged",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "token0",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "token1",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "uint24",
|
||||||
|
"name": "fee",
|
||||||
|
"type": "uint24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickSpacing",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "pool",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "PoolCreated",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "tokenA",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "tokenB",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint24",
|
||||||
|
"name": "fee",
|
||||||
|
"type": "uint24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "createPool",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "pool",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint24",
|
||||||
|
"name": "fee",
|
||||||
|
"type": "uint24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickSpacing",
|
||||||
|
"type": "int24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "enableFeeAmount",
|
||||||
|
"outputs": [],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint24",
|
||||||
|
"name": "fee",
|
||||||
|
"type": "uint24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "feeAmountTickSpacing",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "",
|
||||||
|
"type": "int24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "tokenA",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "tokenB",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint24",
|
||||||
|
"name": "fee",
|
||||||
|
"type": "uint24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "getPool",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "pool",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "owner",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "_owner",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "setOwner",
|
||||||
|
"outputs": [],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
}
|
||||||
|
]
|
||||||
988
substreams/ethereum-uniswap-v3-logs-only/abi/Pool.json
Normal file
988
substreams/ethereum-uniswap-v3-logs-only/abi/Pool.json
Normal file
@@ -0,0 +1,988 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "constructor"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "owner",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickLower",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickUpper",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "Burn",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "owner",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickLower",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickUpper",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "Collect",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "sender",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "CollectProtocol",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "sender",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "paid0",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "paid1",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "Flash",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint16",
|
||||||
|
"name": "observationCardinalityNextOld",
|
||||||
|
"type": "uint16"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint16",
|
||||||
|
"name": "observationCardinalityNextNew",
|
||||||
|
"type": "uint16"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "IncreaseObservationCardinalityNext",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint160",
|
||||||
|
"name": "sqrtPriceX96",
|
||||||
|
"type": "uint160"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tick",
|
||||||
|
"type": "int24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "Initialize",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "sender",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "owner",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickLower",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickUpper",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "Mint",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint8",
|
||||||
|
"name": "feeProtocol0Old",
|
||||||
|
"type": "uint8"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint8",
|
||||||
|
"name": "feeProtocol1Old",
|
||||||
|
"type": "uint8"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint8",
|
||||||
|
"name": "feeProtocol0New",
|
||||||
|
"type": "uint8"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint8",
|
||||||
|
"name": "feeProtocol1New",
|
||||||
|
"type": "uint8"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "SetFeeProtocol",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"anonymous": false,
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "sender",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": true,
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "int256",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "int256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "int256",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "int256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint160",
|
||||||
|
"name": "sqrtPriceX96",
|
||||||
|
"type": "uint160"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "liquidity",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"indexed": false,
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tick",
|
||||||
|
"type": "int24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "Swap",
|
||||||
|
"type": "event"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickLower",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickUpper",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "burn",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickLower",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickUpper",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount0Requested",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount1Requested",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "collect",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount0Requested",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount1Requested",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "collectProtocol",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "factory",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "fee",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint24",
|
||||||
|
"name": "",
|
||||||
|
"type": "uint24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "feeGrowthGlobal0X128",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "feeGrowthGlobal1X128",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "bytes",
|
||||||
|
"name": "data",
|
||||||
|
"type": "bytes"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "flash",
|
||||||
|
"outputs": [],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint16",
|
||||||
|
"name": "observationCardinalityNext",
|
||||||
|
"type": "uint16"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "increaseObservationCardinalityNext",
|
||||||
|
"outputs": [],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint160",
|
||||||
|
"name": "sqrtPriceX96",
|
||||||
|
"type": "uint160"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "initialize",
|
||||||
|
"outputs": [],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "liquidity",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "maxLiquidityPerTick",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickLower",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickUpper",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "amount",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "bytes",
|
||||||
|
"name": "data",
|
||||||
|
"type": "bytes"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "mint",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "index",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "observations",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint32",
|
||||||
|
"name": "blockTimestamp",
|
||||||
|
"type": "uint32"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int56",
|
||||||
|
"name": "tickCumulative",
|
||||||
|
"type": "int56"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint160",
|
||||||
|
"name": "secondsPerLiquidityCumulativeX128",
|
||||||
|
"type": "uint160"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "bool",
|
||||||
|
"name": "initialized",
|
||||||
|
"type": "bool"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint32[]",
|
||||||
|
"name": "secondsAgos",
|
||||||
|
"type": "uint32[]"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "observe",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int56[]",
|
||||||
|
"name": "tickCumulatives",
|
||||||
|
"type": "int56[]"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint160[]",
|
||||||
|
"name": "secondsPerLiquidityCumulativeX128s",
|
||||||
|
"type": "uint160[]"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "bytes32",
|
||||||
|
"name": "key",
|
||||||
|
"type": "bytes32"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "positions",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "_liquidity",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "feeGrowthInside0LastX128",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "feeGrowthInside1LastX128",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "tokensOwed0",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "tokensOwed1",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "protocolFees",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "token0",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "token1",
|
||||||
|
"type": "uint128"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint8",
|
||||||
|
"name": "feeProtocol0",
|
||||||
|
"type": "uint8"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint8",
|
||||||
|
"name": "feeProtocol1",
|
||||||
|
"type": "uint8"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "setFeeProtocol",
|
||||||
|
"outputs": [],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "slot0",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint160",
|
||||||
|
"name": "sqrtPriceX96",
|
||||||
|
"type": "uint160"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tick",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint16",
|
||||||
|
"name": "observationIndex",
|
||||||
|
"type": "uint16"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint16",
|
||||||
|
"name": "observationCardinality",
|
||||||
|
"type": "uint16"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint16",
|
||||||
|
"name": "observationCardinalityNext",
|
||||||
|
"type": "uint16"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint8",
|
||||||
|
"name": "feeProtocol",
|
||||||
|
"type": "uint8"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "bool",
|
||||||
|
"name": "unlocked",
|
||||||
|
"type": "bool"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickLower",
|
||||||
|
"type": "int24"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tickUpper",
|
||||||
|
"type": "int24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "snapshotCumulativesInside",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int56",
|
||||||
|
"name": "tickCumulativeInside",
|
||||||
|
"type": "int56"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint160",
|
||||||
|
"name": "secondsPerLiquidityInsideX128",
|
||||||
|
"type": "uint160"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint32",
|
||||||
|
"name": "secondsInside",
|
||||||
|
"type": "uint32"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "recipient",
|
||||||
|
"type": "address"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "bool",
|
||||||
|
"name": "zeroForOne",
|
||||||
|
"type": "bool"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int256",
|
||||||
|
"name": "amountSpecified",
|
||||||
|
"type": "int256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint160",
|
||||||
|
"name": "sqrtPriceLimitX96",
|
||||||
|
"type": "uint160"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "bytes",
|
||||||
|
"name": "data",
|
||||||
|
"type": "bytes"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "swap",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int256",
|
||||||
|
"name": "amount0",
|
||||||
|
"type": "int256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int256",
|
||||||
|
"name": "amount1",
|
||||||
|
"type": "int256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "nonpayable",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int16",
|
||||||
|
"name": "wordPosition",
|
||||||
|
"type": "int16"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "tickBitmap",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "",
|
||||||
|
"type": "uint256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "tickSpacing",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "",
|
||||||
|
"type": "int24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"internalType": "int24",
|
||||||
|
"name": "tick",
|
||||||
|
"type": "int24"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"name": "ticks",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "uint128",
|
||||||
|
"name": "liquidityGross",
|
||||||
|
"type": "uint128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int128",
|
||||||
|
"name": "liquidityNet",
|
||||||
|
"type": "int128"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "feeGrowthOutside0X128",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint256",
|
||||||
|
"name": "feeGrowthOutside1X128",
|
||||||
|
"type": "uint256"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "int56",
|
||||||
|
"name": "tickCumulativeOutside",
|
||||||
|
"type": "int56"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint160",
|
||||||
|
"name": "secondsPerLiquidityOutsideX128",
|
||||||
|
"type": "uint160"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "uint32",
|
||||||
|
"name": "secondsOutside",
|
||||||
|
"type": "uint32"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"internalType": "bool",
|
||||||
|
"name": "initialized",
|
||||||
|
"type": "bool"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "token0",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"inputs": [],
|
||||||
|
"name": "token1",
|
||||||
|
"outputs": [
|
||||||
|
{
|
||||||
|
"internalType": "address",
|
||||||
|
"name": "",
|
||||||
|
"type": "address"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"stateMutability": "view",
|
||||||
|
"type": "function"
|
||||||
|
}
|
||||||
|
]
|
||||||
12
substreams/ethereum-uniswap-v3-logs-only/buf.gen.yaml
Normal file
12
substreams/ethereum-uniswap-v3-logs-only/buf.gen.yaml
Normal file
@@ -0,0 +1,12 @@
|
|||||||
|
|
||||||
|
version: v1
|
||||||
|
plugins:
|
||||||
|
- plugin: buf.build/community/neoeinstein-prost:v0.2.2
|
||||||
|
out: src/pb
|
||||||
|
opt:
|
||||||
|
- file_descriptor_set=false
|
||||||
|
|
||||||
|
- plugin: buf.build/community/neoeinstein-prost-crate:v0.3.1
|
||||||
|
out: src/pb
|
||||||
|
opt:
|
||||||
|
- no_features
|
||||||
12
substreams/ethereum-uniswap-v3-logs-only/build.rs
Normal file
12
substreams/ethereum-uniswap-v3-logs-only/build.rs
Normal file
@@ -0,0 +1,12 @@
|
|||||||
|
use anyhow::{Ok, Result};
|
||||||
|
use substreams_ethereum::Abigen;
|
||||||
|
|
||||||
|
fn main() -> Result<(), anyhow::Error> {
|
||||||
|
Abigen::new("Factory", "abi/Factory.json")?
|
||||||
|
.generate()?
|
||||||
|
.write_to_file("src/abi/factory.rs")?;
|
||||||
|
Abigen::new("Pool", "abi/Pool.json")?
|
||||||
|
.generate()?
|
||||||
|
.write_to_file("src/abi/pool.rs")?;
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
@@ -0,0 +1,125 @@
|
|||||||
|
specVersion: v0.1.0
|
||||||
|
package:
|
||||||
|
name: "ethereum_uniswap_v3_logs_only"
|
||||||
|
version: v0.1.0
|
||||||
|
|
||||||
|
protobuf:
|
||||||
|
files:
|
||||||
|
- tycho/evm/v1/entity.proto
|
||||||
|
- tycho/evm/v1/common.proto
|
||||||
|
- tycho/evm/v1/utils.proto
|
||||||
|
- uniswap.proto
|
||||||
|
importPaths:
|
||||||
|
- ./proto/v1
|
||||||
|
- ../../proto/
|
||||||
|
|
||||||
|
binaries:
|
||||||
|
default:
|
||||||
|
type: wasm/rust-v1
|
||||||
|
file: ../target/wasm32-unknown-unknown/release/ethereum_uniswap_v3_logs_only.wasm
|
||||||
|
|
||||||
|
modules:
|
||||||
|
- name: map_pools_created
|
||||||
|
kind: map
|
||||||
|
initialBlock: 12369621
|
||||||
|
inputs:
|
||||||
|
- params: string
|
||||||
|
- source: sf.ethereum.type.v2.Block
|
||||||
|
output:
|
||||||
|
type: proto:tycho.evm.v1.BlockEntityChanges
|
||||||
|
|
||||||
|
- name: store_pools
|
||||||
|
kind: store
|
||||||
|
initialBlock: 12369621
|
||||||
|
updatePolicy: set_if_not_exists
|
||||||
|
valueType: proto:uniswap.v3.Pool
|
||||||
|
inputs:
|
||||||
|
- map: map_pools_created
|
||||||
|
|
||||||
|
- name: map_events
|
||||||
|
kind: map
|
||||||
|
initialBlock: 12369621
|
||||||
|
inputs:
|
||||||
|
- source: sf.ethereum.type.v2.Block
|
||||||
|
- store: store_pools
|
||||||
|
output:
|
||||||
|
type: proto:uniswap.v3.Events
|
||||||
|
|
||||||
|
- name: map_balance_changes
|
||||||
|
kind: map
|
||||||
|
initialBlock: 12369621
|
||||||
|
inputs:
|
||||||
|
- map: map_events
|
||||||
|
output:
|
||||||
|
type: proto:tycho.evm.v1.BlockBalanceDeltas
|
||||||
|
|
||||||
|
- name: store_pools_balances
|
||||||
|
kind: store
|
||||||
|
initialBlock: 12369621
|
||||||
|
updatePolicy: add
|
||||||
|
valueType: bigint
|
||||||
|
inputs:
|
||||||
|
- map: map_balance_changes
|
||||||
|
|
||||||
|
- name: map_ticks_changes
|
||||||
|
kind: map
|
||||||
|
initialBlock: 12369621
|
||||||
|
inputs:
|
||||||
|
- map: map_events
|
||||||
|
output:
|
||||||
|
type: proto:uniswap.v3.TickDeltas
|
||||||
|
|
||||||
|
- name: store_ticks_liquidity
|
||||||
|
kind: store
|
||||||
|
initialBlock: 12369621
|
||||||
|
updatePolicy: add
|
||||||
|
valueType: bigint
|
||||||
|
inputs:
|
||||||
|
- map: map_ticks_changes
|
||||||
|
|
||||||
|
- name: store_pool_current_tick
|
||||||
|
kind: store
|
||||||
|
initialBlock: 12369621
|
||||||
|
updatePolicy: set
|
||||||
|
valueType: int64
|
||||||
|
inputs:
|
||||||
|
- map: map_events
|
||||||
|
|
||||||
|
- name: map_liquidity_changes
|
||||||
|
kind: map
|
||||||
|
initialBlock: 12369621
|
||||||
|
inputs:
|
||||||
|
- map: map_events
|
||||||
|
- store: store_pool_current_tick
|
||||||
|
output:
|
||||||
|
type: proto:uniswap.v3.LiquidityChanges
|
||||||
|
|
||||||
|
- name: store_liquidity
|
||||||
|
kind: store
|
||||||
|
initialBlock: 12369621
|
||||||
|
updatePolicy: set_sum
|
||||||
|
valueType: bigint
|
||||||
|
inputs:
|
||||||
|
- map: map_liquidity_changes
|
||||||
|
|
||||||
|
- name: map_protocol_changes
|
||||||
|
kind: map
|
||||||
|
initialBlock: 12369621
|
||||||
|
inputs:
|
||||||
|
- source: sf.ethereum.type.v2.Block
|
||||||
|
- map: map_pools_created
|
||||||
|
- map: map_events
|
||||||
|
- map: map_balance_changes
|
||||||
|
- store: store_pools_balances
|
||||||
|
mode: deltas
|
||||||
|
- map: map_ticks_changes
|
||||||
|
- store: store_ticks_liquidity
|
||||||
|
mode: deltas
|
||||||
|
- map: map_liquidity_changes
|
||||||
|
- store: store_liquidity
|
||||||
|
mode: deltas
|
||||||
|
output:
|
||||||
|
type: proto:tycho.evm.v1.BlockChanges
|
||||||
|
|
||||||
|
params:
|
||||||
|
map_pools_created: "1F98431c8aD98523631AE4a59f267346ea31F984"
|
||||||
177
substreams/ethereum-uniswap-v3-logs-only/proto/v1/uniswap.proto
Normal file
177
substreams/ethereum-uniswap-v3-logs-only/proto/v1/uniswap.proto
Normal file
@@ -0,0 +1,177 @@
|
|||||||
|
syntax = "proto3";
|
||||||
|
|
||||||
|
package uniswap.v3;
|
||||||
|
|
||||||
|
message Pool {
|
||||||
|
bytes address = 1;
|
||||||
|
bytes token0 = 2;
|
||||||
|
bytes token1 = 3;
|
||||||
|
bytes created_tx_hash = 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
// A struct describing a transaction.
|
||||||
|
message Transaction {
|
||||||
|
// The transaction hash.
|
||||||
|
bytes hash = 1;
|
||||||
|
// The sender of the transaction.
|
||||||
|
bytes from = 2;
|
||||||
|
// The receiver of the transaction.
|
||||||
|
bytes to = 3;
|
||||||
|
// The transactions index within the block.
|
||||||
|
uint64 index = 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
// A change to a pool's tick.
|
||||||
|
message TickDelta {
|
||||||
|
// The address of the pool.
|
||||||
|
bytes pool_address = 1;
|
||||||
|
// The index of the tick.
|
||||||
|
int32 tick_index = 2;
|
||||||
|
// The liquidity net delta of this tick. Bigint encoded as signed little endian bytes.
|
||||||
|
bytes liquidity_net_delta = 3;
|
||||||
|
// Used to determine the order of the balance changes. Necessary for the balance store.
|
||||||
|
uint64 ordinal = 4;
|
||||||
|
Transaction transaction = 5;
|
||||||
|
}
|
||||||
|
|
||||||
|
// A group of TickDelta
|
||||||
|
message TickDeltas {
|
||||||
|
repeated TickDelta deltas = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// A change to a pool's liquidity.
|
||||||
|
message LiquidityChange {
|
||||||
|
// The address of the pool.
|
||||||
|
bytes pool_address = 1;
|
||||||
|
// The liquidity changed amount. Bigint encoded as signed little endian bytes.
|
||||||
|
bytes value = 2;
|
||||||
|
// The type of update, can be absolute or delta.
|
||||||
|
LiquidityChangeType change_type = 3;
|
||||||
|
// Used to determine the order of the balance changes. Necessary for the balance store.
|
||||||
|
uint64 ordinal = 4;
|
||||||
|
Transaction transaction = 5;
|
||||||
|
}
|
||||||
|
|
||||||
|
// A group of LiquidityChange
|
||||||
|
message LiquidityChanges {
|
||||||
|
repeated LiquidityChange changes = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
enum LiquidityChangeType {
|
||||||
|
DELTA = 0;
|
||||||
|
ABSOLUTE = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Events {
|
||||||
|
repeated PoolEvent pool_events = 3;
|
||||||
|
|
||||||
|
message PoolEvent {
|
||||||
|
oneof type {
|
||||||
|
Initialize initialize = 1;
|
||||||
|
Mint mint = 2;
|
||||||
|
Collect collect = 3;
|
||||||
|
Burn burn = 4;
|
||||||
|
Swap swap = 5;
|
||||||
|
Flash flash = 6;
|
||||||
|
SetFeeProtocol set_fee_protocol = 7;
|
||||||
|
CollectProtocol collect_protocol = 8;
|
||||||
|
}
|
||||||
|
uint64 log_ordinal = 100;
|
||||||
|
string pool_address = 102;
|
||||||
|
string token0 = 103;
|
||||||
|
string token1 = 104;
|
||||||
|
Transaction transaction = 105;
|
||||||
|
|
||||||
|
message Initialize {
|
||||||
|
// Unsigned
|
||||||
|
string sqrt_price = 1;
|
||||||
|
int32 tick = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Mint {
|
||||||
|
string sender = 1;
|
||||||
|
string owner = 2;
|
||||||
|
// Signed
|
||||||
|
int32 tick_lower = 3;
|
||||||
|
// Signed
|
||||||
|
int32 tick_upper = 4;
|
||||||
|
// Unsigned
|
||||||
|
string amount = 5;
|
||||||
|
// Unsigned
|
||||||
|
string amount_0 = 6;
|
||||||
|
// Unsigned
|
||||||
|
string amount_1 = 7;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Collect {
|
||||||
|
string owner = 1;
|
||||||
|
string recipient = 2;
|
||||||
|
int32 tick_lower = 3;
|
||||||
|
int32 tick_upper = 4;
|
||||||
|
// Unsigned
|
||||||
|
string amount_0 = 5;
|
||||||
|
// Unsigned
|
||||||
|
string amount_1 = 6;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Burn {
|
||||||
|
string owner = 1;
|
||||||
|
int32 tick_lower = 2;
|
||||||
|
int32 tick_upper = 3;
|
||||||
|
// Unsigned
|
||||||
|
string amount = 4;
|
||||||
|
// Unsigned
|
||||||
|
string amount_0 = 5;
|
||||||
|
// Unsigned
|
||||||
|
string amount_1 = 6;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Swap {
|
||||||
|
string sender = 1;
|
||||||
|
string recipient = 2;
|
||||||
|
// Signed
|
||||||
|
string amount_0 = 3;
|
||||||
|
// Signed
|
||||||
|
string amount_1 = 4;
|
||||||
|
// Unsigned
|
||||||
|
string sqrt_price = 6;
|
||||||
|
// Unsigned
|
||||||
|
string liquidity = 7;
|
||||||
|
int32 tick = 8;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Flash {
|
||||||
|
string sender = 1;
|
||||||
|
string recipient = 2;
|
||||||
|
// Unsigned
|
||||||
|
string amount_0 = 3;
|
||||||
|
// Unsigned
|
||||||
|
string amount_1 = 4;
|
||||||
|
// Unsigned
|
||||||
|
string paid_0 = 5;
|
||||||
|
// Unsigned
|
||||||
|
string paid_1 = 6;
|
||||||
|
}
|
||||||
|
|
||||||
|
message SetFeeProtocol {
|
||||||
|
// Unsigned
|
||||||
|
uint64 fee_protocol_0_old = 1;
|
||||||
|
// Unsigned
|
||||||
|
uint64 fee_protocol_1_old = 2;
|
||||||
|
// Unsigned
|
||||||
|
uint64 fee_protocol_0_new = 3;
|
||||||
|
// Unsigned
|
||||||
|
uint64 fee_protocol_1_new = 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
message CollectProtocol {
|
||||||
|
string sender = 1;
|
||||||
|
string recipient = 2;
|
||||||
|
// Unsigned
|
||||||
|
string amount_0 = 3;
|
||||||
|
// Unsigned
|
||||||
|
string amount_1 = 4;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
1040
substreams/ethereum-uniswap-v3-logs-only/src/abi/factory.rs
Normal file
1040
substreams/ethereum-uniswap-v3-logs-only/src/abi/factory.rs
Normal file
File diff suppressed because it is too large
Load Diff
4
substreams/ethereum-uniswap-v3-logs-only/src/abi/mod.rs
Normal file
4
substreams/ethereum-uniswap-v3-logs-only/src/abi/mod.rs
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
#![allow(clippy::all, clippy::pedantic, clippy::nursery)]
|
||||||
|
|
||||||
|
pub mod factory;
|
||||||
|
pub mod pool;
|
||||||
5153
substreams/ethereum-uniswap-v3-logs-only/src/abi/pool.rs
Normal file
5153
substreams/ethereum-uniswap-v3-logs-only/src/abi/pool.rs
Normal file
File diff suppressed because it is too large
Load Diff
7
substreams/ethereum-uniswap-v3-logs-only/src/lib.rs
Normal file
7
substreams/ethereum-uniswap-v3-logs-only/src/lib.rs
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
#![allow(clippy::not_unsafe_ptr_arg_deref)]
|
||||||
|
|
||||||
|
mod abi;
|
||||||
|
mod modules;
|
||||||
|
mod pb;
|
||||||
|
|
||||||
|
pub use modules::*;
|
||||||
@@ -0,0 +1,114 @@
|
|||||||
|
use std::str::FromStr;
|
||||||
|
|
||||||
|
use ethabi::ethereum_types::Address;
|
||||||
|
use substreams::scalar::BigInt;
|
||||||
|
use substreams_ethereum::pb::eth::v2::{self as eth};
|
||||||
|
|
||||||
|
use substreams_helper::{event_handler::EventHandler, hex::Hexable};
|
||||||
|
|
||||||
|
use crate::abi::factory::events::PoolCreated;
|
||||||
|
|
||||||
|
use tycho_substreams::prelude::*;
|
||||||
|
|
||||||
|
#[substreams::handlers::map]
|
||||||
|
pub fn map_pools_created(
|
||||||
|
params: String,
|
||||||
|
block: eth::Block,
|
||||||
|
) -> Result<BlockEntityChanges, substreams::errors::Error> {
|
||||||
|
let mut new_pools: Vec<TransactionEntityChanges> = vec![];
|
||||||
|
let factory_address = params.as_str();
|
||||||
|
|
||||||
|
get_new_pools(&block, &mut new_pools, factory_address);
|
||||||
|
|
||||||
|
Ok(BlockEntityChanges { block: None, changes: new_pools })
|
||||||
|
}
|
||||||
|
|
||||||
|
// Extract new pools from PoolCreated events
|
||||||
|
fn get_new_pools(
|
||||||
|
block: ð::Block,
|
||||||
|
new_pools: &mut Vec<TransactionEntityChanges>,
|
||||||
|
factory_address: &str,
|
||||||
|
) {
|
||||||
|
// Extract new pools from PoolCreated events
|
||||||
|
let mut on_pool_created = |event: PoolCreated, _tx: ð::TransactionTrace, _log: ð::Log| {
|
||||||
|
let tycho_tx: Transaction = _tx.into();
|
||||||
|
|
||||||
|
new_pools.push(TransactionEntityChanges {
|
||||||
|
tx: Some(tycho_tx.clone()),
|
||||||
|
entity_changes: vec![EntityChanges {
|
||||||
|
component_id: event.pool.clone().to_hex(),
|
||||||
|
attributes: vec![
|
||||||
|
Attribute {
|
||||||
|
name: "liquidity".to_string(),
|
||||||
|
value: BigInt::from(0).to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Creation.into(),
|
||||||
|
},
|
||||||
|
Attribute {
|
||||||
|
name: "tick".to_string(),
|
||||||
|
value: BigInt::from(0).to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Creation.into(),
|
||||||
|
},
|
||||||
|
Attribute {
|
||||||
|
name: "sqrt_price_x96".to_string(),
|
||||||
|
value: BigInt::from(0).to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Creation.into(),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}],
|
||||||
|
component_changes: vec![ProtocolComponent {
|
||||||
|
id: event.pool.to_hex(),
|
||||||
|
tokens: vec![event.token0.clone(), event.token1.clone()],
|
||||||
|
contracts: vec![],
|
||||||
|
static_att: vec![
|
||||||
|
Attribute {
|
||||||
|
name: "fee".to_string(),
|
||||||
|
value: event.fee.to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Creation.into(),
|
||||||
|
},
|
||||||
|
Attribute {
|
||||||
|
name: "tick_spacing".to_string(),
|
||||||
|
value: event.tick_spacing.to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Creation.into(),
|
||||||
|
},
|
||||||
|
Attribute {
|
||||||
|
name: "pool_address".to_string(),
|
||||||
|
value: event.pool.clone(),
|
||||||
|
change: ChangeType::Creation.into(),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
change: i32::from(ChangeType::Creation),
|
||||||
|
protocol_type: Option::from(ProtocolType {
|
||||||
|
name: "uniswap_v3_pool".to_string(),
|
||||||
|
financial_type: FinancialType::Swap.into(),
|
||||||
|
attribute_schema: vec![],
|
||||||
|
implementation_type: ImplementationType::Custom.into(),
|
||||||
|
}),
|
||||||
|
tx: Some(tycho_tx),
|
||||||
|
}],
|
||||||
|
balance_changes: vec![
|
||||||
|
BalanceChange {
|
||||||
|
token: event.token0,
|
||||||
|
balance: BigInt::from(0).to_signed_bytes_be(),
|
||||||
|
component_id: event
|
||||||
|
.pool
|
||||||
|
.clone()
|
||||||
|
.to_hex()
|
||||||
|
.as_bytes()
|
||||||
|
.to_vec(),
|
||||||
|
},
|
||||||
|
BalanceChange {
|
||||||
|
token: event.token1,
|
||||||
|
balance: BigInt::from(0).to_signed_bytes_be(),
|
||||||
|
component_id: event.pool.to_hex().as_bytes().to_vec(),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
};
|
||||||
|
|
||||||
|
let mut eh = EventHandler::new(block);
|
||||||
|
|
||||||
|
eh.filter_by_address(vec![Address::from_str(factory_address).unwrap()]);
|
||||||
|
|
||||||
|
eh.on::<PoolCreated, _>(&mut on_pool_created);
|
||||||
|
eh.handle_events();
|
||||||
|
}
|
||||||
@@ -0,0 +1,24 @@
|
|||||||
|
use std::str;
|
||||||
|
|
||||||
|
use substreams::store::{StoreNew, StoreSetIfNotExists, StoreSetIfNotExistsProto};
|
||||||
|
use tycho_substreams::models::BlockEntityChanges;
|
||||||
|
|
||||||
|
use crate::pb::uniswap::v3::Pool;
|
||||||
|
|
||||||
|
#[substreams::handlers::store]
|
||||||
|
pub fn store_pools(pools_created: BlockEntityChanges, store: StoreSetIfNotExistsProto<Pool>) {
|
||||||
|
// Store pools. Required so the next maps can match any event to a known pool by their address
|
||||||
|
|
||||||
|
for change in pools_created.changes {
|
||||||
|
for component_change in &change.component_changes {
|
||||||
|
let pool_address: &str = &component_change.id;
|
||||||
|
let pool: Pool = Pool {
|
||||||
|
address: hex::decode(pool_address.trim_start_matches("0x")).unwrap(),
|
||||||
|
token0: component_change.tokens[0].clone(),
|
||||||
|
token1: component_change.tokens[1].clone(),
|
||||||
|
created_tx_hash: change.tx.as_ref().unwrap().hash.clone(),
|
||||||
|
};
|
||||||
|
store.set_if_not_exists(0, format!("{}:{}", "Pool", pool_address), &pool);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,183 @@
|
|||||||
|
use anyhow::Ok;
|
||||||
|
use substreams::{
|
||||||
|
store::{StoreGet, StoreGetProto},
|
||||||
|
Hex,
|
||||||
|
};
|
||||||
|
use substreams_ethereum::{
|
||||||
|
pb::eth::v2::{self as eth, Log, TransactionTrace},
|
||||||
|
Event,
|
||||||
|
};
|
||||||
|
use substreams_helper::hex::Hexable;
|
||||||
|
|
||||||
|
use crate::{
|
||||||
|
abi::pool::events::{
|
||||||
|
Burn, Collect, CollectProtocol, Flash, Initialize, Mint, SetFeeProtocol, Swap,
|
||||||
|
},
|
||||||
|
pb::uniswap::v3::{
|
||||||
|
events::{
|
||||||
|
pool_event::{self, Type},
|
||||||
|
PoolEvent,
|
||||||
|
},
|
||||||
|
Events, Pool,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
#[substreams::handlers::map]
|
||||||
|
pub fn map_events(
|
||||||
|
block: eth::Block,
|
||||||
|
pools_store: StoreGetProto<Pool>,
|
||||||
|
) -> Result<Events, anyhow::Error> {
|
||||||
|
let mut pool_events = block
|
||||||
|
.transaction_traces
|
||||||
|
.into_iter()
|
||||||
|
.filter(|tx| tx.status == 1)
|
||||||
|
.flat_map(|tx| {
|
||||||
|
tx.clone()
|
||||||
|
.receipt
|
||||||
|
.into_iter()
|
||||||
|
.flat_map(|receipt| receipt.logs)
|
||||||
|
.filter_map(|log| {
|
||||||
|
let key = format!("{}:{}", "Pool", log.address.to_hex());
|
||||||
|
// Skip if the log is not from a known uniswapV3 pool.
|
||||||
|
if let Some(pool) = pools_store.get_last(key) {
|
||||||
|
log_to_event(&log, pool, tx.clone())
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.collect::<Vec<_>>()
|
||||||
|
})
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
|
pool_events.sort_unstable_by_key(|e| e.log_ordinal);
|
||||||
|
|
||||||
|
Ok(Events { pool_events })
|
||||||
|
}
|
||||||
|
|
||||||
|
fn log_to_event(event: &Log, pool: Pool, tx: TransactionTrace) -> Option<PoolEvent> {
|
||||||
|
if let Some(init) = Initialize::match_and_decode(event) {
|
||||||
|
Some(PoolEvent {
|
||||||
|
log_ordinal: event.ordinal,
|
||||||
|
pool_address: Hex(pool.address).to_string(),
|
||||||
|
token0: Hex(pool.token0).to_string(),
|
||||||
|
token1: Hex(pool.token1).to_string(),
|
||||||
|
transaction: Some(tx.into()),
|
||||||
|
r#type: Some(Type::Initialize(pool_event::Initialize {
|
||||||
|
sqrt_price: init.sqrt_price_x96.to_string(),
|
||||||
|
tick: init.tick.into(),
|
||||||
|
})),
|
||||||
|
})
|
||||||
|
} else if let Some(swap) = Swap::match_and_decode(event) {
|
||||||
|
Some(PoolEvent {
|
||||||
|
log_ordinal: event.ordinal,
|
||||||
|
pool_address: Hex(pool.address).to_string(),
|
||||||
|
token0: Hex(pool.token0).to_string(),
|
||||||
|
token1: Hex(pool.token1).to_string(),
|
||||||
|
transaction: Some(tx.into()),
|
||||||
|
r#type: Some(Type::Swap(pool_event::Swap {
|
||||||
|
sender: Hex(swap.sender).to_string(),
|
||||||
|
recipient: Hex(swap.recipient).to_string(),
|
||||||
|
amount_0: swap.amount0.to_string(),
|
||||||
|
amount_1: swap.amount1.to_string(),
|
||||||
|
sqrt_price: swap.sqrt_price_x96.to_string(),
|
||||||
|
liquidity: swap.liquidity.to_string(),
|
||||||
|
tick: swap.tick.into(),
|
||||||
|
})),
|
||||||
|
})
|
||||||
|
} else if let Some(flash) = Flash::match_and_decode(event) {
|
||||||
|
Some(PoolEvent {
|
||||||
|
log_ordinal: event.ordinal,
|
||||||
|
pool_address: Hex(pool.address).to_string(),
|
||||||
|
token0: Hex(pool.token0).to_string(),
|
||||||
|
token1: Hex(pool.token1).to_string(),
|
||||||
|
transaction: Some(tx.into()),
|
||||||
|
r#type: Some(Type::Flash(pool_event::Flash {
|
||||||
|
sender: Hex(flash.sender).to_string(),
|
||||||
|
recipient: Hex(flash.recipient).to_string(),
|
||||||
|
amount_0: flash.amount0.to_string(),
|
||||||
|
amount_1: flash.amount1.to_string(),
|
||||||
|
paid_0: flash.paid0.to_string(),
|
||||||
|
paid_1: flash.paid1.to_string(),
|
||||||
|
})),
|
||||||
|
})
|
||||||
|
} else if let Some(mint) = Mint::match_and_decode(event) {
|
||||||
|
Some(PoolEvent {
|
||||||
|
log_ordinal: event.ordinal,
|
||||||
|
pool_address: Hex(pool.address).to_string(),
|
||||||
|
token0: Hex(pool.token0).to_string(),
|
||||||
|
token1: Hex(pool.token1).to_string(),
|
||||||
|
transaction: Some(tx.into()),
|
||||||
|
r#type: Some(Type::Mint(pool_event::Mint {
|
||||||
|
sender: Hex(mint.sender).to_string(),
|
||||||
|
owner: Hex(mint.owner).to_string(),
|
||||||
|
tick_lower: mint.tick_lower.into(),
|
||||||
|
tick_upper: mint.tick_upper.into(),
|
||||||
|
amount: mint.amount.to_string(),
|
||||||
|
amount_0: mint.amount0.to_string(),
|
||||||
|
amount_1: mint.amount1.to_string(),
|
||||||
|
})),
|
||||||
|
})
|
||||||
|
} else if let Some(burn) = Burn::match_and_decode(event) {
|
||||||
|
Some(PoolEvent {
|
||||||
|
log_ordinal: event.ordinal,
|
||||||
|
pool_address: Hex(pool.address).to_string(),
|
||||||
|
token0: Hex(pool.token0).to_string(),
|
||||||
|
token1: Hex(pool.token1).to_string(),
|
||||||
|
transaction: Some(tx.into()),
|
||||||
|
r#type: Some(Type::Burn(pool_event::Burn {
|
||||||
|
owner: Hex(burn.owner).to_string(),
|
||||||
|
tick_lower: burn.tick_lower.into(),
|
||||||
|
tick_upper: burn.tick_upper.into(),
|
||||||
|
amount: burn.amount.to_string(),
|
||||||
|
amount_0: burn.amount0.to_string(),
|
||||||
|
amount_1: burn.amount1.to_string(),
|
||||||
|
})),
|
||||||
|
})
|
||||||
|
} else if let Some(collect) = Collect::match_and_decode(event) {
|
||||||
|
Some(PoolEvent {
|
||||||
|
log_ordinal: event.ordinal,
|
||||||
|
pool_address: Hex(pool.address).to_string(),
|
||||||
|
token0: Hex(pool.token0).to_string(),
|
||||||
|
token1: Hex(pool.token1).to_string(),
|
||||||
|
transaction: Some(tx.into()),
|
||||||
|
r#type: Some(Type::Collect(pool_event::Collect {
|
||||||
|
owner: Hex(collect.owner).to_string(),
|
||||||
|
recipient: Hex(collect.recipient).to_string(),
|
||||||
|
tick_lower: collect.tick_lower.into(),
|
||||||
|
tick_upper: collect.tick_upper.into(),
|
||||||
|
amount_0: collect.amount0.to_string(),
|
||||||
|
amount_1: collect.amount1.to_string(),
|
||||||
|
})),
|
||||||
|
})
|
||||||
|
} else if let Some(set_fp) = SetFeeProtocol::match_and_decode(event) {
|
||||||
|
Some(PoolEvent {
|
||||||
|
log_ordinal: event.ordinal,
|
||||||
|
pool_address: Hex(pool.address).to_string(),
|
||||||
|
token0: Hex(pool.token0).to_string(),
|
||||||
|
token1: Hex(pool.token1).to_string(),
|
||||||
|
transaction: Some(tx.into()),
|
||||||
|
r#type: Some(Type::SetFeeProtocol(pool_event::SetFeeProtocol {
|
||||||
|
fee_protocol_0_old: set_fp.fee_protocol0_old.to_u64(),
|
||||||
|
fee_protocol_1_old: set_fp.fee_protocol1_old.to_u64(),
|
||||||
|
fee_protocol_0_new: set_fp.fee_protocol0_new.to_u64(),
|
||||||
|
fee_protocol_1_new: set_fp.fee_protocol1_new.to_u64(),
|
||||||
|
})),
|
||||||
|
})
|
||||||
|
} else if let Some(cp) = CollectProtocol::match_and_decode(event) {
|
||||||
|
Some(PoolEvent {
|
||||||
|
log_ordinal: event.ordinal,
|
||||||
|
pool_address: Hex(pool.address).to_string(),
|
||||||
|
token0: Hex(pool.token0).to_string(),
|
||||||
|
token1: Hex(pool.token1).to_string(),
|
||||||
|
transaction: Some(tx.into()),
|
||||||
|
r#type: Some(Type::CollectProtocol(pool_event::CollectProtocol {
|
||||||
|
sender: Hex(cp.sender).to_string(),
|
||||||
|
recipient: Hex(cp.recipient).to_string(),
|
||||||
|
amount_0: cp.amount0.to_string(),
|
||||||
|
amount_1: cp.amount1.to_string(),
|
||||||
|
})),
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,175 @@
|
|||||||
|
use std::str::FromStr;
|
||||||
|
|
||||||
|
use anyhow::Ok;
|
||||||
|
use tycho_substreams::models::{BalanceDelta, BlockBalanceDeltas};
|
||||||
|
|
||||||
|
use crate::pb::uniswap::v3::{
|
||||||
|
events::{pool_event, PoolEvent},
|
||||||
|
Events,
|
||||||
|
};
|
||||||
|
use substreams::{
|
||||||
|
scalar::BigInt,
|
||||||
|
store::{StoreAddBigInt, StoreNew},
|
||||||
|
};
|
||||||
|
|
||||||
|
#[substreams::handlers::map]
|
||||||
|
pub fn map_balance_changes(events: Events) -> Result<BlockBalanceDeltas, anyhow::Error> {
|
||||||
|
let balance_deltas = events
|
||||||
|
.pool_events
|
||||||
|
.into_iter()
|
||||||
|
.flat_map(event_to_balance_deltas)
|
||||||
|
.collect();
|
||||||
|
|
||||||
|
Ok(BlockBalanceDeltas { balance_deltas })
|
||||||
|
}
|
||||||
|
|
||||||
|
#[substreams::handlers::store]
|
||||||
|
pub fn store_pools_balances(balances_deltas: BlockBalanceDeltas, store: StoreAddBigInt) {
|
||||||
|
tycho_substreams::balances::store_balance_changes(balances_deltas, store);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn event_to_balance_deltas(event: PoolEvent) -> Vec<BalanceDelta> {
|
||||||
|
let address = format!("0x{}", event.pool_address)
|
||||||
|
.as_bytes()
|
||||||
|
.to_vec();
|
||||||
|
match event.r#type.unwrap() {
|
||||||
|
pool_event::Type::Mint(e) => vec![
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token0.clone()).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.amount_0)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: address.clone(),
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event
|
||||||
|
.transaction
|
||||||
|
.clone()
|
||||||
|
.map(Into::into),
|
||||||
|
},
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token1.clone()).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.amount_1)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: address,
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event.transaction.map(Into::into),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
pool_event::Type::Collect(e) => vec![
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token0.clone()).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.amount_0)
|
||||||
|
.unwrap()
|
||||||
|
.neg()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: address.clone(),
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event
|
||||||
|
.transaction
|
||||||
|
.clone()
|
||||||
|
.map(Into::into),
|
||||||
|
},
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token1.clone()).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.amount_1)
|
||||||
|
.unwrap()
|
||||||
|
.neg()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: address,
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event.transaction.map(Into::into),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
//Burn balance changes are accounted for in the Collect event.
|
||||||
|
pool_event::Type::Burn(_) => vec![],
|
||||||
|
pool_event::Type::Swap(e) => {
|
||||||
|
vec![
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token0.clone()).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.amount_0)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: address.clone(),
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event
|
||||||
|
.transaction
|
||||||
|
.clone()
|
||||||
|
.map(Into::into),
|
||||||
|
},
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token1.clone()).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.amount_1)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: address.clone(),
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event.transaction.map(Into::into),
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
|
pool_event::Type::Flash(e) => vec![
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token0).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.paid_0)
|
||||||
|
.unwrap()
|
||||||
|
.clone()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: address.clone(),
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event
|
||||||
|
.transaction
|
||||||
|
.clone()
|
||||||
|
.map(Into::into),
|
||||||
|
},
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token1).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.paid_1)
|
||||||
|
.unwrap()
|
||||||
|
.clone()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: address,
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event.transaction.map(Into::into),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
pool_event::Type::CollectProtocol(e) => {
|
||||||
|
vec![
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token0).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.amount_0)
|
||||||
|
.unwrap()
|
||||||
|
.neg()
|
||||||
|
.clone()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: event
|
||||||
|
.pool_address
|
||||||
|
.clone()
|
||||||
|
.as_bytes()
|
||||||
|
.to_vec(),
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event
|
||||||
|
.transaction
|
||||||
|
.clone()
|
||||||
|
.map(Into::into),
|
||||||
|
},
|
||||||
|
BalanceDelta {
|
||||||
|
token: hex::decode(event.token1).unwrap(),
|
||||||
|
delta: BigInt::from_str(&e.amount_1)
|
||||||
|
.unwrap()
|
||||||
|
.clone()
|
||||||
|
.neg()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
component_id: event
|
||||||
|
.pool_address
|
||||||
|
.clone()
|
||||||
|
.as_bytes()
|
||||||
|
.to_vec(),
|
||||||
|
ord: event.log_ordinal,
|
||||||
|
tx: event.transaction.map(Into::into),
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
|
_ => vec![],
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,137 @@
|
|||||||
|
use std::str::FromStr;
|
||||||
|
|
||||||
|
use substreams::store::{
|
||||||
|
StoreGet, StoreGetInt64, StoreSet, StoreSetInt64, StoreSetSum, StoreSetSumBigInt,
|
||||||
|
};
|
||||||
|
|
||||||
|
use crate::pb::uniswap::v3::{
|
||||||
|
events::{pool_event, PoolEvent},
|
||||||
|
Events, LiquidityChange, LiquidityChangeType, LiquidityChanges,
|
||||||
|
};
|
||||||
|
|
||||||
|
use substreams::{scalar::BigInt, store::StoreNew};
|
||||||
|
|
||||||
|
use anyhow::Ok;
|
||||||
|
|
||||||
|
#[substreams::handlers::store]
|
||||||
|
pub fn store_pool_current_tick(events: Events, store: StoreSetInt64) {
|
||||||
|
events
|
||||||
|
.pool_events
|
||||||
|
.into_iter()
|
||||||
|
.filter_map(event_to_current_tick)
|
||||||
|
.for_each(|(pool, ordinal, new_tick_index)| {
|
||||||
|
store.set(ordinal, format!("pool:{0}", pool), &new_tick_index.into())
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
#[substreams::handlers::map]
|
||||||
|
pub fn map_liquidity_changes(
|
||||||
|
events: Events,
|
||||||
|
pools_current_tick_store: StoreGetInt64,
|
||||||
|
) -> Result<LiquidityChanges, anyhow::Error> {
|
||||||
|
let mut changes = events
|
||||||
|
.pool_events
|
||||||
|
.into_iter()
|
||||||
|
.filter(PoolEvent::can_introduce_liquidity_changes)
|
||||||
|
.map(|e| {
|
||||||
|
(
|
||||||
|
pools_current_tick_store
|
||||||
|
.get_at(e.log_ordinal, format!("pool:{0}", &e.pool_address))
|
||||||
|
.unwrap_or(0),
|
||||||
|
e,
|
||||||
|
)
|
||||||
|
})
|
||||||
|
.filter_map(|(current_tick, event)| event_to_liquidity_deltas(current_tick, event))
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
|
changes.sort_unstable_by_key(|l| l.ordinal);
|
||||||
|
Ok(LiquidityChanges { changes })
|
||||||
|
}
|
||||||
|
|
||||||
|
#[substreams::handlers::store]
|
||||||
|
pub fn store_liquidity(ticks_deltas: LiquidityChanges, store: StoreSetSumBigInt) {
|
||||||
|
ticks_deltas
|
||||||
|
.changes
|
||||||
|
.iter()
|
||||||
|
.for_each(|changes| match changes.change_type() {
|
||||||
|
LiquidityChangeType::Delta => {
|
||||||
|
store.sum(
|
||||||
|
changes.ordinal,
|
||||||
|
format!("pool:{0}", hex::encode(&changes.pool_address)),
|
||||||
|
BigInt::from_signed_bytes_be(&changes.value),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
LiquidityChangeType::Absolute => {
|
||||||
|
store.set(
|
||||||
|
changes.ordinal,
|
||||||
|
format!("pool:{0}", hex::encode(&changes.pool_address)),
|
||||||
|
BigInt::from_signed_bytes_be(&changes.value),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
fn event_to_liquidity_deltas(current_tick: i64, event: PoolEvent) -> Option<LiquidityChange> {
|
||||||
|
match event.r#type.as_ref().unwrap() {
|
||||||
|
pool_event::Type::Mint(mint) => {
|
||||||
|
if current_tick >= mint.tick_lower.into() && current_tick < mint.tick_upper.into() {
|
||||||
|
Some(LiquidityChange {
|
||||||
|
pool_address: hex::decode(event.pool_address).unwrap(),
|
||||||
|
value: BigInt::from_str(&mint.amount)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
change_type: LiquidityChangeType::Delta.into(),
|
||||||
|
ordinal: event.log_ordinal,
|
||||||
|
transaction: Some(event.transaction.unwrap()),
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
pool_event::Type::Burn(burn) => {
|
||||||
|
if current_tick >= burn.tick_lower.into() && current_tick < burn.tick_upper.into() {
|
||||||
|
Some(LiquidityChange {
|
||||||
|
pool_address: hex::decode(event.pool_address).unwrap(),
|
||||||
|
value: BigInt::from_str(&burn.amount)
|
||||||
|
.unwrap()
|
||||||
|
.neg()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
change_type: LiquidityChangeType::Delta.into(),
|
||||||
|
ordinal: event.log_ordinal,
|
||||||
|
transaction: Some(event.transaction.unwrap()),
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
pool_event::Type::Swap(swap) => Some(LiquidityChange {
|
||||||
|
pool_address: hex::decode(event.pool_address).unwrap(),
|
||||||
|
value: BigInt::from_str(&swap.liquidity)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
change_type: LiquidityChangeType::Absolute.into(),
|
||||||
|
ordinal: event.log_ordinal,
|
||||||
|
transaction: Some(event.transaction.unwrap()),
|
||||||
|
}),
|
||||||
|
_ => None,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl PoolEvent {
|
||||||
|
fn can_introduce_liquidity_changes(&self) -> bool {
|
||||||
|
matches!(
|
||||||
|
self.r#type.as_ref().unwrap(),
|
||||||
|
pool_event::Type::Mint(_) | pool_event::Type::Burn(_) | pool_event::Type::Swap(_)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn event_to_current_tick(event: PoolEvent) -> Option<(String, u64, i32)> {
|
||||||
|
match event.r#type.as_ref().unwrap() {
|
||||||
|
pool_event::Type::Initialize(initialize) => {
|
||||||
|
Some((event.pool_address, event.log_ordinal, initialize.tick))
|
||||||
|
}
|
||||||
|
pool_event::Type::Swap(swap) => Some((event.pool_address, event.log_ordinal, swap.tick)),
|
||||||
|
_ => None,
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,91 @@
|
|||||||
|
use std::str::FromStr;
|
||||||
|
|
||||||
|
use substreams::store::StoreAddBigInt;
|
||||||
|
|
||||||
|
use crate::pb::uniswap::v3::{
|
||||||
|
events::{pool_event, PoolEvent},
|
||||||
|
Events, TickDelta, TickDeltas,
|
||||||
|
};
|
||||||
|
|
||||||
|
use substreams::{
|
||||||
|
scalar::BigInt,
|
||||||
|
store::{StoreAdd, StoreNew},
|
||||||
|
};
|
||||||
|
|
||||||
|
use anyhow::Ok;
|
||||||
|
|
||||||
|
#[substreams::handlers::map]
|
||||||
|
pub fn map_ticks_changes(events: Events) -> Result<TickDeltas, anyhow::Error> {
|
||||||
|
let ticks_deltas = events
|
||||||
|
.pool_events
|
||||||
|
.into_iter()
|
||||||
|
.flat_map(event_to_ticks_deltas)
|
||||||
|
.collect();
|
||||||
|
|
||||||
|
Ok(TickDeltas { deltas: ticks_deltas })
|
||||||
|
}
|
||||||
|
|
||||||
|
#[substreams::handlers::store]
|
||||||
|
pub fn store_ticks_liquidity(ticks_deltas: TickDeltas, store: StoreAddBigInt) {
|
||||||
|
let mut deltas = ticks_deltas.deltas.clone();
|
||||||
|
|
||||||
|
deltas.sort_unstable_by_key(|delta| delta.ordinal);
|
||||||
|
|
||||||
|
deltas.iter().for_each(|delta| {
|
||||||
|
store.add(
|
||||||
|
delta.ordinal,
|
||||||
|
format!("pool:{0}:tick:{1}", hex::encode(&delta.pool_address), delta.tick_index,),
|
||||||
|
BigInt::from_signed_bytes_be(&delta.liquidity_net_delta),
|
||||||
|
);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
fn event_to_ticks_deltas(event: PoolEvent) -> Vec<TickDelta> {
|
||||||
|
match event.r#type.as_ref().unwrap() {
|
||||||
|
pool_event::Type::Mint(mint) => {
|
||||||
|
vec![
|
||||||
|
TickDelta {
|
||||||
|
pool_address: hex::decode(&event.pool_address).unwrap(),
|
||||||
|
tick_index: mint.tick_lower,
|
||||||
|
liquidity_net_delta: BigInt::from_str(&mint.amount)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
ordinal: event.log_ordinal,
|
||||||
|
transaction: event.transaction.clone(),
|
||||||
|
},
|
||||||
|
TickDelta {
|
||||||
|
pool_address: hex::decode(&event.pool_address).unwrap(),
|
||||||
|
tick_index: mint.tick_upper,
|
||||||
|
liquidity_net_delta: BigInt::from_str(&mint.amount)
|
||||||
|
.unwrap()
|
||||||
|
.neg()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
ordinal: event.log_ordinal,
|
||||||
|
transaction: event.transaction,
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
|
pool_event::Type::Burn(burn) => vec![
|
||||||
|
TickDelta {
|
||||||
|
pool_address: hex::decode(&event.pool_address).unwrap(),
|
||||||
|
tick_index: burn.tick_lower,
|
||||||
|
liquidity_net_delta: BigInt::from_str(&burn.amount)
|
||||||
|
.unwrap()
|
||||||
|
.neg()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
ordinal: event.log_ordinal,
|
||||||
|
transaction: event.transaction.clone(),
|
||||||
|
},
|
||||||
|
TickDelta {
|
||||||
|
pool_address: hex::decode(&event.pool_address).unwrap(),
|
||||||
|
tick_index: burn.tick_upper,
|
||||||
|
liquidity_net_delta: BigInt::from_str(&burn.amount)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
ordinal: event.log_ordinal,
|
||||||
|
transaction: event.transaction,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
_ => vec![],
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,248 @@
|
|||||||
|
use crate::pb::uniswap::v3::{
|
||||||
|
events::{pool_event, PoolEvent},
|
||||||
|
Events, LiquidityChanges, TickDeltas,
|
||||||
|
};
|
||||||
|
use itertools::Itertools;
|
||||||
|
use std::{collections::HashMap, str::FromStr, vec};
|
||||||
|
use substreams::{pb::substreams::StoreDeltas, scalar::BigInt};
|
||||||
|
use substreams_ethereum::pb::eth::v2::{self as eth};
|
||||||
|
use substreams_helper::hex::Hexable;
|
||||||
|
use tycho_substreams::{balances::aggregate_balances_changes, prelude::*};
|
||||||
|
|
||||||
|
type PoolAddress = Vec<u8>;
|
||||||
|
|
||||||
|
#[substreams::handlers::map]
|
||||||
|
pub fn map_protocol_changes(
|
||||||
|
block: eth::Block,
|
||||||
|
created_pools: BlockEntityChanges,
|
||||||
|
events: Events,
|
||||||
|
balances_map_deltas: BlockBalanceDeltas,
|
||||||
|
balances_store_deltas: StoreDeltas,
|
||||||
|
ticks_map_deltas: TickDeltas,
|
||||||
|
ticks_store_deltas: StoreDeltas,
|
||||||
|
pool_liquidity_changes: LiquidityChanges,
|
||||||
|
pool_liquidity_store_deltas: StoreDeltas,
|
||||||
|
) -> Result<BlockChanges, substreams::errors::Error> {
|
||||||
|
// We merge contract changes by transaction (identified by transaction index) making it easy to
|
||||||
|
// sort them at the very end.
|
||||||
|
let mut transaction_changes: HashMap<_, TransactionChangesBuilder> = HashMap::new();
|
||||||
|
|
||||||
|
// Add created pools to the tx_changes_map
|
||||||
|
for change in created_pools.changes.into_iter() {
|
||||||
|
let tx = change.tx.as_ref().unwrap();
|
||||||
|
let builder = transaction_changes
|
||||||
|
.entry(tx.index)
|
||||||
|
.or_insert_with(|| TransactionChangesBuilder::new(tx));
|
||||||
|
change
|
||||||
|
.component_changes
|
||||||
|
.iter()
|
||||||
|
.for_each(|c| {
|
||||||
|
builder.add_protocol_component(c);
|
||||||
|
});
|
||||||
|
change
|
||||||
|
.entity_changes
|
||||||
|
.iter()
|
||||||
|
.for_each(|ec| {
|
||||||
|
builder.add_entity_change(ec);
|
||||||
|
});
|
||||||
|
change
|
||||||
|
.balance_changes
|
||||||
|
.iter()
|
||||||
|
.for_each(|bc| {
|
||||||
|
builder.add_balance_change(bc);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Balance changes are gathered by the `StoreDelta` based on `PoolBalanceChanged` creating
|
||||||
|
// `BlockBalanceDeltas`. We essentially just process the changes that occurred to the `store`
|
||||||
|
// this block. Then, these balance changes are merged onto the existing map of tx contract
|
||||||
|
// changes, inserting a new one if it doesn't exist.
|
||||||
|
aggregate_balances_changes(balances_store_deltas, balances_map_deltas)
|
||||||
|
.into_iter()
|
||||||
|
.for_each(|(_, (tx, balances))| {
|
||||||
|
let builder = transaction_changes
|
||||||
|
.entry(tx.index)
|
||||||
|
.or_insert_with(|| TransactionChangesBuilder::new(&tx));
|
||||||
|
balances
|
||||||
|
.values()
|
||||||
|
.for_each(|token_bc_map| {
|
||||||
|
token_bc_map
|
||||||
|
.values()
|
||||||
|
.for_each(|bc| builder.add_balance_change(bc))
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// Insert ticks net-liquidity changes
|
||||||
|
ticks_store_deltas
|
||||||
|
.deltas
|
||||||
|
.into_iter()
|
||||||
|
.zip(ticks_map_deltas.deltas)
|
||||||
|
.for_each(|(store_delta, tick_delta)| {
|
||||||
|
let new_value_bigint =
|
||||||
|
BigInt::from_str(&String::from_utf8(store_delta.new_value).unwrap()).unwrap();
|
||||||
|
|
||||||
|
// If old value is empty or the int value is 0, it's considered as a creation.
|
||||||
|
let is_creation = store_delta.old_value.is_empty() ||
|
||||||
|
BigInt::from_str(&String::from_utf8(store_delta.old_value).unwrap())
|
||||||
|
.unwrap()
|
||||||
|
.is_zero();
|
||||||
|
let attribute_name = format!("ticks/{}/net-liquidity", tick_delta.tick_index);
|
||||||
|
let attribute = Attribute {
|
||||||
|
name: attribute_name,
|
||||||
|
value: new_value_bigint.to_signed_bytes_be(),
|
||||||
|
change: if is_creation {
|
||||||
|
ChangeType::Creation.into()
|
||||||
|
} else if new_value_bigint.is_zero() {
|
||||||
|
ChangeType::Deletion.into()
|
||||||
|
} else {
|
||||||
|
ChangeType::Update.into()
|
||||||
|
},
|
||||||
|
};
|
||||||
|
let tx = tick_delta.transaction.unwrap();
|
||||||
|
let builder = transaction_changes
|
||||||
|
.entry(tx.index)
|
||||||
|
.or_insert_with(|| TransactionChangesBuilder::new(&tx.into()));
|
||||||
|
|
||||||
|
builder.add_entity_change(&EntityChanges {
|
||||||
|
component_id: tick_delta.pool_address.to_hex(),
|
||||||
|
attributes: vec![attribute],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// Insert liquidity changes
|
||||||
|
pool_liquidity_store_deltas
|
||||||
|
.deltas
|
||||||
|
.into_iter()
|
||||||
|
.zip(pool_liquidity_changes.changes)
|
||||||
|
.for_each(|(store_delta, change)| {
|
||||||
|
let new_value_bigint = BigInt::from_str(
|
||||||
|
String::from_utf8(store_delta.new_value)
|
||||||
|
.unwrap()
|
||||||
|
.split(':')
|
||||||
|
.nth(1)
|
||||||
|
.unwrap(),
|
||||||
|
)
|
||||||
|
.unwrap();
|
||||||
|
let tx = change.transaction.unwrap();
|
||||||
|
let builder = transaction_changes
|
||||||
|
.entry(tx.index)
|
||||||
|
.or_insert_with(|| TransactionChangesBuilder::new(&tx.into()));
|
||||||
|
|
||||||
|
builder.add_entity_change(&EntityChanges {
|
||||||
|
component_id: change.pool_address.to_hex(),
|
||||||
|
attributes: vec![Attribute {
|
||||||
|
name: "liquidity".to_string(),
|
||||||
|
value: new_value_bigint.to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Update.into(),
|
||||||
|
}],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// Insert others changes
|
||||||
|
events
|
||||||
|
.pool_events
|
||||||
|
.into_iter()
|
||||||
|
.flat_map(event_to_attributes_updates)
|
||||||
|
.for_each(|(tx, pool_address, attr)| {
|
||||||
|
let builder = transaction_changes
|
||||||
|
.entry(tx.index)
|
||||||
|
.or_insert_with(|| TransactionChangesBuilder::new(&tx));
|
||||||
|
builder.add_entity_change(&EntityChanges {
|
||||||
|
component_id: pool_address.to_hex(),
|
||||||
|
attributes: vec![attr],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
Ok(BlockChanges {
|
||||||
|
block: Some((&block).into()),
|
||||||
|
changes: transaction_changes
|
||||||
|
.drain()
|
||||||
|
.sorted_unstable_by_key(|(index, _)| *index)
|
||||||
|
.filter_map(|(_, builder)| builder.build())
|
||||||
|
.collect::<Vec<_>>(),
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
fn event_to_attributes_updates(event: PoolEvent) -> Vec<(Transaction, PoolAddress, Attribute)> {
|
||||||
|
match event.r#type.as_ref().unwrap() {
|
||||||
|
pool_event::Type::Initialize(initalize) => {
|
||||||
|
vec![
|
||||||
|
(
|
||||||
|
event
|
||||||
|
.transaction
|
||||||
|
.clone()
|
||||||
|
.unwrap()
|
||||||
|
.into(),
|
||||||
|
hex::decode(event.pool_address.clone()).unwrap(),
|
||||||
|
Attribute {
|
||||||
|
name: "sqrt_price_x96".to_string(),
|
||||||
|
value: BigInt::from_str(&initalize.sqrt_price)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Update.into(),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
(
|
||||||
|
event.transaction.unwrap().into(),
|
||||||
|
hex::decode(event.pool_address).unwrap(),
|
||||||
|
Attribute {
|
||||||
|
name: "tick".to_string(),
|
||||||
|
value: BigInt::from(initalize.tick).to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Update.into(),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
]
|
||||||
|
}
|
||||||
|
pool_event::Type::Swap(swap) => vec![
|
||||||
|
(
|
||||||
|
event
|
||||||
|
.transaction
|
||||||
|
.clone()
|
||||||
|
.unwrap()
|
||||||
|
.into(),
|
||||||
|
hex::decode(event.pool_address.clone()).unwrap(),
|
||||||
|
Attribute {
|
||||||
|
name: "sqrt_price_x96".to_string(),
|
||||||
|
value: BigInt::from_str(&swap.sqrt_price)
|
||||||
|
.unwrap()
|
||||||
|
.to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Update.into(),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
(
|
||||||
|
event.transaction.unwrap().into(),
|
||||||
|
hex::decode(event.pool_address).unwrap(),
|
||||||
|
Attribute {
|
||||||
|
name: "tick".to_string(),
|
||||||
|
value: BigInt::from(swap.tick).to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Update.into(),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
pool_event::Type::SetFeeProtocol(sfp) => vec![
|
||||||
|
(
|
||||||
|
event
|
||||||
|
.transaction
|
||||||
|
.clone()
|
||||||
|
.unwrap()
|
||||||
|
.into(),
|
||||||
|
hex::decode(event.pool_address.clone()).unwrap(),
|
||||||
|
Attribute {
|
||||||
|
name: "protocol_fees/token0".to_string(),
|
||||||
|
value: BigInt::from(sfp.fee_protocol_0_new).to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Update.into(),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
(
|
||||||
|
event.transaction.unwrap().into(),
|
||||||
|
hex::decode(event.pool_address).unwrap(),
|
||||||
|
Attribute {
|
||||||
|
name: "protocol_fees/token1".to_string(),
|
||||||
|
value: BigInt::from(sfp.fee_protocol_1_new).to_signed_bytes_be(),
|
||||||
|
change: ChangeType::Update.into(),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
_ => vec![],
|
||||||
|
}
|
||||||
|
}
|
||||||
39
substreams/ethereum-uniswap-v3-logs-only/src/modules/mod.rs
Normal file
39
substreams/ethereum-uniswap-v3-logs-only/src/modules/mod.rs
Normal file
@@ -0,0 +1,39 @@
|
|||||||
|
pub use map_pool_created::map_pools_created;
|
||||||
|
pub use map_protocol_changes::map_protocol_changes;
|
||||||
|
pub use store_pools::store_pools;
|
||||||
|
use substreams_ethereum::pb::eth::v2::TransactionTrace;
|
||||||
|
|
||||||
|
use crate::pb::uniswap::v3::Transaction;
|
||||||
|
|
||||||
|
#[path = "1_map_pool_created.rs"]
|
||||||
|
mod map_pool_created;
|
||||||
|
|
||||||
|
#[path = "2_store_pools.rs"]
|
||||||
|
mod store_pools;
|
||||||
|
|
||||||
|
#[path = "3_map_events.rs"]
|
||||||
|
mod map_events;
|
||||||
|
|
||||||
|
#[path = "4_map_and_store_balance_changes.rs"]
|
||||||
|
mod map_store_balance_changes;
|
||||||
|
|
||||||
|
#[path = "4_map_and_store_ticks.rs"]
|
||||||
|
mod map_store_ticks;
|
||||||
|
|
||||||
|
#[path = "4_map_and_store_liquidity.rs"]
|
||||||
|
mod map_store_liquidity;
|
||||||
|
|
||||||
|
#[path = "5_map_protocol_changes.rs"]
|
||||||
|
mod map_protocol_changes;
|
||||||
|
|
||||||
|
impl From<TransactionTrace> for Transaction {
|
||||||
|
fn from(value: TransactionTrace) -> Self {
|
||||||
|
Self { hash: value.hash, from: value.from, to: value.to, index: value.index.into() }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl From<Transaction> for tycho_substreams::prelude::Transaction {
|
||||||
|
fn from(value: Transaction) -> Self {
|
||||||
|
Self { hash: value.hash, from: value.from, to: value.to, index: value.index }
|
||||||
|
}
|
||||||
|
}
|
||||||
8
substreams/ethereum-uniswap-v3-logs-only/src/pb/mod.rs
Normal file
8
substreams/ethereum-uniswap-v3-logs-only/src/pb/mod.rs
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
// @generated
|
||||||
|
pub mod uniswap {
|
||||||
|
// @@protoc_insertion_point(attribute:uniswap.v3)
|
||||||
|
pub mod v3 {
|
||||||
|
include!("uniswap.v3.rs");
|
||||||
|
// @@protoc_insertion_point(uniswap.v3)
|
||||||
|
}
|
||||||
|
}
|
||||||
298
substreams/ethereum-uniswap-v3-logs-only/src/pb/uniswap.v3.rs
Normal file
298
substreams/ethereum-uniswap-v3-logs-only/src/pb/uniswap.v3.rs
Normal file
@@ -0,0 +1,298 @@
|
|||||||
|
// @generated
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Pool {
|
||||||
|
#[prost(bytes="vec", tag="1")]
|
||||||
|
pub address: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
#[prost(bytes="vec", tag="2")]
|
||||||
|
pub token0: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
#[prost(bytes="vec", tag="3")]
|
||||||
|
pub token1: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
#[prost(bytes="vec", tag="4")]
|
||||||
|
pub created_tx_hash: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
}
|
||||||
|
/// A struct describing a transaction.
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Transaction {
|
||||||
|
/// The transaction hash.
|
||||||
|
#[prost(bytes="vec", tag="1")]
|
||||||
|
pub hash: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
/// The sender of the transaction.
|
||||||
|
#[prost(bytes="vec", tag="2")]
|
||||||
|
pub from: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
/// The receiver of the transaction.
|
||||||
|
#[prost(bytes="vec", tag="3")]
|
||||||
|
pub to: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
/// The transactions index within the block.
|
||||||
|
#[prost(uint64, tag="4")]
|
||||||
|
pub index: u64,
|
||||||
|
}
|
||||||
|
/// A change to a pool's tick.
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct TickDelta {
|
||||||
|
/// The address of the pool.
|
||||||
|
#[prost(bytes="vec", tag="1")]
|
||||||
|
pub pool_address: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
/// The index of the tick.
|
||||||
|
#[prost(int32, tag="2")]
|
||||||
|
pub tick_index: i32,
|
||||||
|
/// The liquidity net delta of this tick. Bigint encoded as signed little endian bytes.
|
||||||
|
#[prost(bytes="vec", tag="3")]
|
||||||
|
pub liquidity_net_delta: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
/// Used to determine the order of the balance changes. Necessary for the balance store.
|
||||||
|
#[prost(uint64, tag="4")]
|
||||||
|
pub ordinal: u64,
|
||||||
|
#[prost(message, optional, tag="5")]
|
||||||
|
pub transaction: ::core::option::Option<Transaction>,
|
||||||
|
}
|
||||||
|
/// A group of TickDelta
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct TickDeltas {
|
||||||
|
#[prost(message, repeated, tag="1")]
|
||||||
|
pub deltas: ::prost::alloc::vec::Vec<TickDelta>,
|
||||||
|
}
|
||||||
|
/// A change to a pool's liquidity.
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct LiquidityChange {
|
||||||
|
/// The address of the pool.
|
||||||
|
#[prost(bytes="vec", tag="1")]
|
||||||
|
pub pool_address: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
/// The liquidity changed amount. Bigint encoded as signed little endian bytes.
|
||||||
|
#[prost(bytes="vec", tag="2")]
|
||||||
|
pub value: ::prost::alloc::vec::Vec<u8>,
|
||||||
|
/// The type of update, can be absolute or delta.
|
||||||
|
#[prost(enumeration="LiquidityChangeType", tag="3")]
|
||||||
|
pub change_type: i32,
|
||||||
|
/// Used to determine the order of the balance changes. Necessary for the balance store.
|
||||||
|
#[prost(uint64, tag="4")]
|
||||||
|
pub ordinal: u64,
|
||||||
|
#[prost(message, optional, tag="5")]
|
||||||
|
pub transaction: ::core::option::Option<Transaction>,
|
||||||
|
}
|
||||||
|
/// A group of LiquidityChange
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct LiquidityChanges {
|
||||||
|
#[prost(message, repeated, tag="1")]
|
||||||
|
pub changes: ::prost::alloc::vec::Vec<LiquidityChange>,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Events {
|
||||||
|
#[prost(message, repeated, tag="3")]
|
||||||
|
pub pool_events: ::prost::alloc::vec::Vec<events::PoolEvent>,
|
||||||
|
}
|
||||||
|
/// Nested message and enum types in `Events`.
|
||||||
|
pub mod events {
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct PoolEvent {
|
||||||
|
#[prost(uint64, tag="100")]
|
||||||
|
pub log_ordinal: u64,
|
||||||
|
#[prost(string, tag="102")]
|
||||||
|
pub pool_address: ::prost::alloc::string::String,
|
||||||
|
#[prost(string, tag="103")]
|
||||||
|
pub token0: ::prost::alloc::string::String,
|
||||||
|
#[prost(string, tag="104")]
|
||||||
|
pub token1: ::prost::alloc::string::String,
|
||||||
|
#[prost(message, optional, tag="105")]
|
||||||
|
pub transaction: ::core::option::Option<super::Transaction>,
|
||||||
|
#[prost(oneof="pool_event::Type", tags="1, 2, 3, 4, 5, 6, 7, 8")]
|
||||||
|
pub r#type: ::core::option::Option<pool_event::Type>,
|
||||||
|
}
|
||||||
|
/// Nested message and enum types in `PoolEvent`.
|
||||||
|
pub mod pool_event {
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Initialize {
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="1")]
|
||||||
|
pub sqrt_price: ::prost::alloc::string::String,
|
||||||
|
#[prost(int32, tag="2")]
|
||||||
|
pub tick: i32,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Mint {
|
||||||
|
#[prost(string, tag="1")]
|
||||||
|
pub sender: ::prost::alloc::string::String,
|
||||||
|
#[prost(string, tag="2")]
|
||||||
|
pub owner: ::prost::alloc::string::String,
|
||||||
|
/// Signed
|
||||||
|
#[prost(int32, tag="3")]
|
||||||
|
pub tick_lower: i32,
|
||||||
|
/// Signed
|
||||||
|
#[prost(int32, tag="4")]
|
||||||
|
pub tick_upper: i32,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="5")]
|
||||||
|
pub amount: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="6")]
|
||||||
|
pub amount_0: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="7")]
|
||||||
|
pub amount_1: ::prost::alloc::string::String,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Collect {
|
||||||
|
#[prost(string, tag="1")]
|
||||||
|
pub owner: ::prost::alloc::string::String,
|
||||||
|
#[prost(string, tag="2")]
|
||||||
|
pub recipient: ::prost::alloc::string::String,
|
||||||
|
#[prost(int32, tag="3")]
|
||||||
|
pub tick_lower: i32,
|
||||||
|
#[prost(int32, tag="4")]
|
||||||
|
pub tick_upper: i32,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="5")]
|
||||||
|
pub amount_0: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="6")]
|
||||||
|
pub amount_1: ::prost::alloc::string::String,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Burn {
|
||||||
|
#[prost(string, tag="1")]
|
||||||
|
pub owner: ::prost::alloc::string::String,
|
||||||
|
#[prost(int32, tag="2")]
|
||||||
|
pub tick_lower: i32,
|
||||||
|
#[prost(int32, tag="3")]
|
||||||
|
pub tick_upper: i32,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="4")]
|
||||||
|
pub amount: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="5")]
|
||||||
|
pub amount_0: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="6")]
|
||||||
|
pub amount_1: ::prost::alloc::string::String,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Swap {
|
||||||
|
#[prost(string, tag="1")]
|
||||||
|
pub sender: ::prost::alloc::string::String,
|
||||||
|
#[prost(string, tag="2")]
|
||||||
|
pub recipient: ::prost::alloc::string::String,
|
||||||
|
/// Signed
|
||||||
|
#[prost(string, tag="3")]
|
||||||
|
pub amount_0: ::prost::alloc::string::String,
|
||||||
|
/// Signed
|
||||||
|
#[prost(string, tag="4")]
|
||||||
|
pub amount_1: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="6")]
|
||||||
|
pub sqrt_price: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="7")]
|
||||||
|
pub liquidity: ::prost::alloc::string::String,
|
||||||
|
#[prost(int32, tag="8")]
|
||||||
|
pub tick: i32,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct Flash {
|
||||||
|
#[prost(string, tag="1")]
|
||||||
|
pub sender: ::prost::alloc::string::String,
|
||||||
|
#[prost(string, tag="2")]
|
||||||
|
pub recipient: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="3")]
|
||||||
|
pub amount_0: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="4")]
|
||||||
|
pub amount_1: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="5")]
|
||||||
|
pub paid_0: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="6")]
|
||||||
|
pub paid_1: ::prost::alloc::string::String,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct SetFeeProtocol {
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(uint64, tag="1")]
|
||||||
|
pub fee_protocol_0_old: u64,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(uint64, tag="2")]
|
||||||
|
pub fee_protocol_1_old: u64,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(uint64, tag="3")]
|
||||||
|
pub fee_protocol_0_new: u64,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(uint64, tag="4")]
|
||||||
|
pub fee_protocol_1_new: u64,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||||
|
pub struct CollectProtocol {
|
||||||
|
#[prost(string, tag="1")]
|
||||||
|
pub sender: ::prost::alloc::string::String,
|
||||||
|
#[prost(string, tag="2")]
|
||||||
|
pub recipient: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="3")]
|
||||||
|
pub amount_0: ::prost::alloc::string::String,
|
||||||
|
/// Unsigned
|
||||||
|
#[prost(string, tag="4")]
|
||||||
|
pub amount_1: ::prost::alloc::string::String,
|
||||||
|
}
|
||||||
|
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||||
|
#[derive(Clone, PartialEq, ::prost::Oneof)]
|
||||||
|
pub enum Type {
|
||||||
|
#[prost(message, tag="1")]
|
||||||
|
Initialize(Initialize),
|
||||||
|
#[prost(message, tag="2")]
|
||||||
|
Mint(Mint),
|
||||||
|
#[prost(message, tag="3")]
|
||||||
|
Collect(Collect),
|
||||||
|
#[prost(message, tag="4")]
|
||||||
|
Burn(Burn),
|
||||||
|
#[prost(message, tag="5")]
|
||||||
|
Swap(Swap),
|
||||||
|
#[prost(message, tag="6")]
|
||||||
|
Flash(Flash),
|
||||||
|
#[prost(message, tag="7")]
|
||||||
|
SetFeeProtocol(SetFeeProtocol),
|
||||||
|
#[prost(message, tag="8")]
|
||||||
|
CollectProtocol(CollectProtocol),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)]
|
||||||
|
#[repr(i32)]
|
||||||
|
pub enum LiquidityChangeType {
|
||||||
|
Delta = 0,
|
||||||
|
Absolute = 1,
|
||||||
|
}
|
||||||
|
impl LiquidityChangeType {
|
||||||
|
/// String value of the enum field names used in the ProtoBuf definition.
|
||||||
|
///
|
||||||
|
/// The values are not transformed in any way and thus are considered stable
|
||||||
|
/// (if the ProtoBuf definition does not change) and safe for programmatic use.
|
||||||
|
pub fn as_str_name(&self) -> &'static str {
|
||||||
|
match self {
|
||||||
|
LiquidityChangeType::Delta => "DELTA",
|
||||||
|
LiquidityChangeType::Absolute => "ABSOLUTE",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/// Creates an enum from field names used in the ProtoBuf definition.
|
||||||
|
pub fn from_str_name(value: &str) -> ::core::option::Option<Self> {
|
||||||
|
match value {
|
||||||
|
"DELTA" => Some(Self::Delta),
|
||||||
|
"ABSOLUTE" => Some(Self::Absolute),
|
||||||
|
_ => None,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// @@protoc_insertion_point(module)
|
||||||
@@ -15,4 +15,5 @@ ignore = [
|
|||||||
"ethereum-curve/src/abi",
|
"ethereum-curve/src/abi",
|
||||||
"ethereum-uniswap-v2/src/abi",
|
"ethereum-uniswap-v2/src/abi",
|
||||||
"ethereum-uniswap-v3/src/abi",
|
"ethereum-uniswap-v3/src/abi",
|
||||||
|
"ethereum-uniswap-v3-logs-only/src/abi",
|
||||||
]
|
]
|
||||||
|
|||||||
Reference in New Issue
Block a user