#!/usr/bin/env python3 """Trimite un fișier (audio, imagine, etc.) direct într-un canal Discord. De ce există: `__AUDIO__:` (folosit de fast_commands.py) e interceptat de discord_bot.py DOAR când niciun bloc de text n-a fost deja streamat pe canal în turul curent. Într-un răspuns conversațional normal (acest proces, `claude_session.py`), fiecare bloc de text pe care Claude îl produce e trimis live prin `on_text` înainte ca răspunsul final să fie evaluat — deci prefixul `__AUDIO__:` ajunge mereu trimis ca text brut, nu convertit în attachment. Singura cale de a atașa un fișier dintr-un răspuns Claude obișnuit e apelul direct la REST API-ul Discord, cu tokenul botului. CLI: python3 tools/discord_send_file.py --channel --file /path/audio.wav [--text "mesaj"] Modul: from tools.discord_send_file import send_file send_file(channel_id, "/path/audio.wav", content="mesaj opțional") Channel ID: dacă nu-l știi din conversație, citește `sessions/active.json` (cheia e channel_id-ul; de obicei există o singură sesiune activă). """ import argparse import mimetypes import sys import httpx sys.path.insert(0, "/home/moltbot/echo-core") from src.credential_store import get_secret def send_file(channel_id: str, path: str, content: str | None = None, filename: str | None = None) -> dict: """Trimite un fișier direct pe canalul Discord dat, via REST API. Returns: {"ok": True, "message_id": "..."} sau {"ok": False, "error": "..."} """ token = get_secret("discord_token") if not token: return {"ok": False, "error": "discord_token lipsește din keyring (echo-core)."} filename = filename or path.rsplit("/", 1)[-1] mime = mimetypes.guess_type(filename)[0] or "application/octet-stream" try: with httpx.Client(timeout=30) as client, open(path, "rb") as f: resp = client.post( f"https://discord.com/api/v10/channels/{channel_id}/messages", headers={"Authorization": f"Bot {token}"}, files={"file": (filename, f, mime)}, data={"content": content} if content else {}, ) if resp.status_code not in (200, 201): return {"ok": False, "error": f"HTTP {resp.status_code}: {resp.text[:300]}"} return {"ok": True, "message_id": resp.json().get("id")} except Exception as e: return {"ok": False, "error": str(e)} if __name__ == "__main__": parser = argparse.ArgumentParser(description="Trimite un fișier direct pe un canal Discord") parser.add_argument("--channel", required=True, help="Channel ID Discord") parser.add_argument("--file", required=True, help="Cale către fișierul de trimis") parser.add_argument("--text", default=None, help="Text opțional care însoțește fișierul") args = parser.parse_args() result = send_file(args.channel, args.file, content=args.text) print(result) sys.exit(0 if result.get("ok") else 1)