chia-blockchain 2.5.1rc1__py3-none-any.whl
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.
- chia/__init__.py +10 -0
- chia/__main__.py +5 -0
- chia/_tests/README.md +53 -0
- chia/_tests/__init__.py +0 -0
- chia/_tests/blockchain/__init__.py +0 -0
- chia/_tests/blockchain/blockchain_test_utils.py +195 -0
- chia/_tests/blockchain/config.py +4 -0
- chia/_tests/blockchain/test_augmented_chain.py +145 -0
- chia/_tests/blockchain/test_blockchain.py +4202 -0
- chia/_tests/blockchain/test_blockchain_transactions.py +1031 -0
- chia/_tests/blockchain/test_build_chains.py +59 -0
- chia/_tests/blockchain/test_get_block_generator.py +72 -0
- chia/_tests/blockchain/test_lookup_fork_chain.py +194 -0
- chia/_tests/build-init-files.py +92 -0
- chia/_tests/build-job-matrix.py +204 -0
- chia/_tests/check_pytest_monitor_output.py +34 -0
- chia/_tests/check_sql_statements.py +72 -0
- chia/_tests/chia-start-sim +42 -0
- chia/_tests/clvm/__init__.py +0 -0
- chia/_tests/clvm/benchmark_costs.py +23 -0
- chia/_tests/clvm/coin_store.py +149 -0
- chia/_tests/clvm/test_chialisp_deserialization.py +101 -0
- chia/_tests/clvm/test_clvm_step.py +37 -0
- chia/_tests/clvm/test_condition_codes.py +13 -0
- chia/_tests/clvm/test_curry_and_treehash.py +55 -0
- chia/_tests/clvm/test_message_conditions.py +184 -0
- chia/_tests/clvm/test_program.py +150 -0
- chia/_tests/clvm/test_puzzle_compression.py +143 -0
- chia/_tests/clvm/test_puzzle_drivers.py +45 -0
- chia/_tests/clvm/test_puzzles.py +242 -0
- chia/_tests/clvm/test_singletons.py +540 -0
- chia/_tests/clvm/test_spend_sim.py +181 -0
- chia/_tests/cmds/__init__.py +0 -0
- chia/_tests/cmds/cmd_test_utils.py +469 -0
- chia/_tests/cmds/config.py +3 -0
- chia/_tests/cmds/conftest.py +23 -0
- chia/_tests/cmds/test_click_types.py +200 -0
- chia/_tests/cmds/test_cmd_framework.py +620 -0
- chia/_tests/cmds/test_cmds_util.py +97 -0
- chia/_tests/cmds/test_daemon.py +92 -0
- chia/_tests/cmds/test_dev_gh.py +131 -0
- chia/_tests/cmds/test_farm_cmd.py +66 -0
- chia/_tests/cmds/test_show.py +116 -0
- chia/_tests/cmds/test_sim.py +207 -0
- chia/_tests/cmds/test_timelock_args.py +75 -0
- chia/_tests/cmds/test_tx_config_args.py +154 -0
- chia/_tests/cmds/testing_classes.py +59 -0
- chia/_tests/cmds/wallet/__init__.py +0 -0
- chia/_tests/cmds/wallet/test_consts.py +47 -0
- chia/_tests/cmds/wallet/test_dao.py +565 -0
- chia/_tests/cmds/wallet/test_did.py +403 -0
- chia/_tests/cmds/wallet/test_nft.py +471 -0
- chia/_tests/cmds/wallet/test_notifications.py +124 -0
- chia/_tests/cmds/wallet/test_offer.toffer +1 -0
- chia/_tests/cmds/wallet/test_tx_decorators.py +27 -0
- chia/_tests/cmds/wallet/test_vcs.py +400 -0
- chia/_tests/cmds/wallet/test_wallet.py +1125 -0
- chia/_tests/cmds/wallet/test_wallet_check.py +109 -0
- chia/_tests/conftest.py +1419 -0
- chia/_tests/connection_utils.py +125 -0
- chia/_tests/core/__init__.py +0 -0
- chia/_tests/core/cmds/__init__.py +0 -0
- chia/_tests/core/cmds/test_beta.py +382 -0
- chia/_tests/core/cmds/test_keys.py +1734 -0
- chia/_tests/core/cmds/test_wallet.py +126 -0
- chia/_tests/core/config.py +3 -0
- chia/_tests/core/consensus/__init__.py +0 -0
- chia/_tests/core/consensus/test_block_creation.py +54 -0
- chia/_tests/core/consensus/test_pot_iterations.py +117 -0
- chia/_tests/core/custom_types/__init__.py +0 -0
- chia/_tests/core/custom_types/test_coin.py +107 -0
- chia/_tests/core/custom_types/test_proof_of_space.py +144 -0
- chia/_tests/core/custom_types/test_spend_bundle.py +70 -0
- chia/_tests/core/daemon/__init__.py +0 -0
- chia/_tests/core/daemon/config.py +4 -0
- chia/_tests/core/daemon/test_daemon.py +2128 -0
- chia/_tests/core/daemon/test_daemon_register.py +109 -0
- chia/_tests/core/daemon/test_keychain_proxy.py +101 -0
- chia/_tests/core/data_layer/__init__.py +0 -0
- chia/_tests/core/data_layer/config.py +5 -0
- chia/_tests/core/data_layer/conftest.py +106 -0
- chia/_tests/core/data_layer/test_data_cli.py +56 -0
- chia/_tests/core/data_layer/test_data_layer.py +83 -0
- chia/_tests/core/data_layer/test_data_layer_util.py +218 -0
- chia/_tests/core/data_layer/test_data_rpc.py +3847 -0
- chia/_tests/core/data_layer/test_data_store.py +2424 -0
- chia/_tests/core/data_layer/test_data_store_schema.py +381 -0
- chia/_tests/core/data_layer/test_plugin.py +91 -0
- chia/_tests/core/data_layer/util.py +233 -0
- chia/_tests/core/farmer/__init__.py +0 -0
- chia/_tests/core/farmer/config.py +3 -0
- chia/_tests/core/farmer/test_farmer_api.py +103 -0
- chia/_tests/core/full_node/__init__.py +0 -0
- chia/_tests/core/full_node/config.py +4 -0
- chia/_tests/core/full_node/dos/__init__.py +0 -0
- chia/_tests/core/full_node/dos/config.py +3 -0
- chia/_tests/core/full_node/full_sync/__init__.py +0 -0
- chia/_tests/core/full_node/full_sync/config.py +4 -0
- chia/_tests/core/full_node/full_sync/test_full_sync.py +443 -0
- chia/_tests/core/full_node/ram_db.py +27 -0
- chia/_tests/core/full_node/stores/__init__.py +0 -0
- chia/_tests/core/full_node/stores/config.py +4 -0
- chia/_tests/core/full_node/stores/test_block_store.py +590 -0
- chia/_tests/core/full_node/stores/test_coin_store.py +897 -0
- chia/_tests/core/full_node/stores/test_full_node_store.py +1219 -0
- chia/_tests/core/full_node/stores/test_hint_store.py +229 -0
- chia/_tests/core/full_node/stores/test_sync_store.py +135 -0
- chia/_tests/core/full_node/test_address_manager.py +588 -0
- chia/_tests/core/full_node/test_block_height_map.py +556 -0
- chia/_tests/core/full_node/test_conditions.py +556 -0
- chia/_tests/core/full_node/test_full_node.py +2700 -0
- chia/_tests/core/full_node/test_generator_tools.py +82 -0
- chia/_tests/core/full_node/test_hint_management.py +104 -0
- chia/_tests/core/full_node/test_node_load.py +34 -0
- chia/_tests/core/full_node/test_performance.py +179 -0
- chia/_tests/core/full_node/test_subscriptions.py +492 -0
- chia/_tests/core/full_node/test_transactions.py +203 -0
- chia/_tests/core/full_node/test_tx_processing_queue.py +155 -0
- chia/_tests/core/large_block.py +2388 -0
- chia/_tests/core/make_block_generator.py +70 -0
- chia/_tests/core/mempool/__init__.py +0 -0
- chia/_tests/core/mempool/config.py +4 -0
- chia/_tests/core/mempool/test_mempool.py +3255 -0
- chia/_tests/core/mempool/test_mempool_fee_estimator.py +104 -0
- chia/_tests/core/mempool/test_mempool_fee_protocol.py +55 -0
- chia/_tests/core/mempool/test_mempool_item_queries.py +190 -0
- chia/_tests/core/mempool/test_mempool_manager.py +2084 -0
- chia/_tests/core/mempool/test_mempool_performance.py +64 -0
- chia/_tests/core/mempool/test_singleton_fast_forward.py +567 -0
- chia/_tests/core/node_height.py +28 -0
- chia/_tests/core/server/__init__.py +0 -0
- chia/_tests/core/server/config.py +3 -0
- chia/_tests/core/server/flood.py +84 -0
- chia/_tests/core/server/serve.py +135 -0
- chia/_tests/core/server/test_api_protocol.py +21 -0
- chia/_tests/core/server/test_capabilities.py +66 -0
- chia/_tests/core/server/test_dos.py +319 -0
- chia/_tests/core/server/test_event_loop.py +109 -0
- chia/_tests/core/server/test_loop.py +294 -0
- chia/_tests/core/server/test_node_discovery.py +73 -0
- chia/_tests/core/server/test_rate_limits.py +482 -0
- chia/_tests/core/server/test_server.py +226 -0
- chia/_tests/core/server/test_upnp.py +8 -0
- chia/_tests/core/services/__init__.py +0 -0
- chia/_tests/core/services/config.py +3 -0
- chia/_tests/core/services/test_services.py +188 -0
- chia/_tests/core/ssl/__init__.py +0 -0
- chia/_tests/core/ssl/config.py +3 -0
- chia/_tests/core/ssl/test_ssl.py +202 -0
- chia/_tests/core/test_coins.py +33 -0
- chia/_tests/core/test_cost_calculation.py +313 -0
- chia/_tests/core/test_crawler.py +175 -0
- chia/_tests/core/test_crawler_rpc.py +53 -0
- chia/_tests/core/test_daemon_rpc.py +24 -0
- chia/_tests/core/test_db_conversion.py +130 -0
- chia/_tests/core/test_db_validation.py +162 -0
- chia/_tests/core/test_farmer_harvester_rpc.py +505 -0
- chia/_tests/core/test_filter.py +35 -0
- chia/_tests/core/test_full_node_rpc.py +768 -0
- chia/_tests/core/test_merkle_set.py +343 -0
- chia/_tests/core/test_program.py +47 -0
- chia/_tests/core/test_rpc_util.py +86 -0
- chia/_tests/core/test_seeder.py +420 -0
- chia/_tests/core/test_setproctitle.py +13 -0
- chia/_tests/core/util/__init__.py +0 -0
- chia/_tests/core/util/config.py +4 -0
- chia/_tests/core/util/test_block_cache.py +44 -0
- chia/_tests/core/util/test_cached_bls.py +57 -0
- chia/_tests/core/util/test_config.py +337 -0
- chia/_tests/core/util/test_file_keyring_synchronization.py +105 -0
- chia/_tests/core/util/test_files.py +391 -0
- chia/_tests/core/util/test_jsonify.py +146 -0
- chia/_tests/core/util/test_keychain.py +522 -0
- chia/_tests/core/util/test_keyring_wrapper.py +491 -0
- chia/_tests/core/util/test_lockfile.py +380 -0
- chia/_tests/core/util/test_log_exceptions.py +187 -0
- chia/_tests/core/util/test_lru_cache.py +56 -0
- chia/_tests/core/util/test_significant_bits.py +40 -0
- chia/_tests/core/util/test_streamable.py +883 -0
- chia/_tests/db/__init__.py +0 -0
- chia/_tests/db/test_db_wrapper.py +566 -0
- chia/_tests/environments/__init__.py +0 -0
- chia/_tests/environments/common.py +35 -0
- chia/_tests/environments/full_node.py +47 -0
- chia/_tests/environments/wallet.py +429 -0
- chia/_tests/ether.py +19 -0
- chia/_tests/farmer_harvester/__init__.py +0 -0
- chia/_tests/farmer_harvester/config.py +3 -0
- chia/_tests/farmer_harvester/test_farmer.py +1264 -0
- chia/_tests/farmer_harvester/test_farmer_harvester.py +292 -0
- chia/_tests/farmer_harvester/test_filter_prefix_bits.py +131 -0
- chia/_tests/farmer_harvester/test_third_party_harvesters.py +528 -0
- chia/_tests/farmer_harvester/test_third_party_harvesters_data.json +29 -0
- chia/_tests/fee_estimation/__init__.py +0 -0
- chia/_tests/fee_estimation/config.py +3 -0
- chia/_tests/fee_estimation/test_fee_estimation_integration.py +262 -0
- chia/_tests/fee_estimation/test_fee_estimation_rpc.py +287 -0
- chia/_tests/fee_estimation/test_fee_estimation_unit_tests.py +144 -0
- chia/_tests/fee_estimation/test_mempoolitem_height_added.py +146 -0
- chia/_tests/generator/__init__.py +0 -0
- chia/_tests/generator/puzzles/__init__.py +0 -0
- chia/_tests/generator/puzzles/test_generator_deserialize.clsp +3 -0
- chia/_tests/generator/puzzles/test_generator_deserialize.clsp.hex +1 -0
- chia/_tests/generator/puzzles/test_multiple_generator_input_arguments.clsp +19 -0
- chia/_tests/generator/puzzles/test_multiple_generator_input_arguments.clsp.hex +1 -0
- chia/_tests/generator/test_compression.py +201 -0
- chia/_tests/generator/test_generator_types.py +44 -0
- chia/_tests/generator/test_rom.py +180 -0
- chia/_tests/plot_sync/__init__.py +0 -0
- chia/_tests/plot_sync/config.py +3 -0
- chia/_tests/plot_sync/test_delta.py +101 -0
- chia/_tests/plot_sync/test_plot_sync.py +618 -0
- chia/_tests/plot_sync/test_receiver.py +451 -0
- chia/_tests/plot_sync/test_sender.py +116 -0
- chia/_tests/plot_sync/test_sync_simulated.py +451 -0
- chia/_tests/plot_sync/util.py +68 -0
- chia/_tests/plotting/__init__.py +0 -0
- chia/_tests/plotting/config.py +3 -0
- chia/_tests/plotting/test_plot_manager.py +781 -0
- chia/_tests/plotting/util.py +12 -0
- chia/_tests/pools/__init__.py +0 -0
- chia/_tests/pools/config.py +5 -0
- chia/_tests/pools/test_pool_cli_parsing.py +128 -0
- chia/_tests/pools/test_pool_cmdline.py +1001 -0
- chia/_tests/pools/test_pool_config.py +42 -0
- chia/_tests/pools/test_pool_puzzles_lifecycle.py +397 -0
- chia/_tests/pools/test_pool_rpc.py +1123 -0
- chia/_tests/pools/test_pool_wallet.py +205 -0
- chia/_tests/pools/test_wallet_pool_store.py +161 -0
- chia/_tests/process_junit.py +348 -0
- chia/_tests/rpc/__init__.py +0 -0
- chia/_tests/rpc/test_rpc_client.py +138 -0
- chia/_tests/rpc/test_rpc_server.py +183 -0
- chia/_tests/simulation/__init__.py +0 -0
- chia/_tests/simulation/config.py +6 -0
- chia/_tests/simulation/test_simulation.py +501 -0
- chia/_tests/simulation/test_simulator.py +232 -0
- chia/_tests/simulation/test_start_simulator.py +107 -0
- chia/_tests/testconfig.py +13 -0
- chia/_tests/timelord/__init__.py +0 -0
- chia/_tests/timelord/config.py +3 -0
- chia/_tests/timelord/test_new_peak.py +437 -0
- chia/_tests/timelord/test_timelord.py +11 -0
- chia/_tests/tools/1315537.json +170 -0
- chia/_tests/tools/1315544.json +160 -0
- chia/_tests/tools/1315630.json +150 -0
- chia/_tests/tools/300000.json +105 -0
- chia/_tests/tools/442734.json +140 -0
- chia/_tests/tools/466212.json +130 -0
- chia/_tests/tools/__init__.py +0 -0
- chia/_tests/tools/config.py +5 -0
- chia/_tests/tools/test-blockchain-db.sqlite +0 -0
- chia/_tests/tools/test_full_sync.py +30 -0
- chia/_tests/tools/test_legacy_keyring.py +82 -0
- chia/_tests/tools/test_run_block.py +128 -0
- chia/_tests/tools/test_virtual_project.py +591 -0
- chia/_tests/util/__init__.py +0 -0
- chia/_tests/util/benchmark_cost.py +170 -0
- chia/_tests/util/benchmarks.py +153 -0
- chia/_tests/util/bip39_test_vectors.json +148 -0
- chia/_tests/util/blockchain.py +134 -0
- chia/_tests/util/blockchain_mock.py +132 -0
- chia/_tests/util/build_network_protocol_files.py +302 -0
- chia/_tests/util/clvm_generator.bin +0 -0
- chia/_tests/util/config.py +3 -0
- chia/_tests/util/constants.py +20 -0
- chia/_tests/util/db_connection.py +37 -0
- chia/_tests/util/full_sync.py +253 -0
- chia/_tests/util/gen_ssl_certs.py +114 -0
- chia/_tests/util/generator_tools_testing.py +45 -0
- chia/_tests/util/get_name_puzzle_conditions.py +52 -0
- chia/_tests/util/key_tool.py +36 -0
- chia/_tests/util/misc.py +675 -0
- chia/_tests/util/network_protocol_data.py +1072 -0
- chia/_tests/util/protocol_messages_bytes-v1.0 +0 -0
- chia/_tests/util/protocol_messages_json.py +2701 -0
- chia/_tests/util/rpc.py +26 -0
- chia/_tests/util/run_block.py +163 -0
- chia/_tests/util/setup_nodes.py +481 -0
- chia/_tests/util/spend_sim.py +492 -0
- chia/_tests/util/split_managers.py +102 -0
- chia/_tests/util/temp_file.py +14 -0
- chia/_tests/util/test_action_scope.py +144 -0
- chia/_tests/util/test_async_pool.py +366 -0
- chia/_tests/util/test_build_job_matrix.py +42 -0
- chia/_tests/util/test_build_network_protocol_files.py +7 -0
- chia/_tests/util/test_chia_version.py +50 -0
- chia/_tests/util/test_collection.py +11 -0
- chia/_tests/util/test_condition_tools.py +229 -0
- chia/_tests/util/test_config.py +426 -0
- chia/_tests/util/test_dump_keyring.py +60 -0
- chia/_tests/util/test_errors.py +10 -0
- chia/_tests/util/test_full_block_utils.py +279 -0
- chia/_tests/util/test_installed.py +20 -0
- chia/_tests/util/test_limited_semaphore.py +53 -0
- chia/_tests/util/test_logging_filter.py +42 -0
- chia/_tests/util/test_misc.py +445 -0
- chia/_tests/util/test_network.py +73 -0
- chia/_tests/util/test_network_protocol_files.py +578 -0
- chia/_tests/util/test_network_protocol_json.py +267 -0
- chia/_tests/util/test_network_protocol_test.py +256 -0
- chia/_tests/util/test_paginator.py +71 -0
- chia/_tests/util/test_pprint.py +17 -0
- chia/_tests/util/test_priority_mutex.py +488 -0
- chia/_tests/util/test_recursive_replace.py +116 -0
- chia/_tests/util/test_replace_str_to_bytes.py +137 -0
- chia/_tests/util/test_service_groups.py +15 -0
- chia/_tests/util/test_ssl_check.py +31 -0
- chia/_tests/util/test_testnet_overrides.py +19 -0
- chia/_tests/util/test_tests_misc.py +38 -0
- chia/_tests/util/test_timing.py +37 -0
- chia/_tests/util/test_trusted_peer.py +51 -0
- chia/_tests/util/time_out_assert.py +191 -0
- chia/_tests/wallet/__init__.py +0 -0
- chia/_tests/wallet/cat_wallet/__init__.py +0 -0
- chia/_tests/wallet/cat_wallet/config.py +4 -0
- chia/_tests/wallet/cat_wallet/test_cat_lifecycle.py +468 -0
- chia/_tests/wallet/cat_wallet/test_cat_outer_puzzle.py +69 -0
- chia/_tests/wallet/cat_wallet/test_cat_wallet.py +1826 -0
- chia/_tests/wallet/cat_wallet/test_offer_lifecycle.py +291 -0
- chia/_tests/wallet/cat_wallet/test_trades.py +2600 -0
- chia/_tests/wallet/clawback/__init__.py +0 -0
- chia/_tests/wallet/clawback/config.py +3 -0
- chia/_tests/wallet/clawback/test_clawback_decorator.py +78 -0
- chia/_tests/wallet/clawback/test_clawback_lifecycle.py +292 -0
- chia/_tests/wallet/clawback/test_clawback_metadata.py +50 -0
- chia/_tests/wallet/config.py +4 -0
- chia/_tests/wallet/conftest.py +278 -0
- chia/_tests/wallet/dao_wallet/__init__.py +0 -0
- chia/_tests/wallet/dao_wallet/config.py +3 -0
- chia/_tests/wallet/dao_wallet/test_dao_clvm.py +1330 -0
- chia/_tests/wallet/dao_wallet/test_dao_wallets.py +3488 -0
- chia/_tests/wallet/db_wallet/__init__.py +0 -0
- chia/_tests/wallet/db_wallet/config.py +3 -0
- chia/_tests/wallet/db_wallet/test_db_graftroot.py +141 -0
- chia/_tests/wallet/db_wallet/test_dl_offers.py +491 -0
- chia/_tests/wallet/db_wallet/test_dl_wallet.py +823 -0
- chia/_tests/wallet/did_wallet/__init__.py +0 -0
- chia/_tests/wallet/did_wallet/config.py +4 -0
- chia/_tests/wallet/did_wallet/test_did.py +2284 -0
- chia/_tests/wallet/nft_wallet/__init__.py +0 -0
- chia/_tests/wallet/nft_wallet/config.py +4 -0
- chia/_tests/wallet/nft_wallet/test_nft_1_offers.py +1493 -0
- chia/_tests/wallet/nft_wallet/test_nft_bulk_mint.py +1024 -0
- chia/_tests/wallet/nft_wallet/test_nft_lifecycle.py +375 -0
- chia/_tests/wallet/nft_wallet/test_nft_offers.py +1209 -0
- chia/_tests/wallet/nft_wallet/test_nft_puzzles.py +172 -0
- chia/_tests/wallet/nft_wallet/test_nft_wallet.py +2584 -0
- chia/_tests/wallet/nft_wallet/test_ownership_outer_puzzle.py +70 -0
- chia/_tests/wallet/rpc/__init__.py +0 -0
- chia/_tests/wallet/rpc/config.py +4 -0
- chia/_tests/wallet/rpc/test_dl_wallet_rpc.py +285 -0
- chia/_tests/wallet/rpc/test_wallet_rpc.py +3153 -0
- chia/_tests/wallet/simple_sync/__init__.py +0 -0
- chia/_tests/wallet/simple_sync/config.py +3 -0
- chia/_tests/wallet/simple_sync/test_simple_sync_protocol.py +718 -0
- chia/_tests/wallet/sync/__init__.py +0 -0
- chia/_tests/wallet/sync/config.py +4 -0
- chia/_tests/wallet/sync/test_wallet_sync.py +1692 -0
- chia/_tests/wallet/test_address_type.py +189 -0
- chia/_tests/wallet/test_bech32m.py +45 -0
- chia/_tests/wallet/test_clvm_streamable.py +244 -0
- chia/_tests/wallet/test_coin_management.py +354 -0
- chia/_tests/wallet/test_coin_selection.py +588 -0
- chia/_tests/wallet/test_conditions.py +400 -0
- chia/_tests/wallet/test_debug_spend_bundle.py +218 -0
- chia/_tests/wallet/test_new_wallet_protocol.py +1174 -0
- chia/_tests/wallet/test_nft_store.py +192 -0
- chia/_tests/wallet/test_notifications.py +196 -0
- chia/_tests/wallet/test_offer_parsing_performance.py +48 -0
- chia/_tests/wallet/test_puzzle_store.py +132 -0
- chia/_tests/wallet/test_sign_coin_spends.py +159 -0
- chia/_tests/wallet/test_signer_protocol.py +947 -0
- chia/_tests/wallet/test_singleton.py +122 -0
- chia/_tests/wallet/test_singleton_lifecycle_fast.py +772 -0
- chia/_tests/wallet/test_singleton_store.py +152 -0
- chia/_tests/wallet/test_taproot.py +19 -0
- chia/_tests/wallet/test_transaction_store.py +945 -0
- chia/_tests/wallet/test_util.py +185 -0
- chia/_tests/wallet/test_wallet.py +2139 -0
- chia/_tests/wallet/test_wallet_action_scope.py +85 -0
- chia/_tests/wallet/test_wallet_blockchain.py +111 -0
- chia/_tests/wallet/test_wallet_coin_store.py +1002 -0
- chia/_tests/wallet/test_wallet_interested_store.py +43 -0
- chia/_tests/wallet/test_wallet_key_val_store.py +40 -0
- chia/_tests/wallet/test_wallet_node.py +780 -0
- chia/_tests/wallet/test_wallet_retry.py +95 -0
- chia/_tests/wallet/test_wallet_state_manager.py +259 -0
- chia/_tests/wallet/test_wallet_test_framework.py +275 -0
- chia/_tests/wallet/test_wallet_trade_store.py +218 -0
- chia/_tests/wallet/test_wallet_user_store.py +34 -0
- chia/_tests/wallet/test_wallet_utils.py +156 -0
- chia/_tests/wallet/vc_wallet/__init__.py +0 -0
- chia/_tests/wallet/vc_wallet/config.py +3 -0
- chia/_tests/wallet/vc_wallet/test_cr_outer_puzzle.py +70 -0
- chia/_tests/wallet/vc_wallet/test_vc_lifecycle.py +883 -0
- chia/_tests/wallet/vc_wallet/test_vc_wallet.py +830 -0
- chia/_tests/wallet/wallet_block_tools.py +327 -0
- chia/_tests/weight_proof/__init__.py +0 -0
- chia/_tests/weight_proof/config.py +3 -0
- chia/_tests/weight_proof/test_weight_proof.py +528 -0
- chia/apis.py +19 -0
- chia/clvm/__init__.py +0 -0
- chia/cmds/__init__.py +0 -0
- chia/cmds/beta.py +184 -0
- chia/cmds/beta_funcs.py +137 -0
- chia/cmds/check_wallet_db.py +420 -0
- chia/cmds/chia.py +151 -0
- chia/cmds/cmd_classes.py +323 -0
- chia/cmds/cmd_helpers.py +242 -0
- chia/cmds/cmds_util.py +488 -0
- chia/cmds/coin_funcs.py +275 -0
- chia/cmds/coins.py +182 -0
- chia/cmds/completion.py +49 -0
- chia/cmds/configure.py +332 -0
- chia/cmds/dao.py +1064 -0
- chia/cmds/dao_funcs.py +598 -0
- chia/cmds/data.py +708 -0
- chia/cmds/data_funcs.py +385 -0
- chia/cmds/db.py +87 -0
- chia/cmds/db_backup_func.py +77 -0
- chia/cmds/db_upgrade_func.py +452 -0
- chia/cmds/db_validate_func.py +184 -0
- chia/cmds/dev.py +18 -0
- chia/cmds/farm.py +100 -0
- chia/cmds/farm_funcs.py +200 -0
- chia/cmds/gh.py +275 -0
- chia/cmds/init.py +63 -0
- chia/cmds/init_funcs.py +367 -0
- chia/cmds/installers.py +131 -0
- chia/cmds/keys.py +527 -0
- chia/cmds/keys_funcs.py +863 -0
- chia/cmds/netspace.py +50 -0
- chia/cmds/netspace_funcs.py +54 -0
- chia/cmds/options.py +32 -0
- chia/cmds/param_types.py +238 -0
- chia/cmds/passphrase.py +131 -0
- chia/cmds/passphrase_funcs.py +292 -0
- chia/cmds/peer.py +51 -0
- chia/cmds/peer_funcs.py +129 -0
- chia/cmds/plotnft.py +260 -0
- chia/cmds/plotnft_funcs.py +405 -0
- chia/cmds/plots.py +230 -0
- chia/cmds/plotters.py +18 -0
- chia/cmds/rpc.py +208 -0
- chia/cmds/show.py +72 -0
- chia/cmds/show_funcs.py +215 -0
- chia/cmds/signer.py +296 -0
- chia/cmds/sim.py +225 -0
- chia/cmds/sim_funcs.py +509 -0
- chia/cmds/start.py +24 -0
- chia/cmds/start_funcs.py +109 -0
- chia/cmds/stop.py +62 -0
- chia/cmds/units.py +9 -0
- chia/cmds/wallet.py +1901 -0
- chia/cmds/wallet_funcs.py +1874 -0
- chia/consensus/__init__.py +0 -0
- chia/consensus/block_body_validation.py +562 -0
- chia/consensus/block_creation.py +546 -0
- chia/consensus/block_header_validation.py +1059 -0
- chia/consensus/block_record.py +31 -0
- chia/consensus/block_rewards.py +53 -0
- chia/consensus/blockchain.py +1087 -0
- chia/consensus/blockchain_interface.py +56 -0
- chia/consensus/coinbase.py +30 -0
- chia/consensus/condition_costs.py +9 -0
- chia/consensus/constants.py +49 -0
- chia/consensus/cost_calculator.py +15 -0
- chia/consensus/default_constants.py +89 -0
- chia/consensus/deficit.py +55 -0
- chia/consensus/difficulty_adjustment.py +412 -0
- chia/consensus/find_fork_point.py +111 -0
- chia/consensus/full_block_to_block_record.py +167 -0
- chia/consensus/get_block_challenge.py +106 -0
- chia/consensus/get_block_generator.py +27 -0
- chia/consensus/make_sub_epoch_summary.py +210 -0
- chia/consensus/multiprocess_validation.py +268 -0
- chia/consensus/pos_quality.py +19 -0
- chia/consensus/pot_iterations.py +67 -0
- chia/consensus/puzzles/__init__.py +0 -0
- chia/consensus/puzzles/chialisp_deserialisation.clsp +69 -0
- chia/consensus/puzzles/chialisp_deserialisation.clsp.hex +1 -0
- chia/consensus/puzzles/rom_bootstrap_generator.clsp +37 -0
- chia/consensus/puzzles/rom_bootstrap_generator.clsp.hex +1 -0
- chia/consensus/vdf_info_computation.py +156 -0
- chia/daemon/__init__.py +0 -0
- chia/daemon/client.py +252 -0
- chia/daemon/keychain_proxy.py +502 -0
- chia/daemon/keychain_server.py +365 -0
- chia/daemon/server.py +1606 -0
- chia/daemon/windows_signal.py +56 -0
- chia/data_layer/__init__.py +0 -0
- chia/data_layer/data_layer.py +1291 -0
- chia/data_layer/data_layer_api.py +33 -0
- chia/data_layer/data_layer_errors.py +50 -0
- chia/data_layer/data_layer_server.py +170 -0
- chia/data_layer/data_layer_util.py +985 -0
- chia/data_layer/data_layer_wallet.py +1311 -0
- chia/data_layer/data_store.py +2267 -0
- chia/data_layer/dl_wallet_store.py +407 -0
- chia/data_layer/download_data.py +389 -0
- chia/data_layer/puzzles/__init__.py +0 -0
- chia/data_layer/puzzles/graftroot_dl_offers.clsp +100 -0
- chia/data_layer/puzzles/graftroot_dl_offers.clsp.hex +1 -0
- chia/data_layer/s3_plugin_config.yml +33 -0
- chia/data_layer/s3_plugin_service.py +468 -0
- chia/data_layer/util/__init__.py +0 -0
- chia/data_layer/util/benchmark.py +107 -0
- chia/data_layer/util/plugin.py +40 -0
- chia/farmer/__init__.py +0 -0
- chia/farmer/farmer.py +923 -0
- chia/farmer/farmer_api.py +820 -0
- chia/full_node/__init__.py +0 -0
- chia/full_node/bitcoin_fee_estimator.py +85 -0
- chia/full_node/block_height_map.py +271 -0
- chia/full_node/block_store.py +576 -0
- chia/full_node/bundle_tools.py +19 -0
- chia/full_node/coin_store.py +647 -0
- chia/full_node/fee_estimate.py +54 -0
- chia/full_node/fee_estimate_store.py +24 -0
- chia/full_node/fee_estimation.py +92 -0
- chia/full_node/fee_estimator.py +90 -0
- chia/full_node/fee_estimator_constants.py +38 -0
- chia/full_node/fee_estimator_interface.py +42 -0
- chia/full_node/fee_history.py +25 -0
- chia/full_node/fee_tracker.py +564 -0
- chia/full_node/full_node.py +3327 -0
- chia/full_node/full_node_api.py +2025 -0
- chia/full_node/full_node_store.py +1033 -0
- chia/full_node/hint_management.py +56 -0
- chia/full_node/hint_store.py +93 -0
- chia/full_node/mempool.py +589 -0
- chia/full_node/mempool_check_conditions.py +146 -0
- chia/full_node/mempool_manager.py +853 -0
- chia/full_node/pending_tx_cache.py +112 -0
- chia/full_node/puzzles/__init__.py +0 -0
- chia/full_node/puzzles/block_program_zero.clsp +14 -0
- chia/full_node/puzzles/block_program_zero.clsp.hex +1 -0
- chia/full_node/puzzles/decompress_coin_spend_entry.clsp +5 -0
- chia/full_node/puzzles/decompress_coin_spend_entry.clsp.hex +1 -0
- chia/full_node/puzzles/decompress_coin_spend_entry_with_prefix.clsp +7 -0
- chia/full_node/puzzles/decompress_coin_spend_entry_with_prefix.clsp.hex +1 -0
- chia/full_node/puzzles/decompress_puzzle.clsp +6 -0
- chia/full_node/puzzles/decompress_puzzle.clsp.hex +1 -0
- chia/full_node/signage_point.py +16 -0
- chia/full_node/subscriptions.py +247 -0
- chia/full_node/sync_store.py +146 -0
- chia/full_node/tx_processing_queue.py +78 -0
- chia/full_node/util/__init__.py +0 -0
- chia/full_node/weight_proof.py +1720 -0
- chia/harvester/__init__.py +0 -0
- chia/harvester/harvester.py +272 -0
- chia/harvester/harvester_api.py +380 -0
- chia/introducer/__init__.py +0 -0
- chia/introducer/introducer.py +122 -0
- chia/introducer/introducer_api.py +70 -0
- chia/legacy/__init__.py +0 -0
- chia/legacy/keyring.py +155 -0
- chia/plot_sync/__init__.py +0 -0
- chia/plot_sync/delta.py +61 -0
- chia/plot_sync/exceptions.py +56 -0
- chia/plot_sync/receiver.py +386 -0
- chia/plot_sync/sender.py +340 -0
- chia/plot_sync/util.py +43 -0
- chia/plotters/__init__.py +0 -0
- chia/plotters/bladebit.py +388 -0
- chia/plotters/chiapos.py +63 -0
- chia/plotters/madmax.py +224 -0
- chia/plotters/plotters.py +577 -0
- chia/plotters/plotters_util.py +133 -0
- chia/plotting/__init__.py +0 -0
- chia/plotting/cache.py +213 -0
- chia/plotting/check_plots.py +283 -0
- chia/plotting/create_plots.py +278 -0
- chia/plotting/manager.py +436 -0
- chia/plotting/util.py +336 -0
- chia/pools/__init__.py +0 -0
- chia/pools/pool_config.py +110 -0
- chia/pools/pool_puzzles.py +459 -0
- chia/pools/pool_wallet.py +933 -0
- chia/pools/pool_wallet_info.py +118 -0
- chia/pools/puzzles/__init__.py +0 -0
- chia/pools/puzzles/pool_member_innerpuz.clsp +70 -0
- chia/pools/puzzles/pool_member_innerpuz.clsp.hex +1 -0
- chia/pools/puzzles/pool_waitingroom_innerpuz.clsp +69 -0
- chia/pools/puzzles/pool_waitingroom_innerpuz.clsp.hex +1 -0
- chia/protocols/__init__.py +0 -0
- chia/protocols/farmer_protocol.py +102 -0
- chia/protocols/full_node_protocol.py +219 -0
- chia/protocols/harvester_protocol.py +216 -0
- chia/protocols/introducer_protocol.py +25 -0
- chia/protocols/pool_protocol.py +177 -0
- chia/protocols/protocol_message_types.py +139 -0
- chia/protocols/protocol_state_machine.py +87 -0
- chia/protocols/protocol_timing.py +8 -0
- chia/protocols/shared_protocol.py +86 -0
- chia/protocols/timelord_protocol.py +93 -0
- chia/protocols/wallet_protocol.py +401 -0
- chia/py.typed +0 -0
- chia/rpc/__init__.py +0 -0
- chia/rpc/crawler_rpc_api.py +80 -0
- chia/rpc/data_layer_rpc_api.py +644 -0
- chia/rpc/data_layer_rpc_client.py +188 -0
- chia/rpc/data_layer_rpc_util.py +58 -0
- chia/rpc/farmer_rpc_api.py +365 -0
- chia/rpc/farmer_rpc_client.py +86 -0
- chia/rpc/full_node_rpc_api.py +959 -0
- chia/rpc/full_node_rpc_client.py +292 -0
- chia/rpc/harvester_rpc_api.py +141 -0
- chia/rpc/harvester_rpc_client.py +54 -0
- chia/rpc/rpc_client.py +164 -0
- chia/rpc/rpc_server.py +521 -0
- chia/rpc/timelord_rpc_api.py +32 -0
- chia/rpc/util.py +93 -0
- chia/rpc/wallet_request_types.py +904 -0
- chia/rpc/wallet_rpc_api.py +4943 -0
- chia/rpc/wallet_rpc_client.py +1814 -0
- chia/seeder/__init__.py +0 -0
- chia/seeder/crawl_store.py +425 -0
- chia/seeder/crawler.py +410 -0
- chia/seeder/crawler_api.py +135 -0
- chia/seeder/dns_server.py +593 -0
- chia/seeder/peer_record.py +146 -0
- chia/seeder/start_crawler.py +92 -0
- chia/server/__init__.py +0 -0
- chia/server/address_manager.py +658 -0
- chia/server/address_manager_store.py +237 -0
- chia/server/api_protocol.py +116 -0
- chia/server/capabilities.py +24 -0
- chia/server/chia_policy.py +346 -0
- chia/server/introducer_peers.py +76 -0
- chia/server/node_discovery.py +714 -0
- chia/server/outbound_message.py +33 -0
- chia/server/rate_limit_numbers.py +214 -0
- chia/server/rate_limits.py +153 -0
- chia/server/server.py +741 -0
- chia/server/signal_handlers.py +120 -0
- chia/server/ssl_context.py +32 -0
- chia/server/start_data_layer.py +151 -0
- chia/server/start_farmer.py +98 -0
- chia/server/start_full_node.py +112 -0
- chia/server/start_harvester.py +93 -0
- chia/server/start_introducer.py +81 -0
- chia/server/start_service.py +316 -0
- chia/server/start_timelord.py +89 -0
- chia/server/start_wallet.py +113 -0
- chia/server/upnp.py +118 -0
- chia/server/ws_connection.py +766 -0
- chia/simulator/__init__.py +0 -0
- chia/simulator/add_blocks_in_batches.py +54 -0
- chia/simulator/block_tools.py +2054 -0
- chia/simulator/full_node_simulator.py +794 -0
- chia/simulator/keyring.py +128 -0
- chia/simulator/setup_services.py +506 -0
- chia/simulator/simulator_constants.py +13 -0
- chia/simulator/simulator_full_node_rpc_api.py +99 -0
- chia/simulator/simulator_full_node_rpc_client.py +60 -0
- chia/simulator/simulator_protocol.py +29 -0
- chia/simulator/simulator_test_tools.py +164 -0
- chia/simulator/socket.py +24 -0
- chia/simulator/ssl_certs.py +114 -0
- chia/simulator/ssl_certs_1.py +697 -0
- chia/simulator/ssl_certs_10.py +697 -0
- chia/simulator/ssl_certs_2.py +697 -0
- chia/simulator/ssl_certs_3.py +697 -0
- chia/simulator/ssl_certs_4.py +697 -0
- chia/simulator/ssl_certs_5.py +697 -0
- chia/simulator/ssl_certs_6.py +697 -0
- chia/simulator/ssl_certs_7.py +697 -0
- chia/simulator/ssl_certs_8.py +697 -0
- chia/simulator/ssl_certs_9.py +697 -0
- chia/simulator/start_simulator.py +143 -0
- chia/simulator/wallet_tools.py +246 -0
- chia/ssl/__init__.py +0 -0
- chia/ssl/chia_ca.crt +19 -0
- chia/ssl/chia_ca.key +28 -0
- chia/ssl/create_ssl.py +249 -0
- chia/ssl/dst_root_ca.pem +20 -0
- chia/timelord/__init__.py +0 -0
- chia/timelord/iters_from_block.py +50 -0
- chia/timelord/timelord.py +1226 -0
- chia/timelord/timelord_api.py +138 -0
- chia/timelord/timelord_launcher.py +190 -0
- chia/timelord/timelord_state.py +244 -0
- chia/timelord/types.py +22 -0
- chia/types/__init__.py +0 -0
- chia/types/aliases.py +35 -0
- chia/types/block_protocol.py +20 -0
- chia/types/blockchain_format/__init__.py +0 -0
- chia/types/blockchain_format/classgroup.py +5 -0
- chia/types/blockchain_format/coin.py +28 -0
- chia/types/blockchain_format/foliage.py +8 -0
- chia/types/blockchain_format/pool_target.py +5 -0
- chia/types/blockchain_format/program.py +269 -0
- chia/types/blockchain_format/proof_of_space.py +135 -0
- chia/types/blockchain_format/reward_chain_block.py +6 -0
- chia/types/blockchain_format/serialized_program.py +5 -0
- chia/types/blockchain_format/sized_bytes.py +11 -0
- chia/types/blockchain_format/slots.py +9 -0
- chia/types/blockchain_format/sub_epoch_summary.py +5 -0
- chia/types/blockchain_format/tree_hash.py +72 -0
- chia/types/blockchain_format/vdf.py +86 -0
- chia/types/clvm_cost.py +13 -0
- chia/types/coin_record.py +43 -0
- chia/types/coin_spend.py +115 -0
- chia/types/condition_opcodes.py +73 -0
- chia/types/condition_with_args.py +16 -0
- chia/types/eligible_coin_spends.py +365 -0
- chia/types/end_of_slot_bundle.py +5 -0
- chia/types/fee_rate.py +38 -0
- chia/types/full_block.py +5 -0
- chia/types/generator_types.py +13 -0
- chia/types/header_block.py +5 -0
- chia/types/internal_mempool_item.py +18 -0
- chia/types/mempool_inclusion_status.py +9 -0
- chia/types/mempool_item.py +85 -0
- chia/types/mempool_submission_status.py +30 -0
- chia/types/mojos.py +7 -0
- chia/types/peer_info.py +64 -0
- chia/types/signing_mode.py +29 -0
- chia/types/spend_bundle.py +30 -0
- chia/types/spend_bundle_conditions.py +7 -0
- chia/types/transaction_queue_entry.py +55 -0
- chia/types/unfinished_block.py +5 -0
- chia/types/unfinished_header_block.py +37 -0
- chia/types/validation_state.py +14 -0
- chia/types/weight_proof.py +49 -0
- chia/util/__init__.py +0 -0
- chia/util/action_scope.py +168 -0
- chia/util/async_pool.py +226 -0
- chia/util/augmented_chain.py +134 -0
- chia/util/batches.py +42 -0
- chia/util/bech32m.py +126 -0
- chia/util/beta_metrics.py +119 -0
- chia/util/block_cache.py +56 -0
- chia/util/byte_types.py +12 -0
- chia/util/check_fork_next_block.py +33 -0
- chia/util/chia_logging.py +144 -0
- chia/util/chia_version.py +33 -0
- chia/util/collection.py +17 -0
- chia/util/condition_tools.py +201 -0
- chia/util/config.py +367 -0
- chia/util/cpu.py +22 -0
- chia/util/db_synchronous.py +23 -0
- chia/util/db_version.py +32 -0
- chia/util/db_wrapper.py +430 -0
- chia/util/default_root.py +27 -0
- chia/util/dump_keyring.py +93 -0
- chia/util/english.txt +2048 -0
- chia/util/errors.py +353 -0
- chia/util/file_keyring.py +469 -0
- chia/util/files.py +97 -0
- chia/util/full_block_utils.py +345 -0
- chia/util/generator_tools.py +72 -0
- chia/util/hash.py +31 -0
- chia/util/initial-config.yaml +694 -0
- chia/util/inline_executor.py +26 -0
- chia/util/ints.py +19 -0
- chia/util/ip_address.py +39 -0
- chia/util/json_util.py +37 -0
- chia/util/keychain.py +676 -0
- chia/util/keyring_wrapper.py +327 -0
- chia/util/limited_semaphore.py +41 -0
- chia/util/lock.py +49 -0
- chia/util/log_exceptions.py +32 -0
- chia/util/logging.py +36 -0
- chia/util/lru_cache.py +31 -0
- chia/util/math.py +20 -0
- chia/util/network.py +182 -0
- chia/util/paginator.py +48 -0
- chia/util/path.py +31 -0
- chia/util/permissions.py +20 -0
- chia/util/prev_transaction_block.py +21 -0
- chia/util/priority_mutex.py +95 -0
- chia/util/profiler.py +197 -0
- chia/util/recursive_replace.py +24 -0
- chia/util/safe_cancel_task.py +16 -0
- chia/util/service_groups.py +47 -0
- chia/util/setproctitle.py +22 -0
- chia/util/significant_bits.py +32 -0
- chia/util/ssl_check.py +213 -0
- chia/util/streamable.py +642 -0
- chia/util/task_referencer.py +59 -0
- chia/util/task_timing.py +382 -0
- chia/util/timing.py +67 -0
- chia/util/vdf_prover.py +30 -0
- chia/util/virtual_project_analysis.py +540 -0
- chia/util/ws_message.py +66 -0
- chia/wallet/__init__.py +0 -0
- chia/wallet/cat_wallet/__init__.py +0 -0
- chia/wallet/cat_wallet/cat_constants.py +75 -0
- chia/wallet/cat_wallet/cat_info.py +47 -0
- chia/wallet/cat_wallet/cat_outer_puzzle.py +120 -0
- chia/wallet/cat_wallet/cat_utils.py +164 -0
- chia/wallet/cat_wallet/cat_wallet.py +855 -0
- chia/wallet/cat_wallet/dao_cat_info.py +28 -0
- chia/wallet/cat_wallet/dao_cat_wallet.py +669 -0
- chia/wallet/cat_wallet/lineage_store.py +74 -0
- chia/wallet/cat_wallet/puzzles/__init__.py +0 -0
- chia/wallet/cat_wallet/puzzles/cat_truths.clib +31 -0
- chia/wallet/cat_wallet/puzzles/cat_v2.clsp +397 -0
- chia/wallet/cat_wallet/puzzles/cat_v2.clsp.hex +1 -0
- chia/wallet/cat_wallet/puzzles/delegated_tail.clsp +25 -0
- chia/wallet/cat_wallet/puzzles/delegated_tail.clsp.hex +1 -0
- chia/wallet/cat_wallet/puzzles/everything_with_signature.clsp +15 -0
- chia/wallet/cat_wallet/puzzles/everything_with_signature.clsp.hex +1 -0
- chia/wallet/cat_wallet/puzzles/genesis_by_coin_id.clsp +26 -0
- chia/wallet/cat_wallet/puzzles/genesis_by_coin_id.clsp.hex +1 -0
- chia/wallet/cat_wallet/puzzles/genesis_by_coin_id_or_singleton.clsp +42 -0
- chia/wallet/cat_wallet/puzzles/genesis_by_coin_id_or_singleton.clsp.hex +1 -0
- chia/wallet/cat_wallet/puzzles/genesis_by_puzzle_hash.clsp +24 -0
- chia/wallet/cat_wallet/puzzles/genesis_by_puzzle_hash.clsp.hex +1 -0
- chia/wallet/coin_selection.py +188 -0
- chia/wallet/conditions.py +1512 -0
- chia/wallet/dao_wallet/__init__.py +0 -0
- chia/wallet/dao_wallet/dao_info.py +61 -0
- chia/wallet/dao_wallet/dao_utils.py +811 -0
- chia/wallet/dao_wallet/dao_wallet.py +2119 -0
- chia/wallet/db_wallet/__init__.py +0 -0
- chia/wallet/db_wallet/db_wallet_puzzles.py +111 -0
- chia/wallet/derivation_record.py +30 -0
- chia/wallet/derive_keys.py +146 -0
- chia/wallet/did_wallet/__init__.py +0 -0
- chia/wallet/did_wallet/did_info.py +39 -0
- chia/wallet/did_wallet/did_wallet.py +1494 -0
- chia/wallet/did_wallet/did_wallet_puzzles.py +221 -0
- chia/wallet/did_wallet/puzzles/__init__.py +0 -0
- chia/wallet/did_wallet/puzzles/did_innerpuz.clsp +135 -0
- chia/wallet/did_wallet/puzzles/did_innerpuz.clsp.hex +1 -0
- chia/wallet/driver_protocol.py +26 -0
- chia/wallet/key_val_store.py +55 -0
- chia/wallet/lineage_proof.py +58 -0
- chia/wallet/nft_wallet/__init__.py +0 -0
- chia/wallet/nft_wallet/metadata_outer_puzzle.py +92 -0
- chia/wallet/nft_wallet/nft_info.py +120 -0
- chia/wallet/nft_wallet/nft_puzzles.py +305 -0
- chia/wallet/nft_wallet/nft_wallet.py +1687 -0
- chia/wallet/nft_wallet/ownership_outer_puzzle.py +101 -0
- chia/wallet/nft_wallet/puzzles/__init__.py +0 -0
- chia/wallet/nft_wallet/puzzles/create_nft_launcher_from_did.clsp +6 -0
- chia/wallet/nft_wallet/puzzles/create_nft_launcher_from_did.clsp.hex +1 -0
- chia/wallet/nft_wallet/puzzles/nft_intermediate_launcher.clsp +6 -0
- chia/wallet/nft_wallet/puzzles/nft_intermediate_launcher.clsp.hex +1 -0
- chia/wallet/nft_wallet/puzzles/nft_metadata_updater_default.clsp +30 -0
- chia/wallet/nft_wallet/puzzles/nft_metadata_updater_default.clsp.hex +1 -0
- chia/wallet/nft_wallet/puzzles/nft_metadata_updater_updateable.clsp +28 -0
- chia/wallet/nft_wallet/puzzles/nft_metadata_updater_updateable.clsp.hex +1 -0
- chia/wallet/nft_wallet/puzzles/nft_ownership_layer.clsp +100 -0
- chia/wallet/nft_wallet/puzzles/nft_ownership_layer.clsp.hex +1 -0
- chia/wallet/nft_wallet/puzzles/nft_ownership_transfer_program_one_way_claim_with_royalties.clsp +78 -0
- chia/wallet/nft_wallet/puzzles/nft_ownership_transfer_program_one_way_claim_with_royalties.clsp.hex +1 -0
- chia/wallet/nft_wallet/puzzles/nft_state_layer.clsp +74 -0
- chia/wallet/nft_wallet/puzzles/nft_state_layer.clsp.hex +1 -0
- chia/wallet/nft_wallet/singleton_outer_puzzle.py +101 -0
- chia/wallet/nft_wallet/transfer_program_puzzle.py +82 -0
- chia/wallet/nft_wallet/uncurry_nft.py +217 -0
- chia/wallet/notification_manager.py +117 -0
- chia/wallet/notification_store.py +178 -0
- chia/wallet/outer_puzzles.py +84 -0
- chia/wallet/payment.py +33 -0
- chia/wallet/puzzle_drivers.py +118 -0
- chia/wallet/puzzles/__init__.py +0 -0
- chia/wallet/puzzles/augmented_condition.clsp +13 -0
- chia/wallet/puzzles/augmented_condition.clsp.hex +1 -0
- chia/wallet/puzzles/clawback/__init__.py +0 -0
- chia/wallet/puzzles/clawback/drivers.py +188 -0
- chia/wallet/puzzles/clawback/metadata.py +38 -0
- chia/wallet/puzzles/clawback/puzzle_decorator.py +67 -0
- chia/wallet/puzzles/condition_codes.clib +77 -0
- chia/wallet/puzzles/curry-and-treehash.clib +102 -0
- chia/wallet/puzzles/curry.clib +135 -0
- chia/wallet/puzzles/curry_by_index.clib +16 -0
- chia/wallet/puzzles/dao_cat_eve.clsp +17 -0
- chia/wallet/puzzles/dao_cat_eve.clsp.hex +1 -0
- chia/wallet/puzzles/dao_cat_launcher.clsp +36 -0
- chia/wallet/puzzles/dao_cat_launcher.clsp.hex +1 -0
- chia/wallet/puzzles/dao_finished_state.clsp +35 -0
- chia/wallet/puzzles/dao_finished_state.clsp.hex +1 -0
- chia/wallet/puzzles/dao_finished_state.clsp.hex.sha256tree +1 -0
- chia/wallet/puzzles/dao_lockup.clsp +288 -0
- chia/wallet/puzzles/dao_lockup.clsp.hex +1 -0
- chia/wallet/puzzles/dao_lockup.clsp.hex.sha256tree +1 -0
- chia/wallet/puzzles/dao_proposal.clsp +377 -0
- chia/wallet/puzzles/dao_proposal.clsp.hex +1 -0
- chia/wallet/puzzles/dao_proposal.clsp.hex.sha256tree +1 -0
- chia/wallet/puzzles/dao_proposal_timer.clsp +78 -0
- chia/wallet/puzzles/dao_proposal_timer.clsp.hex +1 -0
- chia/wallet/puzzles/dao_proposal_timer.clsp.hex.sha256tree +1 -0
- chia/wallet/puzzles/dao_proposal_validator.clsp +87 -0
- chia/wallet/puzzles/dao_proposal_validator.clsp.hex +1 -0
- chia/wallet/puzzles/dao_proposal_validator.clsp.hex.sha256tree +1 -0
- chia/wallet/puzzles/dao_spend_p2_singleton_v2.clsp +240 -0
- chia/wallet/puzzles/dao_spend_p2_singleton_v2.clsp.hex +1 -0
- chia/wallet/puzzles/dao_spend_p2_singleton_v2.clsp.hex.sha256tree +1 -0
- chia/wallet/puzzles/dao_treasury.clsp +115 -0
- chia/wallet/puzzles/dao_treasury.clsp.hex +1 -0
- chia/wallet/puzzles/dao_update_proposal.clsp +44 -0
- chia/wallet/puzzles/dao_update_proposal.clsp.hex +1 -0
- chia/wallet/puzzles/deployed_puzzle_hashes.json +67 -0
- chia/wallet/puzzles/json.clib +25 -0
- chia/wallet/puzzles/load_clvm.py +161 -0
- chia/wallet/puzzles/merkle_utils.clib +18 -0
- chia/wallet/puzzles/notification.clsp +7 -0
- chia/wallet/puzzles/notification.clsp.hex +1 -0
- chia/wallet/puzzles/p2_1_of_n.clsp +22 -0
- chia/wallet/puzzles/p2_1_of_n.clsp.hex +1 -0
- chia/wallet/puzzles/p2_conditions.clsp +3 -0
- chia/wallet/puzzles/p2_conditions.clsp.hex +1 -0
- chia/wallet/puzzles/p2_conditions.py +26 -0
- chia/wallet/puzzles/p2_delegated_conditions.clsp +18 -0
- chia/wallet/puzzles/p2_delegated_conditions.clsp.hex +1 -0
- chia/wallet/puzzles/p2_delegated_conditions.py +21 -0
- chia/wallet/puzzles/p2_delegated_puzzle.clsp +19 -0
- chia/wallet/puzzles/p2_delegated_puzzle.clsp.hex +1 -0
- chia/wallet/puzzles/p2_delegated_puzzle.py +34 -0
- chia/wallet/puzzles/p2_delegated_puzzle_or_hidden_puzzle.clsp +91 -0
- chia/wallet/puzzles/p2_delegated_puzzle_or_hidden_puzzle.clsp.hex +1 -0
- chia/wallet/puzzles/p2_delegated_puzzle_or_hidden_puzzle.py +160 -0
- chia/wallet/puzzles/p2_m_of_n_delegate_direct.clsp +108 -0
- chia/wallet/puzzles/p2_m_of_n_delegate_direct.clsp.hex +1 -0
- chia/wallet/puzzles/p2_m_of_n_delegate_direct.py +21 -0
- chia/wallet/puzzles/p2_parent.clsp +19 -0
- chia/wallet/puzzles/p2_parent.clsp.hex +1 -0
- chia/wallet/puzzles/p2_puzzle_hash.clsp +18 -0
- chia/wallet/puzzles/p2_puzzle_hash.clsp.hex +1 -0
- chia/wallet/puzzles/p2_puzzle_hash.py +27 -0
- chia/wallet/puzzles/p2_singleton.clsp +30 -0
- chia/wallet/puzzles/p2_singleton.clsp.hex +1 -0
- chia/wallet/puzzles/p2_singleton_aggregator.clsp +81 -0
- chia/wallet/puzzles/p2_singleton_aggregator.clsp.hex +1 -0
- chia/wallet/puzzles/p2_singleton_or_delayed_puzhash.clsp +50 -0
- chia/wallet/puzzles/p2_singleton_or_delayed_puzhash.clsp.hex +1 -0
- chia/wallet/puzzles/p2_singleton_via_delegated_puzzle.clsp +47 -0
- chia/wallet/puzzles/p2_singleton_via_delegated_puzzle.clsp.hex +1 -0
- chia/wallet/puzzles/puzzle_utils.py +34 -0
- chia/wallet/puzzles/settlement_payments.clsp +49 -0
- chia/wallet/puzzles/settlement_payments.clsp.hex +1 -0
- chia/wallet/puzzles/sha256tree.clib +11 -0
- chia/wallet/puzzles/singleton_launcher.clsp +16 -0
- chia/wallet/puzzles/singleton_launcher.clsp.hex +1 -0
- chia/wallet/puzzles/singleton_top_layer.clsp +177 -0
- chia/wallet/puzzles/singleton_top_layer.clsp.hex +1 -0
- chia/wallet/puzzles/singleton_top_layer.py +296 -0
- chia/wallet/puzzles/singleton_top_layer_v1_1.clsp +107 -0
- chia/wallet/puzzles/singleton_top_layer_v1_1.clsp.hex +1 -0
- chia/wallet/puzzles/singleton_top_layer_v1_1.py +345 -0
- chia/wallet/puzzles/singleton_truths.clib +21 -0
- chia/wallet/puzzles/tails.py +348 -0
- chia/wallet/puzzles/utility_macros.clib +48 -0
- chia/wallet/signer_protocol.py +125 -0
- chia/wallet/singleton.py +106 -0
- chia/wallet/singleton_record.py +30 -0
- chia/wallet/trade_manager.py +1102 -0
- chia/wallet/trade_record.py +67 -0
- chia/wallet/trading/__init__.py +0 -0
- chia/wallet/trading/offer.py +702 -0
- chia/wallet/trading/trade_status.py +13 -0
- chia/wallet/trading/trade_store.py +526 -0
- chia/wallet/transaction_record.py +158 -0
- chia/wallet/transaction_sorting.py +14 -0
- chia/wallet/uncurried_puzzle.py +17 -0
- chia/wallet/util/__init__.py +0 -0
- chia/wallet/util/address_type.py +55 -0
- chia/wallet/util/blind_signer_tl.py +164 -0
- chia/wallet/util/clvm_streamable.py +203 -0
- chia/wallet/util/compute_hints.py +66 -0
- chia/wallet/util/compute_memos.py +43 -0
- chia/wallet/util/curry_and_treehash.py +91 -0
- chia/wallet/util/debug_spend_bundle.py +232 -0
- chia/wallet/util/merkle_tree.py +100 -0
- chia/wallet/util/merkle_utils.py +102 -0
- chia/wallet/util/new_peak_queue.py +82 -0
- chia/wallet/util/notifications.py +12 -0
- chia/wallet/util/peer_request_cache.py +174 -0
- chia/wallet/util/pprint.py +39 -0
- chia/wallet/util/puzzle_compression.py +95 -0
- chia/wallet/util/puzzle_decorator.py +100 -0
- chia/wallet/util/puzzle_decorator_type.py +7 -0
- chia/wallet/util/query_filter.py +59 -0
- chia/wallet/util/transaction_type.py +23 -0
- chia/wallet/util/tx_config.py +158 -0
- chia/wallet/util/wallet_sync_utils.py +351 -0
- chia/wallet/util/wallet_types.py +72 -0
- chia/wallet/vc_wallet/__init__.py +0 -0
- chia/wallet/vc_wallet/cr_cat_drivers.py +664 -0
- chia/wallet/vc_wallet/cr_cat_wallet.py +877 -0
- chia/wallet/vc_wallet/cr_outer_puzzle.py +102 -0
- chia/wallet/vc_wallet/cr_puzzles/__init__.py +0 -0
- chia/wallet/vc_wallet/cr_puzzles/conditions_w_fee_announce.clsp +3 -0
- chia/wallet/vc_wallet/cr_puzzles/conditions_w_fee_announce.clsp.hex +1 -0
- chia/wallet/vc_wallet/cr_puzzles/credential_restriction.clsp +304 -0
- chia/wallet/vc_wallet/cr_puzzles/credential_restriction.clsp.hex +1 -0
- chia/wallet/vc_wallet/cr_puzzles/flag_proofs_checker.clsp +45 -0
- chia/wallet/vc_wallet/cr_puzzles/flag_proofs_checker.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_drivers.py +838 -0
- chia/wallet/vc_wallet/vc_puzzles/__init__.py +0 -0
- chia/wallet/vc_wallet/vc_puzzles/covenant_layer.clsp +30 -0
- chia/wallet/vc_wallet/vc_puzzles/covenant_layer.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_puzzles/eml_covenant_morpher.clsp +75 -0
- chia/wallet/vc_wallet/vc_puzzles/eml_covenant_morpher.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_puzzles/eml_transfer_program_covenant_adapter.clsp +32 -0
- chia/wallet/vc_wallet/vc_puzzles/eml_transfer_program_covenant_adapter.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_puzzles/eml_update_metadata_with_DID.clsp +80 -0
- chia/wallet/vc_wallet/vc_puzzles/eml_update_metadata_with_DID.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_puzzles/exigent_metadata_layer.clsp +163 -0
- chia/wallet/vc_wallet/vc_puzzles/exigent_metadata_layer.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_puzzles/p2_announced_delegated_puzzle.clsp +16 -0
- chia/wallet/vc_wallet/vc_puzzles/p2_announced_delegated_puzzle.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_puzzles/standard_vc_backdoor_puzzle.clsp +74 -0
- chia/wallet/vc_wallet/vc_puzzles/standard_vc_backdoor_puzzle.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_puzzles/std_parent_morpher.clsp +23 -0
- chia/wallet/vc_wallet/vc_puzzles/std_parent_morpher.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_puzzles/viral_backdoor.clsp +64 -0
- chia/wallet/vc_wallet/vc_puzzles/viral_backdoor.clsp.hex +1 -0
- chia/wallet/vc_wallet/vc_store.py +263 -0
- chia/wallet/vc_wallet/vc_wallet.py +638 -0
- chia/wallet/wallet.py +698 -0
- chia/wallet/wallet_action_scope.py +96 -0
- chia/wallet/wallet_blockchain.py +244 -0
- chia/wallet/wallet_coin_record.py +72 -0
- chia/wallet/wallet_coin_store.py +351 -0
- chia/wallet/wallet_info.py +35 -0
- chia/wallet/wallet_interested_store.py +188 -0
- chia/wallet/wallet_nft_store.py +279 -0
- chia/wallet/wallet_node.py +1765 -0
- chia/wallet/wallet_node_api.py +207 -0
- chia/wallet/wallet_pool_store.py +119 -0
- chia/wallet/wallet_protocol.py +90 -0
- chia/wallet/wallet_puzzle_store.py +396 -0
- chia/wallet/wallet_retry_store.py +70 -0
- chia/wallet/wallet_singleton_store.py +259 -0
- chia/wallet/wallet_spend_bundle.py +25 -0
- chia/wallet/wallet_state_manager.py +2819 -0
- chia/wallet/wallet_transaction_store.py +496 -0
- chia/wallet/wallet_user_store.py +110 -0
- chia/wallet/wallet_weight_proof_handler.py +126 -0
- chia_blockchain-2.5.1rc1.dist-info/LICENSE +201 -0
- chia_blockchain-2.5.1rc1.dist-info/METADATA +156 -0
- chia_blockchain-2.5.1rc1.dist-info/RECORD +1042 -0
- chia_blockchain-2.5.1rc1.dist-info/WHEEL +4 -0
- chia_blockchain-2.5.1rc1.dist-info/entry_points.txt +17 -0
- mozilla-ca/cacert.pem +3611 -0
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import pytest
|
|
4
|
+
|
|
5
|
+
from chia._tests.util.misc import BenchmarkRunner, wallet_height_at_least
|
|
6
|
+
from chia._tests.util.setup_nodes import OldSimulatorsAndWallets
|
|
7
|
+
from chia._tests.util.time_out_assert import time_out_assert
|
|
8
|
+
from chia.simulator.add_blocks_in_batches import add_blocks_in_batches
|
|
9
|
+
from chia.types.full_block import FullBlock
|
|
10
|
+
from chia.types.mempool_inclusion_status import MempoolInclusionStatus
|
|
11
|
+
from chia.types.peer_info import PeerInfo
|
|
12
|
+
from chia.util.ints import uint64, uint128
|
|
13
|
+
from chia.wallet.util.tx_config import DEFAULT_TX_CONFIG
|
|
14
|
+
from chia.wallet.wallet_node import WalletNode
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
async def wallet_balance_at_least(wallet_node: WalletNode, balance: uint128) -> bool:
|
|
18
|
+
b = await wallet_node.wallet_state_manager.get_confirmed_balance_for_wallet(1)
|
|
19
|
+
return b >= balance
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
@pytest.mark.limit_consensus_modes(reason="benchmark")
|
|
23
|
+
@pytest.mark.anyio
|
|
24
|
+
async def test_mempool_update_performance(
|
|
25
|
+
wallet_nodes_mempool_perf: OldSimulatorsAndWallets,
|
|
26
|
+
default_400_blocks: list[FullBlock],
|
|
27
|
+
self_hostname: str,
|
|
28
|
+
benchmark_runner: BenchmarkRunner,
|
|
29
|
+
) -> None:
|
|
30
|
+
blocks = default_400_blocks
|
|
31
|
+
[full_node_api], [wallet_setup], bt = wallet_nodes_mempool_perf
|
|
32
|
+
full_node = full_node_api.full_node
|
|
33
|
+
wallet_node, wallet_server = wallet_setup
|
|
34
|
+
wallet = wallet_node.wallet_state_manager.main_wallet
|
|
35
|
+
|
|
36
|
+
# We need an initialized mempool as we want to add a transaction, so we use
|
|
37
|
+
# the first block to achieve that
|
|
38
|
+
await full_node.add_block(blocks[0])
|
|
39
|
+
await add_blocks_in_batches(blocks[1:], full_node)
|
|
40
|
+
await wallet_server.start_client(PeerInfo(self_hostname, full_node.server.get_port()), None)
|
|
41
|
+
await time_out_assert(30, wallet_height_at_least, True, wallet_node, 399)
|
|
42
|
+
send_amount = uint64(40_000_000_000_000)
|
|
43
|
+
fee_amount = uint64(2213)
|
|
44
|
+
await time_out_assert(30, wallet_balance_at_least, True, wallet_node, send_amount + fee_amount)
|
|
45
|
+
|
|
46
|
+
ph = await wallet.get_new_puzzlehash()
|
|
47
|
+
async with wallet.wallet_state_manager.new_action_scope(DEFAULT_TX_CONFIG, push=False, sign=True) as action_scope:
|
|
48
|
+
await wallet.generate_signed_transaction(send_amount, ph, action_scope, fee_amount)
|
|
49
|
+
[big_transaction] = action_scope.side_effects.transactions
|
|
50
|
+
assert big_transaction.spend_bundle is not None
|
|
51
|
+
status, err = await full_node.add_transaction(
|
|
52
|
+
big_transaction.spend_bundle, big_transaction.spend_bundle.name(), test=True
|
|
53
|
+
)
|
|
54
|
+
assert err is None
|
|
55
|
+
assert status == MempoolInclusionStatus.SUCCESS
|
|
56
|
+
|
|
57
|
+
cons = list(full_node.server.all_connections.values())
|
|
58
|
+
for con in cons:
|
|
59
|
+
await con.close()
|
|
60
|
+
|
|
61
|
+
blocks = bt.get_consecutive_blocks(3, blocks)
|
|
62
|
+
with benchmark_runner.assert_runtime(seconds=0.45):
|
|
63
|
+
for block in blocks[-3:]:
|
|
64
|
+
await full_node.add_block(block)
|
|
@@ -0,0 +1,567 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import dataclasses
|
|
4
|
+
from typing import Any, Optional
|
|
5
|
+
|
|
6
|
+
import pytest
|
|
7
|
+
from chia_rs import AugSchemeMPL, G1Element, G2Element, PrivateKey
|
|
8
|
+
|
|
9
|
+
from chia._tests.clvm.test_puzzles import public_key_for_index, secret_exponent_for_index
|
|
10
|
+
from chia._tests.core.mempool.test_mempool_manager import (
|
|
11
|
+
IDENTITY_PUZZLE,
|
|
12
|
+
IDENTITY_PUZZLE_HASH,
|
|
13
|
+
TEST_COIN,
|
|
14
|
+
TEST_COIN_ID,
|
|
15
|
+
TEST_HEIGHT,
|
|
16
|
+
mempool_item_from_spendbundle,
|
|
17
|
+
spend_bundle_from_conditions,
|
|
18
|
+
)
|
|
19
|
+
from chia._tests.util.key_tool import KeyTool
|
|
20
|
+
from chia._tests.util.spend_sim import SimClient, SpendSim, sim_and_client
|
|
21
|
+
from chia.consensus.default_constants import DEFAULT_CONSTANTS
|
|
22
|
+
from chia.types.blockchain_format.coin import Coin
|
|
23
|
+
from chia.types.blockchain_format.program import Program
|
|
24
|
+
from chia.types.blockchain_format.serialized_program import SerializedProgram
|
|
25
|
+
from chia.types.blockchain_format.sized_bytes import bytes32
|
|
26
|
+
from chia.types.coin_spend import CoinSpend, make_spend
|
|
27
|
+
from chia.types.condition_opcodes import ConditionOpcode
|
|
28
|
+
from chia.types.eligible_coin_spends import EligibleCoinSpends, UnspentLineageInfo, perform_the_fast_forward
|
|
29
|
+
from chia.types.internal_mempool_item import InternalMempoolItem
|
|
30
|
+
from chia.types.mempool_inclusion_status import MempoolInclusionStatus
|
|
31
|
+
from chia.types.mempool_item import BundleCoinSpend
|
|
32
|
+
from chia.types.spend_bundle import SpendBundle
|
|
33
|
+
from chia.util.errors import Err
|
|
34
|
+
from chia.util.ints import uint64
|
|
35
|
+
from chia.wallet.puzzles import p2_conditions, p2_delegated_puzzle_or_hidden_puzzle
|
|
36
|
+
from chia.wallet.puzzles import singleton_top_layer_v1_1 as singleton_top_layer
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
@pytest.mark.anyio
|
|
40
|
+
async def test_process_fast_forward_spends_nothing_to_do() -> None:
|
|
41
|
+
"""
|
|
42
|
+
This tests the case when we don't have an eligible coin, so there is
|
|
43
|
+
nothing to fast forward and the item remains unchanged
|
|
44
|
+
"""
|
|
45
|
+
|
|
46
|
+
async def get_unspent_lineage_info_for_puzzle_hash(_: bytes32) -> Optional[UnspentLineageInfo]:
|
|
47
|
+
assert False # pragma: no cover
|
|
48
|
+
|
|
49
|
+
sk = AugSchemeMPL.key_gen(b"b" * 32)
|
|
50
|
+
g1 = sk.get_g1()
|
|
51
|
+
sig = AugSchemeMPL.sign(sk, b"foobar", g1)
|
|
52
|
+
conditions = [[ConditionOpcode.AGG_SIG_UNSAFE, bytes(g1), b"foobar"]]
|
|
53
|
+
sb = spend_bundle_from_conditions(conditions, TEST_COIN, sig)
|
|
54
|
+
item = mempool_item_from_spendbundle(sb)
|
|
55
|
+
# This coin is not eligible for fast forward
|
|
56
|
+
assert item.bundle_coin_spends[TEST_COIN_ID].eligible_for_fast_forward is False
|
|
57
|
+
internal_mempool_item = InternalMempoolItem(sb, item.conds, item.height_added_to_mempool, item.bundle_coin_spends)
|
|
58
|
+
original_version = dataclasses.replace(internal_mempool_item)
|
|
59
|
+
eligible_coin_spends = EligibleCoinSpends()
|
|
60
|
+
await eligible_coin_spends.process_fast_forward_spends(
|
|
61
|
+
mempool_item=internal_mempool_item,
|
|
62
|
+
get_unspent_lineage_info_for_puzzle_hash=get_unspent_lineage_info_for_puzzle_hash,
|
|
63
|
+
height=TEST_HEIGHT,
|
|
64
|
+
constants=DEFAULT_CONSTANTS,
|
|
65
|
+
)
|
|
66
|
+
assert eligible_coin_spends == EligibleCoinSpends()
|
|
67
|
+
assert internal_mempool_item == original_version
|
|
68
|
+
|
|
69
|
+
|
|
70
|
+
@pytest.mark.anyio
|
|
71
|
+
async def test_process_fast_forward_spends_unknown_ff() -> None:
|
|
72
|
+
"""
|
|
73
|
+
This tests the case when we process for the first time but we are unable
|
|
74
|
+
to lookup the latest version from the DB
|
|
75
|
+
"""
|
|
76
|
+
|
|
77
|
+
async def get_unspent_lineage_info_for_puzzle_hash(puzzle_hash: bytes32) -> Optional[UnspentLineageInfo]:
|
|
78
|
+
if puzzle_hash == IDENTITY_PUZZLE_HASH:
|
|
79
|
+
return None
|
|
80
|
+
assert False # pragma: no cover
|
|
81
|
+
|
|
82
|
+
test_coin = Coin(TEST_COIN_ID, IDENTITY_PUZZLE_HASH, uint64(1))
|
|
83
|
+
conditions = [[ConditionOpcode.CREATE_COIN, IDENTITY_PUZZLE_HASH, 1]]
|
|
84
|
+
sb = spend_bundle_from_conditions(conditions, test_coin)
|
|
85
|
+
item = mempool_item_from_spendbundle(sb)
|
|
86
|
+
# The coin is eligible for fast forward
|
|
87
|
+
assert item.bundle_coin_spends[test_coin.name()].eligible_for_fast_forward is True
|
|
88
|
+
internal_mempool_item = InternalMempoolItem(sb, item.conds, item.height_added_to_mempool, item.bundle_coin_spends)
|
|
89
|
+
eligible_coin_spends = EligibleCoinSpends()
|
|
90
|
+
# We have no fast forward records yet, so we'll process this coin for the
|
|
91
|
+
# first time here, but the DB lookup will return None
|
|
92
|
+
with pytest.raises(ValueError, match="Cannot proceed with singleton spend fast forward."):
|
|
93
|
+
await eligible_coin_spends.process_fast_forward_spends(
|
|
94
|
+
mempool_item=internal_mempool_item,
|
|
95
|
+
get_unspent_lineage_info_for_puzzle_hash=get_unspent_lineage_info_for_puzzle_hash,
|
|
96
|
+
height=TEST_HEIGHT,
|
|
97
|
+
constants=DEFAULT_CONSTANTS,
|
|
98
|
+
)
|
|
99
|
+
|
|
100
|
+
|
|
101
|
+
@pytest.mark.anyio
|
|
102
|
+
async def test_process_fast_forward_spends_latest_unspent() -> None:
|
|
103
|
+
"""
|
|
104
|
+
This tests the case when we are the latest singleton version already, so
|
|
105
|
+
we don't need to fast forward, we just need to set the next version from
|
|
106
|
+
our additions to chain ff spends.
|
|
107
|
+
"""
|
|
108
|
+
test_amount = uint64(3)
|
|
109
|
+
test_coin = Coin(TEST_COIN_ID, IDENTITY_PUZZLE_HASH, test_amount)
|
|
110
|
+
test_unspent_lineage_info = UnspentLineageInfo(
|
|
111
|
+
coin_id=test_coin.name(),
|
|
112
|
+
coin_amount=test_coin.amount,
|
|
113
|
+
parent_id=test_coin.parent_coin_info,
|
|
114
|
+
parent_amount=test_coin.amount,
|
|
115
|
+
parent_parent_id=TEST_COIN_ID,
|
|
116
|
+
)
|
|
117
|
+
|
|
118
|
+
async def get_unspent_lineage_info_for_puzzle_hash(puzzle_hash: bytes32) -> Optional[UnspentLineageInfo]:
|
|
119
|
+
if puzzle_hash == IDENTITY_PUZZLE_HASH:
|
|
120
|
+
return test_unspent_lineage_info
|
|
121
|
+
assert False # pragma: no cover
|
|
122
|
+
|
|
123
|
+
# At this point, spends are considered *potentially* eligible for singleton
|
|
124
|
+
# fast forward mainly when their amount is even and they don't have conditions
|
|
125
|
+
# that disqualify them
|
|
126
|
+
conditions = [[ConditionOpcode.CREATE_COIN, IDENTITY_PUZZLE_HASH, test_amount - 2]]
|
|
127
|
+
sb = spend_bundle_from_conditions(conditions, test_coin)
|
|
128
|
+
item = mempool_item_from_spendbundle(sb)
|
|
129
|
+
assert item.bundle_coin_spends[test_coin.name()].eligible_for_fast_forward is True
|
|
130
|
+
internal_mempool_item = InternalMempoolItem(sb, item.conds, item.height_added_to_mempool, item.bundle_coin_spends)
|
|
131
|
+
original_version = dataclasses.replace(internal_mempool_item)
|
|
132
|
+
eligible_coin_spends = EligibleCoinSpends()
|
|
133
|
+
await eligible_coin_spends.process_fast_forward_spends(
|
|
134
|
+
mempool_item=internal_mempool_item,
|
|
135
|
+
get_unspent_lineage_info_for_puzzle_hash=get_unspent_lineage_info_for_puzzle_hash,
|
|
136
|
+
height=TEST_HEIGHT,
|
|
137
|
+
constants=DEFAULT_CONSTANTS,
|
|
138
|
+
)
|
|
139
|
+
child_coin = item.bundle_coin_spends[test_coin.name()].additions[0]
|
|
140
|
+
expected_fast_forward_spends = {
|
|
141
|
+
IDENTITY_PUZZLE_HASH: UnspentLineageInfo(
|
|
142
|
+
coin_id=child_coin.name(),
|
|
143
|
+
coin_amount=child_coin.amount,
|
|
144
|
+
parent_id=test_coin.name(),
|
|
145
|
+
parent_amount=test_coin.amount,
|
|
146
|
+
parent_parent_id=test_coin.parent_coin_info,
|
|
147
|
+
)
|
|
148
|
+
}
|
|
149
|
+
# We have set the next version from our additions to chain ff spends
|
|
150
|
+
assert eligible_coin_spends.fast_forward_spends == expected_fast_forward_spends
|
|
151
|
+
# We didn't need to fast forward the item so it stays as is
|
|
152
|
+
assert internal_mempool_item == original_version
|
|
153
|
+
|
|
154
|
+
|
|
155
|
+
def test_perform_the_fast_forward() -> None:
|
|
156
|
+
"""
|
|
157
|
+
This test attempts to spend a coin that is already spent and the current
|
|
158
|
+
unspent version is its grandchild. We fast forward the test coin spend into
|
|
159
|
+
a spend of that latest unspent
|
|
160
|
+
"""
|
|
161
|
+
test_parent_id = bytes32.from_hexstr("0x039759eda861cd44c0af6c9501300f66fe4f5de144b8ae4fc4e8da35701f38ac")
|
|
162
|
+
test_ph = bytes32.from_hexstr("0x9ae0917f3ca301f934468ec60412904c0a88b232aeabf220c01ef53054e0281a")
|
|
163
|
+
test_amount = uint64(1337)
|
|
164
|
+
test_coin = Coin(test_parent_id, test_ph, test_amount)
|
|
165
|
+
test_child_coin = Coin(test_coin.name(), test_ph, test_amount)
|
|
166
|
+
latest_unspent_coin = Coin(test_child_coin.name(), test_ph, test_amount)
|
|
167
|
+
# This spend setup makes us eligible for fast forward so that we perform a
|
|
168
|
+
# meaningful fast forward on the rust side. It was generated using the
|
|
169
|
+
# singleton/child/grandchild dynamics that we have in
|
|
170
|
+
# `test_singleton_fast_forward_different_block` to get a realistic test case
|
|
171
|
+
test_puzzle_reveal = SerializedProgram.fromhex(
|
|
172
|
+
"ff02ffff01ff02ffff01ff02ffff03ffff18ff2fff3480ffff01ff04ffff04ff20ffff04ff2fff808080ffff04ffff02ff3effff04ff0"
|
|
173
|
+
"2ffff04ff05ffff04ffff02ff2affff04ff02ffff04ff27ffff04ffff02ffff03ff77ffff01ff02ff36ffff04ff02ffff04ff09ffff04"
|
|
174
|
+
"ff57ffff04ffff02ff2effff04ff02ffff04ff05ff80808080ff808080808080ffff011d80ff0180ffff04ffff02ffff03ff77ffff018"
|
|
175
|
+
"1b7ffff015780ff0180ff808080808080ffff04ff77ff808080808080ffff02ff3affff04ff02ffff04ff05ffff04ffff02ff0bff5f80"
|
|
176
|
+
"ffff01ff8080808080808080ffff01ff088080ff0180ffff04ffff01ffffffff4947ff0233ffff0401ff0102ffffff20ff02ffff03ff0"
|
|
177
|
+
"5ffff01ff02ff32ffff04ff02ffff04ff0dffff04ffff0bff3cffff0bff34ff2480ffff0bff3cffff0bff3cffff0bff34ff2c80ff0980"
|
|
178
|
+
"ffff0bff3cff0bffff0bff34ff8080808080ff8080808080ffff010b80ff0180ffff02ffff03ffff22ffff09ffff0dff0580ff2280fff"
|
|
179
|
+
"f09ffff0dff0b80ff2280ffff15ff17ffff0181ff8080ffff01ff0bff05ff0bff1780ffff01ff088080ff0180ff02ffff03ff0bffff01"
|
|
180
|
+
"ff02ffff03ffff02ff26ffff04ff02ffff04ff13ff80808080ffff01ff02ffff03ffff20ff1780ffff01ff02ffff03ffff09ff81b3fff"
|
|
181
|
+
"f01818f80ffff01ff02ff3affff04ff02ffff04ff05ffff04ff1bffff04ff34ff808080808080ffff01ff04ffff04ff23ffff04ffff02"
|
|
182
|
+
"ff36ffff04ff02ffff04ff09ffff04ff53ffff04ffff02ff2effff04ff02ffff04ff05ff80808080ff808080808080ff738080ffff02f"
|
|
183
|
+
"f3affff04ff02ffff04ff05ffff04ff1bffff04ff34ff8080808080808080ff0180ffff01ff088080ff0180ffff01ff04ff13ffff02ff"
|
|
184
|
+
"3affff04ff02ffff04ff05ffff04ff1bffff04ff17ff8080808080808080ff0180ffff01ff02ffff03ff17ff80ffff01ff088080ff018"
|
|
185
|
+
"080ff0180ffffff02ffff03ffff09ff09ff3880ffff01ff02ffff03ffff18ff2dffff010180ffff01ff0101ff8080ff0180ff8080ff01"
|
|
186
|
+
"80ff0bff3cffff0bff34ff2880ffff0bff3cffff0bff3cffff0bff34ff2c80ff0580ffff0bff3cffff02ff32ffff04ff02ffff04ff07f"
|
|
187
|
+
"fff04ffff0bff34ff3480ff8080808080ffff0bff34ff8080808080ffff02ffff03ffff07ff0580ffff01ff0bffff0102ffff02ff2eff"
|
|
188
|
+
"ff04ff02ffff04ff09ff80808080ffff02ff2effff04ff02ffff04ff0dff8080808080ffff01ff0bffff0101ff058080ff0180ff02fff"
|
|
189
|
+
"f03ffff21ff17ffff09ff0bff158080ffff01ff04ff30ffff04ff0bff808080ffff01ff088080ff0180ff018080ffff04ffff01ffa07f"
|
|
190
|
+
"aa3253bfddd1e0decb0906b2dc6247bbc4cf608f58345d173adb63e8b47c9fffa030d940e53ed5b56fee3ae46ba5f4e59da5e2cc9242f"
|
|
191
|
+
"6e482fe1f1e4d9a463639a0eff07522495060c066f66f32acc2a77e3a3e737aca8baea4d1a64ea4cdc13da9ffff04ffff010dff018080"
|
|
192
|
+
"80"
|
|
193
|
+
)
|
|
194
|
+
test_solution = SerializedProgram.fromhex(
|
|
195
|
+
"ffffa030d940e53ed5b56fee3ae46ba5f4e59da5e2cc9242f6e482fe1f1e4d9a463639ffa0c7b89cfb9abf2c4cb212a4840b37d762f4c"
|
|
196
|
+
"880b8517b0dadb0c310ded24dd86dff82053980ff820539ffff80ffff01ffff33ffa0c7b89cfb9abf2c4cb212a4840b37d762f4c880b8"
|
|
197
|
+
"517b0dadb0c310ded24dd86dff8205398080ff808080"
|
|
198
|
+
)
|
|
199
|
+
test_coin_spend = CoinSpend(test_coin, test_puzzle_reveal, test_solution)
|
|
200
|
+
test_spend_data = BundleCoinSpend(test_coin_spend, False, True, [test_child_coin])
|
|
201
|
+
test_unspent_lineage_info = UnspentLineageInfo(
|
|
202
|
+
coin_id=latest_unspent_coin.name(),
|
|
203
|
+
coin_amount=latest_unspent_coin.amount,
|
|
204
|
+
parent_id=latest_unspent_coin.parent_coin_info,
|
|
205
|
+
parent_amount=test_child_coin.amount,
|
|
206
|
+
parent_parent_id=test_child_coin.parent_coin_info,
|
|
207
|
+
)
|
|
208
|
+
# Start from a fresh state of fast forward spends
|
|
209
|
+
fast_forward_spends: dict[bytes32, UnspentLineageInfo] = {}
|
|
210
|
+
# Perform the fast forward on the test coin (the grandparent)
|
|
211
|
+
new_coin_spend, patched_additions = perform_the_fast_forward(
|
|
212
|
+
test_unspent_lineage_info, test_spend_data, fast_forward_spends
|
|
213
|
+
)
|
|
214
|
+
# Make sure the new coin we got is the grandchild (latest unspent version)
|
|
215
|
+
assert new_coin_spend.coin == latest_unspent_coin
|
|
216
|
+
# Make sure the puzzle reveal is intact
|
|
217
|
+
assert new_coin_spend.puzzle_reveal == test_coin_spend.puzzle_reveal
|
|
218
|
+
# Make sure the solution got patched
|
|
219
|
+
assert new_coin_spend.solution != test_coin_spend.solution
|
|
220
|
+
# Make sure the additions got patched
|
|
221
|
+
expected_child_coin = Coin(latest_unspent_coin.name(), test_ph, test_amount)
|
|
222
|
+
assert patched_additions == [expected_child_coin]
|
|
223
|
+
# Make sure the new fast forward state got updated with the latest unspent
|
|
224
|
+
# becoming the new child, with its parent being the version we just spent
|
|
225
|
+
# (previously latest unspent)
|
|
226
|
+
expected_unspent_lineage_info = UnspentLineageInfo(
|
|
227
|
+
coin_id=expected_child_coin.name(),
|
|
228
|
+
coin_amount=expected_child_coin.amount,
|
|
229
|
+
parent_id=latest_unspent_coin.name(),
|
|
230
|
+
parent_amount=latest_unspent_coin.amount,
|
|
231
|
+
parent_parent_id=latest_unspent_coin.parent_coin_info,
|
|
232
|
+
)
|
|
233
|
+
assert fast_forward_spends == {test_ph: expected_unspent_lineage_info}
|
|
234
|
+
|
|
235
|
+
|
|
236
|
+
def sign_delegated_puz(del_puz: Program, coin: Coin) -> G2Element:
|
|
237
|
+
synthetic_secret_key: PrivateKey = p2_delegated_puzzle_or_hidden_puzzle.calculate_synthetic_secret_key(
|
|
238
|
+
PrivateKey.from_bytes(secret_exponent_for_index(1).to_bytes(32, "big")),
|
|
239
|
+
p2_delegated_puzzle_or_hidden_puzzle.DEFAULT_HIDDEN_PUZZLE_HASH,
|
|
240
|
+
)
|
|
241
|
+
return AugSchemeMPL.sign(
|
|
242
|
+
synthetic_secret_key, (del_puz.get_tree_hash() + coin.name() + DEFAULT_CONSTANTS.AGG_SIG_ME_ADDITIONAL_DATA)
|
|
243
|
+
)
|
|
244
|
+
|
|
245
|
+
|
|
246
|
+
async def make_and_send_spend_bundle(
|
|
247
|
+
sim: SpendSim,
|
|
248
|
+
sim_client: SimClient,
|
|
249
|
+
coin_spends: list[CoinSpend],
|
|
250
|
+
is_eligible_for_ff: bool = True,
|
|
251
|
+
*,
|
|
252
|
+
is_launcher_coin: bool = False,
|
|
253
|
+
signing_puzzle: Optional[Program] = None,
|
|
254
|
+
signing_coin: Optional[Coin] = None,
|
|
255
|
+
aggsig: G2Element = G2Element(),
|
|
256
|
+
) -> tuple[MempoolInclusionStatus, Optional[Err]]:
|
|
257
|
+
if is_launcher_coin or not is_eligible_for_ff:
|
|
258
|
+
assert signing_puzzle is not None
|
|
259
|
+
assert signing_coin is not None
|
|
260
|
+
signature = sign_delegated_puz(signing_puzzle, signing_coin)
|
|
261
|
+
signature += aggsig
|
|
262
|
+
else:
|
|
263
|
+
signature = aggsig
|
|
264
|
+
spend_bundle = SpendBundle(coin_spends, signature)
|
|
265
|
+
status, error = await sim_client.push_tx(spend_bundle)
|
|
266
|
+
if error is None:
|
|
267
|
+
await sim.farm_block()
|
|
268
|
+
return status, error
|
|
269
|
+
|
|
270
|
+
|
|
271
|
+
async def get_singleton_and_remaining_coins(sim: SpendSim) -> tuple[Coin, list[Coin]]:
|
|
272
|
+
coins = await sim.all_non_reward_coins()
|
|
273
|
+
singletons = [coin for coin in coins if coin.amount & 1]
|
|
274
|
+
assert len(singletons) == 1
|
|
275
|
+
singleton = singletons[0]
|
|
276
|
+
coins.remove(singleton)
|
|
277
|
+
return singleton, coins
|
|
278
|
+
|
|
279
|
+
|
|
280
|
+
def make_singleton_coin_spend(
|
|
281
|
+
parent_coin_spend: CoinSpend,
|
|
282
|
+
coin_to_spend: Coin,
|
|
283
|
+
inner_puzzle: Program,
|
|
284
|
+
inner_conditions: list[list[Any]],
|
|
285
|
+
is_eve_spend: bool = False,
|
|
286
|
+
) -> tuple[CoinSpend, Program]:
|
|
287
|
+
lineage_proof = singleton_top_layer.lineage_proof_for_coinsol(parent_coin_spend)
|
|
288
|
+
delegated_puzzle = Program.to((1, inner_conditions))
|
|
289
|
+
inner_solution = Program.to([[], delegated_puzzle, []])
|
|
290
|
+
solution = singleton_top_layer.solution_for_singleton(lineage_proof, uint64(coin_to_spend.amount), inner_solution)
|
|
291
|
+
if is_eve_spend:
|
|
292
|
+
# Parent here is the launcher coin
|
|
293
|
+
puzzle_reveal = SerializedProgram.from_program(
|
|
294
|
+
singleton_top_layer.puzzle_for_singleton(parent_coin_spend.coin.name(), inner_puzzle)
|
|
295
|
+
)
|
|
296
|
+
else:
|
|
297
|
+
puzzle_reveal = parent_coin_spend.puzzle_reveal
|
|
298
|
+
return make_spend(coin_to_spend, puzzle_reveal, solution), delegated_puzzle
|
|
299
|
+
|
|
300
|
+
|
|
301
|
+
async def prepare_singleton_eve(
|
|
302
|
+
sim: SpendSim, sim_client: SimClient, is_eligible_for_ff: bool, start_amount: uint64, singleton_amount: uint64
|
|
303
|
+
) -> tuple[Program, CoinSpend, Program]:
|
|
304
|
+
# Generate starting info
|
|
305
|
+
key_lookup = KeyTool()
|
|
306
|
+
pk = G1Element.from_bytes(public_key_for_index(1, key_lookup))
|
|
307
|
+
starting_puzzle = p2_delegated_puzzle_or_hidden_puzzle.puzzle_for_pk(pk)
|
|
308
|
+
if is_eligible_for_ff:
|
|
309
|
+
# This program allows us to control conditions through solutions
|
|
310
|
+
inner_puzzle = Program.to(13)
|
|
311
|
+
else:
|
|
312
|
+
inner_puzzle = starting_puzzle
|
|
313
|
+
inner_puzzle_hash = inner_puzzle.get_tree_hash()
|
|
314
|
+
# Get our starting standard coin created
|
|
315
|
+
await sim.farm_block(starting_puzzle.get_tree_hash())
|
|
316
|
+
records = await sim_client.get_coin_records_by_puzzle_hash(starting_puzzle.get_tree_hash())
|
|
317
|
+
starting_coin = records[0].coin
|
|
318
|
+
# Launching
|
|
319
|
+
conditions, launcher_coin_spend = singleton_top_layer.launch_conditions_and_coinsol(
|
|
320
|
+
coin=starting_coin, inner_puzzle=inner_puzzle, comment=[], amount=start_amount
|
|
321
|
+
)
|
|
322
|
+
# Keep a remaining coin with an even amount
|
|
323
|
+
conditions.append(
|
|
324
|
+
Program.to([ConditionOpcode.CREATE_COIN, IDENTITY_PUZZLE_HASH, starting_coin.amount - start_amount - 1])
|
|
325
|
+
)
|
|
326
|
+
# Create a solution for standard transaction
|
|
327
|
+
delegated_puzzle = p2_conditions.puzzle_for_conditions(conditions)
|
|
328
|
+
full_solution = p2_delegated_puzzle_or_hidden_puzzle.solution_for_conditions(conditions)
|
|
329
|
+
starting_coin_spend = make_spend(starting_coin, starting_puzzle, full_solution)
|
|
330
|
+
await make_and_send_spend_bundle(
|
|
331
|
+
sim,
|
|
332
|
+
sim_client,
|
|
333
|
+
[starting_coin_spend, launcher_coin_spend],
|
|
334
|
+
is_eligible_for_ff,
|
|
335
|
+
is_launcher_coin=True,
|
|
336
|
+
signing_puzzle=delegated_puzzle,
|
|
337
|
+
signing_coin=starting_coin,
|
|
338
|
+
)
|
|
339
|
+
eve_coin, _ = await get_singleton_and_remaining_coins(sim)
|
|
340
|
+
inner_conditions = [[ConditionOpcode.CREATE_COIN, inner_puzzle_hash, singleton_amount]]
|
|
341
|
+
eve_coin_spend, eve_signing_puzzle = make_singleton_coin_spend(
|
|
342
|
+
parent_coin_spend=launcher_coin_spend,
|
|
343
|
+
coin_to_spend=eve_coin,
|
|
344
|
+
inner_puzzle=inner_puzzle,
|
|
345
|
+
inner_conditions=inner_conditions,
|
|
346
|
+
is_eve_spend=True,
|
|
347
|
+
)
|
|
348
|
+
return inner_puzzle, eve_coin_spend, eve_signing_puzzle
|
|
349
|
+
|
|
350
|
+
|
|
351
|
+
async def prepare_and_test_singleton(
|
|
352
|
+
sim: SpendSim, sim_client: SimClient, is_eligible_for_ff: bool, start_amount: uint64, singleton_amount: uint64
|
|
353
|
+
) -> tuple[Coin, CoinSpend, Program, Coin]:
|
|
354
|
+
inner_puzzle, eve_coin_spend, eve_signing_puzzle = await prepare_singleton_eve(
|
|
355
|
+
sim, sim_client, is_eligible_for_ff, start_amount, singleton_amount
|
|
356
|
+
)
|
|
357
|
+
# At this point we don't have any unspent singleton
|
|
358
|
+
singleton_puzzle_hash = eve_coin_spend.coin.puzzle_hash
|
|
359
|
+
unspent_lineage_info = await sim_client.service.coin_store.get_unspent_lineage_info_for_puzzle_hash(
|
|
360
|
+
singleton_puzzle_hash
|
|
361
|
+
)
|
|
362
|
+
assert unspent_lineage_info is None
|
|
363
|
+
eve_coin = eve_coin_spend.coin
|
|
364
|
+
await make_and_send_spend_bundle(
|
|
365
|
+
sim, sim_client, [eve_coin_spend], is_eligible_for_ff, signing_puzzle=eve_signing_puzzle, signing_coin=eve_coin
|
|
366
|
+
)
|
|
367
|
+
# Now we spent eve and we have an unspent singleton that we can test with
|
|
368
|
+
singleton, [remaining_coin] = await get_singleton_and_remaining_coins(sim)
|
|
369
|
+
assert singleton.amount == singleton_amount
|
|
370
|
+
singleton_puzzle_hash = eve_coin.puzzle_hash
|
|
371
|
+
unspent_lineage_info = await sim_client.service.coin_store.get_unspent_lineage_info_for_puzzle_hash(
|
|
372
|
+
singleton_puzzle_hash
|
|
373
|
+
)
|
|
374
|
+
assert unspent_lineage_info == UnspentLineageInfo(
|
|
375
|
+
coin_id=singleton.name(),
|
|
376
|
+
coin_amount=singleton.amount,
|
|
377
|
+
parent_id=eve_coin.name(),
|
|
378
|
+
parent_amount=eve_coin.amount,
|
|
379
|
+
parent_parent_id=eve_coin.parent_coin_info,
|
|
380
|
+
)
|
|
381
|
+
return singleton, eve_coin_spend, inner_puzzle, remaining_coin
|
|
382
|
+
|
|
383
|
+
|
|
384
|
+
@pytest.mark.anyio
|
|
385
|
+
@pytest.mark.parametrize("is_eligible_for_ff", [True, False])
|
|
386
|
+
async def test_singleton_fast_forward_different_block(is_eligible_for_ff: bool) -> None:
|
|
387
|
+
"""
|
|
388
|
+
This tests uses the `is_eligible_for_ff` parameter to cover both when a
|
|
389
|
+
singleton is eligible for fast forward and when it's not, as we attempt to
|
|
390
|
+
spend an earlier version of it, in a different block, and watch it either
|
|
391
|
+
get properly fast forwarded to the latest unspent (when it's eligible) or
|
|
392
|
+
get correctly rejected as a double spend (when it's not eligible)
|
|
393
|
+
"""
|
|
394
|
+
START_AMOUNT = uint64(1337)
|
|
395
|
+
# We're decrementing the next iteration's amount for testing purposes
|
|
396
|
+
SINGLETON_AMOUNT = uint64(1335)
|
|
397
|
+
# We're incrementing the next iteration's amount for testing purposes
|
|
398
|
+
SINGLETON_CHILD_AMOUNT = uint64(1339)
|
|
399
|
+
async with sim_and_client() as (sim, sim_client):
|
|
400
|
+
singleton, eve_coin_spend, inner_puzzle, remaining_coin = await prepare_and_test_singleton(
|
|
401
|
+
sim, sim_client, is_eligible_for_ff, START_AMOUNT, SINGLETON_AMOUNT
|
|
402
|
+
)
|
|
403
|
+
# Let's spend this first version, to create a bigger singleton child
|
|
404
|
+
singleton_puzzle_hash = eve_coin_spend.coin.puzzle_hash
|
|
405
|
+
inner_puzzle_hash = inner_puzzle.get_tree_hash()
|
|
406
|
+
|
|
407
|
+
sk = AugSchemeMPL.key_gen(b"1" * 32)
|
|
408
|
+
g1 = sk.get_g1()
|
|
409
|
+
sig = AugSchemeMPL.sign(sk, b"foobar", g1)
|
|
410
|
+
inner_conditions: list[list[Any]] = [
|
|
411
|
+
[ConditionOpcode.AGG_SIG_UNSAFE, bytes(g1), b"foobar"],
|
|
412
|
+
[ConditionOpcode.CREATE_COIN, inner_puzzle_hash, SINGLETON_CHILD_AMOUNT],
|
|
413
|
+
]
|
|
414
|
+
singleton_coin_spend, singleton_signing_puzzle = make_singleton_coin_spend(
|
|
415
|
+
eve_coin_spend, singleton, inner_puzzle, inner_conditions
|
|
416
|
+
)
|
|
417
|
+
# Spend also a remaining coin for balance, as we're increasing the singleton amount
|
|
418
|
+
diff_to_balance = SINGLETON_CHILD_AMOUNT - SINGLETON_AMOUNT
|
|
419
|
+
remaining_spend_solution = SerializedProgram.from_program(
|
|
420
|
+
Program.to([[ConditionOpcode.CREATE_COIN, IDENTITY_PUZZLE_HASH, remaining_coin.amount - diff_to_balance]])
|
|
421
|
+
)
|
|
422
|
+
remaining_coin_spend = CoinSpend(remaining_coin, IDENTITY_PUZZLE, remaining_spend_solution)
|
|
423
|
+
await make_and_send_spend_bundle(
|
|
424
|
+
sim,
|
|
425
|
+
sim_client,
|
|
426
|
+
[remaining_coin_spend, singleton_coin_spend],
|
|
427
|
+
is_eligible_for_ff,
|
|
428
|
+
signing_puzzle=singleton_signing_puzzle,
|
|
429
|
+
signing_coin=singleton,
|
|
430
|
+
aggsig=sig,
|
|
431
|
+
)
|
|
432
|
+
unspent_lineage_info = await sim_client.service.coin_store.get_unspent_lineage_info_for_puzzle_hash(
|
|
433
|
+
singleton_puzzle_hash
|
|
434
|
+
)
|
|
435
|
+
singleton_child, [remaining_coin] = await get_singleton_and_remaining_coins(sim)
|
|
436
|
+
assert singleton_child.amount == SINGLETON_CHILD_AMOUNT
|
|
437
|
+
assert unspent_lineage_info == UnspentLineageInfo(
|
|
438
|
+
coin_id=singleton_child.name(),
|
|
439
|
+
coin_amount=singleton_child.amount,
|
|
440
|
+
parent_id=singleton.name(),
|
|
441
|
+
parent_amount=singleton.amount,
|
|
442
|
+
parent_parent_id=eve_coin_spend.coin.name(),
|
|
443
|
+
)
|
|
444
|
+
# Now let's spend the first version again (despite being already spent by now)
|
|
445
|
+
remaining_spend_solution = SerializedProgram.from_program(
|
|
446
|
+
Program.to([[ConditionOpcode.CREATE_COIN, IDENTITY_PUZZLE_HASH, remaining_coin.amount - diff_to_balance]])
|
|
447
|
+
)
|
|
448
|
+
remaining_coin_spend = CoinSpend(remaining_coin, IDENTITY_PUZZLE, remaining_spend_solution)
|
|
449
|
+
status, error = await make_and_send_spend_bundle(
|
|
450
|
+
sim,
|
|
451
|
+
sim_client,
|
|
452
|
+
[remaining_coin_spend, singleton_coin_spend],
|
|
453
|
+
is_eligible_for_ff,
|
|
454
|
+
signing_puzzle=singleton_signing_puzzle,
|
|
455
|
+
signing_coin=singleton,
|
|
456
|
+
aggsig=sig,
|
|
457
|
+
)
|
|
458
|
+
if is_eligible_for_ff:
|
|
459
|
+
# Instead of rejecting this as double spend, we perform a fast forward,
|
|
460
|
+
# spending the singleton child as a result, and creating the latest
|
|
461
|
+
# version which is the grandchild in this scenario
|
|
462
|
+
assert status == MempoolInclusionStatus.SUCCESS
|
|
463
|
+
assert error is None
|
|
464
|
+
unspent_lineage_info = await sim_client.service.coin_store.get_unspent_lineage_info_for_puzzle_hash(
|
|
465
|
+
singleton_puzzle_hash
|
|
466
|
+
)
|
|
467
|
+
singleton_grandchild, [remaining_coin] = await get_singleton_and_remaining_coins(sim)
|
|
468
|
+
assert unspent_lineage_info == UnspentLineageInfo(
|
|
469
|
+
coin_id=singleton_grandchild.name(),
|
|
470
|
+
coin_amount=singleton_grandchild.amount,
|
|
471
|
+
parent_id=singleton_child.name(),
|
|
472
|
+
parent_amount=singleton_child.amount,
|
|
473
|
+
parent_parent_id=singleton.name(),
|
|
474
|
+
)
|
|
475
|
+
else:
|
|
476
|
+
# As this singleton is not eligible for fast forward, attempting to
|
|
477
|
+
# spend one of its earlier versions is considered a double spend
|
|
478
|
+
assert status == MempoolInclusionStatus.FAILED
|
|
479
|
+
assert error == Err.DOUBLE_SPEND
|
|
480
|
+
|
|
481
|
+
|
|
482
|
+
@pytest.mark.anyio
|
|
483
|
+
async def test_singleton_fast_forward_same_block() -> None:
|
|
484
|
+
"""
|
|
485
|
+
This tests covers sending multiple transactions that spend an already spent
|
|
486
|
+
singleton version, all in the same block, to make sure they get properly
|
|
487
|
+
fast forwarded and chained down to a latest unspent version
|
|
488
|
+
"""
|
|
489
|
+
START_AMOUNT = uint64(1337)
|
|
490
|
+
# We're decrementing the next iteration's amount for testing purposes
|
|
491
|
+
SINGLETON_AMOUNT = uint64(1335)
|
|
492
|
+
# We're incrementing the next iteration's amount for testing purposes
|
|
493
|
+
SINGLETON_CHILD_AMOUNT = uint64(1339)
|
|
494
|
+
async with sim_and_client() as (sim, sim_client):
|
|
495
|
+
singleton, eve_coin_spend, inner_puzzle, remaining_coin = await prepare_and_test_singleton(
|
|
496
|
+
sim, sim_client, True, START_AMOUNT, SINGLETON_AMOUNT
|
|
497
|
+
)
|
|
498
|
+
# Let's spend this first version, to create a bigger singleton child
|
|
499
|
+
singleton_puzzle_hash = eve_coin_spend.coin.puzzle_hash
|
|
500
|
+
inner_puzzle_hash = inner_puzzle.get_tree_hash()
|
|
501
|
+
sk = AugSchemeMPL.key_gen(b"9" * 32)
|
|
502
|
+
g1 = sk.get_g1()
|
|
503
|
+
sig = AugSchemeMPL.sign(sk, b"foobar", g1)
|
|
504
|
+
inner_conditions: list[list[Any]] = [
|
|
505
|
+
[ConditionOpcode.AGG_SIG_UNSAFE, bytes(g1), b"foobar"],
|
|
506
|
+
[ConditionOpcode.CREATE_COIN, inner_puzzle_hash, SINGLETON_CHILD_AMOUNT],
|
|
507
|
+
]
|
|
508
|
+
singleton_coin_spend, _ = make_singleton_coin_spend(eve_coin_spend, singleton, inner_puzzle, inner_conditions)
|
|
509
|
+
# Spend also a remaining coin for balance, as we're increasing the singleton amount
|
|
510
|
+
diff_to_balance = SINGLETON_CHILD_AMOUNT - SINGLETON_AMOUNT
|
|
511
|
+
remaining_spend_solution = SerializedProgram.from_program(
|
|
512
|
+
Program.to([[ConditionOpcode.CREATE_COIN, IDENTITY_PUZZLE_HASH, remaining_coin.amount - diff_to_balance]])
|
|
513
|
+
)
|
|
514
|
+
remaining_coin_spend = CoinSpend(remaining_coin, IDENTITY_PUZZLE, remaining_spend_solution)
|
|
515
|
+
await make_and_send_spend_bundle(sim, sim_client, [remaining_coin_spend, singleton_coin_spend], aggsig=sig)
|
|
516
|
+
unspent_lineage_info = await sim_client.service.coin_store.get_unspent_lineage_info_for_puzzle_hash(
|
|
517
|
+
singleton_puzzle_hash
|
|
518
|
+
)
|
|
519
|
+
singleton_child, [remaining_coin] = await get_singleton_and_remaining_coins(sim)
|
|
520
|
+
assert singleton_child.amount == SINGLETON_CHILD_AMOUNT
|
|
521
|
+
assert unspent_lineage_info == UnspentLineageInfo(
|
|
522
|
+
coin_id=singleton_child.name(),
|
|
523
|
+
coin_amount=singleton_child.amount,
|
|
524
|
+
parent_id=singleton.name(),
|
|
525
|
+
parent_amount=singleton.amount,
|
|
526
|
+
parent_parent_id=eve_coin_spend.coin.name(),
|
|
527
|
+
)
|
|
528
|
+
# Now let's send 3 arbitrary spends of the already spent singleton in
|
|
529
|
+
# one block. They should all properly fast forward
|
|
530
|
+
random_amounts = [21, 17, 11]
|
|
531
|
+
|
|
532
|
+
sk = AugSchemeMPL.key_gen(b"a" * 32)
|
|
533
|
+
g1 = sk.get_g1()
|
|
534
|
+
sig = AugSchemeMPL.sign(sk, b"foobar", g1)
|
|
535
|
+
for i in range(3):
|
|
536
|
+
# This cost adjustment allows us to maintain the order of spends due to fee per
|
|
537
|
+
# cost and amounts dynamics
|
|
538
|
+
cost_factor = (i + 1) * 5
|
|
539
|
+
inner_conditions = [[ConditionOpcode.AGG_SIG_UNSAFE, bytes(g1), b"foobar"] for _ in range(cost_factor)]
|
|
540
|
+
aggsig = G2Element()
|
|
541
|
+
for _ in range(cost_factor):
|
|
542
|
+
aggsig += sig
|
|
543
|
+
inner_conditions.append([ConditionOpcode.CREATE_COIN, inner_puzzle_hash, random_amounts[i]])
|
|
544
|
+
singleton_coin_spend, _ = make_singleton_coin_spend(
|
|
545
|
+
eve_coin_spend, singleton, inner_puzzle, inner_conditions
|
|
546
|
+
)
|
|
547
|
+
status, error = await sim_client.push_tx(SpendBundle([singleton_coin_spend], aggsig))
|
|
548
|
+
assert error is None
|
|
549
|
+
assert status == MempoolInclusionStatus.SUCCESS
|
|
550
|
+
|
|
551
|
+
# Farm a block to process all these spend bundles
|
|
552
|
+
await sim.farm_block()
|
|
553
|
+
unspent_lineage_info = await sim_client.service.coin_store.get_unspent_lineage_info_for_puzzle_hash(
|
|
554
|
+
singleton_puzzle_hash
|
|
555
|
+
)
|
|
556
|
+
latest_singleton, [remaining_coin] = await get_singleton_and_remaining_coins(sim)
|
|
557
|
+
assert unspent_lineage_info is not None
|
|
558
|
+
# The unspent coin ID should reflect the latest version
|
|
559
|
+
assert unspent_lineage_info.coin_id == latest_singleton.name()
|
|
560
|
+
# The latest version should have the last random amount
|
|
561
|
+
assert latest_singleton.amount == random_amounts[-1]
|
|
562
|
+
# The unspent coin amount should reflect the latest version
|
|
563
|
+
assert unspent_lineage_info.coin_amount == latest_singleton.amount
|
|
564
|
+
# The unspent parent ID should reflect the latest version's parent
|
|
565
|
+
assert unspent_lineage_info.parent_id == latest_singleton.parent_coin_info
|
|
566
|
+
# The one before it should have the second last random amount
|
|
567
|
+
assert unspent_lineage_info.parent_amount == random_amounts[-2]
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
from chia.full_node.full_node_api import FullNodeAPI
|
|
4
|
+
from chia.util.ints import uint32
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
def node_height_at_least(node: FullNodeAPI, h: uint32) -> bool:
|
|
8
|
+
if node.full_node.blockchain.get_peak() is not None:
|
|
9
|
+
peak = node.full_node.blockchain.get_peak()
|
|
10
|
+
if peak is not None:
|
|
11
|
+
return peak.height >= h
|
|
12
|
+
return False
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
def node_height_exactly(node: FullNodeAPI, h: uint32) -> bool:
|
|
16
|
+
if node.full_node.blockchain.get_peak() is not None:
|
|
17
|
+
peak = node.full_node.blockchain.get_peak()
|
|
18
|
+
if peak is not None:
|
|
19
|
+
return peak.height == h
|
|
20
|
+
return False
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
def node_height_between(node: FullNodeAPI, h1: uint32, h2: uint32) -> bool:
|
|
24
|
+
if node.full_node.blockchain.get_peak() is not None:
|
|
25
|
+
peak = node.full_node.blockchain.get_peak()
|
|
26
|
+
if peak is not None:
|
|
27
|
+
return h1 <= peak.height <= h2
|
|
28
|
+
return False
|
|
File without changes
|