Spaces:
Runtime error
Runtime error
| from fastapi.middleware.cors import CORSMiddleware | |
| from fastapi.responses import FileResponse | |
| from starlette.background import BackgroundTask | |
| import subprocess | |
| import os | |
| import uuid | |
| import json | |
| import requests | |
| import time | |
| import hashlib | |
| import re | |
| import urllib.parse | |
| app = FastAPI() | |
| app.add_middleware( | |
| CORSMiddleware, | |
| allow_origins=["*"], | |
| allow_credentials=True, | |
| allow_methods=["*"], | |
| allow_headers=["*"], | |
| ) | |
| TEMP_DIR = "/tmp/fb_cache" | |
| if not os.path.exists(TEMP_DIR): | |
| os.makedirs(TEMP_DIR) | |
| MAX_FILE_AGE = 1800 | |
| def cleanup(file_path: str): | |
| if os.path.exists(file_path): | |
| os.remove(file_path) | |
| def clean_fb_url(url: str): | |
| if not url: return None | |
| url = url.replace('\\/', '/') | |
| try: | |
| url = json.loads(f'"{url}"') | |
| except: pass | |
| return urllib.parse.unquote(url).replace('&', '&') | |
| def get_ffprobe_info(file_path): | |
| try: | |
| cmd = ['ffprobe', '-v', 'error', '-show_entries', 'stream=codec_type', '-of', 'json', file_path] | |
| result = subprocess.run(cmd, capture_output=True, text=True) | |
| data = json.loads(result.stdout) | |
| return [s['codec_type'] for s in data.get('streams', [])] | |
| except: return [] | |
| def root(): | |
| return {"message": "Bumiz Facebook Pro API Active"} | |
| async def download_private_fb(payload: dict = Body(...)): | |
| html_source = payload.get("html", "") | |
| target_quality = payload.get("quality", "original") # original, 720, 480, 240 | |
| if not html_source: | |
| return {"success": False, "error": "HTML Source is empty."} | |
| # Video & Audio Extraction Logic | |
| video_url = None | |
| audio_url = None | |
| # HD သို့မဟုတ် Progressive Link ကို အရင်ရှာခြင်း | |
| hd_match = re.search(r'"browser_native_hd_url":"([^"]+)"', html_source) | |
| sd_match = re.search(r'"browser_native_sd_url":"([^"]+)"', html_source) | |
| if hd_match: video_url = clean_fb_url(hd_match.group(1)) | |
| elif sd_match: video_url = clean_fb_url(sd_match.group(1)) | |
| # Separate Streams ရှာဖွေခြင်း | |
| v_matches = re.findall(r'"mime_type":"video[^"]+".*?"base_url":"([^"]+)"', html_source) | |
| a_matches = re.findall(r'"mime_type":"audio[^"]+".*?"base_url":"([^"]+)"', html_source) | |
| if not video_url and v_matches: video_url = clean_fb_url(v_matches[0]) | |
| if a_matches: audio_url = clean_fb_url(a_matches[0]) | |
| if not video_url: | |
| return {"success": False, "error": "Video link not found in source."} | |
| file_id = hashlib.md5(f"{video_url}_{target_quality}".encode()).hexdigest() | |
| final_video = os.path.join(TEMP_DIR, f"{file_id}.mp4") | |
| # Cache Check | |
| if os.path.exists(final_video): | |
| os.utime(final_video, None) | |
| return {"success": True, "method": "Cache", "video_url": f"get_file?id={file_id}.mp4", "size": os.path.getsize(final_video)} | |
| # Processing | |
| try: | |
| v_tmp = os.path.join(TEMP_DIR, f"{uuid.uuid4()}_v.mp4") | |
| a_tmp = os.path.join(TEMP_DIR, f"{uuid.uuid4()}_a.mp3") | |
| # Download streams | |
| headers = {'User-Agent': 'Mozilla/5.0'} | |
| with open(v_tmp, 'wb') as f: f.write(requests.get(video_url, headers=headers).content) | |
| if audio_url: | |
| with open(a_tmp, 'wb') as f: f.write(requests.get(audio_url, headers=headers).content) | |
| # Build FFmpeg Command (Force H.264 & AAC) | |
| cmd = ['ffmpeg', '-y', '-i', v_tmp] | |
| if os.path.exists(a_tmp) and os.path.getsize(a_tmp) > 1000: | |
| cmd += ['-i', a_tmp, '-map', '0:v:0', '-map', '1:a:0'] | |
| # Quality Scaling if needed | |
| if target_quality != "original": | |
| cmd += ['-vf', f"scale=w='trunc(oh*a/2)*2':h={target_quality}"] | |
| cmd += ['-c:v', 'libx264', '-preset', 'ultrafast', '-crf', '23', '-c:a', 'aac', '-b:a', '128k', '-movflags', '+faststart', final_video] | |
| subprocess.run(cmd, check=True, capture_output=True) | |
| if os.path.exists(v_tmp): os.remove(v_tmp) | |
| if os.path.exists(a_tmp): os.remove(a_tmp) | |
| return { | |
| "success": True, | |
| "method": "Bumiz Engine", | |
| "video_url": f"get_file?id={file_id}.mp4", | |
| "size": os.path.getsize(final_video) | |
| } | |
| except Exception as e: | |
| return {"success": False, "error": str(e)} | |
| async def get_file(id: str): | |
| file_path = os.path.join(TEMP_DIR, id) | |
| if os.path.exists(file_path): | |
| return FileResponse(file_path, media_type="video/mp4", filename=f"fb_bumiz_{id}", background=BackgroundTask(cleanup, file_path)) | |
| raise HTTPException(status_code=404) |