@page "/store/order/{slug}"

@using Moonlight.App.Services.Store
@using Moonlight.App.Services
@using Moonlight.App.Database.Entities.Store
@using Moonlight.App.Repositories
@using Moonlight.App.Services.ServiceManage

@inject ConfigService ConfigService
@inject StoreService StoreService
@inject IdentityService IdentityService
@inject AlertService AlertService
@inject NavigationManager Navigation
@inject ServiceService ServiceService
@inject Repository<Product> ProductRepository
@inject Repository<Coupon> CouponRepository

<LazyLoader Load="Load">
    @if (SelectedProduct == null)
    {
        @*
TODO: Add 404 here
*@
    }
    else
    {
        <div class="row">
            <div class="col-md-7 col-12">
                <div class="card mb-5">
                    <div class="card-body">
                        <h2 class="fs-2x fw-bold mb-10">@(SelectedProduct.Name)</h2>
                        <p class="text-gray-400 fs-4 fw-semibold">
                            @Formatter.FormatLineBreaks(SelectedProduct.Description)
                        </p>
                    </div>
                </div>
                <div class="row mb-5">
                    <div class="col-md-4 col-12">
                        <a @onclick="() => SetDurationMultiplier(1)" @onclick:preventDefault href="#" class="card card-body bg-hover-secondary text-center @(DurationMultiplier == 1 ? "border border-info" : "")">
                            <h4 class="fw-bold mb-0 align-middle">@(SelectedProduct.Duration * 1) days</h4>
                        </a>
                    </div>
                    <div class="col-md-4 col-12">
                        <a @onclick="() => SetDurationMultiplier(2)" @onclick:preventDefault href="#" class="card card-body bg-hover-secondary text-center @(DurationMultiplier == 2 ? "border border-info" : "")">
                            <h4 class="fw-bold mb-0 align-middle">@(SelectedProduct.Duration * 2) days</h4>
                        </a>
                    </div>
                    <div class="col-md-4 col-12">
                        <a @onclick="() => SetDurationMultiplier(3)" @onclick:preventDefault href="#" class="card card-body bg-hover-secondary text-center @( DurationMultiplier == 3 ? "border border-info" : "")">
                            <h4 class="fw-bold mb-0 align-middle">@(SelectedProduct.Duration * 3) days</h4>
                        </a>
                    </div>
                </div>
                <div class="card mb-5">
                    <div class="card-body">
                        <h3 class="fs-1x fw-bold mb-10">Apply coupon codes</h3>
                        <div class="input-group">
                            <input @bind="CouponCode" class="form-control form-control-solid" placeholder="Coupon code..."/>
                            <button @onclick="ApplyCoupon" class="btn btn-primary">Apply</button>
                        </div>
                    </div>
                </div>
            </div>
            <div class="col-md-1 col-12"></div>
            <div class="col-md-3 col-12">
                <div class="card">
                    <div class="card-header">
                        <h3 class="card-title">Summary</h3>
                    </div>

                    @{
                        var defaultPrice = SelectedProduct.Price * DurationMultiplier;
                        double actualPrice;

                        if (SelectedCoupon == null)
                            actualPrice = defaultPrice;
                        else
                            actualPrice = Math.Round(defaultPrice - (defaultPrice * SelectedCoupon.Percent / 100), 2);

                        var currency = ConfigService.Get().Store.Currency;
                    }

                    <div class="card-body fs-5">
                        <div class="d-flex flex-stack">
                            <div class="text-gray-700 fw-semibold me-2">Today</div>
                            <div class="d-flex align-items-senter">
                                <span class="fw-bold">@(currency) @(actualPrice)</span>
                            </div>
                        </div>
                        <div class="d-flex flex-stack">
                            <div class="text-gray-700 fw-semibold me-2">Renew</div>
                            <div class="d-flex align-items-senter">
                                <span class="fw-bold">@(currency) @(SelectedProduct.Price)</span>
                            </div>
                        </div>
                        <div class="d-flex flex-stack">
                            <div class="text-gray-700 fw-semibold me-2">Duration</div>
                            <div class="d-flex align-items-senter">
                                <span class="fw-bold">@(SelectedProduct.Duration * DurationMultiplier) days</span>
                            </div>
                        </div>
                        <div class="separator my-4"></div>
                        <div class="d-flex flex-stack">
                            <div class="text-gray-700 fw-semibold me-2">Discount</div>
                            <div class="d-flex align-items-senter">
                                <span class="fw-bold">@(SelectedCoupon?.Percent ?? 0)%</span>
                            </div>
                        </div>
                        <div class="d-flex flex-stack">
                            <div class="text-gray-700 fw-semibold me-2">Coupon</div>
                            <div class="d-flex align-items-senter">
                                <span class="fw-bold">@(SelectedCoupon?.Code ?? "None")</span>
                            </div>
                        </div>
                        <div class="separator my-4"></div>
                        <div class="d-flex flex-stack">
                            <div class="text-gray-700 fw-semibold me-2">Total</div>
                            <div class="d-flex align-items-senter">
                                <span class="fw-bold">@(currency) @(actualPrice)</span>
                            </div>
                        </div>
                        <div class="mt-7">
                            @if (!CanBeOrdered && !string.IsNullOrEmpty(ErrorMessage))
                            {
                                <div class="alert alert-warning bg-warning text-white text-center">
                                    @ErrorMessage
                                </div>
                            }
                        </div>
                    </div>
                    <div class="card-footer">
                        @if (IsValidating)
                        {
                            <button class="btn btn-primary w-100 disabled" disabled="">
                                <span class="spinner-border spinner-border-sm align-middle"></span>
                            </button>
                        }
                        else
                        {
                            if (CanBeOrdered)
                            {
                                <WButton OnClick="OnSubmit" Text="@($"Order for {currency} {actualPrice}")" CssClasses="btn btn-primary w-100"/>
                            }
                            else
                            {
                                <button class="btn btn-primary w-100 disabled" disabled="">Order for @(currency) @(actualPrice)</button>
                            }
                        }
                    </div>
                </div>
            </div>
            <div class="col-md-1 col-12"></div>
        </div>
    }
</LazyLoader>

@code
{
    [Parameter]
    public string Slug { get; set; }

    private Product? SelectedProduct;
    private Coupon? SelectedCoupon;
    private int DurationMultiplier = 1;

    private string CouponCode = "";

    private bool CanBeOrdered = false;
    private bool IsValidating = false;
    private string ErrorMessage = "";

    private async Task SetDurationMultiplier(int i)
    {
        DurationMultiplier = i;

        await Revalidate();
    }

    private async Task ApplyCoupon()
    {
        SelectedCoupon = CouponRepository
            .Get()
            .FirstOrDefault(x => x.Code == CouponCode);

        CouponCode = "";
        await InvokeAsync(StateHasChanged);

        if (SelectedCoupon == null)
        {
            await AlertService.Error("", "Invalid coupon code entered");
            return;
        }

        await Revalidate();
    }

    private Task Revalidate()
    {
        if (SelectedProduct == null) // Prevent validating null
            return Task.CompletedTask;

        IsValidating = true;
        InvokeAsync(StateHasChanged);

        Task.Run(async () =>
        {
            try
            {
                await StoreService.Order.Validate(IdentityService.CurrentUser, SelectedProduct, DurationMultiplier, SelectedCoupon);
                CanBeOrdered = true;
            }
            catch (DisplayException e)
            {
                CanBeOrdered = false;
                ErrorMessage = e.Message;
            }

            IsValidating = false;
            await InvokeAsync(StateHasChanged);
        });

        return Task.CompletedTask;
    }

    private async Task Load(LazyLoader _)
    {
        SelectedProduct = ProductRepository
            .Get()
            .FirstOrDefault(x => x.Slug == Slug);

        await Revalidate();
    }

    private async Task OnSubmit()
    {
        if (SelectedProduct == null) // Prevent processing null
            return;

    // Process the order with the selected values
        var service = await StoreService
            .Order
            .Process(
                IdentityService.CurrentUser,
                SelectedProduct,
                DurationMultiplier,
                SelectedCoupon
            );

        Navigation.NavigateTo("/service/" + service.Id);
    }
}