Skip to content

Commit

Permalink
Merge branch 'next' of https://github.com/zowe/zowe-explorer-vscode i…
Browse files Browse the repository at this point in the history
…nto ext-not

Signed-off-by: zFernand0 <[email protected]>
  • Loading branch information
zFernand0 committed Jul 29, 2024
2 parents 8954d7e + 2950dfa commit 0ab43e4
Show file tree
Hide file tree
Showing 18 changed files with 149 additions and 261 deletions.
1 change: 0 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,6 @@
"rimraf": "^3.0.2",
"terser-webpack-plugin": "^5.3.10",
"ts-jest": "^29.0.3",
"tsconfig-paths-webpack-plugin": "^4.1.0",
"tsx": "^4.9.3",
"typescript": "^5.3.3",
"webpack": "^5.89.0",
Expand Down
2 changes: 1 addition & 1 deletion packages/zowe-explorer-api/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ All notable changes to the "zowe-explorer-api" extension will be documented in t
- Fixed an issue where the `onProfilesUpdate` event did not fire after secure credentials were updated. [#2822](https://github.com/zowe/zowe-explorer-vscode/issues/2822)
- Fixed an issue where `ProfilesCache` may return missing or incorrect profile values when multiple extensions call it during activation. [#2831](https://github.com/zowe/zowe-explorer-vscode/issues/2831)
- Removed `handlebars` dependency in favor of `mustache` for technical currency purposes. [#2975](https://github.com/zowe/zowe-explorer-vscode/pull/2975)
- Update Zowe SDKs to `8.0.0-next.202407051717` for technical currency. [#2918](https://github.com/zowe/zowe-explorer-vscode/issues/2918)
- Fixed an issue where the `ZoweVsCodeExtension.updateCredentials` method could remove credentials from session when input prompt was cancelled. [#3009](https://github.com/zowe/zowe-explorer-vscode/pull/3009)
- Fixed an issue where the loaded configuration could be overridden when extenders retrieved the Zowe home directory. [#2994](https://github.com/zowe/zowe-explorer-vscode/pull/2994)
- Update Zowe SDKs to `8.0.0-next.202407232256` for technical currency. [#2994](https://github.com/zowe/zowe-explorer-vscode/pull/2994)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -467,10 +467,11 @@ describe("ZoweVsCodeExtension", () => {
});

it("should do nothing if user input is cancelled", async () => {
const fakeProfile = { user: "fakeUser", password: "fakePass" };
const mockUpdateProperty = jest.fn();
jest.spyOn(ZoweVsCodeExtension as any, "profilesCache", "get").mockReturnValue({
getLoadedProfConfig: jest.fn().mockReturnValue({
profile: {},
profile: fakeProfile,
}),
getProfileInfo: jest.fn().mockReturnValue({
isSecured: jest.fn().mockReturnValue(true),
Expand All @@ -479,17 +480,23 @@ describe("ZoweVsCodeExtension", () => {
refresh: jest.fn(),
});
const showInputBoxSpy = jest.spyOn(Gui, "showInputBox").mockResolvedValueOnce(undefined);
const profileLoaded = await ZoweVsCodeExtension.updateCredentials(promptCredsOptions, undefined as unknown as Types.IApiRegisterClient);
const profileLoaded = await ZoweVsCodeExtension.updateCredentials(
{ ...promptCredsOptions, rePrompt: true },
undefined as unknown as Types.IApiRegisterClient
);
expect(profileLoaded).toBeUndefined();
expect(showInputBoxSpy).toHaveBeenCalledTimes(1);
expect(mockUpdateProperty).toHaveBeenCalledTimes(0);
expect(fakeProfile.user).toBeDefined();
expect(fakeProfile.password).toBeDefined();
});

it("should do nothing if password input is cancelled", async () => {
const fakeProfile = { user: "fakeUser", password: "fakePass" };
const mockUpdateProperty = jest.fn();
jest.spyOn(ZoweVsCodeExtension as any, "profilesCache", "get").mockReturnValue({
getLoadedProfConfig: jest.fn().mockReturnValue({
profile: {},
profile: fakeProfile,
}),
getProfileInfo: jest.fn().mockReturnValue({
isSecured: jest.fn().mockReturnValue(true),
Expand All @@ -498,10 +505,15 @@ describe("ZoweVsCodeExtension", () => {
refresh: jest.fn(),
});
const showInputBoxSpy = jest.spyOn(Gui, "showInputBox").mockResolvedValueOnce("fakeUser").mockResolvedValueOnce(undefined);
const profileLoaded = await ZoweVsCodeExtension.updateCredentials(promptCredsOptions, undefined as unknown as Types.IApiRegisterClient);
const profileLoaded = await ZoweVsCodeExtension.updateCredentials(
{ ...promptCredsOptions, rePrompt: true },
undefined as unknown as Types.IApiRegisterClient
);
expect(profileLoaded).toBeUndefined();
expect(showInputBoxSpy).toHaveBeenCalledTimes(2);
expect(mockUpdateProperty).toHaveBeenCalledTimes(0);
expect(fakeProfile.user).toBeDefined();
expect(fakeProfile.password).toBeDefined();
});

it("should do nothing if profile and sessionName args are not provided", async () => {
Expand Down
6 changes: 6 additions & 0 deletions packages/zowe-explorer-api/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,12 @@
"provenance": true
},
"main": "lib/index.js",
"exports": {
".": {
"@zowe:bundler": "./src/index.ts",
"default": "./lib/index.js"
}
},
"files": [
"lib"
],
Expand Down
6 changes: 3 additions & 3 deletions packages/zowe-explorer-api/src/vscode/ZoweVsCodeExtension.ts
Original file line number Diff line number Diff line change
Expand Up @@ -291,7 +291,6 @@ export class ZoweVsCodeExtension {
value: newUser,
...(options.userInputBoxOptions ?? {}),
});
options.session.user = newUser;
}
if (!newUser || (options.rePrompt && newUser === "")) {
return undefined;
Expand All @@ -307,13 +306,14 @@ export class ZoweVsCodeExtension {
value: newPass,
...(options.passwordInputBoxOptions ?? {}),
});
options.session.password = newPass;
}
if (!newPass || (options.rePrompt && newPass === "")) {
return undefined;
}

return [newUser.trim(), newPass.trim()];
options.session.user = newUser.trim();
options.session.password = newPass.trim();
return [options.session.user, options.session.password];
}

private static async promptCertificate(options: PromptCredentialsOptions.CertificateOptions): Promise<void> {
Expand Down
8 changes: 1 addition & 7 deletions packages/zowe-explorer-ftp-extension/webpack.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,6 @@ const path = require("path");
const webpack = require("webpack");
const fs = require("fs");
const TerserPlugin = require("terser-webpack-plugin");

const { TsconfigPathsPlugin } = require("tsconfig-paths-webpack-plugin");
const ForkTsCheckerWebpackPlugin = require("fork-ts-checker-webpack-plugin");

/**@type {webpack.Configuration}*/
Expand All @@ -39,11 +37,7 @@ const config = {
alias: {
"@zowe/zowe-explorer-api$": path.resolve(__dirname, "..", "zowe-explorer-api/src"),
},
plugins: [
new TsconfigPathsPlugin({
references: ["../zowe-explorer-api"],
}),
],
conditionNames: ["@zowe:bundler", "..."],
},
watchOptions: {
ignored: /node_modules/,
Expand Down
2 changes: 1 addition & 1 deletion packages/zowe-explorer/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ All notable changes to the "vscode-extension-for-zowe" extension will be documen
- Fixed issue where saving changes to favorited PDS member fails when custom temp folder is set on Windows. [#2880](https://github.com/zowe/zowe-explorer-vscode/issues/2880)
- Fixed issue where multiple extensions that contribute profiles to a tree view using the Zowe Explorer API may fail to load. [#2888](https://github.com/zowe/zowe-explorer-vscode/issues/2888)
- Fixed regression where `getProviderForNode` returned the wrong tree provider after performing an action on a Zowe tree node, causing some commands to fail silently. [#2967](https://github.com/zowe/zowe-explorer-vscode/issues/2967)
- Update Zowe SDKs to `8.0.0-next.202407051717` for technical currency. [#2918](https://github.com/zowe/zowe-explorer-vscode/issues/2918)
- Fixed issue where creating a new team configuration file could cause Zowe Explorer to crash, resulting in all sessions disappearing from trees. [#2906](https://github.com/zowe/zowe-explorer-vscode/issues/2906)
- Update Zowe SDKs to `8.0.0-next.202407232256` for technical currency. [#2994](https://github.com/zowe/zowe-explorer-vscode/pull/2994)

## `3.0.0-next.202404242037`
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import {
createISessionWithoutCredentials,
createQuickPickContent,
createQuickPickItem,
createTreeProviders,
createTreeView,
} from "../../../__mocks__/mockCreators/shared";
import { createDatasetSessionNode, createDatasetTree } from "../../../__mocks__/mockCreators/datasets";
Expand All @@ -34,6 +35,8 @@ import { FilterDescriptor, FilterItem } from "../../../../src/management/FilterM
import { SharedActions } from "../../../../src/trees/shared/SharedActions";
import { IconUtils } from "../../../../src/icons/IconUtils";
import { IconGenerator } from "../../../../src/icons/IconGenerator";
import { SharedTreeProviders } from "../../../../src/trees/shared/SharedTreeProviders";
import { TreeViewUtils } from "../../../../src/utils/TreeViewUtils";

function createGlobalMocks() {
const globalMocks = {
Expand Down Expand Up @@ -542,3 +545,27 @@ describe("Shared Actions Unit Tests - Function resetValidationSettings", () => {
expect(response.contextValue).toContain(`${Constants.VALIDATE_SUFFIX}true`);
});
});

describe("Shared Actions Unit Tests - Function refreshAll", () => {
afterAll(() => {
jest.restoreAllMocks();
});

it("should refresh all tree providers and update session nodes", async () => {
createGlobalMocks();
jest.spyOn(SharedTreeProviders, "providers", "get").mockReturnValue(createTreeProviders());
const removedProfNames = new Set<string>();
const addedProfTypes = new Set<string>();
const removeSessionSpy = jest
.spyOn(TreeViewUtils, "removeSession")
.mockImplementation(async (treeProvider, profileName) => removedProfNames.add(profileName));
const addDefaultSessionSpy = jest
.spyOn(TreeViewUtils, "addDefaultSession")
.mockImplementation(async (treeProvider, profileType) => addedProfTypes.add(profileType));
await SharedActions.refreshAll();
expect(removeSessionSpy).toHaveBeenCalledTimes(6);
expect([...removedProfNames]).toEqual(["zosmf", "zosmf2"]);
expect(addDefaultSessionSpy).toHaveBeenCalledTimes(3);
expect([...addedProfTypes]).toEqual(["zosmf"]);
});
});
Original file line number Diff line number Diff line change
Expand Up @@ -122,9 +122,7 @@ describe("Test src/shared/extension", () => {
{ spy: jest.spyOn(test.value, "affectsConfiguration"), arg: [Constants.SETTINGS_LOGS_FOLDER_PATH], ret: false },
{ spy: jest.spyOn(test.value, "affectsConfiguration"), arg: [Constants.SETTINGS_AUTOMATIC_PROFILE_VALIDATION], ret: true },
{ spy: jest.spyOn(Profiles, "getInstance"), arg: [], ret: profileMocks },
{ spy: jest.spyOn(SharedActions, "refreshAll"), arg: ["ds"] },
{ spy: jest.spyOn(SharedActions, "refreshAll"), arg: ["uss"] },
{ spy: jest.spyOn(SharedActions, "refreshAll"), arg: ["job"] },
{ spy: jest.spyOn(SharedActions, "refreshAll"), arg: [] },
{ spy: jest.spyOn(test.value, "affectsConfiguration"), arg: [Constants.SETTINGS_SECURE_CREDENTIALS_ENABLED], ret: false },
],
},
Expand Down Expand Up @@ -359,39 +357,69 @@ describe("Test src/shared/extension", () => {

describe("watchConfigProfile", () => {
let context: any;
let watcherPromise: any;
const spyReadFile = jest.fn().mockReturnValue("test");
const spyExecuteCommand = jest.fn();
const mockEmitter = jest.fn();
const watcher: any = {
onDidCreate: jest.fn().mockImplementation((fun) => fun()),
onDidDelete: jest.fn().mockImplementation((fun) => fun()),
onDidChange: jest.fn().mockImplementation((fun) => fun("uri")),
onDidCreate: jest.fn(),
onDidDelete: jest.fn(),
onDidChange: jest.fn(),
};
beforeEach(() => {
context = { subscriptions: [] };
jest.clearAllMocks();
Object.defineProperty(vscode.workspace, "createFileSystemWatcher", { value: () => watcher, configurable: true });
Object.defineProperty(vscode.workspace, "workspaceFolders", { value: [{ uri: { fsPath: "fsPath" } }], configurable: true });
Object.defineProperty(vscode.commands, "executeCommand", { value: spyExecuteCommand, configurable: true });
Object.defineProperty(vscode.workspace, "fs", { value: { readFile: spyReadFile }, configurable: true });
Object.defineProperty(Constants, "SAVED_PROFILE_CONTENTS", { value: "test", configurable: true });
jest.spyOn(vscode.workspace, "createFileSystemWatcher").mockReturnValue(watcher);
jest.spyOn(ZoweExplorerApiRegister.getInstance().onProfilesUpdateEmitter, "fire").mockImplementation(mockEmitter);
});

afterAll(() => {
jest.restoreAllMocks();
});

it("should be able to trigger all listeners", async () => {
const spyRefreshAll = jest.spyOn(SharedActions, "refreshAll").mockImplementation(jest.fn());
jest.spyOn(ZoweExplorerApiRegister.getInstance().onProfilesUpdateEmitter, "fire").mockImplementation();
await SharedInit.watchConfigProfile(context, { ds: "ds", uss: "uss", job: "job" } as any);
expect(spyExecuteCommand).toHaveBeenCalledWith("zowe.extRefresh");
it("should be able to trigger onDidCreate listener", async () => {
const spyRefreshAll = jest.spyOn(SharedActions, "refreshAll").mockImplementation();
watcher.onDidCreate.mockImplementationOnce((fun) => (watcherPromise = fun()));
SharedInit.watchConfigProfile(context);
await watcherPromise;
expect(context.subscriptions).toContain(watcher);
expect(spyRefreshAll).toHaveBeenCalledTimes(1);
expect(mockEmitter).toHaveBeenCalledTimes(1);
});

it("should be able to trigger onDidDelete listener", async () => {
const spyRefreshAll = jest.spyOn(SharedActions, "refreshAll").mockImplementation();
watcher.onDidDelete.mockImplementationOnce((fun) => (watcherPromise = fun()));
SharedInit.watchConfigProfile(context);
await watcherPromise;
expect(context.subscriptions).toContain(watcher);
expect(spyRefreshAll).toHaveBeenCalledTimes(1);
expect(mockEmitter).toHaveBeenCalledTimes(1);
});

it("should be able to trigger onDidChange listener", async () => {
const spyRefreshAll = jest.spyOn(SharedActions, "refreshAll").mockImplementation();
watcher.onDidChange.mockImplementationOnce((fun) => (watcherPromise = fun("uri")));
SharedInit.watchConfigProfile(context);
await watcherPromise;
expect(context.subscriptions).toContain(watcher);
expect(spyReadFile).toHaveBeenCalledWith("uri");
expect(spyRefreshAll).not.toHaveBeenCalled();
expect(mockEmitter).not.toHaveBeenCalled();
});

spyReadFile.mockReturnValue("other");
await SharedInit.watchConfigProfile(context, { ds: "ds", uss: "uss", job: "job" } as any);
expect(spyRefreshAll).toHaveBeenCalled();
it("should be able to trigger onDidChange listener with changes", async () => {
const spyRefreshAll = jest.spyOn(SharedActions, "refreshAll").mockImplementation();
spyReadFile.mockReturnValueOnce("other");
watcher.onDidChange.mockImplementationOnce((fun) => (watcherPromise = fun("uri")));
SharedInit.watchConfigProfile(context);
await watcherPromise;
expect(context.subscriptions).toContain(watcher);
expect(spyReadFile).toHaveBeenCalledWith("uri");
expect(spyRefreshAll).toHaveBeenCalledTimes(1);
expect(mockEmitter).toHaveBeenCalledTimes(1);
});

it("should trigger callbacks when credentials or credManager are updated by another application", async () => {
Expand Down
6 changes: 3 additions & 3 deletions packages/zowe-explorer/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -1746,7 +1746,7 @@
]
},
"scripts": {
"build": "pnpm clean:bundle && pnpm license && webpack --mode development && pnpm madge",
"build": "pnpm copy-secrets && pnpm clean:bundle && pnpm license && webpack --mode development && pnpm madge",
"test": "pnpm test:unit",
"test:e2e": "cd __tests__/__e2e__/ && wdio run ./wdio.conf.ts",
"test:integration": "cd __tests__/__integration__/bdd && wdio run ./wdio.conf.ts",
Expand All @@ -1773,7 +1773,8 @@
"pretty": "prettier --write .",
"createTestProfileData": "tsx ./scripts/createTestProfileData.ts",
"createDemoNodes": "tsx ./scripts/createDemoNodes.ts",
"generateLocalization": "pnpm dlx @vscode/l10n-dev export --o ./l10n ./src && node ./scripts/generatePoeditorJson.js"
"generateLocalization": "pnpm dlx @vscode/l10n-dev export --o ./l10n ./src && node ./scripts/generatePoeditorJson.js",
"copy-secrets": "tsx ./scripts/getSecretsPrebuilds.ts"
},
"engines": {
"vscode": "^1.79.0"
Expand All @@ -1797,7 +1798,6 @@
"chai": "^4.1.2",
"chai-as-promised": "^7.1.1",
"chalk": "^2.4.1",
"copy-webpack-plugin": "^12.0.2",
"eslint-plugin-zowe-explorer": "3.0.0-next-SNAPSHOT",
"expect": "^24.8.0",
"expect-webdriverio": "^4.13.0",
Expand Down
2 changes: 1 addition & 1 deletion packages/zowe-explorer/src/extension.ts
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ export async function activate(context: vscode.ExtensionContext): Promise<ZoweEx
SharedInit.registerRefreshCommand(context, activate, deactivate);
ZoweExplorerExtender.createInstance(providers.ds, providers.uss, providers.job);

SharedInit.watchConfigProfile(context, providers);
SharedInit.watchConfigProfile(context);
await SharedInit.watchForZoweButtonClick();

return ZoweExplorerApiRegister.getInstance();
Expand Down
9 changes: 2 additions & 7 deletions packages/zowe-explorer/src/trees/ZoweTreeProvider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import { ProfilesUtils } from "../utils/ProfilesUtils";
import { SharedActions } from "./shared/SharedActions";
import { IconUtils } from "../icons/IconUtils";
import { AuthUtils } from "../utils/AuthUtils";
import { TreeViewUtils } from "../utils/TreeViewUtils";

export class ZoweTreeProvider<T extends IZoweTreeNode> {
// Event Emitters used to notify subscribers that the refresh event has fired
Expand Down Expand Up @@ -356,12 +357,6 @@ export class ZoweTreeProvider<T extends IZoweTreeNode> {
}
}
}
if (treeProvider.mSessionNodes.length === 1) {
try {
await treeProvider.addSingleSession(Profiles.getInstance().getDefaultProfile(profileType));
} catch (error) {
ZoweLogger.warn(error);
}
}
await TreeViewUtils.addDefaultSession(treeProvider, profileType);
}
}
12 changes: 11 additions & 1 deletion packages/zowe-explorer/src/trees/shared/SharedActions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import { TreeViewUtils } from "../../utils/TreeViewUtils";
import { FilterItem, FilterDescriptor } from "../../management/FilterManagement";
import { IconUtils } from "../../icons/IconUtils";
import { AuthUtils } from "../../utils/AuthUtils";
import { SharedTreeProviders } from "./SharedTreeProviders";

export class SharedActions {
/**
Expand Down Expand Up @@ -231,8 +232,14 @@ export class SharedActions {
*
* @param {IZoweTree} treeProvider
*/
public static async refreshAll(treeProvider: IZoweTree<IZoweTreeNode>): Promise<void> {
public static async refreshAll(treeProvider?: IZoweTree<IZoweTreeNode>): Promise<void> {
ZoweLogger.trace("refresh.refreshAll called.");
if (treeProvider == null) {
for (const provider of Object.values(SharedTreeProviders.providers)) {
await this.refreshAll(provider);
}
return;
}
await Profiles.getInstance().refresh(ZoweExplorerApiRegister.getInstance());
for (const sessNode of treeProvider.mSessionNodes) {
const profiles = await Profiles.getInstance().fetchAllProfiles();
Expand All @@ -247,6 +254,9 @@ export class SharedActions {
await TreeViewUtils.removeSession(treeProvider, sessNode.label.toString().trim());
}
}
for (const profType of ZoweExplorerApiRegister.getInstance().registeredApiTypes()) {
await TreeViewUtils.addDefaultSession(treeProvider, profType);
}
treeProvider.refresh();
}
}
Loading

0 comments on commit 0ab43e4

Please sign in to comment.