NTP-27557 | Agent transfer handling

This commit is contained in:
vivek bhadola
2025-01-22 14:44:40 +05:30
parent 4b60c2f164
commit 3358f262d7
8 changed files with 80 additions and 73 deletions

View File

@@ -1,4 +1,4 @@
import getResponse from "@universal-call-sdk/common/lib/utils/getResponse.ts";
import apiHelper from "@universal-call-sdk/common/lib/utils/apiHelper.ts";
import {CallTransferData, RequestKeys} from "./types";
import { RequestType } from "@universal-call-sdk/common/lib/types/Request.ts";
import {v4 as uuid} from 'uuid';
@@ -9,7 +9,7 @@ export const loginInAmeyo = (userId: string, password: string) => {
if(!userId || !password) {
return
}
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/userLogin/login`,
method: 'POST',
requestKey: RequestKeys.AMEYO_LOGIN,
@@ -30,7 +30,7 @@ export const loginInAmeyo = (userId: string, password: string) => {
};
export const maintainHeartbeat = (sessionId: string, webcoreTimestamp: string, counter: number) => {
const HEART_BEAT_REQUEST_TEXT = `7|0|8|${window.BASE_AMEYO_URL}/app/application_ui/|93B024BCBAF3AE5EFEC49890FE64CF5F|com.drishti.ameyo.common.ui.rpc.CommonGwtRpcService|keepAliveWithPingPush|java.lang.String/2004016611|java.lang.Integer/3438268394|${sessionId}|${webcoreTimestamp}|1|2|3|4|3|5|5|6|7|8|6|${counter}|${sessionId}|`;
setInterval(() => getResponse({
setInterval(() => apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyo40/service`,
method: 'POST',
requestKey: RequestKeys.AMEYO_HEARTBEAT,
@@ -44,7 +44,7 @@ export const maintainHeartbeat = (sessionId: string, webcoreTimestamp: string, c
};
export const setAgentOnBreak = (sessionId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/cc/userBreak`,
method: 'POST',
requestKey: RequestKeys.AMEYO_ON_BREAK,
@@ -62,7 +62,7 @@ export const setAgentOnBreak = (sessionId: string) => {
export const attachOmniqueService = (sessionId: string, userId: string, campaignId: string) => {
const OMNIQUEUE_TEXT = `7|0|9|${window.BASE_AMEYO_URL}/app/application_ui/|5B1786BFF89E87DC6EAAACDE629A89E2|com.drishti.ameyo.omniqueue.shared.CommonGwtRpcService|selectCamapign|java.lang.String/2004016611|[Ljava.lang.Integer;/1574882222|${sessionId}|${userId}|java.lang.Integer/3438268394|1|2|3|4|3|5|5|6|7|8|6|1|9|${campaignId}|${sessionId}|`;
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyoomniqueue/service`,
method: 'POST',
requestKey: RequestKeys.OMNIQUEUE_SERVICE,
@@ -76,7 +76,7 @@ export const attachOmniqueService = (sessionId: string, userId: string, campaign
};
export const setAgentActive = (sessionId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/cc/userReady`,
method: 'POST',
requestKey: RequestKeys.AMEYO_AVAILABLE,
@@ -92,7 +92,7 @@ export const setAgentActive = (sessionId: string) => {
};
export const getSipAccountInfo = (sessionId: string, userId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/voice/sipAccountInfos/getSipAccountInfo?info=false`,
method: 'GET',
requestKey: RequestKeys.SIP_ACCOUNT_INFO,
@@ -106,7 +106,7 @@ export const getSipAccountInfo = (sessionId: string, userId: string) => {
};
export const autoSelectExtension = (sessionId: string, userId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/voice/autoSelectExtension`,
method: 'POST',
requestKey: RequestKeys.AUTO_SELECT_EXTENSION,
@@ -123,7 +123,7 @@ export const autoSelectExtension = (sessionId: string, userId: string) => {
export const selectCampaign = (sessionId: string, userId: string, campaignId: string) => {
const SELECT_CAMPAIGN_TEXT = `7|0|9|${window.BASE_AMEYO_URL}/app/application_ui/|5B1786BFF89E87DC6EAAACDE629A89E2|com.drishti.ameyo.omniqueue.shared.CommonGwtRpcService|selectCamapign|java.lang.String/2004016611|[Ljava.lang.Integer;/1574882222|${sessionId}|${userId}|java.lang.Integer/3438268394|1|2|3|4|3|5|5|6|7|8|6|1|9|${campaignId}|${sessionId}|`;
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyoomniqueue/service`,
method: 'POST',
requestKey: RequestKeys.SELECT_CAMPAIGN,
@@ -137,7 +137,7 @@ export const selectCampaign = (sessionId: string, userId: string, campaignId: st
};
export const setAutoStatus = (sessionId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/cc/setAutoStatusForUser`,
method: 'POST',
requestKey: RequestKeys.SET_AUTO_STATUS,
@@ -150,7 +150,7 @@ export const setAutoStatus = (sessionId: string) => {
};
export const ameyoHangupUser = (sessionId: string, userCRTObjectId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/voice/hangupUser`,
method: 'POST',
requestKey: RequestKeys.HANGUP_USER,
@@ -163,7 +163,7 @@ export const ameyoHangupUser = (sessionId: string, userCRTObjectId: string) => {
};
export const ameyoDisposeCall = (sessionId: string, campaignId: string, crtObjectId: string, userCRTObjectId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/voice/disposeCall`,
method: 'POST',
requestKey: RequestKeys.DISPOSE_CALL,
@@ -185,7 +185,7 @@ export const ameyoDisposeCall = (sessionId: string, campaignId: string, crtObjec
};
export const getCampaignId = (sessionId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/sessionData/getAllSessionData`,
method: 'GET',
requestKey: RequestKeys.GET_CAMPAIGN_ID,
@@ -198,7 +198,7 @@ export const getCampaignId = (sessionId: string) => {
}
export const getAllAgentsForTransferCall = (sessionId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/voice/getAllUserCampaignVoicePresencesByContactCenterId`,
method: 'GET',
requestKey: RequestKeys.GET_AGENTS_FOR_CALL_TRANSFER,
@@ -212,7 +212,7 @@ export const getAllAgentsForTransferCall = (sessionId: string) => {
export const logoutFromAmeyo = (sessionId: string) => {
const LOGOUT_PAYLOAD_TEXT = `7|0|7|${window.BASE_AMEYO_URL}/app/application_ui/|C066834E4747CF348FD8D1A68865C24D|com.drishti.ameyo.common.ui.rpc.CommonGwtRpcService|doLogout|java.lang.String/2004016611|${sessionId}|Logout from UI|1|2|3|4|2|5|5|6|7|${sessionId}|`;
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyo40/service`,
method: 'POST',
requestKey: RequestKeys.LOGOUT_FROM_AMEYO,
@@ -227,7 +227,7 @@ export const logoutFromAmeyo = (sessionId: string) => {
export const transferCallToAgent = (data: CallTransferData, sessionId: string, crtObjectId: string, userCRTObjectId: string, campaignId: string) => {
return getResponse({
return apiHelper({
url: `${window.BASE_AMEYO_URL}/ameyorestapi/voice/transferToUserInDifferentCampaign`,
method: 'POST',
requestKey: RequestKeys.TRANSFER_CALL_TO_AGENT,

View File

@@ -85,8 +85,6 @@ class AmeyoAdapter implements IAdapter {
},
onLoginFailed: () => {
},
onAgentsForCallTransfer: () => {
},
onCallTransferStatus: () => {
}
};
@@ -304,10 +302,6 @@ class AmeyoAdapter implements IAdapter {
window.postMessage({type: 'onAmeyoAvailabiltyChange', data: this.isAgentAvailable,});
}
private handleAgentsForTransfer = (payload: GenericObject): void => {
this.callbacks.onAgentsForCallTransfer(payload?.data?.response);
}
private handleCallIncoming(data: GenericObject): void {
this.callbacks.onCallIncoming(data?.data);
this.currentCallState = CALL_STATES.CALL_INCOMING;
@@ -378,9 +372,8 @@ class AmeyoAdapter implements IAdapter {
return this.currentCallState;
}
public async getAvailableAgentsForCallTransfer(): Promise<void> {
const res = await getAllAgentsForTransferCall(this.sessionId);
this.handleApiResponse(res,this.handleAgentsForTransfer);
public async getAvailableAgentsForCallTransfer(): Promise<Response> {
return getAllAgentsForTransferCall(this.sessionId);
}
public transferCallToAgent(data: CallTransferData): void {
@@ -421,11 +414,6 @@ class AmeyoAdapter implements IAdapter {
public registerOnLoginFailedListener(callback: () => void): void {
this.callbacks.onLoginFailed = callback;
}
public registerOnAgentsForCallTransfer(callback: (data: GenericObject) => void): void {
this.callbacks.onAgentsForCallTransfer = callback;
}
public registerOnCallTransferStatus(callback: (data: GenericObject) => void): void {
this.callbacks.onCallTransferStatus = callback;
}

View File

@@ -73,7 +73,6 @@ export type CallbackFunctions = {
onAgentAvailabilityChange: (isAgentAvailable: boolean, reason: string) => void;
onForcedLogout: () => void;
onLoginFailed: (err: GenericObject) => void;
onAgentsForCallTransfer: (data: GenericObject) => void;
onCallTransferStatus: (data: GenericObject) => void;
};

View File

@@ -11,7 +11,6 @@ class IAdapter {
registerOnAgentAvailabilityChange(callback: (isAgentAvailable: boolean, reason: string) => void) {callback(false, '')}
registerOnForcedLogoutListener(callback:()=>void) {callback()}
registerOnLoginFailedListener(callback:()=>void) {callback()}
registerOnAgentsForCallTransfer(callback: (data : GenericObject) => void) {callback({})}
registerOnCallTransferStatus(callback: (data: GenericObject) => void) {callback({})}
acceptCall() {}
rejectCall() {}
@@ -30,7 +29,9 @@ class IAdapter {
getAgentAvailability(): boolean {return false}
getLatestCallState(): CALL_STATES {return CALL_STATES.IDLE}
getAvailableAgentsForCallTransfer() {}
getAvailableAgentsForCallTransfer(): Promise<any> {
return Promise.resolve(new Response());
}
transferCallToAgent(data: GenericObject) {console.log("transfer call", data)}
}

View File

@@ -1,8 +1,10 @@
import { RequestKeys } from "@universal-call-sdk/adapter-ameyo/lib/types";
export type Request = {
url: string;
method: string;
data ?:Record<string, any> | string;
requestKey: string;
requestKey: RequestKeys;
requestType ?: RequestType;
headers ?: Record<string, any> | null;
}

View File

@@ -1,13 +1,18 @@
import { RequestKeys } from "@universal-call-sdk/adapter-ameyo/lib/types";
import { METHODS, Request, RequestType } from "../types/Request";
const getFetchResponse = async (
const handleError = (context: string, error: unknown): void => {
console.error(`[${context}]`, error);
};
const getFetchResponse = async(
url: string,
method: string,
data: any,
requestType: RequestType,
headers: any
) => {
const fetchOptions = {
headers: Record<string, string>
): Promise<any> => {
const fetchOptions: RequestInit = {
method,
headers: {
"Content-Type":
@@ -16,44 +21,51 @@ const getFetchResponse = async (
},
...(method !== METHODS.GET && { body: data }),
};
try {
const res = await fetch(url, fetchOptions);
if (!res.ok) {
return { error: res };
throw new Error(`HTTP error! Status: ${res.status} ${res.statusText}`);
}
const contentType = res.headers.get("Content-Type") || "";
if (
requestType === RequestType.JSON &&
contentType.includes("application/json")
) {
if (contentType.includes("application/json")) {
return await res.json();
} else if (
contentType.includes("text/plain") &&
requestType == RequestType.RAW
) {
} else if (contentType.includes("text/plain")) {
return await res.text();
} else {
throw new Error(`Unsupported Content-Type: ${contentType}`);
}
} catch (err) {
console.error("Response is not a valid JSON or text", err);
return { error: "Failed to parse response" };
handleError("Fetch error:", err);
return null;
}
};
export const getResponse = async ({
export const apiHelper = async({
url,
method,
requestKey,
requestType = RequestType.JSON,
headers = null,
headers = {},
data = {},
}: Request) => {
const requestPayload =
requestType === RequestType.RAW ? data : JSON.stringify(data);
try {
if (requestKey === RequestKeys.GET_AGENTS_FOR_CALL_TRANSFER) {
return getFetchResponse(
url,
method,
requestPayload,
requestType,
headers || {}
);
}
const response = await getFetchResponse(
url,
method,
@@ -61,25 +73,17 @@ export const getResponse = async ({
requestType,
headers || {}
);
if (response?.error) {
console.error(response.error);
return {
data: {
requestKey: requestKey,
response: response,
},
};
}
return {
data: {
requestKey: requestKey,
response: response,
requestKey,
response,
},
};
} catch (error) {
console.error("Fetch error:", error);
throw error;
handleError("Response error:", error);
return null;
}
};
export default getResponse;
export default apiHelper;

View File

@@ -8,4 +8,22 @@ export type StateType = {
isCallConnected: boolean,
isCallDisconnected: boolean,
callStartTime: number,
}
interface Campaign {
campaignId: number;
campaignName: string;
campaignType: string;
}
export interface Agent {
userId: string;
userName: string;
userType: string;
sessionId: string;
crtObjectId: string;
isOnBreak: boolean;
isOnAutoCall: boolean;
isPresent: boolean;
statusDescription: string;
campaignList: Campaign[];
}

View File

@@ -1,5 +1,5 @@
import {useEffect, useReducer} from 'react';
import {GenericObject, StateType} from "./types.ts";
import {Agent, GenericObject, StateType} from "./types.ts";
import IAdapter from "@universal-call-sdk/common/lib/Interfaces/IAdapter.ts";
import MetricsProcessor from "@universal-call-sdk/common/lib/utils/metricsProcessor.ts";
import ClickStreamProcessor from "@universal-call-sdk/common/lib/utils/clickStreamProcessor.ts";
@@ -123,10 +123,6 @@ function UseCallSdk({AdapterClass, adapterOptions, metricsConfig, clickStreamCon
adapter?.registerOnForcedLogoutListener(callback);
}
function registerOnAgentsForCallTransfer(callback: (data: GenericObject) => void) {
adapter?.registerOnAgentsForCallTransfer(callback);
}
function registerOnCallTransferStatus(callback: (data: GenericObject) => void) {
adapter?.registerOnCallTransferStatus(callback);
}
@@ -189,8 +185,8 @@ function UseCallSdk({AdapterClass, adapterOptions, metricsConfig, clickStreamCon
return adapter.getLatestCallState();
}
function getAvailableAgentsForCallTransfer() {
adapter.getAvailableAgentsForCallTransfer();
function getAvailableAgentsForCallTransfer(): Promise<Agent[]> {
return adapter.getAvailableAgentsForCallTransfer();
}
function transferCallToAgent(data: GenericObject) {
@@ -204,7 +200,6 @@ function UseCallSdk({AdapterClass, adapterOptions, metricsConfig, clickStreamCon
registerOnCallDisconnected,
registerOnAgentAvailabilityChange,
registerOnForcedLogoutListener,
registerOnAgentsForCallTransfer,
registerOnCallTransferStatus,
registerOnLoginFailedListener,
acceptCall,