Skip to content

Commit a718266

Browse files
Refactors 'pp solution get' to use util, updates card logging
1 parent 9281056 commit a718266

File tree

7 files changed

+47
-120
lines changed

7 files changed

+47
-120
lines changed

src/m365/pp/commands/card/card-clone.ts

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,11 @@ class PpCardCloneCommand extends PowerPlatformCommand {
9999
return args.options.id;
100100
}
101101

102-
const card = await powerPlatform.getCardByName(dynamicsApiUrl, args.options.name!, logger, this.verbose);
102+
if (this.verbose) {
103+
await logger.logToStderr(`Retrieving the card Id for card '${args.options.name}'`);
104+
}
105+
106+
const card = await powerPlatform.getCardByName(dynamicsApiUrl, args.options.name!);
103107
return card.cardid;
104108
}
105109

@@ -108,6 +112,11 @@ class PpCardCloneCommand extends PowerPlatformCommand {
108112
const dynamicsApiUrl = await powerPlatform.getDynamicsInstanceApiUrl(args.options.environmentName, args.options.asAdmin);
109113

110114
const cardId = await this.getCardId(args, dynamicsApiUrl, logger);
115+
116+
if (this.verbose) {
117+
await logger.logToStderr(`Cloning the card with id '${cardId}'`);
118+
}
119+
111120
const requestOptions: CliRequestOptions = {
112121
url: `${dynamicsApiUrl}/api/data/v9.1/CardCreateClone`,
113122
headers: {

src/m365/pp/commands/card/card-get.ts

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -99,11 +99,15 @@ class PpCardGetCommand extends PowerPlatformCommand {
9999

100100
private async getCard(dynamicsApiUrl: string, options: Options, logger: Logger): Promise<any> {
101101
if (options.name) {
102-
return await powerPlatform.getCardByName(dynamicsApiUrl, options.name!, logger, this.verbose);
102+
if (this.verbose) {
103+
await logger.logToStderr(`Retrieving the card with name '${options.name}'`);
104+
}
105+
106+
return await powerPlatform.getCardByName(dynamicsApiUrl, options.name!);
103107
}
104108

105109
if (this.verbose) {
106-
await logger.logToStderr(`Retrieving the card with id ${options.id}`);
110+
await logger.logToStderr(`Retrieving the card with id '${options.id}'`);
107111
}
108112

109113
const requestOptions: CliRequestOptions = {

src/m365/pp/commands/card/card-remove.ts

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -109,7 +109,11 @@ class PpCardRemoveCommand extends PowerPlatformCommand {
109109
return args.options.id;
110110
}
111111

112-
const card = await powerPlatform.getCardByName(dynamicsApiUrl, args.options.name!, logger, this.verbose);
112+
if (this.verbose) {
113+
await logger.logToStderr(`Retrieving the card with name '${args.options.name}'`);
114+
}
115+
116+
const card = await powerPlatform.getCardByName(dynamicsApiUrl, args.options.name!);
113117

114118
return card.cardid;
115119
}
@@ -119,6 +123,11 @@ class PpCardRemoveCommand extends PowerPlatformCommand {
119123
const dynamicsApiUrl = await powerPlatform.getDynamicsInstanceApiUrl(args.options.environmentName, args.options.asAdmin);
120124

121125
const cardId = await this.getCardId(args, dynamicsApiUrl, logger);
126+
127+
if (this.verbose) {
128+
await logger.logToStderr(`Deleting card with Id '${cardId}'`);
129+
}
130+
122131
const requestOptions: CliRequestOptions = {
123132
url: `${dynamicsApiUrl}/api/data/v9.1/cards(${cardId})`,
124133
headers: {

src/m365/pp/commands/solution/solution-get.spec.ts

Lines changed: 12 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,8 @@ describe(commands.SOLUTION_GET, () => {
7777
afterEach(() => {
7878
sinonUtil.restore([
7979
request.get,
80-
powerPlatform.getDynamicsInstanceApiUrl
80+
powerPlatform.getDynamicsInstanceApiUrl,
81+
powerPlatform.getSolutionByName
8182
]);
8283
});
8384

@@ -96,16 +97,7 @@ describe(commands.SOLUTION_GET, () => {
9697

9798
it('fails validation when no solution found', async () => {
9899
sinon.stub(powerPlatform, 'getDynamicsInstanceApiUrl').callsFake(async () => envUrl);
99-
100-
sinon.stub(request, 'get').callsFake(async (opts) => {
101-
if ((opts.url === `https://contoso-dev.api.crm4.dynamics.com/api/data/v9.0/solutions?$filter=isvisible eq true and uniquename eq 'Default'&$expand=publisherid($select=friendlyname)&$select=solutionid,uniquename,version,publisherid,installedon,solutionpackageversion,friendlyname,versionnumber&api-version=9.1`)) {
102-
if ((opts.headers?.accept as string).indexOf('application/json') === 0) {
103-
return ({ "value": [] });
104-
}
105-
}
106-
107-
throw 'Invalid request';
108-
});
100+
sinon.stub(powerPlatform, 'getSolutionByName').rejects(new Error(`The specified solution '${validName}' does not exist.`));
109101

110102
await assert.rejects(command.action(logger, {
111103
options: {
@@ -137,33 +129,15 @@ describe(commands.SOLUTION_GET, () => {
137129

138130
it('retrieves a specific solution from power platform environment with the name parameter', async () => {
139131
sinon.stub(powerPlatform, 'getDynamicsInstanceApiUrl').callsFake(async () => envUrl);
140-
141-
sinon.stub(request, 'get').callsFake(async (opts) => {
142-
if ((opts.url === `https://contoso-dev.api.crm4.dynamics.com/api/data/v9.0/solutions?$filter=isvisible eq true and uniquename eq 'Default'&$expand=publisherid($select=friendlyname)&$select=solutionid,uniquename,version,publisherid,installedon,solutionpackageversion,friendlyname,versionnumber&api-version=9.1`)) {
143-
if ((opts.headers?.accept as string).indexOf('application/json') === 0) {
144-
return solutionResponse;
145-
}
146-
}
147-
148-
throw 'Invalid request';
149-
});
132+
sinon.stub(powerPlatform, 'getSolutionByName').callsFake(async () => solutionResponse.value[0]);
150133

151134
await command.action(logger, { options: { verbose: true, environmentName: '4be50206-9576-4237-8b17-38d8aadfaa36', name: 'Default' } });
152135
assert(loggerLogSpy.calledWith(solutionResponse.value[0]));
153136
});
154137

155138
it('retrieves a specific solution from power platform environment with name parameter in format text', async () => {
156139
sinon.stub(powerPlatform, 'getDynamicsInstanceApiUrl').callsFake(async () => envUrl);
157-
158-
sinon.stub(request, 'get').callsFake(async (opts) => {
159-
if ((opts.url === `https://contoso-dev.api.crm4.dynamics.com/api/data/v9.0/solutions?$filter=isvisible eq true and uniquename eq 'Default'&$expand=publisherid($select=friendlyname)&$select=solutionid,uniquename,version,publisherid,installedon,solutionpackageversion,friendlyname,versionnumber&api-version=9.1`)) {
160-
if ((opts.headers?.accept as string).indexOf('application/json') === 0) {
161-
return solutionResponse;
162-
}
163-
}
164-
165-
throw 'Invalid request';
166-
});
140+
sinon.stub(powerPlatform, 'getSolutionByName').callsFake(async () => solutionResponse.value[0]);
167141

168142
await command.action(logger, { options: { debug: true, environmentName: '4be50206-9576-4237-8b17-38d8aadfaa36', name: 'Default', output: 'text' } });
169143
assert(loggerLogSpy.calledWith(solutionResponseText));
@@ -205,23 +179,15 @@ describe(commands.SOLUTION_GET, () => {
205179

206180
it('correctly handles API OData error', async () => {
207181
sinon.stub(powerPlatform, 'getDynamicsInstanceApiUrl').callsFake(async () => envUrl);
208-
209-
sinon.stub(request, 'get').callsFake(async (opts) => {
210-
if ((opts.url === `https://contoso-dev.api.crm4.dynamics.com/api/data/v9.0/solutions?$filter=isvisible eq true and uniquename eq 'Default'&$expand=publisherid($select=friendlyname)&$select=solutionid,uniquename,version,publisherid,installedon,solutionpackageversion,friendlyname,versionnumber&api-version=9.1`)) {
211-
if ((opts.headers?.accept as string).indexOf('application/json') === 0) {
212-
throw {
213-
error: {
214-
'odata.error': {
215-
code: '-1, InvalidOperationException',
216-
message: {
217-
value: `Resource '' does not exist or one of its queried reference-property objects are not present`
218-
}
219-
}
220-
}
221-
};
182+
sinon.stub(powerPlatform, 'getSolutionByName').rejects({
183+
error: {
184+
'odata.error': {
185+
code: '-1, InvalidOperationException',
186+
message: {
187+
value: `Resource '' does not exist or one of its queried reference-property objects are not present`
188+
}
222189
}
223190
}
224-
225191
});
226192

227193
await assert.rejects(command.action(logger, { options: { environmentName: '4be50206-9576-4237-8b17-38d8aadfaa36', name: 'Default' } } as any),

src/m365/pp/commands/solution/solution-get.ts

Lines changed: 7 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,7 @@ class PpSolutionGetCommand extends PowerPlatformCommand {
8989

9090
try {
9191
const dynamicsApiUrl = await powerPlatform.getDynamicsInstanceApiUrl(args.options.environmentName, args.options.asAdmin);
92+
9293
const res = await this.getSolution(dynamicsApiUrl, args.options);
9394

9495
if (!args.options.output || !cli.shouldTrimOutput(args.options.output)) {
@@ -109,28 +110,20 @@ class PpSolutionGetCommand extends PowerPlatformCommand {
109110
}
110111

111112
private async getSolution(dynamicsApiUrl: string, options: Options): Promise<Solution> {
113+
if (options.name) {
114+
return powerPlatform.getSolutionByName(dynamicsApiUrl, options.name);
115+
}
116+
112117
const requestOptions: CliRequestOptions = {
113118
headers: {
114119
accept: 'application/json;odata.metadata=none'
115120
},
116121
responseType: 'json'
117122
};
118123

119-
if (options.id) {
120-
requestOptions.url = `${dynamicsApiUrl}/api/data/v9.0/solutions(${options.id})?$expand=publisherid($select=friendlyname)&$select=solutionid,uniquename,version,publisherid,installedon,solutionpackageversion,friendlyname,versionnumber&api-version=9.1`;
121-
122-
const result = await request.get<Solution>(requestOptions);
123-
return result;
124-
}
125-
126-
requestOptions.url = `${dynamicsApiUrl}/api/data/v9.0/solutions?$filter=isvisible eq true and uniquename eq \'${options.name}\'&$expand=publisherid($select=friendlyname)&$select=solutionid,uniquename,version,publisherid,installedon,solutionpackageversion,friendlyname,versionnumber&api-version=9.1`;
127-
const result = await request.get<{ value: Solution[] }>(requestOptions);
128-
129-
if (result.value.length === 0) {
130-
throw `The specified solution '${options.name}' does not exist.`;
131-
}
124+
requestOptions.url = `${dynamicsApiUrl}/api/data/v9.0/solutions(${options.id})?$expand=publisherid($select=friendlyname)&$select=solutionid,uniquename,version,publisherid,installedon,solutionpackageversion,friendlyname,versionnumber&api-version=9.1`;
132125

133-
return result.value[0];
126+
return request.get<Solution>(requestOptions);
134127
}
135128
}
136129

src/utils/powerPlatform.spec.ts

Lines changed: 1 addition & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -6,12 +6,8 @@ import { powerPlatform } from './powerPlatform.js';
66
import { sinonUtil } from "./sinonUtil.js";
77
import { cli } from '../cli/cli.js';
88
import { settingsNames } from '../settingsNames.js';
9-
import { Logger } from '../cli/Logger.js';
109

1110
describe('utils/powerPlatform', () => {
12-
let logger: Logger;
13-
let log: string[];
14-
1511
//#region Mocked responses
1612
const environment = 'Default-727dc1e9-3cd1-4d1f-8102-ab5c936e52f0';
1713
const powerPageResponse = {
@@ -187,51 +183,6 @@ describe('utils/powerPlatform', () => {
187183
sinon.stub(cli, 'getSettingWithDefaultValue').callsFake((settingName, defaultValue) => settingName === settingsNames.prompt ? false : defaultValue);
188184
});
189185

190-
beforeEach(() => {
191-
log = [];
192-
logger = {
193-
log: async (msg: string) => {
194-
log.push(msg);
195-
},
196-
logRaw: async (msg: string) => {
197-
log.push(msg);
198-
},
199-
logToStderr: async (msg: string) => {
200-
log.push(msg);
201-
}
202-
};
203-
});
204-
205-
beforeEach(() => {
206-
log = [];
207-
logger = {
208-
log: async (msg: string) => {
209-
log.push(msg);
210-
},
211-
logRaw: async (msg: string) => {
212-
log.push(msg);
213-
},
214-
logToStderr: async (msg: string) => {
215-
log.push(msg);
216-
}
217-
};
218-
});
219-
220-
beforeEach(() => {
221-
log = [];
222-
logger = {
223-
log: async (msg: string) => {
224-
log.push(msg);
225-
},
226-
logRaw: async (msg: string) => {
227-
log.push(msg);
228-
},
229-
logToStderr: async (msg: string) => {
230-
log.push(msg);
231-
}
232-
};
233-
});
234-
235186
afterEach(() => {
236187
sinonUtil.restore([
237188
request.get,
@@ -458,7 +409,7 @@ describe('utils/powerPlatform', () => {
458409
throw `Invalid request ${opts.url}`;
459410
});
460411

461-
const actual = await powerPlatform.getCardByName(envUrl, validCardName, logger, true);
412+
const actual = await powerPlatform.getCardByName(envUrl, validCardName);
462413
assert.strictEqual(actual, cardResponse.value[0]);
463414
});
464415

src/utils/powerPlatform.ts

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
import { cli } from "../cli/cli.js";
2-
import { Logger } from "../cli/Logger.js";
32
import request, { CliRequestOptions } from "../request.js";
43
import { formatting } from "./formatting.js";
54
import { odata } from "./odata.js";
@@ -117,11 +116,7 @@ export const powerPlatform = {
117116
* @param logger The logger object
118117
* @param verbose Set for verbose logging
119118
*/
120-
async getCardByName(dynamicsApiUrl: string, name: string, logger?: Logger, verbose?: boolean): Promise<any> {
121-
if (verbose && logger) {
122-
await logger.logToStderr(`Retrieving the card with name ${name}`);
123-
}
124-
119+
async getCardByName(dynamicsApiUrl: string, name: string): Promise<any> {
125120
const requestOptions: CliRequestOptions = {
126121
url: `${dynamicsApiUrl}/api/data/v9.1/cards?$filter=name eq '${name}'`,
127122
headers: {

0 commit comments

Comments
 (0)