StreamingCommunity 2.5.6__py3-none-any.whl → 2.5.8__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.
Potentially problematic release.
This version of StreamingCommunity might be problematic. Click here for more details.
- StreamingCommunity/Api/Player/ddl.py +2 -3
- StreamingCommunity/Api/Site/1337xx/__init__.py +5 -6
- StreamingCommunity/Api/Site/1337xx/site.py +7 -14
- StreamingCommunity/Api/Site/1337xx/title.py +3 -5
- StreamingCommunity/Api/Site/altadefinizionegratis/__init__.py +7 -6
- StreamingCommunity/Api/Site/altadefinizionegratis/film.py +14 -19
- StreamingCommunity/Api/Site/altadefinizionegratis/site.py +6 -14
- StreamingCommunity/Api/Site/animeunity/__init__.py +7 -7
- StreamingCommunity/Api/Site/animeunity/film_serie.py +29 -31
- StreamingCommunity/Api/Site/animeunity/site.py +14 -22
- StreamingCommunity/Api/Site/cb01new/__init__.py +5 -4
- StreamingCommunity/Api/Site/cb01new/film.py +2 -5
- StreamingCommunity/Api/Site/cb01new/site.py +5 -13
- StreamingCommunity/Api/Site/ddlstreamitaly/__init__.py +5 -4
- StreamingCommunity/Api/Site/ddlstreamitaly/series.py +12 -49
- StreamingCommunity/Api/Site/ddlstreamitaly/site.py +6 -16
- StreamingCommunity/Api/Site/ddlstreamitaly/util/ScrapeSerie.py +2 -3
- StreamingCommunity/Api/Site/guardaserie/__init__.py +5 -4
- StreamingCommunity/Api/Site/guardaserie/series.py +12 -46
- StreamingCommunity/Api/Site/guardaserie/site.py +5 -13
- StreamingCommunity/Api/Site/guardaserie/util/ScrapeSerie.py +10 -14
- StreamingCommunity/Api/Site/ilcorsaronero/__init__.py +5 -4
- StreamingCommunity/Api/Site/ilcorsaronero/site.py +5 -13
- StreamingCommunity/Api/Site/ilcorsaronero/title.py +3 -5
- StreamingCommunity/Api/Site/mostraguarda/__init__.py +2 -2
- StreamingCommunity/Api/Site/mostraguarda/film.py +4 -8
- StreamingCommunity/Api/Site/streamingcommunity/__init__.py +8 -7
- StreamingCommunity/Api/Site/streamingcommunity/film.py +14 -18
- StreamingCommunity/Api/Site/streamingcommunity/series.py +25 -76
- StreamingCommunity/Api/Site/streamingcommunity/site.py +11 -23
- StreamingCommunity/Api/Template/Util/__init__.py +8 -1
- StreamingCommunity/Api/Template/Util/manage_ep.py +46 -2
- StreamingCommunity/Api/Template/config_loader.py +71 -0
- StreamingCommunity/Lib/Downloader/HLS/downloader.py +60 -60
- StreamingCommunity/Lib/Downloader/HLS/segments.py +40 -15
- StreamingCommunity/Lib/Downloader/MP4/downloader.py +47 -40
- StreamingCommunity/Lib/FFmpeg/command.py +59 -3
- StreamingCommunity/Lib/M3U8/estimator.py +10 -12
- StreamingCommunity/Lib/M3U8/parser.py +12 -51
- StreamingCommunity/Lib/TMBD/tmdb.py +66 -99
- StreamingCommunity/TelegramHelp/telegram_bot.py +222 -68
- StreamingCommunity/Util/_jsonConfig.py +14 -13
- StreamingCommunity/Util/ffmpeg_installer.py +70 -64
- StreamingCommunity/Util/headers.py +11 -122
- StreamingCommunity/Util/os.py +65 -56
- StreamingCommunity/Util/table.py +62 -108
- StreamingCommunity/run.py +16 -11
- {StreamingCommunity-2.5.6.dist-info → StreamingCommunity-2.5.8.dist-info}/METADATA +57 -23
- StreamingCommunity-2.5.8.dist-info/RECORD +86 -0
- StreamingCommunity/Api/Site/1337xx/costant.py +0 -15
- StreamingCommunity/Api/Site/altadefinizionegratis/costant.py +0 -21
- StreamingCommunity/Api/Site/animeunity/costant.py +0 -21
- StreamingCommunity/Api/Site/cb01new/costant.py +0 -19
- StreamingCommunity/Api/Site/ddlstreamitaly/costant.py +0 -20
- StreamingCommunity/Api/Site/guardaserie/costant.py +0 -19
- StreamingCommunity/Api/Site/ilcorsaronero/costant.py +0 -19
- StreamingCommunity/Api/Site/mostraguarda/costant.py +0 -19
- StreamingCommunity/Api/Site/streamingcommunity/costant.py +0 -21
- StreamingCommunity/TelegramHelp/request_manager.py +0 -82
- StreamingCommunity/TelegramHelp/session.py +0 -56
- StreamingCommunity-2.5.6.dist-info/RECORD +0 -96
- {StreamingCommunity-2.5.6.dist-info → StreamingCommunity-2.5.8.dist-info}/LICENSE +0 -0
- {StreamingCommunity-2.5.6.dist-info → StreamingCommunity-2.5.8.dist-info}/WHEEL +0 -0
- {StreamingCommunity-2.5.6.dist-info → StreamingCommunity-2.5.8.dist-info}/entry_points.txt +0 -0
- {StreamingCommunity-2.5.6.dist-info → StreamingCommunity-2.5.8.dist-info}/top_level.txt +0 -0
|
@@ -6,17 +6,19 @@ from typing import Dict
|
|
|
6
6
|
|
|
7
7
|
# External libraries
|
|
8
8
|
import httpx
|
|
9
|
-
from rich.console import Console
|
|
10
9
|
|
|
11
10
|
|
|
12
11
|
# Internal utilities
|
|
13
12
|
from .obj_tmbd import Json_film
|
|
13
|
+
from StreamingCommunity.Util.console import console
|
|
14
|
+
from StreamingCommunity.Util._jsonConfig import config_manager
|
|
14
15
|
from StreamingCommunity.Util.table import TVShowManager
|
|
15
16
|
|
|
16
17
|
|
|
17
18
|
# Variable
|
|
18
19
|
table_show_manager = TVShowManager()
|
|
19
20
|
api_key = "a800ed6c93274fb857ea61bd9e7256c5"
|
|
21
|
+
MAX_TIMEOUT = config_manager.get_int("REQUESTS", "timeout")
|
|
20
22
|
|
|
21
23
|
|
|
22
24
|
|
|
@@ -33,7 +35,7 @@ def get_select_title(table_show_manager, generic_obj):
|
|
|
33
35
|
|
|
34
36
|
# Check if the generic_obj list is empty
|
|
35
37
|
if not generic_obj:
|
|
36
|
-
|
|
38
|
+
console.print("\n[red]No media items available.")
|
|
37
39
|
return None
|
|
38
40
|
|
|
39
41
|
# Example of available colors for columns
|
|
@@ -76,7 +78,7 @@ def get_select_title(table_show_manager, generic_obj):
|
|
|
76
78
|
|
|
77
79
|
# Handle user's quit command
|
|
78
80
|
if last_command == "q" or last_command == "quit":
|
|
79
|
-
|
|
81
|
+
console.print("\n[red]Quit [white]...")
|
|
80
82
|
sys.exit(0)
|
|
81
83
|
|
|
82
84
|
# Check if the selected index is within range
|
|
@@ -84,7 +86,7 @@ def get_select_title(table_show_manager, generic_obj):
|
|
|
84
86
|
return generic_obj[int(last_command)]
|
|
85
87
|
|
|
86
88
|
else:
|
|
87
|
-
|
|
89
|
+
console.print("\n[red]Wrong index")
|
|
88
90
|
sys.exit(0)
|
|
89
91
|
|
|
90
92
|
|
|
@@ -98,8 +100,9 @@ class TheMovieDB:
|
|
|
98
100
|
"""
|
|
99
101
|
self.api_key = api_key
|
|
100
102
|
self.base_url = "https://api.themoviedb.org/3"
|
|
101
|
-
self.console = Console()
|
|
102
103
|
#self.genres = self._fetch_genres()
|
|
104
|
+
self._cached_trending_tv = None
|
|
105
|
+
self._cached_trending_movies = None
|
|
103
106
|
|
|
104
107
|
def _make_request(self, endpoint, params=None):
|
|
105
108
|
"""
|
|
@@ -117,7 +120,7 @@ class TheMovieDB:
|
|
|
117
120
|
|
|
118
121
|
params['api_key'] = self.api_key
|
|
119
122
|
url = f"{self.base_url}/{endpoint}"
|
|
120
|
-
response = httpx.get(url, params=params)
|
|
123
|
+
response = httpx.get(url, params=params, timeout=MAX_TIMEOUT)
|
|
121
124
|
response.raise_for_status()
|
|
122
125
|
|
|
123
126
|
return response.json()
|
|
@@ -132,78 +135,66 @@ class TheMovieDB:
|
|
|
132
135
|
genres = self._make_request("genre/movie/list")
|
|
133
136
|
return {genre['id']: genre['name'] for genre in genres.get('genres', [])}
|
|
134
137
|
|
|
135
|
-
def
|
|
138
|
+
def _display_top_5(self, category: str, data, name_key='title'):
|
|
136
139
|
"""
|
|
137
|
-
|
|
140
|
+
Display top 5 most popular items in a single line with colors.
|
|
138
141
|
|
|
139
142
|
Parameters:
|
|
140
|
-
-
|
|
141
|
-
-
|
|
143
|
+
- category (str): Category label (e.g., "Trending films", "Trending TV shows")
|
|
144
|
+
- data (list): List of media items
|
|
145
|
+
- name_key (str): Key to use for the name ('title' for movies, 'name' for TV shows)
|
|
142
146
|
"""
|
|
143
|
-
#
|
|
144
|
-
|
|
145
|
-
column_info = {
|
|
146
|
-
col[0]: {'color': col[2] if len(col) > 2 else 'white'}
|
|
147
|
-
for col in columns
|
|
148
|
-
}
|
|
149
|
-
tv_show_manager.add_column(column_info)
|
|
150
|
-
|
|
151
|
-
# Add each item to the TV show manager, including rank
|
|
152
|
-
for index, item in enumerate(data):
|
|
153
|
-
|
|
154
|
-
# Convert genre IDs to genre names
|
|
155
|
-
genre_names = [self.genres.get(genre_id, 'Unknown') for genre_id in item.get('genre_ids', [])]
|
|
156
|
-
tv_show = {
|
|
157
|
-
col[0]: str(item.get(col[1], 'N/A')) if col[1] != 'genre_ids' else ', '.join(genre_names)
|
|
158
|
-
for col in columns
|
|
159
|
-
}
|
|
160
|
-
|
|
161
|
-
tv_show_manager.add_tv_show(tv_show)
|
|
147
|
+
# Colors for the titles
|
|
148
|
+
colors = ['cyan', 'magenta', 'yellow', 'green', 'blue']
|
|
162
149
|
|
|
163
|
-
#
|
|
164
|
-
|
|
150
|
+
# Sort by popularity and get top 5
|
|
151
|
+
sorted_data = sorted(data, key=lambda x: x.get('popularity', 0), reverse=True)[:5]
|
|
152
|
+
|
|
153
|
+
# Create list of colored titles
|
|
154
|
+
colored_items = []
|
|
155
|
+
for item, color in zip(sorted_data, colors):
|
|
156
|
+
title = item.get(name_key, 'Unknown')
|
|
157
|
+
colored_items.append(f"[{color}]{title}[/]")
|
|
158
|
+
|
|
159
|
+
# Join with colored arrows and print with proper category label
|
|
160
|
+
console.print(
|
|
161
|
+
f"[bold purple]{category}:[/] {' [red]→[/] '.join(colored_items)}"
|
|
162
|
+
)
|
|
165
163
|
|
|
166
|
-
def
|
|
164
|
+
def display_trending_tv_shows(self):
|
|
167
165
|
"""
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
Parameters:
|
|
171
|
-
- title (str): The title to display.
|
|
172
|
-
- data (list): List of dictionaries containing the data to process.
|
|
173
|
-
- columns (list): A list of tuples, where each tuple contains the column name and the key to fetch the data from the dictionary.
|
|
166
|
+
Fetch and display the top 5 trending TV shows of the week.
|
|
167
|
+
Uses cached data if available, otherwise makes a new request.
|
|
174
168
|
"""
|
|
175
|
-
self.
|
|
176
|
-
|
|
169
|
+
if self._cached_trending_tv is None:
|
|
170
|
+
self._cached_trending_tv = self._make_request("trending/tv/week").get("results", [])
|
|
171
|
+
|
|
172
|
+
self._display_top_5("Trending TV shows", self._cached_trending_tv, name_key='name')
|
|
177
173
|
|
|
178
|
-
def
|
|
174
|
+
def refresh_trending_tv_shows(self):
|
|
179
175
|
"""
|
|
180
|
-
|
|
176
|
+
Force a refresh of the trending TV shows cache.
|
|
181
177
|
"""
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
("Title", "name", 'cyan'),
|
|
185
|
-
("First Air Date", "first_air_date", 'green'),
|
|
186
|
-
("Popularity", "popularity", 'magenta'),
|
|
187
|
-
("Genres", "genre_ids", 'blue'),
|
|
188
|
-
("Origin Country", "origin_country", 'red'),
|
|
189
|
-
("Vote Average", "vote_average", 'yellow')
|
|
190
|
-
]
|
|
191
|
-
self._display_with_title("Trending TV Shows of the Week", data, columns)
|
|
178
|
+
self._cached_trending_tv = self._make_request("trending/tv/week").get("results", [])
|
|
179
|
+
return self._cached_trending_tv
|
|
192
180
|
|
|
193
181
|
def display_trending_films(self):
|
|
194
182
|
"""
|
|
195
|
-
Fetch and display the trending films of the week.
|
|
183
|
+
Fetch and display the top 5 trending films of the week.
|
|
184
|
+
Uses cached data if available, otherwise makes a new request.
|
|
196
185
|
"""
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
("Popularity", "popularity", 'magenta'),
|
|
202
|
-
("Genres", "genre_ids", 'blue'),
|
|
203
|
-
("Vote Average", "vote_average", 'yellow')
|
|
204
|
-
]
|
|
205
|
-
self._display_with_title("Trending Films of the Week", data, columns)
|
|
186
|
+
if self._cached_trending_movies is None:
|
|
187
|
+
self._cached_trending_movies = self._make_request("trending/movie/week").get("results", [])
|
|
188
|
+
|
|
189
|
+
self._display_top_5("Trending films", self._cached_trending_movies, name_key='title')
|
|
206
190
|
|
|
191
|
+
def refresh_trending_films(self):
|
|
192
|
+
"""
|
|
193
|
+
Force a refresh of the trending films cache.
|
|
194
|
+
"""
|
|
195
|
+
self._cached_trending_movies = self._make_request("trending/movie/week").get("results", [])
|
|
196
|
+
return self._cached_trending_movies
|
|
197
|
+
|
|
207
198
|
def search_movie(self, movie_name: str):
|
|
208
199
|
"""
|
|
209
200
|
Search for a movie by name and return its TMDB ID.
|
|
@@ -217,10 +208,10 @@ class TheMovieDB:
|
|
|
217
208
|
generic_obj = []
|
|
218
209
|
data = self._make_request("search/movie", {"query": movie_name}).get("results", [])
|
|
219
210
|
if not data:
|
|
220
|
-
|
|
211
|
+
console.print("No movies found with that name.", style="red")
|
|
221
212
|
return None
|
|
222
213
|
|
|
223
|
-
|
|
214
|
+
console.print("\nSelect a Movie:")
|
|
224
215
|
for i, movie in enumerate(data, start=1):
|
|
225
216
|
generic_obj.append({
|
|
226
217
|
'name': movie['title'],
|
|
@@ -243,7 +234,7 @@ class TheMovieDB:
|
|
|
243
234
|
"""
|
|
244
235
|
movie = self._make_request(f"movie/{tmdb_id}")
|
|
245
236
|
if not movie:
|
|
246
|
-
|
|
237
|
+
console.print("Movie not found.", style="red")
|
|
247
238
|
return None
|
|
248
239
|
|
|
249
240
|
return Json_film(movie)
|
|
@@ -260,12 +251,12 @@ class TheMovieDB:
|
|
|
260
251
|
"""
|
|
261
252
|
data = self._make_request("search/tv", {"query": tv_name}).get("results", [])
|
|
262
253
|
if not data:
|
|
263
|
-
|
|
254
|
+
console.print("No TV shows found with that name.", style="red")
|
|
264
255
|
return None
|
|
265
256
|
|
|
266
|
-
|
|
257
|
+
console.print("\nSelect a TV Show:")
|
|
267
258
|
for i, show in enumerate(data, start=1):
|
|
268
|
-
|
|
259
|
+
console.print(f"{i}. {show['name']} (First Air Date: {show.get('first_air_date', 'N/A')})")
|
|
269
260
|
|
|
270
261
|
choice = int(input("Enter the number of the show you want: ")) - 1
|
|
271
262
|
selected_show = data[choice]
|
|
@@ -283,12 +274,12 @@ class TheMovieDB:
|
|
|
283
274
|
"""
|
|
284
275
|
data = self._make_request(f"tv/{tv_show_id}").get("seasons", [])
|
|
285
276
|
if not data:
|
|
286
|
-
|
|
277
|
+
console.print("No seasons found for this TV show.", style="red")
|
|
287
278
|
return None
|
|
288
279
|
|
|
289
|
-
|
|
280
|
+
console.print("\nSelect a Season:")
|
|
290
281
|
for i, season in enumerate(data, start=1):
|
|
291
|
-
|
|
282
|
+
console.print(f"{i}. {season['name']} (Episodes: {season['episode_count']})")
|
|
292
283
|
|
|
293
284
|
choice = int(input("Enter the number of the season you want: ")) - 1
|
|
294
285
|
return data[choice]["season_number"]
|
|
@@ -306,12 +297,12 @@ class TheMovieDB:
|
|
|
306
297
|
"""
|
|
307
298
|
data = self._make_request(f"tv/{tv_show_id}/season/{season_number}").get("episodes", [])
|
|
308
299
|
if not data:
|
|
309
|
-
|
|
300
|
+
console.print("No episodes found for this season.", style="red")
|
|
310
301
|
return None
|
|
311
302
|
|
|
312
|
-
|
|
303
|
+
console.print("\nSelect an Episode:")
|
|
313
304
|
for i, episode in enumerate(data, start=1):
|
|
314
|
-
|
|
305
|
+
console.print(f"{i}. {episode['name']} (Air Date: {episode.get('air_date', 'N/A')})")
|
|
315
306
|
|
|
316
307
|
choice = int(input("Enter the number of the episode you want: ")) - 1
|
|
317
308
|
return data[choice]
|
|
@@ -319,28 +310,4 @@ class TheMovieDB:
|
|
|
319
310
|
|
|
320
311
|
|
|
321
312
|
# Output
|
|
322
|
-
tmdb = TheMovieDB(api_key)
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
"""
|
|
326
|
-
Example:
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
@ movie
|
|
330
|
-
movie_name = "Interstellar"
|
|
331
|
-
movie_id = tmdb.search_movie(movie_name)
|
|
332
|
-
|
|
333
|
-
if movie_id:
|
|
334
|
-
movie_details = tmdb.get_movie_details(tmdb_id=movie_id)
|
|
335
|
-
print(movie_details)
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
@ series
|
|
339
|
-
tv_name = "Game of Thrones"
|
|
340
|
-
tv_show_id = tmdb.search_tv_show(tv_name)
|
|
341
|
-
if tv_show_id:
|
|
342
|
-
season_number = tmdb.get_seasons(tv_show_id=tv_show_id)
|
|
343
|
-
if season_number:
|
|
344
|
-
episode = tmdb.get_episodes(tv_show_id=tv_show_id, season_number=season_number)
|
|
345
|
-
print(episode)
|
|
346
|
-
"""
|
|
313
|
+
tmdb = TheMovieDB(api_key)
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
# 04.02.
|
|
1
|
+
# 04.02.26
|
|
2
2
|
# Made by: @GiuPic
|
|
3
3
|
|
|
4
4
|
import os
|
|
@@ -9,16 +9,141 @@ import uuid
|
|
|
9
9
|
import json
|
|
10
10
|
import threading
|
|
11
11
|
import subprocess
|
|
12
|
-
|
|
12
|
+
import threading
|
|
13
|
+
from typing import Optional
|
|
13
14
|
|
|
14
15
|
# External libraries
|
|
15
16
|
import telebot
|
|
16
17
|
|
|
18
|
+
session_data = {}
|
|
19
|
+
|
|
20
|
+
class TelegramSession:
|
|
21
|
+
|
|
22
|
+
def set_session(value):
|
|
23
|
+
session_data['script_id'] = value
|
|
24
|
+
|
|
25
|
+
def get_session():
|
|
26
|
+
return session_data.get('script_id', 'unknown')
|
|
27
|
+
|
|
28
|
+
def updateScriptId(screen_id, titolo):
|
|
29
|
+
json_file = "../../scripts.json"
|
|
30
|
+
try:
|
|
31
|
+
with open(json_file, 'r') as f:
|
|
32
|
+
scripts_data = json.load(f)
|
|
33
|
+
except FileNotFoundError:
|
|
34
|
+
scripts_data = []
|
|
35
|
+
|
|
36
|
+
# cerco lo script con lo screen_id
|
|
37
|
+
for script in scripts_data:
|
|
38
|
+
if script["screen_id"] == screen_id:
|
|
39
|
+
# se trovo il match, aggiorno il titolo
|
|
40
|
+
script["titolo"] = titolo
|
|
41
|
+
|
|
42
|
+
# aggiorno il file json
|
|
43
|
+
with open(json_file, 'w') as f:
|
|
44
|
+
json.dump(scripts_data, f, indent=4)
|
|
45
|
+
|
|
46
|
+
return
|
|
47
|
+
|
|
48
|
+
print(f"Screen_id {screen_id} non trovato.")
|
|
49
|
+
|
|
50
|
+
def deleteScriptId(screen_id):
|
|
51
|
+
json_file = "../../scripts.json"
|
|
52
|
+
try:
|
|
53
|
+
with open(json_file, 'r') as f:
|
|
54
|
+
scripts_data = json.load(f)
|
|
55
|
+
except FileNotFoundError:
|
|
56
|
+
scripts_data = []
|
|
57
|
+
|
|
58
|
+
for script in scripts_data:
|
|
59
|
+
if script["screen_id"] == screen_id:
|
|
60
|
+
# se trovo il match, elimino lo script
|
|
61
|
+
scripts_data.remove(script)
|
|
62
|
+
|
|
63
|
+
# aggiorno il file json
|
|
64
|
+
with open(json_file, 'w') as f:
|
|
65
|
+
json.dump(scripts_data, f, indent=4)
|
|
66
|
+
|
|
67
|
+
print(f"Script eliminato per screen_id {screen_id}")
|
|
68
|
+
return
|
|
69
|
+
|
|
70
|
+
print(f"Screen_id {screen_id} non trovato.")
|
|
71
|
+
|
|
72
|
+
class TelegramRequestManager:
|
|
73
|
+
_instance = None
|
|
74
|
+
|
|
75
|
+
def __new__(cls, *args, **kwargs):
|
|
76
|
+
if not cls._instance:
|
|
77
|
+
cls._instance = super().__new__(cls)
|
|
78
|
+
return cls._instance
|
|
79
|
+
|
|
80
|
+
def __init__(self, json_file: str = "active_requests.json"):
|
|
81
|
+
if not hasattr(self, 'initialized'):
|
|
82
|
+
self.json_file = json_file
|
|
83
|
+
self.initialized = True
|
|
84
|
+
self.on_response_callback = None
|
|
85
|
+
|
|
86
|
+
def create_request(self, type: str) -> str:
|
|
87
|
+
request_data = {
|
|
88
|
+
"type": type,
|
|
89
|
+
"response": None,
|
|
90
|
+
"timestamp": time.time()
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
with open(self.json_file, "w") as f:
|
|
94
|
+
json.dump(request_data, f)
|
|
95
|
+
|
|
96
|
+
return "Ok"
|
|
97
|
+
|
|
98
|
+
def save_response(self, message_text: str) -> bool:
|
|
99
|
+
try:
|
|
100
|
+
# Carica il file JSON
|
|
101
|
+
with open(self.json_file, "r") as f:
|
|
102
|
+
data = json.load(f)
|
|
103
|
+
|
|
104
|
+
# Controlla se esiste la chiave 'type' e se la risposta è presente
|
|
105
|
+
if "type" in data and "response" in data:
|
|
106
|
+
data["response"] = message_text # Aggiorna la risposta
|
|
17
107
|
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
from StreamingCommunity.TelegramHelp.request_manager import RequestManager
|
|
108
|
+
with open(self.json_file, "w") as f:
|
|
109
|
+
json.dump(data, f, indent=4)
|
|
21
110
|
|
|
111
|
+
return True
|
|
112
|
+
else:
|
|
113
|
+
return False
|
|
114
|
+
|
|
115
|
+
except (FileNotFoundError, json.JSONDecodeError) as e:
|
|
116
|
+
print(f"⚠️ save_response - errore: {e}")
|
|
117
|
+
return False
|
|
118
|
+
|
|
119
|
+
def get_response(self) -> Optional[str]:
|
|
120
|
+
try:
|
|
121
|
+
with open(self.json_file, "r") as f:
|
|
122
|
+
data = json.load(f)
|
|
123
|
+
|
|
124
|
+
# Verifica se esiste la chiave "response"
|
|
125
|
+
if "response" in data:
|
|
126
|
+
response = data["response"] # Ottieni la risposta direttamente
|
|
127
|
+
|
|
128
|
+
if response is not None and self.on_response_callback:
|
|
129
|
+
self.on_response_callback(response)
|
|
130
|
+
|
|
131
|
+
return response
|
|
132
|
+
|
|
133
|
+
except (FileNotFoundError, json.JSONDecodeError) as e:
|
|
134
|
+
print(f"get_response - errore: {e}")
|
|
135
|
+
return None
|
|
136
|
+
|
|
137
|
+
def clear_file(self) -> bool:
|
|
138
|
+
try:
|
|
139
|
+
with open(self.json_file, "w") as f:
|
|
140
|
+
json.dump({}, f)
|
|
141
|
+
print(f"File {self.json_file} è stato svuotato con successo.")
|
|
142
|
+
return True
|
|
143
|
+
|
|
144
|
+
except Exception as e:
|
|
145
|
+
print(f"⚠️ clear_file - errore: {e}")
|
|
146
|
+
return False
|
|
22
147
|
|
|
23
148
|
# Funzione per caricare variabili da un file .env
|
|
24
149
|
def load_env(file_path="../../.env"):
|
|
@@ -44,13 +169,17 @@ class TelegramBot:
|
|
|
44
169
|
if os.path.exists(cls._config_file):
|
|
45
170
|
with open(cls._config_file, "r") as f:
|
|
46
171
|
config = json.load(f)
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
)
|
|
172
|
+
|
|
173
|
+
# Assicura che authorized_user_id venga trattato come una lista
|
|
174
|
+
authorized_users = config.get('authorized_user_id', [])
|
|
175
|
+
if isinstance(authorized_users, str):
|
|
176
|
+
authorized_users = [int(uid) for uid in authorized_users.split(",") if uid.strip().isdigit()]
|
|
177
|
+
|
|
178
|
+
cls._instance = cls.init_bot(config['token'], authorized_users)
|
|
179
|
+
#cls._instance = cls.init_bot(config['token'], config['authorized_user_id'])
|
|
180
|
+
|
|
50
181
|
else:
|
|
51
|
-
raise Exception(
|
|
52
|
-
"Bot non ancora inizializzato. Chiamare prima init_bot() con token e authorized_user_id"
|
|
53
|
-
)
|
|
182
|
+
raise Exception("Bot non ancora inizializzato. Chiamare prima init_bot() con token e authorized_user_id")
|
|
54
183
|
return cls._instance
|
|
55
184
|
|
|
56
185
|
@classmethod
|
|
@@ -63,7 +192,8 @@ class TelegramBot:
|
|
|
63
192
|
json.dump(config, f)
|
|
64
193
|
return cls._instance
|
|
65
194
|
|
|
66
|
-
def __init__(self, token,
|
|
195
|
+
def __init__(self, token, authorized_users):
|
|
196
|
+
|
|
67
197
|
def monitor_scripts():
|
|
68
198
|
while True:
|
|
69
199
|
try:
|
|
@@ -132,10 +262,10 @@ class TelegramBot:
|
|
|
132
262
|
)
|
|
133
263
|
|
|
134
264
|
self.token = token
|
|
135
|
-
self.
|
|
136
|
-
self.chat_id =
|
|
265
|
+
self.authorized_users = authorized_users
|
|
266
|
+
self.chat_id = authorized_users
|
|
137
267
|
self.bot = telebot.TeleBot(token)
|
|
138
|
-
self.request_manager =
|
|
268
|
+
self.request_manager = TelegramRequestManager()
|
|
139
269
|
|
|
140
270
|
# Registra gli handler
|
|
141
271
|
self.register_handlers()
|
|
@@ -171,7 +301,7 @@ class TelegramBot:
|
|
|
171
301
|
self.handle_response(message)
|
|
172
302
|
|
|
173
303
|
def is_authorized(self, user_id):
|
|
174
|
-
return user_id
|
|
304
|
+
return user_id in self.authorized_users
|
|
175
305
|
|
|
176
306
|
def handle_get_id(self, message):
|
|
177
307
|
if not self.is_authorized(message.from_user.id):
|
|
@@ -194,7 +324,6 @@ class TelegramBot:
|
|
|
194
324
|
|
|
195
325
|
screen_id = str(uuid.uuid4())[:8]
|
|
196
326
|
debug_mode = os.getenv("DEBUG")
|
|
197
|
-
verbose = debug_mode
|
|
198
327
|
|
|
199
328
|
if debug_mode == "True":
|
|
200
329
|
subprocess.Popen(["python3", "../../test_run.py", screen_id])
|
|
@@ -407,6 +536,13 @@ class TelegramBot:
|
|
|
407
536
|
temp_file = f"/tmp/screen_output_{screen_id}.txt"
|
|
408
537
|
|
|
409
538
|
try:
|
|
539
|
+
# Verifica se lo screen con l'ID specificato esiste
|
|
540
|
+
existing_screens = subprocess.check_output(["screen", "-list"]).decode('utf-8')
|
|
541
|
+
if screen_id not in existing_screens:
|
|
542
|
+
print(f"⚠️ La sessione screen con ID {screen_id} non esiste.")
|
|
543
|
+
self.bot.send_message(message.chat.id, f"⚠️ La sessione screen con ID {screen_id} non esiste.")
|
|
544
|
+
return
|
|
545
|
+
|
|
410
546
|
# Cattura l'output della screen
|
|
411
547
|
subprocess.run(
|
|
412
548
|
["screen", "-X", "-S", screen_id, "hardcopy", "-h", temp_file],
|
|
@@ -440,51 +576,22 @@ class TelegramBot:
|
|
|
440
576
|
"\n\n", "\n"
|
|
441
577
|
) # Rimuovi newline multipli
|
|
442
578
|
|
|
443
|
-
#
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
if download_matches:
|
|
448
|
-
# Serie TV e Film StreamingCommunity
|
|
449
|
-
|
|
450
|
-
proc_matches = re.findall(r"Proc: ([\d\.]+%)", cleaned_output)
|
|
451
|
-
|
|
452
|
-
# Creare una stringa unica con tutti i risultati
|
|
453
|
-
result_string = "\n".join(
|
|
454
|
-
[
|
|
455
|
-
f"Download: {download_matches[i].strip()}\nDownload al {proc_matches[i]}"
|
|
456
|
-
for i in range(len(download_matches))
|
|
457
|
-
if i < len(proc_matches)
|
|
458
|
-
]
|
|
459
|
-
)
|
|
460
|
-
|
|
461
|
-
if result_string != "":
|
|
462
|
-
cleaned_output = result_string
|
|
463
|
-
else:
|
|
464
|
-
print(f"❌ La parola 'Download:' non è stata trovata nella stringa.")
|
|
465
|
-
else:
|
|
466
|
-
|
|
467
|
-
download_list = []
|
|
468
|
-
|
|
469
|
-
# Estrai tutte le righe che iniziano con "Download:" fino al prossimo "Download" o alla fine della riga
|
|
470
|
-
matches = re.findall(r"Download:\s*(.*?)(?=Download|$)", cleaned_output)
|
|
579
|
+
# Dentro cleaned_output c'è una stringa recupero quello che si trova tra ## ##
|
|
580
|
+
download_section = re.search(r"##(.*?)##", cleaned_output, re.DOTALL)
|
|
581
|
+
if download_section:
|
|
582
|
+
cleaned_output_0 = "Download: " + download_section.group(1).strip()
|
|
471
583
|
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
match = re.sub(r"downloader.py:\d+Result:400", "", match)
|
|
477
|
-
match = match.strip() # Rimuovo gli spazi bianchi in eccesso
|
|
478
|
-
if match: # Assicurati che la stringa non sia vuota
|
|
479
|
-
print(f"Download {i}: {match}")
|
|
584
|
+
# Recupero tutto quello che viene dopo con ####
|
|
585
|
+
download_section_bottom = re.search(r"####(.*)", cleaned_output, re.DOTALL)
|
|
586
|
+
if download_section_bottom:
|
|
587
|
+
cleaned_output_1 = download_section_bottom.group(1).strip()
|
|
480
588
|
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
print("❌ Nessun download trovato")
|
|
589
|
+
# Unico i due risultati se esistono
|
|
590
|
+
if cleaned_output_0 and cleaned_output_1:
|
|
591
|
+
cleaned_output = f"{cleaned_output_0}\n{cleaned_output_1}"
|
|
592
|
+
# Rimuovo 'segments.py:302' e 'downloader.py:385' se presente
|
|
593
|
+
cleaned_output = re.sub(r'downloader\.py:\d+', '', cleaned_output)
|
|
594
|
+
cleaned_output = re.sub(r'segments\.py:\d+', '', cleaned_output)
|
|
488
595
|
|
|
489
596
|
# Invia l'output pulito
|
|
490
597
|
print(f"📄 Output della screen {screen_id}:\n{cleaned_output}")
|
|
@@ -505,7 +612,16 @@ class TelegramBot:
|
|
|
505
612
|
os.remove(temp_file)
|
|
506
613
|
|
|
507
614
|
def send_message(self, message, choices):
|
|
508
|
-
|
|
615
|
+
|
|
616
|
+
formatted_message = message
|
|
617
|
+
if choices:
|
|
618
|
+
formatted_choices = "\n".join(choices)
|
|
619
|
+
formatted_message = f"{message}\n\n{formatted_choices}"
|
|
620
|
+
|
|
621
|
+
for chat_id in self.authorized_users:
|
|
622
|
+
self.bot.send_message(chat_id, formatted_message)
|
|
623
|
+
|
|
624
|
+
""" if choices is None:
|
|
509
625
|
if self.chat_id:
|
|
510
626
|
print(f"{message}")
|
|
511
627
|
self.bot.send_message(self.chat_id, message)
|
|
@@ -514,7 +630,7 @@ class TelegramBot:
|
|
|
514
630
|
message = f"{message}\n\n{formatted_choices}"
|
|
515
631
|
if self.chat_id:
|
|
516
632
|
print(f"{message}")
|
|
517
|
-
self.bot.send_message(self.chat_id, message)
|
|
633
|
+
self.bot.send_message(self.chat_id, message) """
|
|
518
634
|
|
|
519
635
|
def _send_long_message(self, chat_id, text, chunk_size=4096):
|
|
520
636
|
"""Suddivide e invia un messaggio troppo lungo in più parti."""
|
|
@@ -527,16 +643,20 @@ class TelegramBot:
|
|
|
527
643
|
|
|
528
644
|
if choices is None:
|
|
529
645
|
print(f"{prompt_message}")
|
|
530
|
-
self.bot.send_message(
|
|
646
|
+
""" self.bot.send_message(
|
|
531
647
|
self.chat_id,
|
|
532
648
|
f"{prompt_message}",
|
|
533
|
-
)
|
|
649
|
+
) """
|
|
650
|
+
for chat_id in self.authorized_users: # Manda a tutti gli ID autorizzati
|
|
651
|
+
self.bot.send_message(chat_id, f"{prompt_message}")
|
|
534
652
|
else:
|
|
535
653
|
print(f"{prompt_message}\n\nOpzioni: {', '.join(choices)}")
|
|
536
|
-
self.bot.send_message(
|
|
654
|
+
""" self.bot.send_message(
|
|
537
655
|
self.chat_id,
|
|
538
656
|
f"{prompt_message}\n\nOpzioni: {', '.join(choices)}",
|
|
539
|
-
)
|
|
657
|
+
) """
|
|
658
|
+
for chat_id in self.authorized_users: # Manda a tutti gli ID autorizzati
|
|
659
|
+
self.bot.send_message(chat_id, f"{prompt_message}\n\nOpzioni: {', '.join(choices)}")
|
|
540
660
|
|
|
541
661
|
start_time = time.time()
|
|
542
662
|
while time.time() - start_time < timeout:
|
|
@@ -546,7 +666,8 @@ class TelegramBot:
|
|
|
546
666
|
time.sleep(1)
|
|
547
667
|
|
|
548
668
|
print(f"⚠️ Timeout: nessuna risposta ricevuta.")
|
|
549
|
-
|
|
669
|
+
for chat_id in self.authorized_users: # Manda a tutti gli ID autorizzati
|
|
670
|
+
self.bot.send_message(chat_id, "⚠️ Timeout: nessuna risposta ricevuta.")
|
|
550
671
|
self.request_manager.clear_file()
|
|
551
672
|
return None
|
|
552
673
|
|
|
@@ -558,4 +679,37 @@ class TelegramBot:
|
|
|
558
679
|
|
|
559
680
|
|
|
560
681
|
def get_bot_instance():
|
|
561
|
-
return TelegramBot.get_instance()
|
|
682
|
+
return TelegramBot.get_instance()
|
|
683
|
+
|
|
684
|
+
# Esempio di utilizzo
|
|
685
|
+
if __name__ == "__main__":
|
|
686
|
+
|
|
687
|
+
# Usa le variabili
|
|
688
|
+
token = os.getenv("TOKEN_TELEGRAM")
|
|
689
|
+
authorized_users = os.getenv("AUTHORIZED_USER_ID")
|
|
690
|
+
|
|
691
|
+
# Controlla se le variabili sono presenti
|
|
692
|
+
if not token:
|
|
693
|
+
print("Errore: TOKEN_TELEGRAM non è definito nel file .env.")
|
|
694
|
+
sys.exit(1)
|
|
695
|
+
|
|
696
|
+
if not authorized_users:
|
|
697
|
+
print("Errore: AUTHORIZED_USER_ID non è definito nel file .env.")
|
|
698
|
+
sys.exit(1)
|
|
699
|
+
|
|
700
|
+
try:
|
|
701
|
+
TOKEN = token # Inserisci il token del tuo bot Telegram sul file .env
|
|
702
|
+
AUTHORIZED_USER_ID = list(map(int, authorized_users.split(","))) # Inserisci il tuo ID utente Telegram sul file .env
|
|
703
|
+
except ValueError as e:
|
|
704
|
+
print(f"Errore nella conversione degli ID autorizzati: {e}. Controlla il file .env e assicurati che gli ID siano numeri interi separati da virgole.")
|
|
705
|
+
sys.exit(1)
|
|
706
|
+
|
|
707
|
+
# Inizializza il bot
|
|
708
|
+
bot = TelegramBot.init_bot(TOKEN, AUTHORIZED_USER_ID)
|
|
709
|
+
bot.run()
|
|
710
|
+
|
|
711
|
+
"""
|
|
712
|
+
start - Avvia lo script
|
|
713
|
+
list - Lista script attivi
|
|
714
|
+
get - Mostra ID utente Telegram
|
|
715
|
+
"""
|