ipor-fusion 4.0.0.dev234__tar.gz → 4.0.0.dev240__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/AGENTS.md +4 -2
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/MIGRATION_4.md +19 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/PKG-INFO +1 -1
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/pyproject.toml +1 -1
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/__init__.py +4 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/config_cmd.py +1 -1
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/config_store.py +18 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/market_cmd.py +7 -5
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/options.py +43 -10
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/vault_cmd.py +21 -18
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/__init__.py +4 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/access.py +40 -2
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/mcp/models.py +2 -35
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/mcp/server.py +104 -67
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_helpers.py +8 -2
- ipor_fusion-4.0.0.dev240/tests/test_cli_mcp_parity.py +157 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_oracle_mapping.py +6 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_role_accounts.py +6 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_mcp_models.py +21 -12
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_mcp_server.py +10 -3
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_mcp_vault_validate.py +8 -2
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_public_api.py +24 -20
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.claude-plugin/marketplace.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.claude-plugin/plugin.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.env.example +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.gemini/settings.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.git-blame-ignore-revs +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.github/workflows/cd.yml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.github/workflows/ci.yml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.github/workflows/commit-lint.yml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.github/workflows/notify-slack.yml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.github/workflows/python-build.yml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.github/workflows/python-publish.yml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.github/workflows/release.yml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.github/workflows/report-slack.yml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.gitignore +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.pre-commit-config.yaml +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/.python-version +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/CHANGELOG.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/CLAUDE.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/CODEOWNERS +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/LICENSE +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/README.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/build.sh +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/examples/CONTRIBUTING.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/examples/README.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/examples/advanced_euler_v2_credit_market_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/examples/advanced_euler_v2_looping_arbitrum.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/examples/composed_hypercore_flow_arbitrum_hyperevm.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/examples/crosschain_ccip_usdc_arbitrum_hyperevm.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/examples/external_state_margin_leg_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/examples/simple_aave_v3_supply_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/pytest.ini +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/scripts/commit-check.sh +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/scripts/crosschain_readiness.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/skills/ipor-deploy-vault/SKILL.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/about.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cache.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/chains.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/changelog_cmd.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/main.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/oracle_mapping_view.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/vault_health.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/vault_info_view.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/vault_markets_view.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/cli/vault_rendering.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/config/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/config/roles.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/address.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/context.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/contract.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/erc20.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/external_state_executor.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/fee_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/fuse.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/fuse_action.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/fusion_factory.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/logs.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/multicall.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/oracle.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/plasma_vault.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/rewards_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/simulation.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/simulation_result.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/core/withdraw_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/chainlink.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/codec.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/contracts.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/events.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/indexer.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/lane.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/quote.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/ccip/transport.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/contracts.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/discovery.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/errors.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/fuses/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/fuses/base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/fuses/ccip.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/fuses/stargate.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/lane.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/logs.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/messages.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/simulation.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/stargate/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/stargate/contracts.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/stargate/lane.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/stargate/layerzero.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/stargate/transport.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/crosschain/transport.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/dependency_graph.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/entry_cli.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/entry_mcp.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/errors.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/explorer.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/field_docs.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/aave_v3.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/async_action.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/compound_v3.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/erc4626.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/euler_v2.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/events.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/external_state.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/external_state_event_decoding.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/fluid_instadapp.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/gearbox_v3.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/hypercore.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/hypercore_event_decoding.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/merkl.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/morpho.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/ramses_v2.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/uniswap_v3.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/fuses/universal.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/guide/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/guide/architecture.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/guide/glossary.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/guide/invariants.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/guide/quickstart.md +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/hypercore/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/market_ids.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/market_info.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/mcp/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/mcp/guide.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/morpho_api.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/py.typed +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/__init__.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/aave_v3.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/aave_v4.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/compound_v3.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/hypercore.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/hypercore_outcome.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/lending_health.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/morpho.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/oracle_mapping.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/oracle_mapping_nodes.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/oracle_mapping_reader.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/position_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/ramses_v2.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/uniswap_v3.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/readers/unpriceable.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/substrates.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/types.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/validation.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/vault_data.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/vault_erc20.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/vault_info.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/vault_managers.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/vault_positions.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/src/ipor_fusion/vault_reads.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/UniswapV3UniversalRouter.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_crosschain.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_crosschain_lifecycle.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_crosschain_recovery.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_euler_v2.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_event_args.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_fake_rpc.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_foundry.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_golden.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_guide.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_hypercore_model.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_hypercore_shadow.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_live.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_multicall.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_oracle_mapping_fake.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_simulate.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/_validation.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/addresses.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/conftest.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/constants.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/hypercore_hip3_flow.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/hypercore_market55.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/meta_morpho_v1.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/meta_morpho_v1.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/meta_morpho_v2.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/meta_morpho_v2.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_api/market.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_api/vault_v1.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_api/vault_v2.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_api/vault_v2_not_found.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_blue.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_blue.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_blue_api_error.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_blue_api_error.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_blue_no_api.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/market_golden/morpho_blue_no_api.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/oracle_mapping_golden/mapping.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/oracle_mapping_golden/mapping.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/simulate_v1_request.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/clean.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/clean.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/clean.txt +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/deployment_error.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/deployment_error.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/deployment_error.txt +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/fetched.cli.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/fetched.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/fetched.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/full.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/full.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/full.txt +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/rich.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/rich.mcp.json +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/fixtures/vault_info_golden/rich.txt +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_about.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_access_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cache.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_chains.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_changelog.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_commands.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_config_store.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_hypercore.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_lending_health.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_market_golden.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_market_morpho_blue.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_oracle_mapping_golden.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_pending_requests_scan.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_vault_info_golden.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_vault_predates_getters.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_cli_vault_validate.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_contract_call.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_contract_encoder.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_ccip_events.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_ccip_indexer.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_ccip_quote.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_chainlink.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_contracts.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_encoding.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_errors.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_lane.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_layering.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_readiness.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_readiness_report.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_crosschain_transport.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_docs_typing.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_erc20.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_error_hierarchy.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_examples_composed_hypercore.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_examples_crosschain.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_examples_euler_looping_arbitrum.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_examples_vaults.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_explorer.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_external_state_events.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_external_state_executor.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_fee_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_fuse_encoding.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_fusion_instance.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_guide.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_hypercore_deployment.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_hypercore_events.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_hypercore_flow.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_hypercore_live.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_hypercore_outcome.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_hypercore_readers.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_hypercore_simulation.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_logs.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_mcp_hypercore.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_multicall.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_oracle.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_oracle_mapping.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_plasma_vault.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_public_type_reachability.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_reader_encoding.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_readiness_selection.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_revert_decoding.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_rewards_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_roles.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_sdk_layering.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_borrow_aave_v3_mainnet.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_claim_merkl_wrapper_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_claim_morpho_rewards.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_crosschain_canary.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_crosschain_hypercore.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_crosschain_hyperevm.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_crosschain_lifecycle.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_euler_v2_batch_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_euler_v2_credit_market_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_euler_v2_swap_deploy_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_euler_v2_swap_reconfigure_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_euler_v2_swap_registry_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_examples_arbitrum.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_examples_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_examples_crosschain.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_external_state_executor_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_fusion_factory_clone_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_looping_aave_v3_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_looping_morpho_blue_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_morpho_blue.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_pilot_v3.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_pilot_v4_uniswap.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_pilot_v5_ramses.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_pilot_v5_scheduled.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_plasma_vault_setters_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_readers_integration.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_release_funds.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_swap_on_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulate_vault_from_scratch_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulation_errors.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_simulation_observation.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_solidity_compiler.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_solidity_mirrors.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_substrates.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_types_and_events.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_unpriceable_tokens.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_validation.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_vault_data_block.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_vault_dep_graph.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_vault_info_fetched_golden.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_vault_info_onchain_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_vault_info_onchain_base_no_withdraw_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_vault_reconciliation_onchain_base.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_vault_simulator_blocks.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_web3_context.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/test_withdraw_manager.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/typed_client/consumer.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/tests/typed_client/rejected.py +0 -0
- {ipor_fusion-4.0.0.dev234 → ipor_fusion-4.0.0.dev240}/uv.lock +0 -0
|
@@ -218,7 +218,7 @@ the lifecycle matrix follows that.
|
|
|
218
218
|
| `IporFusionMarkets`, `Roles` | `market_ids.py`, `config/roles.py` mirror `IporFusionMarkets.sol`, `Roles.sol` in `ipor-fusion/contracts/libraries/`; drift-gated by `tests/test_solidity_mirrors.py` — bump its pinned ref in the same change that syncs the mirrors An id sourced from a contracts feature branch ahead of the pinned ref goes in the test's `_AHEAD_OF_UPSTREAM` allowlist and is removed when the ref catches up |
|
|
219
219
|
| substrate decoders | `substrates.py` registry mirrors each market's `contracts/fuses/<protocol>/*SubstrateLib.sol` or `*FuseLib.sol` |
|
|
220
220
|
| `vault_info` / `fusion market` JSON shapes | the builders and their TypedDicts (`VaultInfoJson`, `MorphoBlueMarketJson`, `MetaMorphoV1Json` / `MetaMorphoV2Json`) in `vault_info.py` / `market_info.py`, models in `mcp/models.py` (`extra="forbid"`, the published schema), the `VaultInfoJson`-typed `_full_vault_info_dict` fixture in `test_mcp_models.py` |
|
|
221
|
-
| CLI command set | every CLI command has a matching tool in `mcp/server.py` (`changelog` maps to `server_info`) |
|
|
221
|
+
| CLI command set | every CLI command has a matching tool in `mcp/server.py` with the same arguments (`changelog` maps to `server_info`; `--json` and display filters are CLI-only); `tests/test_cli_mcp_parity.py` enforces it, and both resolve chain and provider through `cli/config_store.resolve_chain_id` |
|
|
222
222
|
|
|
223
223
|
## Layout (`src/ipor_fusion/`)
|
|
224
224
|
|
|
@@ -479,7 +479,9 @@ the rest share names). Read-only: `vault_info`, `vault_validate`,
|
|
|
479
479
|
`vault_list`, `vault_role_accounts`, `vault_oracle_mapping`, `market_morpho_blue`,
|
|
480
480
|
`market_meta_morpho`, `config_show`, `server_info`. Mutating: `vault_add`,
|
|
481
481
|
`vault_remove`, `config_set_provider`, `config_set_etherscan_key`. Every new
|
|
482
|
-
CLI command gets a matching MCP tool
|
|
482
|
+
CLI command gets a matching MCP tool with the same argument names; an optional
|
|
483
|
+
chain or block is `None` when omitted (`ChainArg`, `BlockArg`), never a `0`
|
|
484
|
+
sentinel. Put every fact in its structured home:
|
|
483
485
|
the return shape is the Pydantic return type (it becomes `outputSchema`),
|
|
484
486
|
per-argument semantics go in `Annotated[..., Field(description=...)]`, closed
|
|
485
487
|
value sets are `Literal` enums. The docstring keeps only what has no
|
|
@@ -990,6 +990,25 @@ and `log_index` was passed through as given (a hex string from a raw log); the e
|
|
|
990
990
|
These apply to every caller, type-checked or not. Changes described in full above
|
|
991
991
|
are listed with a link.
|
|
992
992
|
|
|
993
|
+
- **The CLI and the MCP tools take the same arguments.**
|
|
994
|
+
- **MCP inputs:** `chain_id` and `block_number` are optional and omitted means
|
|
995
|
+
auto-detected / latest. The `0` sentinel is gone, and `0` is now rejected with
|
|
996
|
+
an error naming the argument to omit (it is never read as chain or block 0);
|
|
997
|
+
a client that passed `0` must omit the argument instead. The CLI refuses
|
|
998
|
+
`--block-number 0` and `--chain-id 0` the same way. `server_info(changelog_since=)` is `server_info(since=)` as in
|
|
999
|
+
`fusion changelog --since`, and `vault_oracle_mapping` takes `max_depth` like
|
|
1000
|
+
`--max-depth`.
|
|
1001
|
+
- **Chain auto-detection:** both surfaces use the saved vault's chain, else the
|
|
1002
|
+
chain of the only configured provider. The CLI used only the saved vault.
|
|
1003
|
+
- **CLI options:** every `--block-number` rejects a negative block, and
|
|
1004
|
+
`fusion market morpho-blue --block` is `--block-number` (`--block` still
|
|
1005
|
+
works).
|
|
1006
|
+
- **One role-accounts document:** `fusion vault role-accounts --json` and
|
|
1007
|
+
`vault_role_accounts` publish `RoleAccountsJson`, built by
|
|
1008
|
+
`build_role_accounts_json` (exported).
|
|
1009
|
+
- **Parity test:** `tests/test_cli_mcp_parity.py` holds every command to a
|
|
1010
|
+
tool with the same arguments.
|
|
1011
|
+
|
|
993
1012
|
- **`vault validate` publishes one document.** In 3.x the CLI's `--json` output
|
|
994
1013
|
and the MCP `vault_validate` tool returned two different shapes; both now
|
|
995
1014
|
return `VaultValidationJson`, built by `build_vault_validation_json(validation,
|
|
@@ -28,7 +28,9 @@ from ipor_fusion.core.access import (
|
|
|
28
28
|
AccessManager,
|
|
29
29
|
RoleAccount,
|
|
30
30
|
RoleAccountJson,
|
|
31
|
+
RoleAccountsJson,
|
|
31
32
|
RoleStatus,
|
|
33
|
+
build_role_accounts_json,
|
|
32
34
|
resolve_access_manager,
|
|
33
35
|
role_account_sort_key,
|
|
34
36
|
)
|
|
@@ -465,6 +467,8 @@ __all__ = [
|
|
|
465
467
|
"RoleStatus",
|
|
466
468
|
"resolve_access_manager",
|
|
467
469
|
"role_account_sort_key",
|
|
470
|
+
"RoleAccountsJson",
|
|
471
|
+
"build_role_accounts_json",
|
|
468
472
|
"RewardsManager",
|
|
469
473
|
"VestingData",
|
|
470
474
|
"ERC20",
|
|
@@ -88,3 +88,21 @@ def load_config() -> FusionConfig:
|
|
|
88
88
|
def save_config(config: FusionConfig) -> None:
|
|
89
89
|
CONFIG_DIR.mkdir(parents=True, exist_ok=True)
|
|
90
90
|
CONFIG_FILE.write_text(config.model_dump_json(indent=2), encoding="utf-8")
|
|
91
|
+
|
|
92
|
+
|
|
93
|
+
def resolve_chain_id(
|
|
94
|
+
cfg: FusionConfig, vault_address: str, chain_id: ChainId | None
|
|
95
|
+
) -> ChainId | None:
|
|
96
|
+
"""The chain a command or tool runs on: the one given, else the saved
|
|
97
|
+
vault's, else the chain of the only configured provider; None when none
|
|
98
|
+
applies. The CLI and the MCP server share it so both resolve alike."""
|
|
99
|
+
if chain_id is not None:
|
|
100
|
+
return chain_id
|
|
101
|
+
if entry := next(
|
|
102
|
+
(v for v in cfg.vaults if v.address.lower() == vault_address.lower()),
|
|
103
|
+
None,
|
|
104
|
+
):
|
|
105
|
+
return entry.chain_id
|
|
106
|
+
if len(cfg.providers) == 1:
|
|
107
|
+
return ChainId(int(next(iter(cfg.providers))))
|
|
108
|
+
return None
|
|
@@ -16,7 +16,7 @@ from eth_typing import ChecksumAddress
|
|
|
16
16
|
|
|
17
17
|
from ipor_fusion.chains import CHAIN_NAMES
|
|
18
18
|
from ipor_fusion.cli.config_store import load_config
|
|
19
|
-
from ipor_fusion.cli.options import ADDRESS, CHAIN, _resolve_provider
|
|
19
|
+
from ipor_fusion.cli.options import ADDRESS, BLOCK_NUMBER, CHAIN, _resolve_provider
|
|
20
20
|
from ipor_fusion.cli.vault_rendering import _format_amount, _print_table
|
|
21
21
|
from ipor_fusion.core.context import Web3Context
|
|
22
22
|
from ipor_fusion.market_info import (
|
|
@@ -81,8 +81,10 @@ def market() -> None:
|
|
|
81
81
|
help="Chain ID or name (ethereum, base, arbitrum, ...).",
|
|
82
82
|
)
|
|
83
83
|
@click.option(
|
|
84
|
+
"--block-number",
|
|
84
85
|
"--block",
|
|
85
|
-
|
|
86
|
+
"block_number",
|
|
87
|
+
type=BLOCK_NUMBER,
|
|
86
88
|
default=None,
|
|
87
89
|
help="Block number for on-chain reads (default: latest).",
|
|
88
90
|
)
|
|
@@ -109,7 +111,7 @@ def market() -> None:
|
|
|
109
111
|
def morpho_blue(
|
|
110
112
|
market_id: MorphoBlueMarketId,
|
|
111
113
|
chain_id: ChainId,
|
|
112
|
-
|
|
114
|
+
block_number: int | None,
|
|
113
115
|
no_api: bool,
|
|
114
116
|
vault_filter: str | None,
|
|
115
117
|
json_output: bool,
|
|
@@ -125,8 +127,8 @@ def morpho_blue(
|
|
|
125
127
|
cfg = load_config()
|
|
126
128
|
provider_url = _resolve_provider(cfg, chain_id)
|
|
127
129
|
ctx = Web3Context.from_url(provider_url)
|
|
128
|
-
if
|
|
129
|
-
ctx = ctx.at_block(
|
|
130
|
+
if block_number is not None:
|
|
131
|
+
ctx = ctx.at_block(block_number)
|
|
130
132
|
reader = MorphoReader(morpho_blue_address(chain_id))
|
|
131
133
|
mid = market_id
|
|
132
134
|
params, state = reader.read_existing_market(ctx, mid)
|
|
@@ -7,6 +7,7 @@ from web3 import Web3
|
|
|
7
7
|
from ipor_fusion.chains import CHAIN_NAME_TO_ID, ensure_supported_chain
|
|
8
8
|
from ipor_fusion.cli.config_store import (
|
|
9
9
|
FusionConfig,
|
|
10
|
+
resolve_chain_id,
|
|
10
11
|
)
|
|
11
12
|
from ipor_fusion.core.context import Web3Context
|
|
12
13
|
from ipor_fusion.errors import (
|
|
@@ -74,11 +75,11 @@ class ChainType(click.ParamType): # pyright: ignore[reportMissingTypeArgument]
|
|
|
74
75
|
self, value: object, param: click.Parameter | None, ctx: click.Context | None
|
|
75
76
|
) -> ChainId:
|
|
76
77
|
if isinstance(value, int):
|
|
77
|
-
return
|
|
78
|
+
return self._positive(value, param, ctx)
|
|
78
79
|
if not isinstance(value, str):
|
|
79
80
|
self.fail(f"expected string, got {type(value).__name__}", param, ctx)
|
|
80
81
|
try:
|
|
81
|
-
return
|
|
82
|
+
return self._positive(int(value), param, ctx)
|
|
82
83
|
except ValueError:
|
|
83
84
|
pass
|
|
84
85
|
lower = value.lower().strip()
|
|
@@ -91,22 +92,54 @@ class ChainType(click.ParamType): # pyright: ignore[reportMissingTypeArgument]
|
|
|
91
92
|
ctx,
|
|
92
93
|
)
|
|
93
94
|
|
|
95
|
+
def _positive(
|
|
96
|
+
self, value: int, param: click.Parameter | None, ctx: click.Context | None
|
|
97
|
+
) -> ChainId:
|
|
98
|
+
if value <= 0:
|
|
99
|
+
self.fail(
|
|
100
|
+
f"chain ID must be positive, got {value}; omit --chain-id to "
|
|
101
|
+
"auto-detect it",
|
|
102
|
+
param,
|
|
103
|
+
ctx,
|
|
104
|
+
)
|
|
105
|
+
return ChainId(value)
|
|
106
|
+
|
|
94
107
|
|
|
95
108
|
CHAIN = ChainType()
|
|
96
109
|
|
|
97
110
|
|
|
111
|
+
class BlockNumberType(click.IntRange):
|
|
112
|
+
"""A positive block number. 0 is refused rather than read as block 0:
|
|
113
|
+
some callers still pass it meaning "latest"."""
|
|
114
|
+
|
|
115
|
+
name = "block"
|
|
116
|
+
|
|
117
|
+
def __init__(self) -> None:
|
|
118
|
+
super().__init__(min=1)
|
|
119
|
+
|
|
120
|
+
def convert(
|
|
121
|
+
self, value: object, param: click.Parameter | None, ctx: click.Context | None
|
|
122
|
+
) -> int:
|
|
123
|
+
if value in (0, "0"):
|
|
124
|
+
self.fail(
|
|
125
|
+
"0 is not a block selector: omit --block-number for the latest block",
|
|
126
|
+
param,
|
|
127
|
+
ctx,
|
|
128
|
+
)
|
|
129
|
+
return super().convert(value, param, ctx)
|
|
130
|
+
|
|
131
|
+
|
|
132
|
+
BLOCK_NUMBER = BlockNumberType()
|
|
133
|
+
|
|
134
|
+
|
|
98
135
|
def _resolve_chain_id(
|
|
99
136
|
cfg: FusionConfig, vault_address: PlasmaVaultAddress, chain_id: ChainId | None
|
|
100
137
|
) -> ChainId:
|
|
101
|
-
if chain_id is not None:
|
|
102
|
-
return
|
|
103
|
-
if entry := next(
|
|
104
|
-
(v for v in cfg.vaults if v.address.lower() == vault_address.lower()),
|
|
105
|
-
None,
|
|
106
|
-
):
|
|
107
|
-
return entry.chain_id
|
|
138
|
+
if (resolved := resolve_chain_id(cfg, vault_address, chain_id)) is not None:
|
|
139
|
+
return resolved
|
|
108
140
|
raise click.UsageError(
|
|
109
|
-
"
|
|
141
|
+
"Cannot tell the chain: the vault is not saved and there is not exactly one "
|
|
142
|
+
"configured provider — use --chain-id (e.g. --chain-id ethereum, --chain-id 8453)"
|
|
110
143
|
)
|
|
111
144
|
|
|
112
145
|
|
|
@@ -4,7 +4,6 @@ import json
|
|
|
4
4
|
import sys
|
|
5
5
|
|
|
6
6
|
import click
|
|
7
|
-
from web3 import Web3
|
|
8
7
|
|
|
9
8
|
from ipor_fusion.chains import CHAIN_NAMES
|
|
10
9
|
from ipor_fusion.cli.config_store import (
|
|
@@ -13,7 +12,13 @@ from ipor_fusion.cli.config_store import (
|
|
|
13
12
|
load_config,
|
|
14
13
|
save_config,
|
|
15
14
|
)
|
|
16
|
-
from ipor_fusion.cli.options import
|
|
15
|
+
from ipor_fusion.cli.options import (
|
|
16
|
+
BLOCK_NUMBER,
|
|
17
|
+
CHAIN,
|
|
18
|
+
VAULT_ADDRESS,
|
|
19
|
+
_build_ctx,
|
|
20
|
+
_resolve_provider,
|
|
21
|
+
)
|
|
17
22
|
from ipor_fusion.cli.oracle_mapping_view import _print_oracle_mapping
|
|
18
23
|
from ipor_fusion.cli.vault_health import (
|
|
19
24
|
_print_validation,
|
|
@@ -27,8 +32,8 @@ from ipor_fusion.cli.vault_rendering import (
|
|
|
27
32
|
)
|
|
28
33
|
from ipor_fusion.config.roles import Roles
|
|
29
34
|
from ipor_fusion.core.access import (
|
|
35
|
+
build_role_accounts_json,
|
|
30
36
|
resolve_access_manager,
|
|
31
|
-
role_account_sort_key,
|
|
32
37
|
)
|
|
33
38
|
from ipor_fusion.core.context import Web3Context
|
|
34
39
|
from ipor_fusion.core.plasma_vault import PlasmaVault
|
|
@@ -181,7 +186,7 @@ vault.add_command(list_vaults, "ls")
|
|
|
181
186
|
)
|
|
182
187
|
@click.option(
|
|
183
188
|
"--block-number",
|
|
184
|
-
type=
|
|
189
|
+
type=BLOCK_NUMBER,
|
|
185
190
|
default=None,
|
|
186
191
|
help="Block number (default: latest).",
|
|
187
192
|
)
|
|
@@ -226,7 +231,7 @@ def info(
|
|
|
226
231
|
)
|
|
227
232
|
@click.option(
|
|
228
233
|
"--block-number",
|
|
229
|
-
type=
|
|
234
|
+
type=BLOCK_NUMBER,
|
|
230
235
|
default=None,
|
|
231
236
|
help="Block number (default: latest).",
|
|
232
237
|
)
|
|
@@ -287,7 +292,7 @@ def validate(
|
|
|
287
292
|
)
|
|
288
293
|
@click.option(
|
|
289
294
|
"--block-number",
|
|
290
|
-
type=
|
|
295
|
+
type=BLOCK_NUMBER,
|
|
291
296
|
default=None,
|
|
292
297
|
help="Block number (default: latest).",
|
|
293
298
|
)
|
|
@@ -326,21 +331,19 @@ def role_accounts(
|
|
|
326
331
|
raise click.ClickException(
|
|
327
332
|
f"RoleGranted log scan failed ({type(exc).__name__}: {exc})."
|
|
328
333
|
) from exc
|
|
329
|
-
|
|
330
|
-
|
|
334
|
+
document = build_role_accounts_json(
|
|
335
|
+
accounts,
|
|
336
|
+
vault=vault_address,
|
|
337
|
+
access_manager=manager.address,
|
|
338
|
+
chain_id=chain_id,
|
|
339
|
+
role=role_id,
|
|
340
|
+
)
|
|
331
341
|
if json_output:
|
|
332
|
-
|
|
333
|
-
"vault": Web3.to_checksum_address(vault_address),
|
|
334
|
-
"access_manager": manager.address,
|
|
335
|
-
"chain_id": chain_id,
|
|
336
|
-
"role_filter": Roles.get_name(role_id) if role_id is not None else None,
|
|
337
|
-
"accounts": rows,
|
|
338
|
-
}
|
|
339
|
-
click.echo(json.dumps(payload, indent=2))
|
|
342
|
+
click.echo(json.dumps(document, indent=2))
|
|
340
343
|
return
|
|
341
344
|
|
|
342
345
|
click.echo(f"Access Manager: {manager.address}")
|
|
343
|
-
_print_role_accounts_table(
|
|
346
|
+
_print_role_accounts_table(document["accounts"])
|
|
344
347
|
|
|
345
348
|
|
|
346
349
|
@vault.command("oracle-mapping")
|
|
@@ -350,7 +353,7 @@ def role_accounts(
|
|
|
350
353
|
)
|
|
351
354
|
@click.option(
|
|
352
355
|
"--block-number",
|
|
353
|
-
type=
|
|
356
|
+
type=BLOCK_NUMBER,
|
|
354
357
|
default=None,
|
|
355
358
|
help="Block number (default: latest).",
|
|
356
359
|
)
|
|
@@ -2,7 +2,9 @@ from ipor_fusion.core.access import (
|
|
|
2
2
|
AccessManager,
|
|
3
3
|
RoleAccount,
|
|
4
4
|
RoleAccountJson,
|
|
5
|
+
RoleAccountsJson,
|
|
5
6
|
RoleStatus,
|
|
7
|
+
build_role_accounts_json,
|
|
6
8
|
resolve_access_manager,
|
|
7
9
|
role_account_sort_key,
|
|
8
10
|
)
|
|
@@ -138,4 +140,6 @@ __all__ = [
|
|
|
138
140
|
"price_oracle_middleware",
|
|
139
141
|
"resolve_access_manager",
|
|
140
142
|
"role_account_sort_key",
|
|
143
|
+
"RoleAccountsJson",
|
|
144
|
+
"build_role_accounts_json",
|
|
141
145
|
]
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
from collections.abc import Callable
|
|
1
|
+
from collections.abc import Callable, Sequence
|
|
2
2
|
from dataclasses import dataclass
|
|
3
3
|
from typing import TypedDict
|
|
4
4
|
|
|
@@ -21,7 +21,13 @@ from ipor_fusion.errors import (
|
|
|
21
21
|
NotPlasmaVaultError,
|
|
22
22
|
OwnerNotFoundError,
|
|
23
23
|
)
|
|
24
|
-
from ipor_fusion.types import
|
|
24
|
+
from ipor_fusion.types import (
|
|
25
|
+
AccessManagerAddress,
|
|
26
|
+
ChainId,
|
|
27
|
+
Period,
|
|
28
|
+
PlasmaVaultAddress,
|
|
29
|
+
RoleId,
|
|
30
|
+
)
|
|
25
31
|
|
|
26
32
|
|
|
27
33
|
class RoleAccountJson(TypedDict):
|
|
@@ -71,6 +77,38 @@ def role_account_sort_key(role_account: RoleAccount) -> tuple[str, int]:
|
|
|
71
77
|
return (role_account.account.lower(), role_account.role_id)
|
|
72
78
|
|
|
73
79
|
|
|
80
|
+
class RoleAccountsJson(TypedDict):
|
|
81
|
+
"""The ``fusion vault role-accounts --json`` document and the
|
|
82
|
+
``vault_role_accounts`` MCP tool output (`build_role_accounts_json`)."""
|
|
83
|
+
|
|
84
|
+
vault: PlasmaVaultAddress
|
|
85
|
+
access_manager: AccessManagerAddress
|
|
86
|
+
chain_id: ChainId
|
|
87
|
+
role_filter: str | None
|
|
88
|
+
accounts: list[RoleAccountJson]
|
|
89
|
+
|
|
90
|
+
|
|
91
|
+
def build_role_accounts_json(
|
|
92
|
+
accounts: Sequence[RoleAccount],
|
|
93
|
+
*,
|
|
94
|
+
vault: PlasmaVaultAddress,
|
|
95
|
+
access_manager: AccessManagerAddress,
|
|
96
|
+
chain_id: ChainId,
|
|
97
|
+
role: RoleId | Roles | None = None,
|
|
98
|
+
) -> RoleAccountsJson:
|
|
99
|
+
"""Role holders as the one document both tools publish, in
|
|
100
|
+
`role_account_sort_key` order; ``role`` is the filter applied, if any."""
|
|
101
|
+
return {
|
|
102
|
+
"vault": vault,
|
|
103
|
+
"access_manager": access_manager,
|
|
104
|
+
"chain_id": chain_id,
|
|
105
|
+
"role_filter": Roles.get_name(role) if role is not None else None,
|
|
106
|
+
"accounts": [
|
|
107
|
+
ra.to_dict() for ra in sorted(accounts, key=role_account_sort_key)
|
|
108
|
+
],
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
|
|
74
112
|
def _role_status_decoder(values: tuple[bool, int]) -> RoleStatus:
|
|
75
113
|
is_member, execution_delay = values
|
|
76
114
|
return RoleStatus(is_member=is_member, execution_delay=Period(execution_delay))
|
|
@@ -59,7 +59,6 @@ from ipor_fusion.types import (
|
|
|
59
59
|
|
|
60
60
|
if TYPE_CHECKING:
|
|
61
61
|
from ipor_fusion.about import ChangelogEntry
|
|
62
|
-
from ipor_fusion.core.access import RoleAccount
|
|
63
62
|
from ipor_fusion.readers.oracle_mapping import OracleMapping, OracleNode
|
|
64
63
|
|
|
65
64
|
|
|
@@ -503,38 +502,6 @@ class RoleAccountsResponse(_Base):
|
|
|
503
502
|
)
|
|
504
503
|
accounts: list[RoleAccountEntry]
|
|
505
504
|
|
|
506
|
-
@classmethod
|
|
507
|
-
def from_role_accounts(
|
|
508
|
-
cls,
|
|
509
|
-
accounts: list[RoleAccount],
|
|
510
|
-
*,
|
|
511
|
-
vault: str,
|
|
512
|
-
access_manager: str,
|
|
513
|
-
chain_id: ChainId,
|
|
514
|
-
role_filter: str | None,
|
|
515
|
-
) -> RoleAccountsResponse:
|
|
516
|
-
"""Build the response from SDK dataclasses (sorted for stable output)."""
|
|
517
|
-
# Deferred import keeps this module's import graph pydantic-only.
|
|
518
|
-
from ipor_fusion.core.access import role_account_sort_key
|
|
519
|
-
|
|
520
|
-
entries = [
|
|
521
|
-
RoleAccountEntry(
|
|
522
|
-
account=ra.account,
|
|
523
|
-
role_id=ra.role_id,
|
|
524
|
-
role_name=ra.role_name,
|
|
525
|
-
is_member=ra.is_member,
|
|
526
|
-
execution_delay=ra.execution_delay,
|
|
527
|
-
)
|
|
528
|
-
for ra in sorted(accounts, key=role_account_sort_key)
|
|
529
|
-
]
|
|
530
|
-
return cls(
|
|
531
|
-
vault=vault,
|
|
532
|
-
access_manager=access_manager,
|
|
533
|
-
chain_id=chain_id,
|
|
534
|
-
role_filter=role_filter,
|
|
535
|
-
accounts=entries,
|
|
536
|
-
)
|
|
537
|
-
|
|
538
505
|
|
|
539
506
|
# ---------------------------------------------------------------------------
|
|
540
507
|
# Oracle-mapping models
|
|
@@ -1222,9 +1189,9 @@ class ServerInfoResponse(_Base):
|
|
|
1222
1189
|
)
|
|
1223
1190
|
changelog: list[ChangelogEntryModel] = Field(
|
|
1224
1191
|
description="Newest first, and only a slice of the release history: "
|
|
1225
|
-
"the running version's entry alone unless
|
|
1192
|
+
"the running version's entry alone unless since asked for "
|
|
1226
1193
|
"more. Empty when nothing matches: no section for the running "
|
|
1227
|
-
"version, or no release newer than
|
|
1194
|
+
"version, or no release newer than since."
|
|
1228
1195
|
)
|
|
1229
1196
|
preview_features: list[PreviewFeatureModel] = Field(
|
|
1230
1197
|
default_factory=_package_preview_features,
|