using System; using System.Threading.Tasks; using System.Threading; using System.Collections.Generic; using Aurora.Services; using Aurora.Proto.Playback; using Aurora.Proto.General; using Aurora.Models.Media; namespace Aurora.RemoteImpl { public class RemotePlaybackServiceImpl : RemotePlaybackService.RemotePlaybackServiceBase { public override async Task GetSongStream(SongRequest request, Grpc.Core.IServerStreamWriter responseStream, Grpc.Core.ServerCallContext context) { BaseMedia originalSong = LibraryService.Instance.GetSong(request.Id); if (!(originalSong is LocalAudio)) { return; } //Copy media object to not interfere with other threads LocalAudio songCopy = new LocalAudio((LocalAudio)originalSong); try { //Load only if not already loaded. (Multiple clients may be requesting media) if (!songCopy.IsLoaded) { await songCopy.Load(); } //Send stream Console.WriteLine("Begin sending file"); byte[] buffer = new byte[2048]; // read in chunks of 2KB int bytesRead; while ((bytesRead = songCopy.DataStream.Read(buffer, 0, buffer.Length)) > 0) { Google.Protobuf.ByteString bufferByteString = Google.Protobuf.ByteString.CopyFrom(buffer); await responseStream.WriteAsync(new Chunk { Content = bufferByteString }); } Console.WriteLine("Done sending file"); } catch (Exception ex) { Console.WriteLine("Exception caught while sending audio file: " + ex.Message); } } } }