Illustrations/web/core/views_tts.py

53 lines
1.9 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# core/views_tts.py
from django.contrib.auth.decorators import login_required, user_passes_test
from django.http import HttpResponse, HttpResponseBadRequest, HttpResponseForbidden
from django.shortcuts import get_object_or_404
from django.views.decorators.http import require_GET
from .models import Entry
# If you use the OpenAI SDK:
from openai import OpenAI
import os
client = OpenAI(api_key=os.environ.get("OPENAI_API_KEY", ""))
def _is_staff(user):
return user.is_authenticated and (user.is_staff or user.is_superuser)
@login_required
@user_passes_test(_is_staff)
@require_GET
def api_tts_for_entry(request, entry_id):
"""
Generate MP3 speech for an entry (staffonly).
"""
entry = get_object_or_404(Entry, pk=entry_id)
# ---- Build safe combined text (avoid TypeError) ----
ill = (entry.illustration or "").strip()
app = (entry.application or "").strip()
if ill and not any(ill.endswith(p) for p in ".!?…"):
ill = ill + "."
combined = " ".join([t for t in (ill, app) if t]).strip()
if not combined:
return HttpResponseBadRequest("No text available for this entry.")
# ---- Call OpenAI TTS (MP3) ----
try:
# Use the streaming helper for broad SDK compatibility.
# It yields MP3 audio bytes by default.
with client.audio.speech.with_streaming_response.create(
model="gpt-4o-mini-tts",
voice="alloy", # or another supported voice
input=combined,
) as resp:
audio_bytes = resp.read() # raw MP3 bytes
except Exception as e:
return HttpResponse(f"OpenAI TTS failed: {e}", status=500, content_type="text/plain")
# ---- Serve as audio/mpeg ----
resp = HttpResponse(audio_bytes, content_type="audio/mpeg")
resp["Content-Disposition"] = 'inline; filename="entry-tts.mp3"'
resp["Cache-Control"] = "no-store"
return resp