@pega/custom-dx-components 8.8.14 → 8.8.16

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pega/custom-dx-components",
3
- "version": "8.8.14",
3
+ "version": "8.8.16",
4
4
  "description": "Utility for building custom UI components",
5
5
  "bin": "./bin/index.js",
6
6
  "scripts": {
@@ -13,15 +13,15 @@
13
13
  "type": "module",
14
14
  "sideEffects": false,
15
15
  "dependencies": {
16
- "@babel/core": "^7.19.1",
16
+ "@babel/core": "^7.22.5",
17
17
  "@babel/plugin-proposal-class-properties": "^7.18.6",
18
- "@babel/preset-env": "^7.19.1",
19
- "@babel/preset-react": "^7.18.6",
18
+ "@babel/preset-env": "^7.22.5",
19
+ "@babel/preset-react": "^7.22.5",
20
20
  "adm-zip": "^0.5.9",
21
21
  "ajv": "^8.12.0",
22
22
  "ajv-keywords": "^5.1.0",
23
23
  "arg": "^5.0.2",
24
- "babel-loader": "^8.2.5",
24
+ "babel-loader": "^9.1.2",
25
25
  "chalk": "^5.0.1",
26
26
  "compression-webpack-plugin": "^10.0.0",
27
27
  "css-loader": "6.7.1",
@@ -62,9 +62,9 @@
62
62
  "custom-components"
63
63
  ],
64
64
  "devDependencies": {
65
- "@pega/configs": "^0.5.3",
65
+ "@pega/configs": "^0.4.0",
66
66
  "@pega/prettier-config": "^0.5.3",
67
- "cspell": "^6.9.0",
67
+ "cspell": "^4.0.23",
68
68
  "prettier": "2.7.1"
69
69
  }
70
70
  }
package/src/auth.js CHANGED
@@ -31,7 +31,7 @@ class PegaAuth {
31
31
  obj = JSON.parse(peConfig);
32
32
  } catch (e) {
33
33
  try {
34
- obj = JSON.parse(this.#atob(peConfig));
34
+ obj = JSON.parse(atob(peConfig));
35
35
  } catch (err) {
36
36
  obj = {};
37
37
  }
@@ -42,7 +42,7 @@ class PegaAuth {
42
42
 
43
43
  #updateConfig() {
44
44
  if (this.ssKeyConfig) {
45
- window.sessionStorage.setItem(this.ssKeyConfig, this.#btoa(JSON.stringify(this.config)));
45
+ window.sessionStorage.setItem(this.ssKeyConfig, btoa(JSON.stringify(this.config)));
46
46
  }
47
47
  }
48
48
 
@@ -119,7 +119,7 @@ class PegaAuth {
119
119
  const sessionIndexArg =
120
120
  sessionIndex && this.config.sessionIndexAttempts < 3 ? `&session_index=${sessionIndex}` : '';
121
121
  const userIdentifierArg = userIdentifier ? `&UserIdentifier=${encodeURIComponent(userIdentifier)}` : '';
122
- const passwordArg = password && userIdentifier ? `&Password=${encodeURIComponent(window.atob(password))}` : '';
122
+ const passwordArg = password && userIdentifier ? `&Password=${encodeURIComponent(atob(password))}` : '';
123
123
  const moreAuthArgs = bInfinity
124
124
  ? `&enable_psyncid=true${authServiceArg}${sessionIndexArg}${userIdentifierArg}${passwordArg}`
125
125
  : `&isolationID=${isolationId}`;
@@ -137,10 +137,14 @@ class PegaAuth {
137
137
  // Deferring dynamic loading of node libraries til this first method to avoid doing this in constructor
138
138
  await this.#importNodeLibs();
139
139
  }
140
- const { grantType } = this.config;
140
+ const { grantType, noPKCE } = this.config;
141
141
  if (grantType && grantType !== 'authCode') {
142
142
  return this.getToken();
143
143
  }
144
+ // Make sure browser in a secure context, else PKCE will fail
145
+ if (!this.isNode && !noPKCE && !window.isSecureContext) {
146
+ throw (new Error(`Authorization code grant flow failed due to insecure browser context at ${window.location.origin}. Use localhost or https.`));
147
+ }
144
148
  return this.#authCodeStart();
145
149
  }
146
150
 
@@ -155,7 +159,7 @@ class PegaAuth {
155
159
  };
156
160
 
157
161
  const redirectOrigin = fnGetRedirectUriOrigin();
158
- const state = this.isNode ? '' : this.#btoa(window.location.origin);
162
+ const state = this.isNode ? '' : btoa(window.location.origin);
159
163
 
160
164
  return new Promise((resolve, reject) => {
161
165
  this.#buildAuthorizeUrl(state).then((url) => {
@@ -281,7 +285,7 @@ class PegaAuth {
281
285
  const bCloseWithinFrame = false;
282
286
  elCloseBtn = document.createElement('img');
283
287
  elCloseBtn.onclick = fnCloseAndReject;
284
- elCloseBtn.src = `data:image/svg+xml;base64,${this.#btoa(svgCloseBtn)}`;
288
+ elCloseBtn.src = `data:image/svg+xml;base64,${btoa(svgCloseBtn)}`;
285
289
  const oBtnStyle = elCloseBtn.style;
286
290
  oBtnStyle.cursor = 'pointer';
287
291
  // If svg doesn't set width and height might want to set oBtStyle width and height to something like '2em'
@@ -290,9 +294,10 @@ class PegaAuth {
290
294
  oBtnStyle.zIndex = nFrameZLevel + 1;
291
295
  const nTopOffset = bCloseWithinFrame ? 5 : -10;
292
296
  const nRightOffset = bCloseWithinFrame ? -34 : -20;
293
- oBtnStyle.top = `${Math.round(Math.max(window.innerHeight - loginBoxHeight, 0) / 2) + nTopOffset}px`;
294
- oBtnStyle.left = `${Math.round(Math.max(window.innerWidth - loginBoxWidth, 0) / 2) + loginBoxWidth + nRightOffset
295
- }px`;
297
+ const nTop = Math.round(Math.max(window.innerHeight - loginBoxHeight, 0) / 2) + nTopOffset;
298
+ oBtnStyle.top = `${nTop}px`;
299
+ const nLeft = Math.round(Math.max(window.innerWidth - loginBoxWidth, 0) / 2) + loginBoxWidth + nRightOffset;
300
+ oBtnStyle.left = `${nLeft}px`;
296
301
  document.body.insertBefore(elCloseBtn, document.body.firstChild);
297
302
  // If the password was wrong, then the login screen will be in the iframe
298
303
  // ..and with Pega without realization of US-372314 it may replace the top (main portal) window
@@ -437,7 +442,7 @@ class PegaAuth {
437
442
  }
438
443
  if (grantType === 'passwordCreds') {
439
444
  formData.append('username', userIdentifier);
440
- formData.append('password', this.#atob(password));
445
+ formData.append('password', atob(password));
441
446
  }
442
447
 
443
448
  return fetch(tokenUri, {
@@ -536,7 +541,7 @@ class PegaAuth {
536
541
 
537
542
  const hdrs = { 'content-type': this.urlencoded };
538
543
  if (clientSecret) {
539
- const basicCreds = window.btoa(`${clientId}:${clientSecret}`);
544
+ const basicCreds = btoa(`${clientId}:${clientSecret}`);
540
545
  hdrs.authorization = `Basic ${basicCreds}`;
541
546
  }
542
547
  const aTknProps = ['access_token'];
@@ -584,25 +589,9 @@ class PegaAuth {
584
589
  return this.subtle.digest('SHA-256', new TextEncoder().encode(str));
585
590
  }
586
591
 
587
- /* btoa to work with node or browser - create B64 string */
588
- #btoa(str) {
589
- if (this.isNode) {
590
- return Buffer.from(str, 'binary').toString('base64');
591
- }
592
- return window.btoa(str);
593
- }
594
-
595
- /* atoa to work with node or browser - convert B64 to binary */
596
- #atob(str) {
597
- if (this.isNode) {
598
- return Buffer.from(str, 'base64').toString('binary');
599
- }
600
- return window.atob(str);
601
- }
602
-
603
592
  // Base64 encode
604
593
  #encode64(buff) {
605
- return this.#btoa(new Uint8Array(buff).reduce((s, b) => s + String.fromCharCode(b), ''));
594
+ return btoa(new Uint8Array(buff).reduce((s, b) => s + String.fromCharCode(b), ''));
606
595
  }
607
596
 
608
597
  /*
package/src/cli.js CHANGED
@@ -51,7 +51,7 @@ const parseArgumentsIntoOptions = rawArgs => {
51
51
  task: args._[0],
52
52
  git: true, // args['--git'] || false
53
53
  runInstall: true, // args['--install'] || false
54
- skipBundle: false,
54
+ skipBundle: args['--skipBundle'] || false,
55
55
  params: rawArgs
56
56
  };
57
57
  };
@@ -16,6 +16,12 @@ import { PUBLISH_COMPONENT_SERVICE_REST_ENDPOINT, TOKEN_PATH } from '../../const
16
16
 
17
17
  export const getPublishComponentQuestions = async () => {
18
18
  const components = await getComponents();
19
+
20
+ if (components.length == 0) {
21
+ console.log(chalk.redBright("No components to build"));
22
+ process.exit(1);
23
+ }
24
+
19
25
  const defaultPegaConfig = await getPegaServerConfig();
20
26
 
21
27
  return [
@@ -32,7 +32,7 @@ export const getBuildComponentQuestions = async () => {
32
32
  const defaultPegaConfig = await getPegaServerConfig();
33
33
 
34
34
  if (components.length == 0) {
35
- console.log(chalk.bold.yellow(`No components to build`));
35
+ console.log(chalk.redBright("No components to build"));
36
36
  process.exit(1);
37
37
  }
38
38
 
@@ -10,7 +10,7 @@ import { getComponentDirectoryPath, showVersion, getComponents } from '../../uti
10
10
  import { getBuildComponentQuestions, cleanUp } from './helper.js';
11
11
 
12
12
 
13
- export function getCustomTasks(componentKey, sourceMap, devBuild) {
13
+ export function getCustomTasks(componentKey, sourceMap, devBuild, options) {
14
14
 
15
15
  const sDevBuild = devBuild ? '(dev build)' : '';
16
16
  return new Listr(
@@ -32,6 +32,7 @@ export function getCustomTasks(componentKey, sourceMap, devBuild) {
32
32
  {
33
33
  title: `Bundle component ${sDevBuild}`,
34
34
  task: async () => bundleComponent(componentKey, sourceMap, devBuild),
35
+ skip: () => (options.skipBundle ? 'Skipped bundling component' : undefined)
35
36
  }
36
37
  ],
37
38
  {
@@ -45,7 +46,7 @@ export function getCustomTasks(componentKey, sourceMap, devBuild) {
45
46
 
46
47
 
47
48
 
48
- export default async () => {
49
+ export default async (options) => {
49
50
  showVersion();
50
51
 
51
52
 
@@ -58,7 +59,7 @@ export default async () => {
58
59
  for (const componentKey of components) {
59
60
  console.log(chalk.bold.green(`Building ${componentKey}`));
60
61
 
61
- const myCustomTasks = getCustomTasks(componentKey, sourceMap, devBuild );
62
+ const myCustomTasks = getCustomTasks(componentKey, sourceMap, devBuild, options );
62
63
 
63
64
  // eslint-disable-next-line no-await-in-loop
64
65
  await myCustomTasks.run().catch(err => {
@@ -6,9 +6,7 @@
6
6
  "main": "src/index.js",
7
7
  "scripts": {
8
8
  "startStorybook": "start-storybook --port 6040 --quiet",
9
- "build": "tsc -b tsconfig.build.json",
10
9
  "lint": "run-p -cl lint:*",
11
- "fix": "run-p -cl fix:*",
12
10
  "authenticate": "custom-dx-components authenticate",
13
11
  "buildComponent": "custom-dx-components buildComponent",
14
12
  "buildAllComponents": "custom-dx-components buildAllComponents",
@@ -26,7 +24,11 @@
26
24
  "lint:es": "eslint .",
27
25
  "lint:styles": "stylelint \"./**/*.@(js|jsx|ts|tsx)\"",
28
26
  "lint:format": "prettier -c .",
29
- "lint:spelling": "cspell --no-progress **/*",
27
+ "lint:spelling": "cspell --no-progress **/*"
28
+ },
29
+ "scriptsComments": {
30
+ "build": "tsc -b tsconfig.build.json",
31
+ "fix": "run-p -cl fix:*",
30
32
  "fix:es": "eslint --fix .",
31
33
  "fix:format": "prettier -w ."
32
34
  },
@@ -56,7 +58,7 @@
56
58
  },
57
59
  "devDependencies": {
58
60
  "@pega/configs": "^0.5.3",
59
- "@pega/custom-dx-components": "^8.8.14",
61
+ "@pega/custom-dx-components": "^8.8.16",
60
62
  "@pega/eslint-config": "^0.3.2",
61
63
  "@storybook/addon-actions": "^6.5.12",
62
64
  "@storybook/addon-essentials": "^6.5.12",
@@ -83,6 +85,7 @@
83
85
  "eslint-plugin-sonarjs": "^0.11.0",
84
86
  "jest": "^29.3.1",
85
87
  "jest-environment-jsdom": "^29.3.1",
88
+ "npm-quick-run": "^1.18.0",
86
89
  "npm-run-all": "^4.1.5",
87
90
  "prettier": "2.7.1",
88
91
  "stylelint": "^14.11.0",
@@ -21,6 +21,12 @@ import {
21
21
 
22
22
  export const getPublishComponentQuestions = async () => {
23
23
  const components = await getComponents();
24
+
25
+ if (components.length == 0) {
26
+ console.log(chalk.redBright("No components to publish"));
27
+ process.exit(1);
28
+ }
29
+
24
30
  const defaultPegaConfig = await getPegaServerConfig();
25
31
 
26
32
  return [
@@ -63,6 +63,12 @@ export default async options => {
63
63
  showVersion();
64
64
 
65
65
  const components = await getComponents();
66
+
67
+ if (components.length == 0) {
68
+ console.log(chalk.redBright("No components to publish"));
69
+ process.exit(1);
70
+ }
71
+
66
72
  const questions = await getPublishComponentQuestions();
67
73
  const answers = await inquirer.prompt(questions);
68
74
  const { sourceMap, devBuild } = answers;