using CityInfo.API.DbContexts; using CityInfo.API.Entities; using Microsoft.EntityFrameworkCore; namespace CityInfo.API.Services { public class CityInfoRepository : ICityInfoRepository { private CityInfoContext _context; public CityInfoRepository(CityInfoContext context) { _context = context ?? throw new ArgumentNullException(nameof(CityInfoContext)); } public async Task> GetCitiesAsync() { return await _context.Cities.OrderBy((city) => city.Name).ToListAsync(); } public async Task<(IEnumerable, PaginationMetadata)> GetCitiesAsync(string? name, string? searchQuery, int pageNumber, int pageSize) { var collection = _context.Cities as IQueryable; if (!string.IsNullOrEmpty(name)) { name = name.Trim(); collection = collection.Where((city) => city.Name == name); } if (!string.IsNullOrEmpty(searchQuery)) { searchQuery = searchQuery.Trim(); collection = collection.Where( (city) => ( city.Name.Contains(searchQuery) | (city.Description != null && city.Description.Contains(searchQuery)) ) ); } var totalItemCount = await collection.CountAsync(); var paginationMetaData = new PaginationMetadata(totalItemCount, pageSize, pageNumber); var collectionToReturn = await collection .OrderBy((city) => city.Name) .Skip(pageSize * (pageNumber - 1)) .Take(pageSize) .ToListAsync(); return (collectionToReturn, paginationMetaData); } public async Task GetCityAsync(int cityId, bool includePointsOfinterest) { if (includePointsOfinterest) { return await _context.Cities .Include((city) => city.PointsOfInterest) .Where((city) => city.Id == cityId) .FirstOrDefaultAsync(); } return await _context.Cities .Where((city) => city.Id == cityId) .FirstOrDefaultAsync(); } public async Task CityExistAsync(int cityId) { return await _context.Cities.AnyAsync((city) => city.Id == cityId); } public async Task> GetPointsOfinterestForCityAsync(int cityId) { return await _context.PointsOfInterest.Where((poi) => poi.CityId == cityId).ToListAsync(); } public async Task GetPointOfInterestForCityAsync(int cityId, int pointOfInterestId) { return await _context.PointsOfInterest.Where((poi) => poi.CityId == cityId && poi.Id == pointOfInterestId).FirstOrDefaultAsync(); } public async Task CreatePointOfInterestForCityAsync(int cityId, PointOfInterest pointOfInterest) { var city = await GetCityAsync(cityId, includePointsOfinterest: false); if (city != null) { city.PointsOfInterest.Add(pointOfInterest); } } public async Task SaveChangesAsync() { return (await _context.SaveChangesAsync() >= 0); } public void DeletePointOfInterest(PointOfInterest pointOfInterest) { _context.PointsOfInterest.Remove(pointOfInterest); } public async Task CityNameMatchesCityId(string? cityName, int cityId) { return await _context.Cities.AnyAsync((city) => city.Name == cityName && city.Id == cityId); } } }