Transcripcion en vivo + transcripcion mejorada

This commit is contained in:
2025-07-16 15:50:13 +00:00
parent 8386b685d6
commit 89168522b6
12 changed files with 293 additions and 223 deletions

View File

@ -11,31 +11,13 @@ defmodule WhisperLiveWeb.AudioChannel do
{:ok, socket}
end
def handle_in("audio_chunk", %{"data" => base64_audio, "sample_rate" => sample_rate}, socket) do
# 1. Decodificas el audio base64
{:ok, bin} = Base.decode64(base64_audio)
# 2. Guardas o procesas el chunk de audio
# Podrías escribirlo en un archivo temporal para enviar a Whisper
tmpfile = tmp_path("chunk_#{socket.assigns.ref}")
:ok = File.write!(tmpfile, encode_wav(bin, sample_rate))
# 3. Llamas a la transcripción del chunk (podría ser sync o async)
case send_to_whisper(tmpfile) do
{:ok, transcription} ->
# 4. Envías el texto parcial por PubSub o Push a LiveView/cliente
Phoenix.PubSub.broadcast(YourApp.PubSub, "transcription:#{socket.assigns.ref}", {:transcription, transcription})
{:error, reason} ->
Logger.error("Error en transcripción parcial: #{inspect(reason)}")
end
File.rm(tmpfile)
def handle_in("audio_chunk", %{"data" => data, "sample_rate" => rate}, socket) do
{:ok, binary} = Base.decode64(data)
AudioBuffer.append(socket_id(socket), {rate, binary})
Logger.info("📦 Chunk recibido: #{byte_size(binary)} bytes, sample_rate: #{rate}")
{:noreply, socket}
end
def handle_in("stop_audio", _payload, socket) do
Logger.info("🛑 Grabación detenida por cliente")
@ -47,16 +29,8 @@ defmodule WhisperLiveWeb.AudioChannel do
filename = "recordings/recording_#{System.system_time(:millisecond)}.wav"
File.mkdir_p!("recordings")
File.write!(filename, encode_wav(merged, rate))
Logger.info("💾 Audio guardado en #{filename}")
# 🔁 Transcribir automáticamente
case send_to_whisper(filename) do
{:ok, response} ->
Logger.info("📝 Transcripción recibida: #{response}")
{:error, reason} ->
Logger.error("❌ Error al transcribir: #{inspect(reason)}")
end
whisper_large(filename)
File.rm!(filename)
_ ->
Logger.warning("⚠️ No se recibieron chunks de audio")
end
@ -93,18 +67,16 @@ defmodule WhisperLiveWeb.AudioChannel do
>> <> data
end
defp send_to_whisper(filepath) do
url = "http://localhost:4000/infer"
defp whisper_large(filepath) do
url = "http://localhost:4000/large"
{:ok, file_bin} = File.read(filepath)
filename = Path.basename(filepath)
headers = [
{'Content-Type', 'multipart/form-data; boundary=----ElixirBoundary'}
{'Content-Type', 'multipart/form-data; boundary=----ElixirBoundary'}
]
body =
[
body = [
"------ElixirBoundary\r\n",
"Content-Disposition: form-data; name=\"file\"; filename=\"#{filename}\"\r\n",
"Content-Type: audio/wav\r\n\r\n",
@ -114,21 +86,17 @@ defmodule WhisperLiveWeb.AudioChannel do
:httpc.request(:post, {url, headers, 'multipart/form-data; boundary=----ElixirBoundary', body}, [], [])
|> case do
{:ok, {{_, 200, _}, _headers, body}} ->
{:ok, to_string(body)}
{:ok, {{_, 200, _}, _headers, body}} ->
# Logger.info("transcripcion mejorada --------------------------\n -> > #{IO.iodata_to_binary(body)}")
Phoenix.PubSub.broadcast(WhisperLive.PubSub, "transcription", {:transcription_m, "#{IO.iodata_to_binary(body)}"})
{:ok, {{_, status, _}, _, body}} ->
{:error, {:http_error, status, to_string(body)}}
{:ok, "#{IO.iodata_to_binary(body)}"}
error ->
{:error, error}
{:ok, {{_, status, _}, _, body}} ->
{:error, {:http_error, status, IO.iodata_to_binary(body)}}
error ->
{:error, error}
end
end
defp tmp_path(prefix) do
unique = :erlang.unique_integer([:positive]) |> Integer.to_string()
filename = prefix <> "_" <> unique <> ".wav"
Path.join(System.tmp_dir!(), filename)
end
end