warp-beacon 2.8.14__tar.gz → 2.8.16__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 (74) hide show
  1. {warp_beacon-2.8.14/warp_beacon.egg-info → warp_beacon-2.8.16}/PKG-INFO +1 -1
  2. warp_beacon-2.8.16/warp_beacon/__version__.py +2 -0
  3. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/__init__.py +1 -1
  4. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/fail_handler.py +22 -3
  5. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/bot.py +2 -1
  6. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/handlers.py +0 -13
  7. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/uploader/__init__.py +48 -73
  8. {warp_beacon-2.8.14 → warp_beacon-2.8.16/warp_beacon.egg-info}/PKG-INFO +1 -1
  9. warp_beacon-2.8.14/warp_beacon/__version__.py +0 -2
  10. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/LICENSE +0 -0
  11. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/MANIFEST.in +0 -0
  12. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/README.md +0 -0
  13. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/assets/cc-group-black.png +0 -0
  14. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/assets/placeholder.gif +0 -0
  15. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/etc/.gitignore +0 -0
  16. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/etc/accounts.json +0 -0
  17. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/etc/proxies.json +0 -0
  18. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/etc/warp_beacon.conf +0 -0
  19. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/etc/warp_beacon.service +0 -0
  20. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/pyproject.toml +0 -0
  21. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/setup.cfg +0 -0
  22. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/setup.py +0 -0
  23. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/__init__.py +0 -0
  24. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/compress/__init__.py +0 -0
  25. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/compress/video.py +0 -0
  26. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/jobs/__init__.py +0 -0
  27. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/jobs/abstract.py +0 -0
  28. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/jobs/download_job.py +0 -0
  29. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/jobs/types.py +0 -0
  30. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/jobs/upload_job.py +0 -0
  31. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/mediainfo/__init__.py +0 -0
  32. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/mediainfo/abstract.py +0 -0
  33. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/mediainfo/audio.py +0 -0
  34. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/mediainfo/silencer.py +0 -0
  35. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/mediainfo/video.py +0 -0
  36. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scheduler/__init__.py +0 -0
  37. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scheduler/instagram_human.py +0 -0
  38. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scheduler/scheduler.py +0 -0
  39. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/X/X.py +0 -0
  40. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/X/__init__.py +0 -0
  41. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/X/abstract.py +0 -0
  42. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/X/types.py +0 -0
  43. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/abstract.py +0 -0
  44. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/account_selector.py +0 -0
  45. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/exceptions.py +0 -0
  46. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/instagram/__init__.py +0 -0
  47. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/instagram/captcha.py +0 -0
  48. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/instagram/instagram.py +0 -0
  49. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/instagram/wb_instagrapi.py +0 -0
  50. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/link_resolver.py +0 -0
  51. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/utils.py +0 -0
  52. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/youtube/__init__.py +0 -0
  53. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/youtube/abstract.py +0 -0
  54. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/youtube/music.py +0 -0
  55. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/youtube/shorts.py +0 -0
  56. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/scraper/youtube/youtube.py +0 -0
  57. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/storage/__init__.py +0 -0
  58. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/storage/mongo.py +0 -0
  59. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/__init__.py +0 -0
  60. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/caption_shortener.py +0 -0
  61. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/download_status.py +0 -0
  62. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/edit_message.py +0 -0
  63. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/placeholder_message.py +0 -0
  64. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/progress_bar.py +0 -0
  65. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/progress_file_reader.py +0 -0
  66. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/types.py +0 -0
  67. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/telegram/utils.py +0 -0
  68. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/warp_beacon.py +0 -0
  69. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon/yt_auth.py +0 -0
  70. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon.egg-info/SOURCES.txt +0 -0
  71. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon.egg-info/dependency_links.txt +0 -0
  72. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon.egg-info/entry_points.txt +0 -0
  73. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon.egg-info/requires.txt +0 -0
  74. {warp_beacon-2.8.14 → warp_beacon-2.8.16}/warp_beacon.egg-info/top_level.txt +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: warp_beacon
3
- Version: 2.8.14
3
+ Version: 2.8.16
4
4
  Summary: Telegram bot for expanding external media links
5
5
  Home-page: https://github.com/sb0y/warp_beacon
6
6
  Author: Andrey Bagrintsev
@@ -0,0 +1,2 @@
1
+ __version__ = "2.8.16"
2
+
@@ -318,7 +318,7 @@ class AsyncDownloader(object):
318
318
  if items:
319
319
  # success
320
320
  for job in fail_handler.get_failed_jobs():
321
- self.queue_task(job)
321
+ self.queue_task(job["job"])
322
322
  # media info processing
323
323
  for item in items:
324
324
  media_info = {"filesize": 0}
@@ -16,12 +16,15 @@ class FailHandler(object):
16
16
  self.client.close()
17
17
 
18
18
  def store_failed_job(self, job: DownloadJob) -> int:
19
- db_id = -1
19
+ db_id = ""
20
20
  try:
21
21
  job_serilized = pickle.dumps(job)
22
22
  db_id = self.db.insert_one(
23
23
  {
24
- "job_data": job_serilized
24
+ "job_data": job_serilized,
25
+ "uniq_id": job.uniq_id,
26
+ "message_id": job.message_id,
27
+ "chat_id": job.chat_id
25
28
  }).inserted_id
26
29
  except Exception as e:
27
30
  logging.error("Failed to store job as failed!")
@@ -33,10 +36,26 @@ class FailHandler(object):
33
36
  try:
34
37
  cursor = self.db.find()
35
38
  for document in cursor:
36
- ret.append(pickle.loads(document["job_data"]))
39
+ ret.append({
40
+ "_id": document["_id"],
41
+ "job": pickle.loads(document["job_data"]),
42
+ "uniq_id": document.get("uniq_id"),
43
+ "message_id": document.get("message_id"),
44
+ "chat_id": document.get("chat_id")
45
+ })
37
46
  if clean:
38
47
  self.db.delete_many({})
39
48
  except Exception as e:
40
49
  logging.error("Failed to get failed jobs!")
41
50
  logging.exception(e)
42
51
  return ret
52
+
53
+ def remove_failed_job(self, uniq_id: str) -> bool:
54
+ try:
55
+ result = self.db.delete_one({"uniq_id": uniq_id})
56
+ if result.deleted_count > 0:
57
+ return True
58
+ except Exception as e:
59
+ logging.error("Failed to remove failed job!", exc_info=e)
60
+
61
+ return False
@@ -69,9 +69,11 @@ class Bot(object):
69
69
  )
70
70
 
71
71
  self.editor = EditMessage(self.client)
72
+ self.handlers = Handlers(self)
72
73
 
73
74
  self.uploader = AsyncUploader(
74
75
  storage=self.storage,
76
+ upload_wrapper=self.handlers.upload_wrapper,
75
77
  admin_message_callback=self.send_text_to_admin,
76
78
  request_yt_auth_callback=self.request_yt_auth,
77
79
  pool_size=int(os.environ.get("UPLOAD_POOL_SIZE", default=workers_amount)),
@@ -85,7 +87,6 @@ class Bot(object):
85
87
  )
86
88
 
87
89
  self.scheduler = IGScheduler(self.downloader)
88
- self.handlers = Handlers(self)
89
90
 
90
91
  self.client.add_handler(MessageHandler(self.handlers.start, filters.command("start")))
91
92
  self.client.add_handler(MessageHandler(self.handlers.help, filters.command("help")))
@@ -14,8 +14,6 @@ from warp_beacon.jobs.upload_job import UploadJob
14
14
  from warp_beacon.jobs import Origin
15
15
  from warp_beacon.jobs.types import JobType
16
16
  from warp_beacon.scraper.link_resolver import LinkResolver
17
- from warp_beacon.scraper.fail_handler import FailHandler
18
- from warp_beacon.storage.mongo import DBClient
19
17
 
20
18
  class Handlers(object):
21
19
  storage = None
@@ -25,12 +23,6 @@ class Handlers(object):
25
23
  def __init__(self, bot: "Bot") -> None:
26
24
  self.bot = bot
27
25
  self.storage = bot.storage
28
- # add uploader callbacks to handle service restart
29
- for job in FailHandler(DBClient()).get_failed_jobs(clean=False):
30
- self.bot.uploader.add_callback(
31
- job.placeholder_message_id,
32
- self.upload_wrapper
33
- )
34
26
 
35
27
  async def help(self, _: Client, message: Message) -> None:
36
28
  """Send a message when the command /help is issued."""
@@ -147,11 +139,6 @@ class Handlers(object):
147
139
  text="Failed to create message placeholder. Please check your bot Internet connection."
148
140
  )
149
141
 
150
- self.bot.uploader.add_callback(
151
- job.placeholder_message_id,
152
- self.upload_wrapper
153
- )
154
-
155
142
  self.bot.downloader.queue_task(job)
156
143
  except Exception as e:
157
144
  logging.error("Failed to schedule download task!")
@@ -12,26 +12,17 @@ from warp_beacon.storage import Storage
12
12
 
13
13
  class AsyncUploader(object):
14
14
  __JOE_BIDEN_WAKEUP = None
15
- threads = None
16
- allow_loop = True
17
- job_queue = None
18
- callbacks = None
19
- storage = None
20
- in_process = None
21
- loop = None
22
- admin_message_callback = None
23
- request_yt_auth_callback = None
24
15
  pool_size = 1
25
16
 
26
17
  def __init__(self,
27
18
  loop: asyncio.AbstractEventLoop,
28
19
  storage: Storage,
20
+ upload_wrapper: Callable,
29
21
  admin_message_callback: Callable,
30
22
  request_yt_auth_callback: Callable,
31
23
  pool_size: int=min(32, os.cpu_count() + 4)
32
24
  ) -> None:
33
25
  self.threads = []
34
- self.callbacks = {}
35
26
  self.in_process = set()
36
27
  self.storage = storage
37
28
  self.loop = loop
@@ -39,6 +30,7 @@ class AsyncUploader(object):
39
30
  self.admin_message_callback = admin_message_callback
40
31
  self.request_yt_auth_callback = request_yt_auth_callback
41
32
  self.pool_size = pool_size
33
+ self.upload_wrapper = upload_wrapper
42
34
 
43
35
  def __del__(self) -> None:
44
36
  self.stop_all()
@@ -49,18 +41,6 @@ class AsyncUploader(object):
49
41
  thread.start()
50
42
  self.threads.append(thread)
51
43
 
52
- def add_callback(self, message_id: int, callback: Callable) -> None:
53
- if message_id not in self.callbacks:
54
- async def callback_wrap(*args, **kwargs) -> None:
55
- await callback(*args, **kwargs)
56
- #self.remove_callback(message_id)
57
- self.callbacks[message_id] = {"callback": callback_wrap}
58
-
59
- def remove_callback(self, message_id: int) -> None:
60
- if message_id in self.callbacks:
61
- logging.debug("Removing callback with message id #%d", message_id)
62
- del self.callbacks[message_id]
63
-
64
44
  def stop_all(self) -> None:
65
45
  self.allow_loop = False
66
46
  if self.threads:
@@ -115,7 +95,6 @@ class AsyncUploader(object):
115
95
 
116
96
  in_process = job.in_process
117
97
  uniq_id = job.uniq_id
118
- message_id = job.placeholder_message_id
119
98
 
120
99
  if not in_process and not job.job_failed and not job.job_warning and not job.replay:
121
100
  if job.media_type == JobType.TEXT:
@@ -123,65 +102,61 @@ class AsyncUploader(object):
123
102
  else:
124
103
  logging.info("Accepted upload job, file(s): '%s'", path)
125
104
 
105
+ async def callback_wrap(*args, **kwargs) -> None:
106
+ await self.upload_wrapper(*args, **kwargs)
107
+
126
108
  try:
127
- if message_id in self.callbacks:
128
- if job.job_failed:
129
- logging.info("URL '%s' download failed. Skipping upload job ...", job.url)
130
- if job.job_failed_msg: # we want to say something to user
131
- self.loop.call_soon_threadsafe(
132
- asyncio.create_task,
133
- self.callbacks[message_id]["callback"](job)
134
- )
135
- self.process_done(uniq_id)
136
- self.remove_callback(message_id)
137
- continue
138
-
139
- if job.replay:
109
+ if job.job_failed:
110
+ logging.info("URL '%s' download failed. Skipping upload job ...", job.url)
111
+ if job.job_failed_msg: # we want to say something to user
140
112
  self.loop.call_soon_threadsafe(
141
113
  asyncio.create_task,
142
- self.callbacks[message_id]["callback"](job)
114
+ callback_wrap(job)
143
115
  )
144
- self.remove_callback(message_id)
145
- continue
116
+ self.process_done(uniq_id)
117
+ continue
118
+
119
+ if job.replay:
120
+ self.loop.call_soon_threadsafe(
121
+ asyncio.create_task,
122
+ callback_wrap(job)
123
+ )
124
+ continue
146
125
 
147
- if job.job_warning:
148
- logging.info("Job warning occurred ...")
149
- if job.job_warning_msg:
150
- self.loop.call_soon_threadsafe(
151
- asyncio.create_task,
152
- self.callbacks[message_id]["callback"](job)
153
- )
154
- continue
155
- if in_process:
156
- db_list_dicts = self.storage.db_lookup_id(uniq_id)
157
- if db_list_dicts:
158
- tg_file_ids = [i["tg_file_id"] for i in db_list_dicts]
159
- dlds_len = len(db_list_dicts)
160
- if dlds_len > 1:
161
- job.tg_file_id = ",".join(tg_file_ids)
162
- job.media_type = JobType.COLLECTION
163
- elif dlds_len:
164
- job.tg_file_id = ",".join(tg_file_ids)
165
- db_data = db_list_dicts.pop()
166
- job.media_type = JobType[db_data["media_type"].upper()]
167
- job.canonical_name = db_data.get("canonical_name", "")
168
- self.loop.call_soon_threadsafe(
169
- asyncio.create_task,
170
- self.callbacks[message_id]["callback"](job)
171
- )
172
- self.process_done(uniq_id)
173
- self.remove_callback(message_id)
174
- else:
175
- self.queue_task(job)
176
- else:
126
+ if job.job_warning:
127
+ logging.info("Job warning occurred ...")
128
+ if job.job_warning_msg:
177
129
  self.loop.call_soon_threadsafe(
178
130
  asyncio.create_task,
179
- self.callbacks[message_id]["callback"](job)
131
+ callback_wrap(job)
132
+ )
133
+ continue
134
+ if in_process:
135
+ db_list_dicts = self.storage.db_lookup_id(uniq_id)
136
+ if db_list_dicts:
137
+ tg_file_ids = [i["tg_file_id"] for i in db_list_dicts]
138
+ dlds_len = len(db_list_dicts)
139
+ if dlds_len > 1:
140
+ job.tg_file_id = ",".join(tg_file_ids)
141
+ job.media_type = JobType.COLLECTION
142
+ elif dlds_len:
143
+ job.tg_file_id = ",".join(tg_file_ids)
144
+ db_data = db_list_dicts.pop()
145
+ job.media_type = JobType[db_data["media_type"].upper()]
146
+ job.canonical_name = db_data.get("canonical_name", "")
147
+ self.loop.call_soon_threadsafe(
148
+ asyncio.create_task,
149
+ callback_wrap(job)
180
150
  )
181
151
  self.process_done(uniq_id)
182
- self.remove_callback(message_id)
152
+ else:
153
+ self.queue_task(job)
183
154
  else:
184
- logging.info("No callback no call!!")
155
+ self.loop.call_soon_threadsafe(
156
+ asyncio.create_task,
157
+ callback_wrap(job)
158
+ )
159
+ self.process_done(uniq_id)
185
160
  except Exception as e:
186
161
  logging.exception(e)
187
162
  except Empty:
@@ -189,4 +164,4 @@ class AsyncUploader(object):
189
164
  except Exception as e:
190
165
  logging.error("Exception occurred inside upload worker!")
191
166
  logging.exception(e)
192
- logging.info("Thread done")
167
+ logging.info("Thread done")
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: warp_beacon
3
- Version: 2.8.14
3
+ Version: 2.8.16
4
4
  Summary: Telegram bot for expanding external media links
5
5
  Home-page: https://github.com/sb0y/warp_beacon
6
6
  Author: Andrey Bagrintsev
@@ -1,2 +0,0 @@
1
- __version__ = "2.8.14"
2
-
File without changes
File without changes
File without changes
File without changes
File without changes