using System;
using System.Collections.Generic;
using System.IdentityModel.Tokens.Jwt;
using System.Linq;
using System.Security.Claims;
using System.Text;

using FMSAdmin.Data;
using FMSAdmin.Helpers;
using FMSAdmin.Entities;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
using Microsoft.IdentityModel.Tokens;
using FMSAdmin.Models;
using System.Transactions;

namespace FMSAdmin.Services {
    public class AnnouncementService {
        private readonly ILogger<AnnouncementService> _logger;
        private readonly FMSContext _context;
        private readonly StorageHelper _storage;
        private readonly PushHelper _push;

        public AnnouncementService(
            ILogger<AnnouncementService> logger,
            FMSContext context,
            StorageHelper storage,
            PushHelper push) {
            _logger = logger;
            _context = context;
            _storage = storage;
            _push = push;
        }

        public IQueryable<CmAnnouncement> GetAll() {
            var query = _context.CmAnnouncement;
            return query;
        }

        public IQueryable<CmAnnouncement> Gets(int id, int siteId) {
            var data = _context.CmAnnouncement.Where(x => x.AnnouncementId == id && x.SiteId == siteId);
            return data;
        }

        public void Create(CmAnnouncement data) {
            using (var trans = new TransactionScope()) {
                if (data.CmFile != null && data.CmFile.IsUpload) {
                    data.CmFile.SiteId = data.SiteId;
                    var category = _context.CmFileCategory.First(x => x.Name == "announcement");
                    data.CmFile.FileCategory = category;
                    data.CmFile.CreatedDate = DateTime.Now;
                } else {
                    data.CmFile = null;
                }
                data.IsUse = true;
                data.ReadCount = 0;
                data.AddDate = DateTime.Now;
                _context.CmAnnouncement.Add(data);
                _context.SaveChanges();

                if (data.CmFile != null && data.CmFile.IsUpload) {
                    // 카피
                    _storage.CopyEntity(data.CmFile.Path, data.CmFile);
                }

                trans.Complete();
            }

            if (data.IsAllView != null && data.IsAllView == true) {
                _push.SendToAllUsers("공지사항", data.Title, new {
                    type = "announcement",
                    id = data.AnnouncementId
                });
            } else {
                _push.SendToSiteUsers(data.SiteId, "공지사항", data.Title, new {
                    type = "announcement",
                    id = data.AnnouncementId
                });
            }

        }

        public void Edit(int id, int siteId, CmAnnouncement data) {
            using (var trans = new TransactionScope()) {
                if (data.CmFile != null && data.CmFile.IsUpload) {
                    data.CmFile.SiteId = data.SiteId;
                    var category = _context.CmFileCategory.First(x => x.Name == "announcement");
                    data.CmFile.FileCategory = category;
                    data.CmFile.CreatedDate = DateTime.Now;
                }

                var persist = _context.CmAnnouncement
                                .Where(x => x.AnnouncementId == id && x.SiteId == siteId).FirstOrDefault();
                if (persist == null) {
                    throw new ServiceException("정보를 찾을 수 없습니다.");
                }

                persist.SiteId = data.SiteId;
                persist.AnnouncementId = data.AnnouncementId;
                persist.BusinessFieldId = data.BusinessFieldId;
                persist.Title = data.Title;
                persist.Contents = data.Contents;
                persist.RegisterUserId = data.RegisterUserId;
                persist.UpdateDate = data.UpdateDate;
                persist.IsAllView = data.IsAllView;
                if (data.CmFile != null && data.CmFile.IsUpload) {
                    persist.CmFile = data.CmFile;
                }
                if (data.CmFile != null && data.CmFile.IsDelete) {
                    persist.CmFile = null;
                    persist.FileId = null;
                }
                _context.CmAnnouncement.Update(persist);
                _context.SaveChanges();

                if (data.CmFile != null && data.CmFile.IsUpload) {
                    // 카피
                    _storage.CopyEntity(data.CmFile.Path, persist.CmFile);
                }

                trans.Complete();
            }
        }

        public void Delete(int id, int siteId) {
            var data = _context.CmAnnouncement.First(x => x.AnnouncementId == id && x.SiteId == siteId);
            _context.CmAnnouncement.Remove(data);
            _context.SaveChanges();
        }

        public void AddCount(int id, int siteId) {
            var persist = _context.CmAnnouncement
                            .Where(x => x.AnnouncementId == id && x.SiteId == siteId).FirstOrDefault();
            if (persist == null) {
                throw new ServiceException("정보를 찾을 수 없습니다.");
            }

            persist.ReadCount += 1;
            _context.CmAnnouncement.Update(persist);
            _context.SaveChanges();
        }
    }
}