Spaces:
Running
Running
Update app.py
Browse files
app.py
CHANGED
@@ -1,59 +1,82 @@
|
|
1 |
import os
|
2 |
import logging
|
|
|
|
|
|
|
|
|
|
|
3 |
from telegram import Update
|
4 |
from telegram.ext import Application, MessageHandler, filters
|
5 |
from transformers import pipeline, AutoTokenizer, VitsModel
|
6 |
-
import
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
import torch
|
11 |
|
12 |
-
# تهيئة
|
13 |
logging.basicConfig(
|
14 |
format='%(asctime)s - %(name)s - %(levelname)s - %(message)s',
|
15 |
level=logging.INFO
|
16 |
)
|
17 |
logger = logging.getLogger(__name__)
|
18 |
|
19 |
-
# تهيئة النماذج
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
24 |
|
25 |
-
|
26 |
-
|
|
|
27 |
|
28 |
-
|
29 |
-
|
|
|
30 |
try:
|
31 |
audio = AudioSegment.from_wav(input_path)
|
32 |
-
audio = audio.low_pass_filter(3000)
|
33 |
-
audio = audio.high_pass_filter(100)
|
34 |
-
audio = audio.normalize()
|
35 |
-
audio = audio.fade_in(150).fade_out(150)
|
36 |
audio.export(output_path, format="wav")
|
37 |
return True
|
38 |
except Exception as e:
|
39 |
logger.error(f"فشل تحسين الصوت: {str(e)}")
|
40 |
return False
|
41 |
|
42 |
-
|
|
|
|
|
43 |
try:
|
44 |
audio, sr = librosa.load(audio_path, sr=16000)
|
45 |
-
sf.write("temp.wav", audio, sr) #
|
46 |
result = asr_pipeline("temp.wav")
|
47 |
return result["text"]
|
48 |
except Exception as e:
|
49 |
logger.error(f"فشل التعرف على الصوت: {str(e)}")
|
50 |
return ""
|
51 |
|
52 |
-
async def generate_response(text):
|
|
|
53 |
try:
|
54 |
chatbot = pipeline(
|
55 |
"text-generation",
|
56 |
-
model="aubmindlab/aragpt2-base"
|
|
|
57 |
)
|
58 |
response = chatbot(
|
59 |
text,
|
@@ -64,26 +87,22 @@ async def generate_response(text):
|
|
64 |
return response[0]['generated_text']
|
65 |
except Exception as e:
|
66 |
logger.error(f"فشل توليد الرد: {str(e)}")
|
67 |
-
return "
|
68 |
|
69 |
-
async def text_to_speech(text):
|
|
|
70 |
try:
|
71 |
inputs = tts_tokenizer(text, return_tensors="pt")
|
72 |
with torch.no_grad():
|
73 |
output = tts_model(**inputs)
|
74 |
waveform = output.waveform[0].numpy()
|
75 |
-
|
76 |
-
# ===== التغيير الرئيسي هنا =====
|
77 |
-
sf.write("bot_response.wav", waveform, tts_model.config.sampling_rate) # <-- استبدال torchaudio
|
78 |
-
|
79 |
except Exception as e:
|
80 |
logger.error(f"فشل تحويل النص إلى صوت: {str(e)}")
|
81 |
|
82 |
-
async def process_voice(update: Update, context):
|
|
|
83 |
try:
|
84 |
-
user = update.message.from_user
|
85 |
-
logger.info(f"رسالة صوتية من {user.first_name}")
|
86 |
-
|
87 |
# تحميل الملف الصوتي
|
88 |
voice_file = await update.message.voice.get_file()
|
89 |
await voice_file.download_to_drive("user_voice.ogg")
|
@@ -93,7 +112,7 @@ async def process_voice(update: Update, context):
|
|
93 |
bot_response = await generate_response(user_text)
|
94 |
await text_to_speech(bot_response)
|
95 |
|
96 |
-
#
|
97 |
if enhance_audio("bot_response.wav", "bot_response_enhanced.wav"):
|
98 |
await update.message.reply_voice("bot_response_enhanced.wav")
|
99 |
else:
|
@@ -101,10 +120,11 @@ async def process_voice(update: Update, context):
|
|
101 |
|
102 |
except Exception as e:
|
103 |
logger.error(f"خطأ رئيسي: {str(e)}")
|
104 |
-
await update.message.reply_text("⚠️ حدث خطأ غير
|
105 |
|
|
|
106 |
if __name__ == "__main__":
|
107 |
-
TOKEN = os.getenv("TELEGRAM_TOKEN")
|
108 |
application = Application.builder().token(TOKEN).build()
|
109 |
application.add_handler(MessageHandler(filters.VOICE, process_voice))
|
110 |
application.run_polling()
|
|
|
1 |
import os
|
2 |
import logging
|
3 |
+
import numpy as np
|
4 |
+
import torch
|
5 |
+
import librosa
|
6 |
+
import soundfile as sf
|
7 |
+
from pydub import AudioSegment
|
8 |
from telegram import Update
|
9 |
from telegram.ext import Application, MessageHandler, filters
|
10 |
from transformers import pipeline, AutoTokenizer, VitsModel
|
11 |
+
from huggingface_hub import login # المكتبة الجديدة المطلوبة
|
12 |
+
|
13 |
+
# ================ الخطوة 1: تسجيل الدخول باستخدام توكن Hugging Face ================
|
14 |
+
login(token=os.getenv("HF_TOKEN")) # تأكد من إضافة متغير HF_TOKEN في الإعدادات
|
|
|
15 |
|
16 |
+
# ================ تهيئة نظام التسجيل ================
|
17 |
logging.basicConfig(
|
18 |
format='%(asctime)s - %(name)s - %(levelname)s - %(message)s',
|
19 |
level=logging.INFO
|
20 |
)
|
21 |
logger = logging.getLogger(__name__)
|
22 |
|
23 |
+
# ================ تهيئة النماذج مع التوكن ================
|
24 |
+
try:
|
25 |
+
# 1. نموذج التعرف على الكلام (ASR)
|
26 |
+
asr_pipeline = pipeline(
|
27 |
+
task="automatic-speech-recognition",
|
28 |
+
model="jonatasgrosman/wav2vec2-large-xlsr-53-arabic", # نموذج بديل متوفر
|
29 |
+
token=os.getenv("HF_TOKEN") # استخدام التوكن هنا
|
30 |
+
)
|
31 |
+
|
32 |
+
# 2. نموذج توليف الكلام (TTS)
|
33 |
+
tts_tokenizer = AutoTokenizer.from_pretrained(
|
34 |
+
"facebook/mms-tts-ara",
|
35 |
+
token=os.getenv("HF_TOKEN") # استخدام التوكن هنا
|
36 |
+
)
|
37 |
+
tts_model = VitsModel.from_pretrained(
|
38 |
+
"facebook/mms-tts-ara",
|
39 |
+
token=os.getenv("HF_TOKEN") # استخدام التوكن هنا
|
40 |
+
)
|
41 |
|
42 |
+
except Exception as e:
|
43 |
+
logger.error(f"خطأ في تحميل النماذج: {str(e)}")
|
44 |
+
raise
|
45 |
|
46 |
+
# ================ دالة تحسين جودة الصوت ================
|
47 |
+
def enhance_audio(input_path: str, output_path: str) -> bool:
|
48 |
+
"""تطبيق تأثيرات تحسين على الملف الصوتي"""
|
49 |
try:
|
50 |
audio = AudioSegment.from_wav(input_path)
|
51 |
+
audio = audio.low_pass_filter(3000) # تقليل الضوضاء
|
52 |
+
audio = audio.high_pass_filter(100) # إزالة الهوم
|
53 |
+
audio = audio.normalize() # توحيد مستوى الصوت
|
54 |
+
audio = audio.fade_in(150).fade_out(150) # إضافة fade
|
55 |
audio.export(output_path, format="wav")
|
56 |
return True
|
57 |
except Exception as e:
|
58 |
logger.error(f"فشل تحسين الصوت: {str(e)}")
|
59 |
return False
|
60 |
|
61 |
+
# ================ الدوال الرئيسية ================
|
62 |
+
async def speech_to_text(audio_path: str) -> str:
|
63 |
+
"""تحويل الصوت إلى نص"""
|
64 |
try:
|
65 |
audio, sr = librosa.load(audio_path, sr=16000)
|
66 |
+
sf.write("temp.wav", audio, sr) # تحويل إلى wav
|
67 |
result = asr_pipeline("temp.wav")
|
68 |
return result["text"]
|
69 |
except Exception as e:
|
70 |
logger.error(f"فشل التعرف على الصوت: {str(e)}")
|
71 |
return ""
|
72 |
|
73 |
+
async def generate_response(text: str) -> str:
|
74 |
+
"""توليد رد الذكاء الاصطناعي"""
|
75 |
try:
|
76 |
chatbot = pipeline(
|
77 |
"text-generation",
|
78 |
+
model="aubmindlab/aragpt2-base",
|
79 |
+
token=os.getenv("HF_TOKEN") # استخدام التوكن هنا
|
80 |
)
|
81 |
response = chatbot(
|
82 |
text,
|
|
|
87 |
return response[0]['generated_text']
|
88 |
except Exception as e:
|
89 |
logger.error(f"فشل توليد الرد: {str(e)}")
|
90 |
+
return "حدث خطأ في توليد الرد."
|
91 |
|
92 |
+
async def text_to_speech(text: str) -> None:
|
93 |
+
"""تحويل النص إلى صوت"""
|
94 |
try:
|
95 |
inputs = tts_tokenizer(text, return_tensors="pt")
|
96 |
with torch.no_grad():
|
97 |
output = tts_model(**inputs)
|
98 |
waveform = output.waveform[0].numpy()
|
99 |
+
sf.write("bot_response.wav", waveform, tts_model.config.sampling_rate) # حفظ الملف
|
|
|
|
|
|
|
100 |
except Exception as e:
|
101 |
logger.error(f"فشل تحويل النص إلى صوت: {str(e)}")
|
102 |
|
103 |
+
async def process_voice(update: Update, context) -> None:
|
104 |
+
"""معالجة الرسائل الصوتية الواردة"""
|
105 |
try:
|
|
|
|
|
|
|
106 |
# تحميل الملف الصوتي
|
107 |
voice_file = await update.message.voice.get_file()
|
108 |
await voice_file.download_to_drive("user_voice.ogg")
|
|
|
112 |
bot_response = await generate_response(user_text)
|
113 |
await text_to_speech(bot_response)
|
114 |
|
115 |
+
# إرسال الرد
|
116 |
if enhance_audio("bot_response.wav", "bot_response_enhanced.wav"):
|
117 |
await update.message.reply_voice("bot_response_enhanced.wav")
|
118 |
else:
|
|
|
120 |
|
121 |
except Exception as e:
|
122 |
logger.error(f"خطأ رئيسي: {str(e)}")
|
123 |
+
await update.message.reply_text("⚠️ حدث خطأ غير متوقع.")
|
124 |
|
125 |
+
# ================ تشغيل البوت ================
|
126 |
if __name__ == "__main__":
|
127 |
+
TOKEN = os.getenv("TELEGRAM_TOKEN") # تأكد من إضافة TELEGRAM_TOKEN في الإعدادات
|
128 |
application = Application.builder().token(TOKEN).build()
|
129 |
application.add_handler(MessageHandler(filters.VOICE, process_voice))
|
130 |
application.run_polling()
|