namespace Hims.Domain.Services
{
    using System.Collections.Generic;
    using System.Threading.Tasks;

    using Hims.Domain.Entities;
    using Hims.Shared.EntityModels;
    using Hims.Shared.UserModels;
    using Hims.Shared.UserModels.Telemedicine;


    /// <summary>
    /// The Web Telemedicine Service interface.
    /// </summary>
    public interface IWebTelemedicineService
    {
        /// <summary>
        /// Calls the log asynchronous.
        /// </summary>
        /// <param name="callLog">The call log.</param>
        /// <returns></returns>
        Task<int> CallLogAsync(CallLog callLog);

        /// <summary>
        /// Initiates the patient call intimate asynchronous.
        /// </summary>
        /// <param name="telemedicineCallId">The telemedicine call identifier.</param>
        /// <param name="receiverId">The receiver identifier.</param>
        /// <param name="callerId">The caller identifier.</param>
        /// <returns></returns>
        Task<int> InitiatePatientCallIntimateAsync(int telemedicineCallId, int receiverId, int callerId);

        /// <summary>
        /// Gets the template asynchronous.
        /// </summary>
        /// <param name="templateId">The template identifier.</param>
        /// <returns></returns>
        Task<string> GetTemplateAsync(int templateId);

        /// <summary>
        /// Sets the template asynchronous.
        /// </summary>
        /// <param name="telemedicineCallId">The telemedicine call identifier.</param>
        /// <param name="templateId">The template identifier.</param>
        /// <param name="accountId">The account identifier.</param>
        /// <returns></returns>
        Task<string> SetTemplateAsync(int telemedicineCallId, int templateId, int accountId);

        /// <summary>
        /// Gets all templates.
        /// </summary>
        /// <returns></returns>
        Task<List<TelemedicineTemplateModel>> GetAllTemplates();

        /// <summary>
        /// Initializes the call asynchronous.
        /// </summary>
        /// <param name="telemedicineCallId">The telemedicine call identifier.</param>
        /// <param name="callerId">The caller identifier.</param>
        /// <returns></returns>
        Task<int> InitializeCallAsync(int telemedicineCallId, int callerId);

        /// <summary>
        /// The call close all async.
        /// </summary>
        /// <param name="telemedicineCallId">
        /// The telemedicine call id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> CallCloseAllAsync(int telemedicineCallId);

        /// <summary>
        /// The call cancel async.
        /// </summary>
        /// <param name="telemedicineCallId">
        /// The telemedicine call id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> CallCancelAsync(int telemedicineCallId);

        /// <summary>
        /// The others call close async.
        /// </summary>
        /// <param name="telemedicineCallId">
        /// The telemedicine call id.
        /// </param>
        /// <param name="receiverId">
        /// The receiver id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> OthersCallCloseAsync(int telemedicineCallId, int receiverId);

        /// <summary>
        /// Doctors the call close asynchronous.
        /// </summary>
        /// <param name="telemedicineCallId">The telemedicine call identifier.</param>
        /// <param name="accountId">The account identifier.</param>
        /// <returns></returns>
        Task<int> DoctorCallCloseAsync(int telemedicineCallId, int accountId);

        /// <summary>
        /// The patient call intimate async.
        /// </summary>
        /// <param name="telemedicineCallId">
        /// The telemedicine call id.
        /// </param>
        /// <param name="receiverId">
        /// The receiver id.
        /// </param>
        /// <param name="callerId">
        /// The caller id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> PatientCallIntimateAsync(int telemedicineCallId, int receiverId, int callerId);

        /// <summary>
        /// The get join device tokens async.
        /// </summary>
        /// <param name="telemedicineCallId">
        /// The telemedicine call id.
        /// </param>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetJoinDeviceTokensAsync(int telemedicineCallId, int accountId);

        /// <summary>
        /// The get join device tokens async.
        /// </summary>
        /// <param name="referenceId">
        /// The reference id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetProviderDeviceTokensAsync(int referenceId);

        /// <summary>
        /// The get join device tokens async.
        /// </summary>
        /// <param name="referenceIds">
        /// The reference ids.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetAssistantsDeviceTokensAsync(string referenceIds);

        /// <summary>
        /// The get users async.
        /// </summary>
        /// <param name="providerId">
        /// The provider id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<int>> GetAssistantIdsAsync(int providerId);

        /// <summary>
        /// The get patient ios device tokens.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetPatientIosDeviceTokens(string appointmentNo);

        /// <summary>
        /// The create telemedicine async.
        /// </summary>
        /// <param name="appointmentId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> CreateAsync(int appointmentId);

        /// <summary>
        /// The get telemedicine status async.
        /// </summary>
        /// <param name="telemedicineId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> GetStatusAsync(int telemedicineId);

        /// <summary>
        /// The get telemedicine async.
        /// </summary>
        /// <param name="telemedicineId">
        /// The telemedicine id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<WebTelemedicineModel> GetAsync(int telemedicineId);

        /// <summary>
        /// The update count async.
        /// </summary>
        /// <param name="telemedicineId">
        /// The telemedicine id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> UpdateCountAsync(int telemedicineId);

        /// <summary>
        /// The update status async.
        /// </summary>
        /// <param name="telemedicineId">
        /// The telemedicine id.
        /// </param>
        /// <param name="status">
        /// The status.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> UpdateStatusAsync(int telemedicineId, int status);

        /// <summary>
        /// The get patient appointments.
        /// </summary>
        /// <param name="patientId">
        /// The patient id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<string>> FetchPatientAppointmentsAsync(int patientId);

        /// <summary>
        /// The get patient appointments.
        /// </summary>
        /// <param name="providerId">
        /// The patient id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<string>> FetchProviderAppointmentsAsync(int? providerId, int? practiceId);

        /// <summary>
        /// The get room names.
        /// </summary>
        /// <param name="appointmentIds">
        /// The appointment ids.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<RoomDetails>> FetchRoomNamesAsync(List<int> appointmentIds);

        /// <summary>
        /// The get nurse or receptionist device tokens.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <param name="roleId">
        /// The role id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetNurseOrReceptionistDeviceTokens(string appointmentNo, int roleId);

        /// <summary>
        /// The get doctor device tokens.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetDoctorDeviceTokens(string appointmentNo);

        /// <summary>
        /// The get patient device tokens.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetPatientDeviceTokens(string appointmentNo);

        /// <summary>
        /// The get nurses or receptionists.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<TelemedicineUserModel>> GetNursesOrReceptionists(string appointmentNo);

        /// <summary>
        /// The get nurse or receptionist device tokens alt.
        /// </summary>
        /// <param name="roleId">
        /// The role id.
        /// </param>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetNurseOrReceptionistDeviceTokensAlt(int roleId, int accountId);

        /// <summary>
        /// The get appointment details.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<TelemedicineAppointmentModel> GetAppointmentDetails(string appointmentNo);

        /// <summary>
        /// The get device tokens by account.
        /// </summary>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetDeviceTokensByAccount(int accountId);

        /// <summary>
        /// The get user account.
        /// </summary>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<TelemedicineUserModel> GetUserAccount(int accountId);

        /// <summary>
        /// The get room name.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<string> GetRoomName(string appointmentNo);

        /// <summary>
        /// The get device tokens by account ids.
        /// </summary>
        /// <param name="accountIds">
        /// The account ids.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetDeviceTokensByAccountIds(List<int> accountIds);

        /// <summary>
        /// The create telemedicine history.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <param name="callType">
        /// The call Type.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> CreateTelemedicineHistory(string appointmentNo, int accountId, int callType);

        /// <summary>
        /// The call join async.
        /// </summary>
        /// <param name="telemedicineId">
        /// The telemedicine id.
        /// </param>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> CallJoinAsync(int telemedicineId, int accountId);

        /// <summary>
        /// The call close all async.
        /// </summary>
        /// <param name="telemedicineCallId">
        /// The telemedicine call id.
        /// </param>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> CallCloseAllAsync(int telemedicineCallId, int accountId);

        /// <summary>
        /// The get patient account id.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> GetPatientAccountId(string appointmentNo);

        /// <summary>
        /// The get doctor account id.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> GetDoctorAccountId(string appointmentNo);

        /// <summary>
        /// The get call close all device tokens async.
        /// </summary>
        /// <param name="telemedicineCallId">
        /// The telemedicine call id.
        /// </param>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<AccountSessionModel>> GetCallCloseAllDeviceTokensAsync(int telemedicineCallId, int accountId);

        /// <summary>
        /// The call reject async.
        /// </summary>
        /// <param name="telemedicineCallId">
        /// The telemedicine call id.
        /// </param>
        /// <param name="accountId">
        /// The account id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> CallRejectAsync(int telemedicineCallId, int accountId);

        /// <summary>
        /// The get no of calls.
        /// </summary>
        /// <param name="appointmentId">
        /// The appointment id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<int>> GetNoOfCalls(int appointmentId);

        /// <summary>
        /// The get call history.
        /// </summary>
        /// <param name="appointmentId">
        /// The appointment id.
        /// </param>
        /// <param name="telemedicineCallHistoryId">
        /// The telemedicine call history id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<IEnumerable<CallHistoryModel>> GetCallHistory(int appointmentId, int telemedicineCallHistoryId);

        /// <summary>
        /// The get telemedicine id.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <param name="receiverId">
        /// The receiver id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> GetReceiverTelemedicineId(string appointmentNo, int receiverId);

        /// <summary>
        /// The get telemedicine id.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <param name="receiverId">
        /// The receiver id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<TelemedicineCallHistory> GetTelemedicineCallHistory(string appointmentNo, int receiverId);

        /// <summary>
        /// The get telemedicine id.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <param name="callerId">
        /// The receiver id.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<int> GetCallerTelemedicineId(string appointmentNo, int callerId);

        /// <summary>
        /// The get active domain.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<TelemedicineDomainModel> GetActiveDomain(string appointmentNo);

        /// <summary>
        /// The get active room name.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<StatusResponse> GetActiveRoomName(string appointmentNo);

        /// <summary>
        /// The get patient details.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<BasicPatientDetailsModel> GetPatientDetails(string appointmentNo);

        /// <summary>
        /// The get provider details.
        /// </summary>
        /// <param name="appointmentNo">
        /// The appointment no.
        /// </param>
        /// <returns>
        /// The <see cref="Task"/>.
        /// </returns>
        Task<BasicPatientDetailsModel> GetProviderDetails(string appointmentNo);
    }
}