@pega/react-sdk-overrides 0.23.26 → 0.23.28

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.
Files changed (238) hide show
  1. package/LICENSE +201 -0
  2. package/README.md +17 -0
  3. package/SECURITY.md +10 -0
  4. package/lib/designSystemExtension/AlertBanner/AlertBanner.tsx +39 -0
  5. package/lib/designSystemExtension/AlertBanner/index.tsx +1 -0
  6. package/lib/designSystemExtension/Banner/Banner.tsx +21 -7
  7. package/lib/designSystemExtension/CaseSummaryFields/CaseSummaryFields.css +0 -1
  8. package/lib/designSystemExtension/CaseSummaryFields/CaseSummaryFields.tsx +36 -26
  9. package/lib/designSystemExtension/DetailsFields/DetailsFields.tsx +21 -28
  10. package/lib/designSystemExtension/DetailsFields/index.tsx +1 -1
  11. package/lib/designSystemExtension/FieldGroup/FieldGroup.tsx +50 -18
  12. package/lib/designSystemExtension/FieldGroupList/FieldGroupList.tsx +13 -12
  13. package/lib/designSystemExtension/FieldValueList/FieldValueList.tsx +18 -27
  14. package/lib/designSystemExtension/Operator/Operator.tsx +106 -87
  15. package/lib/designSystemExtension/Pulse/Pulse.tsx +21 -19
  16. package/lib/designSystemExtension/RichTextEditor/RichTextEditor.tsx +122 -0
  17. package/lib/designSystemExtension/RichTextEditor/index.tsx +1 -0
  18. package/lib/designSystemExtension/WssQuickCreate/WssQuickCreate.tsx +21 -12
  19. package/lib/field/AutoComplete/AutoComplete.tsx +33 -16
  20. package/lib/field/AutoComplete/config-ext.json +2 -3
  21. package/lib/field/CancelAlert/CancelAlert.tsx +21 -15
  22. package/lib/field/CancelAlert/index.tsx +1 -1
  23. package/lib/field/Checkbox/Checkbox.tsx +29 -19
  24. package/lib/field/Checkbox/config-ext.json +2 -3
  25. package/lib/field/Currency/Currency.tsx +27 -38
  26. package/lib/field/Currency/config-ext.json +2 -3
  27. package/lib/field/Currency/currency-utils.ts +10 -18
  28. package/lib/field/Date/Date.tsx +33 -15
  29. package/lib/field/Date/config-ext.json +2 -3
  30. package/lib/field/DateTime/DateTime.tsx +22 -11
  31. package/lib/field/DateTime/config-ext.json +1 -2
  32. package/lib/field/Decimal/Decimal.tsx +64 -17
  33. package/lib/field/Decimal/config-ext.json +1 -2
  34. package/lib/field/Decimal/index.tsx +1 -1
  35. package/lib/field/Dropdown/Dropdown.tsx +154 -18
  36. package/lib/field/Dropdown/config-ext.json +1 -2
  37. package/lib/field/Email/Email.tsx +16 -7
  38. package/lib/field/Email/config-ext.json +1 -2
  39. package/lib/field/Email/index.tsx +1 -1
  40. package/lib/field/Group/Group.tsx +37 -0
  41. package/lib/field/Group/config-ext.json +7 -0
  42. package/lib/field/Group/index.tsx +1 -0
  43. package/lib/field/Integer/Integer.tsx +15 -6
  44. package/lib/field/Integer/config-ext.json +1 -2
  45. package/lib/field/Percentage/Percentage.tsx +14 -6
  46. package/lib/field/Percentage/config-ext.json +1 -2
  47. package/lib/field/Phone/Phone.tsx +17 -7
  48. package/lib/field/Phone/index.tsx +1 -1
  49. package/lib/field/RadioButtons/RadioButtons.tsx +55 -24
  50. package/lib/field/RadioButtons/config-ext.json +1 -2
  51. package/lib/field/RichText/RichText.tsx +96 -0
  52. package/lib/field/RichText/index.tsx +1 -0
  53. package/lib/field/ScalarList/ScalarList.tsx +63 -0
  54. package/lib/field/ScalarList/config-ext.json +7 -0
  55. package/lib/field/ScalarList/index.tsx +1 -0
  56. package/lib/field/SemanticLink/SemanticLink.tsx +26 -25
  57. package/lib/field/SemanticLink/config-ext.json +1 -2
  58. package/lib/field/SemanticLink/utils.ts +8 -10
  59. package/lib/field/TextArea/TextArea.tsx +15 -5
  60. package/lib/field/TextArea/config-ext.json +1 -2
  61. package/lib/field/TextContent/TextContent.tsx +9 -2
  62. package/lib/field/TextContent/config-ext.json +1 -2
  63. package/lib/field/TextInput/TextInput.tsx +41 -10
  64. package/lib/field/TextInput/config-ext.json +1 -2
  65. package/lib/field/TextInput/index.tsx +1 -1
  66. package/lib/field/Time/Time.tsx +21 -18
  67. package/lib/field/Time/config-ext.json +1 -2
  68. package/lib/field/URL/URL.tsx +23 -6
  69. package/lib/field/URL/config-ext.json +1 -2
  70. package/lib/field/URL/index.tsx +1 -1
  71. package/lib/field/UserReference/UserReference.tsx +52 -58
  72. package/lib/field/UserReference/UserReferenceUtils.ts +2 -2
  73. package/lib/field/UserReference/config-ext.json +1 -2
  74. package/lib/helpers/{attachmentHelpers.js → attachmentHelpers.ts} +16 -11
  75. package/lib/helpers/case-utils.tsx +99 -0
  76. package/lib/helpers/common-utils.ts +8 -0
  77. package/lib/helpers/data_page.ts +3 -6
  78. package/lib/helpers/date-format-utils.ts +29 -19
  79. package/lib/helpers/{event-utils.js → event-utils.ts} +4 -4
  80. package/lib/helpers/{field-group-utils.js → field-group-utils.ts} +9 -10
  81. package/lib/helpers/formatters/Boolean.ts +21 -0
  82. package/lib/helpers/formatters/{Currency.js → Currency.ts} +22 -27
  83. package/lib/helpers/formatters/CurrencyMap.ts +915 -0
  84. package/lib/helpers/formatters/{Date.js → Date.ts} +20 -26
  85. package/lib/helpers/formatters/{common.js → common.ts} +3 -4
  86. package/lib/helpers/formatters/{index.js → index.ts} +22 -22
  87. package/lib/helpers/{reactContextHelpers.js → reactContextHelpers.ts} +2 -2
  88. package/lib/helpers/simpleTableHelpers.ts +65 -85
  89. package/lib/helpers/state-utils.tsx +43 -0
  90. package/lib/helpers/template-utils.ts +4 -8
  91. package/lib/helpers/utils.ts +16 -8
  92. package/lib/helpers/versionHelpers.ts +1 -5
  93. package/lib/infra/ActionButtons/ActionButtons.tsx +46 -42
  94. package/lib/infra/ActionButtons/index.tsx +1 -1
  95. package/lib/infra/Assignment/Assignment.tsx +99 -84
  96. package/lib/infra/Assignment/index.tsx +1 -1
  97. package/lib/infra/AssignmentCard/AssignmentCard.tsx +19 -26
  98. package/lib/infra/AssignmentCard/index.tsx +1 -1
  99. package/lib/infra/Containers/FlowContainer/FlowContainer.tsx +98 -232
  100. package/lib/infra/Containers/FlowContainer/helpers.ts +138 -0
  101. package/lib/infra/Containers/FlowContainer/index.tsx +1 -1
  102. package/lib/infra/Containers/ModalViewContainer/ListViewActionButtons/ListViewActionButtons.tsx +66 -0
  103. package/lib/infra/Containers/ModalViewContainer/ListViewActionButtons/index.tsx +1 -0
  104. package/lib/infra/Containers/ModalViewContainer/ModalViewContainer.tsx +105 -70
  105. package/lib/infra/Containers/ModalViewContainer/index.tsx +1 -1
  106. package/lib/infra/Containers/SimpleView/SimpleView.tsx +48 -0
  107. package/lib/infra/Containers/SimpleView/helper.ts +125 -0
  108. package/lib/infra/Containers/SimpleView/index.tsx +1 -0
  109. package/lib/infra/Containers/ViewContainer/ViewContainer.tsx +49 -64
  110. package/lib/infra/Containers/helpers.ts +6 -0
  111. package/lib/infra/DashboardFilter/DashboardFilter.tsx +26 -51
  112. package/lib/infra/DashboardFilter/filterUtils.tsx +12 -40
  113. package/lib/infra/DeferLoad/DeferLoad.tsx +22 -31
  114. package/lib/infra/DeferLoad/index.tsx +1 -1
  115. package/lib/infra/ErrorBoundary/ErrorBoundary.tsx +25 -38
  116. package/lib/infra/MultiStep/MultiStep.css +11 -15
  117. package/lib/infra/MultiStep/MultiStep.tsx +180 -216
  118. package/lib/infra/MultiStep/index.tsx +1 -1
  119. package/lib/infra/NavBar/NavBar.css +103 -105
  120. package/lib/infra/NavBar/NavBar.tsx +28 -43
  121. package/lib/infra/Reference/Reference.tsx +16 -22
  122. package/lib/infra/Region/Region.tsx +9 -9
  123. package/lib/infra/RootContainer/RootContainer.tsx +82 -125
  124. package/lib/infra/RootContainer/index.tsx +1 -1
  125. package/lib/infra/Stages/Stages.tsx +38 -39
  126. package/lib/infra/VerticalTabs/LeftAlignVerticalTabs/LeftAlignVerticalTabs.tsx +17 -10
  127. package/lib/infra/VerticalTabs/VerticalTabs/VerticalTabs.tsx +29 -36
  128. package/lib/infra/View/View.tsx +32 -63
  129. package/lib/template/AppShell/AppShell.css +22 -23
  130. package/lib/template/AppShell/AppShell.tsx +51 -69
  131. package/lib/template/BannerPage/BannerPage.tsx +26 -33
  132. package/lib/template/CaseSummary/CaseSummary.tsx +23 -18
  133. package/lib/template/CaseSummary/config-ext.json +1 -2
  134. package/lib/template/CaseView/CaseView.tsx +122 -114
  135. package/lib/template/CaseView/config-ext.json +1 -2
  136. package/lib/template/CaseViewActionsMenu/CaseViewActionsMenu.tsx +46 -35
  137. package/lib/template/Confirmation/Confirmation.tsx +25 -53
  138. package/lib/template/Confirmation/config-ext.json +1 -2
  139. package/lib/template/DataReference/DataReference.tsx +112 -140
  140. package/lib/template/DataReference/config-ext.json +1 -2
  141. package/lib/template/DefaultForm/DefaultForm.css +7 -3
  142. package/lib/template/DefaultForm/DefaultForm.tsx +26 -20
  143. package/lib/template/DefaultForm/config-ext.json +1 -2
  144. package/lib/template/DefaultForm/utils/index.ts +33 -0
  145. package/lib/template/Details/Details/Details.tsx +24 -28
  146. package/lib/template/Details/DetailsSubTabs/DetailsSubTabs.tsx +15 -22
  147. package/lib/template/Details/DetailsSubTabs/config-ext.json +1 -2
  148. package/lib/template/Details/DetailsThreeColumn/DetailsThreeColumn.tsx +25 -29
  149. package/lib/template/Details/DetailsThreeColumn/config-ext.json +1 -2
  150. package/lib/template/Details/DetailsTwoColumn/DetailsTwoColumn.tsx +25 -29
  151. package/lib/template/Details/DetailsTwoColumn/config-ext.json +1 -2
  152. package/lib/template/Details/DetailsTwoColumn/index.tsx +1 -1
  153. package/lib/template/Details/DynamicTabs/DynamicTabs.tsx +79 -0
  154. package/lib/template/Details/DynamicTabs/config.json +36 -0
  155. package/lib/template/Details/DynamicTabs/index.tsx +1 -0
  156. package/lib/template/FieldGroupTemplate/FieldGroupTemplate.tsx +24 -34
  157. package/lib/template/InlineDashboard/InlineDashboard.tsx +16 -14
  158. package/lib/template/InlineDashboardPage/InlineDashboardPage.tsx +19 -21
  159. package/lib/template/ListPage/ListPage.tsx +12 -16
  160. package/lib/template/ListPage/config-ext.json +1 -2
  161. package/lib/template/ListView/{DefaultViewMeta.js → DefaultViewMeta.ts} +1 -3
  162. package/lib/template/ListView/ListView.tsx +245 -306
  163. package/lib/template/ListView/config-ext.json +1 -2
  164. package/lib/template/ListView/{hooks.js → hooks.ts} +24 -24
  165. package/lib/template/ListView/{utils.js → utils.ts} +202 -91
  166. package/lib/template/MultiReferenceReadOnly/MultiReferenceReadOnly.tsx +25 -30
  167. package/lib/template/NarrowWide/NarrowWide/NarrowWide.css +0 -2
  168. package/lib/template/NarrowWide/NarrowWide/NarrowWide.tsx +31 -29
  169. package/lib/template/NarrowWide/NarrowWideDetails/NarrowWideDetails.tsx +27 -31
  170. package/lib/template/NarrowWide/NarrowWideDetails/config-ext.json +1 -2
  171. package/lib/template/NarrowWide/NarrowWideForm/NarrowWideForm.css +0 -2
  172. package/lib/template/NarrowWide/NarrowWideForm/NarrowWideForm.tsx +17 -19
  173. package/lib/template/NarrowWide/NarrowWideForm/config-ext.json +1 -2
  174. package/lib/template/NarrowWide/NarrowWidePage/NarrowWidePage.tsx +16 -26
  175. package/lib/template/NarrowWide/NarrowWidePage/config-ext.json +1 -2
  176. package/lib/template/OneColumn/OneColumn/OneColumn.tsx +17 -17
  177. package/lib/template/OneColumn/OneColumn/config-ext.json +1 -2
  178. package/lib/template/OneColumn/OneColumnPage/OneColumnPage.tsx +9 -16
  179. package/lib/template/OneColumn/OneColumnPage/config-ext.json +1 -2
  180. package/lib/template/OneColumn/OneColumnTab/OneColumnTab.tsx +8 -14
  181. package/lib/template/OneColumn/OneColumnTab/config-ext.json +1 -2
  182. package/lib/template/PromotedFilters/PromotedFilters.css +1 -1
  183. package/lib/template/PromotedFilters/PromotedFilters.tsx +44 -34
  184. package/lib/template/SimpleTable/SimpleTable/SimpleTable.tsx +115 -14
  185. package/lib/template/SimpleTable/SimpleTable/config-ext.json +1 -2
  186. package/lib/template/SimpleTable/SimpleTableManual/SimpleTableManual.tsx +171 -100
  187. package/lib/template/SimpleTable/SimpleTableSelect/SimpleTableSelect.tsx +34 -40
  188. package/lib/template/SingleReferenceReadOnly/SingleReferenceReadOnly.tsx +45 -48
  189. package/lib/template/SubTabs/SubTabs.tsx +26 -45
  190. package/lib/template/SubTabs/config-ext.json +1 -2
  191. package/lib/template/SubTabs/tabUtils.ts +2 -7
  192. package/lib/template/TwoColumn/TwoColumn/TwoColumn.css +0 -1
  193. package/lib/template/TwoColumn/TwoColumn/TwoColumn.tsx +33 -36
  194. package/lib/template/TwoColumn/TwoColumn/config-ext.json +1 -2
  195. package/lib/template/TwoColumn/TwoColumnPage/TwoColumnPage.tsx +9 -16
  196. package/lib/template/TwoColumn/TwoColumnPage/config-ext.json +1 -2
  197. package/lib/template/TwoColumn/TwoColumnTab/TwoColumnTab.tsx +33 -33
  198. package/lib/template/TwoColumn/TwoColumnTab/config-ext.json +1 -2
  199. package/lib/template/WideNarrow/WideNarrow/WideNarrow.css +0 -2
  200. package/lib/template/WideNarrow/WideNarrow/WideNarrow.tsx +29 -27
  201. package/lib/template/WideNarrow/WideNarrowDetails/WideNarrowDetails.tsx +39 -33
  202. package/lib/template/WideNarrow/WideNarrowDetails/config-ext.json +1 -2
  203. package/lib/template/WideNarrow/WideNarrowForm/WideNarrowForm.css +0 -2
  204. package/lib/template/WideNarrow/WideNarrowForm/WideNarrowForm.tsx +16 -18
  205. package/lib/template/WideNarrow/WideNarrowForm/config-ext.json +1 -2
  206. package/lib/template/WideNarrow/WideNarrowPage/WideNarrowPage.tsx +15 -25
  207. package/lib/template/WideNarrow/WideNarrowPage/config-ext.json +1 -2
  208. package/lib/template/WideNarrow/WideNarrowPage/index.tsx +1 -1
  209. package/lib/template/WssNavBar/WssNavBar.tsx +20 -9
  210. package/lib/widget/AppAnnouncement/AppAnnouncement.tsx +34 -41
  211. package/lib/widget/AppAnnouncement/config-ext.json +1 -2
  212. package/lib/widget/Attachment/Attachment.css +75 -4
  213. package/lib/widget/Attachment/Attachment.tsx +370 -388
  214. package/lib/widget/Attachment/index.tsx +1 -1
  215. package/lib/widget/CaseHistory/CaseHistory.tsx +67 -67
  216. package/lib/widget/CaseHistory/config-ext.json +1 -2
  217. package/lib/widget/CaseHistory/index.tsx +1 -1
  218. package/lib/widget/FileUtility/ActionButtonsForFileUtil/ActionButtonsForFileUtil.tsx +19 -9
  219. package/lib/widget/FileUtility/FileUtility/FileUtility.css +2 -2
  220. package/lib/widget/FileUtility/FileUtility/FileUtility.tsx +324 -246
  221. package/lib/widget/FileUtility/FileUtility/config-ext.json +1 -2
  222. package/lib/widget/Followers/Followers.tsx +27 -25
  223. package/lib/widget/Followers/config-ext.json +1 -2
  224. package/lib/widget/QuickCreate/QuickCreate.tsx +24 -16
  225. package/lib/widget/SummaryItem/SummaryItem.css +9 -9
  226. package/lib/widget/SummaryItem/SummaryItem.tsx +62 -54
  227. package/lib/widget/SummaryItem/index.tsx +1 -1
  228. package/lib/widget/SummaryList/SummaryList.tsx +15 -4
  229. package/lib/widget/ToDo/ToDo.css +4 -4
  230. package/lib/widget/ToDo/ToDo.tsx +80 -116
  231. package/lib/widget/ToDo/config-ext.json +1 -2
  232. package/package.json +5 -2
  233. package/lib/helpers/auth.js +0 -483
  234. package/lib/helpers/authManager.js +0 -631
  235. package/lib/helpers/config_access.js +0 -268
  236. package/lib/helpers/formatters/Boolean.js +0 -38
  237. package/lib/helpers/formatters/CurrencyMap.js +0 -908
  238. package/lib/infra/Containers/FlowContainer/helpers.js +0 -147
@@ -1,483 +0,0 @@
1
- class PegaAuth {
2
-
3
- constructor(ssKeyConfig) {
4
- this.ssKeyConfig = ssKeyConfig;
5
- this.bEncodeSI = false;
6
- this.reloadConfig();
7
- }
8
-
9
- reloadConfig() {
10
- const peConfig = window.sessionStorage.getItem(this.ssKeyConfig);
11
- let obj = {};
12
- if( peConfig ) {
13
- try {
14
- obj = JSON.parse(peConfig);
15
- } catch (e) {
16
- try {
17
- obj = JSON.parse(window.atob(peConfig));
18
- } catch(e2) {
19
- obj = {};
20
- }
21
- }
22
- }
23
-
24
- this.config = peConfig ? obj : null;
25
- }
26
-
27
- #updateConfig() {
28
- const sSI = JSON.stringify(this.config);
29
- window.sessionStorage.setItem(this.ssKeyConfig, this.bEncodeSI ? window.btoa(sSI) : sSI);
30
- }
31
-
32
- // For PKCE the authorize includes a code_challenge & code_challenge_method as well
33
- async #buildAuthorizeUrl(state) {
34
- const {clientId, redirectUri, authorizeUri, authService, sessionIndex, appAlias, useLocking,
35
- userIdentifier, password} = this.config;
36
-
37
- // Generate random string of 64 chars for verifier. RFC 7636 says from 43-128 chars
38
- let buf = new Uint8Array(64);
39
- window.crypto.getRandomValues(buf);
40
- this.config.codeVerifier = this.#base64UrlSafeEncode(buf);
41
- // If sessionIndex exists then increment attempts count (we will stop sending session_index after two failures)
42
- if( sessionIndex ) {
43
- this.config.sessionIndexAttempts += 1;
44
- }
45
- // Persist codeVerifier in session storage so it survives the redirects that are to follow
46
- this.#updateConfig();
47
-
48
- if( !state ) {
49
- // Calc random state variable
50
- buf = new Uint8Array(32);
51
- window.crypto.getRandomValues(buf);
52
- state = this.#base64UrlSafeEncode(buf);
53
- }
54
-
55
- // Trim alias to include just the real alias piece
56
- const addtlScope = appAlias ? `+app.alias.${appAlias.replace(/^app\//, '')}` : "";
57
-
58
- // Add explicit creds if specified to try to avoid login popup
59
- const moreAuthArgs =
60
- (authService ? `&authentication_service=${encodeURIComponent(authService)}` : "") +
61
- (sessionIndex && this.config.sessionIndexAttempts < 3 ? `&session_index=${sessionIndex}` : "") +
62
- (useLocking ? `&enable_psyncId=true` : '') +
63
- (userIdentifier ? `&UserIdentifier=${encodeURIComponent(userIdentifier)}` : '') +
64
- (userIdentifier && password ? `&Password=${encodeURIComponent(window.atob(password))}` : '');
65
-
66
- return this.#getCodeChallenge(this.config.codeVerifier).then( cc => {
67
- // Now includes new enable_psyncId=true and session_index params
68
- return `${authorizeUri}?client_id=${clientId}&response_type=code&redirect_uri=${redirectUri}&scope=openid+email+profile${addtlScope}&state=${state}&code_challenge=${cc}&code_challenge_method=S256${moreAuthArgs}`;
69
- });
70
- }
71
-
72
- async login() {
73
- const fnGetRedirectUriOrigin = () => {
74
- const redirectUri = this.config.redirectUri;
75
- const nRootOffset = redirectUri.indexOf("//");
76
- const nFirstPathOffset = nRootOffset !== -1 ? redirectUri.indexOf("/",nRootOffset+2) : -1;
77
- return nFirstPathOffset !== -1 ? redirectUri.substring(0,nFirstPathOffset) : redirectUri;
78
- };
79
-
80
- const redirectOrigin = fnGetRedirectUriOrigin();
81
- // eslint-disable-next-line no-restricted-globals
82
- const state = window.btoa(location.origin);
83
-
84
- return new Promise( (resolve, reject) => {
85
-
86
- this.#buildAuthorizeUrl(state).then((url) => {
87
- let myWindow = null; // popup or iframe
88
- let elIframe = null;
89
- let elCloseBtn = null
90
- const iframeTimeout = this.config.silentTimeout !== undefined ? this.config.silentTimeout : 5000;
91
- let bWinIframe = iframeTimeout > 0 && ((!!this.config.userIdentifier && !!this.config.password) || this.config.iframeLoginUI || this.config.authService !== "pega");
92
- let tmrAuthComplete = null;
93
- let checkWindowClosed = null;
94
- const myWinOnLoad = () => {
95
- try{
96
- if( bWinIframe ) {
97
- elIframe.contentWindow.postMessage({type:"PegaAuth"}, redirectOrigin);
98
- // eslint-disable-next-line no-console
99
- console.log("authjs(login): loaded a page in iFrame");
100
- } else {
101
- myWindow.postMessage({type:"PegaAuth"}, redirectOrigin);
102
- }
103
- } catch(e) {
104
- // eslint-disable-next-line no-console
105
- console.log("authjs(login): Exception trying to postMessage on load");
106
- }
107
- };
108
- const fnOpenPopup = () => {
109
- myWindow = window.open(url, '_blank', 'width=700,height=500,left=200,top=100');
110
- if( !myWindow ) {
111
- // Blocked by popup-blocker
112
- // eslint-disable-next-line prefer-promise-reject-errors
113
- return reject("blocked");
114
- }
115
- checkWindowClosed = setInterval( () => {
116
- if( myWindow.closed ) {
117
- clearInterval(checkWindowClosed);
118
- // eslint-disable-next-line prefer-promise-reject-errors
119
- reject("closed");
120
- }
121
- }, 500);
122
- try {
123
- myWindow.addEventListener("load", myWinOnLoad, true);
124
- } catch(e) {
125
- // eslint-disable-next-line no-console
126
- console.log("authjs(login): Exception trying to add onload handler to opened window;")
127
- }
128
- };
129
-
130
- const fnCloseIframe = () => {
131
- elIframe.parentNode.removeChild(elIframe);
132
- elCloseBtn.parentNode.removeChild(elCloseBtn);
133
- // eslint-disable-next-line no-multi-assign
134
- elIframe = elCloseBtn = null;
135
- bWinIframe = false;
136
- };
137
- const fnCloseAndReject = () => {
138
- fnCloseIframe();
139
- // eslint-disable-next-line prefer-promise-reject-errors
140
- reject("closed");
141
- };
142
- // If there is a userIdentifier and password specified or an external SSO auth service,
143
- // we can try to use this silently in an iFrame first
144
- if( bWinIframe ) {
145
- const nFrameZLevel = 99999;
146
- elIframe = document.createElement('iframe');
147
- // eslint-disable-next-line prefer-template
148
- elIframe.id = 'pe'+this.config.clientId;
149
- const loginBoxWidth=500;
150
- const loginBoxHeight=700;
151
- const oStyle = elIframe.style;
152
- oStyle.position = 'absolute';
153
- oStyle.display = 'none';
154
- oStyle.zIndex = nFrameZLevel;
155
- oStyle.top=`${Math.round(Math.max(window.innerHeight-loginBoxHeight,0)/2)}px`;
156
- oStyle.left=`${Math.round(Math.max(window.innerWidth-loginBoxWidth,0)/2)}px`;
157
- oStyle.width='500px';
158
- oStyle.height='700px';
159
- // Add Iframe to top of document DOM to have it load
160
- document.body.insertBefore(elIframe,document.body.firstChild);
161
- // Add Iframe to DOM to have it load
162
- document.getElementsByTagName('body')[0].appendChild(elIframe);
163
- elIframe.addEventListener("load", myWinOnLoad, true);
164
- // Disallow iframe content attempts to navigate main window
165
- elIframe.setAttribute("sandbox","allow-scripts allow-forms allow-same-origin");
166
- elIframe.setAttribute('src', url);
167
-
168
- const svgCloseBtn =
169
- `<?xml version="1.0" encoding="UTF-8"?>
170
- <svg width="34px" height="34px" viewBox="0 0 34 34" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
171
- <title>Dismiss - Black</title>
172
- <g stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
173
- <g transform="translate(1.000000, 1.000000)">
174
- <circle fill="#252C32" cx="16" cy="16" r="16"></circle>
175
- <g transform="translate(9.109375, 9.214844)" fill="#FFFFFF" fill-rule="nonzero">
176
- <path d="M12.7265625,0 L0,12.6210938 L1.0546875,13.5703125 L13.78125,1.0546875 L12.7265625,0 Z M13.7460938,12.5507812 L1.01953125,0 L0,1.01953125 L12.7617188,13.6054688 L13.7460938,12.5507812 Z"></path>
177
- </g>
178
- </g>
179
- </g>
180
- </svg>`;
181
- const bCloseWithinFrame = false;
182
- elCloseBtn = document.createElement('img');
183
- elCloseBtn.onclick = fnCloseAndReject;
184
- // eslint-disable-next-line prefer-template
185
- elCloseBtn.src = 'data:image/svg+xml;base64,' + window.btoa(svgCloseBtn);
186
- const oBtnStyle = elCloseBtn.style;
187
- oBtnStyle.cursor = 'pointer';
188
- // If svg doesn't set width and height might want to set oBtStyle width and height to something like '2em'
189
- oBtnStyle.position = 'absolute';
190
- oBtnStyle.display = 'none';
191
- oBtnStyle.zIndex = nFrameZLevel+1;
192
- const nTopOffset = bCloseWithinFrame ? 5 : -10;
193
- const nRightOffset = bCloseWithinFrame ? -34 : -20;
194
- oBtnStyle.top = `${Math.round(Math.max(window.innerHeight-loginBoxHeight,0)/2)+nTopOffset}px`;
195
- oBtnStyle.left = `${Math.round(Math.max(window.innerWidth-loginBoxWidth,0)/2)+loginBoxWidth+nRightOffset}px`;
196
- document.body.insertBefore(elCloseBtn,document.body.firstChild);
197
- // If the password was wrong, then the login screen will be in the iframe
198
- // ..and with Pega without realization of US-372314 it may replace the top (main portal) window
199
- // For now set a timer and if the timer expires, remove the iFrame and use same url within
200
- // visible window
201
- tmrAuthComplete = setTimeout( () => {
202
- clearTimeout(tmrAuthComplete);
203
- // remove password from config
204
- if( this.config.password ) {
205
- delete this.config.password;
206
- this.#updateConfig();
207
- }
208
-
209
- if( this.config.iframeLoginUI ) {
210
- elIframe.style.display="block";
211
- elCloseBtn.style.display="block";
212
- } else {
213
- fnCloseIframe();
214
- fnOpenPopup();
215
- }
216
- }, iframeTimeout);
217
- } else {
218
- fnOpenPopup();
219
- }
220
-
221
- let authMessageReceiver = null;
222
- /* Retrieve token(s) and close login window */
223
- const fnGetTokenAndFinish = (code) => {
224
- window.removeEventListener("message", authMessageReceiver, false);
225
- this.getToken(code).then(token => {
226
- if( bWinIframe ) {
227
- clearTimeout(tmrAuthComplete);
228
- fnCloseIframe();
229
- } else {
230
- clearInterval(checkWindowClosed);
231
- myWindow.close();
232
- }
233
- resolve(token);
234
- })
235
- .catch(e => {
236
- reject(e);
237
- });
238
- };
239
- /* Handler to receive the auth code */
240
- authMessageReceiver = (event) => {
241
- // Check origin to make sure it is the redirect origin
242
- if( event.origin !== redirectOrigin )
243
- return;
244
- if( !event.data || !event.data.type || event.data.type !== "PegaAuth" )
245
- return;
246
- // eslint-disable-next-line no-console
247
- console.log("authjs(login): postMessage received with code");
248
- const code = event.data.code.toString();
249
- fnGetTokenAndFinish(code);
250
- };
251
- window.addEventListener("message", authMessageReceiver, false);
252
- window.authCodeCallback = (code) => {
253
- // eslint-disable-next-line no-console
254
- console.log("authjs(login): authCodeCallback used with code");
255
- fnGetTokenAndFinish(code);
256
- };
257
- });
258
- });
259
- }
260
-
261
- // Login redirect
262
- loginRedirect() {
263
- // eslint-disable-next-line no-restricted-globals
264
- const state = btoa(location.origin);
265
- this.#buildAuthorizeUrl(state).then((url) => {
266
- // eslint-disable-next-line no-restricted-globals
267
- location.href = url;
268
- });
269
- }
270
-
271
-
272
- // For PKCE token endpoint includes code_verifier
273
- getToken(authCode) {
274
- // Reload config to pick up the previously stored codeVerifier
275
- this.reloadConfig();
276
-
277
- const {clientId, clientSecret, redirectUri, tokenUri, codeVerifier} = this.config;
278
-
279
- // eslint-disable-next-line no-restricted-globals
280
- const queryString = location.search;
281
- const urlParams = new URLSearchParams(queryString);
282
- const code = authCode || urlParams.get("code");
283
-
284
- const formData = new URLSearchParams();
285
- formData.append("client_id", clientId);
286
- if( clientSecret ) {
287
- formData.append("client_secret", clientSecret);
288
- }
289
- formData.append("grant_type", "authorization_code");
290
- formData.append("code", code);
291
- formData.append("redirect_uri", redirectUri);
292
- formData.append("code_verifier", codeVerifier);
293
-
294
- return fetch(tokenUri, {
295
- method: "POST",
296
- headers: new Headers({
297
- "content-type": "application/x-www-form-urlencoded",
298
- }),
299
-
300
- body: formData.toString(),
301
- })
302
- .then((response) => response.json())
303
- .then(token => {
304
- // .expires_in contains the # of seconds before access token expires
305
- // add property to keep track of current time when the token expires
306
- token.eA = Date.now() + (token.expires_in * 1000);
307
- if( this.config.codeVerifier ) {
308
- delete this.config.codeVerifier;
309
- }
310
- // If there is a session_index then move this to the peConfig structure (as used on authorize)
311
- if( token.session_index ) {
312
- this.config.sessionIndex = token.session_index;
313
- }
314
- // If we got a token and have a session index, then reset the sessionIndexAttempts
315
- if( this.config.sessionIndex ) {
316
- this.config.sessionIndexAttempts = 0;
317
- }
318
- this.#updateConfig();
319
- return token;
320
- })
321
- .catch(e => {
322
- // eslint-disable-next-line no-console
323
- console.log(e)
324
- });
325
- }
326
-
327
- /* eslint-disable camelcase */
328
- async refreshToken(refresh_token) {
329
- const {clientId, clientSecret, tokenUri} = this.config;
330
-
331
- const formData = new URLSearchParams();
332
- formData.append("client_id", clientId);
333
- if( clientSecret ) {
334
- formData.append("client_secret", clientSecret);
335
- }
336
- formData.append("grant_type", "refresh_token");
337
- formData.append("refresh_token", refresh_token);
338
-
339
- return fetch(tokenUri, {
340
- method: "POST",
341
- headers: new Headers({
342
- "content-type": "application/x-www-form-urlencoded",
343
- }),
344
-
345
- body: formData.toString(),
346
- })
347
- .then((response) => {
348
- if( !response.ok && response.status === 401 ) {
349
- return null;
350
- }
351
- return response.json();
352
- })
353
- .then(token => {
354
- if( token ) {
355
- // .expires_in contains the # of seconds before access token expires
356
- // add property to keep track of current time when the token expires
357
- token.eA = Date.now() + (token.expires_in * 1000);
358
- }
359
- return token;
360
- })
361
- .catch(e => {
362
- // eslint-disable-next-line no-console
363
- console.log(e)
364
- });
365
- }
366
-
367
- async revokeTokens(access_token, refresh_token = null) {
368
- if( !this.config || !this.config.revokeUri) {
369
- // Must have a config structure and revokeUri to proceed
370
- return;
371
- }
372
- const {clientId, clientSecret, revokeUri} = this.config;
373
-
374
- const hdrs = {"content-type":"application/x-www-form-urlencoded"};
375
- if( clientSecret ) {
376
- const creds = `${clientId}:${clientSecret}`;
377
- hdrs.authorization = `Basic ${window.btoa(creds)}`;
378
- }
379
- const aTknProps = ["access_token"];
380
- if( refresh_token ) {
381
- aTknProps.push("refresh_token");
382
- }
383
- aTknProps.forEach( (prop) => {
384
- const formData = new URLSearchParams();
385
- if( !clientSecret ) {
386
- formData.append("client_id", clientId);
387
- }
388
- formData.append("token", prop==="access_token" ? access_token : refresh_token);
389
- formData.append("token_type_hint", prop);
390
- fetch(revokeUri, {
391
- method: "POST",
392
- headers: new Headers(hdrs),
393
- body: formData.toString(),
394
- })
395
- .then((response) => {
396
- if( !response.ok ) {
397
- // eslint-disable-next-line no-console
398
- console.log( `Error revoking ${prop}:${response.status}` );
399
- }
400
- })
401
- .catch(e => {
402
- // eslint-disable-next-line no-console
403
- console.log(e);
404
- });
405
- } );
406
- // Also clobber any sessionIndex
407
- if( this.config.sessionIndex ) {
408
- delete this.config.sessionIndex;
409
- this.#updateConfig();
410
- }
411
- }
412
-
413
- // For userinfo endpoint to return meaningful data, endpoint must include appAlias (if specified) and authorize must
414
- // specify profile and optionally email scope to get such info returned
415
- async getUserinfo(access_token) {
416
- if( !this.config || !this.config.userinfoUri ) {
417
- // Must have a config structure and userInfo to proceed
418
- return {};
419
- }
420
- const hdrs = {'authorization':`bearer ${access_token}`,'content-type':'application/json;charset=UTF-8'};
421
- return fetch(this.config.userinfoUri, {
422
- method: "GET",
423
- headers: new Headers(hdrs)})
424
- .then( response => {
425
- if( response.ok) {
426
- return response.json();
427
- } else {
428
- // eslint-disable-next-line no-console
429
- console.log( `Error invoking userinfo: ${response.status}` );
430
- }
431
- })
432
- .then( data => {
433
- return data;
434
- })
435
- .catch(e => {
436
- // eslint-disable-next-line no-console
437
- console.log(e);
438
- });
439
- }
440
-
441
- /* eslint-enable camelcase */
442
-
443
- // eslint-disable-next-line class-methods-use-this
444
- #sha256Hash(str) {
445
- return window.crypto.subtle.digest("SHA-256", new TextEncoder().encode(str));
446
- }
447
-
448
- // Base64 encode
449
- // eslint-disable-next-line class-methods-use-this
450
- #encode64(buff) {
451
- return window.btoa(new Uint8Array(buff).reduce((s, b) => s + String.fromCharCode(b), ''));
452
- }
453
-
454
- /*
455
- * Base64 url safe encoding of an array
456
- */
457
- #base64UrlSafeEncode(buf) {
458
- const s = this.#encode64(buf).replace(/\+/g, "-").replace(/\//g, "_").replace(/=/g, "");
459
- return s;
460
- }
461
-
462
- /* Calc code verifier if necessary
463
- */
464
- /* eslint-disable camelcase */
465
- #getCodeChallenge(code_verifier) {
466
- return this.#sha256Hash(code_verifier).then (
467
- (hashed) => {
468
- return this.#base64UrlSafeEncode(hashed)
469
- }
470
- ).catch(
471
- (error) => {
472
- // eslint-disable-next-line no-console
473
- console.log(error)
474
- }
475
- ).finally(
476
- () => { return null }
477
- )
478
- }
479
- /* eslint-enable camelcase */
480
-
481
- }
482
-
483
- export default PegaAuth;