helius-python 0.1.0__tar.gz → 0.2.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (33) hide show
  1. helius_python-0.2.0/.github/ISSUE_TEMPLATE/bug_report.yml +83 -0
  2. helius_python-0.2.0/.github/ISSUE_TEMPLATE/config.yml +9 -0
  3. helius_python-0.2.0/.github/ISSUE_TEMPLATE/feature_request.yml +41 -0
  4. {helius_python-0.1.0 → helius_python-0.2.0}/AGENTS.md +9 -9
  5. {helius_python-0.1.0 → helius_python-0.2.0}/CONTRIBUTING.md +2 -1
  6. helius_python-0.2.0/PKG-INFO +317 -0
  7. helius_python-0.2.0/README.md +297 -0
  8. {helius_python-0.1.0 → helius_python-0.2.0}/examples/block_explorer.py +9 -6
  9. {helius_python-0.1.0 → helius_python-0.2.0}/examples/devnet_airdrop.py +2 -2
  10. {helius_python-0.1.0 → helius_python-0.2.0}/examples/network_status.py +2 -2
  11. {helius_python-0.1.0 → helius_python-0.2.0}/examples/priority_fees.py +2 -2
  12. {helius_python-0.1.0 → helius_python-0.2.0}/examples/stake_overview.py +22 -14
  13. {helius_python-0.1.0 → helius_python-0.2.0}/examples/token_inspector.py +2 -2
  14. {helius_python-0.1.0 → helius_python-0.2.0}/examples/transaction_inspector.py +5 -4
  15. {helius_python-0.1.0 → helius_python-0.2.0}/examples/wallet_tracker.py +9 -6
  16. {helius_python-0.1.0 → helius_python-0.2.0}/pyproject.toml +1 -1
  17. {helius_python-0.1.0 → helius_python-0.2.0}/src/helius/models.py +10 -0
  18. helius_python-0.1.0/src/helius/client.py → helius_python-0.2.0/src/helius/solana_rpc.py +121 -42
  19. {helius_python-0.1.0 → helius_python-0.2.0}/tests/unit/test_helius_client.py +253 -116
  20. {helius_python-0.1.0 → helius_python-0.2.0}/tests/unit/test_models.py +17 -0
  21. {helius_python-0.1.0 → helius_python-0.2.0}/tests/unit/test_rpc_request.py +4 -2
  22. helius_python-0.1.0/PKG-INFO +0 -363
  23. helius_python-0.1.0/README.md +0 -343
  24. {helius_python-0.1.0 → helius_python-0.2.0}/.editorconfig +0 -0
  25. {helius_python-0.1.0 → helius_python-0.2.0}/.github/workflows/python-package.yml +0 -0
  26. {helius_python-0.1.0 → helius_python-0.2.0}/.github/workflows/python-publish.yml +0 -0
  27. {helius_python-0.1.0 → helius_python-0.2.0}/.gitignore +0 -0
  28. {helius_python-0.1.0 → helius_python-0.2.0}/CLAUDE.md +0 -0
  29. {helius_python-0.1.0 → helius_python-0.2.0}/LICENSE +0 -0
  30. {helius_python-0.1.0 → helius_python-0.2.0}/requirements.txt +0 -0
  31. {helius_python-0.1.0 → helius_python-0.2.0}/src/helius/__init__.py +0 -0
  32. {helius_python-0.1.0 → helius_python-0.2.0}/tests/fixtures/account.json +0 -0
  33. {helius_python-0.1.0 → helius_python-0.2.0}/tests/fixtures/supply.json +0 -0
@@ -0,0 +1,83 @@
1
+ name: Bug report
2
+ description: Report a bug in helius-python
3
+ title: "[Bug]: "
4
+ labels: ["bug"]
5
+ body:
6
+ - type: markdown
7
+ attributes:
8
+ value: |
9
+ Thanks for taking the time to file a bug report! Please fill out the
10
+ sections below so we can reproduce and fix the issue quickly.
11
+ - type: textarea
12
+ id: summary
13
+ attributes:
14
+ label: Summary
15
+ description: A clear and concise description of the bug.
16
+ validations:
17
+ required: true
18
+ - type: textarea
19
+ id: reproduction
20
+ attributes:
21
+ label: Reproduction
22
+ description: |
23
+ Minimal, runnable code snippet that reproduces the bug. Please redact
24
+ your API key.
25
+ render: python
26
+ placeholder: |
27
+ from helius.solana_rpc import HeliusClient
28
+
29
+ with HeliusClient(api_key="...") as c:
30
+ c.get_balance(public_key="...")
31
+ validations:
32
+ required: true
33
+ - type: textarea
34
+ id: expected
35
+ attributes:
36
+ label: Expected behavior
37
+ validations:
38
+ required: true
39
+ - type: textarea
40
+ id: actual
41
+ attributes:
42
+ label: Actual behavior
43
+ description: Include the full traceback if any.
44
+ render: shell
45
+ validations:
46
+ required: true
47
+ - type: input
48
+ id: helius_version
49
+ attributes:
50
+ label: helius-python version
51
+ placeholder: "0.1.0"
52
+ validations:
53
+ required: true
54
+ - type: input
55
+ id: python_version
56
+ attributes:
57
+ label: Python version
58
+ placeholder: "3.12.3"
59
+ validations:
60
+ required: true
61
+ - type: input
62
+ id: os
63
+ attributes:
64
+ label: Operating system
65
+ placeholder: "macOS 14.5 / Ubuntu 24.04 / Windows 11"
66
+ validations:
67
+ required: true
68
+ - type: dropdown
69
+ id: network
70
+ attributes:
71
+ label: Helius network
72
+ options:
73
+ - Mainnet
74
+ - Devnet
75
+ - Testnet
76
+ - Other / not applicable
77
+ validations:
78
+ required: true
79
+ - type: textarea
80
+ id: additional_context
81
+ attributes:
82
+ label: Additional context
83
+ description: Anything else that might be relevant (logs, screenshots, related issues).
@@ -0,0 +1,9 @@
1
+ blank_issues_enabled: false
2
+ contact_links:
3
+ - name: Helius RPC documentation
4
+ url: https://www.helius.dev/docs/rpc
5
+ about: Questions about Helius RPC behavior, rate limits, or network errors
6
+ belong upstream — this library is a thin typed wrapper.
7
+ - name: Solana JSON-RPC documentation
8
+ url: https://solana.com/docs/rpc
9
+ about: Reference for the underlying Solana JSON-RPC API.
@@ -0,0 +1,41 @@
1
+ name: Feature request
2
+ description: Suggest a new RPC method, model, or improvement
3
+ title: "[Feature]: "
4
+ labels: ["enhancement"]
5
+ body:
6
+ - type: markdown
7
+ attributes:
8
+ value: |
9
+ Thanks for the suggestion! Please describe what you'd like to see
10
+ added or changed.
11
+ - type: textarea
12
+ id: problem
13
+ attributes:
14
+ label: Problem
15
+ description: What problem are you trying to solve? What's the use case?
16
+ validations:
17
+ required: true
18
+ - type: textarea
19
+ id: proposal
20
+ attributes:
21
+ label: Proposed solution
22
+ description: |
23
+ Describe the API or behavior you'd like. For new RPC methods, please
24
+ link the upstream Helius docs (both the guide and the API reference
25
+ pages).
26
+ placeholder: |
27
+ Add `HeliusClient.get_foo(...)` wrapping `getFoo`.
28
+ - Guide: https://www.helius.dev/docs/rpc/guides/getfoo
29
+ - API reference: https://www.helius.dev/docs/api-reference/rpc/http/getfoo
30
+ validations:
31
+ required: true
32
+ - type: textarea
33
+ id: alternatives
34
+ attributes:
35
+ label: Alternatives considered
36
+ description: Other approaches you considered and why you ruled them out.
37
+ - type: textarea
38
+ id: additional_context
39
+ attributes:
40
+ label: Additional context
41
+ description: Anything else (related issues, prior art in other libraries).
@@ -1,4 +1,4 @@
1
- When implementing a function for a RPC method in the HeliusClient class, read the docs for the specific RPC method. For example, for the get_supply function (getSupply RPC method) you should read https://www.helius.dev/docs/rpc/guides/getsupply and https://www.helius.dev/docs/api-reference/rpc/http/getsupply.
1
+ When implementing a function for a RPC method in the SolanaRpcClient class, read the docs for the specific RPC method. For example, for the get_supply function (getSupply RPC method) you should read https://www.helius.dev/docs/rpc/guides/getsupply and https://www.helius.dev/docs/api-reference/rpc/http/getsupply.
2
2
 
3
3
  # API Reference
4
4
 
@@ -6,7 +6,7 @@ The API reference is generated from **Google-style docstrings** on every public
6
6
 
7
7
  ## Where docstrings live
8
8
 
9
- - **Client methods** (`HeliusClient.get_*`, `is_*`, `request_*`, etc.) — every public method gets a docstring. Private methods (`_send`, dunders) do not need one.
9
+ - **Client methods** (`SolanaRpcClient.get_*`, `is_*`, `request_*`, etc.) — every public method gets a docstring. Private methods (`_send`, dunders) do not need one.
10
10
  - **Models** (`src/helius/models.py`) — every public model class gets a docstring describing what it represents. Individual fields don't need per-field docstrings if their names and types are self-explanatory; only document fields where the meaning, units, or nullability isn't obvious from the type alone.
11
11
  - **Builders / helpers** (`RpcRequest`) — class docstring describing purpose, plus one-line docstrings on each public method.
12
12
 
@@ -123,7 +123,7 @@ tests/
123
123
  unit/
124
124
  test_rpc_request.py # RpcRequest builder
125
125
  test_models.py # pydantic model validation against fixtures
126
- test_client.py # one test (or small group) per client method
126
+ test_solana_rpc.py # one test (or small group) per client method
127
127
  ```
128
128
 
129
129
  ## Three Layers
@@ -154,7 +154,7 @@ One fixture per model is enough. The goal is to catch schema mismatches (missing
154
154
 
155
155
  ### 3. Client methods — `respx`-mocked tests
156
156
 
157
- For each method on `HeliusClient`, write at least one test that asserts **both** sides of the wire:
157
+ For each method on `SolanaRpcClient`, write at least one test that asserts **both** sides of the wire:
158
158
 
159
159
  - **Outgoing request:** the JSON body sent to Helius matches the JSON-RPC payload you expect — correct `method`, correct positional `params`, correct config object with snake → camel mapping, and optional arguments omitted when `None`.
160
160
  - **Return value:** the method correctly parses a canned response into the documented return shape (model, tuple, primitive, etc.).
@@ -169,7 +169,7 @@ Skeleton:
169
169
  import json
170
170
  import httpx
171
171
  import respx
172
- from helius.client import HeliusClient
172
+ from helius.solana_rpc import SolanaRpcClient
173
173
 
174
174
  @respx.mock
175
175
  def test_get_balance():
@@ -183,7 +183,7 @@ def test_get_balance():
183
183
  },
184
184
  )
185
185
  )
186
- with HeliusClient(api_key="test") as c:
186
+ with SolanaRpcClient(api_key="test") as c:
187
187
  assert c.get_balance("So11...112", commitment="finalized") == 42
188
188
 
189
189
  sent = route.calls.last.request
@@ -197,9 +197,9 @@ For methods with branching logic (e.g. `get_block_production`, `get_token_accoun
197
197
 
198
198
  ## Conventions
199
199
 
200
- - Construct `HeliusClient` in tests with an explicit `api_key="test"` (or similar). Never rely on a real `.env` file.
201
- - Use the context-manager form (`with HeliusClient(...) as c:`) in tests so the `httpx.Client` is closed cleanly.
202
- - Group tests in `tests/unit/test_client.py` by method, but a single file is fine until it grows unwieldy.
200
+ - Construct `SolanaRpcClient` in tests with an explicit `api_key="test"` (or similar). Never rely on a real `.env` file.
201
+ - Use the context-manager form (`with SolanaRpcClient(...) as c:`) in tests so the `httpx.Client` is closed cleanly.
202
+ - Group tests in `tests/unit/test_solana_rpc.py` by method, but a single file is fine until it grows unwieldy.
203
203
  - Test names should describe the behavior, not the implementation: `test_get_balance_includes_commitment_in_config`, not `test_get_balance_calls_set`.
204
204
  - When adding a new client method, the PR must include: (a) a `respx` test asserting the request payload, and (b) a fixture-based model test if the method introduces or uses a model. This is enforced in `CONTRIBUTING.md`.
205
205
 
@@ -43,6 +43,7 @@ easiest to most involved:
43
43
  fleshed out.
44
44
  - **Improve docs and examples.** Clearer docstrings, better README snippets,
45
45
  more realistic examples.
46
+ - **Create an example or refine an existing one.** Examples make it easier for developers to get started.
46
47
 
47
48
  If you're not sure where to start, browse the
48
49
  [open issues](https://github.com/markosnarinian/helius-python/issues).
@@ -65,7 +66,7 @@ prior discussion; just send them.
65
66
  ## Codebase Conventions
66
67
 
67
68
  Please match the existing style of the codebase. Skim
68
- [`src/helius/client.py`](src/helius/client.py) and
69
+ [`src/helius/solana_rpc.py`](src/helius/solana_rpc.py) and
69
70
  [`src/helius/models.py`](src/helius/models.py) before writing new code. In
70
71
  particular:
71
72
 
@@ -0,0 +1,317 @@
1
+ Metadata-Version: 2.4
2
+ Name: helius-python
3
+ Version: 0.2.0
4
+ Summary: Typed Python client for the Helius API
5
+ Project-URL: Homepage, https://github.com/markosnarinian/helius-python
6
+ Project-URL: Issues, https://github.com/markosnarinian/helius-python/issues
7
+ Author-email: Markos Narinian <manarinian@gmail.com>
8
+ License-Expression: MIT
9
+ License-File: LICENSE
10
+ Classifier: Operating System :: OS Independent
11
+ Classifier: Programming Language :: Python :: 3
12
+ Requires-Python: >=3.10
13
+ Requires-Dist: httpx
14
+ Requires-Dist: pydantic
15
+ Requires-Dist: python-dotenv
16
+ Provides-Extra: dev
17
+ Requires-Dist: pytest; extra == 'dev'
18
+ Requires-Dist: respx; extra == 'dev'
19
+ Description-Content-Type: text/markdown
20
+
21
+ # helius-python
22
+
23
+ <p align="center">
24
+ <img width="562" height="118" alt="Helius-Horizontal-Logo" src="https://github.com/user-attachments/assets/d87ffd10-b168-4830-bbad-d2fef67368a5" /><svg width="562" height="118" viewBox="0 0 562 118" fill="none" xmlns="http://www.w3.org/2000/svg">
25
+ <g clip-path="url(#clip0_7532_34078)">
26
+ <path d="M74.6261 24.7253C69.9876 22.7665 64.8892 21.6871 59.531 21.6871C54.1727 21.6871 49.0743 22.7665 44.4358 24.7253L58.3013 0.709587C58.8412 -0.229856 60.2007 -0.229856 60.7406 0.709587L74.6161 24.7253H74.6261Z" fill="url(#paint0_linear_7532_34078)"/>
27
+ <path d="M40.7468 26.5242C31.6098 31.5812 24.742 40.2161 22.0128 50.54L11.7061 24.2856C11.3063 23.2762 12.156 22.2168 13.2257 22.3767L40.7468 26.5242Z" fill="url(#paint1_linear_7532_34078)"/>
28
+ <path d="M28.9906 84.4099L0.999611 75.7751C-0.0400563 75.4552 -0.33996 74.126 0.449787 73.3965L21.2431 54.1079C20.9032 56.1767 20.7233 58.3054 20.7233 60.4741C20.7233 69.5088 23.8123 77.8238 28.9906 84.4099Z" fill="url(#paint2_linear_7532_34078)"/>
29
+ <path d="M58.951 99.2611L34.4089 115.981C33.5091 116.591 32.2895 116.011 32.2096 114.922L30.0203 85.6492C37.018 93.8443 47.3747 99.0812 58.951 99.2511V99.2611Z" fill="url(#paint3_linear_7532_34078)"/>
30
+ <path d="M88.9513 85.7692L86.772 114.892C86.692 115.971 85.4724 116.561 84.5727 115.951L60.0806 99.2612C71.6269 99.1013 81.9536 93.9043 88.9513 85.7692Z" fill="url(#paint4_linear_7532_34078)"/>
31
+ <path d="M118.042 75.6851L90.1711 84.28C95.2895 77.7139 98.3385 69.4488 98.3385 60.4741C98.3385 58.2754 98.1486 56.1167 97.7987 54.0179L118.582 73.2965C119.382 74.0361 119.072 75.3653 118.042 75.6751V75.6851Z" fill="url(#paint5_linear_7532_34078)"/>
32
+ <path d="M107.355 24.3356L97.0588 50.5801C94.3396 40.2662 87.4918 31.6413 78.3848 26.5643L105.836 22.4268C106.906 22.2668 107.755 23.3262 107.355 24.3356Z" fill="url(#paint6_linear_7532_34078)"/>
33
+ <path d="M59.5307 107.636C53.8026 107.636 49.1641 112.273 49.1641 118H69.9074C69.9074 112.273 65.2689 107.636 59.5407 107.636H59.5307Z" fill="url(#paint7_linear_7532_34078)"/>
34
+ <path d="M97.4388 90.6563C93.8699 95.1336 94.5997 101.66 99.0782 105.228L112.004 89.0172C107.526 85.4494 100.998 86.1789 97.4288 90.6563H97.4388Z" fill="url(#paint8_linear_7532_34078)"/>
35
+ <path d="M105.936 50.57C107.206 56.1567 112.774 59.6446 118.352 58.3653L113.733 38.1473C108.145 39.4166 104.656 44.9833 105.936 50.56V50.57Z" fill="url(#paint9_linear_7532_34078)"/>
36
+ <path d="M80.4942 18.8588C85.6525 21.3473 91.8505 19.1786 94.3397 14.0116L75.6557 5.01697C73.1665 10.1739 75.3358 16.3702 80.5042 18.8588H80.4942Z" fill="url(#paint10_linear_7532_34078)"/>
37
+ <path d="M38.0978 18.8588C43.2561 16.3702 45.4254 10.1739 42.9362 5.01697L24.2522 14.0116C26.7414 19.1686 32.9394 21.3373 38.0978 18.8488V18.8588Z" fill="url(#paint11_linear_7532_34078)"/>
38
+ <path d="M13.3958 50.57C14.6654 44.9833 11.1765 39.4266 5.58826 38.1573L0.979736 58.3754C6.56795 59.6446 12.1262 56.1567 13.3958 50.57Z" fill="url(#paint12_linear_7532_34078)"/>
39
+ <path d="M8.49731 89.0172L21.4332 105.228C25.9117 101.66 26.6415 95.1336 23.0726 90.6563C19.5038 86.1789 12.9759 85.4494 8.49731 89.0172Z" fill="url(#paint13_linear_7532_34078)"/>
40
+ <path d="M177.773 30.1321V59.8145H212.612V31.8511H228.487V98.4116H212.612V73.9661H177.773V98.4116H161.898V34.4195L177.773 30.1321Z" fill="#E84125"/>
41
+ <path d="M257.227 84.25H305.792L301.503 98.4016H241.363V31.8411H305.802L301.513 45.9927H257.237V58.0855H298.504V72.2371H257.237V84.25H257.227Z" fill="#E84125"/>
42
+ <path d="M331.274 31.8411V84.25H378.119L373.83 98.4016H315.399V31.8411H331.274Z" fill="#E84125"/>
43
+ <path d="M400.861 31.8411V98.4016H384.987V31.8411H400.861Z" fill="#E84125"/>
44
+ <path d="M467.44 31.8411H483.315V71.9872C483.315 91.3757 467.44 99.8607 446.937 99.8607C426.433 99.8607 411.668 90.7661 411.668 71.9872V34.4195L427.543 30.1321V71.9872C427.543 81.7614 434.061 85.4593 447.706 85.4593C461.352 85.4593 467.44 81.5116 467.44 71.9872V31.8411Z" fill="#E84125"/>
45
+ <path d="M491.382 52.0891C491.382 41.8851 499.45 31.8411 515.235 31.8411H560.54L556.252 45.9927H515.405C510.516 45.9927 508.107 49.0808 508.107 52.0791C508.107 55.0773 510.596 58.0855 515.405 58.0855H538.397C553.922 58.0855 561.99 68.1195 561.99 78.3335C561.99 88.5474 554.352 98.4016 538.397 98.4016H491.382L495.671 84.25H538.227C543.036 84.25 545.525 81.4217 545.525 78.3335C545.525 75.2453 543.126 72.1571 538.227 72.1571H515.235C499.19 72.1571 491.382 62.1231 491.382 52.0891Z" fill="#E84125"/>
46
+ </g>
47
+ <defs>
48
+ <linearGradient id="paint0_linear_7532_34078" x1="41.8666" y1="12.3627" x2="74.6261" y2="12.3627" gradientUnits="userSpaceOnUse">
49
+ <stop stop-color="#E35930"/>
50
+ <stop offset="1" stop-color="#E84125"/>
51
+ </linearGradient>
52
+ <linearGradient id="paint1_linear_7532_34078" x1="9.61681" y1="36.4484" x2="40.7468" y2="36.4484" gradientUnits="userSpaceOnUse">
53
+ <stop stop-color="#E35930"/>
54
+ <stop offset="1" stop-color="#E84125"/>
55
+ </linearGradient>
56
+ <linearGradient id="paint2_linear_7532_34078" x1="-0.919775" y1="69.2589" x2="28.9906" y2="69.2589" gradientUnits="userSpaceOnUse">
57
+ <stop stop-color="#E35930"/>
58
+ <stop offset="1" stop-color="#E84125"/>
59
+ </linearGradient>
60
+ <linearGradient id="paint3_linear_7532_34078" x1="29.4704" y1="100.94" x2="58.951" y2="100.94" gradientUnits="userSpaceOnUse">
61
+ <stop stop-color="#E35930"/>
62
+ <stop offset="1" stop-color="#E84125"/>
63
+ </linearGradient>
64
+ <linearGradient id="paint4_linear_7532_34078" x1="59.0809" y1="100.98" x2="88.9513" y2="100.98" gradientUnits="userSpaceOnUse">
65
+ <stop stop-color="#E35930"/>
66
+ <stop offset="1" stop-color="#E84125"/>
67
+ </linearGradient>
68
+ <linearGradient id="paint5_linear_7532_34078" x1="88.3417" y1="69.149" x2="119.032" y2="69.149" gradientUnits="userSpaceOnUse">
69
+ <stop stop-color="#E35930"/>
70
+ <stop offset="1" stop-color="#E84125"/>
71
+ </linearGradient>
72
+ <linearGradient id="paint6_linear_7532_34078" x1="75.9256" y1="36.4884" x2="107.455" y2="36.4884" gradientUnits="userSpaceOnUse">
73
+ <stop stop-color="#E35930"/>
74
+ <stop offset="1" stop-color="#E84125"/>
75
+ </linearGradient>
76
+ <linearGradient id="paint7_linear_7532_34078" x1="64.1037" y1="108.682" x2="56.3294" y2="122.151" gradientUnits="userSpaceOnUse">
77
+ <stop stop-color="#E35930"/>
78
+ <stop offset="1" stop-color="#E84125"/>
79
+ </linearGradient>
80
+ <linearGradient id="paint8_linear_7532_34078" x1="101.127" y1="87.5512" x2="106.808" y2="102.028" gradientUnits="userSpaceOnUse">
81
+ <stop stop-color="#E35930"/>
82
+ <stop offset="1" stop-color="#E84125"/>
83
+ </linearGradient>
84
+ <linearGradient id="paint9_linear_7532_34078" x1="105.915" y1="45.8351" x2="120.779" y2="50.4203" gradientUnits="userSpaceOnUse">
85
+ <stop stop-color="#E35930"/>
86
+ <stop offset="1" stop-color="#E84125"/>
87
+ </linearGradient>
88
+ <linearGradient id="paint10_linear_7532_34078" x1="76.8142" y1="15.9367" x2="89.6635" y2="7.17242" gradientUnits="userSpaceOnUse">
89
+ <stop stop-color="#E35930"/>
90
+ <stop offset="1" stop-color="#E84125"/>
91
+ </linearGradient>
92
+ <linearGradient id="paint11_linear_7532_34078" x1="33.7238" y1="19.9762" x2="34.884" y2="4.46876" gradientUnits="userSpaceOnUse">
93
+ <stop stop-color="#E35930"/>
94
+ <stop offset="1" stop-color="#E84125"/>
95
+ </linearGradient>
96
+ <linearGradient id="paint12_linear_7532_34078" x1="11.6598" y1="54.776" x2="0.258708" y2="44.1971" gradientUnits="userSpaceOnUse">
97
+ <stop stop-color="#E35930"/>
98
+ <stop offset="1" stop-color="#E84125"/>
99
+ </linearGradient>
100
+ <linearGradient id="paint13_linear_7532_34078" x1="25.3906" y1="94.7132" x2="10.0098" y2="97.0344" gradientUnits="userSpaceOnUse">
101
+ <stop stop-color="#E35930"/>
102
+ <stop offset="1" stop-color="#E84125"/>
103
+ </linearGradient>
104
+ <clipPath id="clip0_7532_34078">
105
+ <rect width="562" height="118" fill="white"/>
106
+ </clipPath>
107
+ </defs>
108
+ </svg>
109
+ </p>
110
+
111
+ <p align="center">
112
+ <a href="https://pypi.org/project/helius-python/"><img src="https://img.shields.io/pypi/v/helius-python.svg" alt="PyPI version"></a>
113
+ <a href="https://pypi.org/project/helius-python/"><img src="https://img.shields.io/pypi/pyversions/helius-python.svg" alt="Python versions"></a>
114
+ <a href="https://github.com/markosnarinian/helius-python/blob/main/LICENSE"><img src="https://img.shields.io/github/license/markosnarinian/helius-python.svg" alt="License"></a>
115
+ <a href="https://github.com/markosnarinian/helius-python/actions/workflows/python-package.yml"><img src="https://github.com/markosnarinian/helius-python/actions/workflows/python-package.yml/badge.svg" alt="CI"></a>
116
+ <a href="https://pypistats.org/packages/helius-python"><img src="https://img.shields.io/pypi/dm/helius-python.svg" alt="Downloads"></a>
117
+ <a href="https://github.com/markosnarinian/helius-python/commits/main"><img src="https://img.shields.io/github/last-commit/markosnarinian/helius-python.svg" alt="Last commit"></a>
118
+ </p>
119
+
120
+ **A complete, typed Python client for [Helius](https://helius.dev) — the Solana developer platform.**
121
+
122
+ ## Coverage
123
+
124
+ The goal of this library is **support every function, method, endpoint,
125
+ and feature that Helius exposes.** If Helius ships it, this client
126
+ wraps it.
127
+
128
+ - ✅ **The full Solana JSON-RPC surface** proxied by Helius —
129
+ `getAccountInfo`, `getBalance`, `getBlock`, `getTransaction`,
130
+ `getProgramAccounts`, `getTokenAccountsByOwner`,
131
+ `getSignaturesForAddress`, and every other standard RPC method.
132
+ **(supported today)**
133
+ - 🚧 **All Helius-specific RPC extensions** — enhanced transactions, DAS
134
+ (Digital Asset Standard) methods, priority fee estimation, and the
135
+ rest of the Helius-only RPC namespace. **(in progress)**
136
+ - 🚧 **Every Helius REST endpoint** — Enhanced Transactions API,
137
+ Webhooks API, Mint API, token metadata, address lookups, and beyond.
138
+ **(in progress)**
139
+ - 🚧 **Platform features** — streaming, websockets, and any new
140
+ capability Helius adds to its API. **(in progress)**
141
+
142
+ > **Current status:** only the standard Solana JSON-RPC surface is
143
+ > implemented today. Support for Helius RPC extensions, REST endpoints,
144
+ > and platform features is actively being worked on.
145
+
146
+ ## Goals
147
+
148
+ 1. **Completeness** — 1:1 coverage of the entire Helius API surface.
149
+ 2. **Type safety** — fully typed responses.
150
+ 3. **Pythonic ergonomics** — `get_account_info(...)` instead of
151
+ `getAccountInfo(...)`, context managers.
152
+ 4. **Zero magic** — thin, predictable wrappers that map directly to the
153
+ documented Helius API.
154
+
155
+ ## Authentication
156
+
157
+ Pass your Helius API key explicitly:
158
+
159
+ ```python
160
+ from helius.solana_rpc import SolanaRpcClient
161
+
162
+ client = SolanaRpcClient(api_key="YOUR_HELIUS_API_KEY")
163
+ ```
164
+
165
+ or set `HELIUS_API_KEY` as an environment variable:
166
+
167
+ ```bash
168
+ export HELIUS_API_KEY=your_helius_api_key
169
+ ```
170
+
171
+ You can also set it in a `.env` file at the project root and let the
172
+ client pick it up automatically:
173
+
174
+ ```env
175
+ HELIUS_API_KEY=your_helius_api_key
176
+ ```
177
+
178
+ ```python
179
+ from helius.solana_rpc import SolanaRpcClient
180
+
181
+ client = SolanaRpcClient() # reads HELIUS_API_KEY from the environment or .env
182
+ ```
183
+
184
+ ## Usage
185
+
186
+ ### As a context manager (recommended)
187
+
188
+ ```python
189
+ from helius.solana_rpc import SolanaRpcClient
190
+
191
+ with SolanaRpcClient(api_key="YOUR_HELIUS_API_KEY") as client:
192
+ _ctx, balance = client.get_balance("So11111111111111111111111111111111111111112")
193
+ _ctx, supply = client.get_supply()
194
+ nodes = client.get_cluster_nodes()
195
+ block = client.get_block(slot=250_000_000)
196
+ tx = client.get_transaction("5j7s...signature...")
197
+ ```
198
+
199
+ `SolanaRpcClient` implements the context-manager protocol via `__enter__` /
200
+ `__exit__`, so the underlying `httpx.Client` is closed cleanly when the
201
+ `with` block exits.
202
+
203
+ ### With an explicit `close()` call
204
+
205
+ If a `with` block doesn't fit your code structure (e.g. the client lives
206
+ on a long-lived object), call `close()` yourself when you're done:
207
+
208
+ ```python
209
+ from helius.solana_rpc import SolanaRpcClient
210
+
211
+ client = SolanaRpcClient(api_key="YOUR_HELIUS_API_KEY")
212
+ try:
213
+ _ctx, balance = client.get_balance("So11111111111111111111111111111111111111112")
214
+ _ctx, supply = client.get_supply()
215
+ finally:
216
+ client.close()
217
+ ```
218
+
219
+ Client classes also implement `__del__` as a safety net — if you forget
220
+ to `close()` or use `with`, the underlying HTTP client is still closed
221
+ when the instance is garbage-collected. Prefer `with` or `close()`
222
+ regardless.
223
+
224
+ > 🚧 **Exception & error handling is a work in progress.** Today,
225
+ > transport errors surface as raw `httpx` exceptions and Helius/Solana
226
+ > RPC errors are not yet wrapped in typed exception classes. A
227
+ > consistent error hierarchy is being worked on.
228
+
229
+ ### Defaults
230
+
231
+ | Argument | Default | Notes |
232
+ | ---------- | ------------------------------------------------------------------------- | ------------------------------------------------------------------ |
233
+ | `base_url` | `"https://mainnet.helius-rpc.com"` | Override to point at devnet, staging, or a custom Helius endpoint. |
234
+ | `api_key` | `None` → falls back to `HELIUS_API_KEY` from the environment, then `.env` | If none is provided, the constructor raises `ValueError`. |
235
+
236
+ Per-method RPC parameters (`commitment`, `encoding`, `min_context_slot`,
237
+ etc.) are left unset by default — the Helius/Solana server defaults
238
+ apply unless you pass them explicitly.
239
+
240
+ ### Reference
241
+
242
+ For parameters, semantics, and return shapes, see the official Helius docs:
243
+ [RPC guide](https://www.helius.dev/docs/rpc) and
244
+ [API reference](https://www.helius.dev/docs/api-reference).
245
+
246
+ If you hit a bug, a missing parameter, or surprising behavior, please
247
+ [open an issue](https://github.com/markosnarinian/helius-python/issues).
248
+
249
+ ### Supported methods
250
+
251
+ The method names map 1:1 to the Solana JSON-RPC spec, just converted to
252
+ `snake_case`. If you know the RPC method name, you know the Python function.
253
+
254
+ ## Status
255
+
256
+ Actively expanding toward full coverage of the Helius API. See
257
+ [`src/helius/solana_rpc.py`](src/helius/solana_rpc.py) for the current list of
258
+ implemented methods; missing endpoints are tracked as issues and added
259
+ continuously.
260
+
261
+ | Solana JSON-RPC method | Python method | Helius docs |
262
+ | ----------------------------------- | --------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
263
+ | `getAccountInfo` | `get_account_info(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getaccountinfo), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getaccountinfo) |
264
+ | `getBalance` | `get_balance(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getbalance), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getbalance) |
265
+ | `getBlock` | `get_block(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getblock), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getblock) |
266
+ | `getBlockCommitment` | `get_block_commitment(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getblockcommitment), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getblockcommitment) |
267
+ | `getBlockHeight` | `get_block_height(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getblockheight), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getblockheight) |
268
+ | `getBlockProduction` | `get_block_production(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getblockproduction), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getblockproduction) |
269
+ | `getBlocks` | `get_blocks(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getblocks), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getblocks) |
270
+ | `getBlocksWithLimit` | `get_blocks_with_limit(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getblockswithlimit), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getblockswithlimit) |
271
+ | `getBlockTime` | `get_block_time(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getblocktime), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getblocktime) |
272
+ | `getClusterNodes` | `get_cluster_nodes()` | [guide](https://www.helius.dev/docs/rpc/guides/getclusternodes), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getclusternodes) |
273
+ | `getEpochInfo` | `get_epoch_info(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getepochinfo), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getepochinfo) |
274
+ | `getEpochSchedule` | `get_epoch_schedule()` | [guide](https://www.helius.dev/docs/rpc/guides/getepochschedule), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getepochschedule) |
275
+ | `getFeeForMessage` | `get_fee_for_message(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getfeeformessage), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getfeeformessage) |
276
+ | `getFirstAvailableBlock` | `get_first_available_block()` | [guide](https://www.helius.dev/docs/rpc/guides/getfirstavailableblock), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getfirstavailableblock) |
277
+ | `getGenesisHash` | `get_genesis_hash()` | [guide](https://www.helius.dev/docs/rpc/guides/getgenesishash), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getgenesishash) |
278
+ | `getHealth` | `get_health()` | [guide](https://www.helius.dev/docs/rpc/guides/gethealth), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gethealth) |
279
+ | `getHighestSnapshotSlot` | `get_highest_snapshot_slot()` | [guide](https://www.helius.dev/docs/rpc/guides/gethighestsnapshotslot), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gethighestsnapshotslot) |
280
+ | `getIdentity` | `get_identity()` | [guide](https://www.helius.dev/docs/rpc/guides/getidentity), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getidentity) |
281
+ | `getInflationGovernor` | `get_inflation_governor(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getinflationgovernor), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getinflationgovernor) |
282
+ | `getInflationRate` | `get_inflation_rate()` | [guide](https://www.helius.dev/docs/rpc/guides/getinflationrate), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getinflationrate) |
283
+ | `getInflationReward` | `get_inflation_reward(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getinflationreward), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getinflationreward) |
284
+ | `getLargestAccounts` | `get_largest_accounts(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getlargestaccounts), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getlargestaccounts) |
285
+ | `getLatestBlockhash` | `get_latest_blockhash(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getlatestblockhash), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getlatestblockhash) |
286
+ | `getLeaderSchedule` | `client.get_leader_schedule(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getleaderschedule), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getleaderschedule) |
287
+ | `getMaxRetransmitSlot` | `client.get_max_retransmit_slot()` | [guide](https://www.helius.dev/docs/rpc/guides/getmaxretransmitslot), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getmaxretransmitslot) |
288
+ | `getMaxShredInsertSlot` | `get_max_shred_insert_slot()` | [guide](https://www.helius.dev/docs/rpc/guides/getmaxshredinsertslot), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getmaxshredinsertslot) |
289
+ | `getMinimumBalanceForRentExemption` | `get_minimum_balance_for_rent_exemption(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getminimumbalanceforrentexemption), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getminimumbalanceforrentexemption) |
290
+ | `getMultipleAccounts` | `get_multiple_accounts(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getmultipleaccounts), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getmultipleaccounts) |
291
+ | `getProgramAccounts` | `get_program_accounts(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getprogramaccounts), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getprogramaccounts) |
292
+ | `getRecentPerformanceSamples` | `get_recent_performance_samples(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getrecentperformancesamples), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getrecentperformancesamples) |
293
+ | `getRecentPrioritizationFees` | `get_recent_prioritization_fees(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getrecentprioritizationfees), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getrecentprioritizationfees) |
294
+ | `getSignaturesForAddress` | `get_signatures_for_address(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getsignaturesforaddress), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getsignaturesforaddress) |
295
+ | `getSignatureStatuses` | `get_signature_statuses(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getsignaturestatuses), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getsignaturestatuses) |
296
+ | `getSlot` | `get_slot(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getslot), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getslot) |
297
+ | `getSlotLeader` | `get_slot_leader(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getslotleader), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getslotleader) |
298
+ | `getSlotLeaders` | `get_slot_leaders(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getslotleaders), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getslotleaders) |
299
+ | `getStakeMinimumDelegation` | `get_stake_minimum_delegation(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getstakeminimumdelegation), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getstakeminimumdelegation) |
300
+ | `getSupply` | `get_supply(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getsupply), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getsupply) |
301
+ | `getTokenAccountBalance` | `get_token_account_balance(...)` | [guide](https://www.helius.dev/docs/rpc/guides/gettokenaccountbalance), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gettokenaccountbalance) |
302
+ | `getTokenAccountsByDelegate` | `get_token_accounts_by_delegate(...)` | [guide](https://www.helius.dev/docs/rpc/guides/gettokenaccountsbydelegate), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gettokenaccountsbydelegate) |
303
+ | `getTokenAccountsByOwner` | `get_token_accounts_by_owner(...)` | [guide](https://www.helius.dev/docs/rpc/guides/gettokenaccountsbyowner), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gettokenaccountsbyowner) |
304
+ | `getTokenLargestAccounts` | `get_token_largest_accounts(...)` | [guide](https://www.helius.dev/docs/rpc/guides/gettokenlargestaccounts), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gettokenlargestaccounts) |
305
+ | `getTokenSupply` | `get_token_supply(...)` | [guide](https://www.helius.dev/docs/rpc/guides/gettokensupply), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gettokensupply) |
306
+ | `getTransaction` | `get_transaction(...)` | [guide](https://www.helius.dev/docs/rpc/guides/gettransaction), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gettransaction) |
307
+ | `getTransactionCount` | `get_transaction_count(...)` | [guide](https://www.helius.dev/docs/rpc/guides/gettransactioncount), [reference](https://www.helius.dev/docs/api-reference/rpc/http/gettransactioncount) |
308
+ | `getVersion` | `get_version()` | [guide](https://www.helius.dev/docs/rpc/guides/getversion), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getversion) |
309
+ | `getVoteAccounts` | `get_vote_accounts(...)` | [guide](https://www.helius.dev/docs/rpc/guides/getvoteaccounts), [reference](https://www.helius.dev/docs/api-reference/rpc/http/getvoteaccounts) |
310
+ | `isBlockhashValid` | `is_blockhash_valid(...)` | [guide](https://www.helius.dev/docs/rpc/guides/isblockhashvalid), [reference](https://www.helius.dev/docs/api-reference/rpc/http/isblockhashvalid) |
311
+ | `minimumLedgerSlot` | `minimum_ledger_slot()` | [guide](https://www.helius.dev/docs/rpc/guides/minimumledgerslot), [reference](https://www.helius.dev/docs/api-reference/rpc/http/minimumledgerslot) |
312
+ | `requestAirdrop` | `request_airdrop(...)` | [guide](https://www.helius.dev/docs/rpc/guides/requestairdrop), [reference](https://www.helius.dev/docs/api-reference/rpc/http/requestairdrop) |
313
+ | `sendTransaction` | `send_transaction(...)` | [guide](https://www.helius.dev/docs/rpc/guides/sendtransaction), [reference](https://www.helius.dev/docs/api-reference/rpc/http/sendtransaction) |
314
+
315
+ ## License
316
+
317
+ [MIT](LICENSE)