using AsbCloudApp.Data; using AsbCloudApp.Exceptions; using AsbCloudApp.Repositories; using AsbCloudApp.Requests; using AsbCloudApp.Services; using AsbCloudDb; using AsbCloudDb.Model; using Mapster; using Microsoft.EntityFrameworkCore; using System; using System.Collections.Generic; using System.Linq; using System.Threading; using System.Threading.Tasks; namespace AsbCloudInfrastructure.Repository; /// /// сервис по работе с faq-вопросами /// public class FaqRepository : IFaqRepository { private readonly IAsbCloudDbContext db; private readonly IWellService wellService; public FaqRepository(IAsbCloudDbContext db, IWellService wellService) { this.db = db; this.wellService = wellService; } public async Task> GetFilteredAsync(FaqRequest request, CancellationToken token) { var query = db.Faqs.AsNoTracking(); if (request.IsFrequently) { query = query.Where(o => o.IsFrequently); } if (request.HasAnswer) { query = query.Where(o => !string.IsNullOrEmpty(o.Answer)); } if (!request.IncludeDeleted) { query = query.Where(o => o.State != Faq.StateDeleted); } var entities = query .OrderByDescending(e => e.DateCreatedQuestion) .Select(o => new FaqDto() { Id = o.Id, Question = o.Question, Answer = o.Answer, CounterQuestion = o.CounterQuestion, IsFrequently = o.IsFrequently, State = o.State, DateCreatedQuestion = o.DateCreatedQuestion, IdAuthorQuestion = o.IdAuthorQuestion, AurhorQuestionName = o.AuthorQuestion.MakeDisplayName(), AurhorAnswerName = (o.AuthorAnswer != null) ? o.AuthorAnswer.MakeDisplayName() : string.Empty, }); var result = await entities.AsNoTracking() .ToArrayAsync(token) .ConfigureAwait(false); return result; } public async Task InsertAsync(FaqDto faqDto, CancellationToken token) { var entity = faqDto.Adapt(); entity.DateCreatedQuestion = entity.DateLastEditedQuestion = DateTimeOffset.UtcNow; entity.CounterQuestion = 1; entity.State = Faq.StateOpened; if (!string.IsNullOrEmpty(entity.Answer)) entity.IdAuthorAnswer = entity.IdAuthorQuestion; db.Faqs.Add(entity); await db.SaveChangesAsync(token).ConfigureAwait(false); return entity.Id; } public async Task MergeAsync(int sourceId1, int sourceId2, bool mergeQuestions, CancellationToken token) { var sourceFaqs = db.Faqs.Where(e => e.Id == sourceId1 || e.Id == sourceId2).ToArray(); if (sourceFaqs.Count() < 2) throw new ArgumentInvalidException(nameof(sourceFaqs), "Questions with target ids don't exist"); var newFaq = new Faq() { CounterQuestion = sourceFaqs.Sum(e => e.CounterQuestion), State = 0, IsFrequently = sourceFaqs.Any(e => e.IsFrequently), IdAuthorQuestion = sourceFaqs.Last().IdAuthorQuestion, DateCreatedQuestion = DateTimeOffset.UtcNow, DateLastEditedQuestion = DateTimeOffset.UtcNow, Answer = mergeQuestions == true ? string.Join(Environment.NewLine, sourceFaqs.Select(e => e.Answer)) : sourceFaqs.Last().Answer, Question = mergeQuestions == true ? string.Join(Environment.NewLine, sourceFaqs.Select(e => e.Question)) : sourceFaqs.Last().Question, }; db.Faqs.Add(newFaq); await db.SaveChangesAsync(token).ConfigureAwait(false); if (newFaq.Id == 0) throw new ArgumentInvalidException(nameof(sourceId1), "Error creating new question"); foreach (var sourceFaq in sourceFaqs) { sourceFaq.IdReplacementQuestion = newFaq.Id; sourceFaq.State = Faq.StateDeleted; } await db.SaveChangesAsync(token).ConfigureAwait(false); return newFaq.Id; } public async Task UpdateAsync(FaqDto dto, CancellationToken token) { var entity = dto.Adapt(); entity.DateLastEditedQuestion = DateTimeOffset.UtcNow; db.Faqs.Update(entity); return await db.SaveChangesAsync(token) .ConfigureAwait(false); } public async Task MarkAsDeletedAsync(int id, CancellationToken token) { var entity = db.Faqs.FirstOrDefault(e => e.Id == id) ?? throw new ArgumentInvalidException(nameof(id), "Question doesn't exist"); entity.State = Faq.StateDeleted; entity.DateLastEditedQuestion = DateTimeOffset.UtcNow; return await db.SaveChangesAsync(token) .ConfigureAwait(false); } public async Task DeleteAsync(int id, CancellationToken token) { var faq = db.Faqs.FirstOrDefault(f => f.Id == id) ?? throw new ArgumentInvalidException(nameof(id), "Question doesn't exist"); db.Faqs.Remove(faq); return await db.SaveChangesAsync(token); } }