Fixed bug where deletes of artifact groupings would not cascade
This commit is contained in:
128
OpenArchival.Blazor.Blog/BlogPostViewer.razor
Normal file
128
OpenArchival.Blazor.Blog/BlogPostViewer.razor
Normal file
@@ -0,0 +1,128 @@
|
||||
@using Microsoft.EntityFrameworkCore
|
||||
@using MudBlazor
|
||||
@using OpenArchival.DataAccess
|
||||
|
||||
@page "/articles/{ArticleIdString}"
|
||||
|
||||
@if (_article is not null)
|
||||
{
|
||||
@if (_article.ArtifactGroupings.Any()) {
|
||||
{
|
||||
<MudPaper Class="pa-4 ma-2 rounded overflow-y-auto" Style="max-height: 400px;" Elevation="3">
|
||||
<MudText Typo="Typo.h6">Related Artifacts</MudText>
|
||||
<MudDivider/>
|
||||
|
||||
<MudGrid Justify="Justify.Center" Class="mt-4">
|
||||
@foreach(ArtifactGrouping grouping in _article.ArtifactGroupings)
|
||||
{
|
||||
<MudItem xs="12" sm="12" md="8" lg="4">
|
||||
<MudLink Href="@($"/archive/{grouping.Id}")" Target="_blank" Style="text-decoration: none; color: inherit;">
|
||||
|
||||
<MudCard Style="@($"height: {Math.Floor(400 * 0.7)}px; display: flex; flex-direction: column;")" >
|
||||
@if (grouping.ChildArtifactEntries[0].Files.Any())
|
||||
{
|
||||
<MudCardMedia Image="@($"/api/files/{grouping.ChildArtifactEntries[0].Files[0].Id}")"/>
|
||||
}
|
||||
|
||||
<MudCardContent Style=@($"flex-grow: 1; overflow-y: clip; height:{Math.Floor(400 * 0.3)}px;")>
|
||||
<MudText Typo="Typo.h5">@grouping.Title</MudText>
|
||||
<MudText Typo="Typo.body2">@grouping.Description</MudText>
|
||||
</MudCardContent>
|
||||
</MudCard>
|
||||
|
||||
</MudLink>
|
||||
</MudItem>
|
||||
}
|
||||
</MudGrid>
|
||||
</MudPaper>
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
<MudPaper Class="pa-4 ma-2 rounded" Elevation="3">
|
||||
<MudGrid Justify="Justify.Center" Class="mb-2">
|
||||
<MudItem>
|
||||
<MudImage ObjectPosition=ObjectPosition.Center Class="rounded-1g" Src=@($"/api/files/{_article.MainPhoto.Id}") Height="400"></MudImage>
|
||||
</MudItem>
|
||||
</MudGrid>
|
||||
<MudText Typo="Typo.h6">@_article.Title</MudText>
|
||||
<MudDivider/>
|
||||
<MudText Typo="Typo.caption">Posted: @_article.CreationTime.Hour:@_article.CreationTime.Minute @_article.CreationTime.Month/@_article.CreationTime.Day/@_article.CreationTime.Year</MudText>
|
||||
<MudText Typo="Typo.caption">Updated: @_article.ModifiedTime.Hour:@_article.ModifiedTime.Minute @_article.ModifiedTime.Month/@_article.ModifiedTime.Day/@_article.ModifiedTime.Year</MudText>
|
||||
<MudDivider/>
|
||||
<MudText Typo="Typo.caption" style="font-weight: 100;">Tags:</MudText>
|
||||
<OpenArchival.Blazor.CustomComponents.ChipContainer T="BlogPostTag" @bind-Items=_article.Tags DeleteEnabled=false></OpenArchival.Blazor.CustomComponents.ChipContainer>
|
||||
</MudPaper>
|
||||
|
||||
<MudPaper Class="pa-4 ma-2 rounded" Elevation="3">
|
||||
@((MarkupString)_article.Content)
|
||||
</MudPaper>
|
||||
}
|
||||
@inject IArtifactGroupingProvider GroupingProvider;
|
||||
@inject NavigationManager NavigationManager;
|
||||
@inject IDbContextFactory<ApplicationDbContext> ContextFactory;
|
||||
@code {
|
||||
[Parameter]
|
||||
public string ArticleIdString { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The converted grouping id from the URL
|
||||
/// </summary>
|
||||
private int _articleId { get; set; }
|
||||
|
||||
private BlogPost _article { get; set; } = default!;
|
||||
|
||||
protected override async Task OnParametersSetAsync()
|
||||
{
|
||||
if (!int.TryParse(ArticleIdString, out int articleId))
|
||||
{
|
||||
NavigationManager.NavigateTo("/article-not-found");
|
||||
return;
|
||||
}
|
||||
|
||||
_articleId = articleId;
|
||||
|
||||
await using var context = await ContextFactory.CreateDbContextAsync();
|
||||
|
||||
// --- FIX: Added .Include(a => a.Views) AND .FirstOrDefaultAsync(a => a.Id == _articleId)
|
||||
var article = await context.BlogPosts
|
||||
.Include(a => a.Views)
|
||||
.Include(a => a.ArtifactGroupings)
|
||||
.ThenInclude(g => g.ChildArtifactEntries)
|
||||
.ThenInclude(e => e.Files)
|
||||
.Include(article=>article.Views)
|
||||
.Include(article=>article.Tags)
|
||||
.Include(article=>article.MainPhoto)
|
||||
.FirstOrDefaultAsync(a => a.Id == _articleId); // <-- FIX 2: Filter by the correct ID
|
||||
|
||||
if (article is null)
|
||||
{
|
||||
NavigationManager.NavigateTo("/article-not-found");
|
||||
return;
|
||||
}
|
||||
|
||||
_article = article;
|
||||
|
||||
// --- This logic will now work correctly ---
|
||||
if (_article.Views is null)
|
||||
{
|
||||
// This article has never been viewed, create a new view count
|
||||
var viewCount = new BlogPostViewCount() { Post = _article, Views = 1 };
|
||||
context.Add(viewCount); // Add the new count to the context
|
||||
_article.Views = viewCount; // Associate it with the article
|
||||
}
|
||||
else
|
||||
{
|
||||
// It has been viewed, just increment the count
|
||||
_article.Views.Views++;
|
||||
}
|
||||
|
||||
await context.SaveChangesAsync(); // This will now correctly INSERT or UPDATE
|
||||
|
||||
// StateHasChanged() is not strictly necessary here, but doesn't hurt.
|
||||
StateHasChanged();
|
||||
|
||||
await base.OnParametersSetAsync();
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user