namespace Hims.Infrastructure.Services
{
    using System;
    using System.Collections.Generic;
    using System.Threading.Tasks;
    using Dapper;
    using Domain.Entities;
    using Domain.Repositories.UnitOfWork;
    using Domain.Services;
    using Shared.EntityModels;
    using Shared.UserModels.Filters;

    /// <inheritdoc />
    public class FeedbackServices : IFeedbackService
    {
        /// <summary>
        /// The unit of work.
        /// </summary>
        private readonly IUnitOfWork unitOfWork;

        /// <inheritdoc cref="IFeedbackService" />
        public FeedbackServices(IUnitOfWork unitOfWork) => this.unitOfWork = unitOfWork;


        /// <inheritdoc />
        public async Task<int> AddAsync(FeedbackModel model)
        {
            try
            {

                var feedback = new Feedback
                {

                    RatingId = model.RatingId,
                    RatingStatus = model.RatingStatus,
                    PatientId = model.PatientId,
                    Mobile = model.Mobile,
                    Comments = model.Comments,
                    Question = model.Question
,
                    CreatedDate = DateTime.UtcNow,
                };

                return await this.unitOfWork.Feedbacks.InsertAsync(feedback);
            }
            catch (Exception e)
            {
                Console.WriteLine(e.Message.ToString());
            }

            return 0;
        }

        /// <inheritdoc />
        public Task<IEnumerable<FeedbackModel>> FetchQuestionAsync(FeedbackFilterModel model)
        {
            var where = " WHERE 1 = 1 ";
            if (model.RatingId > 0)
            {
                where += $@" AND ""RatingId""= {model.RatingId}";
            }

            if (!string.IsNullOrEmpty(model.CreatedDate))
            {
                where += $@" And f.""CreatedDate"":: DATE = '{model.CreatedDate}' :: DATE";
            }

            var query = $@"SELECT COUNT(*) OVER () AS ""TotalItems"", * FROM ""QuestionFeedback"" 
                         { where} Order by ""QuestionFeedbackId"" DESC";

            if (model.PageIndex <= 0)
            {
                return this.unitOfWork.Current.QueryAsync<FeedbackModel>(query);
            }

            model.PageIndex -= 1;
            query += " LIMIT " + model.PageSize + " offset " + (model.PageIndex * model.PageSize);
            return this.unitOfWork.Current.QueryAsync<FeedbackModel>(query);
        }

        /// <inheritdoc />
        public async Task<int> UpdateAsync(FeedbackModel model)
        {
            var checkIf = await this.unitOfWork.Current.QueryFirstOrDefaultAsync<int>($@"SELECT COUNT(""QuestionFeedbackId"") FROM ""QuestionFeedback"" WHERE TRIM(UPPER(""Question"")) = '{model.Question.ToUpper().Trim()}' AND ""QuestionFeedbackId"" <> {model.QuestionFeedbackId}");
            if (checkIf > 0)
            {
                return -1;
            }

            var feedback = await this.unitOfWork.QuestionFeedbacks.FindAsync(m => m.QuestionFeedbackId == model.QuestionFeedbackId);
            feedback.Question = model.Question;
            feedback.Active = true;
            feedback.ModifiedBy = model.ModifiedBy;
            feedback.ModifiedDate = DateTime.UtcNow;
            return await this.unitOfWork.QuestionFeedbacks.UpdateAsync(feedback);
        }

        /// <inheritdoc />
        public Task<int> DeleteAsync(int questionFeedbackId)
        {
            var query = $@"DELETE FROM ""QuestionFeedback"" WHERE ""QuestionFeedbackId""= {questionFeedbackId}";
            return this.unitOfWork.Current.ExecuteAsync(query);
        }

        /// <inheritdoc />
        public Task<IEnumerable<FeedbackModel>> FetchAsync(FeedbackFilterModel model)
        {
            var where = " WHERE 1 = 1 ";
            if (model.RatingId > 0)
            {
                where += $@" AND ""RatingId""= {model.RatingId}";
            }

            if (!string.IsNullOrEmpty(model.CreatedDate))
            {
                where += $@" And f.""CreatedDate"":: DATE = '{model.CreatedDate}' :: DATE";
            }

            var query = $@"SELECT COUNT(*) OVER () AS ""TotalItems"", f.*, p.""PatientId"", p.""FullName""  FROM ""Feedback"" f left join ""Patient"" p on p.""PatientId"" = f.""PatientId""
                         {where} Order by f.""FeedbackId"" DESC";

            if (model.PageIndex <= 0)
            {
                return this.unitOfWork.Current.QueryAsync<FeedbackModel>(query);
            }

            model.PageIndex -= 1;
            query += " LIMIT " + model.PageSize + " offset " + (model.PageIndex * model.PageSize);
            return this.unitOfWork.Current.QueryAsync<FeedbackModel>(query);
        }

        /// <inheritdoc />
        public async Task<int> AddFeedbackQuestionAsync(FeedbackModel model)
        {
            try
            {
                var checkIf = await this.unitOfWork.Current.QueryFirstOrDefaultAsync<int>($@"SELECT COUNT(""QuestionFeedbackId"") FROM ""QuestionFeedback"" WHERE TRIM(UPPER(""Question"")) = '{model.Question.ToUpper().Trim()}'");
                if (checkIf > 0)
                {
                    return -1;
                }

                var question = new QuestionFeedback
                {

                    Question = model.Question,
                    CreatedBy = model.CreatedBy,
                    CreatedDate = DateTime.UtcNow,
                    Active = true,

                };

                return await this.unitOfWork.QuestionFeedbacks.InsertAsync(question);
            }
            catch (Exception e)
            {
                Console.WriteLine(e.Message.ToString());
            }

            return 0;
        }
    }
}