Skip to content

Instantly share code, notes, and snippets.

@magicxor
Created June 24, 2024 22:28
Show Gist options
  • Select an option

  • Save magicxor/135e77be98fe3577b88f6d8d3aa18cb2 to your computer and use it in GitHub Desktop.

Select an option

Save magicxor/135e77be98fe3577b88f6d8d3aa18cb2 to your computer and use it in GitHub Desktop.
Live audio transcription via faster-whisper-server WS /v1/audio/transcriptions endpoint
using System.Buffers;
using System.Net.WebSockets;
using System.Text;
using NAudio.Wave;
namespace ConsoleApp1;
public class Program
{
public static async Task Main(string[] args)
{
var cancellationTokenSource = new CancellationTokenSource();
var cancellationToken = cancellationTokenSource.Token;
var webSocket = new ClientWebSocket();
await webSocket.ConnectAsync(new Uri("ws://localhost:8000/v1/audio/transcriptions"), cancellationToken);
var initMessage =
$$"""
{"uid": "{{Guid.NewGuid()}}", "language": "en", "task": "transcribe", "model": "small.en", "use_vad": false}
""";
// await webSocket.SendAsync(Encoding.UTF8.GetBytes(initMessage), WebSocketMessageType.Text, true, cancellationToken);
var waveIn = new WaveInEvent
{
WaveFormat = new WaveFormat(rate: 16_000, bits: 16, channels: 1),
};
waveIn.DataAvailable += (_, e) =>
{
Task.Run(() =>
{
if (webSocket.State == WebSocketState.Open)
webSocket.SendAsync(e.Buffer,
WebSocketMessageType.Binary,
WebSocketMessageFlags.EndOfMessage | WebSocketMessageFlags.DisableCompression,
cancellationToken);
},
cancellationToken);
};
waveIn.StartRecording();
Console.WriteLine("Recording...");
using var memoryStream = new MemoryStream();
while (webSocket.State == WebSocketState.Open)
{
WebSocketReceiveResult result;
do
{
var buffer = ArrayPool<byte>.Shared.Rent(1024);
try
{
result = await webSocket.ReceiveAsync(buffer, cancellationToken);
var bytesReceived = result.Count;
if (result.MessageType == WebSocketMessageType.Close)
{
if (webSocket.State == WebSocketState.Open)
await webSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, "server closed connection", cancellationToken);
await cancellationTokenSource.CancelAsync();
}
else
{
var memory = buffer.AsMemory(0, bytesReceived);
await memoryStream.WriteAsync(memory, cancellationToken);
}
}
finally
{
ArrayPool<byte>.Shared.Return(buffer);
}
} while (!result.EndOfMessage);
if (result.MessageType == WebSocketMessageType.Text)
{
var streamPosition = (int)memoryStream.Position;
var buffer = ArrayPool<byte>.Shared.Rent(streamPosition);
var memory = buffer.AsMemory(0, streamPosition);
try
{
memoryStream.Position = 0;
await memoryStream.ReadExactlyAsync(memory, cancellationToken);
var msgString = Encoding.UTF8.GetString(memory.Span);
Console.WriteLine(msgString);
}
finally
{
ArrayPool<byte>.Shared.Return(buffer);
}
}
memoryStream.Position = 0;
}
waveIn.StopRecording();
if (webSocket.State == WebSocketState.Open)
await webSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, "client closed connection", cancellationToken);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment