from flask import Flask, send_file, jsonify from selenium import webdriver from selenium.webdriver.chrome.service import Service from selenium.webdriver.chrome.options import Options from selenium.webdriver.common.by import By from selenium.webdriver.support.ui import WebDriverWait from selenium.webdriver.support import expected_conditions as EC from webdriver_manager.chrome import ChromeDriverManager import requests import time import io import shutil import os import socket app = Flask(__name__) mobile_emulation = { "deviceMetrics": {"width": 360, "height": 640, "pixelRatio": 3.0}, "userAgent": "Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/137.0.0.0 Mobile Safari/537.36" } def get_instagram_ip(): try: # Resolve instagram.com to IP using Python (which usually works better in containers) ip = socket.gethostbyname("www.instagram.com") print(f"DEBUG: Resolved www.instagram.com to {ip}") return ip except Exception as e: print(f"DEBUG: DNS Resolution failed: {e}") return None def get_video_stream(target_url): chrome_options = Options() # 1. Resolve IP manually ig_ip = get_instagram_ip() if ig_ip: # Force Chrome to map www.instagram.com to the resolved IP # This bypasses Chrome's internal DNS resolver chrome_options.add_argument(f'--host-resolver-rules=MAP www.instagram.com {ig_ip}, MAP .instagram.com {ig_ip}') # 2. Standard Docker Flags chrome_options.add_argument('--headless=new') chrome_options.add_argument('--no-sandbox') chrome_options.add_argument('--disable-dev-shm-usage') chrome_options.add_argument('--disable-gpu') # 3. Network Flags chrome_options.add_argument('--dns-prefetch-disable') chrome_options.add_argument('--disable-features=NetworkService') # 4. User Data user_data_dir = f'/tmp/chrome-user-data-{int(time.time())}' chrome_options.add_argument(f'--user-data-dir={user_data_dir}') chrome_options.add_experimental_option("mobileEmulation", mobile_emulation) service = Service(ChromeDriverManager().install()) driver = webdriver.Chrome(service=service, options=chrome_options) try: print(f"Navigating to: {target_url}") driver.get(target_url) wait = WebDriverWait(driver, 20) video_element = wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, "video"))) video_src = video_element.get_attribute('src') print(f"Found Video SRC: {video_src}") if not video_src: raise Exception("No video src found") # Use Python requests to download (it handles DNS better) session = requests.Session() headers = { "User-Agent": mobile_emulation["userAgent"], "Referer": "https://www.instagram.com/", } response = session.get(video_src, headers=headers, stream=True) if response.status_code in [200, 206]: return io.BytesIO(response.content) else: raise Exception(f"Download failed: {response.status_code}") finally: try: driver.quit() except: pass if os.path.exists(user_data_dir): shutil.rmtree(user_data_dir, ignore_errors=True) @app.route('/download/') def download_route(link): if not link.startswith('http'): link = f'https://{link}' try: print(f"Processing: {link}") video_stream = get_video_stream(link) return send_file( video_stream, mimetype='video/mp4', as_attachment=True, download_name=f'insta_{int(time.time())}.mp4' ) except Exception as e: print(f"ERROR: {e}") return jsonify({"error": str(e), "logs": "Check logs"}), 500 @app.route('/') def home(): return "Instagram Downloader (DNS Bypass Mode)" if __name__ == '__main__': app.run(host='0.0.0.0', port=7860)