mirror of https://github.com/ErsatzTV/ErsatzTV.git
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
169 lines
6.3 KiB
169 lines
6.3 KiB
@page "/media/trakt/lists" |
|
@using ErsatzTV.Application.MediaCollections |
|
@using ErsatzTV.Application.Configuration |
|
@implements IDisposable |
|
@inject IDialogService _dialog |
|
@inject IMediator _mediator |
|
@inject ISnackbar _snackbar |
|
@inject ILogger<TraktLists> _logger |
|
@inject IEntityLocker _locker |
|
@inject ChannelWriter<IBackgroundServiceRequest> _workerChannel |
|
|
|
<MudContainer MaxWidth="MaxWidth.ExtraLarge" Class="pt-8"> |
|
<div> |
|
<MudButton Variant="Variant.Filled" |
|
Color="Color.Primary" |
|
Disabled="@_locker.IsTraktLocked()" |
|
OnClick="@(_ => AddTraktList())"> |
|
Add Trakt List |
|
</MudButton> |
|
</div> |
|
<MudTable Class="mt-4" |
|
Hover="true" |
|
@bind-RowsPerPage="@_traktListsRowsPerPage" |
|
ServerData="@(new Func<TableState, Task<TableData<TraktListViewModel>>>(ServerReloadTraktLists))" |
|
Dense="true" |
|
@ref="_traktListsTable"> |
|
<ToolBarContent> |
|
<MudText Typo="Typo.h6">Trakt Lists</MudText> |
|
</ToolBarContent> |
|
<ColGroup> |
|
<col/> |
|
<col/> |
|
<col/> |
|
<col style="width: 180px;"/> |
|
</ColGroup> |
|
<HeaderContent> |
|
<MudTh>Id</MudTh> |
|
<MudTh>Name</MudTh> |
|
<MudTh>Match Status</MudTh> |
|
<MudTh/> |
|
</HeaderContent> |
|
<RowTemplate> |
|
<MudTd DataLabel="Id">@context.Slug</MudTd> |
|
<MudTd DataLabel="Name">@context.Name</MudTd> |
|
<MudTd DataLabel="Match Status">@context.MatchCount of @context.ItemCount</MudTd> |
|
<MudTd> |
|
<div style="align-items: center; display: flex;"> |
|
<MudTooltip Text="Search Trakt List"> |
|
<MudIconButton Icon="@Icons.Material.Filled.Search" |
|
Disabled="@_locker.IsTraktLocked()" |
|
Link="@($"search?query=trakt_list%3a{context.TraktId}")"> |
|
</MudIconButton> |
|
</MudTooltip> |
|
<MudTooltip Text="Match Trakt List Items"> |
|
<MudIconButton Icon="@Icons.Material.Filled.Refresh" |
|
Disabled="@_locker.IsTraktLocked()" |
|
OnClick="@(_ => MatchListItems(context))"> |
|
</MudIconButton> |
|
</MudTooltip> |
|
<MudTooltip Text="Delete Trakt List"> |
|
<MudIconButton Icon="@Icons.Material.Filled.Delete" |
|
Disabled="@_locker.IsTraktLocked()" |
|
OnClick="@(_ => DeleteTraktList(context))"> |
|
</MudIconButton> |
|
</MudTooltip> |
|
</div> |
|
</MudTd> |
|
</RowTemplate> |
|
<PagerContent> |
|
<MudTablePager/> |
|
</PagerContent> |
|
</MudTable> |
|
</MudContainer> |
|
|
|
@code { |
|
private readonly CancellationTokenSource _cts = new(); |
|
|
|
private MudTable<TraktListViewModel> _traktListsTable; |
|
|
|
private int _traktListsRowsPerPage = 10; |
|
|
|
public void Dispose() |
|
{ |
|
_cts.Cancel(); |
|
_cts.Dispose(); |
|
} |
|
|
|
protected override void OnInitialized() => _locker.OnTraktChanged += LockChanged; |
|
|
|
protected override async Task OnParametersSetAsync() => _traktListsRowsPerPage = await _mediator.Send(new GetConfigElementByKey(ConfigElementKey.TraktListsPageSize), _cts.Token) |
|
.Map(maybeRows => maybeRows.Match(ce => int.TryParse(ce.Value, out int rows) ? rows : 10, () => 10)); |
|
|
|
private void LockChanged(object sender, EventArgs e) => |
|
InvokeAsync( |
|
async () => |
|
{ |
|
StateHasChanged(); |
|
if (_traktListsTable != null && !_locker.IsTraktLocked()) |
|
{ |
|
await _traktListsTable.ReloadServerData(); |
|
} |
|
}); |
|
|
|
private async Task MatchListItems(TraktListViewModel traktList) |
|
{ |
|
if (_locker.LockTrakt()) |
|
{ |
|
await _workerChannel.WriteAsync(new MatchTraktListItems(traktList.Id), _cts.Token); |
|
} |
|
} |
|
|
|
private async Task DeleteTraktList(TraktListViewModel traktList) |
|
{ |
|
if (_locker.LockTrakt()) |
|
{ |
|
var parameters = new DialogParameters { { "EntityType", "Trakt List" }, { "EntityName", traktList.Name } }; |
|
var options = new DialogOptions { CloseButton = true, MaxWidth = MaxWidth.ExtraSmall }; |
|
|
|
IDialogReference dialog = await _dialog.ShowAsync<DeleteDialog>("Delete Trakt List", parameters, options); |
|
DialogResult result = await dialog.Result; |
|
if (!result.Canceled) |
|
{ |
|
await _workerChannel.WriteAsync(new DeleteTraktList(traktList.Id), _cts.Token); |
|
} |
|
else |
|
{ |
|
_locker.UnlockTrakt(); |
|
} |
|
} |
|
} |
|
|
|
private async Task<TableData<TraktListViewModel>> ServerReloadTraktLists(TableState state) |
|
{ |
|
try |
|
{ |
|
await _mediator.Send(new SaveConfigElementByKey(ConfigElementKey.TraktListsPageSize, state.PageSize.ToString()), _cts.Token); |
|
|
|
PagedTraktListsViewModel data = await _mediator.Send(new GetPagedTraktLists(state.Page, state.PageSize), _cts.Token); |
|
return new TableData<TraktListViewModel> { TotalItems = data.TotalCount, Items = data.Page }; |
|
} |
|
catch (Exception ex) when (ex is TaskCanceledException or OperationCanceledException or AggregateException) |
|
{ |
|
return new TableData<TraktListViewModel> |
|
{ |
|
TotalItems = 0, |
|
Items = Array.Empty<TraktListViewModel>() |
|
}; |
|
} |
|
} |
|
|
|
private async Task AddTraktList() |
|
{ |
|
if (_locker.LockTrakt()) |
|
{ |
|
var options = new DialogOptions { CloseButton = true, MaxWidth = MaxWidth.Small }; |
|
IDialogReference dialog = await _dialog.ShowAsync<AddTraktListDialog>("Add Trakt List", options); |
|
DialogResult result = await dialog.Result; |
|
if (!result.Canceled && result.Data is string url) |
|
{ |
|
await _workerChannel.WriteAsync(new AddTraktList(url), _cts.Token); |
|
} |
|
else |
|
{ |
|
_locker.UnlockTrakt(); |
|
} |
|
} |
|
} |
|
|
|
} |