using CMSMicroservice.Protobuf.Protos.SitePageSettings;
using CMSMicroservice.Application.SitePageSettingsCQ.Commands.DeletePageImage;
using CMSMicroservice.Application.SitePageSettingsCQ.Commands.SavePageImage;
using CMSMicroservice.Application.SitePageSettingsCQ.Commands.SavePageSettings;
using CMSMicroservice.Application.SitePageSettingsCQ.Queries.GetAllPageSettings;
using CMSMicroservice.Application.SitePageSettingsCQ.Queries.GetPageSettings;
using Google.Protobuf.WellKnownTypes;
using Grpc.Core;
using MediatR;

namespace CMSMicroservice.WebApi.Services;

public class SitePageSettingsService : SitePageSettingsContract.SitePageSettingsContractBase
{
    private readonly ISender _sender;

    public SitePageSettingsService(ISender sender)
    {
        _sender = sender;
    }

    // ── GetPageSettings ──
    public override async Task<PageSettingsResponse> GetPageSettings(GetPageSettingsRequest request, ServerCallContext context)
    {
        var query = new GetPageSettingsQuery { PageKey = request.PageKey };
        var result = await _sender.Send(query, context.CancellationToken);

        if (result == null)
            throw new RpcException(new Status(StatusCode.NotFound, $"صفحه با کلید '{request.PageKey}' یافت نشد"));

        return MapToResponse(result);
    }

    // ── GetAllPageSettings ──
    public override async Task<GetAllPageSettingsResponse> GetAllPageSettings(GetAllPageSettingsRequest request, ServerCallContext context)
    {
        var query = new GetAllPageSettingsQuery();
        var result = await _sender.Send(query, context.CancellationToken);

        var response = new GetAllPageSettingsResponse();
        foreach (var item in result)
        {
            response.Pages.Add(new PageSettingsSummary
            {
                Id = item.Id,
                PageKey = item.PageKey,
                Title = item.Title,
                IsActive = item.IsActive,
                ImageCount = item.ImageCount,
                LastModified = Timestamp.FromDateTime(DateTime.SpecifyKind(item.LastModified, DateTimeKind.Utc))
            });
        }

        return response;
    }

    // ── SavePageSettings ──
    public override async Task<SavePageSettingsResponse> SavePageSettings(SavePageSettingsRequest request, ServerCallContext context)
    {
        var command = new SavePageSettingsCommand
        {
            PageKey = request.PageKey,
            Title = request.Title,
            MetaDescription = request.MetaDescription,
            HeroTitle = request.HeroTitle,
            HeroSubtitle = request.HeroSubtitle,
            IsActive = request.IsActive,
            SettingsJson = request.SettingsJson,
            ImageFileBytes = request.HeroImageFile?.File?.ToByteArray(),
            ImageFileMime = request.HeroImageFile?.Mime,
            ImageFileName = request.HeroImageFile?.FileName
        };

        var result = await _sender.Send(command, context.CancellationToken);
        return new SavePageSettingsResponse { Id = result.Id, Success = result.Success };
    }

    // ── SavePageImage ──
    public override async Task<SavePageImageResponse> SavePageImage(SavePageImageRequest request, ServerCallContext context)
    {
        var command = new SavePageImageCommand
        {
            Id = request.Id,
            SitePageSettingsId = request.SitePageSettingsId,
            ImageGroup = request.ImageGroup,
            Title = request.Title,
            Subtitle = request.Subtitle,
            Description = request.Description,
            LinkUrl = request.LinkUrl,
            IconName = request.IconName,
            SortOrder = request.SortOrder,
            IsActive = request.IsActive,
            ImageFileBytes = request.ImageFile?.File?.ToByteArray(),
            ImageFileMime = request.ImageFile?.Mime,
            ImageFileName = request.ImageFile?.FileName
        };

        var result = await _sender.Send(command, context.CancellationToken);
        return new SavePageImageResponse { Id = result.Id, Success = result.Success };
    }

    // ── DeletePageImage ──
    public override async Task<Empty> DeletePageImage(DeletePageImageRequest request, ServerCallContext context)
    {
        var command = new DeletePageImageCommand { Id = request.Id };
        await _sender.Send(command, context.CancellationToken);
        return new Empty();
    }

    // ── Private Mapping Helpers ──
    private static PageSettingsResponse MapToResponse(PageSettingsDto dto)
    {
        var response = new PageSettingsResponse
        {
            Id = dto.Id,
            PageKey = dto.PageKey,
            Title = dto.Title,
            MetaDescription = dto.MetaDescription,
            HeroTitle = dto.HeroTitle,
            HeroSubtitle = dto.HeroSubtitle,
            HeroImagePath = dto.HeroImagePath,
            IsActive = dto.IsActive,
            SettingsJson = dto.SettingsJson ?? string.Empty
        };

        foreach (var img in dto.Images)
        {
            response.Images.Add(new PageImageItem
            {
                Id = img.Id,
                ImageGroup = img.ImageGroup,
                Title = img.Title,
                Subtitle = img.Subtitle,
                Description = img.Description,
                ImagePath = img.ImagePath,
                ThumbnailPath = img.ThumbnailPath,
                LinkUrl = img.LinkUrl,
                IconName = img.IconName,
                SortOrder = img.SortOrder,
                IsActive = img.IsActive
            });
        }

        return response;
    }
}
