axdata 0.1.0__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.
- axdata/__init__.py +16 -0
- axdata/cache.py +19 -0
- axdata/client.py +1223 -0
- axdata-0.1.0.dist-info/METADATA +238 -0
- axdata-0.1.0.dist-info/RECORD +427 -0
- axdata-0.1.0.dist-info/WHEEL +5 -0
- axdata-0.1.0.dist-info/entry_points.txt +8 -0
- axdata-0.1.0.dist-info/licenses/LICENSE +162 -0
- axdata-0.1.0.dist-info/top_level.txt +6 -0
- axdata_core/__init__.py +221 -0
- axdata_core/_tdx_wire/__init__.py +35 -0
- axdata_core/_tdx_wire/_shim.py +140 -0
- axdata_core/_tdx_wire/api/__init__.py +51 -0
- axdata_core/_tdx_wire/api/auction.py +24 -0
- axdata_core/_tdx_wire/api/bars.py +24 -0
- axdata_core/_tdx_wire/api/base.py +26 -0
- axdata_core/_tdx_wire/api/codes.py +25 -0
- axdata_core/_tdx_wire/api/corporate.py +24 -0
- axdata_core/_tdx_wire/api/finance.py +24 -0
- axdata_core/_tdx_wire/api/intraday.py +24 -0
- axdata_core/_tdx_wire/api/quotes.py +26 -0
- axdata_core/_tdx_wire/api/resources.py +25 -0
- axdata_core/_tdx_wire/api/session.py +24 -0
- axdata_core/_tdx_wire/api/trades.py +24 -0
- axdata_core/_tdx_wire/client.py +33 -0
- axdata_core/_tdx_wire/exceptions.py +27 -0
- axdata_core/_tdx_wire/hosts.py +106 -0
- axdata_core/_tdx_wire/models/__init__.py +93 -0
- axdata_core/_tdx_wire/models/auction.py +26 -0
- axdata_core/_tdx_wire/models/corporate.py +27 -0
- axdata_core/_tdx_wire/models/finance.py +26 -0
- axdata_core/_tdx_wire/models/intraday.py +31 -0
- axdata_core/_tdx_wire/models/kline.py +27 -0
- axdata_core/_tdx_wire/models/quote.py +32 -0
- axdata_core/_tdx_wire/models/resource.py +24 -0
- axdata_core/_tdx_wire/models/security.py +24 -0
- axdata_core/_tdx_wire/models/session.py +27 -0
- axdata_core/_tdx_wire/models/subchart.py +25 -0
- axdata_core/_tdx_wire/models/trade.py +28 -0
- axdata_core/_tdx_wire/protocol/__init__.py +49 -0
- axdata_core/_tdx_wire/protocol/commands/__init__.py +43 -0
- axdata_core/_tdx_wire/protocol/commands/auction.py +110 -0
- axdata_core/_tdx_wire/protocol/commands/codec.py +43 -0
- axdata_core/_tdx_wire/protocol/commands/corporate.py +98 -0
- axdata_core/_tdx_wire/protocol/commands/finance.py +96 -0
- axdata_core/_tdx_wire/protocol/commands/intraday.py +122 -0
- axdata_core/_tdx_wire/protocol/commands/klines.py +102 -0
- axdata_core/_tdx_wire/protocol/commands/lookup.py +36 -0
- axdata_core/_tdx_wire/protocol/commands/price_limits.py +89 -0
- axdata_core/_tdx_wire/protocol/commands/quotes.py +102 -0
- axdata_core/_tdx_wire/protocol/commands/registry.py +36 -0
- axdata_core/_tdx_wire/protocol/commands/resources.py +99 -0
- axdata_core/_tdx_wire/protocol/commands/security.py +103 -0
- axdata_core/_tdx_wire/protocol/commands/session.py +82 -0
- axdata_core/_tdx_wire/protocol/commands/subchart.py +97 -0
- axdata_core/_tdx_wire/protocol/commands/trades.py +107 -0
- axdata_core/_tdx_wire/protocol/constants.py +124 -0
- axdata_core/_tdx_wire/protocol/frame.py +68 -0
- axdata_core/_tdx_wire/protocol/unit.py +85 -0
- axdata_core/_tdx_wire/py.typed +1 -0
- axdata_core/_tdx_wire/transport/__init__.py +34 -0
- axdata_core/_tdx_wire/transport/base.py +25 -0
- axdata_core/_tdx_wire/transport/memory.py +24 -0
- axdata_core/_tdx_wire/transport/pool.py +32 -0
- axdata_core/_tdx_wire/transport/socket.py +39 -0
- axdata_core/adapters/__init__.py +0 -0
- axdata_core/adapters/cls/__init__.py +17 -0
- axdata_core/adapters/cls/provider_bridge.py +23 -0
- axdata_core/adapters/cls/request.py +632 -0
- axdata_core/adapters/cls/source_adapter_registry.py +31 -0
- axdata_core/adapters/cninfo/__init__.py +17 -0
- axdata_core/adapters/cninfo/provider_bridge.py +25 -0
- axdata_core/adapters/cninfo/request.py +2425 -0
- axdata_core/adapters/cninfo/source_adapter_registry.py +42 -0
- axdata_core/adapters/eastmoney/__init__.py +17 -0
- axdata_core/adapters/eastmoney/provider_bridge.py +25 -0
- axdata_core/adapters/eastmoney/request.py +1128 -0
- axdata_core/adapters/eastmoney/source_adapter_registry.py +42 -0
- axdata_core/adapters/exchange/__init__.py +17 -0
- axdata_core/adapters/exchange/provider_bridge.py +25 -0
- axdata_core/adapters/exchange/request.py +1214 -0
- axdata_core/adapters/exchange/source_adapter_registry.py +42 -0
- axdata_core/adapters/kph/__init__.py +17 -0
- axdata_core/adapters/kph/provider_bridge.py +23 -0
- axdata_core/adapters/kph/request.py +509 -0
- axdata_core/adapters/kph/source_adapter_registry.py +31 -0
- axdata_core/adapters/sina/__init__.py +17 -0
- axdata_core/adapters/sina/provider_bridge.py +25 -0
- axdata_core/adapters/sina/request.py +5155 -0
- axdata_core/adapters/sina/source_adapter_registry.py +42 -0
- axdata_core/adapters/tdx/__init__.py +32 -0
- axdata_core/adapters/tdx/adjustment.py +50 -0
- axdata_core/adapters/tdx/adjustment_fetch.py +51 -0
- axdata_core/adapters/tdx/auction_fetch.py +51 -0
- axdata_core/adapters/tdx/client_factory.py +110 -0
- axdata_core/adapters/tdx/code_fetch.py +62 -0
- axdata_core/adapters/tdx/codes.py +54 -0
- axdata_core/adapters/tdx/derived_rows.py +69 -0
- axdata_core/adapters/tdx/downloader.py +193 -0
- axdata_core/adapters/tdx/downloader_interface_sets.py +50 -0
- axdata_core/adapters/tdx/downloader_profiles.py +43 -0
- axdata_core/adapters/tdx/downloader_registry.py +115 -0
- axdata_core/adapters/tdx/execution_utils.py +55 -0
- axdata_core/adapters/tdx/f10_executor.py +57 -0
- axdata_core/adapters/tdx/f10_normalize.py +61 -0
- axdata_core/adapters/tdx/f10_params.py +57 -0
- axdata_core/adapters/tdx/f10_postprocess.py +67 -0
- axdata_core/adapters/tdx/f10_render.py +48 -0
- axdata_core/adapters/tdx/f10_request.py +62 -0
- axdata_core/adapters/tdx/finance_fetch.py +61 -0
- axdata_core/adapters/tdx/finance_maps.py +54 -0
- axdata_core/adapters/tdx/finance_normalize.py +57 -0
- axdata_core/adapters/tdx/host_config.py +115 -0
- axdata_core/adapters/tdx/interface_sets.py +50 -0
- axdata_core/adapters/tdx/intraday_fetch.py +68 -0
- axdata_core/adapters/tdx/kline_helpers.py +58 -0
- axdata_core/adapters/tdx/limit_ladder_fetch.py +60 -0
- axdata_core/adapters/tdx/limit_ladder_topics.py +53 -0
- axdata_core/adapters/tdx/normalize_utils.py +75 -0
- axdata_core/adapters/tdx/options.py +61 -0
- axdata_core/adapters/tdx/price_limit_calendar.py +49 -0
- axdata_core/adapters/tdx/price_limit_fetch.py +53 -0
- axdata_core/adapters/tdx/price_limit_history.py +50 -0
- axdata_core/adapters/tdx/price_limits.py +58 -0
- axdata_core/adapters/tdx/provider_bridge.py +68 -0
- axdata_core/adapters/tdx/quote_fetch.py +61 -0
- axdata_core/adapters/tdx/quote_identity.py +49 -0
- axdata_core/adapters/tdx/rank_fetch.py +55 -0
- axdata_core/adapters/tdx/rank_params.py +52 -0
- axdata_core/adapters/tdx/realtime_refresh.py +45 -0
- axdata_core/adapters/tdx/request.py +11 -0
- axdata_core/adapters/tdx/request_adapter_runtime.py +41 -0
- axdata_core/adapters/tdx/request_client.py +51 -0
- axdata_core/adapters/tdx/request_compat.py +89 -0
- axdata_core/adapters/tdx/request_dispatch.py +50 -0
- axdata_core/adapters/tdx/request_filters.py +60 -0
- axdata_core/adapters/tdx/request_host_config.py +110 -0
- axdata_core/adapters/tdx/request_limits.py +59 -0
- axdata_core/adapters/tdx/request_methods.py +41 -0
- axdata_core/adapters/tdx/request_params.py +62 -0
- axdata_core/adapters/tdx/request_seams.py +41 -0
- axdata_core/adapters/tdx/resources/__init__.py +0 -0
- axdata_core/adapters/tdx/resources/finance_maps/__init__.py +0 -0
- axdata_core/adapters/tdx/resources/finance_maps/incon.dat +3702 -0
- axdata_core/adapters/tdx/resources/finance_maps/tdxhy.cfg +5620 -0
- axdata_core/adapters/tdx/resources/finance_maps/tdxzs.cfg +605 -0
- axdata_core/adapters/tdx/security_codes.py +54 -0
- axdata_core/adapters/tdx/series_history.py +57 -0
- axdata_core/adapters/tdx/server_cache.py +58 -0
- axdata_core/adapters/tdx/snapshot_normalize.py +56 -0
- axdata_core/adapters/tdx/source_adapter_registry.py +69 -0
- axdata_core/adapters/tdx/source_execution.py +44 -0
- axdata_core/adapters/tdx/source_execution_registry.py +70 -0
- axdata_core/adapters/tdx/stats_cache.py +184 -0
- axdata_core/adapters/tdx/stats_models.py +159 -0
- axdata_core/adapters/tdx/stats_resource.py +304 -0
- axdata_core/adapters/tdx/status_fetch.py +55 -0
- axdata_core/adapters/tdx/time_series_normalize.py +67 -0
- axdata_core/adapters/tdx/tqlex.py +50 -0
- axdata_core/adapters/tdx/wire_requests.py +60 -0
- axdata_core/adapters/tdx_ext/__init__.py +66 -0
- axdata_core/adapters/tdx_ext/client.py +688 -0
- axdata_core/adapters/tdx_ext/exceptions.py +51 -0
- axdata_core/adapters/tdx_ext/host_config.py +40 -0
- axdata_core/adapters/tdx_ext/interface_sets.py +65 -0
- axdata_core/adapters/tdx_ext/local_cache.py +649 -0
- axdata_core/adapters/tdx_ext/models.py +96 -0
- axdata_core/adapters/tdx_ext/options.py +36 -0
- axdata_core/adapters/tdx_ext/pool.py +153 -0
- axdata_core/adapters/tdx_ext/provider_bridge.py +35 -0
- axdata_core/adapters/tdx_ext/request.py +498 -0
- axdata_core/adapters/tdx_ext/request_execution.py +118 -0
- axdata_core/adapters/tdx_ext/request_instruments.py +221 -0
- axdata_core/adapters/tdx_ext/request_normalize.py +356 -0
- axdata_core/adapters/tdx_ext/request_params.py +157 -0
- axdata_core/adapters/tdx_ext/request_series.py +98 -0
- axdata_core/adapters/tdx_ext/server_cache.py +13 -0
- axdata_core/adapters/tdx_ext/servers.py +35 -0
- axdata_core/adapters/tdx_ext/source_adapter_registry.py +42 -0
- axdata_core/adapters/tdx_ext/source_execution.py +19 -0
- axdata_core/adapters/tdx_ext/source_execution_registry.py +43 -0
- axdata_core/adapters/tencent/__init__.py +17 -0
- axdata_core/adapters/tencent/provider_bridge.py +25 -0
- axdata_core/adapters/tencent/request.py +729 -0
- axdata_core/adapters/tencent/source_adapter_registry.py +42 -0
- axdata_core/axp.py +1843 -0
- axdata_core/builtin_providers.py +586 -0
- axdata_core/builtin_source_declarations.py +156 -0
- axdata_core/cli.py +1818 -0
- axdata_core/collector_registry.py +227 -0
- axdata_core/collector_runner.py +1016 -0
- axdata_core/collector_scheduler.py +3155 -0
- axdata_core/collector_templates.py +339 -0
- axdata_core/data_browser.py +1696 -0
- axdata_core/diagnostics.py +734 -0
- axdata_core/downloader_engine.py +1480 -0
- axdata_core/downloader_registry.py +62 -0
- axdata_core/downloaders.py +1619 -0
- axdata_core/legacy_provider_adapter.py +68 -0
- axdata_core/paths.py +51 -0
- axdata_core/plugin_config.py +272 -0
- axdata_core/plugin_status.py +419 -0
- axdata_core/plugins.py +1363 -0
- axdata_core/provider_catalog.py +462 -0
- axdata_core/provider_registry.py +833 -0
- axdata_core/quality.py +86 -0
- axdata_core/query.py +242 -0
- axdata_core/resources/__init__.py +2 -0
- axdata_core/resources/tdx_extended_servers.json +22 -0
- axdata_core/resources/tdx_quote_servers.json +49 -0
- axdata_core/sample_collectors.py +42 -0
- axdata_core/schema.py +385 -0
- axdata_core/source_adapter_factory.py +95 -0
- axdata_core/source_adapter_options.py +18 -0
- axdata_core/source_errors.py +43 -0
- axdata_core/source_execution_options.py +37 -0
- axdata_core/source_execution_registry.py +27 -0
- axdata_core/source_projection.py +21 -0
- axdata_core/source_request.py +441 -0
- axdata_core/source_session.py +355 -0
- axdata_core/sources/__init__.py +40 -0
- axdata_core/sources/base.py +112 -0
- axdata_core/sources/catalog.py +60 -0
- axdata_core/sources/cls/__init__.py +5 -0
- axdata_core/sources/cls/catalog.py +231 -0
- axdata_core/sources/cninfo/__init__.py +5 -0
- axdata_core/sources/cninfo/catalog.py +1994 -0
- axdata_core/sources/display_docs.py +139 -0
- axdata_core/sources/eastmoney/__init__.py +5 -0
- axdata_core/sources/eastmoney/catalog.py +509 -0
- axdata_core/sources/exchange/__init__.py +5 -0
- axdata_core/sources/exchange/catalog.py +361 -0
- axdata_core/sources/kph/__init__.py +5 -0
- axdata_core/sources/kph/catalog.py +255 -0
- axdata_core/sources/sina/__init__.py +5 -0
- axdata_core/sources/sina/catalog.py +2951 -0
- axdata_core/sources/tdx/__init__.py +5 -0
- axdata_core/sources/tdx/catalog.py +4546 -0
- axdata_core/sources/tdx_ext/__init__.py +5 -0
- axdata_core/sources/tdx_ext/catalog.py +1518 -0
- axdata_core/sources/tencent/__init__.py +5 -0
- axdata_core/sources/tencent/catalog.py +370 -0
- axdata_core/storage.py +186 -0
- axdata_core/tdx_f10_catalog.py +52 -0
- axdata_core/tdx_f10_models.py +50 -0
- axdata_core/tdx_f10_names.py +47 -0
- axdata_core/tdx_f10_specs.py +56 -0
- axdata_core/tdx_plugin_required.py +43 -0
- axdata_core/tdx_server_config.py +65 -0
- axdata_core/trade_calendar_cache.py +397 -0
- axdata_source_cninfo/__init__.py +15 -0
- axdata_source_cninfo/adapter.py +31 -0
- axdata_source_cninfo/axdata-provider.json +384 -0
- axdata_source_cninfo/catalog.py +209 -0
- axdata_source_cninfo/metadata.py +8 -0
- axdata_source_cninfo/provider.py +41 -0
- axdata_source_tdx/__init__.py +15 -0
- axdata_source_tdx/_tdx_wire/__init__.py +26 -0
- axdata_source_tdx/_tdx_wire/_binary.py +218 -0
- axdata_source_tdx/_tdx_wire/_code_utils.py +42 -0
- axdata_source_tdx/_tdx_wire/_command_codec.py +186 -0
- axdata_source_tdx/_tdx_wire/_command_codes.py +74 -0
- axdata_source_tdx/_tdx_wire/_command_defaults.py +15 -0
- axdata_source_tdx/_tdx_wire/_command_dispatch.py +96 -0
- axdata_source_tdx/_tdx_wire/_command_layouts.py +96 -0
- axdata_source_tdx/_tdx_wire/_command_lookup.py +25 -0
- axdata_source_tdx/_tdx_wire/_command_metadata.py +32 -0
- axdata_source_tdx/_tdx_wire/_command_registry.py +61 -0
- axdata_source_tdx/_tdx_wire/_connection_defaults.py +13 -0
- axdata_source_tdx/_tdx_wire/_host_defaults.py +51 -0
- axdata_source_tdx/_tdx_wire/_host_probe.py +81 -0
- axdata_source_tdx/_tdx_wire/_host_resource.py +70 -0
- axdata_source_tdx/_tdx_wire/_host_utils.py +31 -0
- axdata_source_tdx/_tdx_wire/_market.py +66 -0
- axdata_source_tdx/_tdx_wire/_request_defaults.py +11 -0
- axdata_source_tdx/_tdx_wire/_security_classification.py +61 -0
- axdata_source_tdx/_tdx_wire/_time_utils.py +7 -0
- axdata_source_tdx/_tdx_wire/api/__init__.py +45 -0
- axdata_source_tdx/_tdx_wire/api/auction.py +25 -0
- axdata_source_tdx/_tdx_wire/api/bars.py +31 -0
- axdata_source_tdx/_tdx_wire/api/base.py +39 -0
- axdata_source_tdx/_tdx_wire/api/codes.py +25 -0
- axdata_source_tdx/_tdx_wire/api/corporate.py +11 -0
- axdata_source_tdx/_tdx_wire/api/finance.py +10 -0
- axdata_source_tdx/_tdx_wire/api/intraday.py +38 -0
- axdata_source_tdx/_tdx_wire/api/quotes.py +78 -0
- axdata_source_tdx/_tdx_wire/api/resources.py +34 -0
- axdata_source_tdx/_tdx_wire/api/session.py +16 -0
- axdata_source_tdx/_tdx_wire/api/trades.py +34 -0
- axdata_source_tdx/_tdx_wire/client.py +470 -0
- axdata_source_tdx/_tdx_wire/exceptions.py +25 -0
- axdata_source_tdx/_tdx_wire/hosts.py +27 -0
- axdata_source_tdx/_tdx_wire/models/__init__.py +87 -0
- axdata_source_tdx/_tdx_wire/models/auction.py +58 -0
- axdata_source_tdx/_tdx_wire/models/corporate.py +59 -0
- axdata_source_tdx/_tdx_wire/models/finance.py +80 -0
- axdata_source_tdx/_tdx_wire/models/intraday.py +112 -0
- axdata_source_tdx/_tdx_wire/models/kline.py +58 -0
- axdata_source_tdx/_tdx_wire/models/quote.py +262 -0
- axdata_source_tdx/_tdx_wire/models/resource.py +18 -0
- axdata_source_tdx/_tdx_wire/models/security.py +28 -0
- axdata_source_tdx/_tdx_wire/models/session.py +30 -0
- axdata_source_tdx/_tdx_wire/models/subchart.py +39 -0
- axdata_source_tdx/_tdx_wire/models/trade.py +46 -0
- axdata_source_tdx/_tdx_wire/protocol/__init__.py +43 -0
- axdata_source_tdx/_tdx_wire/protocol/_frame_constants.py +5 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/__init__.py +37 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/auction.py +165 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/codec.py +37 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/corporate.py +163 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/finance.py +180 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/intraday.py +382 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/klines.py +396 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/lookup.py +31 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/price_limits.py +110 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/quotes.py +804 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/registry.py +30 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/resources.py +107 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/security.py +163 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/session.py +129 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/subchart.py +182 -0
- axdata_source_tdx/_tdx_wire/protocol/commands/trades.py +275 -0
- axdata_source_tdx/_tdx_wire/protocol/constants.py +70 -0
- axdata_source_tdx/_tdx_wire/protocol/frame.py +141 -0
- axdata_source_tdx/_tdx_wire/protocol/unit.py +98 -0
- axdata_source_tdx/_tdx_wire/py.typed +1 -0
- axdata_source_tdx/_tdx_wire/transport/__init__.py +28 -0
- axdata_source_tdx/_tdx_wire/transport/base.py +21 -0
- axdata_source_tdx/_tdx_wire/transport/memory.py +42 -0
- axdata_source_tdx/_tdx_wire/transport/pool.py +148 -0
- axdata_source_tdx/_tdx_wire/transport/socket.py +373 -0
- axdata_source_tdx/adapter.py +31 -0
- axdata_source_tdx/adjustment.py +163 -0
- axdata_source_tdx/adjustment_fetch.py +148 -0
- axdata_source_tdx/auction_fetch.py +162 -0
- axdata_source_tdx/axdata-provider.json +23680 -0
- axdata_source_tdx/catalog.py +39 -0
- axdata_source_tdx/client_factory.py +61 -0
- axdata_source_tdx/code_fetch.py +579 -0
- axdata_source_tdx/codes.py +69 -0
- axdata_source_tdx/collectors.py +525 -0
- axdata_source_tdx/derived_rows.py +500 -0
- axdata_source_tdx/downloader.py +139 -0
- axdata_source_tdx/downloader_interface_sets.py +29 -0
- axdata_source_tdx/downloader_profiles.py +731 -0
- axdata_source_tdx/downloader_registry.py +85 -0
- axdata_source_tdx/execution_utils.py +141 -0
- axdata_source_tdx/f10_executor.py +414 -0
- axdata_source_tdx/f10_normalize.py +169 -0
- axdata_source_tdx/f10_params.py +221 -0
- axdata_source_tdx/f10_postprocess.py +405 -0
- axdata_source_tdx/f10_render.py +29 -0
- axdata_source_tdx/f10_request.py +365 -0
- axdata_source_tdx/finance_fetch.py +514 -0
- axdata_source_tdx/finance_maps.py +377 -0
- axdata_source_tdx/finance_normalize.py +273 -0
- axdata_source_tdx/host_config.py +51 -0
- axdata_source_tdx/interface_sets.py +180 -0
- axdata_source_tdx/intraday_fetch.py +600 -0
- axdata_source_tdx/kline_helpers.py +333 -0
- axdata_source_tdx/limit_ladder_fetch.py +614 -0
- axdata_source_tdx/limit_ladder_topics.py +280 -0
- axdata_source_tdx/metadata.py +8 -0
- axdata_source_tdx/normalize_utils.py +264 -0
- axdata_source_tdx/options.py +195 -0
- axdata_source_tdx/price_limit_calendar.py +106 -0
- axdata_source_tdx/price_limit_fetch.py +264 -0
- axdata_source_tdx/price_limit_history.py +100 -0
- axdata_source_tdx/price_limits.py +142 -0
- axdata_source_tdx/provider.py +44 -0
- axdata_source_tdx/provider_bridge.py +43 -0
- axdata_source_tdx/quote_fetch.py +485 -0
- axdata_source_tdx/quote_identity.py +50 -0
- axdata_source_tdx/rank_fetch.py +316 -0
- axdata_source_tdx/rank_params.py +181 -0
- axdata_source_tdx/realtime_refresh.py +51 -0
- axdata_source_tdx/request_adapter.py +533 -0
- axdata_source_tdx/request_adapter_runtime.py +302 -0
- axdata_source_tdx/request_client.py +98 -0
- axdata_source_tdx/request_compat.py +432 -0
- axdata_source_tdx/request_dispatch.py +138 -0
- axdata_source_tdx/request_entrypoints.py +146 -0
- axdata_source_tdx/request_filters.py +154 -0
- axdata_source_tdx/request_host_config.py +103 -0
- axdata_source_tdx/request_limits.py +15 -0
- axdata_source_tdx/request_methods.py +1910 -0
- axdata_source_tdx/request_params.py +225 -0
- axdata_source_tdx/request_seams.py +534 -0
- axdata_source_tdx/resources/__init__.py +0 -0
- axdata_source_tdx/resources/finance_maps/__init__.py +1 -0
- axdata_source_tdx/resources/finance_maps/incon.dat +3702 -0
- axdata_source_tdx/resources/finance_maps/tdxhy.cfg +5620 -0
- axdata_source_tdx/resources/finance_maps/tdxzs.cfg +605 -0
- axdata_source_tdx/resources/tdx_extended_servers.json +22 -0
- axdata_source_tdx/resources/tdx_quote_servers.json +49 -0
- axdata_source_tdx/security_codes.py +127 -0
- axdata_source_tdx/series_history.py +348 -0
- axdata_source_tdx/server_cache.py +21 -0
- axdata_source_tdx/snapshot_normalize.py +232 -0
- axdata_source_tdx/source_adapter_registry.py +42 -0
- axdata_source_tdx/source_execution.py +22 -0
- axdata_source_tdx/source_execution_registry.py +43 -0
- axdata_source_tdx/stats_cache.py +150 -0
- axdata_source_tdx/stats_models.py +161 -0
- axdata_source_tdx/stats_resource.py +242 -0
- axdata_source_tdx/status_fetch.py +209 -0
- axdata_source_tdx/tdx_f10_catalog.py +957 -0
- axdata_source_tdx/tdx_f10_models.py +47 -0
- axdata_source_tdx/tdx_f10_names.py +48 -0
- axdata_source_tdx/tdx_f10_specs.py +1142 -0
- axdata_source_tdx/tdx_server_config.py +389 -0
- axdata_source_tdx/time_series_normalize.py +370 -0
- axdata_source_tdx/tqlex.py +138 -0
- axdata_source_tdx/wire.py +32 -0
- axdata_source_tdx/wire_requests.py +190 -0
- axdata_source_tdx_ext/__init__.py +15 -0
- axdata_source_tdx_ext/adapter.py +31 -0
- axdata_source_tdx_ext/axdata-provider.json +9424 -0
- axdata_source_tdx_ext/catalog.py +33 -0
- axdata_source_tdx_ext/metadata.py +8 -0
- axdata_source_tdx_ext/provider.py +44 -0
- axdata_source_tencent/__init__.py +15 -0
- axdata_source_tencent/adapter.py +31 -0
- axdata_source_tencent/axdata-provider.json +291 -0
- axdata_source_tencent/catalog.py +190 -0
- axdata_source_tencent/metadata.py +8 -0
- axdata_source_tencent/provider.py +41 -0
|
@@ -0,0 +1,470 @@
|
|
|
1
|
+
"""Minimal TDX 7709 client used by AxData source code-table requests."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
from collections.abc import Sequence
|
|
6
|
+
from dataclasses import dataclass, field
|
|
7
|
+
from importlib import import_module
|
|
8
|
+
from typing import TYPE_CHECKING, Any
|
|
9
|
+
|
|
10
|
+
from ._connection_defaults import DEFAULT_PROBE_TIMEOUT, DEFAULT_PROBE_WORKERS
|
|
11
|
+
from ._request_defaults import DEFAULT_CODE_PAGE_SIZE, DEFAULT_FILE_CHUNK_SIZE, DEFAULT_QUOTE_BATCH_SIZE
|
|
12
|
+
|
|
13
|
+
if TYPE_CHECKING:
|
|
14
|
+
from .api.auction import AuctionApi
|
|
15
|
+
from .api.bars import BarApi
|
|
16
|
+
from .api.codes import CodeApi
|
|
17
|
+
from .api.corporate import CorporateApi
|
|
18
|
+
from .api.finance import FinanceApi
|
|
19
|
+
from .api.intraday import IntradayApi
|
|
20
|
+
from .api.quotes import QuoteApi
|
|
21
|
+
from .api.resources import ResourceApi
|
|
22
|
+
from .api.session import SessionApi
|
|
23
|
+
from .api.trades import TradeApi
|
|
24
|
+
from .models.auction import AuctionProcessSeries
|
|
25
|
+
from .models.corporate import CapitalChangeBlock
|
|
26
|
+
from .models.finance import FinanceInfoBlock
|
|
27
|
+
from .models.intraday import (
|
|
28
|
+
HistoricalIntradaySeries,
|
|
29
|
+
RecentHistoricalIntradaySeries,
|
|
30
|
+
TodayIntradaySeries,
|
|
31
|
+
)
|
|
32
|
+
from .models.kline import KlineSeries
|
|
33
|
+
from .models.quote import CategoryQuotePage, ExplicitQuote, LegacyQuote, QuoteRefreshBatch
|
|
34
|
+
from .models.resource import FileContentChunk
|
|
35
|
+
from .models.security import SecurityCode
|
|
36
|
+
from .models.subchart import IntradaySubchartSeries
|
|
37
|
+
from .models.trade import TradeDetailSeries
|
|
38
|
+
from .transport.base import Transport
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
@dataclass(slots=True)
|
|
42
|
+
class TdxClient:
|
|
43
|
+
"""Small client for the TDX security code table.
|
|
44
|
+
|
|
45
|
+
Higher-level quote, kline, minute, trade, F10, and helper APIs are
|
|
46
|
+
intentionally not exposed here. Add them back one interface at a time when
|
|
47
|
+
AxData has a concrete product contract for them.
|
|
48
|
+
"""
|
|
49
|
+
|
|
50
|
+
transport: Transport | None = None
|
|
51
|
+
host: str | None = None
|
|
52
|
+
hosts: Sequence[str] | None = None
|
|
53
|
+
timeout: float = 8.0
|
|
54
|
+
pool_size: int = 1
|
|
55
|
+
probe_hosts: bool = False
|
|
56
|
+
probe_timeout: float = DEFAULT_PROBE_TIMEOUT
|
|
57
|
+
probe_workers: int = DEFAULT_PROBE_WORKERS
|
|
58
|
+
heartbeat_interval: float | None = None
|
|
59
|
+
_auction: AuctionApi | None = field(default=None, init=False, repr=False)
|
|
60
|
+
_session: SessionApi | None = field(default=None, init=False, repr=False)
|
|
61
|
+
_bars: BarApi | None = field(default=None, init=False, repr=False)
|
|
62
|
+
_codes: CodeApi | None = field(default=None, init=False, repr=False)
|
|
63
|
+
_corporate: CorporateApi | None = field(default=None, init=False, repr=False)
|
|
64
|
+
_finance: FinanceApi | None = field(default=None, init=False, repr=False)
|
|
65
|
+
_intraday: IntradayApi | None = field(default=None, init=False, repr=False)
|
|
66
|
+
_quotes: QuoteApi | None = field(default=None, init=False, repr=False)
|
|
67
|
+
_resources: ResourceApi | None = field(default=None, init=False, repr=False)
|
|
68
|
+
_trades: TradeApi | None = field(default=None, init=False, repr=False)
|
|
69
|
+
_code_count_cache: dict[str, int] = field(init=False, repr=False)
|
|
70
|
+
_codes_all_cache: dict[str, list[SecurityCode]] = field(init=False, repr=False)
|
|
71
|
+
|
|
72
|
+
@classmethod
|
|
73
|
+
def from_hosts(
|
|
74
|
+
cls,
|
|
75
|
+
hosts: list[str] | tuple[str, ...] | None = None,
|
|
76
|
+
*,
|
|
77
|
+
timeout: float = 8.0,
|
|
78
|
+
pool_size: int = 1,
|
|
79
|
+
probe_hosts: bool = False,
|
|
80
|
+
probe_timeout: float = DEFAULT_PROBE_TIMEOUT,
|
|
81
|
+
probe_workers: int = DEFAULT_PROBE_WORKERS,
|
|
82
|
+
heartbeat_interval: float | None = None,
|
|
83
|
+
) -> TdxClient:
|
|
84
|
+
"""Create a client backed by one or more real TDX 7709 hosts."""
|
|
85
|
+
|
|
86
|
+
from .transport.pool import PooledSocketTransport
|
|
87
|
+
|
|
88
|
+
return cls(
|
|
89
|
+
transport=PooledSocketTransport(
|
|
90
|
+
hosts=hosts,
|
|
91
|
+
timeout=timeout,
|
|
92
|
+
pool_size=pool_size,
|
|
93
|
+
probe_hosts=probe_hosts,
|
|
94
|
+
probe_timeout=probe_timeout,
|
|
95
|
+
probe_workers=probe_workers,
|
|
96
|
+
heartbeat_interval=heartbeat_interval,
|
|
97
|
+
),
|
|
98
|
+
hosts=hosts,
|
|
99
|
+
timeout=timeout,
|
|
100
|
+
pool_size=pool_size,
|
|
101
|
+
probe_hosts=probe_hosts,
|
|
102
|
+
probe_timeout=probe_timeout,
|
|
103
|
+
probe_workers=probe_workers,
|
|
104
|
+
heartbeat_interval=heartbeat_interval,
|
|
105
|
+
)
|
|
106
|
+
|
|
107
|
+
@classmethod
|
|
108
|
+
def in_memory(cls) -> TdxClient:
|
|
109
|
+
"""Create a deterministic client for tests."""
|
|
110
|
+
|
|
111
|
+
from .transport.memory import InMemoryTransport
|
|
112
|
+
|
|
113
|
+
return cls(transport=InMemoryTransport())
|
|
114
|
+
|
|
115
|
+
def __post_init__(self) -> None:
|
|
116
|
+
if self.transport is None:
|
|
117
|
+
from .transport.pool import PooledSocketTransport
|
|
118
|
+
|
|
119
|
+
resolved_hosts = _resolve_hosts(self.host, self.hosts)
|
|
120
|
+
self.transport = PooledSocketTransport(
|
|
121
|
+
hosts=resolved_hosts or None,
|
|
122
|
+
timeout=self.timeout,
|
|
123
|
+
pool_size=self.pool_size,
|
|
124
|
+
probe_hosts=self.probe_hosts,
|
|
125
|
+
probe_timeout=self.probe_timeout,
|
|
126
|
+
probe_workers=self.probe_workers,
|
|
127
|
+
heartbeat_interval=self.heartbeat_interval,
|
|
128
|
+
)
|
|
129
|
+
self._code_count_cache = {}
|
|
130
|
+
self._codes_all_cache = {}
|
|
131
|
+
|
|
132
|
+
def _api(self, cache_name: str, module_name: str, class_name: str) -> Any:
|
|
133
|
+
value = getattr(self, cache_name)
|
|
134
|
+
if value is None:
|
|
135
|
+
module = import_module(f"{__package__}.{module_name}")
|
|
136
|
+
api_cls = getattr(module, class_name)
|
|
137
|
+
value = api_cls(self.transport)
|
|
138
|
+
setattr(self, cache_name, value)
|
|
139
|
+
return value
|
|
140
|
+
|
|
141
|
+
@property
|
|
142
|
+
def auction(self) -> AuctionApi:
|
|
143
|
+
return self._api("_auction", "api.auction", "AuctionApi")
|
|
144
|
+
|
|
145
|
+
@auction.setter
|
|
146
|
+
def auction(self, value: AuctionApi) -> None:
|
|
147
|
+
self._auction = value
|
|
148
|
+
|
|
149
|
+
@property
|
|
150
|
+
def session(self) -> SessionApi:
|
|
151
|
+
return self._api("_session", "api.session", "SessionApi")
|
|
152
|
+
|
|
153
|
+
@session.setter
|
|
154
|
+
def session(self, value: SessionApi) -> None:
|
|
155
|
+
self._session = value
|
|
156
|
+
|
|
157
|
+
@property
|
|
158
|
+
def bars(self) -> BarApi:
|
|
159
|
+
return self._api("_bars", "api.bars", "BarApi")
|
|
160
|
+
|
|
161
|
+
@bars.setter
|
|
162
|
+
def bars(self, value: BarApi) -> None:
|
|
163
|
+
self._bars = value
|
|
164
|
+
|
|
165
|
+
@property
|
|
166
|
+
def codes(self) -> CodeApi:
|
|
167
|
+
return self._api("_codes", "api.codes", "CodeApi")
|
|
168
|
+
|
|
169
|
+
@codes.setter
|
|
170
|
+
def codes(self, value: CodeApi) -> None:
|
|
171
|
+
self._codes = value
|
|
172
|
+
|
|
173
|
+
@property
|
|
174
|
+
def corporate(self) -> CorporateApi:
|
|
175
|
+
return self._api("_corporate", "api.corporate", "CorporateApi")
|
|
176
|
+
|
|
177
|
+
@corporate.setter
|
|
178
|
+
def corporate(self, value: CorporateApi) -> None:
|
|
179
|
+
self._corporate = value
|
|
180
|
+
|
|
181
|
+
@property
|
|
182
|
+
def finance(self) -> FinanceApi:
|
|
183
|
+
return self._api("_finance", "api.finance", "FinanceApi")
|
|
184
|
+
|
|
185
|
+
@finance.setter
|
|
186
|
+
def finance(self, value: FinanceApi) -> None:
|
|
187
|
+
self._finance = value
|
|
188
|
+
|
|
189
|
+
@property
|
|
190
|
+
def intraday(self) -> IntradayApi:
|
|
191
|
+
return self._api("_intraday", "api.intraday", "IntradayApi")
|
|
192
|
+
|
|
193
|
+
@intraday.setter
|
|
194
|
+
def intraday(self, value: IntradayApi) -> None:
|
|
195
|
+
self._intraday = value
|
|
196
|
+
|
|
197
|
+
@property
|
|
198
|
+
def quotes(self) -> QuoteApi:
|
|
199
|
+
return self._api("_quotes", "api.quotes", "QuoteApi")
|
|
200
|
+
|
|
201
|
+
@quotes.setter
|
|
202
|
+
def quotes(self, value: QuoteApi) -> None:
|
|
203
|
+
self._quotes = value
|
|
204
|
+
|
|
205
|
+
@property
|
|
206
|
+
def resources(self) -> ResourceApi:
|
|
207
|
+
return self._api("_resources", "api.resources", "ResourceApi")
|
|
208
|
+
|
|
209
|
+
@resources.setter
|
|
210
|
+
def resources(self, value: ResourceApi) -> None:
|
|
211
|
+
self._resources = value
|
|
212
|
+
|
|
213
|
+
@property
|
|
214
|
+
def trades(self) -> TradeApi:
|
|
215
|
+
return self._api("_trades", "api.trades", "TradeApi")
|
|
216
|
+
|
|
217
|
+
@trades.setter
|
|
218
|
+
def trades(self, value: TradeApi) -> None:
|
|
219
|
+
self._trades = value
|
|
220
|
+
|
|
221
|
+
def connect(self) -> None:
|
|
222
|
+
self.transport.connect()
|
|
223
|
+
|
|
224
|
+
def close(self) -> None:
|
|
225
|
+
self.transport.close()
|
|
226
|
+
|
|
227
|
+
def __enter__(self) -> TdxClient:
|
|
228
|
+
self.connect()
|
|
229
|
+
return self
|
|
230
|
+
|
|
231
|
+
def __exit__(self, exc_type, exc, tb) -> None:
|
|
232
|
+
self.close()
|
|
233
|
+
|
|
234
|
+
def ping(self) -> str:
|
|
235
|
+
return self.session.ping()
|
|
236
|
+
|
|
237
|
+
def clear_cache(self) -> None:
|
|
238
|
+
self._code_count_cache.clear()
|
|
239
|
+
self._codes_all_cache.clear()
|
|
240
|
+
|
|
241
|
+
def get_count(self, exchange, *, refresh: bool = False) -> int:
|
|
242
|
+
market = _normalize_market(exchange)
|
|
243
|
+
if not refresh and market in self._code_count_cache:
|
|
244
|
+
return self._code_count_cache[market]
|
|
245
|
+
count = self.codes.count(market)
|
|
246
|
+
self._code_count_cache[market] = count
|
|
247
|
+
return count
|
|
248
|
+
|
|
249
|
+
def get_codes(self, exchange, *, start: int = 0, limit: int | None = DEFAULT_CODE_PAGE_SIZE):
|
|
250
|
+
market = _normalize_market(exchange)
|
|
251
|
+
if start < 0:
|
|
252
|
+
raise ValueError("start must be >= 0")
|
|
253
|
+
if limit is None:
|
|
254
|
+
return self.codes.all(market)[start:]
|
|
255
|
+
if limit < 0:
|
|
256
|
+
raise ValueError("limit must be >= 0")
|
|
257
|
+
return self.codes.list(market, start=start, limit=limit)
|
|
258
|
+
|
|
259
|
+
def get_codes_all(self, exchange, *, refresh: bool = False) -> list[SecurityCode]:
|
|
260
|
+
market = _normalize_market(exchange)
|
|
261
|
+
if not refresh and market in self._codes_all_cache:
|
|
262
|
+
return list(self._codes_all_cache[market])
|
|
263
|
+
items = list(self.codes.all(market))
|
|
264
|
+
self._codes_all_cache[market] = items
|
|
265
|
+
self._code_count_cache[market] = len(items)
|
|
266
|
+
return list(items)
|
|
267
|
+
|
|
268
|
+
def get_legacy_quotes(
|
|
269
|
+
self,
|
|
270
|
+
securities: Sequence[tuple[str, str]],
|
|
271
|
+
*,
|
|
272
|
+
batch_size: int = DEFAULT_QUOTE_BATCH_SIZE,
|
|
273
|
+
) -> list[LegacyQuote]:
|
|
274
|
+
normalized = [(_normalize_market(market), str(code)) for market, code in securities]
|
|
275
|
+
return self.quotes.legacy_all(normalized, batch_size=batch_size)
|
|
276
|
+
|
|
277
|
+
def get_explicit_quotes(
|
|
278
|
+
self,
|
|
279
|
+
securities: Sequence[tuple[str, str]],
|
|
280
|
+
*,
|
|
281
|
+
batch_size: int = DEFAULT_QUOTE_BATCH_SIZE,
|
|
282
|
+
) -> list[ExplicitQuote]:
|
|
283
|
+
normalized = [(_normalize_market(market), str(code)) for market, code in securities]
|
|
284
|
+
return self.quotes.explicit_all(normalized, batch_size=batch_size)
|
|
285
|
+
|
|
286
|
+
def get_quote_refresh(
|
|
287
|
+
self,
|
|
288
|
+
cursors: Sequence[tuple[str, str, int] | tuple[str, str]],
|
|
289
|
+
) -> QuoteRefreshBatch:
|
|
290
|
+
normalized = []
|
|
291
|
+
for item in cursors:
|
|
292
|
+
if len(item) == 2:
|
|
293
|
+
market, code = item
|
|
294
|
+
cursor = 0
|
|
295
|
+
else:
|
|
296
|
+
market, code, cursor = item
|
|
297
|
+
normalized.append((_normalize_market(market), str(code), int(cursor)))
|
|
298
|
+
return self.quotes.refresh(normalized)
|
|
299
|
+
|
|
300
|
+
def download_file_resource_chunk(
|
|
301
|
+
self,
|
|
302
|
+
path: str,
|
|
303
|
+
*,
|
|
304
|
+
offset: int = 0,
|
|
305
|
+
size: int = DEFAULT_FILE_CHUNK_SIZE,
|
|
306
|
+
) -> FileContentChunk:
|
|
307
|
+
return self.resources.download_chunk(path, offset=offset, size=size)
|
|
308
|
+
|
|
309
|
+
def download_file_resource(
|
|
310
|
+
self,
|
|
311
|
+
path: str,
|
|
312
|
+
*,
|
|
313
|
+
chunk_size: int = DEFAULT_FILE_CHUNK_SIZE,
|
|
314
|
+
max_bytes: int | None = None,
|
|
315
|
+
) -> bytes:
|
|
316
|
+
return self.resources.download_file(path, chunk_size=chunk_size, max_bytes=max_bytes)
|
|
317
|
+
|
|
318
|
+
def get_category_quotes(
|
|
319
|
+
self,
|
|
320
|
+
*,
|
|
321
|
+
category: int = 6,
|
|
322
|
+
sort_type: int = 0,
|
|
323
|
+
start: int = 0,
|
|
324
|
+
count: int = 80,
|
|
325
|
+
ascending: bool = False,
|
|
326
|
+
filter_raw: int = 0,
|
|
327
|
+
) -> CategoryQuotePage:
|
|
328
|
+
return self.quotes.category(
|
|
329
|
+
category=category,
|
|
330
|
+
sort_type=sort_type,
|
|
331
|
+
start=start,
|
|
332
|
+
count=count,
|
|
333
|
+
ascending=ascending,
|
|
334
|
+
filter_raw=filter_raw,
|
|
335
|
+
)
|
|
336
|
+
|
|
337
|
+
def get_price_limits(self, *, start_index: int = 0):
|
|
338
|
+
return self.quotes.price_limits(start_index=start_index)
|
|
339
|
+
|
|
340
|
+
def get_price_limits_all(self):
|
|
341
|
+
return self.quotes.price_limits_all()
|
|
342
|
+
|
|
343
|
+
def get_auction_process(
|
|
344
|
+
self,
|
|
345
|
+
code: str,
|
|
346
|
+
*,
|
|
347
|
+
mode_or_selector_raw: int = 3,
|
|
348
|
+
start: int = 0,
|
|
349
|
+
count: int = 500,
|
|
350
|
+
include_raw: bool = False,
|
|
351
|
+
) -> AuctionProcessSeries:
|
|
352
|
+
return self.auction.process(
|
|
353
|
+
code,
|
|
354
|
+
mode_or_selector_raw=mode_or_selector_raw,
|
|
355
|
+
start=start,
|
|
356
|
+
count=count,
|
|
357
|
+
include_raw=include_raw,
|
|
358
|
+
)
|
|
359
|
+
|
|
360
|
+
def get_kline(
|
|
361
|
+
self,
|
|
362
|
+
code: str,
|
|
363
|
+
*,
|
|
364
|
+
period: str = "day",
|
|
365
|
+
start: int = 0,
|
|
366
|
+
count: int = 800,
|
|
367
|
+
adjust: str | None = None,
|
|
368
|
+
anchor_date=None,
|
|
369
|
+
kind: str = "stock",
|
|
370
|
+
include_raw: bool = False,
|
|
371
|
+
) -> KlineSeries:
|
|
372
|
+
return self.bars.get(
|
|
373
|
+
code,
|
|
374
|
+
period=period,
|
|
375
|
+
start=start,
|
|
376
|
+
count=count,
|
|
377
|
+
adjust=adjust,
|
|
378
|
+
anchor_date=anchor_date,
|
|
379
|
+
kind=kind,
|
|
380
|
+
include_raw=include_raw,
|
|
381
|
+
)
|
|
382
|
+
|
|
383
|
+
def get_capital_changes(self, code: str, *, include_raw: bool = False) -> CapitalChangeBlock:
|
|
384
|
+
return self.corporate.capital_changes(code, include_raw=include_raw)
|
|
385
|
+
|
|
386
|
+
def get_finance_info(self, code, *, include_raw: bool = False) -> FinanceInfoBlock:
|
|
387
|
+
return self.finance.info(code, include_raw=include_raw)
|
|
388
|
+
|
|
389
|
+
def get_historical_intraday(
|
|
390
|
+
self,
|
|
391
|
+
code: str,
|
|
392
|
+
*,
|
|
393
|
+
trade_date,
|
|
394
|
+
include_raw: bool = False,
|
|
395
|
+
) -> HistoricalIntradaySeries:
|
|
396
|
+
return self.intraday.historical(code, trade_date=trade_date, include_raw=include_raw)
|
|
397
|
+
|
|
398
|
+
def get_recent_historical_intraday(
|
|
399
|
+
self,
|
|
400
|
+
code: str,
|
|
401
|
+
*,
|
|
402
|
+
trade_date,
|
|
403
|
+
include_raw: bool = False,
|
|
404
|
+
) -> RecentHistoricalIntradaySeries:
|
|
405
|
+
return self.intraday.recent_historical(code, trade_date=trade_date, include_raw=include_raw)
|
|
406
|
+
|
|
407
|
+
def get_today_intraday(
|
|
408
|
+
self,
|
|
409
|
+
code: str,
|
|
410
|
+
*,
|
|
411
|
+
include_raw: bool = False,
|
|
412
|
+
) -> TodayIntradaySeries:
|
|
413
|
+
return self.intraday.today(code, include_raw=include_raw)
|
|
414
|
+
|
|
415
|
+
def get_intraday_subchart(
|
|
416
|
+
self,
|
|
417
|
+
code: str,
|
|
418
|
+
*,
|
|
419
|
+
selector=0,
|
|
420
|
+
include_raw: bool = False,
|
|
421
|
+
) -> IntradaySubchartSeries:
|
|
422
|
+
return self.intraday.subchart(code, selector=selector, include_raw=include_raw)
|
|
423
|
+
|
|
424
|
+
def get_today_trades(
|
|
425
|
+
self,
|
|
426
|
+
code: str,
|
|
427
|
+
*,
|
|
428
|
+
start: int = 0,
|
|
429
|
+
count: int = 115,
|
|
430
|
+
include_raw: bool = False,
|
|
431
|
+
) -> TradeDetailSeries:
|
|
432
|
+
return self.trades.today(code, start=start, count=count, include_raw=include_raw)
|
|
433
|
+
|
|
434
|
+
def get_historical_trades(
|
|
435
|
+
self,
|
|
436
|
+
code: str,
|
|
437
|
+
*,
|
|
438
|
+
trade_date,
|
|
439
|
+
start: int = 0,
|
|
440
|
+
count: int = 900,
|
|
441
|
+
include_raw: bool = False,
|
|
442
|
+
) -> TradeDetailSeries:
|
|
443
|
+
return self.trades.historical(
|
|
444
|
+
code,
|
|
445
|
+
trade_date=trade_date,
|
|
446
|
+
start=start,
|
|
447
|
+
count=count,
|
|
448
|
+
include_raw=include_raw,
|
|
449
|
+
)
|
|
450
|
+
|
|
451
|
+
|
|
452
|
+
def _resolve_hosts(host: str | None, hosts: Sequence[str] | None) -> list[str]:
|
|
453
|
+
if hosts is None:
|
|
454
|
+
resolved_hosts = []
|
|
455
|
+
elif isinstance(hosts, str):
|
|
456
|
+
resolved_hosts = [hosts]
|
|
457
|
+
else:
|
|
458
|
+
resolved_hosts = list(hosts)
|
|
459
|
+
if host is not None:
|
|
460
|
+
resolved_hosts.insert(0, host)
|
|
461
|
+
return resolved_hosts
|
|
462
|
+
|
|
463
|
+
|
|
464
|
+
def _normalize_market(value) -> str:
|
|
465
|
+
from ._market import normalize_market
|
|
466
|
+
|
|
467
|
+
return normalize_market(value)
|
|
468
|
+
|
|
469
|
+
|
|
470
|
+
Client = TdxClient
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
"""axdata_source_tdx._tdx_wire exception hierarchy."""
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
class TdxWireError(Exception):
|
|
5
|
+
"""Base class for package errors."""
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
class ProtocolError(TdxWireError):
|
|
9
|
+
"""Raised when protocol encoding or decoding fails."""
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
class TransportError(TdxWireError):
|
|
13
|
+
"""Raised when the transport cannot complete a request."""
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
class ConnectionClosedError(TransportError):
|
|
17
|
+
"""Raised when the remote server closes the connection."""
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
class ResponseTimeoutError(TransportError):
|
|
21
|
+
"""Raised when a request does not receive a response in time."""
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
class UnsupportedCommandError(TdxWireError):
|
|
25
|
+
"""Raised when an API method has no migrated 7709 command yet."""
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
"""Default 7709 quote server hosts."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
from importlib import import_module
|
|
6
|
+
|
|
7
|
+
from ._connection_defaults import DEFAULT_PROBE_TIMEOUT, DEFAULT_PROBE_WORKERS
|
|
8
|
+
from ._host_defaults import DEFAULT_QUOTE_HOSTS
|
|
9
|
+
from ._host_probe import HostProbeResult, probe_host, probe_hosts, sort_hosts_by_latency
|
|
10
|
+
from ._host_utils import normalize_host, unique_hosts
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
_RESOURCE_MODULE = "axdata_source_tdx._tdx_wire._host_resource"
|
|
14
|
+
_RESOURCE_EXPORTS = {"DEFAULT_HOSTS", "SERVER_FILE", "SERVER_RESOURCE_PACKAGE", "load_server_config", "load_server_hosts"}
|
|
15
|
+
FALLBACK_HOSTS: tuple[str, ...] = DEFAULT_QUOTE_HOSTS
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
def __getattr__(name: str):
|
|
19
|
+
if name in _RESOURCE_EXPORTS:
|
|
20
|
+
value = getattr(import_module(_RESOURCE_MODULE), name)
|
|
21
|
+
globals()[name] = value
|
|
22
|
+
return value
|
|
23
|
+
raise AttributeError(f"module {__name__!r} has no attribute {name!r}")
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
def __dir__() -> list[str]:
|
|
27
|
+
return sorted(set(globals()) | _RESOURCE_EXPORTS)
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
"""Data models exposed by the minimal TDX code-table protocol."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
from importlib import import_module
|
|
6
|
+
|
|
7
|
+
_EXPORT_MODULES = {
|
|
8
|
+
"AuctionProcessRecord": ".auction",
|
|
9
|
+
"AuctionProcessSeries": ".auction",
|
|
10
|
+
"CapitalChangeBlock": ".corporate",
|
|
11
|
+
"CapitalChangeRecord": ".corporate",
|
|
12
|
+
"CategoryQuote": ".quote",
|
|
13
|
+
"CategoryQuotePage": ".quote",
|
|
14
|
+
"ExplicitQuote": ".quote",
|
|
15
|
+
"FileContentChunk": ".resource",
|
|
16
|
+
"FinanceInfoBlock": ".finance",
|
|
17
|
+
"FinanceInfoRecord": ".finance",
|
|
18
|
+
"HandshakeInfo": ".session",
|
|
19
|
+
"HeartbeatAck": ".session",
|
|
20
|
+
"HistoricalIntradayPoint": ".intraday",
|
|
21
|
+
"HistoricalIntradaySeries": ".intraday",
|
|
22
|
+
"IntradaySubchartPoint": ".subchart",
|
|
23
|
+
"IntradaySubchartSeries": ".subchart",
|
|
24
|
+
"KlineBar": ".kline",
|
|
25
|
+
"KlineSeries": ".kline",
|
|
26
|
+
"LegacyQuote": ".quote",
|
|
27
|
+
"PriceLimitRecord": ".quote",
|
|
28
|
+
"QuoteLevel": ".quote",
|
|
29
|
+
"QuoteRefreshBatch": ".quote",
|
|
30
|
+
"QuoteRefreshCursor": ".quote",
|
|
31
|
+
"QuoteRefreshRecord": ".quote",
|
|
32
|
+
"RecentHistoricalIntradayPoint": ".intraday",
|
|
33
|
+
"RecentHistoricalIntradaySeries": ".intraday",
|
|
34
|
+
"SecurityCode": ".security",
|
|
35
|
+
"TodayIntradayPoint": ".intraday",
|
|
36
|
+
"TodayIntradaySeries": ".intraday",
|
|
37
|
+
"TradeDetailRecord": ".trade",
|
|
38
|
+
"TradeDetailSeries": ".trade",
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
__all__ = [
|
|
42
|
+
"AuctionProcessRecord",
|
|
43
|
+
"AuctionProcessSeries",
|
|
44
|
+
"CapitalChangeBlock",
|
|
45
|
+
"CapitalChangeRecord",
|
|
46
|
+
"FinanceInfoBlock",
|
|
47
|
+
"FinanceInfoRecord",
|
|
48
|
+
"HandshakeInfo",
|
|
49
|
+
"HeartbeatAck",
|
|
50
|
+
"HistoricalIntradayPoint",
|
|
51
|
+
"HistoricalIntradaySeries",
|
|
52
|
+
"RecentHistoricalIntradayPoint",
|
|
53
|
+
"RecentHistoricalIntradaySeries",
|
|
54
|
+
"TodayIntradayPoint",
|
|
55
|
+
"TodayIntradaySeries",
|
|
56
|
+
"IntradaySubchartPoint",
|
|
57
|
+
"IntradaySubchartSeries",
|
|
58
|
+
"KlineBar",
|
|
59
|
+
"KlineSeries",
|
|
60
|
+
"CategoryQuote",
|
|
61
|
+
"CategoryQuotePage",
|
|
62
|
+
"ExplicitQuote",
|
|
63
|
+
"FileContentChunk",
|
|
64
|
+
"LegacyQuote",
|
|
65
|
+
"PriceLimitRecord",
|
|
66
|
+
"QuoteLevel",
|
|
67
|
+
"QuoteRefreshBatch",
|
|
68
|
+
"QuoteRefreshCursor",
|
|
69
|
+
"QuoteRefreshRecord",
|
|
70
|
+
"SecurityCode",
|
|
71
|
+
"TradeDetailRecord",
|
|
72
|
+
"TradeDetailSeries",
|
|
73
|
+
]
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
def __getattr__(name: str):
|
|
77
|
+
module_name = _EXPORT_MODULES.get(name)
|
|
78
|
+
if module_name is None:
|
|
79
|
+
raise AttributeError(f"module {__name__!r} has no attribute {name!r}")
|
|
80
|
+
module = import_module(module_name, __name__)
|
|
81
|
+
value = getattr(module, name)
|
|
82
|
+
globals()[name] = value
|
|
83
|
+
return value
|
|
84
|
+
|
|
85
|
+
|
|
86
|
+
def __dir__() -> list[str]:
|
|
87
|
+
return sorted(set(globals()) | set(__all__))
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
"""Call-auction process models for the private TDX 7709 wire client."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
from dataclasses import dataclass
|
|
6
|
+
from datetime import time
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
@dataclass(frozen=True, slots=True)
|
|
10
|
+
class AuctionProcessRecord:
|
|
11
|
+
index: int
|
|
12
|
+
auction_time: time
|
|
13
|
+
minute_of_day_raw: int
|
|
14
|
+
second_raw: int
|
|
15
|
+
price: float
|
|
16
|
+
price_milli: int
|
|
17
|
+
matched_volume: int
|
|
18
|
+
unmatched_signed_raw: int
|
|
19
|
+
unmatched_volume: int
|
|
20
|
+
unmatched_direction: int
|
|
21
|
+
reserved_zero_0e: int
|
|
22
|
+
record_hex: str = ""
|
|
23
|
+
|
|
24
|
+
@property
|
|
25
|
+
def time_seconds(self) -> int:
|
|
26
|
+
return self.minute_of_day_raw * 60 + self.second_raw
|
|
27
|
+
|
|
28
|
+
@property
|
|
29
|
+
def matched_amount_estimated(self) -> float:
|
|
30
|
+
return self.price * self.matched_volume * 100.0
|
|
31
|
+
|
|
32
|
+
@property
|
|
33
|
+
def unmatched_amount_estimated(self) -> float:
|
|
34
|
+
return self.price * self.unmatched_volume * 100.0
|
|
35
|
+
|
|
36
|
+
@property
|
|
37
|
+
def unmatched_direction_raw(self) -> int:
|
|
38
|
+
return self.unmatched_direction
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
@dataclass(frozen=True, slots=True)
|
|
42
|
+
class AuctionProcessSeries:
|
|
43
|
+
exchange: str
|
|
44
|
+
market_id: int
|
|
45
|
+
code: str
|
|
46
|
+
mode_or_selector_raw: int
|
|
47
|
+
start: int
|
|
48
|
+
request_count: int
|
|
49
|
+
records: tuple[AuctionProcessRecord, ...]
|
|
50
|
+
raw_payload: bytes = b""
|
|
51
|
+
|
|
52
|
+
@property
|
|
53
|
+
def full_code(self) -> str:
|
|
54
|
+
return f"{self.exchange}{self.code}"
|
|
55
|
+
|
|
56
|
+
@property
|
|
57
|
+
def count(self) -> int:
|
|
58
|
+
return len(self.records)
|