Files

167 lines
5.5 KiB
Plaintext

@page "/articles/search"
@page "/articles/search/{SearchTerms}"
@using Microsoft.EntityFrameworkCore
@using Microsoft.Extensions.Logging
@using MudBlazor
@using OpenArchival.DataAccess
@using System.Linq
@using System.Text.RegularExpressions
@using System.Net
<BlogPostSearchBar @ref="_searchBar"
@bind-SelectedFilter="_selectedFilter"
SearchTermsChanged="PerformSearchAsyncCallback" />
@{
if (_showMostRecent && PostSearch.TotalResults > 0)
{
<MudGrid Justify="Justify.FlexStart" Class="mt-1 ml-1 mb-2">
<MudText Typo="Typo.h6" Color="Color.Primary">Most Recent Posts:</MudText>
</MudGrid>
}
else if (PostSearch.TotalResults > 0)
{
<MudGrid Justify="Justify.FlexStart" Class="mt-1 ml-1 mb-2">
<MudText Typo="Typo.subtitle2" Class="my-2">@PostSearch.TotalResults results found</MudText>
<MudButton Class="ml-1" StartIcon="@Icons.Material.Filled.Clear" OnClick="OnClearResults" Variant="Variant.Filled" Color="Color.Primary" Size="Size.Small">Clear</MudButton>
</MudGrid>
}
}
@if (PostSearch.SearchResults.Count > 0)
{
<MudGrid>
@foreach (var post in PostSearch.SearchResults)
{
<MudItem xs="12" sm="6" md="4" lg="4">
<MudLink Href="@($"/articles/{post.Id}")" Target="_blank" Style="text-decoration: none; color: inherit;">
<MudCard Style="@($"height: {Math.Floor(400 * 0.7)}px; display: flex; flex-direction: column;")">
@if (post.MainPhoto != null)
{
<MudCardMedia Image="@($"/api/files/{post.MainPhoto.Id}")" Style="height: 100%;" />
}
else
{
<MudCardMedia Image="/images/placeholder.png" Style="height: 100%;" /> }
<MudCardContent Style=@($"flex-grow: 1; overflow-y: clip; height:{Math.Floor(400 * 0.3)}px;")>
<MudText Typo="Typo.h5">@post.Title</MudText>
<MudText Typo="Typo.body2">@CreateContentSnippet(post.Content)</MudText>
</MudCardContent>
</MudCard>
</MudLink>
</MudItem>
}
</MudGrid>
<MudPaper Class="d-flex justify-center py-2 mt-4" Elevation="0">
<MudPagination Count="PostSearch.TotalPages"
Selected="PostSearch.CurrentPage"
SelectedChanged="OnPageChangedAsync" />
</MudPaper>
}
@inject IDbContextFactory<ApplicationDbContext> ContextFactory;
@inject ILogger<SearchBlog> Logger;
@inject NavigationManager NavigationManager;
@inject BlogPostSearch PostSearch;
@code {
[Parameter]
public string SearchTerms { get; set; } = "";
private BlogSearchFilterType _selectedFilter = BlogSearchFilterType.All;
private BlogPostSearchBar _searchBar = default!;
// List for the "no results" slider display
private List<SearchPageSliderEntry> _sliderEntries { get; set; } = [];
private bool _showMostRecent = true;
protected override async Task OnParametersSetAsync()
{
// This runs when the page loads, checking for search terms in the URL
if (string.IsNullOrWhiteSpace(SearchTerms))
{
await PostSearch.Search("", _selectedFilter, 1);
_showMostRecent = true;
}
else
{
await PostSearch.Search(SearchTerms, _selectedFilter, 1);
_showMostRecent = false;
}
}
/// <summary>
/// This is called by the SearchBar component's 'SearchTermsChanged' event.
/// </summary>
private async Task PerformSearchAsyncCallback(string searchTerms)
{
if (string.IsNullOrEmpty(searchTerms))
{
_showMostRecent = true;
} else
{
_showMostRecent = false;
}
SearchTerms = searchTerms; // Update the page's parameter
// Update the URL to reflect the new search
NavigationManager.NavigateTo($"/articles/search/{Uri.EscapeDataString(searchTerms)}", replace: true);
// Perform the search (always start on page 1)
await PostSearch.Search(searchTerms, _selectedFilter, 1);
StateHasChanged(); // Re-render the page with results
}
/// <summary>
/// This is called by the MudPagination's 'SelectedChanged' event.
/// </summary>
private async Task OnPageChangedAsync(int page)
{
// Load the specific page using the service
await PostSearch.LoadPageAsync(page);
StateHasChanged(); // Re-render with the new page's data
}
/// <summary>
/// Clears the search results and state.
/// </summary>
private void OnClearResults()
{
PostSearch.ClearResults();
SearchTerms = "";
// Navigate back to the base search page
NavigationManager.NavigateTo("/articles/search", replace: true);
StateHasChanged();
}
public static string CreateContentSnippet(string html, int maxLength = 150)
{
if (string.IsNullOrEmpty(html))
{
return string.Empty;
}
// Strip HTML tags
string plainText = Regex.Replace(html, @"<[^>]+>", string.Empty);
// Decode HTML entities
plainText = WebUtility.HtmlDecode(plainText).Trim();
if (plainText.Length > maxLength)
{
return plainText.Substring(0, maxLength) + "...";
}
return plainText;
}
}