using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.SignalR;
using SameBeat.Api.Hubs;
using SameBeat.Application.DTO;
using SameBeat.Application.Interfejsy;
using SameBeat.Application.Komendy;
namespace SameBeat.Api.Controllers;
///
/// Sterowanie muzyka przez hosta (ETAP 4). Trasa zaczyna sie od "api/host", wiec jest automatycznie
/// chroniona [Authorize] przez KonwencjaAutoryzacjiHosta.
///
/// KONTEKST: muzyka NIE idzie przez LiveKit ani SignalR jako dzwiek -- kazda przegladarka (host i
/// kazdy widz) samodzielnie odtwarza TEN SAM plik audio spod Utwor.Url, a backend trzyma tylko
/// "zegar" (kiedy sie zaczelo, od ktorego miejsca) i widzowie synchronizuja swoja pozycje
/// odtwarzania do tego zegara. To jak radio internetowe.
///
/// Po kazdej akcji sterujacej zegarem rozsylamy "StanMuzykiZmieniony" (payload StanMuzykiDto) do
/// WSZYSTKICH klientow. Zmiany samej biblioteki/kolejki (dodanie/usuniecie utworu) rozsylamy jako
/// "MuzykaZmieniona" z aktualna kolejka (payload List<PozycjaPlaylistyDto>).
///
[ApiController]
[Route("api/host/music")]
public class HostMusicController : ControllerBase
{
private readonly ISerwisMuzyki _serwisMuzyki;
private readonly IHubContext _hubKontekst;
public HostMusicController(ISerwisMuzyki serwisMuzyki, IHubContext hubKontekst)
{
_serwisMuzyki = serwisMuzyki;
_hubKontekst = hubKontekst;
}
[HttpPost("utwory")]
public async Task DodajUtworAsync([FromBody] DodajUtworKomenda komenda, CancellationToken token)
{
var wynik = await _serwisMuzyki.DodajUtworAsync(komenda, token);
if (!wynik.Sukces || wynik.Dane is null)
{
return BadRequest(new { blad = wynik.Blad });
}
return Ok(wynik.Dane);
}
/// Cala biblioteka utworow -- do wyboru przy dodawaniu na playliste.
[HttpGet("utwory")]
public async Task PobierzUtworyAsync(CancellationToken token)
{
var wynik = await _serwisMuzyki.PobierzUtworyAsync(token);
if (!wynik.Sukces || wynik.Dane is null)
{
return BadRequest(new { blad = wynik.Blad });
}
return Ok(wynik.Dane);
}
[HttpPost("playlista/dodaj")]
public async Task DodajDoPlaylistyAsync([FromBody] DodajDoPlaylistyKomenda komenda, CancellationToken token)
{
var wynik = await _serwisMuzyki.DodajDoPlaylistyAsync(komenda.UtworId, token);
if (!wynik.Sukces || wynik.Dane is null)
{
return BadRequest(new { blad = wynik.Blad });
}
await _hubKontekst.Clients.All.SendAsync("MuzykaZmieniona", wynik.Dane, cancellationToken: token);
return Ok(wynik.Dane);
}
[HttpDelete("playlista/{pozycjaId:guid}")]
public async Task UsunZPlaylistyAsync(Guid pozycjaId, CancellationToken token)
{
var wynik = await _serwisMuzyki.UsunZPlaylistyAsync(pozycjaId, token);
if (!wynik.Sukces || wynik.Dane is null)
{
return BadRequest(new { blad = wynik.Blad });
}
await _hubKontekst.Clients.All.SendAsync("MuzykaZmieniona", wynik.Dane, cancellationToken: token);
return Ok(wynik.Dane);
}
/// Aktualna kolejka -- do wyswietlenia w panelu hosta po odswiezeniu strony.
[HttpGet("playlista")]
public async Task PobierzPlaylisteAsync(CancellationToken token)
{
var wynik = await _serwisMuzyki.PobierzPlaylisteAsync(token);
if (!wynik.Sukces || wynik.Dane is null)
{
return BadRequest(new { blad = wynik.Blad });
}
return Ok(wynik.Dane);
}
[HttpPost("play")]
public async Task OdtworzAsync([FromBody] OdtworzKomenda komenda, CancellationToken token)
{
var wynik = await _serwisMuzyki.OdtworzAsync(komenda.UtworId, token);
return await RozglosStanMuzykiAsync(wynik, token);
}
[HttpPost("pause")]
public async Task WstrzymajAsync(CancellationToken token)
{
var wynik = await _serwisMuzyki.WstrzymajAsync(token);
return await RozglosStanMuzykiAsync(wynik, token);
}
[HttpPost("next")]
public async Task NastepnyAsync(CancellationToken token)
{
var wynik = await _serwisMuzyki.NastepnyAsync(token);
return await RozglosStanMuzykiAsync(wynik, token);
}
[HttpPost("poprzedni")]
public async Task PoprzedniAsync(CancellationToken token)
{
var wynik = await _serwisMuzyki.PoprzedniAsync(token);
return await RozglosStanMuzykiAsync(wynik, token);
}
[HttpPost("glosnosc")]
public async Task UstawGlosnoscAsync([FromBody] UstawGlosnoscKomenda komenda, CancellationToken token)
{
var wynik = await _serwisMuzyki.UstawGlosnoscAsync(komenda.Wartosc, token);
return await RozglosStanMuzykiAsync(wynik, token);
}
private async Task RozglosStanMuzykiAsync(WynikOperacji wynik, CancellationToken token)
{
if (!wynik.Sukces || wynik.Dane is null)
{
return BadRequest(new { blad = wynik.Blad });
}
await _hubKontekst.Clients.All.SendAsync("StanMuzykiZmieniony", wynik.Dane, cancellationToken: token);
return Ok(wynik.Dane);
}
}