Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(plugin-meetings): add retry mechanism to fetching clusters #3813

30 changes: 27 additions & 3 deletions packages/@webex/plugin-meetings/src/reachability/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -114,6 +114,32 @@ export default class Reachability extends EventsScope {
this.clusterReachability = {};
}

/**
* Fetches the list of media clusters from the backend
* @param {boolean} isRetry
* @private
* @returns {Promise<{clusters: ClusterList, joinCookie: any}>}
*/
async getClusters(isRetry = false): Promise<{clusters: ClusterList; joinCookie: any}> {
try {
const {clusters, joinCookie} = await this.reachabilityRequest.getClusters(
MeetingUtil.getIpVersion(this.webex)
);

return {clusters, joinCookie};
} catch (error) {
if (isRetry) {
throw new Error('Failed to get clusters list');
k-wasniowski marked this conversation as resolved.
Show resolved Hide resolved
}

LoggerProxy.logger.error(
`Reachability:index#getClusters --> Failed with error: ${error}, retrying...`
);

return this.getClusters(true);
}
}

/**
* Gets a list of media clusters from the backend and performs reachability checks on all the clusters
* @returns {Promise<ReachabilityResults>} reachability results
Expand All @@ -123,9 +149,7 @@ export default class Reachability extends EventsScope {
public async gatherReachability(): Promise<ReachabilityResults> {
// Fetch clusters and measure latency
try {
const {clusters, joinCookie} = await this.reachabilityRequest.getClusters(
MeetingUtil.getIpVersion(this.webex)
);
const {clusters, joinCookie} = await this.getClusters();

// @ts-ignore
await this.webex.boundedStorage.put(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import Reachability, {
ReachabilityResults,
ReachabilityResultsForBackend,
} from '@webex/plugin-meetings/src/reachability/';
import { ClusterNode } from '../../../../src/reachability/request';
import {ClusterNode} from '../../../../src/reachability/request';
import MeetingUtil from '@webex/plugin-meetings/src/meeting/util';
import * as ClusterReachabilityModule from '@webex/plugin-meetings/src/reachability/clusterReachability';
import Metrics from '@webex/plugin-meetings/src/metrics';
Expand Down Expand Up @@ -145,7 +145,6 @@ describe('isAnyPublicClusterReachable', () => {
});
});


describe('isWebexMediaBackendUnreachable', () => {
let webex;

Expand Down Expand Up @@ -1466,6 +1465,70 @@ describe('gatherReachability', () => {
xtls: [], // empty list because TLS is disabled in config
});
});

it('retry of getClusters is succesfull', async () => {
webex.config.meetings.experimental = {
enableTcpReachability: true,
enableTlsReachability: false,
};

const getClustersResult = {
clusters: {
'cluster name': {
udp: ['testUDP1', 'testUDP2'],
tcp: ['testTCP1', 'testTCP2'],
xtls: ['testXTLS1', 'testXTLS2'],
isVideoMesh: false,
},
},
joinCookie: {id: 'id'},
};

const reachability = new Reachability(webex);

let getClustersCallCount = 0;

reachability.reachabilityRequest.getClusters = sinon.stub().callsFake(() => {
getClustersCallCount++;

if (getClustersCallCount == 1) {
throw new Error('fake error');
}

return getClustersResult;
});

const promise = reachability.gatherReachability();

await simulateTimeout();
await promise;

assert.equal(getClustersCallCount, 2);

assert.calledOnce(clusterReachabilityCtorStub);
});

it('two failed calls to getClusters', async () => {
const reachability = new Reachability(webex);

let getClustersCallCount = 0;

reachability.reachabilityRequest.getClusters = sinon.stub().callsFake(() => {
getClustersCallCount++;

throw new Error('fake error');
});

const promise = reachability.gatherReachability();

await simulateTimeout();

await promise;

assert.equal(getClustersCallCount, 2);

assert.neverCalledWith(clusterReachabilityCtorStub);
});
});

describe('getReachabilityResults', () => {
Expand Down
Loading