erc_4626.vault_protocol.lagoon.offchain_metadata
Documentation for eth_defi.erc_4626.vault_protocol.lagoon.offchain_metadata Python module.
Lagoon vault offchain metadata.
Lagoon stores vault descriptions in their web app, not onchain or in a public data repository
We reverse-engineered the Lagoon Next.js app and discovered web application API endpoints at
app.lagoon.financethat serve vault metadata including descriptionsThe listing endpoint
/api/vaultsreturns paginated vault data without descriptionsThe detail endpoint
/api/vaultreturns full vault data includingdescriptionandshortDescriptionWe fetch and cache this data locally to avoid repeated API calls
Two-level caching: disk (1-day TTL) + an expiring in-process dictionary
Module Attributes
Lagoon web app API base URL, reverse-engineered from their Next.js frontend |
|
How long Lagoon metadata is cached before the scanner refreshes it. |
|
Prevent one failed refresh from being retried for every vault in the same scan. |
Functions
|
Fetch vault metadata from Lagoon's offchain web app API. |
|
Fetch and cache Lagoon offchain vault metadata for a given chain. |
Classes
Metadata about a Lagoon vault curator. |
|
Metadata about a Lagoon vault from offchain source. |
- DEFAULT_CACHE_PATH = PosixPath('/home/runner/.tradingstrategy/cache/lagoon')
Where we cache fetched Lagoon metadata files
- DEFAULT_API_BASE_URL = 'https://app.lagoon.finance/api'
Lagoon web app API base URL, reverse-engineered from their Next.js frontend
- DEFAULT_CACHE_DURATION = datetime.timedelta(days=1)
How long Lagoon metadata is cached before the scanner refreshes it.
- FAILED_REFRESH_RETRY_DELAY = datetime.timedelta(seconds=3600)
Prevent one failed refresh from being retried for every vault in the same scan.
- class LagoonCuratorMetadata
Bases:
TypedDictMetadata about a Lagoon vault curator.
Extracted from the Lagoon web app API
/api/vaultendpoint.- __init__(*args, **kwargs)
- __new__(**kwargs)
- clear()
Remove all items from the dict.
- copy()
Return a shallow copy of the dict.
- fromkeys(value=None, /)
Create a new dictionary with keys from iterable and values set to value.
- get(key, default=None, /)
Return the value for key if key is in the dictionary, else default.
- items()
Return a set-like object providing a view on the dict’s items.
- keys()
Return a set-like object providing a view on the dict’s keys.
- pop(k[, d]) v, remove specified key and return the corresponding value.
If the key is not found, return the default if given; otherwise, raise a KeyError.
- popitem()
Remove and return a (key, value) pair as a 2-tuple.
Pairs are returned in LIFO (last-in, first-out) order. Raises KeyError if the dict is empty.
- setdefault(key, default=None, /)
Insert key with a value of default if key is not in the dictionary.
Return the value for key if key is in the dictionary, else default.
- update([E, ]**F) None. Update D from mapping/iterable E and F.
If E is present and has a .keys() method, then does: for k in E.keys(): D[k] = E[k] If E is present and lacks a .keys() method, then does: for k, v in E: D[k] = v In either case, this is followed by: for k in F: D[k] = F[k]
- values()
Return an object providing a view on the dict’s values.
- class LagoonVaultMetadata
Bases:
TypedDictMetadata about a Lagoon vault from offchain source.
Fetched from the Lagoon web app API at
app.lagoon.finance. Discovered by reverse-engineering the Lagoon Next.js JavaScript bundles.Listing endpoint:
GET /api/vaults?chainId={chainId}&pageIndex=0&pageSize=100Detail endpoint:
GET /api/vault?chainId={chainId}&address={address}
The detail endpoint returns
descriptionandshortDescriptionfields that are not available in the listing endpoint.- description: Optional[str]
Full vault strategy description.
Example:
RockSolid's rETH Vault maximizes rETH-based returns by allocating it across DeFi protocols like AAVE and Morpho...
- short_description: Optional[str]
One-liner vault summary.
Example:
Our rETH vault both monitors for the latest opportunities, monitors funding rates to ensure optimal allocations...
- logo_url: Optional[str]
Vault share token logo URL on Lagoon’s GCS bucket.
Example:
https://storage.googleapis.com/lagoon-logos/shares/rocketh
- transparency_url: Optional[str]
URL to an external transparency/reporting page, if provided by the curator
- curators: list[eth_defi.erc_4626.vault_protocol.lagoon.offchain_metadata.LagoonCuratorMetadata]
List of curators managing this vault
- __init__(*args, **kwargs)
- __new__(**kwargs)
- clear()
Remove all items from the dict.
- copy()
Return a shallow copy of the dict.
- fromkeys(value=None, /)
Create a new dictionary with keys from iterable and values set to value.
- get(key, default=None, /)
Return the value for key if key is in the dictionary, else default.
- items()
Return a set-like object providing a view on the dict’s items.
- keys()
Return a set-like object providing a view on the dict’s keys.
- pop(k[, d]) v, remove specified key and return the corresponding value.
If the key is not found, return the default if given; otherwise, raise a KeyError.
- popitem()
Remove and return a (key, value) pair as a 2-tuple.
Pairs are returned in LIFO (last-in, first-out) order. Raises KeyError if the dict is empty.
- setdefault(key, default=None, /)
Insert key with a value of default if key is not in the dictionary.
Return the value for key if key is in the dictionary, else default.
- update([E, ]**F) None. Update D from mapping/iterable E and F.
If E is present and has a .keys() method, then does: for k in E.keys(): D[k] = E[k] If E is present and lacks a .keys() method, then does: for k, v in E: D[k] = v In either case, this is followed by: for k in F: D[k] = F[k]
- values()
Return an object providing a view on the dict’s values.
- fetch_lagoon_vaults_for_chain(chain_id, cache_path=PosixPath('/home/runner/.tradingstrategy/cache/lagoon'), api_base_url='https://app.lagoon.finance/api', now_=None, max_cache_duration=datetime.timedelta(days=1))
Fetch and cache Lagoon offchain vault metadata for a given chain.
Enumerates vaults using the listing endpoint, then fetches each vault’s detail (including description) from the detail endpoint
One JSON cache file per chain
Serialises concurrent readers and writers with a file lock
Retains stale metadata when Lagoon has a transient API failure
The official Lagoon web application uses these endpoints under
https://app.lagoon.finance/api.- Parameters
chain_id (int) – EVM chain id
cache_path (pathlib.Path) – Directory for cache files (default
~/.tradingstrategy/cache/lagoon/)api_base_url (str) – Lagoon API base URL
now – Override current time (for testing)
max_cache_duration (datetime.timedelta) – How long before refreshing cache (default 1 day)
now_ (Optional[datetime.datetime]) –
- Returns
Dict mapping checksummed vault address to
LagoonVaultMetadata- Return type
dict[eth_typing.evm.HexAddress, eth_defi.erc_4626.vault_protocol.lagoon.offchain_metadata.LagoonVaultMetadata]
- fetch_lagoon_vault_metadata(web3, vault_address, now_=None, cache_path=PosixPath('/home/runner/.tradingstrategy/cache/lagoon'))
Fetch vault metadata from Lagoon’s offchain web app API.
Use both expiring in-process and disk caches to avoid repeated fetches
- Parameters
web3 (web3.main.Web3) – Web3 instance (used to get chain_id and checksum address)
vault_address (eth_typing.evm.HexAddress) – Vault contract address
now – Override the current naive UTC time for testing.
cache_path (pathlib.Path) – Directory containing Lagoon metadata cache files.
now_ (Optional[datetime.datetime]) –
- Returns
Metadata dict or None if the vault is not in Lagoon’s app database
- Return type
Optional[eth_defi.erc_4626.vault_protocol.lagoon.offchain_metadata.LagoonVaultMetadata]