From f8ad801e0c5bc1b4c3ff008f3b1140245b407560 Mon Sep 17 00:00:00 2001 From: bohd4nx Date: Fri, 29 May 2026 01:27:29 +0300 Subject: [PATCH] feat: enhance documentation with contributing guidelines and security policy refactor: update README configuration parameters and add error handling section refactor: streamline tonapi imports and add WalletVersion to __all__ chore: update project metadata in pyproject.toml --- CONTRIBUTING.md | 56 +++++++++++++++++++++++++++ README.md | 43 ++++++++++++++++---- SECURITY.md | 19 +++++++++ pyfragment/__init__.py | 3 +- pyfragment/domains/tonapi/__init__.py | 15 ------- pyproject.toml | 13 +++---- 6 files changed, 119 insertions(+), 30 deletions(-) create mode 100644 CONTRIBUTING.md create mode 100644 SECURITY.md diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..581a776 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,56 @@ +# Contributing to pyfragment + +## Development setup + +```bash +git clone https://github.com/bohd4nx/pyfragment.git +cd pyfragment +pip install -e ".[dev]" +``` + +## Running checks + +```bash +# Lint and format +ruff check . --fix && ruff format . + +# Type check +mypy . --explicit-package-bases + +# Tests +pytest +``` + +All three must pass before opening a PR. + +## Project structure + +``` +pyfragment/ + client.py — FragmentClient (public entry point) + core/ — transport, cookies, constants + domains/ — one package per feature domain + ads/ — recharge_ads, topup_ton + anonymous_numbers/— buy_number, manage_number + giveaways/ — giveaway_stars, giveaway_premium + marketplace/ — search_usernames, search_numbers, search_gifts + purchases/ — purchase_stars, purchase_premium + tonapi/ — wallet info, transaction signing + models/ — result dataclasses and enums + exceptions.py — exception hierarchy +tests/ — unit tests (pytest) +examples/ — runnable usage examples (excluded from CI) +``` + +## Conventions + +- All public async methods live on `FragmentClient` and delegate to a domain service. +- Domain functions receive a `FragmentClient` instance, never raw httpx clients. +- Patch targets in tests use the module where the name is **defined**, e.g. `pyfragment.domains.tonapi.transaction.process_transaction`. +- Versioning follows [CalVer](https://calver.org/): `YYYY.MINOR.MICRO`. Bump in `pyproject.toml`; tag as `vYYYY.MINOR.MICRO`. + +## Pull requests + +- Keep PRs focused — one feature or fix per PR. +- Update `CHANGELOG.md` under `[Unreleased]`. +- Add or update tests for any changed behaviour. diff --git a/README.md b/README.md index 06c13d1..3a7d969 100644 --- a/README.md +++ b/README.md @@ -39,13 +39,13 @@ Requires Python 3.10+. ## Configuration -| Parameter | Type | Default | Description | -| ---------------- | ------------- | -------- | -------------------------------------------------------- | -| `seed` | `str` | — | 24-word TON wallet mnemonic | -| `api_key` | `str` | — | Tonapi key from [tonconsole.com](https://tonconsole.com) | -| `cookies` | `dict \| str` | — | Fragment session cookies | -| `wallet_version` | `str` | `"V5R1"` | `"V4R2"` or `"V5R1"` | -| `timeout` | `float` | `30.0` | HTTP request timeout in seconds | +| Parameter | Type | Default | Description | +| ---------------- | ------------- | -------- | ----------------------------------------------------------- | +| `seed` | `str` | — | 12-, 18-, or 24-word TON wallet mnemonic | +| `api_key` | `str` | — | Tonapi key from [tonconsole.com](https://tonconsole.com) | +| `cookies` | `dict \| str` | — | Fragment session cookies | +| `wallet_version` | `str` | `"V5R1"` | `"V4R2"` or `"V5R1"` (also accepts `WalletVersion` literal) | +| `timeout` | `float` | `30.0` | HTTP request timeout in seconds | --- @@ -128,12 +128,41 @@ Full runnable examples: - https://github.com/bohd4nx/pyfragment/tree/master/examples +--- + +## Error Handling + +All exceptions inherit from `FragmentError`. Catch specific ones or the base class: + +```python +from pyfragment import ( + ConfigurationError, # invalid arguments (amount, months, payment_method, etc.) + UserNotFoundError, # recipient not found on Fragment + WalletError, # insufficient TON/USDT balance + TransactionError, # broadcast failed, duplicate seqno, invalid payload + FragmentAPIError, # Fragment API returned an error response + FragmentPageError, # page fetch or hash extraction failed + AnonymousNumberError, # number not owned, wrong state, login code issues + CookieError, # missing or malformed session cookies + ParseError, # failed to decode Fragment payload + VerificationError, # on-chain verification step failed + OperationError, # generic operation-level failure + UnexpectedError, # unexpected API response structure +) +``` + Payload debug/decode helper (thanks): - https://ton-cell-abi-viewer.vercel.app/ --- +## Changelog + +See [CHANGELOG.md](https://github.com/bohd4nx/pyfragment/blob/master/CHANGELOG.md) for release history. + +--- +
### Made with ❤️ by [@bohd4nx](https://t.me/bohd4nx) diff --git a/SECURITY.md b/SECURITY.md new file mode 100644 index 0000000..475c2e7 --- /dev/null +++ b/SECURITY.md @@ -0,0 +1,19 @@ +# Security Policy + +## Reporting a vulnerability + +Please **do not** open a public GitHub issue for security vulnerabilities. + +Report them privately via GitHub's [Security Advisory](https://github.com/bohd4nx/pyfragment/security/advisories/new) feature, or contact the maintainer directly at [@bohd4nx](https://t.me/bohd4nx) on Telegram. + +Include: + +- A description of the vulnerability and its potential impact. +- Steps to reproduce or a proof-of-concept. +- Affected versions. + +You will receive a response within 72 hours. Once the fix is released, the advisory will be published. + +## Scope + +This library handles sensitive credentials (TON seed phrases, Fragment session cookies, Tonapi keys). Please treat any finding that could expose or misuse these credentials as high severity. diff --git a/pyfragment/__init__.py b/pyfragment/__init__.py index 2b33d5e..fc9d194 100644 --- a/pyfragment/__init__.py +++ b/pyfragment/__init__.py @@ -21,7 +21,7 @@ from pyfragment.exceptions import ( ) from pyfragment.models.anonymous_numbers import LoginCodeResult, TerminateSessionsResult from pyfragment.models.cookies import CookieResult -from pyfragment.models.enums import PaymentMethod +from pyfragment.models.enums import PaymentMethod, WalletVersion from pyfragment.models.giveaways import PremiumGiveawayResult, StarsGiveawayResult from pyfragment.models.marketplace import GiftsResult, NumbersResult, UsernamesResult from pyfragment.models.payments import AdsRechargeResult, AdsTopupResult, PremiumResult, StarsResult @@ -65,5 +65,6 @@ __all__ = [ "UnexpectedError", # literal types "PaymentMethod", + "WalletVersion", "get_cookies_from_browser", ] diff --git a/pyfragment/domains/tonapi/__init__.py b/pyfragment/domains/tonapi/__init__.py index 0a26afe..42b4b85 100644 --- a/pyfragment/domains/tonapi/__init__.py +++ b/pyfragment/domains/tonapi/__init__.py @@ -1,20 +1,5 @@ -from pyfragment.domains.tonapi.account import ( - check_ton_payment_balance, - check_usdt_payment_balance, - get_account_info, - get_usdt_balance, - get_wallet_info, -) from pyfragment.domains.tonapi.service import TonapiService -from pyfragment.domains.tonapi.transaction import clean_decode, process_transaction __all__ = [ "TonapiService", - "clean_decode", - "check_ton_payment_balance", - "check_usdt_payment_balance", - "get_account_info", - "get_usdt_balance", - "get_wallet_info", - "process_transaction", ] diff --git a/pyproject.toml b/pyproject.toml index da7fcb1..431667e 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -21,7 +21,6 @@ keywords = [ "telegram-ads", "ton", "ton-blockchain", - "tonkeeper", "tonapi", "anonymous-numbers", "username-auctions", @@ -36,7 +35,6 @@ keywords = [ classifiers = [ "Development Status :: 5 - Production/Stable", "Intended Audience :: Developers", - "Intended Audience :: Financial and Insurance Industry", "License :: OSI Approved :: MIT License", "Natural Language :: English", "Operating System :: OS Independent", @@ -50,8 +48,6 @@ classifiers = [ "Topic :: Software Development :: Libraries :: Python Modules", "Topic :: Internet", "Topic :: Internet :: WWW/HTTP", - "Topic :: Office/Business :: Financial", - "Topic :: Office/Business :: Financial :: Investment", "Typing :: Typed", ] dependencies = ["httpx>=0.25", "tonutils>=2.0.1"] @@ -78,7 +74,7 @@ addopts = "-v --tb=short" [tool.ruff] line-length = 128 -target-version = "py312" +target-version = "py310" [tool.ruff.lint] # E — pycodestyle errors, F — pyflakes, W — warnings, I — isort, UP — pyupgrade @@ -89,9 +85,12 @@ ignore = ["E501", "UP017"] [tool.ruff.lint.per-file-ignores] "tests/*" = ["E402"] -"systests/*" = ["E402"] [tool.mypy] python_version = "3.10" strict = true -exclude = ["^systests/", "^examples/"] +exclude = ["^examples/"] + +[[tool.mypy.overrides]] +module = "rookiepy" +ignore_missing_imports = true