From c2d4631ed1b88b9fa510ce302583fed2df750244 Mon Sep 17 00:00:00 2001 From: devinleighsmith Date: Wed, 28 Jun 2023 00:38:51 -0700 Subject: [PATCH 1/6] psp-5860 limit lease and license access by region. --- .../Leases/Controllers/SearchController.cs | 12 ++-- .../Reports/Controllers/LeaseController.cs | 11 ++-- source/backend/api/Services/ILeaseService.cs | 3 + .../api/Services/LeaseReportsService.cs | 9 ++- source/backend/api/Services/LeaseService.cs | 47 ++++++++++++- .../dal/Helpers/Extensions/LeaseExtensions.cs | 9 ++- .../dal/Helpers/Extensions/UserExtensions.cs | 11 ++++ .../Interfaces/ILeaseRepository.cs | 4 +- .../dal/Repositories/LeaseRepository.cs | 8 +-- .../dal/Repositories/UserRepository.cs | 2 + .../backend/tests/core/Entities/UserHelper.cs | 9 ++- .../Leases/SearchControllerTest.cs | 16 ++--- .../Reports/LeaseControllerTest.cs | 66 +++++++++---------- .../api/Helpers/PrincipalExtensionsTest.cs | 59 +++++++++++++++++ .../api/Services/LeaseReportsServiceTest.cs | 11 +++- .../unit/api/Services/LeaseServiceTest.cs | 15 +++++ .../dal/Repositories/LeaseRepositoryTest.cs | 10 ++- .../leases/add/AddLeaseContainer.test.tsx | 22 +++++++ .../leases/add/AdministrationSubForm.test.tsx | 4 ++ .../leases/add/AdministrationSubForm.tsx | 4 +- .../AddLeaseContainer.test.tsx.snap | 16 +---- .../AdministrationSubForm.test.tsx.snap | 50 ++++++-------- .../list/LeaseFilter/LeaseFilter.test.tsx | 7 +- .../leases/list/LeaseFilter/LeaseFilter.tsx | 14 ++-- .../__snapshots__/LeaseFilter.test.tsx.snap | 20 ++++++ .../__snapshots__/LeaseListView.test.tsx.snap | 20 ++++++ 26 files changed, 329 insertions(+), 130 deletions(-) create mode 100644 source/backend/tests/unit/api/Helpers/PrincipalExtensionsTest.cs diff --git a/source/backend/api/Areas/Leases/Controllers/SearchController.cs b/source/backend/api/Areas/Leases/Controllers/SearchController.cs index 6b7468822b..e3c7b24635 100644 --- a/source/backend/api/Areas/Leases/Controllers/SearchController.cs +++ b/source/backend/api/Areas/Leases/Controllers/SearchController.cs @@ -8,8 +8,8 @@ using Pims.Api.Helpers.Exceptions; using Pims.Api.Helpers.Extensions; using Pims.Api.Policies; +using Pims.Api.Services; using Pims.Dal.Entities.Models; -using Pims.Dal.Repositories; using Pims.Dal.Security; using Swashbuckle.AspNetCore.Annotations; @@ -27,7 +27,7 @@ namespace Pims.Api.Areas.Lease.Controllers public class SearchController : ControllerBase { #region Variables - private readonly ILeaseRepository _leaseRepository; + private readonly ILeaseService _leaseService; private readonly IMapper _mapper; #endregion @@ -36,12 +36,12 @@ public class SearchController : ControllerBase /// /// Creates a new instance of a SearchController(LIS) class, initializes it with the specified arguments. /// - /// + /// /// /// - public SearchController(ILeaseRepository leaseRepository, IMapper mapper) + public SearchController(ILeaseService leaseService, IMapper mapper) { - _leaseRepository = leaseRepository; + _leaseService = leaseService; _mapper = mapper; } #endregion @@ -85,7 +85,7 @@ public IActionResult GetLeases([FromBody] LeaseFilterModel filter) throw new BadRequestException("Property filter must contain valid values."); } - var leases = _leaseRepository.GetPage((LeaseFilter)filter); + var leases = _leaseService.GetPage((LeaseFilter)filter); return new JsonResult(_mapper.Map>(leases)); } #endregion diff --git a/source/backend/api/Areas/Reports/Controllers/LeaseController.cs b/source/backend/api/Areas/Reports/Controllers/LeaseController.cs index 2d7c1ddfe1..4e81ee2aac 100644 --- a/source/backend/api/Areas/Reports/Controllers/LeaseController.cs +++ b/source/backend/api/Areas/Reports/Controllers/LeaseController.cs @@ -37,7 +37,7 @@ public class LeaseController : ControllerBase { #region Variables private readonly ILookupRepository _lookupRepository; - private readonly ILeaseRepository _leaseRepository; + private readonly ILeaseService _leaseService; private readonly ILeaseReportsService _leaseReportService; private readonly ILeasePaymentService _leasePaymentService; private readonly IMapper _mapper; @@ -50,15 +50,15 @@ public class LeaseController : ControllerBase /// Creates a new instance of a ReportController class, initializes it with the specified arguments. /// /// - /// + /// /// /// /// /// - public LeaseController(ILookupRepository lookupRepository, ILeaseRepository leaseRepository, ILeaseReportsService leaseReportService, ILeasePaymentService leasePaymentService, IWebHostEnvironment webHostEnvironment, IMapper mapper) + public LeaseController(ILookupRepository lookupRepository, ILeaseService leaseService, ILeaseReportsService leaseReportService, ILeasePaymentService leasePaymentService, IWebHostEnvironment webHostEnvironment, IMapper mapper) { _lookupRepository = lookupRepository; - _leaseRepository = leaseRepository; + _leaseService = leaseService; _leaseReportService = leaseReportService; _leasePaymentService = leasePaymentService; _mapper = mapper; @@ -202,8 +202,7 @@ public IActionResult ExportLeasePayments(int fiscalYearStart) /// public IEnumerable GetCrossJoinLeases(Lease.Models.Search.LeaseFilterModel filter, bool all = false) { - filter.Quantity = all ? _leaseRepository.Count() : filter.Quantity; - var page = _leaseRepository.GetPage((LeaseFilter)filter); + var page = _leaseService.GetPage((LeaseFilter)filter, all); var allLeases = page.Items.SelectMany(l => l.PimsLeaseTerms.DefaultIfEmpty(), (lease, term) => (lease, term)) .SelectMany(lt => lt.lease.PimsPropertyLeases.DefaultIfEmpty(), (leaseTerm, property) => (leaseTerm.term, leaseTerm.lease, property)) .SelectMany(ltp => ltp.lease.PimsLeaseTenants.DefaultIfEmpty(), (leaseTermProperty, tenant) => (leaseTermProperty.term, leaseTermProperty.lease, leaseTermProperty.property, tenant)); diff --git a/source/backend/api/Services/ILeaseService.cs b/source/backend/api/Services/ILeaseService.cs index 41c174d308..9ead6f5938 100644 --- a/source/backend/api/Services/ILeaseService.cs +++ b/source/backend/api/Services/ILeaseService.cs @@ -1,5 +1,6 @@ using System.Collections.Generic; using Pims.Dal.Entities; +using Pims.Dal.Entities.Models; using Pims.Dal.Exceptions; namespace Pims.Api.Services @@ -10,6 +11,8 @@ public interface ILeaseService PimsLease GetById(long leaseId); + Paged GetPage(LeaseFilter filter, bool? all = false); + PimsLease Add(PimsLease lease, IEnumerable userOverrides); PimsLease Update(PimsLease lease, IEnumerable userOverrides); diff --git a/source/backend/api/Services/LeaseReportsService.cs b/source/backend/api/Services/LeaseReportsService.cs index 10ec33fa86..61f0bc512b 100644 --- a/source/backend/api/Services/LeaseReportsService.cs +++ b/source/backend/api/Services/LeaseReportsService.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Linq; using System.Security.Claims; using Pims.Core.Extensions; using Pims.Dal.Entities; @@ -13,11 +14,13 @@ namespace Pims.Api.Services public class LeaseReportsService : ILeaseReportsService { private readonly ILeaseRepository _leaseRepository; + private readonly IUserRepository _userRepository; private readonly ClaimsPrincipal _user; - public LeaseReportsService(ILeaseRepository leaseRepository, ClaimsPrincipal user) + public LeaseReportsService(ILeaseRepository leaseRepository, IUserRepository userRepository, ClaimsPrincipal user) { _leaseRepository = leaseRepository; + _userRepository = userRepository; _user = user; } @@ -25,6 +28,7 @@ public IEnumerable GetAggregatedLeaseReport(int fiscalYearStart) { _user.ThrowIfNotAuthorized(Permissions.LeaseView); DateTime fiscalYearStartDate = fiscalYearStart.ToFiscalYearDate(); + var user = _userRepository.GetByKeycloakUserId(this._user.GetUserKey()); // fiscal defined as April 01 to March 31 of following year return _leaseRepository.GetAllByFilter( @@ -34,7 +38,8 @@ public IEnumerable GetAggregatedLeaseReport(int fiscalYearStart) StartBeforeDate = fiscalYearStartDate.AddYears(1).AddDays(-1), NotInStatus = new List() { PimsLeaseStatusTypes.DRAFT, PimsLeaseStatusTypes.DISCARD }, IsReceivable = true, - }, true); + }, user.PimsRegionUsers.Select(u => u.RegionCode).ToHashSet(), + true); } } } diff --git a/source/backend/api/Services/LeaseService.cs b/source/backend/api/Services/LeaseService.cs index 77586a6f7d..ad49404493 100644 --- a/source/backend/api/Services/LeaseService.cs +++ b/source/backend/api/Services/LeaseService.cs @@ -6,6 +6,7 @@ using Pims.Core.Extensions; using Pims.Dal.Constants; using Pims.Dal.Entities; +using Pims.Dal.Entities.Models; using Pims.Dal.Exceptions; using Pims.Dal.Helpers; using Pims.Dal.Helpers.Extensions; @@ -27,6 +28,7 @@ public class LeaseService : BaseService, ILeaseService private readonly IEntityNoteRepository _entityNoteRepository; private readonly IInsuranceRepository _insuranceRepository; private readonly ILeaseTenantRepository _tenantRepository; + private readonly IUserRepository _userRepository; public LeaseService( ClaimsPrincipal user, @@ -39,7 +41,8 @@ public LeaseService( ILookupRepository lookupRepository, IEntityNoteRepository entityNoteRepository, IInsuranceRepository insuranceRepository, - ILeaseTenantRepository tenantRepository) + ILeaseTenantRepository tenantRepository, + IUserRepository userRepository) : base(user, logger) { _logger = logger; @@ -53,6 +56,7 @@ public LeaseService( _propertyImprovementRepository = propertyImprovementRepository; _insuranceRepository = insuranceRepository; _tenantRepository = tenantRepository; + _userRepository = userRepository; } public bool IsRowVersionEqual(long leaseId, long rowVersion) @@ -63,6 +67,11 @@ public bool IsRowVersionEqual(long leaseId, long rowVersion) public PimsLease GetById(long leaseId) { + _logger.LogInformation("Getting lease {leaseId}", leaseId); + _user.ThrowIfNotAuthorized(Permissions.LeaseView); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(leaseId).RegionCode); + var lease = _leaseRepository.Get(leaseId); foreach (PimsPropertyLease propertyLease in lease.PimsPropertyLeases) { @@ -76,10 +85,23 @@ public PimsLease GetById(long leaseId) return lease; } + public Paged GetPage(LeaseFilter filter, bool? all = false) + { + _logger.LogInformation("Getting lease page {filter}", filter); + _user.ThrowIfNotAuthorized(Permissions.LeaseView); + filter.Quantity = all.HasValue && all.Value ? _leaseRepository.Count() : filter.Quantity; + var user = _userRepository.GetByKeycloakUserId(this.User.GetUserKey()); + + var leases = _leaseRepository.GetPage(filter, user.PimsRegionUsers.Select(u => u.RegionCode).ToHashSet()); + return leases; + } + public IEnumerable GetInsuranceByLeaseId(long leaseId) { _logger.LogInformation("Getting insurance on lease {leaseId}", leaseId); _user.ThrowIfNotAuthorized(Permissions.LeaseView); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(leaseId).RegionCode); return _insuranceRepository.GetByLeaseId(leaseId); } @@ -88,6 +110,8 @@ public IEnumerable UpdateInsuranceByLeaseId(long leaseId, IEnumer { _logger.LogInformation("Updating insurance on lease {leaseId}", leaseId); _user.ThrowIfNotAuthorized(Permissions.LeaseEdit); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(leaseId).RegionCode); _insuranceRepository.UpdateLeaseInsurance(leaseId, pimsInsurances); _insuranceRepository.CommitTransaction(); @@ -99,6 +123,8 @@ public IEnumerable GetImprovementsByLeaseId(long leaseI { _logger.LogInformation("Getting property improvements on lease {leaseId}", leaseId); _user.ThrowIfNotAuthorized(Permissions.LeaseView); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(leaseId).RegionCode); return _propertyImprovementRepository.GetByLeaseId(leaseId); } @@ -107,6 +133,8 @@ public IEnumerable UpdateImprovementsByLeaseId(long lea { _logger.LogInformation("Updating property improvements on lease {leaseId}", leaseId); _user.ThrowIfNotAuthorized(Permissions.LeaseEdit); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(leaseId).RegionCode); _propertyImprovementRepository.Update(leaseId, pimsPropertyImprovements); _propertyImprovementRepository.CommitTransaction(); @@ -118,6 +146,8 @@ public IEnumerable GetTenantsByLeaseId(long leaseId) { _logger.LogInformation("Getting tenants on lease {leaseId}", leaseId); _user.ThrowIfNotAuthorized(Permissions.LeaseView); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(leaseId).RegionCode); return _tenantRepository.GetByLeaseId(leaseId); } @@ -126,6 +156,8 @@ public IEnumerable UpdateTenantsByLeaseId(long leaseId, IEnumer { _logger.LogInformation("Updating tenants on lease {leaseId}", leaseId); _user.ThrowIfNotAuthorized(Permissions.LeaseEdit); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(leaseId).RegionCode); _tenantRepository.Update(leaseId, pimsLeaseTenants); _tenantRepository.CommitTransaction(); @@ -135,6 +167,11 @@ public IEnumerable UpdateTenantsByLeaseId(long leaseId, IEnumer public PimsLease Add(PimsLease lease, IEnumerable userOverrides) { + _logger.LogInformation("Adding lease"); + _user.ThrowIfNotAuthorized(Permissions.LeaseAdd); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(lease.LeaseId).RegionCode); + var leasesWithProperties = AssociatePropertyLeases(lease, userOverrides); return _leaseRepository.Add(leasesWithProperties); } @@ -143,13 +180,21 @@ public IEnumerable GetPropertiesByLeaseId(long leaseId) { _logger.LogInformation("Getting properties on lease {leaseId}", leaseId); _user.ThrowIfNotAuthorized(Permissions.LeaseView); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); + pimsUser.ThrowInvalidAccessToLeaseFile(_leaseRepository.GetNoTracking(leaseId).RegionCode); return _propertyLeaseRepository.GetAllByLeaseId(leaseId); } public PimsLease Update(PimsLease lease, IEnumerable userOverrides) { + _logger.LogInformation("Updating lease {leaseId}", lease.LeaseId); + _user.ThrowIfNotAuthorized(Permissions.LeaseEdit); + var pimsUser = _userRepository.GetUserInfoByKeycloakUserId(_user.GetUserKey()); var currentLease = _leaseRepository.GetNoTracking(lease.LeaseId); + pimsUser.ThrowInvalidAccessToLeaseFile(currentLease.RegionCode); // need to check that the user is able to access the current lease as well as has the region for the updated lease. + pimsUser.ThrowInvalidAccessToLeaseFile(lease.RegionCode); + var currentProperties = _propertyLeaseRepository.GetAllByLeaseId(lease.LeaseId); if (currentLease.LeaseStatusTypeCode != lease.LeaseStatusTypeCode) diff --git a/source/backend/dal/Helpers/Extensions/LeaseExtensions.cs b/source/backend/dal/Helpers/Extensions/LeaseExtensions.cs index 22dae7c00b..af9da6293e 100644 --- a/source/backend/dal/Helpers/Extensions/LeaseExtensions.cs +++ b/source/backend/dal/Helpers/Extensions/LeaseExtensions.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using System.Globalization; using System.Linq; using Microsoft.Data.SqlClient; @@ -20,13 +21,13 @@ public static class LeaseExtensions /// /// /// - public static IQueryable GenerateLeaseQuery(this PimsContext context, Entity.Models.LeaseFilter filter, bool loadPayments = false) + public static IQueryable GenerateLeaseQuery(this PimsContext context, Entity.Models.LeaseFilter filter, HashSet regionCodes, bool loadPayments = false) { filter.ThrowIfNull(nameof(filter)); var query = context.PimsLeases.AsNoTracking(); - query = query.GenerateCommonLeaseQuery(filter, loadPayments); + query = query.GenerateCommonLeaseQuery(filter, regionCodes, loadPayments); return query; } @@ -146,10 +147,12 @@ public static string GetTenantName(this Pims.Dal.Entities.PimsLeaseTenant lease) /// /// /// - private static IQueryable GenerateCommonLeaseQuery(this IQueryable query, Entity.Models.LeaseFilter filter, bool loadPayments = false) + private static IQueryable GenerateCommonLeaseQuery(this IQueryable query, Entity.Models.LeaseFilter filter, HashSet regions, bool loadPayments = false) { filter.ThrowIfNull(nameof(filter)); + query = query.Where(l => !l.RegionCode.HasValue || regions.Contains(l.RegionCode.Value)); + if (!string.IsNullOrWhiteSpace(filter.TenantName)) { query = query.Where(l => l.PimsLeaseTenants.Any(tenant => tenant.Person != null && EF.Functions.Like( diff --git a/source/backend/dal/Helpers/Extensions/UserExtensions.cs b/source/backend/dal/Helpers/Extensions/UserExtensions.cs index ef11df922c..4039ccf857 100644 --- a/source/backend/dal/Helpers/Extensions/UserExtensions.cs +++ b/source/backend/dal/Helpers/Extensions/UserExtensions.cs @@ -1,3 +1,6 @@ +using System.Linq; +using Pims.Dal.Exceptions; + namespace Pims.Dal.Entities { /// @@ -14,5 +17,13 @@ public static string GetIdirUsername(this PimsUser user) { return $"{user.GuidIdentifierValue.ToString().Replace("-", string.Empty)}@idir"; } + + public static void ThrowInvalidAccessToLeaseFile(this PimsUser pimsUser, short? leaseRegionCode) + { + if (leaseRegionCode.HasValue && !pimsUser.PimsRegionUsers.Any(ur => ur.RegionCode == leaseRegionCode)) + { + throw new NotAuthorizedException("User is not assigned to the Lease File's region"); + } + } } } diff --git a/source/backend/dal/Repositories/Interfaces/ILeaseRepository.cs b/source/backend/dal/Repositories/Interfaces/ILeaseRepository.cs index d3cdb386ae..dc0e06afa2 100644 --- a/source/backend/dal/Repositories/Interfaces/ILeaseRepository.cs +++ b/source/backend/dal/Repositories/Interfaces/ILeaseRepository.cs @@ -11,7 +11,7 @@ public interface ILeaseRepository : IRepository { int Count(); - IEnumerable GetAllByFilter(LeaseFilter filter, bool loadPayments = false); + IEnumerable GetAllByFilter(LeaseFilter filter, HashSet regionCodes, bool loadPayments = false); long GetRowVersion(long id); @@ -19,7 +19,7 @@ public interface ILeaseRepository : IRepository PimsLease GetNoTracking(long id); - Paged GetPage(LeaseFilter filter); + Paged GetPage(LeaseFilter filter, HashSet regions); IList GetAllLeaseDocuments(long leaseId); diff --git a/source/backend/dal/Repositories/LeaseRepository.cs b/source/backend/dal/Repositories/LeaseRepository.cs index 92aff3b5b0..1be9a27dd2 100644 --- a/source/backend/dal/Repositories/LeaseRepository.cs +++ b/source/backend/dal/Repositories/LeaseRepository.cs @@ -48,7 +48,7 @@ public int Count() /// /// /// - public IEnumerable GetAllByFilter(LeaseFilter filter, bool loadPayments = false) + public IEnumerable GetAllByFilter(LeaseFilter filter, HashSet regionCodes, bool loadPayments = false) { this.User.ThrowIfNotAuthorized(Permissions.LeaseView); filter.ThrowIfNull(nameof(filter)); @@ -57,7 +57,7 @@ public IEnumerable GetAllByFilter(LeaseFilter filter, bool loadPaymen throw new ArgumentException("Argument must have a valid filter", nameof(filter)); } - var query = this.Context.GenerateLeaseQuery(filter, loadPayments); + var query = this.Context.GenerateLeaseQuery(filter, regionCodes, loadPayments); var leases = query.OrderBy(l => l.LeaseId).ToArray(); @@ -234,7 +234,7 @@ public PimsLease GetNoTracking(long id) /// /// /// - public Paged GetPage(LeaseFilter filter) + public Paged GetPage(LeaseFilter filter, HashSet regions) { this.User.ThrowIfNotAuthorized(Permissions.LeaseView); filter.ThrowIfNull(nameof(filter)); @@ -244,7 +244,7 @@ public Paged GetPage(LeaseFilter filter) } var skip = (filter.Page - 1) * filter.Quantity; - var query = this.Context.GenerateLeaseQuery(filter); + var query = this.Context.GenerateLeaseQuery(filter, regions); var items = query .Skip(skip) .Take(filter.Quantity) diff --git a/source/backend/dal/Repositories/UserRepository.cs b/source/backend/dal/Repositories/UserRepository.cs index 5b0fa21b27..0aec7e0882 100644 --- a/source/backend/dal/Repositories/UserRepository.cs +++ b/source/backend/dal/Repositories/UserRepository.cs @@ -344,6 +344,8 @@ public PimsUser GetByKeycloakUserId(Guid keycloakUserId) .ThenInclude(r => r.Role) .Include(u => u.Person) .ThenInclude(p => p.PimsContactMethods) + .Include(u => u.PimsRegionUsers) + .ThenInclude(ru => ru.RegionCodeNavigation) .AsNoTracking() .SingleOrDefault(u => u.GuidIdentifierValue == keycloakUserId) ?? throw new KeyNotFoundException(); } diff --git a/source/backend/tests/core/Entities/UserHelper.cs b/source/backend/tests/core/Entities/UserHelper.cs index 1e1a596dff..54ca9593fe 100644 --- a/source/backend/tests/core/Entities/UserHelper.cs +++ b/source/backend/tests/core/Entities/UserHelper.cs @@ -28,12 +28,13 @@ public static Entity.PimsUser CreateUser(string username) /// /// /// - /// /// /// + /// /// + /// /// - public static Entity.PimsUser CreateUser(long id, Guid keycloakUserId, string username, string firstName = "given name", string lastName = "surname", Entity.PimsRole role = null, Entity.PimsOrganization organization = null, Entity.PimsAddress address = null, bool isContractor = false) + public static Entity.PimsUser CreateUser(long id, Guid keycloakUserId, string username, string firstName = "given name", string lastName = "surname", Entity.PimsRole role = null, Entity.PimsOrganization organization = null, Entity.PimsAddress address = null, bool isContractor = false, short? regionCode = null) { organization ??= EntityHelper.CreateOrganization(id, "Organization 1"); role ??= EntityHelper.CreateRole("Real Estate Manager"); @@ -48,6 +49,10 @@ public static Entity.PimsUser CreateUser(long id, Guid keycloakUserId, string us user.PimsUserRoles.Add(new Entity.PimsUserRole() { Role = role, RoleId = role.Id, User = user, UserId = user.Internal_Id }); user.PimsUserOrganizations.Add(new Entity.PimsUserOrganization() { Organization = organization, OrganizationId = organization.Internal_Id, User = user, UserId = user.Internal_Id }); user.UserTypeCode = isContractor ? EnumUserTypeCodes.CONTRACT.ToString() : EnumUserTypeCodes.MINSTAFF.ToString(); + if (regionCode.HasValue) + { + user.PimsRegionUsers.Add(new Entity.PimsRegionUser() { RegionCode = regionCode.Value }); + } return user; } diff --git a/source/backend/tests/unit/api/Controllers/Leases/SearchControllerTest.cs b/source/backend/tests/unit/api/Controllers/Leases/SearchControllerTest.cs index af41c17e98..420224dc39 100644 --- a/source/backend/tests/unit/api/Controllers/Leases/SearchControllerTest.cs +++ b/source/backend/tests/unit/api/Controllers/Leases/SearchControllerTest.cs @@ -27,7 +27,7 @@ namespace Pims.Api.Test.Controllers.Lease [ExcludeFromCodeCoverage] public class SearchControllerTest { - private Mock _repository; + private Mock _service; private SearchController _controller; private IMapper _mapper; private TestHelper _helper; @@ -37,7 +37,7 @@ public SearchControllerTest() _helper = new TestHelper(); _controller = _helper.CreateController(Permissions.LeaseView); _mapper = _helper.GetService(); - _repository = _helper.GetService>(); + _service = _helper.GetService>(); } #region Variables @@ -68,13 +68,13 @@ public void GetLeases_All_Success(SModel.LeaseFilterModel filter) // Arrange var leases = new[] { EntityHelper.CreateLease(1) }; - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(new Paged(leases)); + _service.Setup(m => m.GetPage(It.IsAny(), false)).Returns(new Paged(leases)); // Act var result = _controller.GetLeases(filter); // Assert - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _service.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); } /// @@ -87,13 +87,13 @@ public void GetProperties_Query_Success(Uri uri) // Arrange var leases = new[] { EntityHelper.CreateLease(1) }; - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(new Paged(leases)); + _service.Setup(m => m.GetPage(It.IsAny(), false)).Returns(new Paged(leases)); // Act var result = _controller.GetLeases(); // Assert - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _service.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); } /// @@ -109,7 +109,7 @@ public void GetProperties_Query_NoFilter_BadRequest() // Act // Assert Assert.Throws(() => _controller.GetLeases()); - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Never()); + _service.Verify(m => m.GetPage(It.IsAny(), false), Times.Never()); } /// @@ -122,7 +122,7 @@ public void GetProperties_NoFilter_BadRequest() // Act // Assert Assert.Throws(() => _controller.GetLeases(null)); - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Never()); + _service.Verify(m => m.GetPage(It.IsAny(), false), Times.Never()); } #endregion #endregion diff --git a/source/backend/tests/unit/api/Controllers/Reports/LeaseControllerTest.cs b/source/backend/tests/unit/api/Controllers/Reports/LeaseControllerTest.cs index 8b13c59986..11f7d2b44a 100644 --- a/source/backend/tests/unit/api/Controllers/Reports/LeaseControllerTest.cs +++ b/source/backend/tests/unit/api/Controllers/Reports/LeaseControllerTest.cs @@ -50,7 +50,7 @@ public class LeaseControllerTest private Mock _service; private Mock _paymentService; - private Mock _repository; + private Mock _leaseService; private LeaseController _controller; private IMapper _mapper; private TestHelper _helper; @@ -68,7 +68,7 @@ public LeaseControllerTest() _lookupRepository = _helper.GetService>(); _webHost = _helper.GetService>(); _headers = _helper.GetService>(); - _repository = _helper.GetService>(); + _leaseService = _helper.GetService>(); } #region Tests @@ -86,7 +86,7 @@ public void ExportLeases_Csv_Success(LeaseFilterModel filter) var leases = new[] { EntityHelper.CreateLease(1) }; var page = new Paged(leases, filter.Page, filter.Quantity); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.ExportLeases(filter); @@ -95,7 +95,7 @@ public void ExportLeases_Csv_Success(LeaseFilterModel filter) var actionResult = Assert.IsType(result); var actualResult = Assert.IsType(actionResult.Content); Assert.Equal(ContentTypes.CONTENTTYPECSV, actionResult.ContentType); - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); } /// @@ -111,13 +111,13 @@ public void ExportLeases_Csv_Query_Success(Uri uri) var leases = new[] { EntityHelper.CreateLease(1) }; var page = new Paged(leases); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.ExportLeases(); // Assert - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); } [Fact] @@ -144,13 +144,13 @@ public void ExportLeases_Lease_Mapping() var leases = new[] { lease }; var page = new Paged(leases); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.GetCrossJoinLeases(new LeaseFilterModel()).FirstOrDefault(); // Assert - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); result.MotiRegion.Should().Be("region"); result.LFileNo.Should().Be("L-010-070"); result.StartDate.Should().Be(new DateTime(2000, 1, 1)); @@ -183,13 +183,13 @@ public void ExportLeases_LeaseTerm_Mapping() var leases = new[] { lease }; var page = new Paged(leases); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.GetCrossJoinLeases(new LeaseFilterModel()).FirstOrDefault(); // Assert - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); result.CurrentTermStartDate.Should().Be(leaseTerm.TermStartDate); result.CurrentTermEndDate.Should().Be(leaseTerm.TermExpiryDate); result.TermStartDate.Should().Be(leaseTerm.TermStartDate); @@ -218,13 +218,13 @@ public void ExportLeases_LeaseTenant_Mapping() var leases = new[] { lease }; var page = new Paged(leases); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.GetCrossJoinLeases(new LeaseFilterModel()); // Assert - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); result.ToArray()[0].TenantName.Should().Be("org"); result.ToArray()[1].TenantName.Should().Be("first middle last"); } @@ -246,13 +246,13 @@ public void ExportLeases_LeaseProperty_Mapping() var leases = new[] { lease }; var page = new Paged(leases); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.GetCrossJoinLeases(new LeaseFilterModel()).FirstOrDefault(); // Assert - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); result.Pid.Should().Be(1); result.Pin.Should().Be(2); result.CivicAddress.Should().Be("1 2 3 m"); @@ -278,13 +278,13 @@ public void ExportLeases_Cartesion() var leases = new[] { lease }; var page = new Paged(leases); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.GetCrossJoinLeases(new LeaseFilterModel()); // Assert - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); result.Count().Should().Be(9); } @@ -302,7 +302,7 @@ public void ExportLeases_Excel_Success(LeaseFilterModel filter) var leases = new[] { EntityHelper.CreateLease(1) }; var page = new Paged(leases, filter.Page, filter.Quantity); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.ExportLeases(filter); @@ -312,7 +312,7 @@ public void ExportLeases_Excel_Success(LeaseFilterModel filter) Assert.Equal(ContentTypes.CONTENTTYPEEXCELX, actionResult.ContentType); Assert.NotNull(actionResult.FileDownloadName); Assert.True(actionResult.FileStream.Length > 0); - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); } /// @@ -327,10 +327,10 @@ public void ExportLeases_Excel_Query_Success(Uri uri) var leases = new[] { EntityHelper.CreateLease(1) }; - var repository = _helper.GetService>(); + var service = _helper.GetService>(); var mapper = _helper.GetService(); var page = new Paged(leases); - repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + service.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.ExportLeases(); @@ -340,7 +340,7 @@ public void ExportLeases_Excel_Query_Success(Uri uri) Assert.Equal(ContentTypes.CONTENTTYPEEXCELX, actionResult.ContentType); Assert.NotNull(actionResult.FileDownloadName); Assert.True(actionResult.FileStream.Length > 0); - repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + service.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); } /// @@ -356,7 +356,7 @@ public void ExportLeases_ExcelX_Success(LeaseFilterModel filter) var leases = new[] { EntityHelper.CreateLease(1) }; var page = new Paged(leases, filter.Page, filter.Quantity); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.ExportLeases(filter); @@ -366,7 +366,7 @@ public void ExportLeases_ExcelX_Success(LeaseFilterModel filter) Assert.Equal(ContentTypes.CONTENTTYPEEXCELX, actionResult.ContentType); Assert.NotNull(actionResult.FileDownloadName); Assert.True(actionResult.FileStream.Length > 0); - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); } /// @@ -382,7 +382,7 @@ public void ExportLeases_ExcelX_Query_Success(Uri uri) var leases = new[] { EntityHelper.CreateLease(1) }; var page = new Paged(leases); - _repository.Setup(m => m.GetPage(It.IsAny())).Returns(page); + _leaseService.Setup(m => m.GetPage(It.IsAny(), false)).Returns(page); // Act var result = _controller.ExportLeases(); @@ -392,7 +392,7 @@ public void ExportLeases_ExcelX_Query_Success(Uri uri) Assert.Equal(ContentTypes.CONTENTTYPEEXCELX, actionResult.ContentType); Assert.NotNull(actionResult.FileDownloadName); Assert.True(actionResult.FileStream.Length > 0); - _repository.Verify(m => m.GetPage(It.IsAny()), Times.Once()); + _leaseService.Verify(m => m.GetPage(It.IsAny(), false), Times.Once()); } /// @@ -405,12 +405,12 @@ public void ExportLeases_Query_NoFilter_BadRequest() var helper = new TestHelper(); var controller = helper.CreateController(Permissions.LeaseView); - var repository = helper.GetService>(); + var service = helper.GetService>(); // Act // Assert Assert.Throws(() => controller.ExportLeases()); - repository.Verify(m => m.GetPage(It.IsAny()), Times.Never()); + service.Verify(m => m.GetPage(It.IsAny(), false), Times.Never()); } /// @@ -423,12 +423,12 @@ public void ExportLeases_NoFilter_BadRequest() var helper = new TestHelper(); var controller = helper.CreateController(Permissions.LeaseView); - var repository = helper.GetService>(); + var service = helper.GetService>(); // Act // Assert Assert.Throws(() => controller.ExportLeases(null)); - repository.Verify(m => m.GetPage(It.IsAny()), Times.Never()); + service.Verify(m => m.GetPage(It.IsAny(), false), Times.Never()); } /// @@ -441,13 +441,13 @@ public void ExportLeases_NoAcceptHeader_BadRequest() var helper = new TestHelper(); var controller = helper.CreateController(Permissions.LeaseView); - var repository = helper.GetService>(); + var service = helper.GetService>(); var filter = new LeaseFilterModel() { }; // Act // Assert Assert.Throws(() => controller.ExportLeases(filter)); - repository.Verify(m => m.GetPage(It.IsAny()), Times.Never()); + service.Verify(m => m.GetPage(It.IsAny(), false), Times.Never()); } /// @@ -460,7 +460,7 @@ public void ExportLeases_InvalidAcceptHeader_BadRequest() var helper = new TestHelper(); var controller = helper.CreateController(Permissions.LeaseView); - var repository = helper.GetService>(); + var service = helper.GetService>(); var headers = helper.GetService>(); headers.Setup(m => m["Accept"]).Returns("invalid"); var filter = new LeaseFilterModel() { }; @@ -468,7 +468,7 @@ public void ExportLeases_InvalidAcceptHeader_BadRequest() // Act // Assert Assert.Throws(() => controller.ExportLeases(filter)); - repository.Verify(m => m.GetPage(It.IsAny()), Times.Never()); + service.Verify(m => m.GetPage(It.IsAny(), false), Times.Never()); } #endregion #region ExportAggregatedLeases diff --git a/source/backend/tests/unit/api/Helpers/PrincipalExtensionsTest.cs b/source/backend/tests/unit/api/Helpers/PrincipalExtensionsTest.cs new file mode 100644 index 0000000000..9a03318326 --- /dev/null +++ b/source/backend/tests/unit/api/Helpers/PrincipalExtensionsTest.cs @@ -0,0 +1,59 @@ +using FluentAssertions; +using Moq; +using Pims.Api.Helpers.Exceptions; +using Pims.Core.Extensions; +using Pims.Core.Test; +using Pims.Dal.Entities; +using Pims.Dal.Exceptions; +using Pims.Dal.Repositories; +using Pims.Dal.Security; +using System; +using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Xunit; + +namespace Pims.Api.Test.Helpers +{ + [Trait("category", "unit")] + [Trait("category", "api")] + [Trait("area", "helpers")] + [Trait("group", "permissons")] + [ExcludeFromCodeCoverage] + public class PrincipalExtensionsTest + { + private TestHelper _helper; + + public PrincipalExtensionsTest() + { + _helper = new TestHelper(); + } + + #region Tests + [Fact] + public void LeaseRegionUserAccess_NoRegion_Success() + { + var pimsUser = EntityHelper.CreateUser("testuser"); + pimsUser.ThrowInvalidAccessToLeaseFile(null); + } + + [Fact] + public void LeaseRegionUserAccess_HasRegion_Failure() + { + var pimsUser = EntityHelper.CreateUser(1, Guid.NewGuid(), "testuser", regionCode: 1); + Action act = () => pimsUser.ThrowInvalidAccessToLeaseFile(2); + act.Should().Throw(); + } + + [Fact] + public void LeaseRegionUserAccess_HasRegion_Success() + { + var pimsUser = EntityHelper.CreateUser(1, Guid.NewGuid(), "testuser", regionCode: 1); + Action act = () => pimsUser.ThrowInvalidAccessToLeaseFile(1); + act.Should().NotThrow(); + } + #endregion + } +} diff --git a/source/backend/tests/unit/api/Services/LeaseReportsServiceTest.cs b/source/backend/tests/unit/api/Services/LeaseReportsServiceTest.cs index b6ba0e79a4..a7a51f3e46 100644 --- a/source/backend/tests/unit/api/Services/LeaseReportsServiceTest.cs +++ b/source/backend/tests/unit/api/Services/LeaseReportsServiceTest.cs @@ -28,6 +28,7 @@ public class LeaseReportsServiceTest : IDisposable { public TestHelper helper; public Mock leaseRepository; + public Mock userRepository; public ILeaseReportsService leaseReportsService; public LeaseReportsServiceTest() @@ -44,6 +45,7 @@ private void MockCommonServices() { this.leaseReportsService = this.helper.Create(); this.leaseRepository = this.helper.GetService>(); + this.userRepository = this.helper.GetService>(); } #region Tests @@ -59,7 +61,7 @@ public void GetAggregatedLeases_NotAuthorized() var term = new PimsLeaseTerm() { TermStartDate = DateTime.Now, TermExpiryDate = DateTime.Now.AddDays(10) }; this.MockCommonServices(); - this.leaseRepository.Setup(x => x.GetAllByFilter(It.IsAny(), true)).Returns(new List() { lease }); + this.leaseRepository.Setup(x => x.GetAllByFilter(It.IsAny(), It.IsAny>(), true)).Returns(new List() { lease }); // Act // Assert @@ -78,7 +80,9 @@ public void GetAggregatedLeases_Success() var term = new PimsLeaseTerm() { TermStartDate = DateTime.Now, TermExpiryDate = DateTime.Now.AddDays(10) }; this.MockCommonServices(); - this.leaseRepository.Setup(x => x.GetAllByFilter(It.IsAny(), true)).Returns(new List() { lease }); + this.leaseRepository.Setup(x => x.GetAllByFilter(It.IsAny(), It.IsAny>(), true)).Returns(new List() { lease }); + this.userRepository.Setup(x => x.GetByKeycloakUserId(It.IsAny())).Returns(new PimsUser() { PimsRegionUsers = new List() }); + // Act var leases = this.leaseReportsService.GetAggregatedLeaseReport(2022); @@ -86,7 +90,8 @@ public void GetAggregatedLeases_Success() // Assert leases.Should().HaveCount(1); leases.FirstOrDefault().Should().Be(lease); - this.leaseRepository.Verify(x => x.GetAllByFilter(It.IsAny(), true)); + this.leaseRepository.Verify(x => x.GetAllByFilter(It.IsAny(), It.IsAny>(), true)); + this.userRepository.Verify(x => x.GetByKeycloakUserId(It.IsAny())); } #endregion #endregion diff --git a/source/backend/tests/unit/api/Services/LeaseServiceTest.cs b/source/backend/tests/unit/api/Services/LeaseServiceTest.cs index 69f9f1d5ad..a88095711b 100644 --- a/source/backend/tests/unit/api/Services/LeaseServiceTest.cs +++ b/source/backend/tests/unit/api/Services/LeaseServiceTest.cs @@ -59,7 +59,10 @@ public void Update_WithoutStatusNote() }; var leaseRepository = _helper.GetService>(); + var userRepository = _helper.GetService>(); leaseRepository.Setup(x => x.GetNoTracking(It.IsAny())).Returns(currentLeaseEntity); + leaseRepository.Setup(x => x.Get(It.IsAny())).Returns(EntityHelper.CreateLease(1)); + userRepository.Setup(x => x.GetByKeycloakUserId(It.IsAny())).Returns(new PimsUser()); var noteRepository = _helper.GetService>(); @@ -89,7 +92,10 @@ public void Update_WithStatusNote() }; var leaseRepository = _helper.GetService>(); + var userRepository = _helper.GetService>(); leaseRepository.Setup(x => x.GetNoTracking(It.IsAny())).Returns(currentLeaseEntity); + leaseRepository.Setup(x => x.Get(It.IsAny())).Returns(EntityHelper.CreateLease(1)); + userRepository.Setup(x => x.GetByKeycloakUserId(It.IsAny())).Returns(new PimsUser()); var noteRepository = _helper.GetService>(); @@ -110,8 +116,11 @@ public void Update_Properties_Success() var leaseRepository = _helper.GetService>(); var propertyLeaseRepository = _helper.GetService>(); var propertyRepository = _helper.GetService>(); + var userRepository = _helper.GetService>(); propertyRepository.Setup(x => x.GetByPid(It.IsAny())).Returns(lease.PimsPropertyLeases.FirstOrDefault().Property); leaseRepository.Setup(x => x.GetNoTracking(It.IsAny())).Returns(lease); + leaseRepository.Setup(x => x.Get(It.IsAny())).Returns(EntityHelper.CreateLease(1)); + userRepository.Setup(x => x.GetByKeycloakUserId(It.IsAny())).Returns(new PimsUser()); // Act @@ -132,9 +141,12 @@ public void Update_Properties_Delete_Success() var leaseRepository = _helper.GetService>(); var propertyLeaseRepository = _helper.GetService>(); var propertyRepository = _helper.GetService>(); + var userRepository = _helper.GetService>(); propertyLeaseRepository.Setup(x => x.GetAllByLeaseId(It.IsAny())).Returns(lease.PimsPropertyLeases); propertyRepository.Setup(x => x.GetByPid(It.IsAny())).Returns(lease.PimsPropertyLeases.FirstOrDefault().Property); leaseRepository.Setup(x => x.GetNoTracking(It.IsAny())).Returns(lease); + leaseRepository.Setup(x => x.Get(It.IsAny())).Returns(EntityHelper.CreateLease(1)); + userRepository.Setup(x => x.GetByKeycloakUserId(It.IsAny())).Returns(new PimsUser()); // Act updatedLease = service.Update(updatedLease, new List()); @@ -156,11 +168,14 @@ public void Update_Properties_Delete_POI_Success() var leaseRepository = _helper.GetService>(); var propertyLeaseRepository = _helper.GetService>(); var propertyRepository = _helper.GetService>(); + var userRepository = _helper.GetService>(); propertyLeaseRepository.Setup(x => x.GetAllByLeaseId(It.IsAny())).Returns(lease.PimsPropertyLeases); propertyRepository.Setup(x => x.GetByPid(It.IsAny())).Returns(deletedProperty); propertyRepository.Setup(x => x.GetAllAssociationsById(It.IsAny())).Returns(lease.PimsPropertyLeases.FirstOrDefault().Property); leaseRepository.Setup(x => x.GetNoTracking(It.IsAny())).Returns(lease); + leaseRepository.Setup(x => x.Get(It.IsAny())).Returns(EntityHelper.CreateLease(1)); + userRepository.Setup(x => x.GetByKeycloakUserId(It.IsAny())).Returns(new PimsUser()); // Act updatedLease = service.Update(updatedLease, new List()); diff --git a/source/backend/tests/unit/dal/Repositories/LeaseRepositoryTest.cs b/source/backend/tests/unit/dal/Repositories/LeaseRepositoryTest.cs index d37afbc084..62ec5f1005 100644 --- a/source/backend/tests/unit/dal/Repositories/LeaseRepositoryTest.cs +++ b/source/backend/tests/unit/dal/Repositories/LeaseRepositoryTest.cs @@ -5,6 +5,7 @@ using FluentAssertions; using Microsoft.EntityFrameworkCore; using Moq; +using NSubstitute; using Pims.Api.Services; using Pims.Core.Test; using Pims.Dal.Entities; @@ -85,7 +86,7 @@ public void Get_Leases_Paged(LeaseFilter filter, int expectedCount) var service = helper.CreateRepository(user); // Act - var result = service.GetAllByFilter(filter); + var result = service.GetAllByFilter(filter, new HashSet()); // Assert Assert.NotNull(result); @@ -105,7 +106,7 @@ public void Get_Leases_NotAuthorized() // Act // Assert Assert.Throws(() => - service.GetAllByFilter(null)); + service.GetAllByFilter(null, new HashSet())); } [Theory] @@ -126,7 +127,7 @@ public void Get_Leases_Filter(LeaseFilter filter, int expectedCount) var service = helper.CreateRepository(user); // Act - var result = service.GetPage(filter); + var result = service.GetPage(filter, new HashSet()); // Assert Assert.NotNull(result); @@ -381,6 +382,9 @@ public void Update_Lease_Properties_Update() var propertyLeaseRepository = helper.GetService>(); propertyLeaseRepository.Setup(x => x.UpdatePropertyLeases(It.IsAny(), It.IsAny>())); + var userRepository = helper.GetService>(); + userRepository.Setup(x => x.GetUserInfoByKeycloakUserId(It.IsAny())).Returns(EntityHelper.CreateUser("test")); + // Act var updateProperty = EntityHelper.CreateProperty(context, 2); helper.SaveChanges(); diff --git a/source/frontend/src/features/leases/add/AddLeaseContainer.test.tsx b/source/frontend/src/features/leases/add/AddLeaseContainer.test.tsx index 19bc9d1464..f4d3c332d8 100644 --- a/source/frontend/src/features/leases/add/AddLeaseContainer.test.tsx +++ b/source/frontend/src/features/leases/add/AddLeaseContainer.test.tsx @@ -5,6 +5,7 @@ import MockAdapter from 'axios-mock-adapter'; import { createMemoryHistory } from 'history'; import { noop } from 'lodash'; +import { useUserInfoRepository } from '@/hooks/repositories/useUserInfoRepository'; import { mockLookups } from '@/mocks/lookups.mock'; import { Api_Lease } from '@/models/api/Lease'; import { UserOverrideCode } from '@/models/api/UserOverrideCode'; @@ -24,6 +25,27 @@ jest.mock('@react-keycloak/web'); }, }); +const retrieveUserInfo = jest.fn(); +jest.mock('@/hooks/repositories/useUserInfoRepository'); +(useUserInfoRepository as jest.Mock).mockReturnValue({ + retrieveUserInfo, + retrieveUserInfoLoading: true, + retrieveUserInfoResponse: { + userRegions: [ + { + id: 1, + userId: 5, + regionCode: 1, + }, + { + id: 2, + userId: 5, + regionCode: 2, + }, + ], + }, +}); + // Need to mock this library for unit tests jest.mock('react-visibility-sensor', () => { return jest.fn().mockImplementation(({ children }) => { diff --git a/source/frontend/src/features/leases/add/AdministrationSubForm.test.tsx b/source/frontend/src/features/leases/add/AdministrationSubForm.test.tsx index ba22c72750..342ba0367e 100644 --- a/source/frontend/src/features/leases/add/AdministrationSubForm.test.tsx +++ b/source/frontend/src/features/leases/add/AdministrationSubForm.test.tsx @@ -14,6 +14,9 @@ const storeState = { [lookupCodesSlice.name]: { lookupCodes: mockLookups }, }; +// mock auth library +jest.mock('@react-keycloak/web'); + describe('AdministrationSubForm component', () => { const setup = async ( renderOptions: RenderOptions & Partial = {}, @@ -25,6 +28,7 @@ describe('AdministrationSubForm component', () => { , { ...renderOptions, + claims: [], store: storeState, history, }, diff --git a/source/frontend/src/features/leases/add/AdministrationSubForm.tsx b/source/frontend/src/features/leases/add/AdministrationSubForm.tsx index a0ffd2467d..b30db83de9 100644 --- a/source/frontend/src/features/leases/add/AdministrationSubForm.tsx +++ b/source/frontend/src/features/leases/add/AdministrationSubForm.tsx @@ -5,6 +5,7 @@ import { Col, Row } from 'react-bootstrap'; import { FastDatePicker, Input, Select } from '@/components/common/form'; import { InlineInput } from '@/components/common/form/styles'; +import { UserRegionSelectContainer } from '@/components/common/form/UserRegionSelect/UserRegionSelectContainer'; import { Section } from '@/components/common/Section/Section'; import { SectionField } from '@/components/common/Section/SectionField'; import * as API from '@/constants/API'; @@ -29,7 +30,6 @@ const AdministrationSubForm: React.FunctionComponent< const purposeTypes = getOptionsByType(API.LEASE_PURPOSE_TYPES); const initiatorTypes = getOptionsByType(API.LEASE_INITIATOR_TYPES); const responsibilityTypes = getOptionsByType(API.LEASE_RESPONSIBILITY_TYPES); - const regionTypes = getOptionsByType(API.REGION_TYPES); //clear the associated other fields if the corresponding type has its value changed from other to something else. useEffect(() => { @@ -64,7 +64,7 @@ const AdministrationSubForm: React.FunctionComponent< - Southern Interior Region - - diff --git a/source/frontend/src/features/leases/add/__snapshots__/AdministrationSubForm.test.tsx.snap b/source/frontend/src/features/leases/add/__snapshots__/AdministrationSubForm.test.tsx.snap index 98c6adc57c..e95f7e9c34 100644 --- a/source/frontend/src/features/leases/add/__snapshots__/AdministrationSubForm.test.tsx.snap +++ b/source/frontend/src/features/leases/add/__snapshots__/AdministrationSubForm.test.tsx.snap @@ -126,8 +126,28 @@ exports[`AdministrationSubForm component renders as expected 1`] = ` class="c3 required text-left col-4" >
+ + + + +
diff --git a/source/frontend/src/features/leases/list/LeaseFilter/LeaseFilter.test.tsx b/source/frontend/src/features/leases/list/LeaseFilter/LeaseFilter.test.tsx index e6708e874f..4d90292bac 100644 --- a/source/frontend/src/features/leases/list/LeaseFilter/LeaseFilter.test.tsx +++ b/source/frontend/src/features/leases/list/LeaseFilter/LeaseFilter.test.tsx @@ -12,12 +12,17 @@ const storeState = { const setFilter = jest.fn(); +jest.mock('@react-keycloak/web'); + // render component under test const setup = ( renderOptions: RenderOptions & ILeaseFilterProps = { store: storeState, setFilter }, ) => { const { filter, setFilter: setFilterFn, ...rest } = renderOptions; - const utils = render(, { ...rest }); + const utils = render(, { + ...rest, + claims: [], + }); const searchButton = utils.getByTestId('search'); const resetButton = utils.getByTestId('reset-button'); return { searchButton, resetButton, setFilter: setFilterFn, ...utils }; diff --git a/source/frontend/src/features/leases/list/LeaseFilter/LeaseFilter.tsx b/source/frontend/src/features/leases/list/LeaseFilter/LeaseFilter.tsx index 3b238e696f..eeaede64be 100644 --- a/source/frontend/src/features/leases/list/LeaseFilter/LeaseFilter.tsx +++ b/source/frontend/src/features/leases/list/LeaseFilter/LeaseFilter.tsx @@ -6,13 +6,13 @@ import { FaTimes } from 'react-icons/fa'; import styled from 'styled-components'; import { ResetButton, SearchButton } from '@/components/common/buttons'; -import { FastDatePicker, Input, Select } from '@/components/common/form'; +import { FastDatePicker, Input } from '@/components/common/form'; +import { UserRegionSelectContainer } from '@/components/common/form/UserRegionSelect/UserRegionSelectContainer'; import { SelectInput } from '@/components/common/List/SelectInput'; import { FilterBoxForm } from '@/components/common/styles'; import TooltipIcon from '@/components/common/TooltipIcon'; -import { LEASE_PROGRAM_TYPES, LEASE_STATUS_TYPES, REGION_TYPES } from '@/constants/API'; +import { LEASE_PROGRAM_TYPES, LEASE_STATUS_TYPES } from '@/constants/API'; import useLookupCodeHelpers from '@/hooks/useLookupCodeHelpers'; -import { mapLookupCode } from '@/utils'; import { ILeaseFilter, ILeaseSearchBy } from '../../interfaces'; import { LeaseFilterSchema } from './LeaseFilterYupSchema'; @@ -71,8 +71,6 @@ export const LeaseFilter: React.FunctionComponent mapLookupCode(c)); - const leaseStatusOptions = lookupCodes.getByType(LEASE_STATUS_TYPES); const leaseProgramTypes = lookupCodes.getByType(LEASE_PROGRAM_TYPES); @@ -231,11 +229,7 @@ export const LeaseFilter: React.FunctionComponent - + + + + +