using System; using System.Collections.Generic; using System.Linq; using System.Threading; using System.Threading.Tasks; using IdentityServer4.Extensions; using InternshipSystem.Api.Commands; using InternshipSystem.Api.Security; using InternshipSystem.Core; using InternshipSystem.Core.Entity.Internship; using InternshipSystem.Core.UglyOrmArtifacts; using InternshipSystem.Repository; using Microsoft.EntityFrameworkCore; namespace InternshipSystem.Api.UseCases { public class UpdateInternshipRegistrationUseCase { private readonly InternshipDbContext _dbContext; private readonly Edition _edition; private readonly User _user; private readonly InternshipRegistration subjectRegistration; public UpdateInternshipRegistrationUseCase(InternshipDbContext dbContext, InternshipRegistration internshipRegistration, Edition edition, User user) { _dbContext = dbContext; _edition = edition; _user = user; subjectRegistration = internshipRegistration; } public async Task<(DocumentState State, IEnumerable)> UpdateInternshipRegistration( UpdateRegistrationForm registrationCommand, CancellationToken cancellationToken) { subjectRegistration.Start = registrationCommand.Start ?? subjectRegistration.Start; subjectRegistration.End = registrationCommand.End ?? subjectRegistration.End; subjectRegistration.DeclaredHours = registrationCommand.Hours ?? subjectRegistration.DeclaredHours; if (registrationCommand.Type.HasValue) { UpdateInternshipType(registrationCommand.Type.Value); } if (registrationCommand.Mentor.HasValue) { UpdateMentor(registrationCommand.Mentor.Value); } if (!registrationCommand.Subjects.IsNullOrEmpty()) { UpdateSubjects(registrationCommand.Subjects); } if (registrationCommand.Company.HasValue) { await UpdateCompanyAndBranch(registrationCommand.Company.Value, cancellationToken); } return subjectRegistration.ValidateStatus(_edition); } private void UpdateInternshipType(long typeId) { var editionInternshipType = _edition.AvailableInternshipTypes.FirstOrDefault(i => i.InternshipTypeId == typeId); subjectRegistration.Type = editionInternshipType?.InternshipType ?? subjectRegistration.Type; } private async Task UpdateCompanyAndBranch(UpdateCompany companyUpdate, CancellationToken cancellationToken) { var company = subjectRegistration.Company; if (companyUpdate.Id.HasValue) { company = await _dbContext.Companies .Include(c => c.Branches) .FirstAsync(c => c.Id == companyUpdate.Id.Value, cancellationToken); } else if (companyUpdate.IsCustomUpdate) { company = await _dbContext.Companies .Include(c => c.Branches) .SingleOrDefaultAsync(c => c.Provider == _user.PersonNumber, cancellationToken) ?? Company.CreateCompany(companyUpdate.Nip, companyUpdate.Name, _user.PersonNumber); company.Name = companyUpdate.Name ?? company.Name; company.Nip = companyUpdate.Nip ?? company.Nip; subjectRegistration.BranchAddress = null; } if (companyUpdate.BranchOffice.HasValue) { var branchUpdate = companyUpdate.BranchOffice.Value; var branch = subjectRegistration.BranchAddress; if (branchUpdate.Id.HasValue) { branch = company.Branches.First(b => b.Id == branchUpdate.Id.Value); } else if (branchUpdate.IsCustomUpdate) { branch = company.Branches.FirstOrDefault(b => b.Provider == _user.PersonNumber); if (branch == null) { branch = BranchOffice.CreateBranch(branchUpdate.Country, branchUpdate.City, branchUpdate.PostalCode, branchUpdate.Street, branchUpdate.Building, _user.PersonNumber); company.AddBranchOffice(branch); } branch.Address.Country = branchUpdate.Country ?? branch.Address.Country; branch.Address.City = branchUpdate.City ?? branch.Address.City; branch.Address.PostalCode = branchUpdate.PostalCode ?? branch.Address.PostalCode; branch.Address.Street = branchUpdate.Country ?? branch.Address.Street; branch.Address.Building = branchUpdate.Building ?? branch.Address.Building; } subjectRegistration.BranchAddress = branch; } subjectRegistration.Company = company; } private void UpdateSubjects(IEnumerable subjects) { if (!_edition.AreSubjectsAvailable(subjects)) { throw new ArgumentException("subjects chosen are not available in this edition"); } subjectRegistration.Subjects = subjects .Select(i => new ProgramSubject { Registration = subjectRegistration, InternshipSubjectId = i }) .ToList(); } private void UpdateMentor(UpdateMentor mentorUpdate) { subjectRegistration.Mentor ??= new Mentor(); subjectRegistration.Mentor.UpdateInformation(mentorUpdate.FirstName, mentorUpdate.LastName, mentorUpdate.Email, mentorUpdate.PhoneNumber); } } }