أداة مفتوحة المصدر لفصل الآلات الموسيقية عن الصوت البشري في مقاطع اليوتيوب بجودة جيدة وبدون أي تكاليف.
نظام Drift Guard يطابق حركة الصوت و الصورة حتى عند التقديم وتغيير السرعات.
يعتمد على خوارزميات الذكاء الاصطناعي لفصل الترددات.
خيارات متعددة: تشغيل سحابي مجاني على كروت Tesla T4 أو تشغيل محلي دون إرسال بيانات.
متوافق مع جميع متصفحات Chromium (Chrome / Edge / Brave / CachyOS Browser)
chrome://extensions (أو edge://extensions في متصفح Microsoft Edge).
manifest.json مباشرة.
استخدم كرت شاشة سحابي مجاني (Tesla T4) بدون استهلاك موارد جهازك
# 1. إغلاق أي جلسات سابقة وتحرير المنافذ
!fuser -k 8000/tcp 2>/dev/null
!pkill -f cloudflared 2>/dev/null
# 2. تثبيت الحزم المطلوبة وتنزيل نفق Cloudflare
!wget -q -nc -O /usr/local/bin/cloudflared https://github.com/cloudflare/cloudflared/releases/latest/download/cloudflared-linux-amd64
!chmod +x /usr/local/bin/cloudflared
!pip install -q -U --no-cache-dir --pre "yt-dlp[default]"
!pip install -q -U --no-cache-dir demucs soundfile scipy fastapi uvicorn requests
import os, glob, shutil, subprocess, threading, time, re, gc
import torch
from fastapi import FastAPI, HTTPException, BackgroundTasks
from fastapi.middleware.cors import CORSMiddleware
from fastapi.responses import FileResponse, JSONResponse
import uvicorn, yt_dlp
app = FastAPI(title="Naqawa Cloud Engine")
app.add_middleware(
CORSMiddleware,
allow_origins=["*"],
allow_credentials=True,
allow_methods=["*"],
allow_headers=["*"],
)
CACHE_DIR = "/content/audio_cache"
os.makedirs(CACHE_DIR, exist_ok=True)
COOKIE_FILE = "/content/cookies.txt"
task_status = {}
def extract_video_id(url: str):
patterns = [
r'(?:v=|\/)([0-9A-Za-z_-]{11})(?:[&?]|$)',
r'youtu\.be\/([0-9A-Za-z_-]{11})',
r'embed\/([0-9A-Za-z_-]{11})',
r'shorts\/([0-9A-Za-z_-]{11})'
]
for p in patterns:
m = re.search(p, url)
if m:
return m.group(1)
return None
def download_audio_safe(video_id: str, raw_template: str, work_dir: str):
client_profiles = [
['tv_downgraded', 'tv'],
['web_embedded'],
['android_vr', 'mweb'],
['ios', 'android']
]
last_err = ""
for client in client_profiles:
try:
download_opts = {
'format': 'bestaudio/best',
'outtmpl': raw_template,
'quiet': True,
'no_warnings': True,
'source_address': '0.0.0.0',
'extractor_args': {
'youtube': {
'player_client': client,
'player_skip': ['webpage', 'configs']
}
}
}
if os.path.exists(COOKIE_FILE):
download_opts['cookiefile'] = COOKIE_FILE
with yt_dlp.YoutubeDL(download_opts) as ydl:
ydl.download([f"https://www.youtube.com/watch?v={video_id}"])
downloaded = glob.glob(os.path.join(work_dir, "raw_audio.*"))
if downloaded:
return downloaded[0]
except Exception as e:
last_err = str(e)
continue
raise Exception(f"تعذر سحب الصوت: {last_err}")
def background_processor(video_id: str, url: str):
cached_file = os.path.join(CACHE_DIR, f"{video_id}.mp3")
work_dir = f"/content/work_{video_id}"
os.makedirs(work_dir, exist_ok=True)
raw_template = os.path.join(work_dir, "raw_audio.%(ext)s")
try:
task_status[video_id] = {"status": "processing", "stage": "⬇️ سحب الصوت بدون قيود..."}
raw_file = download_audio_safe(video_id, raw_template, work_dir)
task_status[video_id] = {"status": "processing", "stage": "🎛️ تجهيز ملف الترددات (WAV)..."}
input_wav = os.path.join(work_dir, "input.wav")
subprocess.run(["ffmpeg", "-y", "-i", raw_file, "-vn", "-ar", "44100", "-ac", "2", input_wav], check=True)
task_status[video_id] = {"status": "processing", "stage": "🧠 فصل الموسيقى بذكاء Demucs v4..."}
cmd = [
"demucs", "--two-stems", "vocals",
"-d", "cuda" if torch.cuda.is_available() else "cpu",
"-n", "htdemucs",
"--segment", "7",
"-o", work_dir,
input_wav
]
res = subprocess.run(cmd, capture_output=True, text=True)
if res.returncode != 0:
raise Exception(f"خطأ Demucs: {res.stderr[:200]}")
vocals_list = glob.glob(os.path.join(work_dir, "**", "vocals.wav"), recursive=True)
if not vocals_list:
raise Exception("تعذر العثور على المسار الصوتي المستخرج")
vocals_path = vocals_list[0]
task_status[video_id] = {"status": "processing", "stage": "💾 تصدير وحفظ المسار النقي..."}
subprocess.run(["ffmpeg", "-y", "-i", vocals_path, "-b:a", "192k", cached_file], check=True)
task_status[video_id] = {"status": "ready"}
except Exception as e:
task_status[video_id] = {"status": "error", "detail": str(e)}
finally:
shutil.rmtree(work_dir, ignore_errors=True)
if torch.cuda.is_available():
torch.cuda.empty_cache()
gc.collect()
@app.get("/")
def health():
return {"status": "online", "device": "CUDA" if torch.cuda.is_available() else "CPU"}
@app.get("/process")
@app.post("/process")
def process_endpoint(url: str, background_tasks: BackgroundTasks):
video_id = extract_video_id(url)
if not video_id:
return JSONResponse(status_code=400, content={"detail": "رابط الفيديو غير صالح"})
cached_file = os.path.join(CACHE_DIR, f"{video_id}.mp3")
if os.path.exists(cached_file):
return {"status": "ready", "video_id": video_id}
if video_id in task_status and task_status[video_id]["status"] == "processing":
return {"status": "processing", "video_id": video_id}
task_status[video_id] = {"status": "processing", "stage": "بدء الجدولة السحابية..."}
background_tasks.add_task(background_processor, video_id, url)
return {"status": "processing", "video_id": video_id}
@app.get("/status/{video_id}")
def status_endpoint(video_id: str):
cached_file = os.path.join(CACHE_DIR, f"{video_id}.mp3")
if os.path.exists(cached_file):
return {"status": "ready", "video_id": video_id}
if video_id in task_status:
return task_status[video_id]
return JSONResponse(status_code=404, content={"status": "error", "detail": "المهمة غير مسجلة"})
@app.get("/audio/{video_id}")
def stream_audio(video_id: str):
file_path = os.path.join(CACHE_DIR, f"{video_id}.mp3")
if os.path.exists(file_path):
return FileResponse(file_path, media_type="audio/mpeg")
raise HTTPException(status_code=404)
threading.Thread(target=lambda: uvicorn.run(app, host="127.0.0.1", port=8000, log_level="warning"), daemon=True).start()
time.sleep(2)
tunnel = subprocess.Popen(["cloudflared", "tunnel", "--url", "http://127.0.0.1:8000"], stdout=subprocess.PIPE, stderr=subprocess.STDOUT, text=True)
public_url = None
for line in tunnel.stdout:
m = re.search(r'https://[a-zA-Z0-9-]+\.trycloudflare\.com', line)
if m:
public_url = m.group(0)
break
print("\n" + "="*60)
print(f"🔥 انسخ هذا الرابط وضعه في الإضافة:\n{public_url}")
print("="*60 + "\n")
شغّل المعالجة محلياً عبر معالجك (CPU) أو كرت الشاشة (NVIDIA GPU)
افتح موجه الأوامر (CMD أو Terminal)، ونفّذ الأوامر التالية بالترتيب (سيتم إنشاء كل شيء وتشغيله داخل مجلد التنزيلات Downloads تلقائياً):
audio_cache داخل مجلد التنزيلات بجانب ملف السيرفر. يمكنك تغيير المسار بتمرير الأمر: --cache-dir "مسار_المجلد_الجديد" عند تشغيل السيرفر.
ماذا يحدث في نظامك؟ وكيف تحذف الأداة كلياً بنقرة واحدة دون ترك أي أثر
جميع مكتبات الذكاء الاصطناعي (PyTorch, Demucs) تُثبت داخل مجلد البيئة naqawa_env فقط، ولا يتم تعديل أو تنزيل أي شيء في بايثون النظام أو مسارات النظام العامة.
على نظام Windows لا يتم تعديل الـ Registry أبداً، وعلى Linux لا يتم تعديل أي ملفات ضبط بالنظام (Config files). الأداة محمولة بالكامل (Portable).
في الخيار المحلي، تُعالج المقاطع وتُحفظ داخل مجلد audio_cache على قرصك، ولا يخرج أي مسار صوتي أو رابط خارج شبكتك الخاصة.
naqawa.zip، ويمكنك حذفه يدوياً كأي مجلد عادي في أي وقت.