diff --git a/src/Somnia.GuestLog/Components/Pages/GuestDocuments/GuestDocList.razor b/src/Somnia.GuestLog/Components/Pages/GuestDocuments/GuestDocList.razor index 712c5f2..7f973fc 100644 --- a/src/Somnia.GuestLog/Components/Pages/GuestDocuments/GuestDocList.razor +++ b/src/Somnia.GuestLog/Components/Pages/GuestDocuments/GuestDocList.razor @@ -13,32 +13,53 @@ Somnia - Guest Docs - Guest Documents + @LanguageLocale.page_GuestDocList_pageTitle - + @LanguageLocale.general_btnSearch + + @LanguageLocale.page_GuestDocList_btnNewGuest - - @foreach (var module in _moduleList) - { - @module - } - + + + + + + @foreach (string docType in dataListService.GetDataListByName(GuestConsts.DataList_DocumentTypes)) + { + + @dataListService.GetLocalizedValue(GuestConsts.DataList_DocumentTypes, docType) + + } + + + + + + + + + + + Hideable="true" ColumnsPanelReordering="true" Elevation="2"> - Document List - - - @LanguageLocale.general_reloadData - + @LanguageLocale.page_GuestDocList_documentList + + @LanguageLocale.general_ConfigureColumns @@ -67,9 +88,13 @@ + + + - + @LanguageLocale.general_confirmDeleteMsg @@ -85,8 +110,10 @@ private IEnumerable guestDocList = []; private bool _dataLoading = true; - private HashSet _moduleList = []; - private HashSet _selectedModuleList = []; + private bool _showAllData = false; + private const int resultLimit = 200; + + private GuestDocFilterDTO docFilter = new GuestDocFilterDTO(); private MudDataGrid _dataGrid = null!; private MudMessageBox _msgBoxConfirmDelete = null!; @@ -95,17 +122,24 @@ protected override async Task OnInitializedAsync() { await LoadDataAsync(showMsg: false); - - @* _moduleList = guestDocList.Select(e => e.Module).ToHashSet(); *@ } #region Data Loading + private async Task SearchDataAsync() + { + docFilter.Name = docFilter.Name?.ToUpper(); + docFilter.Surname = docFilter.Surname?.ToUpper(); + + await LoadDataAsync(); + } + private async Task LoadDataAsync(bool showMsg = true) { _dataLoading = true; - guestDocList = await GuestDocService.GetDtoListAsync(); + int dataLimit = _showAllData ? 0 : resultLimit; + guestDocList = await GuestDocService.GetDtoListByFilterAsync(filter: docFilter, limit: dataLimit); if (showMsg) { @@ -118,13 +152,6 @@ #region Event Handlers - private async Task FilterModuleValuesChanged(IReadOnlyCollection newValues) - { - _selectedModuleList = [.. newValues]; - - await LoadDataAsync(); - } - private async Task BtnConfigureColumnsClick(MouseEventArgs args) { _dataGrid.ShowColumnsPanel(args); diff --git a/src/Somnia.GuestLog/GuestConsts.cs b/src/Somnia.GuestLog/GuestConsts.cs index d22f412..cb88347 100644 --- a/src/Somnia.GuestLog/GuestConsts.cs +++ b/src/Somnia.GuestLog/GuestConsts.cs @@ -8,9 +8,6 @@ public static class GuestConsts public const string Page_GuestDocs_Detail = "/guest-documents/d/{docId}"; - public const string regexPattern_phoneNum = @"\+?\d{1,4}?[-.\s]?\(?\d{1,3}?\)?[-.\s]?\d{1,4}[-.\s]?\d{1,4}[-.\s]?\d{1,9}"; - - public const string DataList_DocumentTypes = "DocumentType"; public const string DataList_GenderOptions = "GenderOption"; public const string DataList_CountryCodes = "CountryCode"; diff --git a/src/Somnia.GuestLog/Models/DTOs/GuestDocFilterDTO.cs b/src/Somnia.GuestLog/Models/DTOs/GuestDocFilterDTO.cs new file mode 100644 index 0000000..b7a7275 --- /dev/null +++ b/src/Somnia.GuestLog/Models/DTOs/GuestDocFilterDTO.cs @@ -0,0 +1,13 @@ +namespace Somnia.GuestLog.Models.DTOs; + +public class GuestDocFilterDTO +{ + public string? DocumentType { get; set; } + public string? DocumentNumber { get; set; } + + public string? Name { get; set; } + public string? Surname { get; set; } + + public string? PhoneNumber { get; set; } + +} diff --git a/src/Somnia.GuestLog/Resources/LanguageLocale.resx b/src/Somnia.GuestLog/Resources/LanguageLocale.resx index bff279b..87a237e 100644 --- a/src/Somnia.GuestLog/Resources/LanguageLocale.resx +++ b/src/Somnia.GuestLog/Resources/LanguageLocale.resx @@ -147,6 +147,7 @@ In Progress... Configure Columns Deleting can not be undone! + Confirm? Delete Create Edit @@ -155,8 +156,12 @@ Search Save Cancel + Use '%' as wildcard + Guest Documents + Document List New Guest + Show all elements This Guest Document Already exists!! Go to existing document diff --git a/src/Somnia.GuestLog/Services/GuestDocumentService.cs b/src/Somnia.GuestLog/Services/GuestDocumentService.cs index fc52e34..78e8eb7 100644 --- a/src/Somnia.GuestLog/Services/GuestDocumentService.cs +++ b/src/Somnia.GuestLog/Services/GuestDocumentService.cs @@ -3,6 +3,7 @@ using Microsoft.EntityFrameworkCore; using Somnia.GuestLog.Infrastructure; using Somnia.GuestLog.Models.DTOs; using Somnia.GuestLog.Models.Entities; +using Somnia.GuestLog.Utils; namespace Somnia.GuestLog.Services; @@ -127,6 +128,40 @@ public class GuestDocumentService( return dbList.Select(x => GetDtoFromDb(x)); } + /// + /// Get GuestDocumentDTO from DB with the given filters. + /// Result count can be limited for perfomance reasons. + /// + /// Filters to use + /// Result count. Set to 0 for unlimited results + /// Filtered GuestDocumentDTO result list + public async Task> GetDtoListByFilterAsync(GuestDocFilterDTO filter, int limit = 0) + { + using var dbContext = contextFactory.CreateDbContext(); + + var query = dbContext.GuestDocuments.AsQueryable(); + + query = query.WhereIf(!string.IsNullOrEmpty(filter.DocumentType), + e => e.DocumentType == filter.DocumentType); + query = query.WhereIf(!string.IsNullOrEmpty(filter.DocumentNumber), + e => e.DocumentNum == filter.DocumentNumber); + + query = query.WhereIf(!string.IsNullOrEmpty(filter.Name), + e => EF.Functions.Like(e.Name, filter.Name)); + query = query.WhereIf(!string.IsNullOrEmpty(filter.Surname), + e => EF.Functions.Like(e.Surname, filter.Surname)); + + query = query.OrderByDescending(e => e.UpdateTime); + + if (limit > 0) + { + query = query.Take(limit); + } + + var dbList = await query.ToListAsync(); + + return dbList.Select(x => GetDtoFromDb(x)); + } public GuestDocumentDTO GetDtoFromDb(GuestDocument dbItem) { @@ -154,5 +189,4 @@ public class GuestDocumentService( UpdateTime = dbItem.UpdateTime, }; } - } \ No newline at end of file diff --git a/src/Somnia.GuestLog/Services/IGuestDocumentService.cs b/src/Somnia.GuestLog/Services/IGuestDocumentService.cs index 18df554..6611a6a 100644 --- a/src/Somnia.GuestLog/Services/IGuestDocumentService.cs +++ b/src/Somnia.GuestLog/Services/IGuestDocumentService.cs @@ -10,6 +10,7 @@ public interface IGuestDocumentService public Task DeleteDocumentAsync(string docType, string docNum); public Task GetDtoByIdAsync(string docType, string docNum); + public Task> GetDtoListByFilterAsync(GuestDocFilterDTO filter, int limit = 0); public Task> GetDtoListAsync(); //TODO: Add Filter diff --git a/src/Somnia.GuestLog/Utils/QueryExtensions.cs b/src/Somnia.GuestLog/Utils/QueryExtensions.cs new file mode 100644 index 0000000..e512d17 --- /dev/null +++ b/src/Somnia.GuestLog/Utils/QueryExtensions.cs @@ -0,0 +1,11 @@ +using System.Linq.Expressions; + +namespace Somnia.GuestLog.Utils; + +public static class QueryExtensions +{ + public static IQueryable WhereIf(this IQueryable source, bool condition, Expression> predicate) + { + return condition ? source.Where(predicate) : source; + } +} diff --git a/src/Somnia.GuestLog/Utils/RegexUtils.cs b/src/Somnia.GuestLog/Utils/RegexUtils.cs index 946c797..f3dafd6 100644 --- a/src/Somnia.GuestLog/Utils/RegexUtils.cs +++ b/src/Somnia.GuestLog/Utils/RegexUtils.cs @@ -12,4 +12,7 @@ public static partial class RegexUtils [GeneratedRegex("^[A-Z]{3}[0-9]{6}$")] public static partial Regex RegexGuestDocSuportNumber(); + + [GeneratedRegex(@"^\+?\d{1,4}?[-.\s]?\(?\d{1,3}?\)?[-.\s]?\d{1,4}[-.\s]?\d{1,4}[-.\s]?\d{1,9}$")] + public static partial Regex RegexPhoneNumber(); } diff --git a/src/Somnia.GuestLog/Validators/GuestDocumentDTOValidator.cs b/src/Somnia.GuestLog/Validators/GuestDocumentDTOValidator.cs index 767af16..a04a1d4 100644 --- a/src/Somnia.GuestLog/Validators/GuestDocumentDTOValidator.cs +++ b/src/Somnia.GuestLog/Validators/GuestDocumentDTOValidator.cs @@ -55,7 +55,7 @@ public class GuestDocumentDTOValidator : AbstractValidator .When(x => !string.IsNullOrEmpty(x.EmailAddress)); RuleFor(x => x.PhoneNumber) - .Matches(GuestConsts.regexPattern_phoneNum) + .Matches(RegexUtils.RegexPhoneNumber()).WithMessage("Invalid format") .When(x => !string.IsNullOrEmpty(x.PhoneNumber)); RuleFor(x => x.AddressCountry)