From 73d6d0df944df797525c2b02c97565e0c7858f67 Mon Sep 17 00:00:00 2001 From: "Daniel J. Summers" Date: Sat, 19 Jun 2021 22:49:50 -0400 Subject: [PATCH] Add WIP for listing page (#16) --- .../Client/JobsJobsJobs.Client.csproj.user | 1 + .../Client/Pages/Listings/Mine.razor | 25 +++++++++ .../Client/Pages/Listings/Mine.razor.cs | 41 +++++++++++++++ .../Api/Controllers/ListingController.cs | 52 +++++++++++++++++++ .../Server/Data/ListingExtensions.cs | 25 +++++++++ 5 files changed, 144 insertions(+) create mode 100644 src/JobsJobsJobs/Client/Pages/Listings/Mine.razor create mode 100644 src/JobsJobsJobs/Client/Pages/Listings/Mine.razor.cs create mode 100644 src/JobsJobsJobs/Server/Areas/Api/Controllers/ListingController.cs create mode 100644 src/JobsJobsJobs/Server/Data/ListingExtensions.cs diff --git a/src/JobsJobsJobs/Client/JobsJobsJobs.Client.csproj.user b/src/JobsJobsJobs/Client/JobsJobsJobs.Client.csproj.user index 8a6c2b4..bf96c1b 100644 --- a/src/JobsJobsJobs/Client/JobsJobsJobs.Client.csproj.user +++ b/src/JobsJobsJobs/Client/JobsJobsJobs.Client.csproj.user @@ -4,6 +4,7 @@ RazorPageScaffolder root/Common/RazorPage JobsJobsJobs + true ProjectDebugger diff --git a/src/JobsJobsJobs/Client/Pages/Listings/Mine.razor b/src/JobsJobsJobs/Client/Pages/Listings/Mine.razor new file mode 100644 index 0000000..dd3c55f --- /dev/null +++ b/src/JobsJobsJobs/Client/Pages/Listings/Mine.razor @@ -0,0 +1,25 @@ +@page "/listings/mine" +@inject HttpClient http +@inject NavigationManager nav +@inject AppState state + + +

My Job Listings

+ + + @if (Loading) + { +

Loading job listings…

+ } + else + { + @if (Listings.Any()) + { +

TODO: list them

+ } + else + { +

No job listings found

+ } + } +
diff --git a/src/JobsJobsJobs/Client/Pages/Listings/Mine.razor.cs b/src/JobsJobsJobs/Client/Pages/Listings/Mine.razor.cs new file mode 100644 index 0000000..c9b9ec9 --- /dev/null +++ b/src/JobsJobsJobs/Client/Pages/Listings/Mine.razor.cs @@ -0,0 +1,41 @@ +using JobsJobsJobs.Shared; +using Microsoft.AspNetCore.Components; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Threading.Tasks; + +namespace JobsJobsJobs.Client.Pages.Listings +{ + public partial class Mine : ComponentBase + { + /// + /// Whether the page is loading data + /// + private bool Loading { get; set; } = true; + + /// + /// Error messages encountered while searching for profiles + /// + private IList ErrorMessages { get; } = new List(); + + /// + /// The job listings entered by the current user + /// + private IEnumerable Listings { get; set; } = Enumerable.Empty(); + + protected override async Task OnInitializedAsync() + { + var listings = await ServerApi.RetrieveMany(http, "listing/mine"); + + if (listings.IsOk) + { + Listings = listings.Ok; + } + else + { + ErrorMessages.Add(listings.Error); + } + } + } +} diff --git a/src/JobsJobsJobs/Server/Areas/Api/Controllers/ListingController.cs b/src/JobsJobsJobs/Server/Areas/Api/Controllers/ListingController.cs new file mode 100644 index 0000000..501ab68 --- /dev/null +++ b/src/JobsJobsJobs/Server/Areas/Api/Controllers/ListingController.cs @@ -0,0 +1,52 @@ +using JobsJobsJobs.Server.Data; +using JobsJobsJobs.Shared; +using Microsoft.AspNetCore.Authorization; +using Microsoft.AspNetCore.Mvc; +using NodaTime; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Security.Claims; +using System.Threading.Tasks; + +namespace JobsJobsJobs.Server.Areas.Api.Controllers +{ + /// + /// API controller for job listings + /// + [Route("api/listings")] + [Authorize] + [ApiController] + public class ListingController : ControllerBase + { + /// + /// The data context + /// + private readonly JobsDbContext _db; + + /// + /// The NodaTime clock instance + /// + private readonly IClock _clock; + + /// + /// Constructor + /// + /// The data context to use for this request + /// The clock instance to use for this request + public ListingController(JobsDbContext db, IClock clock) + { + _db = db; + _clock = clock; + } + + /// + /// The current citizen ID + /// + private CitizenId CurrentCitizenId => CitizenId.Parse(User.FindFirst(ClaimTypes.NameIdentifier)!.Value); + + [HttpGet("mine")] + public async Task Mine() => + Ok(await _db.FindListingsByCitizen(CurrentCitizenId)); + } +} diff --git a/src/JobsJobsJobs/Server/Data/ListingExtensions.cs b/src/JobsJobsJobs/Server/Data/ListingExtensions.cs new file mode 100644 index 0000000..28c6c26 --- /dev/null +++ b/src/JobsJobsJobs/Server/Data/ListingExtensions.cs @@ -0,0 +1,25 @@ +using JobsJobsJobs.Shared; +using Microsoft.EntityFrameworkCore; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Threading.Tasks; + +namespace JobsJobsJobs.Server.Data +{ + /// + /// Extensions to JobsDbContext to support manipulation of job listings + /// + public static class ListingExtensions + { + /// + /// Find all job listings for the given citizen ID + /// + /// The citizen ID for which job listings should be retrieved + /// The job listings entered by the given citizen + public static async Task> FindListingsByCitizen(this JobsDbContext db, CitizenId citizenId) + => await db.Listings.AsNoTracking() + .Where(l => l.CitizenId == citizenId) + .ToListAsync().ConfigureAwait(false); + } +}