dextrades


Namedextrades JSON
Version 0.1.12 PyPI version JSON
download
home_pageNone
SummaryHigh-performance DEX swap streaming and analysis (Rust/PyO3)
upload_time2025-10-08 19:10:34
maintainerNone
docs_urlNone
authorDextrades contributors
requires_python>=3.12
licenseNone
keywords ethereum dex uniswap streaming polars arrow pyarrow rust pyo3
VCS
bugtrack_url
requirements No requirements were recorded.
Travis-CI No Travis.
coveralls test coverage No coveralls.
            <h1>
<p align="center">
  <br>DexTrades πŸ¦„ 
</p >
</h1>

<p align="center">
A Python library for streaming DEX trades from RPC nodes.
</p>

<p align="center">
  <a href="https://pypi.org/project/dextrades">
    <img src="https://img.shields.io/pypi/v/dextrades.svg?label=pypi&logo=PyPI&logoColor=white" alt="PyPI">
  </a>
  <a href="https://opensource.org/licenses/MIT">
    <img src="https://img.shields.io/badge/License-MIT-yellow.svg" alt="License: MIT">
  </a>
</p>

## ✨ Features

* **Direct On-Chain Data**: Pulls event logs directly from a given RPC URL, requiring no indexers or third-party APIs. It currently decodes swaps from Uniswap V2 and V3.

* **Data Enrichment Pipeline**: The library can enrich raw log data with:
    * Token metadata (symbols, decimals) for readable amounts.
    * Block timestamps for each swap.
    * USD values calculated using Chainlink ETH/USD price feeds at the swap's block height.

* **Rust Core**: Built with a Rust backend (`PyO3`, `alloy`) for processing. It implements RPC provider racing, a circuit breaker, and automatic retries for connection resilience.

* **Friendly Python API**: Provides an `async` generator to stream trades. Enrichments are controlled via boolean flags. Supports streaming individual swaps or Apache Arrow batches.

##  πŸ“¦ Installation


Using `uv` (recommended):
```bash
uv add dextrades
````

Or with `pip`:

```bash
pip install dextrades
```

## πŸ’» Usage

The `Client` manages connections to one or more RPC endpoints. The `stream_swaps` method returns an async iterator of swap events.

```python
import asyncio
import dextrades

urls = [
    "https://eth-pokt.nodies.app",
    "https://ethereum.publicnode.com",
]
with dextrades.Client(urls) as client:
    # Stream a small block range; normalized token amounts included
    async for swap in client.stream_swaps(
        ["uniswap_v2", "uniswap_v3"],
        17000003, 17000003,
        batch_size=1,
        enrich_timestamps=True,
        enrich_usd=True,
    ):
        print(
            swap.get("dex_protocol"),
            swap.get("token_sold_symbol"), swap.get("token_sold_amount"),
            "β†’",
            swap.get("token_bought_symbol"), swap.get("token_bought_amount"),
            "USD:", swap.get("value_usd"),
        )
```
### Example Output

```
time                 dex           bought           sold              value_usd  trader  hash  
-----------------------------------------------------------------------------------------------------------------------------
2023-04-08 01:58:47  Uniswap V2    0.0529  WETH     98.9990  USDC        $99.00  0x5eA7  0x37f7
2023-04-08 01:58:47  Uniswap V2    0.0398  XMON      0.0529  WETH        $98.63  0x5eA7  0x37f7
2023-04-08 01:58:47  Uniswap V2    0.0452  WETH      0.7000  QNT         $84.38  0x4a30  0x5428
2023-04-08 01:58:47  Uniswap V2    3.2402  WETH      2.9994  PAXG     $6,045.62  0xdBC2  0x8f46
```



## πŸ“Š Available Fields

| Enricher | Fields Added | Description |
|----------|--------------|-------------|
| **Core** | `block_number`, `tx_hash`, `log_index`, `dex_protocol`, `pool_address` | Always present |
| **transaction** | `tx_from`, `tx_to`, `gas_used` | Transaction context |
| **timestamp** | `block_timestamp` | Block mining time |
| **token_metadata** | `token0_address`, `token1_address`, `token0_symbol`, `token1_symbol`, `token0_decimals`, `token1_decimals` | Token information |
| **swap** | `token_bought_address`, `token_sold_address`, `token_bought_symbol`, `token_sold_symbol`, `token_bought_amount`, `token_sold_amount`, `token_bought_amount_raw`, `token_sold_amount_raw` | Trade direction & amounts |
| **price_usd** | `value_usd`, `value_usd_method`, `chainlink_updated_at` | USD valuation (stablecoins + Chainlink ETH/USD) |


### Network overrides (generic per-chain pricing)

Provide network-specific overrides at client initialization to make USD pricing and warmup work on non-mainnet chains.

```python
overrides = {
    # Wrapped native token address (e.g., WETH, wCAMP)
    "native_wrapped": "0x4200000000000000000000000000000000000006",
    # Chainlink-style native/USD aggregator (optional)
    # "native_usd_aggregator": "0x...",
    # Stablecoin addresses to treat as USD stables on this network
    "stable_addresses": [
        # "0x...", "0x..."
    ],
    # Optional warmup tokens that exist on the current network (avoid noisy warmup logs)
    "warmup_tokens": []
}

with dextrades.Client(["<rpc-url>"], network_overrides=overrides) as client:
    async for swap in client.stream_swaps(["uniswap_v2", "uniswap_v3"], 100, 100, enrich_usd=True):
        ...
```

If no per-network aggregator is provided, USD pricing falls back to:
- Stablecoin passthrough (by address or common stable symbols)
- Native/USD via Chainlink only on Ethereum mainnet (default mainnet aggregator)

### Router filter (optional)

Filter to SmartRouter transactions only:

```python
async for swap in client.stream_swaps(["uniswap_v2","uniswap_v3"], 100, 100, routers=["0xRouter..."]):
    ...

# Also available for individual streaming:
client.stream_individual_swaps(["uniswap_v2","uniswap_v3"], 100, 100, routers=["0xRouter..."])
```



## πŸ—ΊοΈ Roadmap

- [x] Uniswap V2
- [x] Uniswap V3
- [x]  and deduplication
- [x] Enrichments: 
  - [x] token metadata
  - [x] trade direction
  - [x] timestamps
  - [x] USD values via Chainlink
  - [x] USD values via stablecoin passthrough 
- [x] RPC provider
  - [x] racing
  - [x] retries
  - [x] circuit breakers
  - [x] sharded `getLogs`
- [x] Python API
- [x] CLI
- [x] example and demo
- [x] benchmarks
- [ ] additional enrichments:
  - [ ] trader balance
  - [ ] Uniswap V3 Quoter fallback for non-WETH/stable tokens
- [ ] Chainlink Feed Registry (USD feeds) and multi-chain aggregator addresses
- [ ] CLI UX polish (enrichment flags, simple table mode)
- [ ] Light metrics: stage counters and provider health snapshot
- [ ] Additional DEX protocols
- [ ] Optional persistent caches and Parquet/Polars export helpers


            

Raw data

            {
    "_id": null,
    "home_page": null,
    "name": "dextrades",
    "maintainer": null,
    "docs_url": null,
    "requires_python": ">=3.12",
    "maintainer_email": null,
    "keywords": "ethereum, dex, uniswap, streaming, polars, arrow, pyarrow, rust, pyo3",
    "author": "Dextrades contributors",
    "author_email": null,
    "download_url": "https://files.pythonhosted.org/packages/5c/7c/0802faad671db7de4796463ab11478e0b764efaee7d48c8863e08d6c426b/dextrades-0.1.12.tar.gz",
    "platform": null,
    "description": "<h1>\n<p align=\"center\">\n  <br>DexTrades \ud83e\udd84 \n</p >\n</h1>\n\n<p align=\"center\">\nA Python library for streaming DEX trades from RPC nodes.\n</p>\n\n<p align=\"center\">\n  <a href=\"https://pypi.org/project/dextrades\">\n    <img src=\"https://img.shields.io/pypi/v/dextrades.svg?label=pypi&logo=PyPI&logoColor=white\" alt=\"PyPI\">\n  </a>\n  <a href=\"https://opensource.org/licenses/MIT\">\n    <img src=\"https://img.shields.io/badge/License-MIT-yellow.svg\" alt=\"License: MIT\">\n  </a>\n</p>\n\n## \u2728 Features\n\n* **Direct On-Chain Data**: Pulls event logs directly from a given RPC URL, requiring no indexers or third-party APIs. It currently decodes swaps from Uniswap V2 and V3.\n\n* **Data Enrichment Pipeline**: The library can enrich raw log data with:\n    * Token metadata (symbols, decimals) for readable amounts.\n    * Block timestamps for each swap.\n    * USD values calculated using Chainlink ETH/USD price feeds at the swap's block height.\n\n* **Rust Core**: Built with a Rust backend (`PyO3`, `alloy`) for processing. It implements RPC provider racing, a circuit breaker, and automatic retries for connection resilience.\n\n* **Friendly Python API**: Provides an `async` generator to stream trades. Enrichments are controlled via boolean flags. Supports streaming individual swaps or Apache Arrow batches.\n\n##  \ud83d\udce6 Installation\n\n\nUsing `uv` (recommended):\n```bash\nuv add dextrades\n````\n\nOr with `pip`:\n\n```bash\npip install dextrades\n```\n\n## \ud83d\udcbb Usage\n\nThe `Client` manages connections to one or more RPC endpoints. The `stream_swaps` method returns an async iterator of swap events.\n\n```python\nimport asyncio\nimport dextrades\n\nurls = [\n    \"https://eth-pokt.nodies.app\",\n    \"https://ethereum.publicnode.com\",\n]\nwith dextrades.Client(urls) as client:\n    # Stream a small block range; normalized token amounts included\n    async for swap in client.stream_swaps(\n        [\"uniswap_v2\", \"uniswap_v3\"],\n        17000003, 17000003,\n        batch_size=1,\n        enrich_timestamps=True,\n        enrich_usd=True,\n    ):\n        print(\n            swap.get(\"dex_protocol\"),\n            swap.get(\"token_sold_symbol\"), swap.get(\"token_sold_amount\"),\n            \"\u2192\",\n            swap.get(\"token_bought_symbol\"), swap.get(\"token_bought_amount\"),\n            \"USD:\", swap.get(\"value_usd\"),\n        )\n```\n### Example Output\n\n```\ntime                 dex           bought           sold              value_usd  trader  hash  \n-----------------------------------------------------------------------------------------------------------------------------\n2023-04-08 01:58:47  Uniswap V2    0.0529  WETH     98.9990  USDC        $99.00  0x5eA7  0x37f7\n2023-04-08 01:58:47  Uniswap V2    0.0398  XMON      0.0529  WETH        $98.63  0x5eA7  0x37f7\n2023-04-08 01:58:47  Uniswap V2    0.0452  WETH      0.7000  QNT         $84.38  0x4a30  0x5428\n2023-04-08 01:58:47  Uniswap V2    3.2402  WETH      2.9994  PAXG     $6,045.62  0xdBC2  0x8f46\n```\n\n\n\n## \ud83d\udcca Available Fields\n\n| Enricher | Fields Added | Description |\n|----------|--------------|-------------|\n| **Core** | `block_number`, `tx_hash`, `log_index`, `dex_protocol`, `pool_address` | Always present |\n| **transaction** | `tx_from`, `tx_to`, `gas_used` | Transaction context |\n| **timestamp** | `block_timestamp` | Block mining time |\n| **token_metadata** | `token0_address`, `token1_address`, `token0_symbol`, `token1_symbol`, `token0_decimals`, `token1_decimals` | Token information |\n| **swap** | `token_bought_address`, `token_sold_address`, `token_bought_symbol`, `token_sold_symbol`, `token_bought_amount`, `token_sold_amount`, `token_bought_amount_raw`, `token_sold_amount_raw` | Trade direction & amounts |\n| **price_usd** | `value_usd`, `value_usd_method`, `chainlink_updated_at` | USD valuation (stablecoins + Chainlink ETH/USD) |\n\n\n### Network overrides (generic per-chain pricing)\n\nProvide network-specific overrides at client initialization to make USD pricing and warmup work on non-mainnet chains.\n\n```python\noverrides = {\n    # Wrapped native token address (e.g., WETH, wCAMP)\n    \"native_wrapped\": \"0x4200000000000000000000000000000000000006\",\n    # Chainlink-style native/USD aggregator (optional)\n    # \"native_usd_aggregator\": \"0x...\",\n    # Stablecoin addresses to treat as USD stables on this network\n    \"stable_addresses\": [\n        # \"0x...\", \"0x...\"\n    ],\n    # Optional warmup tokens that exist on the current network (avoid noisy warmup logs)\n    \"warmup_tokens\": []\n}\n\nwith dextrades.Client([\"<rpc-url>\"], network_overrides=overrides) as client:\n    async for swap in client.stream_swaps([\"uniswap_v2\", \"uniswap_v3\"], 100, 100, enrich_usd=True):\n        ...\n```\n\nIf no per-network aggregator is provided, USD pricing falls back to:\n- Stablecoin passthrough (by address or common stable symbols)\n- Native/USD via Chainlink only on Ethereum mainnet (default mainnet aggregator)\n\n### Router filter (optional)\n\nFilter to SmartRouter transactions only:\n\n```python\nasync for swap in client.stream_swaps([\"uniswap_v2\",\"uniswap_v3\"], 100, 100, routers=[\"0xRouter...\"]):\n    ...\n\n# Also available for individual streaming:\nclient.stream_individual_swaps([\"uniswap_v2\",\"uniswap_v3\"], 100, 100, routers=[\"0xRouter...\"])\n```\n\n\n\n## \ud83d\uddfa\ufe0f Roadmap\n\n- [x] Uniswap V2\n- [x] Uniswap V3\n- [x]  and deduplication\n- [x] Enrichments: \n  - [x] token metadata\n  - [x] trade direction\n  - [x] timestamps\n  - [x] USD values via Chainlink\n  - [x] USD values via stablecoin passthrough \n- [x] RPC provider\n  - [x] racing\n  - [x] retries\n  - [x] circuit breakers\n  - [x] sharded `getLogs`\n- [x] Python API\n- [x] CLI\n- [x] example and demo\n- [x] benchmarks\n- [ ] additional enrichments:\n  - [ ] trader balance\n  - [ ] Uniswap V3 Quoter fallback for non-WETH/stable tokens\n- [ ] Chainlink Feed Registry (USD feeds) and multi-chain aggregator addresses\n- [ ] CLI UX polish (enrichment flags, simple table mode)\n- [ ] Light metrics: stage counters and provider health snapshot\n- [ ] Additional DEX protocols\n- [ ] Optional persistent caches and Parquet/Polars export helpers\n\n",
    "bugtrack_url": null,
    "license": null,
    "summary": "High-performance DEX swap streaming and analysis (Rust/PyO3)",
    "version": "0.1.12",
    "project_urls": {
        "Documentation": "https://github.com/elyase/dextrades#readme",
        "Homepage": "https://github.com/elyase/dextrades",
        "Repository": "https://github.com/elyase/dextrades"
    },
    "split_keywords": [
        "ethereum",
        " dex",
        " uniswap",
        " streaming",
        " polars",
        " arrow",
        " pyarrow",
        " rust",
        " pyo3"
    ],
    "urls": [
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "650d09880076289b2c9f1bb790843dd60f8e19e5bc38212f4e8a488234c4cbc6",
                "md5": "7ac0313eb9fe0441d39732f7bb9a272d",
                "sha256": "cf83e181a9f76aaedf89c2e12d0bc40a3b87fa5bd1f045aedfd55ae2d1a54b05"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12-cp312-cp312-macosx_10_12_x86_64.whl",
            "has_sig": false,
            "md5_digest": "7ac0313eb9fe0441d39732f7bb9a272d",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": ">=3.12",
            "size": 3551729,
            "upload_time": "2025-10-08T19:10:17",
            "upload_time_iso_8601": "2025-10-08T19:10:17.631598Z",
            "url": "https://files.pythonhosted.org/packages/65/0d/09880076289b2c9f1bb790843dd60f8e19e5bc38212f4e8a488234c4cbc6/dextrades-0.1.12-cp312-cp312-macosx_10_12_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "a6ea344d34b9ffa073a1feadb87b1b7666d664bed53c92fc6254ec3543153232",
                "md5": "efa3972d4d536f78805bccafe58b95ea",
                "sha256": "3a14f3c86bafe30fb032ce79e7b46472faa70b69dac6de28f6f0e31a9aec30e1"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12-cp312-cp312-macosx_11_0_arm64.whl",
            "has_sig": false,
            "md5_digest": "efa3972d4d536f78805bccafe58b95ea",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": ">=3.12",
            "size": 3413949,
            "upload_time": "2025-10-08T19:10:19",
            "upload_time_iso_8601": "2025-10-08T19:10:19.174885Z",
            "url": "https://files.pythonhosted.org/packages/a6/ea/344d34b9ffa073a1feadb87b1b7666d664bed53c92fc6254ec3543153232/dextrades-0.1.12-cp312-cp312-macosx_11_0_arm64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "fd2f5355e56324cfce41f90f04517556bdd1ee24fc0dd037efb3524e0b4f847e",
                "md5": "0cceda807e6fbded05c6beb513153928",
                "sha256": "c739cb01b83f1fb674746416a5942bff4d9ba98386bc805a10c55efcf16c3da7"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl",
            "has_sig": false,
            "md5_digest": "0cceda807e6fbded05c6beb513153928",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": ">=3.12",
            "size": 3822548,
            "upload_time": "2025-10-08T19:10:24",
            "upload_time_iso_8601": "2025-10-08T19:10:24.772472Z",
            "url": "https://files.pythonhosted.org/packages/fd/2f/5355e56324cfce41f90f04517556bdd1ee24fc0dd037efb3524e0b4f847e/dextrades-0.1.12-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "23154edc5d389cc60a9ba0e5b4a6fde7ca6cc47c14c6d157577a935bd76b72c8",
                "md5": "0cebd521dcb447db4afed219073dc3dc",
                "sha256": "0b07b4d6f56964a40ecb00701473052cb37a30bd43460d44856cd2191c41ab8a"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12-cp312-cp312-manylinux_2_34_x86_64.whl",
            "has_sig": false,
            "md5_digest": "0cebd521dcb447db4afed219073dc3dc",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": ">=3.12",
            "size": 6051849,
            "upload_time": "2025-10-08T19:10:26",
            "upload_time_iso_8601": "2025-10-08T19:10:26.198695Z",
            "url": "https://files.pythonhosted.org/packages/23/15/4edc5d389cc60a9ba0e5b4a6fde7ca6cc47c14c6d157577a935bd76b72c8/dextrades-0.1.12-cp312-cp312-manylinux_2_34_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "587d7bc164642f0b96a6b29d1ef52b5e0d69af74cb1aa5a13a84daf914e9bda1",
                "md5": "41a4ef17f12e8bc44c13f495807a93dd",
                "sha256": "ac8b5712e895fdbe2fe1838647a4ace505b05795b065511557a7712fa42defb4"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12-cp312-cp312-win_amd64.whl",
            "has_sig": false,
            "md5_digest": "41a4ef17f12e8bc44c13f495807a93dd",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": ">=3.12",
            "size": 3190830,
            "upload_time": "2025-10-08T19:10:27",
            "upload_time_iso_8601": "2025-10-08T19:10:27.778664Z",
            "url": "https://files.pythonhosted.org/packages/58/7d/7bc164642f0b96a6b29d1ef52b5e0d69af74cb1aa5a13a84daf914e9bda1/dextrades-0.1.12-cp312-cp312-win_amd64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "3e712fa891a2df23d449693bd0d3b812da78e1407aece54b79a5584699cf5bd1",
                "md5": "24dc12d200f371601af38c9bca91b3ec",
                "sha256": "af6e69a86f865e96437de7a2e89498ac752d7d8e82103d533110de5517723b15"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12-cp313-cp313-macosx_10_12_x86_64.whl",
            "has_sig": false,
            "md5_digest": "24dc12d200f371601af38c9bca91b3ec",
            "packagetype": "bdist_wheel",
            "python_version": "cp313",
            "requires_python": ">=3.12",
            "size": 3552341,
            "upload_time": "2025-10-08T19:10:29",
            "upload_time_iso_8601": "2025-10-08T19:10:29.584272Z",
            "url": "https://files.pythonhosted.org/packages/3e/71/2fa891a2df23d449693bd0d3b812da78e1407aece54b79a5584699cf5bd1/dextrades-0.1.12-cp313-cp313-macosx_10_12_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "7e24c9ad740e44e1d75e7c9031bd86e7e5397b3a18eee8c916261068c6d403b9",
                "md5": "004843c558f11f27beb9f01bf358f5f7",
                "sha256": "d0097c84952cd5917a3f4caa2accc13e39074c5d3ac8d73debd5ddcb402373dd"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12-cp313-cp313-macosx_11_0_arm64.whl",
            "has_sig": false,
            "md5_digest": "004843c558f11f27beb9f01bf358f5f7",
            "packagetype": "bdist_wheel",
            "python_version": "cp313",
            "requires_python": ">=3.12",
            "size": 3414411,
            "upload_time": "2025-10-08T19:10:31",
            "upload_time_iso_8601": "2025-10-08T19:10:31.344876Z",
            "url": "https://files.pythonhosted.org/packages/7e/24/c9ad740e44e1d75e7c9031bd86e7e5397b3a18eee8c916261068c6d403b9/dextrades-0.1.12-cp313-cp313-macosx_11_0_arm64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "c7e5d7fa6b360f7df83f1e25e07a50eb35e83062bfaa255c295b2520ddcb9c7e",
                "md5": "0e004f572fd13a1a6b0c0c8caf6f6982",
                "sha256": "e279cf3a7c26a130298a498d5ef8e5c50fcb4ed136b5b8f7aa27cb504a6da4a8"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12-cp313-cp313-win_amd64.whl",
            "has_sig": false,
            "md5_digest": "0e004f572fd13a1a6b0c0c8caf6f6982",
            "packagetype": "bdist_wheel",
            "python_version": "cp313",
            "requires_python": ">=3.12",
            "size": 3190222,
            "upload_time": "2025-10-08T19:10:32",
            "upload_time_iso_8601": "2025-10-08T19:10:32.676947Z",
            "url": "https://files.pythonhosted.org/packages/c7/e5/d7fa6b360f7df83f1e25e07a50eb35e83062bfaa255c295b2520ddcb9c7e/dextrades-0.1.12-cp313-cp313-win_amd64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "5c7c0802faad671db7de4796463ab11478e0b764efaee7d48c8863e08d6c426b",
                "md5": "772c0bbb57010c227c5bd2e2b1d9bd5c",
                "sha256": "e62396e6491734f71859318c1444b4945177396183adbe9c36add8a378c448f1"
            },
            "downloads": -1,
            "filename": "dextrades-0.1.12.tar.gz",
            "has_sig": false,
            "md5_digest": "772c0bbb57010c227c5bd2e2b1d9bd5c",
            "packagetype": "sdist",
            "python_version": "source",
            "requires_python": ">=3.12",
            "size": 113717,
            "upload_time": "2025-10-08T19:10:34",
            "upload_time_iso_8601": "2025-10-08T19:10:34.263125Z",
            "url": "https://files.pythonhosted.org/packages/5c/7c/0802faad671db7de4796463ab11478e0b764efaee7d48c8863e08d6c426b/dextrades-0.1.12.tar.gz",
            "yanked": false,
            "yanked_reason": null
        }
    ],
    "upload_time": "2025-10-08 19:10:34",
    "github": true,
    "gitlab": false,
    "bitbucket": false,
    "codeberg": false,
    "github_user": "elyase",
    "github_project": "dextrades#readme",
    "travis_ci": false,
    "coveralls": false,
    "github_actions": true,
    "lcname": "dextrades"
}
        
Elapsed time: 2.24942s