using e_suite.API.Common.repository;
using e_suite.Database.Audit;
using e_suite.Database.Core;
using e_suite.Database.Core.Extensions;
using e_suite.Database.Core.Tables.Printer;
using eSuite.Core.Miscellaneous;
using Microsoft.EntityFrameworkCore;

namespace e_suite.Modules.SpecificationManager.repository;

public class SpecificationManagerRepository : RepositoryBase, ISpecificationManagerRepository
{
    public SpecificationManagerRepository(IEsuiteDatabaseDbContext databaseDbContext) : base(databaseDbContext)
    {
    }

    public IQueryable<Specification> GetSpecifications()
    {
        return DatabaseDbContext.Specifications
            .Include(x => x.Site)
            .ThenInclude( x => x.Organisation)
            .Where(x => x.Deleted == false);
    }

    public IQueryable<Specification> GetSpecificationsFromForms(IEnumerable<long> formIds)
    {
        var specifications = GetSpecifications()
            .Where(x => formIds.Contains(x.Id));

        return specifications;
    }

    public async Task<Specification?> GetSpecification(GeneralIdRef generalIdRef, CancellationToken cancellationToken)
    {
        return await GetSpecifications().FindByGeneralIdRefAsync(generalIdRef, cancellationToken);
    }
    
    public async Task CreateSpecification(
        AuditUserDetails auditUserDetails,
        Specification newSpecification,
        CancellationToken cancellationToken
    )
    {
        DatabaseDbContext.Specifications.Add(newSpecification);
        await DatabaseDbContext.SaveChangesAsync(auditUserDetails, cancellationToken);
    }

    public async Task CreateSpecification(
        AuditUserDetails auditUserDetails,
        IEnumerable<Specification> newSpecifications,
        CancellationToken cancellationToken
    )
    {
        await DatabaseDbContext.Specifications.AddRangeAsync(newSpecifications, cancellationToken);
        await DatabaseDbContext.SaveChangesAsync(auditUserDetails, cancellationToken);
    }

    public async Task EditSpecification(
        AuditUserDetails auditUserDetails,
        Specification specification,
        CancellationToken cancellationToken
    )
    {
        DatabaseDbContext.Specifications.Update(specification);
        await DatabaseDbContext.SaveChangesAsync(auditUserDetails, cancellationToken);
    }

    public async Task EditSpecification(
        AuditUserDetails auditUserDetails,
        IEnumerable<Specification> specifications,
        CancellationToken cancellationToken
    )
    {
        DatabaseDbContext.Specifications.UpdateRange(specifications);
        await DatabaseDbContext.SaveChangesAsync(auditUserDetails, cancellationToken);
    }
}