from telegram import Update
from telegram.ext import ContextTypes
from services.tiktok import download_tiktok_video
import shutil
import asyncio
from utils.ansi_stripper import strip_ansi_codes
import httpx # Importar httpx
import os # Importar os para os.path.getsize
import re # Importar re para expressões regulares
from handlers.commands import DOWNLOAD_COUNT # Importar DOWNLOAD_COUNT
async def process_tiktok(update: Update, context: ContextTypes.DEFAULT_TYPE):
url = update.message.text
progress_message = await update.message.reply_text("🎵 Baixando do TikTok...")
loop = asyncio.get_running_loop()
last_update_time = 0
async def update_progress_display(raw_progress_line):
nonlocal last_update_time
current_time = loop.time()
if current_time - last_update_time > 2: # Atualiza a cada 2 segundos para evitar flood
last_update_time = current_time
# Regex para extrair informações da linha de progresso do yt-dlp
# Ex: "[download] 57.6% of 1.20GiB at 4.20MiB/s ETA 00:04"
match = re.search(r"\[download\]\s+(?P<percent>\d+\.\d+)%\s+of\s+(?P<total_size>[\d\.]+\w+)\s+at\s+(?P<speed>[\d\.]+\w+/s)\s+ETA\s+(?P<eta>\d{2}:\d{2})", raw_progress_line)
progress_text = "Progresso: N/A"
speed_text = "Velocidade: N/A"
eta_text = "Tempo estimado: N/A"
if match:
percent = match.group("percent")
total_size = match.group("total_size")
speed = match.group("speed")
eta = match.group("eta")
progress_text = f"Progresso: {percent}% de {total_size}"
speed_text = f"Velocidade: {speed}"
eta_text = f"Tempo estimado: {eta}"
else:
# Se não encontrar o padrão principal, tenta pegar outras informações úteis
if "download" in raw_progress_line.lower():
progress_text = f"Progresso: {raw_progress_line}"
try:
await progress_message.edit_text(
f"🎵 Baixando do TikTok...\n\n"
f"{strip_ansi_codes(progress_text)}\n"
f"{strip_ansi_codes(speed_text)}\n"
f"{strip_ansi_codes(eta_text)}"
)
except Exception:
pass # Ignora erros de edição de mensagem (ex: mensagem inalterada)
temp_dir = None
try:
file_path, title, temp_dir = await download_tiktok_video(url, update_progress_display)
await progress_message.edit_text("📤 Enviando vídeo...")
# Decide se envia como video ou documento
size_mb = (await asyncio.to_thread(os.path.getsize, file_path) / 1024 / 1024)
if size_mb <= 50:
await context.bot.send_video(
chat_id=update.effective_chat.id,
video=await asyncio.to_thread(open, file_path, 'rb'), # Envia o conteúdo como bytes
caption=f"🎵 {title}"
)
else:
await context.bot.send_document(
chat_id=update.effective_chat.id,
document=await asyncio.to_thread(open, file_path, 'rb'), # Envia o conteúdo como bytes
filename=f"{title}.mp4",
caption=f"📁 Arquivo grande enviado como documento ({int(size_mb)}MB).",
)
await progress_message.delete()
global DOWNLOAD_COUNT
DOWNLOAD_COUNT += 1 # Incrementa o contador de downloads
except httpx.ReadError:
await progress_message.edit_text(
"❌ Erro: O arquivo de vídeo pode ser muito grande para ser enviado ao Telegram. "
"O limite para bots é de 50MB. Tente um vídeo mais curto."
)
except Exception as e: # Captura Exception genérica para erros do subprocesso
error_text = str(e)
if "Erro ao baixar do TikTok:" in error_text:
await progress_message.edit_text(f"❌ {error_text}")
elif "A operação de download do TikTok excedeu o tempo limite" in error_text:
await progress_message.edit_text(f"❌ {error_text}")
else:
await progress_message.edit_text(f"❌ Erro inesperado ao baixar do TikTok: {error_text}")
finally:
if temp_dir:
shutil.rmtree(temp_dir, ignore_errors=True)