Disconnect or reject an incoming call in Genesys

Your media toolbar application listens to different events published from the microservice.

There are three ways to disconnect a call:
  1. From your media toolbar application.
  2. From your Fusion application.
  3. From your soft phone configured for Genesys.

Scenario 1 and 2: Disconnect call from media toolbar and Fusion applications

The following flow diagram shows the sequence of operations performed once an agent disconnects a call from Fusion or from the media toolbar application:

The disconnect call from the media toolbar and Fusion application scenario in Genesys.

  1. An agent can disconnect the call either from the Fusion application or from the media toolbar application.
    • When the agent clicks the Decline button in the Fusion application, the onToolbarInteractionCommand event is fired with command as reject.

      When the agent clicks the End Call button in the Fusion application, the onToolbarInteractionCommand event is fired with command as wrapup.

      When the agent declines the call from media toolbar application, your microservice is notified that the call has been declined.

      When the agent ends the call from media toolbar application, your microservice is notified that the call has ended.

  2. The media toolbar application receives this event, and if the event is to disconnect a call, your microservice is notified to disconnect the call.
  3. When your microservice receives the notification, it should request the Genesys server disconnect the call using the com.genesyslab.platform.voice.protocol.tserver.requests.party.RequestReleaseCall request.
  4. When the RequestReleaseCall request is succeeds, the EventReleased message is propagated from Genesys through your microservice to your media toolbar application.
  5. The media toolbar application receives the EventReleased message through the web socket and fires the closeCommEvent action with reason as reject if call is declined or wrapup if call is ended.
  6. When the Fusion application identifies this action, the call dialog box is discarded from the UI if reason is reject, or the wrap up window displayed in the UI if reason is wrapup.

Agent disconnects the call either from the application Fusion or from the media toolbar application

An agent can disconnect the call either from the Fusion application or from the media toolbar application.

  • When agent clicks the Decline button in the Fusion application, onToolbarInteractionCommand event is fired with command as reject.
  • When agent clicks the End Call button in the Fusion application, the onToolbarInteractionCommand event is fired with the command as wrapup.
  • When an agent declines the call from media toolbar application, the microservice is notified that the call has been declined.
  • When agent ends the call from media toolbar application, the microservice is notified that the call has ended.

Notify your microservice to disconnect the call

When the agent disconnects the call from media toolbar application or from the Fusion application, you need to notify your microservice that the agent disconnected the call. For that, update your rejectCall function in the vendorHandler.ts file as shown in the following example:

public async rejectCall(): Promise<void> {
        const headers: Headers = (new Headers()) as Headers;
        headers.set('Content-type', 'application/json');
        const message: any = {
            "type": "Reject",
            "connectionId": VendorHandler.connectionId
        };
        const request: Request = new Request(`${VendorHandler.REST_ENDPOINT_URL}`, {
            method: 'POST',
            headers: headers,
            body: JSON.stringify(message)
        }) as Request;
        await fetch(request);
    }
 
    public async hangupCall(): Promise<void> {
        const headers: Headers = (new Headers()) as Headers;
        headers.set('Content-type', 'application/json');
        const message: any = {
            "type": "Reject",
            "connectionId": VendorHandler.connectionId
        };
        const request: Request = new Request(`${VendorHandler.REST_ENDPOINT_URL}`, {
            method: 'POST',
            headers: headers,
            body: JSON.stringify(message)
        }) as Request;
        await fetch(request);
    }

Microservice creates request for disconnecting the call

The microservice then uses PSDK to create request the call be disconnected.

Microservice receives EventReleased message

After the request for disconnecting the call succeeds, the Genesys server responds with the withEventReleased message and it will be propagated to your media toolbar application through the microservice.

Call the closeCommEvent from media toolbar application

When the EventReleased message is received through the web socket, the callHangupHandler function is called from the integrationEventsHandler.ts file as shown in the following example:

public webSocketOnMessage(event: MessageEvent): void {
        const jsonMessage = JSON.parse(event.data);
        console.log(jsonMessage);
        if (jsonMessage.eventName === "EventRegistered") {
            // Genesys notifies that the agent is ready
            this.integrationEventsHandler.makeAgentAvailable();
        } else if (jsonMessage.eventName === "EventRinging") {
            // Show incoming call notification
            this.integrationEventsHandler.incomingCallHandler(jsonMessage.ANI, jsonMessage.eventId);
            VendorHandler.connectionId = jsonMessage.connectionId;
        } else if (jsonMessage.eventName === "EventEstablished") {
            // Genesys notifies that the call is accepted
            this.integrationEventsHandler.callAcceptedHandler(jsonMessage.eventId);
        } else if (jsonMessage.eventName === "EventReleased") {
            // Genesys notifies that the call is disconnected
            this.integrationEventsHandler.callHangupHandler(jsonMessage.eventId);
        }
        console.log("Message is received");
    }

Call is disconnected in the Fusion application

Your Fusion application will remove the incoming call notification if the call is declined or it will show the WRAPUPwindow if the call is ended. The media toolbar application UI will be updated to show that the agent is available for calls.

Scenario 3: Disconnect call from softphone

When the agent accepts the call from a softphone, the EventEstablished event sends a notification that the call has been accepted. You can add logic for handling the call accepted scenario in the EventEstablished event as shown in the following diagram. The flow diagram shows the sequence of operations performed once an agent accepts an incoming call from the softphone:

The disconnect from softphone scenario in Genesys.

  1. When an agent disconnects a call from the softphone application, the Genesys server is notified to disconnect the call and once disconnect succeeds, the Genesys server sends the EventReleased message to your microservice and it propagates this message to your media toolbar application through the web socket.
  2. The media toolbar application receives this event, and fires the closeCommEvent action.
  3. After the Fusion application identifies the action, the call dialog box will be discarded from the UI if the reason is reject or the WRAPUP window if the call is ended.

Microservice propagates EventReleased message to your media toolbar application

When the agent disconnects a call from the softphone application, the Genesys server is notified to disconnect the call and after the call is disconnected, the Genesys server sends the EventReleased message to your microservice and it propagates this message to your media toolbar application through the web socket.

Call the closeCommEvent from media toolbar application

When the EventReleased message is received through web socket, callHangupHandler function is started in the integrationEventsHandler.ts file as shown in the following example:

public webSocketOnMessage(event: MessageEvent): void {
        const jsonMessage = JSON.parse(event.data);
        console.log(jsonMessage);
        if (jsonMessage.eventName === "EventRegistered") {
            // Genesys notifies that the agent is ready
            this.integrationEventsHandler.makeAgentAvailable();
        } else if (jsonMessage.eventName === "EventRinging") {
            // Show incoming call notification
            this.integrationEventsHandler.incomingCallHandler(jsonMessage.ANI, jsonMessage.eventId);
            VendorHandler.connectionId = jsonMessage.connectionId;
        } else if (jsonMessage.eventName === "EventEstablished") {
            // Genesys notifies that the call is accepted
            this.integrationEventsHandler.callAcceptedHandler(jsonMessage.eventId);
        } else if (jsonMessage.eventName === "EventReleased") {
            // Genesys notifies that the call is disconnected
            this.integrationEventsHandler.callHangupHandler(jsonMessage.eventId);
        }
        console.log("Message is received");
    }

Call is disconnected in the Fusion application

You Fusion application will remove the incoming call notification if the call is declined or it will show the WRAPUP window if the call is ended. The media toolbar application UI will be updated to show that the agent is available for calls.

Complete code

Here's the complete code for the vendorHandler.ts file for disconnecting a call.

import { ICtiVendorHandler } from './ICtiVendorHandler';
import { IntegrationEventsHandler } from '../integrationEventsHandler';
 
export class VendorHandler implements ICtiVendorHandler {
    public static connectionId: string;
    private static REST_ENDPOINT_URL: string = 'http://localhost:8087/genesys/events';
    private static WS_ENDPOINT_URL: string = 'ws://localhost:8087/genesysWs';
    private integrationEventsHandler: IntegrationEventsHandler;
 
    constructor(integrationEventsHandler: IntegrationEventsHandler) {
        this.integrationEventsHandler = integrationEventsHandler;
    }
 
    public async webSocketOnOpenHandler(): Promise<void> {
        console.log("WebSocket opened");
        const headers: Headers = (new Headers()) as Headers;
        headers.set('Content-type', 'application/json');
        const message: any = {
            "type": "initialize"
        };
        const request: Request = new Request(`${VendorHandler.REST_ENDPOINT_URL}`, {
            method: 'POST',
            headers: headers,
            body: JSON.stringify(message)
        }) as Request;
        await fetch(request);
    }
    public webSocketErrorHandler(error: any): void {
        console.log("WebSocket error", error);
    }
    public webSocketCloseHandler(event: Event): void {
        console.log("WebSocket is closed", event);
    }
 
    public webSocketOnMessage(event: MessageEvent): void {
        const jsonMessage = JSON.parse(event.data);
        console.log(jsonMessage);
        if (jsonMessage.eventName === "EventRegistered") {
            // Genesys notifies that the agent is ready
            this.integrationEventsHandler.makeAgentAvailable();
        } else if (jsonMessage.eventName === "EventRinging") {
            // Show incoming call notification
            this.integrationEventsHandler.incomingCallHandler(jsonMessage.ANI, jsonMessage.eventId);
            VendorHandler.connectionId = jsonMessage.connectionId;
        } else if (jsonMessage.eventName === "EventEstablished") {
            // Genesys notifies that the call is accepted
            this.integrationEventsHandler.callAcceptedHandler(jsonMessage.eventId);
            VendorHandler.connectionId = jsonMessage.connectionId;
        } else if (jsonMessage.eventName === "EventReleased") {
            // Genesys notifies that the call is disconnected
            this.integrationEventsHandler.callHangupHandler(jsonMessage.eventId);
        }
        console.log("Message is received");
    }
    public async makeAgentAvailable(): Promise<void> {
        let webSocket: WebSocket = new WebSocket(`${VendorHandler.WS_ENDPOINT_URL}`);
        webSocket.onopen = this.webSocketOnOpenHandler.bind(this);
        webSocket.onmessage = this.webSocketOnMessage.bind(this);
        webSocket.onclose = this.webSocketCloseHandler.bind(this);
        webSocket.onerror = this.webSocketErrorHandler.bind(this);
    }
 
    public async makeAgentUnavailable(): Promise<void> {
        // TODO: call the vendor specific api to make the agent available
    }
    public async makeOutboundCall(phoneNumber: string, eventId: string): Promise<void> {
        // TODO: call the vendor specific api to make the make an outbound call
    }
    public async acceptCall(): Promise<void> {
        const headers: Headers = (new Headers()) as Headers;
        headers.set('Content-type', 'application/json');
        const message: any = {
            "type": "Accept",
            "connectionId": VendorHandler.connectionId
        };
        const request: Request = new Request(`${VendorHandler.REST_ENDPOINT_URL}`, {
            method: 'POST',
            headers: headers,
            body: JSON.stringify(message)
        }) as Request;
        await fetch(request);
    }
    public async rejectCall(): Promise<void> {
        const headers: Headers = (new Headers()) as Headers;
        headers.set('Content-type', 'application/json');
        const message: any = {
            "type": "Reject",
            "connectionId": VendorHandler.connectionId
        };
        const request: Request = new Request(`${VendorHandler.REST_ENDPOINT_URL}`, {
            method: 'POST',
            headers: headers,
            body: JSON.stringify(message)
        }) as Request;
        await fetch(request);
    }
 
    public async hangupCall(): Promise<void> {
        const headers: Headers = (new Headers()) as Headers;
        headers.set('Content-type', 'application/json');
        const message: any = {
            "type": "Reject",
            "connectionId": VendorHandler.connectionId
        };
        const request: Request = new Request(`${VendorHandler.REST_ENDPOINT_URL}`, {
            method: 'POST',
            headers: headers,
            body: JSON.stringify(message)
        }) as Request;
        await fetch(request);
    }
}

Verify your progress

After finishing these steps, use OJET server to start you application and sign in to your Fusion application. Open the media toolbar and make your agent available for calls by clicking on the Agent Availability button. Then, start a call to your customer care number. You'll receive the incoming call notification in your media toolbar application and in your Fusion application window. You can accept the call from your media toolbar application or from your Fusion application or from your softphone application. Once you accept the call, your media toolbar state will change to the ACCEPTED state and the engagement is opened in your Fusion application. You can disconnect the call from your media toolbar application or from your Fusion application or from the softphone. Once you disconnect the call, your media toolbar state will be changed to the DISCONNECTED state.