@namespace Oqtane.Modules.Admin.UserProfile
@inherits ModuleBase
@inject NavigationManager NavigationManager
@inject IUserService UserService
@inject IProfileService ProfileService
@inject ISettingService SettingService
@inject INotificationService NotificationService
@inject IStringLocalizer<Index> Localizer

@if (PageState.User != null && photofileid != -1)
{
    <img src="@(ContentUrl(photofileid))" alt="@displayname" style="max-width: 400px" class="rounded-circle mx-auto d-block">
}
else
{
    <br />
}
<TabStrip>
    <TabPanel Name="Identity" ResourceKey="Identity">
        @if (PageState.User != null)
        {
            <table class="table table-borderless">
                <tr>
                    <td>
                        <label for="Name" class="control-label">@Localizer["Username:"] </label>
                    </td>
                    <td>
                        <input class="form-control" @bind="@username" readonly />
                    </td>
                </tr>
                <tr>
                    <td>
                        <label for="Name" class="control-label">@Localizer["Password:"] </label>
                    </td>
                    <td>
                        <input type="password" class="form-control" @bind="@password" autocomplete="new-password" />
                    </td>
                </tr>
                <tr>
                    <td>
                        <label for="Name" class="control-label">@Localizer["Confirm Password:"] </label>
                    </td>
                    <td>
                        <input type="password" class="form-control" @bind="@confirm" autocomplete="new-password" />
                    </td>
                </tr>
                <tr>
                    <td>
                        <label for="Name" class="control-label">@Localizer["Email:"] </label>
                    </td>
                    <td>
                        <input class="form-control" @bind="@email" />
                    </td>
                </tr>
                <tr>
                    <td>
                        <label for="Name" class="control-label">@Localizer["Full Name:"] </label>
                    </td>
                    <td>
                        <input class="form-control" @bind="@displayname" />
                    </td>
                </tr>
                <tr>
                    <td>
                        <label for="Name" class="control-label">@Localizer["Photo:"] </label>
                    </td>
                    <td>
                        <FileManager FileId="@photofileid" @ref="filemanager" />
                    </td>
                </tr>
            </table>
            <button type="button" class="btn btn-primary" @onclick="Save">@Localizer["Save"]</button>
            <button type="button" class="btn btn-secondary" @onclick="Cancel">@Localizer["Cancel"]</button>
        }
    </TabPanel>
    <TabPanel Name="Profile" ResourceKey="Profile">
        @if (profiles != null && settings != null)
        {
        <table class="table table-borderless">
            @foreach (Profile profile in profiles)
            {
                var p = profile;
                if (!p.IsPrivate || UserSecurity.IsAuthorized(PageState.User, RoleNames.Admin))
                {
                    if (p.Category != category)
                    {
                        <tr>
                            <th colspan="2" style="text-align: center;">
                                @p.Category
                            </th>
                        </tr>
                        category = p.Category;
                    }
                    <tr>
                        <td>
                            <Label For="@p.Name" HelpText="@p.Description">@p.Title</Label>
                        </td>
                        <td>
                            @if (!string.IsNullOrEmpty(p.Options))
                            {
                                <select id="@p.Name" class="form-control" @onchange="@(e => ProfileChanged(e, p.Name))">
                                    @foreach (var option in p.Options.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries))
                                    {
                                        @if(GetProfileValue(p.Name, "") == option || (GetProfileValue(p.Name, "") == "" && p.DefaultValue == option))
                                        {
                                            <option value="@option" selected>@option</option>
                                        }
                                        else
                                        {
                                            <option value="@option">@option</option>
                                        }
                                    }
                                </select>
                            }
                            else
                            {
                                @if (p.IsRequired)
                                {
                                    <input id="@p.Name" class="form-control" maxlength="@p.MaxLength" value="@GetProfileValue(p.Name, p.DefaultValue)" required @onchange="@(e => ProfileChanged(e, p.Name))" />
                                }
                                else
                                {
                                    <input id="@p.Name" class="form-control" maxlength="@p.MaxLength" value="@GetProfileValue(p.Name, p.DefaultValue)" @onchange="@(e => ProfileChanged(e, p.Name))" />
                                }
                            }
                        </td>
                    </tr>
                }
            }
        </table>
            <button type="button" class="btn btn-primary" @onclick="Save">@Localizer["Save"]</button>
            <button type="button" class="btn btn-secondary" @onclick="Cancel">@Localizer["Cancel"]</button>
        }
    </TabPanel>
    <TabPanel Name="Notifications" ResourceKey="Notifications">
        @if (notifications != null)
        {
            <ActionLink Action="Add" Text="Send Notification" Security="SecurityAccessLevel.View" EditMode="false" ResourceKey="SendNotification" />
            <br /><br />
            @if (filter == "to")
            {
                <Pager Items="@notifications">
                    <Header>
                        <th style="width: 1px;">&nbsp;</th>
                        <th style="width: 1px;">&nbsp;</th>
                        <th>@Localizer["From"]</th>
                        <th>@Localizer["Subject"]</th>
                        <th>@Localizer["Received"]</th>
                    </Header>
                    <Row>
                        <td><ActionLink Action="View" Parameters="@($"id=" + context.NotificationId.ToString())" Security="SecurityAccessLevel.View" EditMode="false" ResourceKey="ViewNotification" /></td>
                        <td><ActionDialog Header="Delete Notification" Message="Are You Sure You Wish To Delete This Notification?" Action="Delete" Security="SecurityAccessLevel.View" Class="btn btn-danger" OnClick="@(async () => await Delete(context))" EditMode="false" ResourceKey="DeleteNotification" /></td>
                        <td>@context.FromDisplayName</td>
                        <td>@context.Subject</td>
                        <td>@context.CreatedOn</td>
                    </Row>
                    <Detail>
                        <td colspan="2"></td>
                        <td colspan="3">
                            @{ 
                            string input = "___";
                            if (context.Body.Contains(input)){ 
                            context.Body = context.Body.Split(input)[0];
                            context.Body = context.Body.Replace("\n", "");
                            context.Body = context.Body.Replace("\r", "");
                            } }
                            @(context.Body.Length > 100 ? (context.Body.Substring(0, 97) + "...") : context.Body)
                        </td>
                    </Detail>
                </Pager>
            }
            else
            {
                <Pager Items="@notifications">
                    <Header>
                        <th>&nbsp;</th>
                        <th>&nbsp;</th>
                        <th>@Localizer["To"]</th>
                        <th>@Localizer["Subject"]</th>
                        <th>@Localizer["Sent"]</th>
                    </Header>
                    <Row>
                        <td><ActionLink Action="View" Parameters="@($"id=" + context.NotificationId.ToString())" Security="SecurityAccessLevel.View" EditMode="false" ResourceKey="ViewNotification" /></td>
                        <td><ActionDialog Header="Delete Notification" Message="Are You Sure You Wish To Delete This Notification?" Action="Delete" Security="SecurityAccessLevel.View" Class="btn btn-danger" OnClick="@(async () => await Delete(context))" EditMode="false" ResourceKey="DeleteNotification" /></td>
                        <td>@context.ToDisplayName</td>
                        <td>@context.Subject</td>
                        <td>@context.CreatedOn</td>
                    </Row>
                    <Detail>
                        <td colspan="2"></td>
                        <td colspan="3">
                            @{ 
                            string input = "___";
                            if (context.Body.Contains(input)){ 
                            context.Body = context.Body.Split(input)[0];
                            context.Body = context.Body.Replace("\n", "");
                            context.Body = context.Body.Replace("\r", "");
                            } }
                            @(context.Body.Length > 100 ? (context.Body.Substring(0, 97) + "...") : context.Body)
                        </td>
                    </Detail>
                </Pager>
            }
            <br /><hr />
            <select class="form-control" @onchange="(e => FilterChanged(e))">
                <option value="to">@Localizer["Inbox"]</option>
                <option value="from">@Localizer["Sent Items"]</option>
            </select>
        }
    </TabPanel>
</TabStrip>

@code {
    private string username = string.Empty;
    private string password = string.Empty;
    private string confirm = string.Empty;
    private string email = string.Empty;
    private string displayname = string.Empty;
    private FileManager filemanager;
    private int photofileid = -1;
    private List<Profile> profiles;
    private Dictionary<string, string> settings;
    private string category = string.Empty;
    private string filter = "to";
    private List<Notification> notifications;

    public override SecurityAccessLevel SecurityAccessLevel => SecurityAccessLevel.View;

    protected override async Task OnInitializedAsync()
    {
        try
        {
            if (PageState.User != null)
            {
                username = PageState.User.Username;
                email = PageState.User.Email;
                displayname = PageState.User.DisplayName;

                if (PageState.User.PhotoFileId != null)
                {
                    photofileid = PageState.User.PhotoFileId.Value;
                }

                profiles = await ProfileService.GetProfilesAsync(ModuleState.SiteId);
                settings = await SettingService.GetUserSettingsAsync(PageState.User.UserId);

                await LoadNotificationsAsync();
            }
            else
            {
                AddModuleMessage(Localizer["Current User Is Not Logged In"], MessageType.Warning);
            }
        }
        catch (Exception ex)
        {
            await logger.LogError(ex, "Error Loading User Profile {Error}", ex.Message);
            AddModuleMessage(Localizer["Error Loading User Profile"], MessageType.Error);
        }
    }

    private async Task LoadNotificationsAsync()
    {
        notifications = await NotificationService.GetNotificationsAsync(PageState.Site.SiteId, filter, PageState.User.UserId);
        notifications = notifications.Where(item => item.DeletedBy != PageState.User.Username).ToList();
    }

    private string GetProfileValue(string SettingName, string DefaultValue)
        => SettingService.GetSetting(settings, SettingName, DefaultValue);

    private async Task Save()
    {
        try
        {
            if (username != string.Empty && email != string.Empty && ValidateProfiles())
            {
                if (password == confirm)
                {
                    var user = PageState.User;
                    user.Username = username;
                    user.Password = password;
                    user.Email = email;
                    user.DisplayName = (displayname == string.Empty ? username : displayname);
                    user.PhotoFileId = null;
                    photofileid = filemanager.GetFileId();

                    if (photofileid != -1)
                    {
                        user.PhotoFileId = photofileid;
                    }

                    await UserService.UpdateUserAsync(user);
                    await SettingService.UpdateUserSettingsAsync(settings, PageState.User.UserId);
                    await logger.LogInformation("User Profile Saved");
                    AddModuleMessage(Localizer["User Profile Updated Successfully"], MessageType.Success);
                }
                else
                {
                    AddModuleMessage(Localizer["Passwords Entered Do Not Match"], MessageType.Warning);
                }
            }
            else
            {
                AddModuleMessage(Localizer["You Must Provide A Username and Email Address As Well As All Required Profile Information"], MessageType.Warning);
            }
        }
        catch (Exception ex)
        {
            await logger.LogError(ex, "Error Saving User Profile {Error}", ex.Message);
            AddModuleMessage(Localizer["Error Saving User Profile"], MessageType.Error);
        }
    }

    private bool ValidateProfiles()
    {
        bool valid = true;
        foreach (Profile profile in profiles)
        {
            if (string.IsNullOrEmpty(SettingService.GetSetting(settings, profile.Name, string.Empty)) && !string.IsNullOrEmpty(profile.DefaultValue))
            {
                settings = SettingService.SetSetting(settings, profile.Name, profile.DefaultValue);
            }
            if (!profile.IsPrivate || UserSecurity.IsAuthorized(PageState.User, RoleNames.Admin))
            {
                if (profile.IsRequired && string.IsNullOrEmpty(SettingService.GetSetting(settings, profile.Name, string.Empty)))
                {
                    valid = false;
                }
            }
        }
        return valid;
    }

    private void Cancel()
    {
        NavigationManager.NavigateTo(NavigateUrl(string.Empty));
    }

    private void ProfileChanged(ChangeEventArgs e, string SettingName)
    {
        var value = (string)e.Value;
        settings = SettingService.SetSetting(settings, SettingName, value);
    }

    private async Task Delete(Notification Notification)
    {
        try
        {
            if (!Notification.IsDeleted)
            {
                Notification.IsDeleted = true;
                await NotificationService.UpdateNotificationAsync(Notification);
            }
            else
            {
                await NotificationService.DeleteNotificationAsync(Notification.NotificationId);
            }

            await logger.LogInformation("Notification Deleted {Notification}", Notification);
            await LoadNotificationsAsync();
            StateHasChanged();
        }
        catch (Exception ex)
        {
            await logger.LogError(ex, "Error Deleting Notification {Notification} {Error}", Notification, ex.Message);
            AddModuleMessage(ex.Message, MessageType.Error);
        }
    }

    private async void FilterChanged(ChangeEventArgs e)
    {
        filter = (string)e.Value;

        await LoadNotificationsAsync();
        StateHasChanged();
    }

}
