mm-strk 0.4.2__tar.gz → 0.5.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.
- mm_strk-0.5.0/.claude/settings.local.json +15 -0
- mm_strk-0.5.0/ADR.md +3 -0
- mm_strk-0.5.0/CLAUDE.md +24 -0
- mm_strk-0.5.0/PKG-INFO +7 -0
- mm_strk-0.5.0/README.md +72 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/pyproject.toml +20 -20
- mm_strk-0.5.0/src/mm_strk/__init__.py +1 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/src/mm_strk/account.py +6 -5
- {mm_strk-0.4.2 → mm_strk-0.5.0}/src/mm_strk/balance.py +3 -0
- mm_strk-0.5.0/src/mm_strk/cli/__init__.py +1 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/src/mm_strk/cli/cli.py +7 -3
- {mm_strk-0.4.2 → mm_strk-0.5.0}/src/mm_strk/cli/cli_utils.py +3 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/src/mm_strk/cli/commands/__init__.py +2 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/src/mm_strk/cli/commands/node.py +16 -3
- {mm_strk-0.4.2 → mm_strk-0.5.0}/src/mm_strk/domain.py +6 -3
- mm_strk-0.5.0/tests/__init__.py +1 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/tests/conftest.py +5 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/tests/test_account.py +4 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/tests/test_balance.py +3 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/tests/test_domain.py +4 -0
- mm_strk-0.5.0/uv.lock +1566 -0
- mm_strk-0.4.2/PKG-INFO +0 -7
- mm_strk-0.4.2/README.txt +0 -9
- mm_strk-0.4.2/src/mm_strk/__init__.py +0 -0
- mm_strk-0.4.2/src/mm_strk/cli/__init__.py +0 -0
- mm_strk-0.4.2/tests/__init__.py +0 -0
- mm_strk-0.4.2/uv.lock +0 -1401
- {mm_strk-0.4.2 → mm_strk-0.5.0}/.gitignore +0 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/dict.dic +0 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/justfile +0 -0
- {mm_strk-0.4.2 → mm_strk-0.5.0}/src/mm_strk/py.typed +0 -0
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
{
|
|
2
|
+
"permissions": {
|
|
3
|
+
"allow": [
|
|
4
|
+
"Bash(just lint:*)",
|
|
5
|
+
"WebFetch(domain:github.com)",
|
|
6
|
+
"WebFetch(domain:docs.starknet.io)",
|
|
7
|
+
"Bash(curl:*)",
|
|
8
|
+
"WebFetch(domain:www.starknet.io)",
|
|
9
|
+
"WebFetch(domain:www.comparenodes.com)",
|
|
10
|
+
"WebFetch(domain:starknetpy.readthedocs.io)",
|
|
11
|
+
"WebFetch(domain:pypi.org)",
|
|
12
|
+
"WebFetch(domain:drpc.org)"
|
|
13
|
+
]
|
|
14
|
+
}
|
|
15
|
+
}
|
mm_strk-0.5.0/ADR.md
ADDED
mm_strk-0.5.0/CLAUDE.md
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
# AI Agent Start Guide
|
|
2
|
+
|
|
3
|
+
## Critical: Language
|
|
4
|
+
RESPOND IN ENGLISH. Always. No exceptions.
|
|
5
|
+
User's language does NOT determine your response language.
|
|
6
|
+
Only switch if user EXPLICITLY requests it (e.g., "respond in {language}").
|
|
7
|
+
Language switching applies ONLY to chat. All code, comments, commit messages, and files must ALWAYS be in English — no exceptions.
|
|
8
|
+
|
|
9
|
+
## Mandatory Rules (external)
|
|
10
|
+
These files are REQUIRED. Read them fully and follow all rules.
|
|
11
|
+
- `~/.claude/shared-rules/general.md`
|
|
12
|
+
- `~/.claude/shared-rules/python.md`
|
|
13
|
+
|
|
14
|
+
## Project Reading (context)
|
|
15
|
+
These files are REQUIRED for project understanding.
|
|
16
|
+
- `README.md`
|
|
17
|
+
|
|
18
|
+
## Preflight (mandatory)
|
|
19
|
+
Before your first response:
|
|
20
|
+
1. Read all files listed above.
|
|
21
|
+
2. Do not answer until all are read.
|
|
22
|
+
3. In your first reply, list every file you have read from this document.
|
|
23
|
+
|
|
24
|
+
Failure to follow this protocol is considered an error.
|
mm_strk-0.5.0/PKG-INFO
ADDED
mm_strk-0.5.0/README.md
ADDED
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
# mm-strk
|
|
2
|
+
|
|
3
|
+
Starknet utilities library.
|
|
4
|
+
|
|
5
|
+
**Requires RPC node version 0.9+**
|
|
6
|
+
|
|
7
|
+
## Installation
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
pip install mm-strk
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
## API
|
|
14
|
+
|
|
15
|
+
### is_address
|
|
16
|
+
|
|
17
|
+
Validates a Starknet address.
|
|
18
|
+
|
|
19
|
+
```python
|
|
20
|
+
from mm_strk.account import is_address
|
|
21
|
+
|
|
22
|
+
is_address("0x123abc") # True - minimal form
|
|
23
|
+
is_address("0x0000000000000000000000000000000000000000000000000000000000123abc") # True - full 64-char form
|
|
24
|
+
is_address("invalid") # False
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
### get_balance
|
|
28
|
+
|
|
29
|
+
Queries token balance for an address.
|
|
30
|
+
|
|
31
|
+
```python
|
|
32
|
+
import asyncio
|
|
33
|
+
from mm_strk.balance import get_balance, ETH_ADDRESS_MAINNET, STRK_ADDRESS_MAINNET
|
|
34
|
+
|
|
35
|
+
result = asyncio.run(get_balance(
|
|
36
|
+
rpc_url="https://your-rpc-node.com",
|
|
37
|
+
address="0x123...",
|
|
38
|
+
token=ETH_ADDRESS_MAINNET,
|
|
39
|
+
))
|
|
40
|
+
if result.is_ok():
|
|
41
|
+
print(result.ok) # balance in wei
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
Token constants:
|
|
45
|
+
- `ETH_ADDRESS_MAINNET`, `ETH_DECIMALS` (18)
|
|
46
|
+
- `STRK_ADDRESS_MAINNET`, `STRK_DECIMALS` (18)
|
|
47
|
+
- `USDC_ADDRESS_MAINNET`, `USDC_DECIMALS` (6)
|
|
48
|
+
- `USDT_ADDRESS_MAINNET`, `USDT_DECIMALS` (6)
|
|
49
|
+
- `DAI_ADDRESS_MAINNET`, `DAI_DECIMALS` (18)
|
|
50
|
+
|
|
51
|
+
### address_to_domain
|
|
52
|
+
|
|
53
|
+
Resolves a Starknet address to its Starknet ID domain.
|
|
54
|
+
|
|
55
|
+
```python
|
|
56
|
+
import asyncio
|
|
57
|
+
from mm_strk.domain import address_to_domain
|
|
58
|
+
|
|
59
|
+
result = asyncio.run(address_to_domain("0x123..."))
|
|
60
|
+
if result.is_ok():
|
|
61
|
+
print(result.ok) # "example.stark" or None if not found
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
## CLI
|
|
65
|
+
|
|
66
|
+
### mm-strk node
|
|
67
|
+
|
|
68
|
+
Check status of Starknet RPC nodes.
|
|
69
|
+
|
|
70
|
+
```bash
|
|
71
|
+
mm-strk node https://rpc-node-1.com https://rpc-node-2.com
|
|
72
|
+
```
|
|
@@ -1,13 +1,9 @@
|
|
|
1
1
|
[project]
|
|
2
2
|
name = "mm-strk"
|
|
3
|
-
version = "0.
|
|
3
|
+
version = "0.5.0"
|
|
4
4
|
description = ""
|
|
5
|
-
requires-python = ">=3.
|
|
6
|
-
dependencies = [
|
|
7
|
-
"mm-web3~=0.5.1",
|
|
8
|
-
"starknet-py~=0.27.0",
|
|
9
|
-
"typer>=0.16.0",
|
|
10
|
-
]
|
|
5
|
+
requires-python = ">=3.14"
|
|
6
|
+
dependencies = ["mm-web3~=0.6.2", "starknet-py~=0.29.0", "typer~=0.21.1"]
|
|
11
7
|
[project.scripts]
|
|
12
8
|
mm-strk = "mm_strk.cli.cli:app"
|
|
13
9
|
|
|
@@ -17,29 +13,32 @@ requires = ["hatchling"]
|
|
|
17
13
|
build-backend = "hatchling.build"
|
|
18
14
|
|
|
19
15
|
|
|
20
|
-
[
|
|
21
|
-
dev
|
|
22
|
-
"
|
|
23
|
-
"
|
|
24
|
-
"
|
|
25
|
-
"
|
|
26
|
-
"
|
|
27
|
-
"
|
|
28
|
-
"
|
|
29
|
-
"
|
|
16
|
+
[dependency-groups]
|
|
17
|
+
dev = [
|
|
18
|
+
"bandit~=1.9.3",
|
|
19
|
+
"mypy~=1.19.1",
|
|
20
|
+
"pip-audit~=2.10.0",
|
|
21
|
+
"pre-commit~=4.5.1",
|
|
22
|
+
"pytest~=9.0.2",
|
|
23
|
+
"pytest-asyncio~=1.3.0",
|
|
24
|
+
"pytest-xdist~=3.8.0",
|
|
25
|
+
"ruff~=0.15.0",
|
|
26
|
+
"python-dotenv~=1.2.0",
|
|
30
27
|
]
|
|
28
|
+
|
|
29
|
+
[tool.uv]
|
|
31
30
|
override-dependencies = ["pywin32 ; sys_platform == 'win32'"]
|
|
32
31
|
|
|
33
32
|
|
|
34
33
|
[tool.mypy]
|
|
35
|
-
python_version = "3.
|
|
34
|
+
python_version = "3.14"
|
|
36
35
|
warn_no_return = false
|
|
37
36
|
strict = true
|
|
38
37
|
exclude = ["^tests/", "^tmp/"]
|
|
39
38
|
|
|
40
39
|
[tool.ruff]
|
|
41
40
|
line-length = 130
|
|
42
|
-
target-version = "
|
|
41
|
+
target-version = "py314"
|
|
43
42
|
[tool.ruff.lint]
|
|
44
43
|
select = ["ALL"]
|
|
45
44
|
ignore = [
|
|
@@ -47,7 +46,6 @@ ignore = [
|
|
|
47
46
|
"A005", # flake8-builtins: stdlib-module-shadowing
|
|
48
47
|
"ERA001", # eradicate: commented-out-code
|
|
49
48
|
"PT", # flake8-pytest-style
|
|
50
|
-
"D", # pydocstyle
|
|
51
49
|
"FIX", # flake8-fixme
|
|
52
50
|
"PLR0911", # pylint: too-many-return-statements
|
|
53
51
|
"PLR0912", # pylint: too-many-branches
|
|
@@ -65,6 +63,8 @@ ignore = [
|
|
|
65
63
|
"RET503", # flake8-return: implicit-return
|
|
66
64
|
"COM812", # it's used in ruff formatter
|
|
67
65
|
"ASYNC109", # flake8-async: async-function-with-timeout
|
|
66
|
+
"D203", # pydocstyle: one-blank-line-before-class (conflicts with D211)
|
|
67
|
+
"D213", # pydocstyle: multi-line-summary-second-line (conflicts with D212)
|
|
68
68
|
]
|
|
69
69
|
[tool.ruff.lint.pep8-naming]
|
|
70
70
|
classmethod-decorators = ["field_validator"]
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"""Starknet utilities library."""
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
"""Starknet address validation."""
|
|
2
|
+
|
|
1
3
|
import re
|
|
2
4
|
|
|
3
5
|
# Maximum allowable value for a StarkNet address (251 bits)
|
|
@@ -5,15 +7,14 @@ MAX_STARKNET_ADDRESS = 2**251
|
|
|
5
7
|
|
|
6
8
|
|
|
7
9
|
def is_address(address: str) -> bool:
|
|
8
|
-
"""
|
|
9
|
-
Validates a StarkNet address.
|
|
10
|
+
"""Validate a Starknet address.
|
|
10
11
|
|
|
11
12
|
- Must be a string starting with '0x'.
|
|
12
13
|
- Hex part 1-64 chars.
|
|
13
14
|
- Integer value < 2**251.
|
|
14
15
|
- Accepts either:
|
|
15
|
-
|
|
16
|
-
|
|
16
|
+
* Full 64-hex-character padded form.
|
|
17
|
+
* Minimal form without leading zeros (canonical).
|
|
17
18
|
"""
|
|
18
19
|
# Type and prefix
|
|
19
20
|
if not isinstance(address, str) or not address.startswith("0x"):
|
|
@@ -39,5 +40,5 @@ def is_address(address: str) -> bool:
|
|
|
39
40
|
return True
|
|
40
41
|
|
|
41
42
|
# Minimal form (no leading zeros)
|
|
42
|
-
canonical =
|
|
43
|
+
canonical = f"{value:x}"
|
|
43
44
|
return hex_part.lower() == canonical
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
"""Token balance querying on Starknet."""
|
|
2
|
+
|
|
1
3
|
import aiohttp
|
|
2
4
|
from aiohttp_socks import ProxyConnector
|
|
3
5
|
from mm_result import Result
|
|
@@ -19,6 +21,7 @@ STRK_DECIMALS = 18
|
|
|
19
21
|
|
|
20
22
|
|
|
21
23
|
async def get_balance(rpc_url: str, address: str, token: str, timeout: float = 5, proxy: str | None = None) -> Result[int]:
|
|
24
|
+
"""Get token balance for a Starknet address."""
|
|
22
25
|
try:
|
|
23
26
|
timeout_config = aiohttp.ClientTimeout(total=timeout)
|
|
24
27
|
connector = ProxyConnector.from_url(proxy) if proxy else None
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"""CLI package for mm-strk."""
|
|
@@ -1,7 +1,9 @@
|
|
|
1
|
+
"""CLI entry point for mm-strk."""
|
|
2
|
+
|
|
1
3
|
from typing import Annotated
|
|
2
4
|
|
|
3
|
-
import mm_print
|
|
4
5
|
import typer
|
|
6
|
+
from mm_print import print_plain
|
|
5
7
|
|
|
6
8
|
from mm_strk.cli import cli_utils, commands
|
|
7
9
|
|
|
@@ -9,14 +11,15 @@ app = typer.Typer(no_args_is_help=True, pretty_exceptions_enable=False, add_comp
|
|
|
9
11
|
|
|
10
12
|
|
|
11
13
|
def version_callback(value: bool) -> None:
|
|
14
|
+
"""Print version and exit when --version is passed."""
|
|
12
15
|
if value:
|
|
13
|
-
|
|
16
|
+
print_plain(f"mm-strk: {cli_utils.get_version()}")
|
|
14
17
|
raise typer.Exit
|
|
15
18
|
|
|
16
19
|
|
|
17
20
|
@app.callback()
|
|
18
21
|
def main(_version: bool = typer.Option(None, "--version", callback=version_callback, is_eager=True)) -> None:
|
|
19
|
-
|
|
22
|
+
"""Starknet utilities CLI."""
|
|
20
23
|
|
|
21
24
|
|
|
22
25
|
@app.command(name="node", help="Checks RPC URLs for availability and status")
|
|
@@ -24,4 +27,5 @@ def node_command(
|
|
|
24
27
|
urls: Annotated[list[str], typer.Argument()],
|
|
25
28
|
proxy: Annotated[str | None, typer.Option("--proxy", "-p", help="Proxy")] = None,
|
|
26
29
|
) -> None:
|
|
30
|
+
"""Check RPC node availability and status."""
|
|
27
31
|
commands.node.run(urls, proxy)
|
|
@@ -1,19 +1,25 @@
|
|
|
1
|
+
"""Starknet node status checking."""
|
|
2
|
+
|
|
1
3
|
import asyncio
|
|
2
4
|
|
|
3
|
-
import mm_print
|
|
4
5
|
import typer
|
|
6
|
+
from mm_print import print_json
|
|
5
7
|
from pydantic import BaseModel
|
|
6
8
|
from starknet_py.net.client_models import SyncStatus
|
|
7
9
|
from starknet_py.net.full_node_client import FullNodeClient
|
|
8
10
|
|
|
9
11
|
|
|
10
12
|
class NodeStatus(BaseModel):
|
|
13
|
+
"""Starknet node status response."""
|
|
14
|
+
|
|
15
|
+
spec_version: str
|
|
11
16
|
block_number: int | str
|
|
12
17
|
chain_id: int | str
|
|
13
18
|
syncing_status: bool | SyncStatus | str
|
|
14
19
|
|
|
15
20
|
|
|
16
21
|
def run(urls: list[str], proxy: str | None) -> None:
|
|
22
|
+
"""Check status of Starknet nodes."""
|
|
17
23
|
if proxy:
|
|
18
24
|
typer.echo("proxy is not supported yet")
|
|
19
25
|
raise typer.Exit(code=1)
|
|
@@ -21,16 +27,23 @@ def run(urls: list[str], proxy: str | None) -> None:
|
|
|
21
27
|
|
|
22
28
|
|
|
23
29
|
async def _run(urls: list[str]) -> None:
|
|
30
|
+
"""Fetch and print status for all given node URLs."""
|
|
24
31
|
result = {}
|
|
25
32
|
for url in urls:
|
|
26
33
|
result[url] = (await _node_status(url)).model_dump()
|
|
27
34
|
|
|
28
|
-
|
|
35
|
+
print_json(result)
|
|
29
36
|
|
|
30
37
|
|
|
31
38
|
async def _node_status(url: str) -> NodeStatus:
|
|
39
|
+
"""Fetch status from a single node."""
|
|
32
40
|
client = FullNodeClient(node_url=url)
|
|
33
41
|
|
|
42
|
+
try:
|
|
43
|
+
spec_version: str = await client.spec_version()
|
|
44
|
+
except Exception as e:
|
|
45
|
+
spec_version = str(e)
|
|
46
|
+
|
|
34
47
|
try:
|
|
35
48
|
block_number: int | str = await client.get_block_number()
|
|
36
49
|
except Exception as e:
|
|
@@ -46,4 +59,4 @@ async def _node_status(url: str) -> NodeStatus:
|
|
|
46
59
|
except Exception as e:
|
|
47
60
|
syncing_status = str(e)
|
|
48
61
|
|
|
49
|
-
return NodeStatus(block_number=block_number, chain_id=chain_id, syncing_status=syncing_status)
|
|
62
|
+
return NodeStatus(spec_version=spec_version, block_number=block_number, chain_id=chain_id, syncing_status=syncing_status)
|
|
@@ -1,9 +1,12 @@
|
|
|
1
|
+
"""Starknet domain resolution via starknet.id API."""
|
|
2
|
+
|
|
1
3
|
from mm_http import http_request
|
|
2
4
|
from mm_result import Result
|
|
3
5
|
from mm_std import str_contains_any
|
|
4
6
|
|
|
5
7
|
|
|
6
8
|
async def address_to_domain(address: str, timeout: float = 5.0, proxy: str | None = None) -> Result[str | None]:
|
|
9
|
+
"""Resolve a Starknet address to its .stark domain name."""
|
|
7
10
|
url = "https://api.starknet.id/addr_to_domain"
|
|
8
11
|
res = await http_request(url, params={"addr": address}, proxy=proxy, timeout=timeout)
|
|
9
12
|
if (
|
|
@@ -14,7 +17,7 @@ async def address_to_domain(address: str, timeout: float = 5.0, proxy: str | Non
|
|
|
14
17
|
return res.to_result_ok(None)
|
|
15
18
|
if res.is_err():
|
|
16
19
|
return res.to_result_err()
|
|
17
|
-
|
|
18
|
-
if
|
|
19
|
-
return res.to_result_ok(
|
|
20
|
+
domain_res = res.json_body("domain")
|
|
21
|
+
if domain_res.is_ok():
|
|
22
|
+
return res.to_result_ok(domain_res.unwrap())
|
|
20
23
|
return res.to_result_err("unknown_response")
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"""Tests for mm-strk."""
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
"""Shared test fixtures."""
|
|
2
|
+
|
|
1
3
|
import os
|
|
2
4
|
|
|
3
5
|
import pytest
|
|
@@ -10,16 +12,19 @@ MAINNET_URL = os.getenv("MAINNET_URL")
|
|
|
10
12
|
|
|
11
13
|
@pytest.fixture
|
|
12
14
|
def anyio_backend() -> str:
|
|
15
|
+
"""Use asyncio as the async backend."""
|
|
13
16
|
return "asyncio"
|
|
14
17
|
|
|
15
18
|
|
|
16
19
|
@pytest.fixture
|
|
17
20
|
def zklend_market_address() -> str:
|
|
21
|
+
"""Return the zkLend market contract address."""
|
|
18
22
|
return "0x04c0a5193d58f74fbace4b74dcf65481e734ed1714121bdc571da345540efa05"
|
|
19
23
|
|
|
20
24
|
|
|
21
25
|
@pytest.fixture
|
|
22
26
|
def mainnet_rpc_url() -> str:
|
|
27
|
+
"""Return the mainnet RPC URL from environment."""
|
|
23
28
|
if not MAINNET_URL:
|
|
24
29
|
raise ValueError("MAINNET_URL environment variable is not set.")
|
|
25
30
|
return MAINNET_URL
|
|
@@ -1,9 +1,12 @@
|
|
|
1
|
+
"""Tests for address validation."""
|
|
2
|
+
|
|
1
3
|
from starknet_py.hash.address import get_checksum_address
|
|
2
4
|
|
|
3
5
|
from mm_strk.account import is_address
|
|
4
6
|
|
|
5
7
|
|
|
6
8
|
def test_valid_addresses():
|
|
9
|
+
"""Test that valid Starknet addresses are accepted."""
|
|
7
10
|
# Compact lower-case and mixed-case hex strings
|
|
8
11
|
assert is_address("0x1") is True
|
|
9
12
|
assert is_address("0x123abc") is True
|
|
@@ -17,6 +20,7 @@ def test_valid_addresses():
|
|
|
17
20
|
|
|
18
21
|
|
|
19
22
|
def test_invalid_addresses():
|
|
23
|
+
"""Test that invalid Starknet addresses are rejected."""
|
|
20
24
|
# Missing prefix or empty
|
|
21
25
|
assert is_address("123abc") is False
|
|
22
26
|
assert is_address("0x") is False
|
|
@@ -1,7 +1,10 @@
|
|
|
1
|
+
"""Tests for token balance querying."""
|
|
2
|
+
|
|
1
3
|
from mm_strk import balance
|
|
2
4
|
|
|
3
5
|
|
|
4
6
|
async def test_get_balance(mainnet_rpc_url):
|
|
7
|
+
"""Test fetching ETH and STRK balances for a known address."""
|
|
5
8
|
address = "0x076601136372fcdbbd914eea797082f7504f828e122288ad45748b0c8b0c9696" # Bybit: Hot Wallet
|
|
6
9
|
assert (await balance.get_balance(mainnet_rpc_url, address, balance.ETH_ADDRESS_MAINNET)).unwrap() > 1
|
|
7
10
|
assert (await balance.get_balance(mainnet_rpc_url, address, balance.STRK_ADDRESS_MAINNET)).unwrap() > 1
|
|
@@ -1,13 +1,17 @@
|
|
|
1
|
+
"""Tests for Starknet domain resolution."""
|
|
2
|
+
|
|
1
3
|
from mm_strk import domain
|
|
2
4
|
|
|
3
5
|
|
|
4
6
|
async def test_address_to_domain_exist():
|
|
7
|
+
"""Test resolving an address that has a .stark domain."""
|
|
5
8
|
res = await domain.address_to_domain("0x0060b56b67e1b4dd1909376496b0e867f165f31c5eac7902d9ff48112f16ef9b")
|
|
6
9
|
assert res.is_ok()
|
|
7
10
|
assert res.unwrap() == "abc.stark"
|
|
8
11
|
|
|
9
12
|
|
|
10
13
|
async def test_address_to_domain_async_not_exist():
|
|
14
|
+
"""Test resolving an address that has no .stark domain."""
|
|
11
15
|
res = await domain.address_to_domain("0x0060b56b67e1b4dd1909376496b0e867f165f31c5eac7902d9ff48112f16ef9a") # not existed
|
|
12
16
|
assert res.is_ok()
|
|
13
17
|
assert res.unwrap() is None
|