"""Render asmr/voices.json into asmr/audio/*.mp3 through the shared inference worker, plus a rain bed. python3 tools/asmr.py Keyless: calls inference.yolopreneur.lol as the gandora app. Skips files that already exist. Needs ffmpeg. """ import json, os, subprocess, sys, urllib.request, urllib.error ROOT = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) OUT = os.path.join(ROOT, "asmr", "audio") W = "https://inference.yolopreneur.lol/v1/speech" H = {"Content-Type": "application/json", "Origin": "https://gandora.yolopreneur.lol", "x-app": "gandora", "User-Agent": "gandora-asmr"} cfg = json.load(open(os.path.join(ROOT, "asmr", "voices.json"))) os.makedirs(OUT, exist_ok=True) fail = 0 bed = os.path.join(OUT, "bed-rain.mp3") if not os.path.exists(bed): subprocess.run(["ffmpeg", "-y", "-loglevel", "error", "-f", "lavfi", "-i", "anoisesrc=c=pink:a=0.5:d=60", "-f", "lavfi", "-i", "anoisesrc=c=brown:a=0.6:d=60", "-filter_complex", "[0]highpass=f=900,lowpass=f=7000,tremolo=f=7:d=0.25[a];[1]lowpass=f=300[b];" "[a][b]amix=inputs=2:weights=1 0.6,afade=t=in:d=2,afade=t=out:st=58:d=2,volume=0.6", "-b:a", "96k", bed], check=True) for v in cfg["voices"]: dst = os.path.join(OUT, v["id"] + ".mp3") if os.path.exists(dst): continue text = cfg["script"].replace("Hey...", "Hey... ", 1) if v.get("tags") else cfg["script"] text = v.get("lead", "") + text + v.get("tail", "") fmt = v.get("format", "mp3") body = {"model": v["model"], "voice": v["voice"], "input": text, "response_format": fmt} if v.get("speed"): body["speed"] = v["speed"] if v.get("style"): body["prompt"] = cfg["style"] try: with urllib.request.urlopen(urllib.request.Request(W, json.dumps(body).encode(), H), timeout=110) as r: data = r.read() except urllib.error.HTTPError as e: print("ERR", v["id"], e.code, e.read()[:200]); fail += 1; continue except Exception as e: print("ERR", v["id"], e); fail += 1; continue if fmt == "mp3": open(dst, "wb").write(data) else: tmp = dst + "." + fmt open(tmp, "wb").write(data) subprocess.run(["ffmpeg", "-y", "-loglevel", "error", "-i", tmp, "-b:a", "128k", dst], check=True) os.remove(tmp) print("ok", v["id"]) sys.exit(0)