tlgr-cli 2.0.1__py3-none-any.whl

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 (192) hide show
  1. tlgr/__init__.py +3 -0
  2. tlgr/__main__.py +6 -0
  3. tlgr/actions/__init__.py +45 -0
  4. tlgr/actions/forward.py +74 -0
  5. tlgr/actions/reply.py +32 -0
  6. tlgr/cli/__init__.py +259 -0
  7. tlgr/cli/confirm.py +55 -0
  8. tlgr/cli/errors.py +84 -0
  9. tlgr/cli/gen.py +690 -0
  10. tlgr/cli/globals.py +273 -0
  11. tlgr/cli/introspect.py +170 -0
  12. tlgr/cli/params.py +189 -0
  13. tlgr/cli/render.py +418 -0
  14. tlgr/core/__init__.py +0 -0
  15. tlgr/core/accounts.py +384 -0
  16. tlgr/core/config.py +358 -0
  17. tlgr/core/custom_tl.py +170 -0
  18. tlgr/core/errors.py +687 -0
  19. tlgr/core/eventtypes.py +1170 -0
  20. tlgr/core/identity.py +127 -0
  21. tlgr/core/launchd.py +122 -0
  22. tlgr/core/logging.py +194 -0
  23. tlgr/core/media.py +134 -0
  24. tlgr/core/output.py +251 -0
  25. tlgr/core/pagination.py +227 -0
  26. tlgr/core/paths.py +360 -0
  27. tlgr/core/peers.py +427 -0
  28. tlgr/core/process.py +138 -0
  29. tlgr/core/signing.py +38 -0
  30. tlgr/core/systemd.py +96 -0
  31. tlgr/core/telethon_compat.py +295 -0
  32. tlgr/core/text.py +211 -0
  33. tlgr/core/timefmt.py +199 -0
  34. tlgr/core/tl.py +98 -0
  35. tlgr/daemon/__init__.py +0 -0
  36. tlgr/daemon/app.py +869 -0
  37. tlgr/daemon/dispatch.py +446 -0
  38. tlgr/daemon/events.py +723 -0
  39. tlgr/daemon/files.py +431 -0
  40. tlgr/daemon/idle.py +119 -0
  41. tlgr/daemon/jobs.py +68 -0
  42. tlgr/daemon/main.py +161 -0
  43. tlgr/daemon/peercred.py +75 -0
  44. tlgr/daemon/policy.py +113 -0
  45. tlgr/daemon/preauth.py +366 -0
  46. tlgr/daemon/ratelimit.py +391 -0
  47. tlgr/daemon/server.py +24 -0
  48. tlgr/daemon/session.py +648 -0
  49. tlgr/daemon/sessions.py +274 -0
  50. tlgr/daemon/singleton.py +114 -0
  51. tlgr/daemon/stream.py +193 -0
  52. tlgr/daemon/transfers.py +219 -0
  53. tlgr/daemon/webhook.py +390 -0
  54. tlgr/data/catalog_index.json +1 -0
  55. tlgr/data/parity_waivers.toml +90 -0
  56. tlgr/filters/__init__.py +42 -0
  57. tlgr/filters/compose.py +121 -0
  58. tlgr/filters/content.py +85 -0
  59. tlgr/filters/context.py +114 -0
  60. tlgr/filters/message.py +161 -0
  61. tlgr/filters/temporal.py +87 -0
  62. tlgr/filters/user.py +36 -0
  63. tlgr/gateway/__init__.py +1 -0
  64. tlgr/gateway/config.py +161 -0
  65. tlgr/gateway/engine.py +215 -0
  66. tlgr/gateway/event.py +22 -0
  67. tlgr/jobs/__init__.py +0 -0
  68. tlgr/jobs/base.py +81 -0
  69. tlgr/jobs/client.py +37 -0
  70. tlgr/models/__init__.py +1220 -0
  71. tlgr/models/admin.py +744 -0
  72. tlgr/models/auth.py +510 -0
  73. tlgr/models/base.py +81 -0
  74. tlgr/models/bot.py +576 -0
  75. tlgr/models/business.py +265 -0
  76. tlgr/models/call.py +586 -0
  77. tlgr/models/config.py +101 -0
  78. tlgr/models/contact.py +481 -0
  79. tlgr/models/daemon.py +336 -0
  80. tlgr/models/dialog.py +626 -0
  81. tlgr/models/envelope.py +68 -0
  82. tlgr/models/error.py +30 -0
  83. tlgr/models/event.py +79 -0
  84. tlgr/models/export.py +66 -0
  85. tlgr/models/gift.py +275 -0
  86. tlgr/models/inline.py +84 -0
  87. tlgr/models/location.py +115 -0
  88. tlgr/models/media.py +507 -0
  89. tlgr/models/message.py +584 -0
  90. tlgr/models/net.py +232 -0
  91. tlgr/models/notify.py +105 -0
  92. tlgr/models/page.py +32 -0
  93. tlgr/models/payment.py +172 -0
  94. tlgr/models/peer.py +400 -0
  95. tlgr/models/poll.py +119 -0
  96. tlgr/models/premium.py +161 -0
  97. tlgr/models/privacy.py +93 -0
  98. tlgr/models/profile.py +217 -0
  99. tlgr/models/reaction.py +160 -0
  100. tlgr/models/resolve.py +175 -0
  101. tlgr/models/settings.py +103 -0
  102. tlgr/models/stars.py +101 -0
  103. tlgr/models/sticker.py +243 -0
  104. tlgr/models/story.py +467 -0
  105. tlgr/models/sync.py +105 -0
  106. tlgr/models/todo.py +36 -0
  107. tlgr/models/webapp.py +89 -0
  108. tlgr/ops/__init__.py +63 -0
  109. tlgr/ops/_admin.py +313 -0
  110. tlgr/ops/_auth.py +599 -0
  111. tlgr/ops/_bots.py +586 -0
  112. tlgr/ops/_calls.py +535 -0
  113. tlgr/ops/_common.py +160 -0
  114. tlgr/ops/_layer.py +46 -0
  115. tlgr/ops/_media.py +592 -0
  116. tlgr/ops/_params.py +212 -0
  117. tlgr/ops/_rights.py +402 -0
  118. tlgr/ops/_send.py +593 -0
  119. tlgr/ops/_serialize.py +667 -0
  120. tlgr/ops/_settings.py +306 -0
  121. tlgr/ops/_spec.py +167 -0
  122. tlgr/ops/_story.py +743 -0
  123. tlgr/ops/account.py +2604 -0
  124. tlgr/ops/agent.py +937 -0
  125. tlgr/ops/auth.py +1282 -0
  126. tlgr/ops/bot.py +4880 -0
  127. tlgr/ops/business.py +1520 -0
  128. tlgr/ops/call.py +1610 -0
  129. tlgr/ops/chat.py +4025 -0
  130. tlgr/ops/chat_admin.py +929 -0
  131. tlgr/ops/chat_extra.py +1061 -0
  132. tlgr/ops/chat_invite.py +716 -0
  133. tlgr/ops/chat_manage.py +1691 -0
  134. tlgr/ops/chat_member.py +1357 -0
  135. tlgr/ops/chat_stats.py +902 -0
  136. tlgr/ops/chat_topic.py +905 -0
  137. tlgr/ops/conference.py +791 -0
  138. tlgr/ops/config.py +1698 -0
  139. tlgr/ops/contact.py +2330 -0
  140. tlgr/ops/daemon.py +1397 -0
  141. tlgr/ops/draft.py +299 -0
  142. tlgr/ops/emoji.py +343 -0
  143. tlgr/ops/events.py +1327 -0
  144. tlgr/ops/export.py +596 -0
  145. tlgr/ops/folder.py +1322 -0
  146. tlgr/ops/gif.py +522 -0
  147. tlgr/ops/gift.py +1546 -0
  148. tlgr/ops/giveaway.py +541 -0
  149. tlgr/ops/inline.py +773 -0
  150. tlgr/ops/job.py +799 -0
  151. tlgr/ops/location.py +917 -0
  152. tlgr/ops/media.py +4495 -0
  153. tlgr/ops/message.py +3769 -0
  154. tlgr/ops/net.py +536 -0
  155. tlgr/ops/notify.py +840 -0
  156. tlgr/ops/passport.py +464 -0
  157. tlgr/ops/payment.py +907 -0
  158. tlgr/ops/poll.py +1078 -0
  159. tlgr/ops/premium.py +488 -0
  160. tlgr/ops/privacy.py +794 -0
  161. tlgr/ops/profile.py +1481 -0
  162. tlgr/ops/proxy.py +750 -0
  163. tlgr/ops/reaction.py +1475 -0
  164. tlgr/ops/resolve.py +1140 -0
  165. tlgr/ops/search.py +521 -0
  166. tlgr/ops/settings.py +1066 -0
  167. tlgr/ops/stars.py +594 -0
  168. tlgr/ops/sticker.py +1602 -0
  169. tlgr/ops/story.py +3216 -0
  170. tlgr/ops/sync.py +788 -0
  171. tlgr/ops/todo.py +514 -0
  172. tlgr/ops/user.py +1406 -0
  173. tlgr/ops/vc.py +2351 -0
  174. tlgr/ops/webapp.py +717 -0
  175. tlgr/ops/webhook.py +418 -0
  176. tlgr/parity.py +386 -0
  177. tlgr/processors/__init__.py +125 -0
  178. tlgr/processors/regex.py +26 -0
  179. tlgr/processors/text.py +56 -0
  180. tlgr/registry.py +519 -0
  181. tlgr/schema.py +173 -0
  182. tlgr/transport/__init__.py +30 -0
  183. tlgr/transport/autostart.py +293 -0
  184. tlgr/transport/client.py +805 -0
  185. tlgr/transport/ndjson.py +44 -0
  186. tlgr/version.py +31 -0
  187. tlgr_cli-2.0.1.dist-info/METADATA +957 -0
  188. tlgr_cli-2.0.1.dist-info/RECORD +192 -0
  189. tlgr_cli-2.0.1.dist-info/WHEEL +5 -0
  190. tlgr_cli-2.0.1.dist-info/entry_points.txt +2 -0
  191. tlgr_cli-2.0.1.dist-info/licenses/LICENSE +21 -0
  192. tlgr_cli-2.0.1.dist-info/top_level.txt +1 -0
tlgr/models/daemon.py ADDED
@@ -0,0 +1,336 @@
1
+ """Daemon, job, flood and dead-letter shapes.
2
+
3
+ Everything an operator reads when something is wrong. Two of these deserve a
4
+ note:
5
+
6
+ * `AccountHealth.state` is a **state machine**, not a boolean. v1 reported
7
+ which clients the daemon held, so an account whose connection had died
8
+ still appeared in `accounts` and the daemon still called itself healthy
9
+ (COR-13/COR-37). `state` plus `behind_seconds` is what makes "alive" and
10
+ "working" separable.
11
+ * `FloodRecord` exists because a flood deadline outlives a process. Telethon
12
+ remembers one in memory and forgets it on exit, so v1 re-hit every wait
13
+ after a restart — and re-hitting a wait is how a short one becomes long.
14
+ """
15
+
16
+ from __future__ import annotations
17
+
18
+ from typing import Any
19
+
20
+ from tlgr.models.base import Model
21
+
22
+ __all__ = [
23
+ "AccountHealth",
24
+ "DaemonStatus",
25
+ "DeadLetter",
26
+ "DeadLetterResult",
27
+ "EventBusStatus",
28
+ "FloodRecord",
29
+ "FloodResult",
30
+ "HealthSummary",
31
+ "Job",
32
+ "JobState",
33
+ "JobTestFrame",
34
+ "LifecycleResult",
35
+ "LogLine",
36
+ "ReconnectResult",
37
+ "ReconnectedAccount",
38
+ "SaveStateResult",
39
+ "SavedState",
40
+ "ServiceResult",
41
+ "WebhookProbe",
42
+ "WebhookSettings",
43
+ ]
44
+
45
+
46
+ class AccountHealth(Model):
47
+ """One account's connection and sync health."""
48
+
49
+ alias: str
50
+ state: str = "unknown"
51
+ user_id: int | None = None
52
+ username: str | None = None
53
+ dc_id: int | None = None
54
+ proxy: str | None = None
55
+ ping_ms: float | None = None
56
+ pts: int | None = None
57
+ qts: int | None = None
58
+ seq: int | None = None
59
+ date: str | None = None
60
+ behind_seconds: int | None = None
61
+ catching_up: bool = False
62
+ channels_tracked: int = 0
63
+ last_update_at: str | None = None
64
+ connected_since: str | None = None
65
+ reconnects: int = 0
66
+ in_flight: int = 0
67
+ resync_needed: list[int] = []
68
+ flood_waits: int = 0
69
+ circuit: str = "closed"
70
+ frozen: bool = False
71
+ error: str | None = None
72
+
73
+
74
+ class EventBusStatus(Model):
75
+ buffered: int = 0
76
+ oldest_seq: int | None = None
77
+ last_seq: int = 0
78
+ subscribers: int = 0
79
+ dropped: int = 0
80
+
81
+
82
+ class DaemonStatus(Model, omit_defaults=False):
83
+ """`tlgr daemon status`. `running` and `healthy` are different questions.
84
+
85
+ `omit_defaults=False` for the whole struct: the answer this operation
86
+ exists to give is "no", and `omit_defaults` drops every false and every
87
+ zero — so a stopped daemon serialised to `{}`, which printed nothing at
88
+ all in human mode and made `status["running"]` a KeyError for the exact
89
+ caller the flag is for. v1 printed `RUNNING false`; a field here is
90
+ always present, whichever way the answer went.
91
+ """
92
+
93
+ running: bool = False
94
+ ready: bool = False
95
+ healthy: bool = False
96
+ pid: int | None = None
97
+ uptime_seconds: int = 0
98
+ #: `None` rather than `""` when the daemon is not answering: nobody read
99
+ #: a version off a process that is not there.
100
+ version: str | None = None
101
+ protocol: int = 0
102
+ layer: int = 0
103
+ socket: str = ""
104
+ socket_owner: int | None = None
105
+ managed_by: str | None = None
106
+ accounts: list[AccountHealth] = []
107
+ events: EventBusStatus | None = None
108
+ webhook: dict[str, Any] = {}
109
+ jobs: list[dict[str, Any]] = []
110
+ # v1's `/daemon/status` carried these two, and AGENT.md documents them.
111
+ connections: dict[str, bool] = {}
112
+ disconnected: list[str] = []
113
+
114
+
115
+ class HealthSummary(Model, omit_defaults=False):
116
+ """`tlgr status`: one screen, the states where everything else fails.
117
+
118
+ `omit_defaults=False` for the same reason as `DaemonStatus`: this screen
119
+ is read when nothing works, which is precisely when every answer on it is
120
+ false — and a screen that prints only the fields that happened to be true
121
+ is at its least useful exactly then.
122
+ """
123
+
124
+ account: str = ""
125
+ user_id: int | None = None
126
+ username: str | None = None
127
+ authorized: bool = False
128
+ connected: bool = False
129
+ dc_id: int | None = None
130
+ proxy: str | None = None
131
+ ping_ms: float | None = None
132
+ layer: int = 0
133
+ behind_seconds: int | None = None
134
+ daemon_running: bool = False
135
+ daemon_healthy: bool = False
136
+ jobs_running: int = 0
137
+ webhook_enabled: bool = False
138
+ flood_waits: int = 0
139
+ frozen: dict[str, Any] = {}
140
+ unconfirmed_sessions: int = 0
141
+ terms_pending: bool = False
142
+ problems: list[str] = []
143
+
144
+
145
+ class LifecycleResult(Model):
146
+ """`daemon start` / `stop` / `restart`."""
147
+
148
+ started: bool = False
149
+ stopped: bool = False
150
+ restarted: bool = False
151
+ already: bool = False
152
+ pid: int | None = None
153
+ socket: str = ""
154
+ ready: bool = False
155
+ accounts: list[str] = []
156
+ catch_up: bool = True
157
+
158
+
159
+ class ServiceResult(Model):
160
+ """`daemon install` / `uninstall`."""
161
+
162
+ installed: bool = False
163
+ uninstalled: bool = False
164
+ already: bool = False
165
+ supervisor: str = ""
166
+ unit: str = ""
167
+ path: str = ""
168
+ stopped: bool = False
169
+
170
+
171
+ class LogLine(Model):
172
+ ts: str = ""
173
+ level: str = ""
174
+ account: str | None = None
175
+ logger: str = ""
176
+ message: str = ""
177
+ raw: str = ""
178
+
179
+
180
+ class ReconnectedAccount(Model):
181
+ alias: str
182
+ reconnected: bool = False
183
+ dc_id: int | None = None
184
+ caught_up: bool = False
185
+ error: str | None = None
186
+
187
+
188
+ class ReconnectResult(Model):
189
+ accounts: list[ReconnectedAccount] = []
190
+
191
+
192
+ class SavedState(Model):
193
+ alias: str
194
+ pts: int | None = None
195
+ qts: int | None = None
196
+ seq: int | None = None
197
+ date: str | None = None
198
+ channels: int = 0
199
+ entities: int = 0
200
+ error: str | None = None
201
+
202
+
203
+ class SaveStateResult(Model):
204
+ accounts: list[SavedState] = []
205
+
206
+
207
+ class FloodRecord(Model):
208
+ """One remembered rate-limit deadline."""
209
+
210
+ account: str
211
+ #: No default: `Model` omits a field equal to its default, and a record
212
+ #: whose kind is absent reads as one that has no kind.
213
+ kind: str
214
+ method: str = ""
215
+ chat: str | None = None
216
+ wait_seconds: int = 0
217
+ until: str | None = None
218
+ hits: int = 1
219
+ circuit_open: bool = False
220
+ expired: bool = False
221
+
222
+
223
+ class FloodResult(Model):
224
+ cleared: int = 0
225
+ circuit_open: bool = False
226
+ accounts: list[str] = []
227
+
228
+
229
+ class DeadLetter(Model):
230
+ """An event a consumer could not be given."""
231
+
232
+ id: str
233
+ seq: int = 0
234
+ source: str = "webhook"
235
+ event: str = ""
236
+ account: str = ""
237
+ chat_id: int | None = None
238
+ attempts: int = 1
239
+ last_error: str = ""
240
+ first_failed_at: str = ""
241
+ last_failed_at: str = ""
242
+
243
+
244
+ class DeadLetterResult(Model):
245
+ attempted: int = 0
246
+ delivered: int = 0
247
+ failed: int = 0
248
+ deleted: int = 0
249
+ remaining: int = 0
250
+ dry_run: bool = False
251
+
252
+
253
+ class JobState(Model):
254
+ """One gateway job."""
255
+
256
+ name: str
257
+ account: str = ""
258
+ enabled: bool = True
259
+ running: bool = False
260
+ events: list[str] = []
261
+ filters: dict[str, Any] = {}
262
+ processors: list[str] = []
263
+ actions: list[dict[str, Any]] = []
264
+ matched: int = 0
265
+ skipped: int = 0
266
+ actions_run: int = 0
267
+ errors: int = 0
268
+ last_match_at: str | None = None
269
+ last_error: str | None = None
270
+
271
+
272
+ class Job(Model):
273
+ """The result of a job mutation."""
274
+
275
+ name: str
276
+ #: No default at all: this is the answer `job enable`/`job disable` was
277
+ #: asked for, and `Model` drops a field equal to its default — so either
278
+ #: value would sometimes be missing from the reply.
279
+ enabled: bool
280
+ account: str = ""
281
+ events: list[str] = []
282
+ removed: bool = False
283
+ reloaded: bool = False
284
+ already: bool = False
285
+ loaded: int = 0
286
+ added: list[str] = []
287
+ removed_names: list[str] = []
288
+ changed: list[str] = []
289
+ errors: list[str] = []
290
+
291
+
292
+ class JobTestFrame(Model):
293
+ """One event fed through a job, and what the pipeline decided."""
294
+
295
+ seq: int = 0
296
+ event: str = ""
297
+ matched: bool = False
298
+ filter_trace: list[str] = []
299
+ processed_text: str | None = None
300
+ actions: list[dict[str, Any]] = []
301
+
302
+
303
+ class WebhookSettings(Model):
304
+ """`tlgr webhook get` / `set`. Secrets are redacted unless asked for."""
305
+
306
+ enabled: bool = False
307
+ url: str = ""
308
+ events: list[str] = []
309
+ filters: dict[str, Any] = {}
310
+ sign: str = "hmac-sha256"
311
+ secret: str | None = None
312
+ token: str | None = None
313
+ max_attempts: int = 5
314
+ backoff: int = 2
315
+ timeout: int = 30
316
+ queue: int = 10000
317
+ on_lag: str = "drop"
318
+ batch: int = 1
319
+ last_delivery_at: str | None = None
320
+ last_status: int | None = None
321
+ delivered: int = 0
322
+ failed: int = 0
323
+ dead_letters: int = 0
324
+ queue_depth: int = 0
325
+ last_seq: int = 0
326
+
327
+
328
+ class WebhookProbe(Model):
329
+ """`tlgr webhook test`: the exact request a receiver would have to verify."""
330
+
331
+ url: str = ""
332
+ status: int | None = None
333
+ latency_ms: int = 0
334
+ request_headers: dict[str, str] = {}
335
+ body: str = ""
336
+ error: str | None = None