ferogram 0.3.0__tar.gz → 0.4.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 (98) hide show
  1. ferogram-0.4.0/.github/workflows/compile-check.yml +146 -0
  2. {ferogram-0.3.0 → ferogram-0.4.0}/CHANGELOG.md +40 -0
  3. {ferogram-0.3.0 → ferogram-0.4.0}/Cargo.lock +1359 -89
  4. {ferogram-0.3.0 → ferogram-0.4.0}/Cargo.toml +2 -2
  5. {ferogram-0.3.0 → ferogram-0.4.0}/FEATURES.md +134 -25
  6. {ferogram-0.3.0 → ferogram-0.4.0}/PKG-INFO +1 -1
  7. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/__init__.py +3 -1
  8. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/client.py +159 -54
  9. {ferogram-0.3.0 → ferogram-0.4.0}/pyproject.toml +1 -1
  10. {ferogram-0.3.0 → ferogram-0.4.0}/src/auth.rs +16 -11
  11. {ferogram-0.3.0 → ferogram-0.4.0}/src/client.rs +86 -11
  12. {ferogram-0.3.0 → ferogram-0.4.0}/src/lib.rs +7 -0
  13. {ferogram-0.3.0 → ferogram-0.4.0}/src/message.rs +82 -12
  14. ferogram-0.4.0/src/session.rs +426 -0
  15. {ferogram-0.3.0 → ferogram-0.4.0}/.github/workflows/publish.yml +0 -0
  16. {ferogram-0.3.0 → ferogram-0.4.0}/.gitignore +0 -0
  17. {ferogram-0.3.0 → ferogram-0.4.0}/LICENSE-APACHE +0 -0
  18. {ferogram-0.3.0 → ferogram-0.4.0}/LICENSE-MIT +0 -0
  19. {ferogram-0.3.0 → ferogram-0.4.0}/README.md +0 -0
  20. {ferogram-0.3.0 → ferogram-0.4.0}/examples/admin_tools.py +0 -0
  21. {ferogram-0.3.0 → ferogram-0.4.0}/examples/command_bot.py +0 -0
  22. {ferogram-0.3.0 → ferogram-0.4.0}/examples/echo_bot.py +0 -0
  23. {ferogram-0.3.0 → ferogram-0.4.0}/examples/group_management.py +0 -0
  24. {ferogram-0.3.0 → ferogram-0.4.0}/examples/media_bot.py +0 -0
  25. {ferogram-0.3.0 → ferogram-0.4.0}/examples/raw_invoke.py +0 -0
  26. {ferogram-0.3.0 → ferogram-0.4.0}/examples/search_bot.py +0 -0
  27. {ferogram-0.3.0 → ferogram-0.4.0}/examples/send_hi.py +0 -0
  28. {ferogram-0.3.0 → ferogram-0.4.0}/examples/send_media.py +0 -0
  29. {ferogram-0.3.0 → ferogram-0.4.0}/examples/send_message.py +0 -0
  30. {ferogram-0.3.0 → ferogram-0.4.0}/examples/update_handlers.py +0 -0
  31. {ferogram-0.3.0 → ferogram-0.4.0}/examples/user_management.py +0 -0
  32. {ferogram-0.3.0 → ferogram-0.4.0}/examples/userbot.py +0 -0
  33. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/filters.py +0 -0
  34. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/logging.py +0 -0
  35. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/py.typed +0 -0
  36. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/__init__.py +0 -0
  37. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/api/__init__.py +0 -0
  38. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/api/functions.py +0 -0
  39. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/api/types.py +0 -0
  40. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/codegen.py +0 -0
  41. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/__init__.py +0 -0
  42. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/_tl_schema.py +0 -0
  43. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/__init__.py +0 -0
  44. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/account.py +0 -0
  45. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/aicompose.py +0 -0
  46. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/auth.py +0 -0
  47. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/bots.py +0 -0
  48. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/channels.py +0 -0
  49. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/chatlists.py +0 -0
  50. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/contacts.py +0 -0
  51. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/folders.py +0 -0
  52. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/fragment.py +0 -0
  53. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/help.py +0 -0
  54. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/langpack.py +0 -0
  55. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/messages.py +0 -0
  56. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/payments.py +0 -0
  57. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/phone.py +0 -0
  58. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/photos.py +0 -0
  59. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/premium.py +0 -0
  60. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/smsjobs.py +0 -0
  61. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/stats.py +0 -0
  62. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/stickers.py +0 -0
  63. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/stories.py +0 -0
  64. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/updates.py +0 -0
  65. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/upload.py +0 -0
  66. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/functions/users.py +0 -0
  67. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/__init__.py +0 -0
  68. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/_base.py +0 -0
  69. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/account.py +0 -0
  70. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/aicompose.py +0 -0
  71. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/auth.py +0 -0
  72. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/bots.py +0 -0
  73. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/channels.py +0 -0
  74. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/chatlists.py +0 -0
  75. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/contacts.py +0 -0
  76. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/fragment.py +0 -0
  77. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/help.py +0 -0
  78. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/messages.py +0 -0
  79. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/payments.py +0 -0
  80. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/phone.py +0 -0
  81. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/photos.py +0 -0
  82. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/premium.py +0 -0
  83. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/smsjobs.py +0 -0
  84. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/stats.py +0 -0
  85. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/stickers.py +0 -0
  86. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/storage.py +0 -0
  87. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/stories.py +0 -0
  88. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/updates.py +0 -0
  89. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/upload.py +0 -0
  90. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/generated/types/users.py +0 -0
  91. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/proxy.py +0 -0
  92. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw/tl.py +0 -0
  93. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/raw_api.tl +0 -0
  94. {ferogram-0.3.0 → ferogram-0.4.0}/ferogram/types.py +0 -0
  95. {ferogram-0.3.0 → ferogram-0.4.0}/src/keyboards.rs +0 -0
  96. {ferogram-0.3.0 → ferogram-0.4.0}/src/raw.rs +0 -0
  97. {ferogram-0.3.0 → ferogram-0.4.0}/src/types.rs +0 -0
  98. {ferogram-0.3.0 → ferogram-0.4.0}/src/updates.rs +0 -0
@@ -0,0 +1,146 @@
1
+ name: Compile Check
2
+
3
+ on:
4
+ workflow_dispatch:
5
+ inputs:
6
+ ref:
7
+ description: "Commit hash, branch, tag, or PR (e.g. abc1234 / main / refs/pull/12/head)"
8
+ required: false
9
+ default: "main"
10
+ target:
11
+ description: "Target platform to check"
12
+ required: true
13
+ default: linux-x86_64
14
+ type: choice
15
+ options:
16
+ - linux-x86_64
17
+ - linux-aarch64
18
+ - android-aarch64
19
+ - all
20
+
21
+ jobs:
22
+
23
+ linux-x86_64:
24
+ if: inputs.target == 'linux-x86_64' || inputs.target == 'all'
25
+ runs-on: ubuntu-latest
26
+ steps:
27
+ - uses: actions/checkout@v4
28
+ with:
29
+ ref: ${{ inputs.ref }}
30
+
31
+ - uses: actions/setup-python@v5
32
+ with:
33
+ python-version: "3.13"
34
+
35
+ - uses: Swatinem/rust-cache@v2
36
+ with:
37
+ key: compile-check-x86_64
38
+
39
+ - name: Install maturin
40
+ run: pip install maturin
41
+
42
+ - name: Build (fast flags)
43
+ env:
44
+ RUSTFLAGS: "-C codegen-units=256 -C debuginfo=0"
45
+ run: maturin build --out dist
46
+
47
+ - name: Install wheel
48
+ run: pip install dist/*.whl --force-reinstall
49
+
50
+ - name: Smoke test
51
+ run: |
52
+ python3 -c "
53
+ from ferogram import (
54
+ Client, StopPropagation, ContinuePropagation, filters,
55
+ User, Dialog, ChatMember, Message,
56
+ InlineButton, InlineKeyboard,
57
+ )
58
+ print('imports ok')
59
+ "
60
+
61
+ linux-aarch64:
62
+ if: inputs.target == 'linux-aarch64' || inputs.target == 'all'
63
+ runs-on: ubuntu-latest
64
+ steps:
65
+ - uses: actions/checkout@v4
66
+ with:
67
+ ref: ${{ inputs.ref }}
68
+
69
+ - uses: actions/setup-python@v5
70
+ with:
71
+ python-version: "3.13"
72
+
73
+ - uses: Swatinem/rust-cache@v2
74
+ with:
75
+ key: compile-check-aarch64
76
+
77
+ - name: Install maturin
78
+ run: pip install maturin
79
+
80
+ - name: Build (fast flags)
81
+ env:
82
+ RUSTFLAGS: "-C codegen-units=256 -C debuginfo=0 -D__ARM_ARCH=8 -march=armv8-a"
83
+ run: maturin build --target aarch64-unknown-linux-gnu --out dist
84
+
85
+ android-aarch64:
86
+ if: inputs.target == 'android-aarch64' || inputs.target == 'all'
87
+ runs-on: ubuntu-latest
88
+ steps:
89
+ - uses: actions/checkout@v4
90
+ with:
91
+ ref: ${{ inputs.ref }}
92
+
93
+ - uses: actions/setup-python@v5
94
+ with:
95
+ python-version: "3.13"
96
+
97
+ - name: Setup Android NDK r26d
98
+ uses: nttld/setup-ndk@v1
99
+ id: ndk
100
+ with:
101
+ ndk-version: r26d
102
+ link-to-sdk: true
103
+
104
+ - uses: Swatinem/rust-cache@v2
105
+ with:
106
+ key: compile-check-android-aarch64
107
+
108
+ - name: Add Rust Android target
109
+ run: rustup target add aarch64-linux-android
110
+
111
+ - name: Install maturin
112
+ run: pip install maturin
113
+
114
+ - name: Fetch Termux libpython3.13
115
+ run: |
116
+ PKGS_URL="https://packages.termux.dev/apt/termux-main/dists/stable/main/binary-aarch64/Packages"
117
+ DEB_PATH=$(curl -sL "$PKGS_URL" | \
118
+ awk '/^Package: python$/{f=1} f && /^Filename:/{print $2; f=0}' | head -1)
119
+ mkdir -p /tmp/termux-py && cd /tmp/termux-py
120
+ curl -sL "https://packages.termux.dev/apt/termux-main/${DEB_PATH}" -o python.deb
121
+ ar x python.deb
122
+ tar xf data.tar.* --wildcards "*/libpython3.13*" 2>/dev/null || true
123
+ LIB_DIR=/tmp/termux-py/data/data/com.termux/files/usr/lib
124
+ if [ ! -f "$LIB_DIR/libpython3.13.so" ]; then
125
+ ln -sf "$(basename $(ls $LIB_DIR/libpython3.13.so* | head -1))" \
126
+ "$LIB_DIR/libpython3.13.so"
127
+ fi
128
+ echo "TERMUX_LIBDIR=$LIB_DIR" >> $GITHUB_ENV
129
+
130
+ - name: Build Android wheel (fast flags)
131
+ env:
132
+ ANDROID_NDK_HOME: ${{ steps.ndk.outputs.ndk-path }}
133
+ ANDROID_API_LEVEL: "24"
134
+ PYO3_CROSS_PYTHON_VERSION: "3.13"
135
+ RUSTFLAGS: "-C codegen-units=256 -C debuginfo=0 -L native=${{ env.TERMUX_LIBDIR }}"
136
+ run: |
137
+ NDK_BIN=$ANDROID_NDK_HOME/toolchains/llvm/prebuilt/linux-x86_64/bin
138
+ export CC_aarch64_linux_android=$NDK_BIN/aarch64-linux-android24-clang
139
+ export CXX_aarch64_linux_android=$NDK_BIN/aarch64-linux-android24-clang++
140
+ export AR_aarch64_linux_android=$NDK_BIN/llvm-ar
141
+ export CARGO_TARGET_AARCH64_LINUX_ANDROID_LINKER=$NDK_BIN/aarch64-linux-android24-clang
142
+ maturin build \
143
+ --release \
144
+ --target aarch64-linux-android \
145
+ --compatibility off \
146
+ --out dist
@@ -1,3 +1,43 @@
1
+ ## 0.4.0 (2026-06-01)
2
+
3
+ ### Added
4
+
5
+ - **Session backends** - `FileSession`, `MemorySession`, `StringSession`, `SqliteSession`, `LibSqlSession`, and `CustomSession` are now first-class types importable from `ferogram`. Pass any of them as the `session` argument to `Client`. Plain string names still work as before.
6
+ - `SqliteSession("name")` stores the session in a SQLite database.
7
+ - `MemorySession()` keeps the session in memory only; nothing is written to disk.
8
+ - `StringSession("AQA...")` resumes from a base64 string, useful for serverless or env-var based deployments.
9
+ - `LibSqlSession.local/remote/replica/memory(...)` targets a local file, remote Turso database, embedded replica, or in-memory libSQL database.
10
+ - `CustomSession(obj)` wraps any Python object implementing `save(bytes)`, `load() -> bytes | None`, and `delete()`.
11
+ - **`channel_kind()` on Message** - `await msg.channel_kind()` returns `"megagroup"`, `"broadcast"`, `"gigagroup"`, or `None`. Uses the peer cache; no RPC.
12
+ - **`is_megagroup()` on Message** - `await msg.is_megagroup()` returns `True` for supergroups.
13
+ - **`is_broadcast()` on Message** - `await msg.is_broadcast()` returns `True` for broadcast channels.
14
+ - **`StopPropagation` and `ContinuePropagation`** - two exceptions exported from `ferogram` to control handler dispatch. `StopPropagation` stops all further group processing. `ContinuePropagation` skips the current handler and continues to the next match in the same group.
15
+ - **Handler groups** - all `on_*` decorators now accept `group: int = 0`. Handlers run in ascending group order; lower group numbers run first.
16
+ - **`add_handler` / `remove_handler`** - register and deregister handlers at runtime without decorators.
17
+ - **Worker pool** - a fixed pool of `workers` coroutines (default 4) now dispatches updates from a bounded `asyncio.Queue`. Replaces the old unbounded `asyncio.create_task` approach. Provides natural backpressure under load.
18
+ - **`workers` kwarg on `Client`** - controls pool size.
19
+ - **`parse_mode` kwarg on `Client`** - sets a global default parse mode applied to every `send_message` call that does not pass its own `parse_mode`.
20
+ - **`flood_sleep_threshold` kwarg on `Client`** - maps to the `AutoSleep` retry policy in the Rust core. Flood waits under this value are slept through automatically; waits above it are raised as exceptions.
21
+ - **`download_with_progress(peer, msg_id, path, on_progress)`** - download media with a progress callback `on_progress(done, total)`.
22
+ - **`upload_with_progress(path, on_progress)`** - upload a file with a progress callback. Returns a handle string accepted by `send_file`.
23
+ - **`ferogram` 0.6.0 as core dependency** - includes `Client.channel_kind_of(channel_id)` which backs the new `Message` methods above.
24
+
25
+ ### Changed
26
+
27
+ - `no_webpage` now defaults to `True` in `send_message` and `edit_message`.
28
+ - `upload_file(data, name, mime)` replaced by `upload(Cursor(data), name)` internally; no change to the Python API.
29
+ - Session resolution order is now `session_string > session object`. `in_memory=True` is deprecated in favor of `MemorySession()`.
30
+ - Handler storage changed from `list` to `dict[group, list]`; dispatch now iterates groups in sorted order.
31
+ - `_resolve_pm` is now used internally to merge per-call and global `parse_mode`.
32
+
33
+ ### Fixed
34
+
35
+ - `channel_kind`, `is_megagroup`, `is_broadcast` on `Message` no longer call `get_chat_full` (an RPC) on every invocation. They read from the peer cache via `Client.channel_kind_of`.
36
+ - Unnecessary `as i64` casts removed from `message.rs`.
37
+ - Nested `if let` blocks collapsed to `if let ... && ...`.
38
+ - `match ... { Some(m) => m, None => return None }` replaced with `as_ref()?`.
39
+
40
+
1
41
  ## 0.3.0 (2026-05-16)
2
42
 
3
43
  ### ferogram core upgraded to 0.5.0