|
from flask import Flask, Response, request, stream_with_context |
|
import subprocess |
|
import shlex |
|
|
|
app = Flask(__name__) |
|
|
|
@app.route('/') |
|
def index(): |
|
return ''' |
|
<html> |
|
<body> |
|
<form action="/download" method="get"> |
|
<input type="url" name="url" style="width: 350px" required> |
|
<input type="submit"> |
|
</form> |
|
</body> |
|
</html> |
|
''' |
|
|
|
@app.route('/download') |
|
def download_file(): |
|
url = request.args.get('url') |
|
if not url: |
|
return 400 |
|
|
|
try: |
|
pre_command = f'proxychains yt-dlp --print format -f "best[height<400]/bestvideo[height<400]+bestaudio" -o - {shlex.quote(url)}' |
|
command = f'proxychains yt-dlp -f "best[height<400]/bestvideo[height<400]+bestaudio" -o - {shlex.quote(url)}' |
|
|
|
pre_check = subprocess.run( |
|
pre_command, |
|
shell=True, |
|
stdout=subprocess.PIPE, |
|
stderr=subprocess.PIPE |
|
) |
|
|
|
if pre_check.returncode != 0: |
|
error_msg = pre_check.stderr.decode('utf-8', 'ignore') |
|
app.logger.error(f"Pre-check failed: {error_msg}") |
|
return f"error: {error_msg}", 500 |
|
|
|
process = subprocess.Popen( |
|
command, |
|
shell=True, |
|
stdout=subprocess.PIPE, |
|
stderr=subprocess.PIPE, |
|
bufsize=8192 |
|
) |
|
|
|
def generate(): |
|
try: |
|
while True: |
|
chunk = process.stdout.read(8192) |
|
if not chunk: |
|
break |
|
yield chunk |
|
|
|
stderr = process.stderr.read() |
|
if process.wait() != 0: |
|
app.logger.error(f"error: {stderr.decode('utf-8', 'ignore')}") |
|
|
|
finally: |
|
if process.poll() is None: |
|
process.terminate() |
|
process.wait() |
|
|
|
filename = 'downloaded_video' |
|
|
|
headers = { |
|
'Content-Type': 'application/octet-stream', |
|
'Content-Disposition': f'attachment; filename="{filename}"' |
|
} |
|
|
|
return Response( |
|
stream_with_context(generate()), |
|
headers=headers |
|
) |
|
|
|
except Exception as e: |
|
return f"error: {str(e)}", 500 |
|
|
|
if __name__ == '__main__': |
|
app.run(host='0.0.0.0', port=7860) |