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

Sort-Jobs Implemented #2462

Merged
merged 6 commits into from
Sep 19, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions packages/zowe-explorer/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@ All notable changes to the "vscode-extension-for-zowe" extension will be documen

### New features and enhancements

- Added "Sort Jobs" feature for job nodes in Jobs tree view. [#2257](https://github.com/zowe/vscode-extension-for-zowe/issues/2251)

### Bug fixes

- Fixed submitting local JCL using command pallet option `Zowe Explorer: Submit JCL` by adding a check for chosen profile returned to continue the action. [#1625](https://github.com/zowe/vscode-extension-for-zowe/issues/1625)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -238,6 +238,9 @@ async function createGlobalMocks() {
"zowe.jobs.startPolling",
"zowe.jobs.stopPolling",
"zowe.jobs.cancelJob",
"zowe.jobs.sortbyname",
"zowe.jobs.sortbyid",
"zowe.jobs.sortbyreturncode",
"zowe.manualPoll",
"zowe.updateSecureCredentials",
"zowe.promptCredentials",
Expand Down
101 changes: 101 additions & 0 deletions packages/zowe-explorer/__tests__/__unit__/job/actions.unit.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ import * as refreshActions from "../../../src/shared/refresh";
import * as sharedUtils from "../../../src/shared/utils";
import { ZoweLogger } from "../../../src/utils/LoggerUtils";
import { SpoolFile } from "../../../src/SpoolProvider";
import { ZosJobsProvider } from "../../../src/job/ZosJobsProvider";

const activeTextEditorDocument = jest.fn();

Expand Down Expand Up @@ -85,6 +86,49 @@ function createGlobalMocks() {
Object.defineProperty(ZoweLogger, "error", { value: jest.fn(), configurable: true });
Object.defineProperty(ZoweLogger, "debug", { value: jest.fn(), configurable: true });
Object.defineProperty(ZoweLogger, "trace", { value: jest.fn(), configurable: true });
Object.defineProperty(vscode.window, "showInformationMessage", { value: jest.fn(), configurable: true });
function settingJobObjects(job: zowe.IJob, setjobname: string, setjobid: string, setjobreturncode: string): zowe.IJob {
job.jobname = setjobname;
job.jobid = setjobid;
job.retcode = setjobreturncode;
return job;
}
const newMocks = jest.fn().mockReturnValue([
(() => {
const JobNode1 = new Job(
"testProfile",
vscode.TreeItemCollapsibleState.None,
null,
createISession(),
settingJobObjects(createIJobObject(), "ZOWEUSR1", "JOB045123", "ABEND S222"),
createIProfile()
);
return JobNode1;
})(),
(() => {
const JobNode2 = new Job(
"testProfile",
vscode.TreeItemCollapsibleState.None,
null,
createISession(),
settingJobObjects(createIJobObject(), "ZOWEUSR1", "JOB045120", "CC 0000"),
createIProfile()
);
return JobNode2;
})(),
(() => {
const JobNode3 = new Job(
"testProfile",
vscode.TreeItemCollapsibleState.None,
null,
createISession(),
settingJobObjects(createIJobObject(), "ZOWEUSR2", "JOB045125", "CC 0000"),
createIProfile()
);
return JobNode3;
})(),
]);
return newMocks;
}

// Idea is borrowed from: https://github.com/kulshekhar/ts-jest/blob/master/src/util/testing.ts
Expand Down Expand Up @@ -1300,3 +1344,60 @@ describe("Job Actions Unit Tests - Misc. functions", () => {
expect(statusMsgSpy).toHaveBeenCalledWith(`$(sync~spin) Polling: ${testDoc.fileName}...`);
});
});
describe("sortjobsby function", () => {
afterEach(() => {
jest.restoreAllMocks();
});
it("if there are no jobs in the zosmf level yet", async () => {
createGlobalMocks();
const testtree = new ZosJobsProvider();
//act
await jobActions.sortJobsBy(testtree.mSessionNodes[0], testtree, "jobname");
await jobActions.sortJobsBy(testtree.mSessionNodes[0], testtree, "jobid");
await jobActions.sortJobsBy(testtree.mSessionNodes[0], testtree, "retcode");
//assert
expect(mocked(vscode.window.showInformationMessage)).toBeCalled();
});
it("sort by name if same sort by increasing id", async () => {
const globalMocks = createGlobalMocks();
const testtree = new ZosJobsProvider();
const expected = new ZosJobsProvider();
testtree.mSessionNodes[0].children = [...[globalMocks()[2], globalMocks()[1], globalMocks()[0]]];
expected.mSessionNodes[0].children = [...[globalMocks()[1], globalMocks()[0], globalMocks()[2]]];
const sortbynamespy = jest.spyOn(jobActions, "sortJobsBy");
//act
await jobActions.sortJobsBy(testtree.mSessionNodes[0], testtree, "jobname");
//asert
expect(sortbynamespy).toBeCalledWith(testtree.mSessionNodes[0], testtree, "jobname");
expect(sortbynamespy).toHaveBeenCalled();
expect(sortbynamespy.mock.calls[0][0].children).toStrictEqual(expected.mSessionNodes[0].children);
});
it("sorts by increasing order of id", async () => {
const globalMocks = createGlobalMocks();
const testtree = new ZosJobsProvider();
const expected = new ZosJobsProvider();
testtree.mSessionNodes[0].children = [...[globalMocks()[2], globalMocks()[1], globalMocks()[0]]];
expected.mSessionNodes[0].children = [...[globalMocks()[1], globalMocks()[0], globalMocks()[2]]];
const sortbyidspy = jest.spyOn(jobActions, "sortJobsBy");
//act
await jobActions.sortJobsBy(testtree.mSessionNodes[0], testtree, "jobid");
//asert
expect(sortbyidspy).toBeCalledWith(testtree.mSessionNodes[0], testtree, "jobid");
expect(sortbyidspy).toHaveBeenCalled();
expect(sortbyidspy.mock.calls[0][0].children).toStrictEqual(expected.mSessionNodes[0].children);
});
it("sort by retcode if same sort by increasing id", async () => {
const globalMocks = createGlobalMocks();
const testtree = new ZosJobsProvider();
const expected = new ZosJobsProvider();
testtree.mSessionNodes[0].children = [...[globalMocks()[2], globalMocks()[1], globalMocks()[0]]];
expected.mSessionNodes[0].children = [...[globalMocks()[0], globalMocks()[1], globalMocks()[2]]];
const sortbyretcodespy = jest.spyOn(jobActions, "sortJobsBy");
//act
await jobActions.sortJobsBy(testtree.mSessionNodes[0], testtree, "retcode");
//asert
expect(sortbyretcodespy).toBeCalledWith(testtree.mSessionNodes[0], testtree, "retcode");
expect(sortbyretcodespy).toHaveBeenCalled();
expect(sortbyretcodespy.mock.calls[0][0].children).toStrictEqual(expected.mSessionNodes[0].children);
});
});
30 changes: 30 additions & 0 deletions packages/zowe-explorer/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,21 @@
}
],
"commands": [
{
"command": "zowe.jobs.sortbyreturncode",
"title": "%jobs.sortbyreturncode%",
"category": "Zowe Explorer"
},
{
"command": "zowe.jobs.sortbyname",
"title": "%jobs.sortbyname%",
"category": "Zowe Explorer"
},
{
"command": "zowe.jobs.sortbyid",
"title": "%jobs.sortbyid%",
"category": "Zowe Explorer"
},
{
"command": "zowe.promptCredentials",
"title": "%zowe.promptCredentials%",
Expand Down Expand Up @@ -1357,6 +1372,21 @@
"when": "view == zowe.jobs.explorer && viewItem =~ /^(?!.*_fav.*)server.*/ && !listMultiSelection",
"command": "zowe.jobs.deleteProfile",
"group": "099_zowe_jobsProfileModification@99"
},
{
"when": "view == zowe.jobs.explorer && viewItem =~ /^(?!.*_fav.*)server.*/ && !listMultiSelection",
"command": "zowe.jobs.sortbyid",
"group": "000_zowe_jobsProfileModification@1"
},
{
"when": "view == zowe.jobs.explorer && viewItem =~ /^(?!.*_fav.*)server.*/ && !listMultiSelection",
"command": "zowe.jobs.sortbyname",
"group": "000_zowe_jobsProfileModification@2"
},
{
"when": "view == zowe.jobs.explorer && viewItem =~ /^(?!.*_fav.*)server.*/ && !listMultiSelection",
"command": "zowe.jobs.sortbyreturncode",
"group": "000_zowe_jobsProfileModification@2"
}
],
"commandPalette": [
Expand Down
5 changes: 4 additions & 1 deletion packages/zowe-explorer/package.nls.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,5 +146,8 @@
"createZoweSchema.reload.button": "Reload Window",
"createZoweSchema.reload.infoMessage": "Team Configuration file created. Location: {0}. \n Please reload your window.",
"copyFile": "Copy",
"pasteFile": "Paste"
"pasteFile": "Paste",
"jobs.sortbyreturncode": "Sort by ReturnCode",
"jobs.sortbyname": "Sort by Name",
"jobs.sortbyid": "Sort by ID"
}
2 changes: 1 addition & 1 deletion packages/zowe-explorer/src/globals.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ export let DS_DIR: string;
export let CONFIG_PATH; // set during activate
export let ISTHEIA = false; // set during activate
export let LOG: imperative.Logger;
export const COMMAND_COUNT = 110;
export const COMMAND_COUNT = 113;
export const MAX_SEARCH_HISTORY = 5;
export const MAX_FILE_HISTORY = 10;
export const MS_PER_SEC = 1000;
Expand Down
15 changes: 14 additions & 1 deletion packages/zowe-explorer/src/job/actions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ import * as zowe from "@zowe/cli";
import { errorHandling } from "../utils/ProfilesUtils";
import { Profiles } from "../Profiles";
import { ZoweExplorerApiRegister } from "../ZoweExplorerApiRegister";
import { Gui, ValidProfileEnum, IZoweTree, IZoweJobTreeNode } from "@zowe/zowe-explorer-api";
import { Gui, IZoweTree, IZoweJobTreeNode } from "@zowe/zowe-explorer-api";
import { Job, Spool } from "./ZoweJobNode";
import * as nls from "vscode-nls";
import SpoolProvider, { encodeJobFile, getSpoolFiles, matchSpool } from "../SpoolProvider";
Expand Down Expand Up @@ -528,3 +528,16 @@ export async function cancelJobs(jobsProvider: IZoweTree<IZoweJobTreeNode>, node
await Gui.showMessage(localize("cancelJobs.succeeded", "Cancelled selected jobs successfully."));
}
}
export async function sortJobsBy(jobs: IZoweJobTreeNode, jobsProvider: IZoweTree<IZoweJobTreeNode>, key: keyof zowe.IJob): Promise<void> {
if (jobs["children"].length == 0) {
await vscode.window.showInformationMessage("No jobs are present in the profile.");
}
jobs["children"].sort((x, y) => {
if (key !== "jobid" && x["job"][key] == y["job"][key]) {
return x["job"]["jobid"] > y["job"]["jobid"] ? 1 : -1;
} else {
return x["job"][key] > y["job"][key] ? 1 : -1;
}
});
jobsProvider.refresh();
}
6 changes: 5 additions & 1 deletion packages/zowe-explorer/src/job/init.ts
Original file line number Diff line number Diff line change
Expand Up @@ -169,7 +169,11 @@ export async function initJobsProvider(context: vscode.ExtensionContext): Promis
await jobActions.cancelJobs(jobsProvider, getSelectedNodeList(node, nodeList));
})
);

context.subscriptions.push(vscode.commands.registerCommand("zowe.jobs.sortbyname", (job) => jobActions.sortJobsBy(job, jobsProvider, "jobname")));
context.subscriptions.push(vscode.commands.registerCommand("zowe.jobs.sortbyid", (job) => jobActions.sortJobsBy(job, jobsProvider, "jobid")));
context.subscriptions.push(
vscode.commands.registerCommand("zowe.jobs.sortbyreturncode", (job) => jobActions.sortJobsBy(job, jobsProvider, "retcode"))
);
initSubscribers(context, jobsProvider);
return jobsProvider;
}