using Capnp.Rpc;
using FabAccessAPI.Exceptions;
using FabAccessAPI.Exceptions.SASL;
using Prism.Services;
using Xamarin.Forms;

namespace Borepin.Service.ErrorMessage
{
    public class ErrorMessageService : IErrorMessageService
    {
        #region Private Members
        private IPageDialogService _PageDialogService;
        #endregion

        #region Constructor
        public ErrorMessageService(IPageDialogService pageDialogService)
        {
            _PageDialogService = pageDialogService;
        }
        #endregion

        #region Methods to Display Connection Error

        public void DisplayConnectFailedMessage(System.Exception exception)
        {
            if(exception is ConnectionException)
            {
                DisplayConnectionMessage(exception as ConnectionException);
            }
            else if(exception is AuthenticationException)
            {
                DisplayAuthenticationMessage(exception as AuthenticationException);
            }
            else
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_ConnectionFailed, Resources.Text.TextResource.ALERT_UnexpectedError, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
        }

        public void DisplayAuthenticationMessage(AuthenticationException exception)
        {
            if (exception.InnerException is BadMechanismException)
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_AuthFailed, Resources.Text.TextResource.ALERT_BadMechanism, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
            else if (exception.InnerException is InvalidCredentialsException)
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_AuthFailed, Resources.Text.TextResource.ALERT_CredentialsInvalid, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
            else if (exception.InnerException is AuthenticationFailedException)
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_AuthFailed, Resources.Text.TextResource.ALERT_SASLAuth, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
            else
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_AuthFailed, Resources.Text.TextResource.ALERT_UnexpectedError, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
        }

        public void DisplayConnectionMessage(ConnectionException exception)
        {
            if(exception.InnerException is System.Security.Authentication.AuthenticationException)
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_ConnectionFailed, Resources.Text.TextResource.ALERT_TLSInvalid, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
            else if(exception.InnerException is FabAccessAPI.Exceptions.TimeoutException)
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_ConnectionFailed, Resources.Text.TextResource.ALERT_ConnectionTimeout, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
            else if(exception.InnerException is RpcException)
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_ConnectionFailed, Resources.Text.TextResource.ALERT_UnableServer, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
            else
            {
                Device.BeginInvokeOnMainThread(async () =>
                {
                    await _PageDialogService.DisplayAlertAsync(Resources.Text.TextResource.ALERT_ConnectionFailed, Resources.Text.TextResource.ALERT_UnexpectedError, Resources.Text.TextResource.OK).ConfigureAwait(false);
                });
            }
        }
        #endregion
    }
}
