mirror of
https://github.com/Azure/cosmos-explorer.git
synced 2024-11-25 15:06:55 +00:00
Refactor NotificationsClient (#270)
This commit is contained in:
parent
3b64d75322
commit
cfb9a0b321
@ -1,46 +0,0 @@
|
||||
import "jquery";
|
||||
import * as Q from "q";
|
||||
import * as DataModels from "../Contracts/DataModels";
|
||||
import * as ViewModels from "../Contracts/ViewModels";
|
||||
import { getAuthorizationHeader } from "../Utils/AuthorizationUtils";
|
||||
import { userContext } from "../UserContext";
|
||||
|
||||
export class NotificationsClientBase {
|
||||
private _extensionEndpoint: string;
|
||||
private _notificationsApiSuffix: string;
|
||||
|
||||
protected constructor(notificationsApiSuffix: string) {
|
||||
this._notificationsApiSuffix = notificationsApiSuffix;
|
||||
}
|
||||
|
||||
public fetchNotifications(): Q.Promise<DataModels.Notification[]> {
|
||||
const deferred: Q.Deferred<DataModels.Notification[]> = Q.defer<DataModels.Notification[]>();
|
||||
const databaseAccount = userContext.databaseAccount;
|
||||
const subscriptionId = userContext.subscriptionId;
|
||||
const resourceGroup = userContext.resourceGroup;
|
||||
const url = `${this._extensionEndpoint}${this._notificationsApiSuffix}?accountName=${databaseAccount.name}&subscriptionId=${subscriptionId}&resourceGroup=${resourceGroup}`;
|
||||
const authorizationHeader: ViewModels.AuthorizationTokenHeaderMetadata = getAuthorizationHeader();
|
||||
const headers: any = {};
|
||||
headers[authorizationHeader.header] = authorizationHeader.token;
|
||||
|
||||
$.ajax({
|
||||
url: url,
|
||||
type: "GET",
|
||||
headers: headers,
|
||||
cache: false
|
||||
}).then(
|
||||
(notifications: DataModels.Notification[], textStatus: string, xhr: JQueryXHR<any>) => {
|
||||
deferred.resolve(notifications);
|
||||
},
|
||||
(xhr: JQueryXHR<any>, textStatus: string, error: any) => {
|
||||
deferred.reject(xhr.responseText);
|
||||
}
|
||||
);
|
||||
|
||||
return deferred.promise;
|
||||
}
|
||||
|
||||
public setExtensionEndpoint(extensionEndpoint: string): void {
|
||||
this._extensionEndpoint = extensionEndpoint;
|
||||
}
|
||||
}
|
41
src/Common/PortalNotifications.ts
Normal file
41
src/Common/PortalNotifications.ts
Normal file
@ -0,0 +1,41 @@
|
||||
import * as DataModels from "../Contracts/DataModels";
|
||||
import * as ViewModels from "../Contracts/ViewModels";
|
||||
import { getAuthorizationHeader } from "../Utils/AuthorizationUtils";
|
||||
import { userContext } from "../UserContext";
|
||||
import { configContext, Platform } from "../ConfigContext";
|
||||
|
||||
const notificationsPath = () => {
|
||||
switch (configContext.platform) {
|
||||
case Platform.Hosted:
|
||||
return "/api/guest/notifications";
|
||||
case Platform.Portal:
|
||||
return "/api/notifications";
|
||||
default:
|
||||
throw new Error(`Unknown platform: ${configContext.platform}`);
|
||||
}
|
||||
};
|
||||
|
||||
export const fetchPortalNotifications = async (): Promise<DataModels.Notification[]> => {
|
||||
if (configContext.platform === Platform.Emulator) {
|
||||
return [];
|
||||
}
|
||||
|
||||
const databaseAccount = userContext.databaseAccount;
|
||||
const subscriptionId = userContext.subscriptionId;
|
||||
const resourceGroup = userContext.resourceGroup;
|
||||
const url = `${configContext.BACKEND_ENDPOINT}${notificationsPath()}?accountName=${
|
||||
databaseAccount.name
|
||||
}&subscriptionId=${subscriptionId}&resourceGroup=${resourceGroup}`;
|
||||
const authorizationHeader: ViewModels.AuthorizationTokenHeaderMetadata = getAuthorizationHeader();
|
||||
const headers = { [authorizationHeader.header]: authorizationHeader.token };
|
||||
|
||||
const response = await window.fetch(url, {
|
||||
headers
|
||||
});
|
||||
|
||||
if (!response.ok) {
|
||||
throw new Error(await response.text());
|
||||
}
|
||||
|
||||
return (await response.json()) as DataModels.Notification[];
|
||||
};
|
@ -103,9 +103,7 @@ describe("SettingsComponent", () => {
|
||||
let settingsComponentInstance = new SettingsComponent(baseProps);
|
||||
expect(settingsComponentInstance.shouldShowKeyspaceSharedThroughputMessage()).toEqual(false);
|
||||
|
||||
const newContainer = new Explorer({
|
||||
notificationsClient: undefined
|
||||
});
|
||||
const newContainer = new Explorer();
|
||||
newContainer.isPreferredApiCassandra = ko.computed(() => true);
|
||||
|
||||
const newCollection = { ...collection };
|
||||
@ -146,9 +144,7 @@ describe("SettingsComponent", () => {
|
||||
let settingsComponentInstance = new SettingsComponent(baseProps);
|
||||
expect(settingsComponentInstance.hasConflictResolution()).toEqual(undefined);
|
||||
|
||||
const newContainer = new Explorer({
|
||||
notificationsClient: undefined
|
||||
});
|
||||
const newContainer = new Explorer();
|
||||
newContainer.databaseAccount = ko.observable({
|
||||
id: undefined,
|
||||
name: undefined,
|
||||
|
@ -12,9 +12,7 @@ import * as SharedConstants from "../../../../Shared/Constants";
|
||||
import ko from "knockout";
|
||||
|
||||
describe("ScaleComponent", () => {
|
||||
const nonNationalCloudContainer = new Explorer({
|
||||
notificationsClient: undefined
|
||||
});
|
||||
const nonNationalCloudContainer = new Explorer();
|
||||
nonNationalCloudContainer.getPlatformType = () => PlatformType.Portal;
|
||||
nonNationalCloudContainer.isRunningOnNationalCloud = () => false;
|
||||
|
||||
@ -87,9 +85,7 @@ describe("ScaleComponent", () => {
|
||||
});
|
||||
|
||||
it("autoScale enabled", () => {
|
||||
const newContainer = new Explorer({
|
||||
notificationsClient: undefined
|
||||
});
|
||||
const newContainer = new Explorer();
|
||||
|
||||
newContainer.databaseAccount({
|
||||
id: undefined,
|
||||
|
@ -105,9 +105,7 @@ describe("SubSettingsComponent", () => {
|
||||
});
|
||||
|
||||
it("partitionKey not visible", () => {
|
||||
const newContainer = new Explorer({
|
||||
notificationsClient: undefined
|
||||
});
|
||||
const newContainer = new Explorer();
|
||||
|
||||
newContainer.isPreferredApiCassandra = ko.computed(() => true);
|
||||
const props = { ...baseProps, container: newContainer };
|
||||
|
@ -3,9 +3,7 @@ import * as ViewModels from "../../../Contracts/ViewModels";
|
||||
import Explorer from "../../Explorer";
|
||||
import ko from "knockout";
|
||||
|
||||
export const container = new Explorer({
|
||||
notificationsClient: undefined
|
||||
});
|
||||
export const container = new Explorer();
|
||||
|
||||
export const collection = ({
|
||||
container: container,
|
||||
|
@ -1051,7 +1051,6 @@ exports[`SettingsComponent renders 1`] = `
|
||||
"parameters": [Function],
|
||||
},
|
||||
"notificationConsoleData": [Function],
|
||||
"notificationsClient": undefined,
|
||||
"onRefreshDatabasesKeyPress": [Function],
|
||||
"onRefreshResourcesClick": [Function],
|
||||
"onSwitchToConnectionString": [Function],
|
||||
@ -2358,7 +2357,6 @@ exports[`SettingsComponent renders 1`] = `
|
||||
"parameters": [Function],
|
||||
},
|
||||
"notificationConsoleData": [Function],
|
||||
"notificationsClient": undefined,
|
||||
"onRefreshDatabasesKeyPress": [Function],
|
||||
"onRefreshResourcesClick": [Function],
|
||||
"onSwitchToConnectionString": [Function],
|
||||
@ -3678,7 +3676,6 @@ exports[`SettingsComponent renders 1`] = `
|
||||
"parameters": [Function],
|
||||
},
|
||||
"notificationConsoleData": [Function],
|
||||
"notificationsClient": undefined,
|
||||
"onRefreshDatabasesKeyPress": [Function],
|
||||
"onRefreshResourcesClick": [Function],
|
||||
"onSwitchToConnectionString": [Function],
|
||||
@ -4985,7 +4982,6 @@ exports[`SettingsComponent renders 1`] = `
|
||||
"parameters": [Function],
|
||||
},
|
||||
"notificationConsoleData": [Function],
|
||||
"notificationsClient": undefined,
|
||||
"onRefreshDatabasesKeyPress": [Function],
|
||||
"onRefreshResourcesClick": [Function],
|
||||
"onSwitchToConnectionString": [Function],
|
||||
|
@ -82,7 +82,6 @@ import { toRawContentUri, fromContentUri } from "../Utils/GitHubUtils";
|
||||
import UserDefinedFunction from "./Tree/UserDefinedFunction";
|
||||
import StoredProcedure from "./Tree/StoredProcedure";
|
||||
import Trigger from "./Tree/Trigger";
|
||||
import { NotificationsClientBase } from "../Common/NotificationsClientBase";
|
||||
import { ContextualPaneBase } from "./Panes/ContextualPaneBase";
|
||||
import TabsBase from "./Tabs/TabsBase";
|
||||
import { CommandButtonComponentProps } from "./Controls/CommandButton/CommandButtonComponent";
|
||||
@ -99,9 +98,6 @@ enum ShareAccessToggleState {
|
||||
Read
|
||||
}
|
||||
|
||||
interface ExplorerOptions {
|
||||
notificationsClient: NotificationsClientBase;
|
||||
}
|
||||
interface AdHocAccessData {
|
||||
readWriteUrl: string;
|
||||
readUrl: string;
|
||||
@ -141,7 +137,6 @@ export default class Explorer {
|
||||
public serverId: ko.Observable<string>;
|
||||
public armEndpoint: ko.Observable<string>;
|
||||
public isTryCosmosDBSubscription: ko.Observable<boolean>;
|
||||
public notificationsClient: NotificationsClientBase;
|
||||
public queriesClient: QueriesClient;
|
||||
public tableDataClient: TableDataClient;
|
||||
public splitter: Splitter;
|
||||
@ -270,7 +265,7 @@ export default class Explorer {
|
||||
|
||||
private static readonly MaxNbDatabasesToAutoExpand = 5;
|
||||
|
||||
constructor(options: ExplorerOptions) {
|
||||
constructor() {
|
||||
const startKey: number = TelemetryProcessor.traceStart(Action.InitializeDataExplorer, {
|
||||
dataExplorerArea: Constants.Areas.ResourceTree
|
||||
});
|
||||
@ -376,7 +371,6 @@ export default class Explorer {
|
||||
}
|
||||
});
|
||||
this.memoryUsageInfo = ko.observable<DataModels.MemoryUsageInfo>();
|
||||
this.notificationsClient = options.notificationsClient;
|
||||
|
||||
this.features = ko.observable();
|
||||
this.serverId = ko.observable<string>();
|
||||
@ -1910,7 +1904,6 @@ export default class Explorer {
|
||||
this.features(inputs.features);
|
||||
this.serverId(inputs.serverId);
|
||||
this.armEndpoint(EnvironmentUtility.normalizeArmEndpointUri(inputs.csmEndpoint || configContext.ARM_ENDPOINT));
|
||||
this.notificationsClient.setExtensionEndpoint(configContext.BACKEND_ENDPOINT);
|
||||
this.databaseAccount(databaseAccount);
|
||||
this.subscriptionType(inputs.subscriptionType);
|
||||
this.quotaId(inputs.quotaId);
|
||||
|
@ -40,7 +40,7 @@ describe("Add Collection Pane", () => {
|
||||
};
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
explorer.hasAutoPilotV2FeatureFlag = ko.computed<boolean>(() => true);
|
||||
});
|
||||
|
||||
|
@ -40,9 +40,7 @@ describe("Add Database Pane", () => {
|
||||
};
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({
|
||||
notificationsClient: null
|
||||
});
|
||||
explorer = new Explorer();
|
||||
});
|
||||
|
||||
it("should be true if subscription type is Benefits", () => {
|
||||
|
@ -17,7 +17,7 @@ describe("Delete Collection Confirmation Pane", () => {
|
||||
let explorer: Explorer;
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
});
|
||||
|
||||
it("should be true if 1 database and 1 collection", () => {
|
||||
@ -56,7 +56,7 @@ describe("Delete Collection Confirmation Pane", () => {
|
||||
|
||||
describe("shouldRecordFeedback()", () => {
|
||||
it("should return true if last collection and database does not have shared throughput else false", () => {
|
||||
let fakeExplorer = new Explorer({ notificationsClient: null });
|
||||
let fakeExplorer = new Explorer();
|
||||
fakeExplorer.isNotificationConsoleExpanded = ko.observable<boolean>(false);
|
||||
fakeExplorer.refreshAllDatabases = () => Q.resolve();
|
||||
|
||||
|
@ -22,7 +22,7 @@ describe("Delete Database Confirmation Pane", () => {
|
||||
});
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
});
|
||||
|
||||
it("should be true if only 1 database", () => {
|
||||
|
@ -7,7 +7,7 @@ describe("Settings Pane", () => {
|
||||
let explorer: Explorer;
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
});
|
||||
|
||||
it("should be true for SQL API", () => {
|
||||
|
@ -6,7 +6,7 @@ import Explorer from "../Explorer";
|
||||
jest.mock("../Explorer");
|
||||
|
||||
const createExplorer = () => {
|
||||
const mock = new Explorer({} as any);
|
||||
const mock = new Explorer();
|
||||
mock.selectedNode = ko.observable();
|
||||
mock.isNotebookEnabled = ko.observable(false);
|
||||
mock.addCollectionText = ko.observable("add collection");
|
||||
|
@ -27,13 +27,9 @@ describe("Documents tab", () => {
|
||||
});
|
||||
|
||||
describe("showPartitionKey", () => {
|
||||
const explorer = new Explorer({
|
||||
notificationsClient: null
|
||||
});
|
||||
const explorer = new Explorer();
|
||||
|
||||
const mongoExplorer = new Explorer({
|
||||
notificationsClient: null
|
||||
});
|
||||
const mongoExplorer = new Explorer();
|
||||
mongoExplorer.defaultExperience(Constants.DefaultAccountExperience.MongoDB);
|
||||
|
||||
const collectionWithoutPartitionKey = <ViewModels.Collection>(<unknown>{
|
||||
|
@ -49,7 +49,7 @@ describe("Query Tab", () => {
|
||||
let explorer: Explorer;
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
});
|
||||
|
||||
it("should be true for accounts using SQL API", () => {
|
||||
@ -69,7 +69,7 @@ describe("Query Tab", () => {
|
||||
let explorer: Explorer;
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
});
|
||||
|
||||
it("should be visible when using a supported API", () => {
|
||||
|
@ -79,7 +79,7 @@ describe("Settings tab", () => {
|
||||
};
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
explorer.hasAutoPilotV2FeatureFlag = ko.computed<boolean>(() => true);
|
||||
});
|
||||
|
||||
@ -178,7 +178,7 @@ describe("Settings tab", () => {
|
||||
let explorer: Explorer;
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
explorer.hasAutoPilotV2FeatureFlag = ko.computed<boolean>(() => true);
|
||||
});
|
||||
|
||||
@ -256,7 +256,7 @@ describe("Settings tab", () => {
|
||||
let explorer: Explorer;
|
||||
|
||||
beforeEach(() => {
|
||||
explorer = new Explorer({ notificationsClient: null });
|
||||
explorer = new Explorer();
|
||||
explorer.hasAutoPilotV2FeatureFlag = ko.computed<boolean>(() => true);
|
||||
});
|
||||
|
||||
@ -337,9 +337,7 @@ describe("Settings tab", () => {
|
||||
}
|
||||
|
||||
function getCollection(defaultApi: string, partitionKeyOption: PartitionKeyOption) {
|
||||
const explorer = new Explorer({
|
||||
notificationsClient: null
|
||||
});
|
||||
const explorer = new Explorer();
|
||||
explorer.defaultExperience(defaultApi);
|
||||
explorer.hasAutoPilotV2FeatureFlag = ko.computed<boolean>(() => true);
|
||||
|
||||
@ -469,9 +467,7 @@ describe("Settings tab", () => {
|
||||
|
||||
describe("AutoPilot", () => {
|
||||
function getCollection(autoPilotTier: DataModels.AutopilotTier) {
|
||||
const explorer = new Explorer({
|
||||
notificationsClient: null
|
||||
});
|
||||
const explorer = new Explorer();
|
||||
explorer.hasAutoPilotV2FeatureFlag = ko.computed<boolean>(() => true);
|
||||
|
||||
explorer.databaseAccount({
|
||||
|
@ -16,7 +16,7 @@ describe("Tabs manager tests", () => {
|
||||
let documentsTab: DocumentsTab;
|
||||
|
||||
beforeAll(() => {
|
||||
explorer = new Explorer({ notificationsClient: undefined });
|
||||
explorer = new Explorer();
|
||||
explorer.databaseAccount = ko.observable<DataModels.DatabaseAccount>({
|
||||
id: "test",
|
||||
name: "test",
|
||||
|
@ -40,6 +40,7 @@ import { configContext } from "../../ConfigContext";
|
||||
import Explorer from "../Explorer";
|
||||
import { userContext } from "../../UserContext";
|
||||
import TabsBase from "../Tabs/TabsBase";
|
||||
import { fetchPortalNotifications } from "../../Common/PortalNotifications";
|
||||
|
||||
export default class Collection implements ViewModels.Collection {
|
||||
public nodeKind: string;
|
||||
@ -1213,7 +1214,7 @@ export default class Collection implements ViewModels.Collection {
|
||||
}
|
||||
|
||||
const deferred: Q.Deferred<DataModels.Notification> = Q.defer<DataModels.Notification>();
|
||||
this.container.notificationsClient.fetchNotifications().then(
|
||||
fetchPortalNotifications().then(
|
||||
(notifications: DataModels.Notification[]) => {
|
||||
if (!notifications || notifications.length === 0) {
|
||||
deferred.resolve(undefined);
|
||||
|
@ -15,6 +15,7 @@ import Explorer from "../Explorer";
|
||||
import { readCollections } from "../../Common/dataAccess/readCollections";
|
||||
import { readDatabaseOffer } from "../../Common/dataAccess/readDatabaseOffer";
|
||||
import { DefaultAccountExperienceType } from "../../DefaultAccountExperienceType";
|
||||
import { fetchPortalNotifications } from "../../Common/PortalNotifications";
|
||||
|
||||
export default class Database implements ViewModels.Database {
|
||||
public nodeKind: string;
|
||||
@ -220,8 +221,8 @@ export default class Database implements ViewModels.Database {
|
||||
}
|
||||
|
||||
const deferred: Q.Deferred<DataModels.Notification> = Q.defer<DataModels.Notification>();
|
||||
this.container.notificationsClient.fetchNotifications().then(
|
||||
(notifications: DataModels.Notification[]) => {
|
||||
fetchPortalNotifications().then(
|
||||
notifications => {
|
||||
if (!notifications || notifications.length === 0) {
|
||||
deferred.resolve(undefined);
|
||||
return;
|
||||
|
@ -2,13 +2,9 @@ import { AccountKind, TagNames, DefaultAccountExperience } from "../../Common/Co
|
||||
|
||||
import Explorer from "../../Explorer/Explorer";
|
||||
|
||||
import { NotificationsClient } from "./NotificationsClient";
|
||||
|
||||
export default class EmulatorExplorerFactory {
|
||||
public static createExplorer(): Explorer {
|
||||
const explorer: Explorer = new Explorer({
|
||||
notificationsClient: new NotificationsClient()
|
||||
});
|
||||
const explorer: Explorer = new Explorer();
|
||||
explorer.databaseAccount({
|
||||
name: "",
|
||||
id: "",
|
||||
|
@ -1,16 +0,0 @@
|
||||
import Q from "q";
|
||||
import * as DataModels from "../../Contracts/DataModels";
|
||||
import { NotificationsClientBase } from "../../Common/NotificationsClientBase";
|
||||
|
||||
export class NotificationsClient extends NotificationsClientBase {
|
||||
private static readonly _notificationsApiSuffix: string = "/api/notifications";
|
||||
|
||||
public constructor() {
|
||||
super(NotificationsClient._notificationsApiSuffix);
|
||||
}
|
||||
|
||||
public fetchNotifications(): Q.Promise<DataModels.Notification[]> {
|
||||
// no notifications for the emulator
|
||||
return Q([]);
|
||||
}
|
||||
}
|
@ -1,11 +1,8 @@
|
||||
import Explorer from "../../Explorer/Explorer";
|
||||
import { NotificationsClient } from "./NotificationsClient";
|
||||
|
||||
export default class HostedExplorerFactory {
|
||||
public createExplorer(): Explorer {
|
||||
const explorer = new Explorer({
|
||||
notificationsClient: new NotificationsClient()
|
||||
});
|
||||
const explorer = new Explorer();
|
||||
|
||||
return explorer;
|
||||
}
|
||||
|
@ -1,9 +0,0 @@
|
||||
import { NotificationsClientBase } from "../../Common/NotificationsClientBase";
|
||||
|
||||
export class NotificationsClient extends NotificationsClientBase {
|
||||
private static readonly _notificationsApiSuffix: string = "/api/guest/notifications";
|
||||
|
||||
public constructor() {
|
||||
super(NotificationsClient._notificationsApiSuffix);
|
||||
}
|
||||
}
|
@ -1,11 +1,8 @@
|
||||
import Explorer from "../../Explorer/Explorer";
|
||||
import { NotificationsClient } from "./NotificationsClient";
|
||||
|
||||
export default class PortalExplorerFactory {
|
||||
public createExplorer(): Explorer {
|
||||
var explorer = new Explorer({
|
||||
notificationsClient: new NotificationsClient()
|
||||
});
|
||||
var explorer = new Explorer();
|
||||
|
||||
return explorer;
|
||||
}
|
||||
|
@ -1,9 +0,0 @@
|
||||
import { NotificationsClientBase } from "../../Common/NotificationsClientBase";
|
||||
|
||||
export class NotificationsClient extends NotificationsClientBase {
|
||||
private static readonly _notificationsApiSuffix: string = "/api/notifications";
|
||||
|
||||
public constructor() {
|
||||
super(NotificationsClient._notificationsApiSuffix);
|
||||
}
|
||||
}
|
@ -9,9 +9,7 @@ describe("TabRouteHandler", () => {
|
||||
let tabRouteHandler: TabRouteHandler;
|
||||
|
||||
beforeAll(() => {
|
||||
(<any>window).dataExplorer = new Explorer({
|
||||
notificationsClient: null
|
||||
}); // create a mock to avoid null refs
|
||||
(<any>window).dataExplorer = new Explorer(); // create a mock to avoid null refs
|
||||
});
|
||||
|
||||
beforeEach(() => {
|
||||
|
@ -60,7 +60,7 @@ describe("AuthorizationUtils", () => {
|
||||
});
|
||||
|
||||
describe("displayTokenRenewalPromptForStatus()", () => {
|
||||
let explorer = new Explorer({} as any) as jest.Mocked<Explorer>;
|
||||
let explorer = new Explorer() as jest.Mocked<Explorer>;
|
||||
|
||||
beforeEach(() => {
|
||||
jest.clearAllMocks();
|
||||
|
Loading…
Reference in New Issue
Block a user