@northern.tech/store 0.30.0 → 0.30.2
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/dist/actions.cjs +21 -1130
- package/dist/actions.cjs.map +1 -1
- package/dist/actions.d.cts +212 -221
- package/dist/actions.d.ts +212 -220
- package/dist/actions.js +21 -18
- package/dist/actions.js.map +1 -1
- package/dist/api/general-api.cjs +61 -459
- package/dist/api/general-api.cjs.map +1 -1
- package/dist/api/general-api.d.cts +15 -17
- package/dist/api/general-api.d.ts +15 -17
- package/dist/api/general-api.js +56 -15
- package/dist/api/general-api.js.map +1 -1
- package/dist/api/users-api.cjs +32 -469
- package/dist/api/users-api.cjs.map +1 -1
- package/dist/api/users-api.d.cts +19 -14
- package/dist/api/users-api.d.ts +19 -13
- package/dist/api/users-api.js +30 -12
- package/dist/api/users-api.js.map +1 -1
- package/dist/appSlice/constants.cjs +190 -144
- package/dist/appSlice/constants.cjs.map +1 -1
- package/dist/appSlice/constants.d.cts +2 -159
- package/dist/appSlice/constants.d.ts +2 -159
- package/dist/appSlice/constants.js +181 -29
- package/dist/appSlice/constants.js.map +1 -1
- package/dist/appSlice/index.cjs +147 -178
- package/dist/appSlice/index.cjs.map +1 -1
- package/dist/appSlice/index.d.cts +2 -148
- package/dist/appSlice/index.d.ts +2 -148
- package/dist/appSlice/index.js +142 -18
- package/dist/appSlice/index.js.map +1 -1
- package/dist/appSlice/mocks.cjs +17 -191
- package/dist/appSlice/mocks.cjs.map +1 -1
- package/dist/appSlice/mocks.d.cts +33 -36
- package/dist/appSlice/mocks.d.ts +33 -36
- package/dist/appSlice/mocks.js +17 -25
- package/dist/appSlice/mocks.js.map +1 -1
- package/dist/appSlice/selectors.cjs +49 -91
- package/dist/appSlice/selectors.cjs.map +1 -1
- package/dist/appSlice/selectors.d.cts +216 -230
- package/dist/appSlice/selectors.d.ts +216 -230
- package/dist/appSlice/selectors.js +29 -44
- package/dist/appSlice/selectors.js.map +1 -1
- package/dist/appSlice/thunks.cjs +6 -4636
- package/dist/appSlice/thunks.d.cts +59 -62
- package/dist/appSlice/thunks.d.ts +59 -62
- package/dist/appSlice/thunks.js +2 -45
- package/dist/auth.cjs +68 -433
- package/dist/auth.cjs.map +1 -1
- package/dist/auth.d.cts +14 -14
- package/dist/auth.d.ts +14 -14
- package/dist/auth.js +65 -18
- package/dist/auth.js.map +1 -1
- package/dist/chunk-CKQMccvm.cjs +28 -0
- package/dist/commonConstants.cjs +14 -393
- package/dist/commonConstants.d.cts +2 -83
- package/dist/commonConstants.d.ts +2 -83
- package/dist/commonConstants.js +2 -33
- package/dist/commonSelectors.cjs +284 -1269
- package/dist/commonSelectors.cjs.map +1 -1
- package/dist/commonSelectors.d.cts +1623 -1416
- package/dist/commonSelectors.d.ts +1623 -1416
- package/dist/commonSelectors.js +277 -51
- package/dist/commonSelectors.js.map +1 -1
- package/dist/constants-5cdwz1iH.d.ts +160 -0
- package/dist/constants-BWEsNG5c.d.ts +28 -0
- package/dist/constants-BciiayPt.d.ts +17 -0
- package/dist/constants-C5AU0mCY.d.ts +157 -0
- package/dist/constants-CIx3fnBv.d.cts +17 -0
- package/dist/constants-CNhpIMME.d.cts +93 -0
- package/dist/constants-Cpgyuy_r.d.ts +57 -0
- package/dist/constants-D41U_jbR.d.cts +160 -0
- package/dist/constants-DK7fI3Rh.d.cts +28 -0
- package/dist/constants-DPLHhjVN.d.cts +157 -0
- package/dist/constants-DrwXHsJ1.d.ts +120 -0
- package/dist/constants-G3wymKIl.d.cts +57 -0
- package/dist/constants-MPLfugsi.d.cts +120 -0
- package/dist/constants-y2XVLQWf.d.ts +93 -0
- package/dist/constants.cjs +784 -972
- package/dist/constants.cjs.map +1 -1
- package/dist/constants.d.cts +8 -14
- package/dist/constants.d.ts +8 -14
- package/dist/constants.js +674 -232
- package/dist/constants.js.map +1 -1
- package/dist/deploymentsSlice/constants.cjs +15 -214
- package/dist/deploymentsSlice/constants.d.cts +2 -163
- package/dist/deploymentsSlice/constants.d.ts +2 -163
- package/dist/deploymentsSlice/constants.js +2 -35
- package/dist/deploymentsSlice/index.cjs +168 -302
- package/dist/deploymentsSlice/index.cjs.map +1 -1
- package/dist/deploymentsSlice/index.d.cts +2 -157
- package/dist/deploymentsSlice/index.d.ts +2 -157
- package/dist/deploymentsSlice/index.js +161 -18
- package/dist/deploymentsSlice/index.js.map +1 -1
- package/dist/deploymentsSlice/mocks.cjs +178 -433
- package/dist/deploymentsSlice/mocks.cjs.map +1 -1
- package/dist/deploymentsSlice/mocks.d.cts +176 -178
- package/dist/deploymentsSlice/mocks.d.ts +176 -178
- package/dist/deploymentsSlice/mocks.js +178 -144
- package/dist/deploymentsSlice/mocks.js.map +1 -1
- package/dist/deploymentsSlice/selectors.cjs +44 -223
- package/dist/deploymentsSlice/selectors.cjs.map +1 -1
- package/dist/deploymentsSlice/selectors.d.cts +73 -87
- package/dist/deploymentsSlice/selectors.d.ts +73 -87
- package/dist/deploymentsSlice/selectors.js +37 -25
- package/dist/deploymentsSlice/selectors.js.map +1 -1
- package/dist/deploymentsSlice/thunks.cjs +16 -4654
- package/dist/deploymentsSlice/thunks.d.cts +223 -236
- package/dist/deploymentsSlice/thunks.d.ts +223 -236
- package/dist/deploymentsSlice/thunks.js +2 -65
- package/dist/devicesSlice/constants.cjs +9 -68
- package/dist/devicesSlice/constants.d.cts +2 -37
- package/dist/devicesSlice/constants.d.ts +2 -37
- package/dist/devicesSlice/constants.js +2 -23
- package/dist/devicesSlice/index.cjs +215 -225
- package/dist/devicesSlice/index.cjs.map +1 -1
- package/dist/devicesSlice/index.d.cts +2 -202
- package/dist/devicesSlice/index.d.ts +2 -202
- package/dist/devicesSlice/index.js +209 -18
- package/dist/devicesSlice/index.js.map +1 -1
- package/dist/devicesSlice/mocks.cjs +146 -339
- package/dist/devicesSlice/mocks.cjs.map +1 -1
- package/dist/devicesSlice/mocks.d.cts +150 -148
- package/dist/devicesSlice/mocks.d.ts +150 -148
- package/dist/devicesSlice/mocks.js +145 -132
- package/dist/devicesSlice/mocks.js.map +1 -1
- package/dist/devicesSlice/selectors.cjs +145 -539
- package/dist/devicesSlice/selectors.cjs.map +1 -1
- package/dist/devicesSlice/selectors.d.cts +685 -699
- package/dist/devicesSlice/selectors.d.ts +685 -699
- package/dist/devicesSlice/selectors.js +123 -59
- package/dist/devicesSlice/selectors.js.map +1 -1
- package/dist/devicesSlice/thunks.cjs +48 -4718
- package/dist/devicesSlice/thunks.d.cts +800 -752
- package/dist/devicesSlice/thunks.d.ts +800 -752
- package/dist/devicesSlice/thunks.js +2 -129
- package/dist/index-4eaLEXy_.d.cts +152 -0
- package/dist/index-BEVkIiNa.d.cts +95 -0
- package/dist/index-BP0uAq36.d.cts +159 -0
- package/dist/index-Bwx9jEiL.d.cts +71 -0
- package/dist/index-CJkrL0oA.d.ts +64 -0
- package/dist/index-CO-py5d4.d.ts +95 -0
- package/dist/index-CTt-eIY8.d.cts +154 -0
- package/dist/index-CkwVnIqd.d.ts +159 -0
- package/dist/index-Cvkvcz4r.d.ts +115 -0
- package/dist/index-DJSlDPRX.d.ts +71 -0
- package/dist/index-DqyY6oZ3.d.ts +205 -0
- package/dist/index-DtePEQPT.d.ts +152 -0
- package/dist/index-Dv3Hfxk_.d.ts +154 -0
- package/dist/index-FyYBBeN-.d.cts +115 -0
- package/dist/index-Lz5JsJ6O.d.cts +205 -0
- package/dist/index-UPc3wvVd.d.cts +64 -0
- package/dist/liststatehook.cjs +83 -948
- package/dist/liststatehook.cjs.map +1 -1
- package/dist/liststatehook.d.cts +29 -239
- package/dist/liststatehook.d.ts +29 -239
- package/dist/liststatehook.js +77 -85
- package/dist/liststatehook.js.map +1 -1
- package/dist/locationutils.cjs +459 -916
- package/dist/locationutils.cjs.map +1 -1
- package/dist/locationutils.d.cts +244 -110
- package/dist/locationutils.d.ts +244 -110
- package/dist/locationutils.js +440 -44
- package/dist/locationutils.js.map +1 -1
- package/dist/monitorSlice/constants.cjs +0 -19
- package/dist/monitorSlice/constants.d.cts +2 -5
- package/dist/monitorSlice/constants.d.ts +2 -5
- package/dist/monitorSlice/constants.js +1 -2
- package/dist/monitorSlice/index.cjs +65 -82
- package/dist/monitorSlice/index.cjs.map +1 -1
- package/dist/monitorSlice/index.d.cts +2 -94
- package/dist/monitorSlice/index.d.ts +2 -94
- package/dist/monitorSlice/index.js +59 -18
- package/dist/monitorSlice/index.js.map +1 -1
- package/dist/monitorSlice/mocks.cjs +50 -126
- package/dist/monitorSlice/mocks.cjs.map +1 -1
- package/dist/monitorSlice/mocks.d.cts +49 -45
- package/dist/monitorSlice/mocks.d.ts +49 -45
- package/dist/monitorSlice/mocks.js +49 -62
- package/dist/monitorSlice/mocks.js.map +1 -1
- package/dist/monitorSlice/selectors.cjs +5 -29
- package/dist/monitorSlice/selectors.cjs.map +1 -1
- package/dist/monitorSlice/selectors.d.cts +10 -1
- package/dist/monitorSlice/selectors.d.ts +10 -1
- package/dist/monitorSlice/selectors.js +5 -6
- package/dist/monitorSlice/selectors.js.map +1 -1
- package/dist/monitorSlice/thunks.cjs +83 -1914
- package/dist/monitorSlice/thunks.cjs.map +1 -1
- package/dist/monitorSlice/thunks.d.cts +112 -120
- package/dist/monitorSlice/thunks.d.ts +112 -120
- package/dist/monitorSlice/thunks.js +78 -42
- package/dist/monitorSlice/thunks.js.map +1 -1
- package/dist/onboardingSlice/constants.cjs +44 -69
- package/dist/onboardingSlice/constants.cjs.map +1 -1
- package/dist/onboardingSlice/constants.d.cts +2 -26
- package/dist/onboardingSlice/constants.d.ts +2 -26
- package/dist/onboardingSlice/constants.js +43 -7
- package/dist/onboardingSlice/constants.js.map +1 -1
- package/dist/onboardingSlice/index.cjs +53 -73
- package/dist/onboardingSlice/index.cjs.map +1 -1
- package/dist/onboardingSlice/index.d.cts +2 -62
- package/dist/onboardingSlice/index.d.ts +2 -62
- package/dist/onboardingSlice/index.js +47 -13
- package/dist/onboardingSlice/index.js.map +1 -1
- package/dist/onboardingSlice/mocks.cjs +12 -81
- package/dist/onboardingSlice/mocks.cjs.map +1 -1
- package/dist/onboardingSlice/mocks.d.cts +14 -15
- package/dist/onboardingSlice/mocks.d.ts +14 -15
- package/dist/onboardingSlice/mocks.js +12 -15
- package/dist/onboardingSlice/mocks.js.map +1 -1
- package/dist/onboardingSlice/selectors.cjs +5 -29
- package/dist/onboardingSlice/selectors.cjs.map +1 -1
- package/dist/onboardingSlice/selectors.d.cts +6 -1
- package/dist/onboardingSlice/selectors.d.ts +6 -1
- package/dist/onboardingSlice/selectors.js +5 -6
- package/dist/onboardingSlice/selectors.js.map +1 -1
- package/dist/onboardingSlice/thunks.cjs +8 -4746
- package/dist/onboardingSlice/thunks.d.cts +124 -143
- package/dist/onboardingSlice/thunks.d.ts +124 -143
- package/dist/onboardingSlice/thunks.js +2 -49
- package/dist/organizationSlice/constants.cjs +11 -95
- package/dist/organizationSlice/constants.d.cts +2 -91
- package/dist/organizationSlice/constants.d.ts +2 -91
- package/dist/organizationSlice/constants.js +2 -27
- package/dist/organizationSlice/index.cjs +113 -152
- package/dist/organizationSlice/index.cjs.map +1 -1
- package/dist/organizationSlice/index.d.cts +2 -74
- package/dist/organizationSlice/index.d.ts +2 -74
- package/dist/organizationSlice/index.js +106 -18
- package/dist/organizationSlice/index.js.map +1 -1
- package/dist/organizationSlice/mocks.cjs +215 -406
- package/dist/organizationSlice/mocks.cjs.map +1 -1
- package/dist/organizationSlice/mocks.d.cts +209 -212
- package/dist/organizationSlice/mocks.d.ts +209 -212
- package/dist/organizationSlice/mocks.js +214 -184
- package/dist/organizationSlice/mocks.js.map +1 -1
- package/dist/organizationSlice/selectors.cjs +97 -474
- package/dist/organizationSlice/selectors.cjs.map +1 -1
- package/dist/organizationSlice/selectors.d.cts +381 -389
- package/dist/organizationSlice/selectors.d.ts +381 -389
- package/dist/organizationSlice/selectors.js +78 -50
- package/dist/organizationSlice/selectors.js.map +1 -1
- package/dist/organizationSlice/thunks.cjs +43 -5150
- package/dist/organizationSlice/thunks.d.cts +638 -649
- package/dist/organizationSlice/thunks.d.ts +638 -649
- package/dist/organizationSlice/thunks.js +2 -119
- package/dist/organizationSlice/types.cjs +0 -19
- package/dist/organizationSlice/types.d.cts +2 -88
- package/dist/organizationSlice/types.d.ts +2 -88
- package/dist/organizationSlice/types.js +1 -1
- package/dist/releasesSlice/constants.cjs +17 -41
- package/dist/releasesSlice/constants.cjs.map +1 -1
- package/dist/releasesSlice/constants.d.cts +2 -15
- package/dist/releasesSlice/constants.d.ts +2 -15
- package/dist/releasesSlice/constants.js +13 -14
- package/dist/releasesSlice/constants.js.map +1 -1
- package/dist/releasesSlice/index.cjs +106 -179
- package/dist/releasesSlice/index.cjs.map +1 -1
- package/dist/releasesSlice/index.d.cts +2 -113
- package/dist/releasesSlice/index.d.ts +2 -113
- package/dist/releasesSlice/index.js +100 -18
- package/dist/releasesSlice/index.js.map +1 -1
- package/dist/releasesSlice/mocks.cjs +44 -220
- package/dist/releasesSlice/mocks.cjs.map +1 -1
- package/dist/releasesSlice/mocks.d.cts +63 -61
- package/dist/releasesSlice/mocks.d.ts +63 -61
- package/dist/releasesSlice/mocks.js +43 -59
- package/dist/releasesSlice/mocks.js.map +1 -1
- package/dist/releasesSlice/selectors.cjs +44 -439
- package/dist/releasesSlice/selectors.cjs.map +1 -1
- package/dist/releasesSlice/selectors.d.cts +268 -280
- package/dist/releasesSlice/selectors.d.ts +268 -280
- package/dist/releasesSlice/selectors.js +31 -36
- package/dist/releasesSlice/selectors.js.map +1 -1
- package/dist/releasesSlice/thunks.cjs +422 -2175
- package/dist/releasesSlice/thunks.cjs.map +1 -1
- package/dist/releasesSlice/thunks.d.cts +305 -307
- package/dist/releasesSlice/thunks.d.ts +305 -307
- package/dist/releasesSlice/thunks.js +413 -65
- package/dist/releasesSlice/thunks.js.map +1 -1
- package/dist/selectors.cjs +136 -1530
- package/dist/selectors.d.cts +10 -36
- package/dist/selectors.d.ts +10 -36
- package/dist/selectors.js +10 -280
- package/dist/sockethook.cjs +140 -515
- package/dist/sockethook.cjs.map +1 -1
- package/dist/sockethook.d.cts +25 -9
- package/dist/sockethook.d.ts +25 -9
- package/dist/sockethook.js +134 -135
- package/dist/sockethook.js.map +1 -1
- package/dist/store-BQxOSRC1.d.ts +234 -0
- package/dist/store-BiIA0r0A.d.cts +234 -0
- package/dist/store.cjs +117 -1290
- package/dist/store.cjs.map +1 -1
- package/dist/store.d.cts +3 -206
- package/dist/store.d.ts +3 -206
- package/dist/store.js +110 -32
- package/dist/store.js.map +1 -1
- package/dist/storehooks.cjs +240 -5783
- package/dist/storehooks.cjs.map +1 -1
- package/dist/storehooks.d.cts +76 -4
- package/dist/storehooks.d.ts +76 -4
- package/dist/storehooks.js +229 -265
- package/dist/storehooks.js.map +1 -1
- package/dist/thunks.cjs +2656 -5918
- package/dist/thunks.cjs.map +1 -1
- package/dist/thunks.d.cts +9 -36
- package/dist/thunks.d.ts +9 -36
- package/dist/thunks.js +2481 -385
- package/dist/thunks.js.map +1 -1
- package/dist/types-B2NRQLFw.d.ts +88 -0
- package/dist/types-ClEfo0dK.d.cts +88 -0
- package/dist/useDeploymentDevice.cjs +26 -4650
- package/dist/useDeploymentDevice.cjs.map +1 -1
- package/dist/useDeploymentDevice.d.cts +4 -2
- package/dist/useDeploymentDevice.d.ts +4 -2
- package/dist/useDeploymentDevice.js +21 -60
- package/dist/useDeploymentDevice.js.map +1 -1
- package/dist/usersSlice/constants.cjs +8 -55
- package/dist/usersSlice/constants.d.cts +2 -52
- package/dist/usersSlice/constants.d.ts +2 -52
- package/dist/usersSlice/constants.js +2 -21
- package/dist/usersSlice/index.cjs +132 -172
- package/dist/usersSlice/index.cjs.map +1 -1
- package/dist/usersSlice/index.d.cts +2 -152
- package/dist/usersSlice/index.d.ts +2 -152
- package/dist/usersSlice/index.js +125 -18
- package/dist/usersSlice/index.js.map +1 -1
- package/dist/usersSlice/mocks.cjs +55 -196
- package/dist/usersSlice/mocks.cjs.map +1 -1
- package/dist/usersSlice/mocks.d.cts +68 -72
- package/dist/usersSlice/mocks.d.ts +68 -72
- package/dist/usersSlice/mocks.js +54 -46
- package/dist/usersSlice/mocks.js.map +1 -1
- package/dist/usersSlice/selectors.cjs +65 -567
- package/dist/usersSlice/selectors.cjs.map +1 -1
- package/dist/usersSlice/selectors.d.cts +364 -376
- package/dist/usersSlice/selectors.d.ts +364 -376
- package/dist/usersSlice/selectors.js +44 -50
- package/dist/usersSlice/selectors.js.map +1 -1
- package/dist/usersSlice/thunks.cjs +39 -4698
- package/dist/usersSlice/thunks.d.cts +820 -856
- package/dist/usersSlice/thunks.d.ts +820 -856
- package/dist/usersSlice/thunks.js +2 -111
- package/dist/utils-CO_CpGFP.d.ts +105 -0
- package/dist/utils-CpPfqW0Q.d.cts +105 -0
- package/dist/utils.cjs +231 -850
- package/dist/utils.cjs.map +1 -1
- package/dist/utils.d.cts +2 -80
- package/dist/utils.d.ts +2 -80
- package/dist/utils.js +211 -50
- package/dist/utils.js.map +1 -1
- package/package.json +11 -13
- package/dist/appSlice/thunks.cjs.map +0 -1
- package/dist/appSlice/thunks.js.map +0 -1
- package/dist/chunk-2DYA3X77.js +0 -15
- package/dist/chunk-2DYA3X77.js.map +0 -1
- package/dist/chunk-4BHM6WVX.js +0 -50
- package/dist/chunk-4BHM6WVX.js.map +0 -1
- package/dist/chunk-4UNLEL5A.js +0 -143
- package/dist/chunk-4UNLEL5A.js.map +0 -1
- package/dist/chunk-6V5IIIF7.js +0 -396
- package/dist/chunk-6V5IIIF7.js.map +0 -1
- package/dist/chunk-ARMI6SZS.js +0 -446
- package/dist/chunk-ARMI6SZS.js.map +0 -1
- package/dist/chunk-AZF4YY3P.js +0 -108
- package/dist/chunk-AZF4YY3P.js.map +0 -1
- package/dist/chunk-B5AI2YPV.js +0 -156
- package/dist/chunk-B5AI2YPV.js.map +0 -1
- package/dist/chunk-CQXDAXQF.js +0 -51
- package/dist/chunk-CQXDAXQF.js.map +0 -1
- package/dist/chunk-DBBE6D36.js +0 -115
- package/dist/chunk-DBBE6D36.js.map +0 -1
- package/dist/chunk-ECVQVQEL.js +0 -68
- package/dist/chunk-ECVQVQEL.js.map +0 -1
- package/dist/chunk-FAJ3I2UQ.js +0 -47
- package/dist/chunk-FAJ3I2UQ.js.map +0 -1
- package/dist/chunk-FCY7BUGK.js +0 -2876
- package/dist/chunk-FCY7BUGK.js.map +0 -1
- package/dist/chunk-FG37HJLC.js +0 -157
- package/dist/chunk-FG37HJLC.js.map +0 -1
- package/dist/chunk-FQAUVV6C.js +0 -246
- package/dist/chunk-FQAUVV6C.js.map +0 -1
- package/dist/chunk-HKN3RN2Z.js +0 -41
- package/dist/chunk-HKN3RN2Z.js.map +0 -1
- package/dist/chunk-HPKXWNEF.js +0 -100
- package/dist/chunk-HPKXWNEF.js.map +0 -1
- package/dist/chunk-JIS4PA3R.js +0 -7
- package/dist/chunk-JIS4PA3R.js.map +0 -1
- package/dist/chunk-JXBTIFMS.js +0 -82
- package/dist/chunk-JXBTIFMS.js.map +0 -1
- package/dist/chunk-JYPSCCT4.js +0 -58
- package/dist/chunk-JYPSCCT4.js.map +0 -1
- package/dist/chunk-L53CPHJU.js +0 -721
- package/dist/chunk-L53CPHJU.js.map +0 -1
- package/dist/chunk-MNJXEB7S.js +0 -304
- package/dist/chunk-MNJXEB7S.js.map +0 -1
- package/dist/chunk-NMAXZ3ZY.js +0 -1
- package/dist/chunk-NMAXZ3ZY.js.map +0 -1
- package/dist/chunk-NXLXPRYW.js +0 -142
- package/dist/chunk-NXLXPRYW.js.map +0 -1
- package/dist/chunk-O6VCSLNE.js +0 -59
- package/dist/chunk-O6VCSLNE.js.map +0 -1
- package/dist/chunk-PQADM3M3.js +0 -115
- package/dist/chunk-PQADM3M3.js.map +0 -1
- package/dist/chunk-SJ75YKOA.js +0 -44
- package/dist/chunk-SJ75YKOA.js.map +0 -1
- package/dist/chunk-TUPBZ6MQ.js +0 -162
- package/dist/chunk-TUPBZ6MQ.js.map +0 -1
- package/dist/chunk-XF3TZSZS.js +0 -25
- package/dist/chunk-XF3TZSZS.js.map +0 -1
- package/dist/chunk-YB3US6OT.js +0 -61
- package/dist/chunk-YB3US6OT.js.map +0 -1
- package/dist/chunk-YDDE5TIH.js +0 -204
- package/dist/chunk-YDDE5TIH.js.map +0 -1
- package/dist/chunk-YO22XLHI.js +0 -7
- package/dist/chunk-YO22XLHI.js.map +0 -1
- package/dist/chunk-Z2O6LYVP.js +0 -144
- package/dist/chunk-Z2O6LYVP.js.map +0 -1
- package/dist/chunk-ZKAH3APE.js +0 -1
- package/dist/chunk-ZKAH3APE.js.map +0 -1
- package/dist/commonConstants.cjs.map +0 -1
- package/dist/commonConstants.js.map +0 -1
- package/dist/deploymentsSlice/constants.cjs.map +0 -1
- package/dist/deploymentsSlice/constants.js.map +0 -1
- package/dist/deploymentsSlice/thunks.cjs.map +0 -1
- package/dist/deploymentsSlice/thunks.js.map +0 -1
- package/dist/devicesSlice/constants.cjs.map +0 -1
- package/dist/devicesSlice/constants.js.map +0 -1
- package/dist/devicesSlice/thunks.cjs.map +0 -1
- package/dist/devicesSlice/thunks.js.map +0 -1
- package/dist/monitorSlice/constants.cjs.map +0 -1
- package/dist/monitorSlice/constants.js.map +0 -1
- package/dist/onboardingSlice/thunks.cjs.map +0 -1
- package/dist/onboardingSlice/thunks.js.map +0 -1
- package/dist/organizationSlice/constants.cjs.map +0 -1
- package/dist/organizationSlice/constants.js.map +0 -1
- package/dist/organizationSlice/thunks.cjs.map +0 -1
- package/dist/organizationSlice/thunks.js.map +0 -1
- package/dist/organizationSlice/types.cjs.map +0 -1
- package/dist/organizationSlice/types.js.map +0 -1
- package/dist/selectors.cjs.map +0 -1
- package/dist/selectors.js.map +0 -1
- package/dist/usersSlice/constants.cjs.map +0 -1
- package/dist/usersSlice/constants.js.map +0 -1
- package/dist/usersSlice/thunks.cjs.map +0 -1
- package/dist/usersSlice/thunks.js.map +0 -1
package/dist/chunk-FCY7BUGK.js
DELETED
|
@@ -1,2876 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
getDeviceMonitorConfig,
|
|
3
|
-
getLatestDeviceAlerts
|
|
4
|
-
} from "./chunk-AZF4YY3P.js";
|
|
5
|
-
import {
|
|
6
|
-
commonErrorFallback,
|
|
7
|
-
commonErrorHandler,
|
|
8
|
-
createAppAsyncThunk
|
|
9
|
-
} from "./chunk-NXLXPRYW.js";
|
|
10
|
-
import {
|
|
11
|
-
users_api_default
|
|
12
|
-
} from "./chunk-XF3TZSZS.js";
|
|
13
|
-
import {
|
|
14
|
-
general_api_default
|
|
15
|
-
} from "./chunk-JYPSCCT4.js";
|
|
16
|
-
import {
|
|
17
|
-
actions_default
|
|
18
|
-
} from "./chunk-HKN3RN2Z.js";
|
|
19
|
-
import {
|
|
20
|
-
actions as actions6,
|
|
21
|
-
sliceName as sliceName6
|
|
22
|
-
} from "./chunk-Z2O6LYVP.js";
|
|
23
|
-
import {
|
|
24
|
-
actions as actions5,
|
|
25
|
-
sliceName as sliceName5
|
|
26
|
-
} from "./chunk-PQADM3M3.js";
|
|
27
|
-
import {
|
|
28
|
-
actions as actions4,
|
|
29
|
-
sliceName as sliceName4
|
|
30
|
-
} from "./chunk-CQXDAXQF.js";
|
|
31
|
-
import {
|
|
32
|
-
actions as actions3,
|
|
33
|
-
sliceName as sliceName3
|
|
34
|
-
} from "./chunk-YDDE5TIH.js";
|
|
35
|
-
import {
|
|
36
|
-
actions,
|
|
37
|
-
sliceName
|
|
38
|
-
} from "./chunk-B5AI2YPV.js";
|
|
39
|
-
import {
|
|
40
|
-
actions as actions2,
|
|
41
|
-
sliceName as sliceName2
|
|
42
|
-
} from "./chunk-4UNLEL5A.js";
|
|
43
|
-
import {
|
|
44
|
-
cleanUp,
|
|
45
|
-
getSessionInfo,
|
|
46
|
-
setSessionInfo
|
|
47
|
-
} from "./chunk-ECVQVQEL.js";
|
|
48
|
-
import {
|
|
49
|
-
getDeviceReportsForUser,
|
|
50
|
-
getOnboardingState,
|
|
51
|
-
getTenantCapabilities,
|
|
52
|
-
getUserCapabilities
|
|
53
|
-
} from "./chunk-MNJXEB7S.js";
|
|
54
|
-
import {
|
|
55
|
-
getCurrentUser,
|
|
56
|
-
getGlobalSettings,
|
|
57
|
-
getIdAttribute,
|
|
58
|
-
getOfflineThresholdSettings,
|
|
59
|
-
getRolesById,
|
|
60
|
-
getSelectedDeviceAttribute,
|
|
61
|
-
getTooltipsState,
|
|
62
|
-
getUserSettings,
|
|
63
|
-
getUsersById
|
|
64
|
-
} from "./chunk-JXBTIFMS.js";
|
|
65
|
-
import {
|
|
66
|
-
getAuditlogState,
|
|
67
|
-
getDeviceTwinIntegrations,
|
|
68
|
-
getOrganization,
|
|
69
|
-
getSpLimits,
|
|
70
|
-
getTenantsList
|
|
71
|
-
} from "./chunk-HPKXWNEF.js";
|
|
72
|
-
import {
|
|
73
|
-
getDeploymentsById,
|
|
74
|
-
getDeploymentsByStatus
|
|
75
|
-
} from "./chunk-O6VCSLNE.js";
|
|
76
|
-
import {
|
|
77
|
-
getAcceptedDevices,
|
|
78
|
-
getDeviceById,
|
|
79
|
-
getDeviceCountsByStatus,
|
|
80
|
-
getDeviceFilters,
|
|
81
|
-
getDeviceListState,
|
|
82
|
-
getDeviceReports,
|
|
83
|
-
getDevicesById,
|
|
84
|
-
getGroupsById,
|
|
85
|
-
getSelectedGroup
|
|
86
|
-
} from "./chunk-TUPBZ6MQ.js";
|
|
87
|
-
import {
|
|
88
|
-
getFeatures,
|
|
89
|
-
getHostedAnnouncement,
|
|
90
|
-
getSearchState
|
|
91
|
-
} from "./chunk-4BHM6WVX.js";
|
|
92
|
-
import {
|
|
93
|
-
convertDeviceListStateToFilters,
|
|
94
|
-
convertToBackendSPLimits,
|
|
95
|
-
extractErrorMessage,
|
|
96
|
-
filtersFilter,
|
|
97
|
-
getComparisonCompatibleVersion,
|
|
98
|
-
mapDeviceAttributes,
|
|
99
|
-
mapFiltersToTerms,
|
|
100
|
-
mapTermsToFilters,
|
|
101
|
-
mergePermissions,
|
|
102
|
-
parseSubscriptionPreview,
|
|
103
|
-
progress
|
|
104
|
-
} from "./chunk-FQAUVV6C.js";
|
|
105
|
-
import {
|
|
106
|
-
ALL_DEVICE_STATES,
|
|
107
|
-
ALL_RELEASES,
|
|
108
|
-
APPLICATION_JSON_CONTENT_TYPE,
|
|
109
|
-
APPLICATION_JWT_CONTENT_TYPE,
|
|
110
|
-
DEPLOYMENT_ROUTES,
|
|
111
|
-
DEPLOYMENT_STATES,
|
|
112
|
-
DEPLOYMENT_TYPES,
|
|
113
|
-
DEVICE_FILTERING_OPTIONS,
|
|
114
|
-
DEVICE_LIST_DEFAULTS,
|
|
115
|
-
DEVICE_STATES,
|
|
116
|
-
EXTERNAL_PROVIDER,
|
|
117
|
-
MAX_PAGE_SIZE,
|
|
118
|
-
OWN_USER_ID,
|
|
119
|
-
PermissionTypes,
|
|
120
|
-
READ_STATES,
|
|
121
|
-
SORTING_OPTIONS,
|
|
122
|
-
SSO_TYPES,
|
|
123
|
-
TENANT_LIST_DEFAULT,
|
|
124
|
-
TIMEOUTS,
|
|
125
|
-
UNGROUPED_GROUP,
|
|
126
|
-
USER_LOGOUT,
|
|
127
|
-
apiRoot,
|
|
128
|
-
auditLogsApiUrl,
|
|
129
|
-
defaultPermissionSets,
|
|
130
|
-
deploymentPrototype,
|
|
131
|
-
deploymentsApiUrl,
|
|
132
|
-
deploymentsApiUrlV2,
|
|
133
|
-
deviceAuthV2,
|
|
134
|
-
deviceConfig,
|
|
135
|
-
deviceConnect,
|
|
136
|
-
emptyFilter,
|
|
137
|
-
emptyRole,
|
|
138
|
-
emptyUiPermissions,
|
|
139
|
-
headerNames,
|
|
140
|
-
inventoryApiUrl,
|
|
141
|
-
inventoryApiUrlV2,
|
|
142
|
-
iotManagerBaseURL,
|
|
143
|
-
itemUiPermissionsReducer,
|
|
144
|
-
maxSessionAge,
|
|
145
|
-
rolesById,
|
|
146
|
-
scopedPermissionAreas,
|
|
147
|
-
settingsKeys,
|
|
148
|
-
ssoIdpApiUrlv1,
|
|
149
|
-
tenantadmApiUrlv1,
|
|
150
|
-
tenantadmApiUrlv2,
|
|
151
|
-
twoFAStates,
|
|
152
|
-
uiPermissionsByArea,
|
|
153
|
-
uiPermissionsById,
|
|
154
|
-
useradmApiUrl,
|
|
155
|
-
useradmApiUrlv2
|
|
156
|
-
} from "./chunk-L53CPHJU.js";
|
|
157
|
-
import {
|
|
158
|
-
rootfsImageVersion
|
|
159
|
-
} from "./chunk-2DYA3X77.js";
|
|
160
|
-
import {
|
|
161
|
-
onboardingSteps,
|
|
162
|
-
orderedOnboardingSteps
|
|
163
|
-
} from "./chunk-FAJ3I2UQ.js";
|
|
164
|
-
import {
|
|
165
|
-
ADDONS,
|
|
166
|
-
PLANS,
|
|
167
|
-
locations
|
|
168
|
-
} from "./chunk-DBBE6D36.js";
|
|
169
|
-
|
|
170
|
-
// src/appSlice/thunks.ts
|
|
171
|
-
import { deepCompare as deepCompare4, extractErrorMessage as extractErrorMessage3 } from "@northern.tech/utils/helpers";
|
|
172
|
-
import Cookies4 from "universal-cookie";
|
|
173
|
-
|
|
174
|
-
// src/deploymentsSlice/thunks.ts
|
|
175
|
-
import { customSort, deepCompare, isEmpty, standardizePhases } from "@northern.tech/utils/helpers";
|
|
176
|
-
import Tracking from "@northern.tech/utils/tracking";
|
|
177
|
-
import validator from "validator";
|
|
178
|
-
var { isUUID } = validator;
|
|
179
|
-
var { receivedDevice, setSnackbar } = actions_default;
|
|
180
|
-
var { page: defaultPage, perPage: defaultPerPage } = DEVICE_LIST_DEFAULTS;
|
|
181
|
-
var deriveDeploymentGroup = ({ filter, group, groups = [], name }) => group || groups.length === 1 && !isUUID(name) ? groups[0] : filter?.name;
|
|
182
|
-
var transformDeployments = (deployments, deploymentsById) => deployments.sort(customSort(true, "created")).reduce(
|
|
183
|
-
(accu, item) => {
|
|
184
|
-
const filter = item.filter;
|
|
185
|
-
let deployment = {
|
|
186
|
-
...deploymentPrototype,
|
|
187
|
-
...deploymentsById[item.id],
|
|
188
|
-
...item,
|
|
189
|
-
// TODO: explicitly set filter term types to address scope type mismatch in deployment specs
|
|
190
|
-
// @ts-expect-error: type misalignment in filter terms type
|
|
191
|
-
filter: filter ? { ...filter, name: filter.name ?? filter.id, filters: mapTermsToFilters(filter.terms) } : void 0,
|
|
192
|
-
name: decodeURIComponent(item.name)
|
|
193
|
-
};
|
|
194
|
-
deployment = { ...deployment, group: deriveDeploymentGroup(deployment) };
|
|
195
|
-
accu.deployments[item.id] = deployment;
|
|
196
|
-
accu.deploymentIds.push(item.id);
|
|
197
|
-
return accu;
|
|
198
|
-
},
|
|
199
|
-
{ deployments: {}, deploymentIds: [] }
|
|
200
|
-
);
|
|
201
|
-
var getDeploymentsByStatus2 = createAppAsyncThunk(
|
|
202
|
-
`${sliceName2}/getDeploymentsByStatus`,
|
|
203
|
-
(options, { dispatch, getState }) => {
|
|
204
|
-
const { status, page = defaultPage, perPage = defaultPerPage, startDate, endDate, group, type, shouldSelect = true, sort = SORTING_OPTIONS.desc } = options;
|
|
205
|
-
const created_after = startDate ? `&created_after=${startDate}` : "";
|
|
206
|
-
const created_before = endDate ? `&created_before=${endDate}` : "";
|
|
207
|
-
const { attribute, scope } = getIdAttribute(getState());
|
|
208
|
-
const attributeHint = `&id_attribute=${attribute}&id_scope=${scope}`;
|
|
209
|
-
const search = group ? `&name=${group}${attributeHint}` : "";
|
|
210
|
-
const typeFilter = type ? `&type=${type}` : "";
|
|
211
|
-
return general_api_default.get(
|
|
212
|
-
`${deploymentsApiUrlV2}/deployments?status=${status}&per_page=${perPage}&page=${page}${created_after}${created_before}${search}${typeFilter}&sort=${sort}`
|
|
213
|
-
).then((res) => {
|
|
214
|
-
const { deployments, deploymentIds } = transformDeployments(res.data, getState().deployments.byId);
|
|
215
|
-
const total = Number(res.headers[headerNames.total]);
|
|
216
|
-
let tasks = [
|
|
217
|
-
dispatch(actions2.receivedDeployments(deployments)),
|
|
218
|
-
dispatch(
|
|
219
|
-
actions2.receivedDeploymentsForStatus({
|
|
220
|
-
deploymentIds,
|
|
221
|
-
status,
|
|
222
|
-
total: !(startDate || endDate || group || type) ? total : getState().deployments.byStatus[status].total
|
|
223
|
-
})
|
|
224
|
-
)
|
|
225
|
-
];
|
|
226
|
-
tasks = deploymentIds.reduce((accu, deploymentId) => {
|
|
227
|
-
if (deployments[deploymentId].type === DEPLOYMENT_TYPES.configuration) {
|
|
228
|
-
accu.push(dispatch(getSingleDeployment(deploymentId)));
|
|
229
|
-
}
|
|
230
|
-
return accu;
|
|
231
|
-
}, tasks);
|
|
232
|
-
if (shouldSelect) {
|
|
233
|
-
tasks.push(dispatch(actions2.selectDeploymentsForStatus({ deploymentIds, status, total })));
|
|
234
|
-
}
|
|
235
|
-
tasks.push({ deploymentIds, total });
|
|
236
|
-
return Promise.all(tasks);
|
|
237
|
-
});
|
|
238
|
-
}
|
|
239
|
-
);
|
|
240
|
-
var isWithinFirstMonth = (expirationDate) => {
|
|
241
|
-
if (!expirationDate) {
|
|
242
|
-
return false;
|
|
243
|
-
}
|
|
244
|
-
const endOfFirstMonth = new Date(expirationDate);
|
|
245
|
-
endOfFirstMonth.setMonth(endOfFirstMonth.getMonth() - 11);
|
|
246
|
-
return endOfFirstMonth > /* @__PURE__ */ new Date();
|
|
247
|
-
};
|
|
248
|
-
var trackDeploymentCreation = (totalDeploymentCount, hasDeployments, trial_expiration) => {
|
|
249
|
-
Tracking.event({ category: "deployments", action: "create" });
|
|
250
|
-
if (!totalDeploymentCount) {
|
|
251
|
-
if (!hasDeployments) {
|
|
252
|
-
Tracking.event({ category: "deployments", action: "create_initial_deployment" });
|
|
253
|
-
if (isWithinFirstMonth(trial_expiration)) {
|
|
254
|
-
Tracking.event({ category: "deployments", action: "create_initial_deployment_first_month" });
|
|
255
|
-
}
|
|
256
|
-
}
|
|
257
|
-
Tracking.event({ category: "deployments", action: "create_initial_deployment_user" });
|
|
258
|
-
}
|
|
259
|
-
};
|
|
260
|
-
var MAX_PREVIOUS_PHASES_COUNT = 5;
|
|
261
|
-
var createDeployment = createAppAsyncThunk(
|
|
262
|
-
`${sliceName2}/createDeployment`,
|
|
263
|
-
({
|
|
264
|
-
newDeployment,
|
|
265
|
-
hasNewRetryDefault = false
|
|
266
|
-
}, { dispatch, getState }) => {
|
|
267
|
-
let request;
|
|
268
|
-
if ("filter_id" in newDeployment && newDeployment.filter_id) {
|
|
269
|
-
request = general_api_default.post(`${deploymentsApiUrlV2}/deployments`, newDeployment);
|
|
270
|
-
} else if ("group" in newDeployment && newDeployment.group) {
|
|
271
|
-
request = general_api_default.post(`${deploymentsApiUrl}/deployments/group/${newDeployment.group}`, newDeployment);
|
|
272
|
-
} else {
|
|
273
|
-
request = general_api_default.post(`${deploymentsApiUrl}/deployments`, newDeployment);
|
|
274
|
-
}
|
|
275
|
-
const totalDeploymentCount = Object.values(getDeploymentsByStatus(getState())).reduce(
|
|
276
|
-
(accu, item) => accu + item.total,
|
|
277
|
-
0
|
|
278
|
-
);
|
|
279
|
-
const { hasDeployments } = getGlobalSettings(getState());
|
|
280
|
-
const { trial_expiration } = getOrganization(getState());
|
|
281
|
-
return request.catch((err) => commonErrorHandler(err, "Error creating deployment.", dispatch)).then((data) => {
|
|
282
|
-
const lastslashindex = data.headers.location.lastIndexOf("/");
|
|
283
|
-
const deploymentId = data.headers.location.substring(lastslashindex + 1);
|
|
284
|
-
const deployment = {
|
|
285
|
-
...newDeployment,
|
|
286
|
-
id: deploymentId,
|
|
287
|
-
devices: "devices" in newDeployment && newDeployment.devices ? newDeployment.devices.map((id) => ({ id, status: "pending" })) : [],
|
|
288
|
-
statistics: { status: {} }
|
|
289
|
-
};
|
|
290
|
-
const tasks = [
|
|
291
|
-
dispatch(actions2.createdDeployment(deployment)),
|
|
292
|
-
dispatch(getSingleDeployment(deploymentId)),
|
|
293
|
-
dispatch(setSnackbar({ message: "Deployment created successfully", autoHideDuration: TIMEOUTS.fiveSeconds }))
|
|
294
|
-
];
|
|
295
|
-
trackDeploymentCreation(totalDeploymentCount, hasDeployments, trial_expiration);
|
|
296
|
-
const { canManageUsers } = getUserCapabilities(getState());
|
|
297
|
-
if (canManageUsers) {
|
|
298
|
-
const { phases, retries } = newDeployment;
|
|
299
|
-
const { previousPhases = [], retries: previousRetries = 0 } = getGlobalSettings(getState());
|
|
300
|
-
const newSettings = { retries: hasNewRetryDefault ? retries : previousRetries, hasDeployments: true };
|
|
301
|
-
if (phases) {
|
|
302
|
-
const standardPhases = standardizePhases(phases);
|
|
303
|
-
const prevPhases = previousPhases.map(standardizePhases);
|
|
304
|
-
if (!prevPhases.find((previousPhaseList) => previousPhaseList.every((oldPhase) => standardPhases.find((phase) => deepCompare(phase, oldPhase))))) {
|
|
305
|
-
prevPhases.push(standardPhases);
|
|
306
|
-
}
|
|
307
|
-
newSettings.previousPhases = prevPhases.slice(-1 * MAX_PREVIOUS_PHASES_COUNT);
|
|
308
|
-
}
|
|
309
|
-
tasks.push(dispatch(saveGlobalSettings(newSettings)));
|
|
310
|
-
}
|
|
311
|
-
return Promise.all(tasks);
|
|
312
|
-
});
|
|
313
|
-
}
|
|
314
|
-
);
|
|
315
|
-
var getDeploymentDevices = createAppAsyncThunk(
|
|
316
|
-
`${sliceName2}/getDeploymentDevices`,
|
|
317
|
-
(options, { dispatch, getState }) => {
|
|
318
|
-
const { id, page = defaultPage, perPage = defaultPerPage } = options;
|
|
319
|
-
return general_api_default.get(`${deploymentsApiUrl}/deployments/${id}/devices/list?&page=${page}&per_page=${perPage}`).then((response) => {
|
|
320
|
-
const { devices: deploymentDevices = {} } = getState().deployments.byId[id] || {};
|
|
321
|
-
const devices = response.data.reduce((accu, item) => {
|
|
322
|
-
accu[item.id] = item;
|
|
323
|
-
const log = (deploymentDevices[item.id] || {}).log;
|
|
324
|
-
if (log) {
|
|
325
|
-
accu[item.id].log = log;
|
|
326
|
-
}
|
|
327
|
-
return accu;
|
|
328
|
-
}, {});
|
|
329
|
-
const selectedDeviceIds = Object.keys(devices);
|
|
330
|
-
let tasks = [
|
|
331
|
-
dispatch(
|
|
332
|
-
actions2.receivedDeploymentDevices({
|
|
333
|
-
id,
|
|
334
|
-
devices,
|
|
335
|
-
selectedDeviceIds,
|
|
336
|
-
totalDeviceCount: Number(response.headers[headerNames.total])
|
|
337
|
-
})
|
|
338
|
-
)
|
|
339
|
-
];
|
|
340
|
-
const devicesById = getDevicesById(getState());
|
|
341
|
-
const lackingData = selectedDeviceIds.reduce((accu, deviceId) => {
|
|
342
|
-
const device = devicesById[deviceId];
|
|
343
|
-
if (!device || !device.identity_data || !device.attributes || Object.keys(device.attributes).length === 0) {
|
|
344
|
-
accu.push(deviceId);
|
|
345
|
-
}
|
|
346
|
-
return accu;
|
|
347
|
-
}, []);
|
|
348
|
-
tasks = lackingData.reduce((accu, deviceId) => [...accu, dispatch(getDeviceById2(deviceId)), dispatch(getDeviceAuth(deviceId))], tasks);
|
|
349
|
-
return Promise.all(tasks);
|
|
350
|
-
});
|
|
351
|
-
}
|
|
352
|
-
);
|
|
353
|
-
var parseDeviceDeployment = ({
|
|
354
|
-
deployment: { id, artifact_name: release, status: deploymentStatus },
|
|
355
|
-
device: { created, deleted, id: deviceId, finished, status, log }
|
|
356
|
-
}) => ({
|
|
357
|
-
id,
|
|
358
|
-
release,
|
|
359
|
-
created,
|
|
360
|
-
deleted,
|
|
361
|
-
deviceId,
|
|
362
|
-
finished,
|
|
363
|
-
status,
|
|
364
|
-
log,
|
|
365
|
-
route: Object.values(DEPLOYMENT_ROUTES).reduce((accu, { key, states }) => {
|
|
366
|
-
if (!accu) {
|
|
367
|
-
return states.includes(deploymentStatus) ? key : accu;
|
|
368
|
-
}
|
|
369
|
-
return accu;
|
|
370
|
-
}, "")
|
|
371
|
-
});
|
|
372
|
-
var getDeviceDeployments = createAppAsyncThunk(`${sliceName2}/getDeviceDeployments`, (options, { dispatch }) => {
|
|
373
|
-
const { deviceId, filterSelection = [], page = defaultPage, perPage = defaultPerPage } = options;
|
|
374
|
-
const filters = filterSelection.map((item) => `&status=${item}`).join("");
|
|
375
|
-
return general_api_default.get(`${deploymentsApiUrl}/deployments/devices/${deviceId}?page=${page}&per_page=${perPage}${filters}`).then(
|
|
376
|
-
({ data, headers }) => Promise.resolve(
|
|
377
|
-
dispatch(
|
|
378
|
-
receivedDevice({
|
|
379
|
-
id: deviceId,
|
|
380
|
-
deviceDeployments: data.map(parseDeviceDeployment),
|
|
381
|
-
deploymentsCount: Number(headers[headerNames.total])
|
|
382
|
-
})
|
|
383
|
-
)
|
|
384
|
-
)
|
|
385
|
-
).catch((err) => commonErrorHandler(err, "There was an error retrieving the device deployment history:", dispatch));
|
|
386
|
-
});
|
|
387
|
-
var resetDeviceDeployments = createAppAsyncThunk(
|
|
388
|
-
`${sliceName2}/resetDeviceDeployments`,
|
|
389
|
-
(deviceId, { dispatch }) => general_api_default.delete(`${deploymentsApiUrl}/deployments/devices/${deviceId}/history`).then(() => Promise.resolve(dispatch(getDeviceDeployments({ deviceId })))).catch((err) => commonErrorHandler(err, "There was an error resetting the device deployment history:", dispatch))
|
|
390
|
-
);
|
|
391
|
-
var getSingleDeployment = createAppAsyncThunk(
|
|
392
|
-
`${sliceName2}/getSingleDeployment`,
|
|
393
|
-
(id, { dispatch, getState }) => general_api_default.get(`${deploymentsApiUrl}/deployments/${id}`).then(({ data }) => {
|
|
394
|
-
const { deployments } = transformDeployments([data], getState().deployments.byId);
|
|
395
|
-
return Promise.resolve(dispatch(actions2.receivedDeployment(deployments[id])));
|
|
396
|
-
})
|
|
397
|
-
);
|
|
398
|
-
var getDeviceLog = createAppAsyncThunk(
|
|
399
|
-
`${sliceName2}/getDeviceLog`,
|
|
400
|
-
({ deploymentId, deviceId }, { dispatch }) => general_api_default.get(`${deploymentsApiUrl}/deployments/${deploymentId}/devices/${deviceId}/log`).catch((e) => {
|
|
401
|
-
console.log("no log here", e);
|
|
402
|
-
return Promise.reject();
|
|
403
|
-
}).then(
|
|
404
|
-
({ data: log }) => Promise.all([Promise.resolve(dispatch(actions2.receivedDeploymentDeviceLog({ id: deploymentId, deviceId, log }))), Promise.resolve(log)])
|
|
405
|
-
)
|
|
406
|
-
);
|
|
407
|
-
var abortDeployment = createAppAsyncThunk(
|
|
408
|
-
`${sliceName2}/abortDeployment`,
|
|
409
|
-
(deploymentId, { dispatch, getState }) => general_api_default.put(`${deploymentsApiUrl}/deployments/${deploymentId}/status`, { status: "aborted" }).then(() => {
|
|
410
|
-
const deploymentsByStatus = getDeploymentsByStatus(getState());
|
|
411
|
-
let status = DEPLOYMENT_STATES.pending;
|
|
412
|
-
let index = deploymentsByStatus.pending.deploymentIds.findIndex((id) => id === deploymentId);
|
|
413
|
-
if (index < 0) {
|
|
414
|
-
status = DEPLOYMENT_STATES.inprogress;
|
|
415
|
-
index = deploymentsByStatus.inprogress.deploymentIds.findIndex((id) => id === deploymentId);
|
|
416
|
-
}
|
|
417
|
-
const deploymentIds = [...deploymentsByStatus[status].deploymentIds.slice(0, index), ...deploymentsByStatus[status].deploymentIds.slice(index + 1)];
|
|
418
|
-
const deploymentsById = getDeploymentsById(getState());
|
|
419
|
-
const deployments = deploymentIds.reduce((accu, id) => {
|
|
420
|
-
accu[id] = deploymentsById[id];
|
|
421
|
-
return accu;
|
|
422
|
-
}, {});
|
|
423
|
-
const total = Math.max(deploymentsByStatus[status].total - 1, 0);
|
|
424
|
-
return Promise.all([
|
|
425
|
-
dispatch(actions2.receivedDeployments(deployments)),
|
|
426
|
-
dispatch(actions2.receivedDeploymentsForStatus({ deploymentIds, status, total })),
|
|
427
|
-
dispatch(actions2.removedDeployment(deploymentId)),
|
|
428
|
-
dispatch(setSnackbar("The deployment was successfully aborted"))
|
|
429
|
-
]);
|
|
430
|
-
}).catch((err) => commonErrorHandler(err, "There was an error while aborting the deployment:", dispatch))
|
|
431
|
-
);
|
|
432
|
-
var updateDeploymentControlMap = createAppAsyncThunk(
|
|
433
|
-
`${sliceName2}/updateDeploymentControlMap`,
|
|
434
|
-
({ deploymentId, updateControlMap }, { dispatch }) => general_api_default.patch(`${deploymentsApiUrl}/deployments/${deploymentId}`, { update_control_map: updateControlMap }).catch((err) => commonErrorHandler(err, "There was an error while updating the deployment status:", dispatch)).then(() => Promise.resolve(dispatch(getSingleDeployment(deploymentId))))
|
|
435
|
-
);
|
|
436
|
-
var setDeploymentsState = createAppAsyncThunk(`${sliceName2}/setDeploymentsState`, (selection, { dispatch, getState }) => {
|
|
437
|
-
const { page, perPage, ...selectionState } = selection;
|
|
438
|
-
const currentState = getState().deployments.selectionState;
|
|
439
|
-
const nextState = {
|
|
440
|
-
...currentState,
|
|
441
|
-
...selectionState,
|
|
442
|
-
...Object.keys(DEPLOYMENT_STATES).reduce((accu, item) => {
|
|
443
|
-
accu[item] = {
|
|
444
|
-
...currentState[item],
|
|
445
|
-
...selectionState[item]
|
|
446
|
-
};
|
|
447
|
-
return accu;
|
|
448
|
-
}, {}),
|
|
449
|
-
general: {
|
|
450
|
-
...currentState.general,
|
|
451
|
-
...selectionState.general
|
|
452
|
-
}
|
|
453
|
-
};
|
|
454
|
-
const tasks = [dispatch(actions2.setDeploymentsState(nextState))];
|
|
455
|
-
if (nextState.selectedId && currentState.selectedId !== nextState.selectedId) {
|
|
456
|
-
tasks.push(dispatch(getSingleDeployment(nextState.selectedId)));
|
|
457
|
-
}
|
|
458
|
-
return Promise.all(tasks);
|
|
459
|
-
});
|
|
460
|
-
var deltaAttributeMappings = [
|
|
461
|
-
{ here: "compressionLevel", there: "compression_level" },
|
|
462
|
-
{ here: "disableChecksum", there: "disable_checksum" },
|
|
463
|
-
{ here: "disableDecompression", there: "disable_external_decompression" },
|
|
464
|
-
{ here: "sourceWindow", there: "source_window_size" },
|
|
465
|
-
{ here: "inputWindow", there: "input_window_size" },
|
|
466
|
-
{ here: "duplicatesWindow", there: "compression_duplicates_window" },
|
|
467
|
-
{ here: "instructionBuffer", there: "instruction_buffer_size" }
|
|
468
|
-
];
|
|
469
|
-
var mapExternalDeltaConfig = (config = {}) => deltaAttributeMappings.reduce((accu, { here, there }) => {
|
|
470
|
-
if (config[there] !== void 0) {
|
|
471
|
-
accu[here] = config[there];
|
|
472
|
-
}
|
|
473
|
-
return accu;
|
|
474
|
-
}, {});
|
|
475
|
-
var getDeploymentsConfig = createAppAsyncThunk(
|
|
476
|
-
`${sliceName2}/getDeploymentsConfig`,
|
|
477
|
-
(_, { dispatch, getState }) => general_api_default.get(`${deploymentsApiUrl}/config`).then(({ data }) => {
|
|
478
|
-
const oldConfig = getState().deployments.config;
|
|
479
|
-
const { delta = {} } = data;
|
|
480
|
-
const { binary_delta = {}, binary_delta_limits = {} } = delta;
|
|
481
|
-
const { xdelta_args = {} } = binary_delta;
|
|
482
|
-
const { xdelta_args_limits = {} } = binary_delta_limits;
|
|
483
|
-
const config = {
|
|
484
|
-
...oldConfig,
|
|
485
|
-
hasDelta: Boolean(delta.enabled),
|
|
486
|
-
binaryDelta: {
|
|
487
|
-
...oldConfig.binaryDelta,
|
|
488
|
-
...mapExternalDeltaConfig(xdelta_args)
|
|
489
|
-
},
|
|
490
|
-
binaryDeltaLimits: {
|
|
491
|
-
...oldConfig.binaryDeltaLimits,
|
|
492
|
-
...mapExternalDeltaConfig(xdelta_args_limits)
|
|
493
|
-
}
|
|
494
|
-
};
|
|
495
|
-
return Promise.resolve(dispatch(actions2.setDeploymentsConfig(config)));
|
|
496
|
-
})
|
|
497
|
-
);
|
|
498
|
-
var deepClean = (source) => Object.entries(source).reduce((accu, [key, value]) => {
|
|
499
|
-
if (value !== void 0) {
|
|
500
|
-
const cleanedValue = typeof value === "object" ? deepClean(value) : value;
|
|
501
|
-
if (cleanedValue === void 0 || typeof cleanedValue === "object" && isEmpty(cleanedValue)) {
|
|
502
|
-
return accu;
|
|
503
|
-
}
|
|
504
|
-
accu = { ...accu ?? {}, [key]: cleanedValue };
|
|
505
|
-
}
|
|
506
|
-
return accu;
|
|
507
|
-
}, void 0);
|
|
508
|
-
var saveDeltaDeploymentsConfig = createAppAsyncThunk(
|
|
509
|
-
`${sliceName2}/saveDeltaDeploymentsConfig`,
|
|
510
|
-
(config, { dispatch, getState }) => {
|
|
511
|
-
const configChange = {
|
|
512
|
-
xdelta_args: deltaAttributeMappings.reduce((accu, { here, there }) => {
|
|
513
|
-
if (config[here] !== void 0) {
|
|
514
|
-
accu[there] = config[here];
|
|
515
|
-
}
|
|
516
|
-
return accu;
|
|
517
|
-
}, {})
|
|
518
|
-
};
|
|
519
|
-
const result = deepClean(configChange);
|
|
520
|
-
if (!result) {
|
|
521
|
-
return Promise.resolve();
|
|
522
|
-
}
|
|
523
|
-
return general_api_default.put(`${deploymentsApiUrl}/config/binary_delta`, result).catch((err) => commonErrorHandler(err, "There was a problem storing your delta artifact generation configuration.", dispatch)).then(() => {
|
|
524
|
-
const oldConfig = getState().deployments.config;
|
|
525
|
-
const newConfig = {
|
|
526
|
-
...oldConfig,
|
|
527
|
-
binaryDelta: {
|
|
528
|
-
...oldConfig.binaryDelta,
|
|
529
|
-
...config
|
|
530
|
-
}
|
|
531
|
-
};
|
|
532
|
-
return Promise.all([dispatch(actions2.setDeploymentsConfig(newConfig)), dispatch(setSnackbar("Settings saved successfully"))]);
|
|
533
|
-
});
|
|
534
|
-
}
|
|
535
|
-
);
|
|
536
|
-
var generateDeploymentLogAnalysis = createAppAsyncThunk(
|
|
537
|
-
`${sliceName2}/generateDeploymentLogAnalysis`,
|
|
538
|
-
({ deploymentId, deviceId }, { dispatch, rejectWithValue }) => general_api_default.get(`${apiRoot}/v1alpha1/deployments/deployments/${deploymentId}/devices/${deviceId}/log/explain`, { timeout: 60 * TIMEOUTS.oneSecond }).then(({ data: result }) => Promise.resolve(result)).catch((err) => {
|
|
539
|
-
if (err.response.status === 429) {
|
|
540
|
-
return rejectWithValue(err.response);
|
|
541
|
-
}
|
|
542
|
-
commonErrorHandler(err, "There was an error analysing the deployment log:", dispatch);
|
|
543
|
-
})
|
|
544
|
-
);
|
|
545
|
-
|
|
546
|
-
// src/devicesSlice/thunks.tsx
|
|
547
|
-
import { Link } from "react-router-dom";
|
|
548
|
-
import { attributeDuplicateFilter, dateRangeToUnix, deepCompare as deepCompare2, getSnackbarMessage } from "@northern.tech/utils/helpers";
|
|
549
|
-
import { isCancel } from "axios";
|
|
550
|
-
import pluralize from "pluralize";
|
|
551
|
-
import { v4 as uuid } from "uuid";
|
|
552
|
-
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
553
|
-
var { cleanUpUpload, initUpload, setSnackbar: setSnackbar2, uploadProgress } = actions_default;
|
|
554
|
-
var { page: defaultPage2, perPage: defaultPerPage2 } = DEVICE_LIST_DEFAULTS;
|
|
555
|
-
var defaultAttributes = [
|
|
556
|
-
{ scope: "identity", attribute: "status" },
|
|
557
|
-
{ scope: "inventory", attribute: "artifact_name" },
|
|
558
|
-
{ scope: "inventory", attribute: "device_type" },
|
|
559
|
-
{ scope: "inventory", attribute: "mender_is_gateway" },
|
|
560
|
-
{ scope: "inventory", attribute: "mender_gateway_system_id" },
|
|
561
|
-
{ scope: "inventory", attribute: rootfsImageVersion },
|
|
562
|
-
{ scope: "monitor", attribute: "alerts" },
|
|
563
|
-
{ scope: "system", attribute: "created_ts" },
|
|
564
|
-
{ scope: "system", attribute: "updated_ts" },
|
|
565
|
-
{ scope: "system", attribute: "check_in_time" },
|
|
566
|
-
{ scope: "system", attribute: "group" },
|
|
567
|
-
{ scope: "tags", attribute: "name" }
|
|
568
|
-
];
|
|
569
|
-
var getGroups = createAppAsyncThunk(
|
|
570
|
-
`${sliceName3}/getGroups`,
|
|
571
|
-
(_, { dispatch, getState }) => general_api_default.get(`${inventoryApiUrl}/groups`).then((res) => {
|
|
572
|
-
const state = getGroupsById(getState());
|
|
573
|
-
const dynamicGroups = Object.entries(state).reduce((accu, [id, group]) => {
|
|
574
|
-
if (group.id || group.filters?.length && id !== UNGROUPED_GROUP.id) {
|
|
575
|
-
accu[id] = group;
|
|
576
|
-
}
|
|
577
|
-
return accu;
|
|
578
|
-
}, {});
|
|
579
|
-
const groups = res.data.reduce((accu, group) => {
|
|
580
|
-
accu[group] = { deviceIds: [], filters: [], total: 0, ...state[group] };
|
|
581
|
-
return accu;
|
|
582
|
-
}, dynamicGroups);
|
|
583
|
-
const filters = [{ key: "group", value: res.data, operator: DEVICE_FILTERING_OPTIONS.$nin.key, scope: "system" }];
|
|
584
|
-
return Promise.all([
|
|
585
|
-
dispatch(actions3.receivedGroups(groups)),
|
|
586
|
-
dispatch(getDevicesByStatus({ filterSelection: filters, group: "", page: 1, perPage: 1, status: void 0 }))
|
|
587
|
-
]).then((promises) => {
|
|
588
|
-
const devicesRetrieval = promises[promises.length - 1] || [];
|
|
589
|
-
const { payload } = devicesRetrieval || {};
|
|
590
|
-
const result = payload[payload.length - 1] || {};
|
|
591
|
-
if (!result.total) {
|
|
592
|
-
return Promise.resolve();
|
|
593
|
-
}
|
|
594
|
-
return Promise.resolve(
|
|
595
|
-
dispatch(
|
|
596
|
-
actions3.addGroup({
|
|
597
|
-
groupName: UNGROUPED_GROUP.id,
|
|
598
|
-
group: { filters: [{ key: "group", value: res.data, operator: DEVICE_FILTERING_OPTIONS.$nin.key, scope: "system" }] }
|
|
599
|
-
})
|
|
600
|
-
)
|
|
601
|
-
);
|
|
602
|
-
});
|
|
603
|
-
})
|
|
604
|
-
);
|
|
605
|
-
var addDevicesToGroup = createAppAsyncThunk(
|
|
606
|
-
`${sliceName3}/addDevicesToGroup`,
|
|
607
|
-
({ group, deviceIds, isCreation }, { dispatch }) => general_api_default.patch(`${inventoryApiUrl}/groups/${group}/devices`, deviceIds).then(() => dispatch(actions3.addToGroup({ group, deviceIds }))).finally(() => isCreation ? Promise.resolve(dispatch(getGroups())) : {})
|
|
608
|
-
);
|
|
609
|
-
var removeDevicesFromGroup = createAppAsyncThunk(
|
|
610
|
-
`${sliceName3}/removeDevicesFromGroup`,
|
|
611
|
-
({ group, deviceIds }, { dispatch }) => general_api_default.delete(`${inventoryApiUrl}/groups/${group}/devices`, deviceIds).then(
|
|
612
|
-
() => Promise.all([
|
|
613
|
-
dispatch(actions3.removeFromGroup({ group, deviceIds })),
|
|
614
|
-
dispatch(
|
|
615
|
-
setSnackbar2({
|
|
616
|
-
message: `The ${pluralize("devices", deviceIds.length)} ${pluralize("were", deviceIds.length)} removed from the group`,
|
|
617
|
-
autoHideDuration: TIMEOUTS.fiveSeconds
|
|
618
|
-
})
|
|
619
|
-
)
|
|
620
|
-
])
|
|
621
|
-
)
|
|
622
|
-
);
|
|
623
|
-
var getGroupNotification = (newGroup, selectedGroup) => {
|
|
624
|
-
const successMessage = "The group was updated successfully";
|
|
625
|
-
if (newGroup === selectedGroup) {
|
|
626
|
-
return { message: successMessage, autoHideDuration: TIMEOUTS.fiveSeconds };
|
|
627
|
-
}
|
|
628
|
-
return {
|
|
629
|
-
action: "",
|
|
630
|
-
autoHideDuration: TIMEOUTS.fiveSeconds,
|
|
631
|
-
message: /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
632
|
-
successMessage,
|
|
633
|
-
" - ",
|
|
634
|
-
/* @__PURE__ */ jsx(Link, { to: `/devices?inventory=group:eq:${newGroup}`, children: "click here" }),
|
|
635
|
-
" to see it."
|
|
636
|
-
] }),
|
|
637
|
-
preventClickToCopy: true
|
|
638
|
-
};
|
|
639
|
-
};
|
|
640
|
-
var addStaticGroup = createAppAsyncThunk(
|
|
641
|
-
`${sliceName3}/addStaticGroup`,
|
|
642
|
-
({ group, devices }, { dispatch, getState }) => Promise.resolve(dispatch(addDevicesToGroup({ group, deviceIds: devices.map(({ id }) => id), isCreation: true }))).then(
|
|
643
|
-
() => Promise.resolve(
|
|
644
|
-
dispatch(
|
|
645
|
-
actions3.addGroup({
|
|
646
|
-
group: { deviceIds: [], total: 0, filters: [], ...getState().devices.groups.byId[group] },
|
|
647
|
-
groupName: group
|
|
648
|
-
})
|
|
649
|
-
)
|
|
650
|
-
).then(
|
|
651
|
-
() => Promise.all([
|
|
652
|
-
dispatch(setDeviceListState({ setOnly: true })),
|
|
653
|
-
dispatch(getGroups()),
|
|
654
|
-
dispatch(setSnackbar2(getGroupNotification(group, getState().devices.groups.selectedGroup)))
|
|
655
|
-
])
|
|
656
|
-
)
|
|
657
|
-
).catch((err) => commonErrorHandler(err, `Group could not be updated:`, dispatch))
|
|
658
|
-
);
|
|
659
|
-
var removeReportsByGroupName = createAppAsyncThunk(`${sliceName3}/removeReportsByGroupName`, (groupName, { dispatch, getState }) => {
|
|
660
|
-
if (!groupName) return Promise.resolve();
|
|
661
|
-
const reports = getDeviceReportsForUser(getState());
|
|
662
|
-
const filteredReports = reports.filter((report) => report.group !== groupName);
|
|
663
|
-
dispatch(saveUserSettings({ reports: filteredReports }));
|
|
664
|
-
});
|
|
665
|
-
var removeStaticGroup = createAppAsyncThunk(
|
|
666
|
-
`${sliceName3}/removeStaticGroup`,
|
|
667
|
-
(groupName, { dispatch }) => general_api_default.delete(`${inventoryApiUrl}/groups/${groupName}`).then(
|
|
668
|
-
() => Promise.all([
|
|
669
|
-
dispatch(actions3.removeGroup(groupName)),
|
|
670
|
-
dispatch(removeReportsByGroupName(groupName)),
|
|
671
|
-
dispatch(getGroups()),
|
|
672
|
-
dispatch(setSnackbar2({ message: "Group was removed successfully", autoHideDuration: TIMEOUTS.fiveSeconds }))
|
|
673
|
-
])
|
|
674
|
-
)
|
|
675
|
-
);
|
|
676
|
-
var getDynamicGroup = createAppAsyncThunk(
|
|
677
|
-
`${sliceName3}/getDynamicGroupById`,
|
|
678
|
-
(id, { dispatch }) => general_api_default.get(`${inventoryApiUrlV2}/filters/${id}`).catch((err) => {
|
|
679
|
-
if (err.response && err.response.status === 404) {
|
|
680
|
-
throw new Error("Request failed with status code 404");
|
|
681
|
-
}
|
|
682
|
-
return commonErrorHandler(err, `Error retrieving the group: `, dispatch, commonErrorFallback);
|
|
683
|
-
})
|
|
684
|
-
);
|
|
685
|
-
var getDynamicGroups = createAppAsyncThunk(
|
|
686
|
-
`${sliceName3}/getDynamicGroups`,
|
|
687
|
-
(_, { dispatch, getState }) => general_api_default.get(`${inventoryApiUrlV2}/filters?per_page=${MAX_PAGE_SIZE}`).then(({ data: filters }) => {
|
|
688
|
-
const state = getGroupsById(getState());
|
|
689
|
-
const staticGroups = Object.entries(state).reduce((accu, [id, group]) => {
|
|
690
|
-
if (!(group.id || group.filters?.length)) {
|
|
691
|
-
accu[id] = group;
|
|
692
|
-
}
|
|
693
|
-
return accu;
|
|
694
|
-
}, {});
|
|
695
|
-
const groups = (filters || []).reduce((accu, filter) => {
|
|
696
|
-
accu[filter.name] = {
|
|
697
|
-
deviceIds: [],
|
|
698
|
-
total: 0,
|
|
699
|
-
...state[filter.name],
|
|
700
|
-
id: filter.id,
|
|
701
|
-
filters: mapTermsToFilters(filter.terms)
|
|
702
|
-
};
|
|
703
|
-
return accu;
|
|
704
|
-
}, staticGroups);
|
|
705
|
-
return Promise.resolve(dispatch(actions3.receivedGroups(groups)));
|
|
706
|
-
}).catch(() => console.log("Dynamic group retrieval failed - likely accessing a non-enterprise backend"))
|
|
707
|
-
);
|
|
708
|
-
var addDynamicGroup = createAppAsyncThunk(
|
|
709
|
-
`${sliceName3}/addDynamicGroup`,
|
|
710
|
-
({ groupName, filterPredicates }, { dispatch, getState }) => general_api_default.post(`${inventoryApiUrlV2}/filters`, { name: groupName, terms: mapFiltersToTerms(filterPredicates) }).then(
|
|
711
|
-
(res) => Promise.resolve(
|
|
712
|
-
dispatch(
|
|
713
|
-
actions3.addGroup({
|
|
714
|
-
groupName,
|
|
715
|
-
group: {
|
|
716
|
-
id: res.headers[headerNames.location].substring(res.headers[headerNames.location].lastIndexOf("/") + 1),
|
|
717
|
-
filters: filterPredicates
|
|
718
|
-
}
|
|
719
|
-
})
|
|
720
|
-
)
|
|
721
|
-
).then(() => {
|
|
722
|
-
const { cleanedFilters } = getGroupFilters(groupName, getState().devices.groups);
|
|
723
|
-
return Promise.all([
|
|
724
|
-
dispatch(actions3.setDeviceFilters(cleanedFilters)),
|
|
725
|
-
dispatch(setSnackbar2(getGroupNotification(groupName, getState().devices.groups.selectedGroup))),
|
|
726
|
-
dispatch(getDynamicGroups())
|
|
727
|
-
]);
|
|
728
|
-
})
|
|
729
|
-
).catch((err) => commonErrorHandler(err, `Group could not be updated:`, dispatch))
|
|
730
|
-
);
|
|
731
|
-
var updateDynamicGroup = createAppAsyncThunk(
|
|
732
|
-
`${sliceName3}/updateDynamicGroup`,
|
|
733
|
-
({ groupName, filterPredicates }, { dispatch, getState }) => {
|
|
734
|
-
const filterId = getState().devices.groups.byId[groupName].id;
|
|
735
|
-
return general_api_default.delete(`${inventoryApiUrlV2}/filters/${filterId}`).then(
|
|
736
|
-
() => Promise.resolve(dispatch(addDynamicGroup({ groupName, filterPredicates })))
|
|
737
|
-
);
|
|
738
|
-
}
|
|
739
|
-
);
|
|
740
|
-
var removeDynamicGroup = createAppAsyncThunk(`${sliceName3}/removeDynamicGroup`, (groupName, { dispatch, getState }) => {
|
|
741
|
-
const filterId = getState().devices.groups.byId[groupName].id;
|
|
742
|
-
return general_api_default.delete(`${inventoryApiUrlV2}/filters/${filterId}`).then(
|
|
743
|
-
() => Promise.all([
|
|
744
|
-
dispatch(actions3.removeGroup(groupName)),
|
|
745
|
-
dispatch(removeReportsByGroupName(groupName)),
|
|
746
|
-
dispatch(setSnackbar2({ message: "Group was removed successfully", autoHideDuration: TIMEOUTS.fiveSeconds }))
|
|
747
|
-
])
|
|
748
|
-
);
|
|
749
|
-
});
|
|
750
|
-
var getGroupFilters = (group, groupsState, filters = []) => {
|
|
751
|
-
const groupName = group === UNGROUPED_GROUP.id || group === UNGROUPED_GROUP.name ? UNGROUPED_GROUP.id : group;
|
|
752
|
-
const selectedGroup = groupsState.byId[groupName];
|
|
753
|
-
const groupFilterLength = selectedGroup?.filters?.length || 0;
|
|
754
|
-
const cleanedFilters = groupFilterLength ? [...filters, ...selectedGroup.filters || []].filter(filtersFilter) : filters;
|
|
755
|
-
return { cleanedFilters, groupName, selectedGroup, groupFilterLength };
|
|
756
|
-
};
|
|
757
|
-
var selectGroup = createAppAsyncThunk(
|
|
758
|
-
`${sliceName3}/selectGroup`,
|
|
759
|
-
({ group, filters = [] }, { dispatch, getState }) => {
|
|
760
|
-
const { cleanedFilters, groupName, selectedGroup, groupFilterLength } = getGroupFilters(group, getState().devices.groups, filters);
|
|
761
|
-
if (getSelectedGroup(getState()) === groupName && (filters.length === 0 && !groupFilterLength || filters.length === cleanedFilters.length)) {
|
|
762
|
-
return Promise.resolve();
|
|
763
|
-
}
|
|
764
|
-
const tasks = [];
|
|
765
|
-
if (groupFilterLength) {
|
|
766
|
-
tasks.push(dispatch(actions3.setDeviceFilters(cleanedFilters)));
|
|
767
|
-
} else {
|
|
768
|
-
tasks.push(dispatch(actions3.setDeviceFilters(filters)));
|
|
769
|
-
tasks.push(dispatch(getGroupDevices({ group: groupName, perPage: 1, shouldIncludeAllStates: true })));
|
|
770
|
-
}
|
|
771
|
-
const selectedGroupName = selectedGroup || !Object.keys(getGroupsById(getState())).length ? groupName : void 0;
|
|
772
|
-
tasks.push(dispatch(actions3.selectGroup(selectedGroupName)));
|
|
773
|
-
return Promise.all(tasks);
|
|
774
|
-
}
|
|
775
|
-
);
|
|
776
|
-
var getEarliestTs = (dateA = "", dateB = "") => !dateA || !dateB ? dateA || dateB : dateA < dateB ? dateA : dateB;
|
|
777
|
-
var reduceReceivedDevices = (devices, ids, state, status) => devices.reduce(
|
|
778
|
-
(accu, device) => {
|
|
779
|
-
const stateDevice = getDeviceById(state, device.id);
|
|
780
|
-
const {
|
|
781
|
-
attributes: storedAttributes = {},
|
|
782
|
-
identity_data: storedIdentity = {},
|
|
783
|
-
monitor: storedMonitor = {},
|
|
784
|
-
tags: storedTags = {},
|
|
785
|
-
group: storedGroup
|
|
786
|
-
} = stateDevice;
|
|
787
|
-
const { identity, inventory, monitor, system = {}, tags } = mapDeviceAttributes(device.attributes);
|
|
788
|
-
device.tags = { ...storedTags, ...tags };
|
|
789
|
-
device.group = system.group ?? storedGroup;
|
|
790
|
-
device.monitor = { ...storedMonitor, ...monitor };
|
|
791
|
-
device.identity_data = { ...storedIdentity, ...identity, ...device.identity_data ? device.identity_data : {} };
|
|
792
|
-
device.status = status ? status : device.status || identity.status;
|
|
793
|
-
device.check_in_time_rounded = system.check_in_time ?? stateDevice.check_in_time_rounded;
|
|
794
|
-
device.check_in_time_exact = device.check_in_time ?? stateDevice.check_in_time_exact;
|
|
795
|
-
device.created_ts = getEarliestTs(getEarliestTs(system.created_ts, device.created_ts), stateDevice.created_ts);
|
|
796
|
-
device.updated_ts = device.attributes ? device.updated_ts : stateDevice.updated_ts;
|
|
797
|
-
device.isNew = new Date(device.created_ts) > new Date(state.app.newThreshold);
|
|
798
|
-
device.isOffline = new Date(device.check_in_time_rounded) < new Date(state.app.offlineThreshold) || device.check_in_time_rounded === void 0;
|
|
799
|
-
device.attributes = device.attributes ? { ...storedAttributes, ...inventory } : storedAttributes;
|
|
800
|
-
accu.devicesById[device.id] = { ...stateDevice, ...device };
|
|
801
|
-
accu.ids.push(device.id);
|
|
802
|
-
return accu;
|
|
803
|
-
},
|
|
804
|
-
{ ids, devicesById: {} }
|
|
805
|
-
);
|
|
806
|
-
var getGroupDevices = createAppAsyncThunk(`${sliceName3}/getGroupDevices`, (options, { dispatch, getState }) => {
|
|
807
|
-
const { group, shouldIncludeAllStates, ...remainder } = options;
|
|
808
|
-
const { cleanedFilters: filterSelection } = getGroupFilters(group, getState().devices.groups);
|
|
809
|
-
return dispatch(
|
|
810
|
-
getDevicesByStatus({
|
|
811
|
-
...remainder,
|
|
812
|
-
filterSelection,
|
|
813
|
-
group,
|
|
814
|
-
status: shouldIncludeAllStates ? void 0 : DEVICE_STATES.accepted
|
|
815
|
-
})
|
|
816
|
-
).unwrap().then((results) => {
|
|
817
|
-
if (!group) {
|
|
818
|
-
return Promise.resolve();
|
|
819
|
-
}
|
|
820
|
-
const { deviceAccu, total } = results[results.length - 1];
|
|
821
|
-
const stateGroup = getState().devices.groups.byId[group];
|
|
822
|
-
if (!stateGroup && !total && !deviceAccu.ids.length) {
|
|
823
|
-
return Promise.resolve();
|
|
824
|
-
}
|
|
825
|
-
return Promise.resolve(
|
|
826
|
-
dispatch(
|
|
827
|
-
actions3.addGroup({
|
|
828
|
-
group: {
|
|
829
|
-
deviceIds: deviceAccu.ids.length === total || stateGroup && stateGroup.deviceIds && deviceAccu.ids.length > stateGroup.deviceIds ? deviceAccu.ids : stateGroup.deviceIds,
|
|
830
|
-
total
|
|
831
|
-
},
|
|
832
|
-
groupName: group
|
|
833
|
-
})
|
|
834
|
-
)
|
|
835
|
-
);
|
|
836
|
-
});
|
|
837
|
-
});
|
|
838
|
-
var getAllGroupDevices = createAppAsyncThunk(
|
|
839
|
-
`${sliceName3}/getAllGroupDevices`,
|
|
840
|
-
({ group, attribute }, { dispatch, getState }) => {
|
|
841
|
-
if (!group || !!group && (!getGroupsById(getState())[group] || getGroupsById(getState())[group].filters.length)) {
|
|
842
|
-
return Promise.resolve();
|
|
843
|
-
}
|
|
844
|
-
const { attributes, filterTerms } = prepareSearchArguments({
|
|
845
|
-
filters: [],
|
|
846
|
-
group,
|
|
847
|
-
state: getState(),
|
|
848
|
-
status: DEVICE_STATES.accepted
|
|
849
|
-
});
|
|
850
|
-
const getAllDevices = (perPage = MAX_PAGE_SIZE, page = defaultPage2, devices = []) => general_api_default.post(`${inventoryApiUrlV2}/filters/search`, {
|
|
851
|
-
page,
|
|
852
|
-
per_page: perPage,
|
|
853
|
-
filters: filterTerms,
|
|
854
|
-
attributes: [...attributes, { scope: "inventory", attribute }]
|
|
855
|
-
}).then((res) => {
|
|
856
|
-
const state = getState();
|
|
857
|
-
const deviceAccu = reduceReceivedDevices(res.data, devices, state);
|
|
858
|
-
dispatch(actions3.receivedDevices(deviceAccu.devicesById));
|
|
859
|
-
const total = Number(res.headers[headerNames.total]);
|
|
860
|
-
if (total > perPage * page) {
|
|
861
|
-
return getAllDevices(perPage, page + 1, deviceAccu.ids);
|
|
862
|
-
}
|
|
863
|
-
return Promise.resolve(dispatch(actions3.addGroup({ group: { deviceIds: deviceAccu.ids, total: deviceAccu.ids.length }, groupName: group })));
|
|
864
|
-
});
|
|
865
|
-
return getAllDevices();
|
|
866
|
-
}
|
|
867
|
-
);
|
|
868
|
-
var getAllDynamicGroupDevices = createAppAsyncThunk(
|
|
869
|
-
`${sliceName3}/getAllDynamicGroupDevices`,
|
|
870
|
-
({ group, attribute }, { dispatch, getState }) => {
|
|
871
|
-
if (!!group && (!getGroupsById(getState())[group] || !getGroupsById(getState())[group].filters.length)) {
|
|
872
|
-
return Promise.resolve();
|
|
873
|
-
}
|
|
874
|
-
const { attributes, filterTerms: filters } = prepareSearchArguments({
|
|
875
|
-
filters: getState().devices.groups.byId[group].filters,
|
|
876
|
-
state: getState(),
|
|
877
|
-
status: DEVICE_STATES.accepted
|
|
878
|
-
});
|
|
879
|
-
const getAllDevices = (perPage = MAX_PAGE_SIZE, page = defaultPage2, devices = []) => general_api_default.post(`${inventoryApiUrlV2}/filters/search`, {
|
|
880
|
-
page,
|
|
881
|
-
per_page: perPage,
|
|
882
|
-
filters,
|
|
883
|
-
attributes: [...attributes, { scope: "inventory", attribute }]
|
|
884
|
-
}).then((res) => {
|
|
885
|
-
const state = getState();
|
|
886
|
-
const deviceAccu = reduceReceivedDevices(res.data, devices, state);
|
|
887
|
-
dispatch(actions3.receivedDevices(deviceAccu.devicesById));
|
|
888
|
-
const total = Number(res.headers[headerNames.total]);
|
|
889
|
-
if (total > deviceAccu.ids.length) {
|
|
890
|
-
return getAllDevices(perPage, page + 1, deviceAccu.ids);
|
|
891
|
-
}
|
|
892
|
-
return Promise.resolve(dispatch(actions3.addGroup({ group: { deviceIds: deviceAccu.ids, total }, groupName: group })));
|
|
893
|
-
});
|
|
894
|
-
return getAllDevices();
|
|
895
|
-
}
|
|
896
|
-
);
|
|
897
|
-
var getDeviceById2 = createAppAsyncThunk(
|
|
898
|
-
`${sliceName3}/getDeviceById`,
|
|
899
|
-
(id, { dispatch, getState }) => general_api_default.get(`${inventoryApiUrl}/devices/${id}`).then((res) => {
|
|
900
|
-
const device = reduceReceivedDevices([res.data], [], getState()).devicesById[id];
|
|
901
|
-
device.etag = res.headers.etag;
|
|
902
|
-
dispatch(actions3.receivedDevice(device));
|
|
903
|
-
return Promise.resolve(device);
|
|
904
|
-
}).catch((err) => {
|
|
905
|
-
const errMsg = extractErrorMessage(err);
|
|
906
|
-
if (errMsg.includes("Not Found")) {
|
|
907
|
-
console.log(`${id} does not have any inventory information`);
|
|
908
|
-
const device = reduceReceivedDevices(
|
|
909
|
-
[
|
|
910
|
-
{
|
|
911
|
-
id,
|
|
912
|
-
attributes: [
|
|
913
|
-
{ name: "status", value: "decomissioned", scope: "identity" },
|
|
914
|
-
{ name: "decomissioned", value: "true", scope: "inventory" }
|
|
915
|
-
],
|
|
916
|
-
log: false
|
|
917
|
-
}
|
|
918
|
-
],
|
|
919
|
-
[],
|
|
920
|
-
getState()
|
|
921
|
-
).devicesById[id];
|
|
922
|
-
dispatch(actions3.receivedDevice(device));
|
|
923
|
-
}
|
|
924
|
-
})
|
|
925
|
-
);
|
|
926
|
-
var getDeviceInfo = createAppAsyncThunk(`${sliceName3}/getDeviceInfo`, (deviceId, { dispatch, getState }) => {
|
|
927
|
-
const device = getDeviceById(getState(), deviceId);
|
|
928
|
-
const { hasDeviceConfig, hasDeviceConnect, hasMonitor } = getTenantCapabilities(getState());
|
|
929
|
-
const { canConfigure } = getUserCapabilities(getState());
|
|
930
|
-
const integrations = getDeviceTwinIntegrations(getState());
|
|
931
|
-
const tasks = [
|
|
932
|
-
dispatch(getDeviceAuth(deviceId)),
|
|
933
|
-
dispatch(getDeviceById2(deviceId)),
|
|
934
|
-
...integrations.map((integration) => dispatch(getDeviceTwin({ deviceId, integration })))
|
|
935
|
-
];
|
|
936
|
-
if (hasDeviceConfig && canConfigure && (device.status === DEVICE_STATES.accepted || device.status === DEVICE_STATES.preauth)) {
|
|
937
|
-
tasks.push(dispatch(getDeviceConfig(deviceId)));
|
|
938
|
-
}
|
|
939
|
-
if (device.status === DEVICE_STATES.accepted) {
|
|
940
|
-
if (hasDeviceConnect) {
|
|
941
|
-
tasks.push(dispatch(getDeviceConnect(deviceId)));
|
|
942
|
-
}
|
|
943
|
-
if (hasMonitor) {
|
|
944
|
-
tasks.push(dispatch(getLatestDeviceAlerts({ id: deviceId })));
|
|
945
|
-
tasks.push(dispatch(getDeviceMonitorConfig(deviceId)));
|
|
946
|
-
}
|
|
947
|
-
}
|
|
948
|
-
return Promise.all(tasks);
|
|
949
|
-
});
|
|
950
|
-
var getAllDeviceCounts = createAppAsyncThunk(
|
|
951
|
-
`${sliceName3}/getAllDeviceCounts`,
|
|
952
|
-
(_, { dispatch }) => general_api_default.get(`${inventoryApiUrlV2}/statistics`).then(({ data }) => {
|
|
953
|
-
const { devices_by_status } = data;
|
|
954
|
-
Object.entries(devices_by_status).map(([status, countsPerTier]) => dispatch(actions3.setDevicesCountByStatus({ countsPerTier, status })));
|
|
955
|
-
return;
|
|
956
|
-
})
|
|
957
|
-
);
|
|
958
|
-
var getDeviceLimits = createAppAsyncThunk(
|
|
959
|
-
`${sliceName3}/getDeviceLimit`,
|
|
960
|
-
(_, { dispatch }) => general_api_default.get(`${deviceAuthV2}/limits/devices`).then((res) => dispatch(actions3.setDeviceLimits(res.data)))
|
|
961
|
-
);
|
|
962
|
-
var setDeviceListState = createAppAsyncThunk(
|
|
963
|
-
`${sliceName3}/setDeviceListState`,
|
|
964
|
-
({ shouldSelectDevices = true, forceRefresh, fetchAuth = true, ...selectionState }, { dispatch, getState }) => {
|
|
965
|
-
const currentState = getDeviceListState(getState());
|
|
966
|
-
const refreshTrigger = forceRefresh ? !currentState.refreshTrigger : selectionState.refreshTrigger;
|
|
967
|
-
const nextState = {
|
|
968
|
-
...currentState,
|
|
969
|
-
setOnly: false,
|
|
970
|
-
refreshTrigger,
|
|
971
|
-
...selectionState,
|
|
972
|
-
sort: { ...currentState.sort, ...selectionState.sort }
|
|
973
|
-
};
|
|
974
|
-
const tasks = [];
|
|
975
|
-
const { isLoading: currentLoading, deviceIds: currentDevices, selection: currentSelection, ...currentRequestState } = currentState;
|
|
976
|
-
const { isLoading: nextLoading, deviceIds: nextDevices, selection: nextSelection, ...nextRequestState } = nextState;
|
|
977
|
-
if (!nextState.setOnly && !deepCompare2(currentRequestState, nextRequestState)) {
|
|
978
|
-
const { direction: sortDown = SORTING_OPTIONS.desc, key: sortCol, scope: sortScope = "" } = nextState.sort ?? {};
|
|
979
|
-
const sortBy = sortCol ? [{ attribute: sortCol, order: sortDown, scope: sortScope }] : void 0;
|
|
980
|
-
const applicableSelectedState = nextState.state === ALL_DEVICE_STATES ? void 0 : nextState.state;
|
|
981
|
-
nextState.isLoading = true;
|
|
982
|
-
tasks.push(
|
|
983
|
-
dispatch(getDevicesByStatus({ ...nextState, status: applicableSelectedState, sortOptions: sortBy, fetchAuth })).unwrap().then((results) => {
|
|
984
|
-
const { deviceAccu, total } = results[results.length - 1];
|
|
985
|
-
const devicesState = shouldSelectDevices ? { deviceIds: deviceAccu.ids, total, isLoading: false } : { isLoading: false };
|
|
986
|
-
return Promise.resolve(dispatch(actions3.setDeviceListState(devicesState)));
|
|
987
|
-
}).catch(() => Promise.resolve({ isLoading: false }))
|
|
988
|
-
);
|
|
989
|
-
}
|
|
990
|
-
if (currentState.page !== nextState.page || currentState.perPage > nextState.perPage || currentState.state !== nextState.state || !deepCompare2(currentState.sort, nextState.sort)) {
|
|
991
|
-
nextState.selection = [];
|
|
992
|
-
}
|
|
993
|
-
tasks.push(dispatch(actions3.setDeviceListState(nextState)));
|
|
994
|
-
return Promise.all(tasks);
|
|
995
|
-
}
|
|
996
|
-
);
|
|
997
|
-
var getDevicesByStatus = createAppAsyncThunk(
|
|
998
|
-
`${sliceName3}/getDevicesByStatus`,
|
|
999
|
-
(options, { dispatch, getState }) => {
|
|
1000
|
-
const {
|
|
1001
|
-
status,
|
|
1002
|
-
fetchAuth = true,
|
|
1003
|
-
filterSelection,
|
|
1004
|
-
group,
|
|
1005
|
-
selectedIssues = [],
|
|
1006
|
-
page = defaultPage2,
|
|
1007
|
-
perPage = defaultPerPage2,
|
|
1008
|
-
sortOptions = [],
|
|
1009
|
-
selectedAttributes = getSelectedDeviceAttribute(getState())
|
|
1010
|
-
} = options;
|
|
1011
|
-
const state = getState();
|
|
1012
|
-
const { applicableFilters, filterTerms } = convertDeviceListStateToFilters({
|
|
1013
|
-
filters: filterSelection ?? getDeviceFilters(state),
|
|
1014
|
-
group: group ?? getSelectedGroup(state),
|
|
1015
|
-
groups: state.devices.groups,
|
|
1016
|
-
offlineThreshold: state.app.offlineThreshold,
|
|
1017
|
-
selectedIssues,
|
|
1018
|
-
status
|
|
1019
|
-
});
|
|
1020
|
-
const attributes = [...defaultAttributes, getIdAttribute(getState()), ...selectedAttributes];
|
|
1021
|
-
return general_api_default.post(`${inventoryApiUrlV2}/filters/search`, {
|
|
1022
|
-
page,
|
|
1023
|
-
per_page: perPage,
|
|
1024
|
-
filters: filterTerms,
|
|
1025
|
-
sort: sortOptions,
|
|
1026
|
-
attributes
|
|
1027
|
-
}).then((response) => {
|
|
1028
|
-
const state2 = getState();
|
|
1029
|
-
const deviceAccu = reduceReceivedDevices(response.data, [], state2, status);
|
|
1030
|
-
let total = !applicableFilters.length ? Number(response.headers[headerNames.total]) : 0;
|
|
1031
|
-
if (status && state2.devices.byStatus[status].counts.total === deviceAccu.ids.length) {
|
|
1032
|
-
total = deviceAccu.ids.length;
|
|
1033
|
-
}
|
|
1034
|
-
const tasks = [dispatch(actions3.receivedDevices(deviceAccu.devicesById))];
|
|
1035
|
-
if (status) {
|
|
1036
|
-
tasks.push(dispatch(actions3.setDevicesByStatus({ deviceIds: deviceAccu.ids, status, total })));
|
|
1037
|
-
}
|
|
1038
|
-
const receivedDevices = Object.values(deviceAccu.devicesById);
|
|
1039
|
-
if (receivedDevices.length && fetchAuth) {
|
|
1040
|
-
tasks.push(dispatch(getDevicesWithAuth(receivedDevices)));
|
|
1041
|
-
}
|
|
1042
|
-
tasks.push(Promise.resolve({ deviceAccu, total: Number(response.headers[headerNames.total]) }));
|
|
1043
|
-
return Promise.all(tasks);
|
|
1044
|
-
}).catch((err) => commonErrorHandler(err, `${status} devices couldn't be loaded.`, dispatch, commonErrorFallback));
|
|
1045
|
-
}
|
|
1046
|
-
);
|
|
1047
|
-
var getAllDevicesByStatus = createAppAsyncThunk(
|
|
1048
|
-
`${sliceName3}/getAllDevicesByStatus`,
|
|
1049
|
-
({ status, attribute }, { dispatch, getState }) => {
|
|
1050
|
-
const attributes = [...defaultAttributes, getIdAttribute(getState())];
|
|
1051
|
-
const getAllDevices = (perPage = MAX_PAGE_SIZE, page = 1, devices = []) => general_api_default.post(`${inventoryApiUrlV2}/filters/search`, {
|
|
1052
|
-
page,
|
|
1053
|
-
per_page: perPage,
|
|
1054
|
-
filters: mapFiltersToTerms([{ key: "status", value: status, operator: DEVICE_FILTERING_OPTIONS.$eq.key, scope: "identity" }]),
|
|
1055
|
-
attributes: [...attributes, { scope: "inventory", attribute }]
|
|
1056
|
-
}).then((res) => {
|
|
1057
|
-
const state = getState();
|
|
1058
|
-
const deviceAccu = reduceReceivedDevices(res.data, devices, state, status);
|
|
1059
|
-
dispatch(actions3.receivedDevices(deviceAccu.devicesById));
|
|
1060
|
-
const total = Number(res.headers[headerNames.total]);
|
|
1061
|
-
if (total > state.deployments.deploymentDeviceLimit) {
|
|
1062
|
-
return Promise.resolve();
|
|
1063
|
-
}
|
|
1064
|
-
if (total > perPage * page) {
|
|
1065
|
-
return getAllDevices(perPage, page + 1, deviceAccu.ids);
|
|
1066
|
-
}
|
|
1067
|
-
return Promise.resolve();
|
|
1068
|
-
});
|
|
1069
|
-
return getAllDevices();
|
|
1070
|
-
}
|
|
1071
|
-
);
|
|
1072
|
-
var searchDevices = createAppAsyncThunk(`${sliceName3}/searchDevices`, (passedOptions = {}, { dispatch, getState }) => {
|
|
1073
|
-
const state = getState();
|
|
1074
|
-
const options = { ...state.app.searchState, ...passedOptions };
|
|
1075
|
-
const { page = defaultPage2, searchTerm, sortOptions = [] } = options;
|
|
1076
|
-
const { columnSelection = [] } = getUserSettings(state);
|
|
1077
|
-
const selectedAttributes = columnSelection.map((column) => ({ attribute: column.key, scope: column.scope }));
|
|
1078
|
-
const attributes = attributeDuplicateFilter([...defaultAttributes, getIdAttribute(state), ...selectedAttributes], "attribute");
|
|
1079
|
-
return general_api_default.post(`${inventoryApiUrlV2}/filters/search`, {
|
|
1080
|
-
page,
|
|
1081
|
-
per_page: 10,
|
|
1082
|
-
filters: [],
|
|
1083
|
-
sort: sortOptions,
|
|
1084
|
-
text: searchTerm,
|
|
1085
|
-
attributes
|
|
1086
|
-
}).then((response) => {
|
|
1087
|
-
const deviceAccu = reduceReceivedDevices(response.data, [], getState());
|
|
1088
|
-
return Promise.all([
|
|
1089
|
-
dispatch(actions3.receivedDevices(deviceAccu.devicesById)),
|
|
1090
|
-
Promise.resolve({ deviceIds: deviceAccu.ids, searchTotal: Number(response.headers[headerNames.total]) })
|
|
1091
|
-
]);
|
|
1092
|
-
}).catch((err) => commonErrorHandler(err, `devices couldn't be searched.`, dispatch, commonErrorFallback));
|
|
1093
|
-
});
|
|
1094
|
-
var ATTRIBUTE_LIST_CUTOFF = 100;
|
|
1095
|
-
var attributeReducer = (attributes = []) => attributes.slice(0, ATTRIBUTE_LIST_CUTOFF).reduce(
|
|
1096
|
-
(accu, { name, scope }) => {
|
|
1097
|
-
if (!accu[scope]) {
|
|
1098
|
-
accu[scope] = [];
|
|
1099
|
-
}
|
|
1100
|
-
accu[scope].push(name);
|
|
1101
|
-
return accu;
|
|
1102
|
-
},
|
|
1103
|
-
{ identity: [], inventory: [], system: [], tags: [] }
|
|
1104
|
-
);
|
|
1105
|
-
var getDeviceAttributes = createAppAsyncThunk(
|
|
1106
|
-
`${sliceName3}/getDeviceAttributes`,
|
|
1107
|
-
(_, { dispatch }) => general_api_default.get(`${inventoryApiUrlV2}/filters/attributes`).then(({ data }) => {
|
|
1108
|
-
const { identity: identityAttributes, inventory: inventoryAttributes, system: systemAttributes, tags: tagAttributes } = attributeReducer(data || []);
|
|
1109
|
-
return dispatch(actions3.setFilterAttributes({ identityAttributes, inventoryAttributes, systemAttributes, tagAttributes }));
|
|
1110
|
-
})
|
|
1111
|
-
);
|
|
1112
|
-
var initializeDistributionData = (report, groups, devices, totalDeviceCount) => {
|
|
1113
|
-
const { attribute, group = "", software = "" } = report;
|
|
1114
|
-
const effectiveAttribute = software ? software : attribute;
|
|
1115
|
-
const { deviceIds, total = 0 } = groups[group] || {};
|
|
1116
|
-
const relevantDevices = deviceIds ? deviceIds.map((id) => devices[id]) : Object.values(devices);
|
|
1117
|
-
const distributionByAttribute = relevantDevices.reduce((accu, item) => {
|
|
1118
|
-
if (!item.attributes || item.status !== DEVICE_STATES.accepted) return accu;
|
|
1119
|
-
const attributeValue = item.attributes[effectiveAttribute];
|
|
1120
|
-
if (!accu[attributeValue]) {
|
|
1121
|
-
accu[attributeValue] = 0;
|
|
1122
|
-
}
|
|
1123
|
-
accu[attributeValue] = accu[attributeValue] + 1;
|
|
1124
|
-
return accu;
|
|
1125
|
-
}, {});
|
|
1126
|
-
const distributionByAttributeSorted = Object.entries(distributionByAttribute).sort((pairA, pairB) => pairB[1] - pairA[1]);
|
|
1127
|
-
const items = distributionByAttributeSorted.map(([key, count]) => ({ key, count }));
|
|
1128
|
-
const dataCount = items.reduce((accu, item) => accu + item.count, 0);
|
|
1129
|
-
const otherCount = (groups[group] ? total : totalDeviceCount) - dataCount;
|
|
1130
|
-
return { items, otherCount, total: otherCount + dataCount };
|
|
1131
|
-
};
|
|
1132
|
-
var updateReportData = createAppAsyncThunk(`${sliceName3}/updateReportData`, (reportIndex, { dispatch, getState }) => {
|
|
1133
|
-
const reports = getDeviceReportsForUser(getState());
|
|
1134
|
-
const report = reports[reportIndex];
|
|
1135
|
-
const { group = "" } = report;
|
|
1136
|
-
const devicesById = getDevicesById(getState());
|
|
1137
|
-
const groups = getGroupsById(getState());
|
|
1138
|
-
const { accepted: acceptedDevicesCount } = getDeviceCountsByStatus(getState());
|
|
1139
|
-
const totalDeviceCount = groups[group] ? groups[group].total : acceptedDevicesCount;
|
|
1140
|
-
const reportsData = getDeviceReports(getState());
|
|
1141
|
-
const newReports = [...reportsData];
|
|
1142
|
-
newReports[reportIndex] = initializeDistributionData(report, groups, devicesById, totalDeviceCount);
|
|
1143
|
-
return Promise.resolve(dispatch(actions3.setDeviceReports(newReports)));
|
|
1144
|
-
});
|
|
1145
|
-
var getReportDataWithoutBackendSupport = createAppAsyncThunk(
|
|
1146
|
-
`${sliceName3}/getReportDataWithoutBackendSupport`,
|
|
1147
|
-
(reportIndex, { dispatch, getState }) => {
|
|
1148
|
-
const reports = getDeviceReportsForUser(getState());
|
|
1149
|
-
const report = reports[reportIndex];
|
|
1150
|
-
if (!report) {
|
|
1151
|
-
return;
|
|
1152
|
-
}
|
|
1153
|
-
const { attribute, group = "", software = "" } = report;
|
|
1154
|
-
const effectiveAttribute = software ? software : attribute;
|
|
1155
|
-
const devicesById = getDevicesById(getState());
|
|
1156
|
-
const acceptedDevices = getAcceptedDevices(getState());
|
|
1157
|
-
const { accepted: acceptedDevicesCount } = getDeviceCountsByStatus(getState());
|
|
1158
|
-
const groups = getGroupsById(getState());
|
|
1159
|
-
const { deviceIds = [], filters = [], total = 0 } = groups[group] || {};
|
|
1160
|
-
let groupDevicesRequest = Promise.resolve({
|
|
1161
|
-
payload: { groupName: "", group: { deviceIds: Object.keys(devicesById), total: Object.keys(devicesById).length } }
|
|
1162
|
-
});
|
|
1163
|
-
if (group && (!(deviceIds.length && total) || deviceIds.length !== total || !deviceIds.every((id) => !!devicesById[id]))) {
|
|
1164
|
-
groupDevicesRequest = filters.length ? dispatch(getAllDynamicGroupDevices({ group, attribute: effectiveAttribute })).unwrap() : dispatch(getAllGroupDevices({ group, attribute: effectiveAttribute })).unwrap();
|
|
1165
|
-
} else if (!group && (acceptedDevices.deviceIds.length !== acceptedDevicesCount || !acceptedDevices.deviceIds.every((id) => !!devicesById[id]))) {
|
|
1166
|
-
groupDevicesRequest = dispatch(getAllDevicesByStatus({ status: DEVICE_STATES.accepted, attribute: effectiveAttribute })).unwrap();
|
|
1167
|
-
}
|
|
1168
|
-
return groupDevicesRequest.then(() => dispatch(updateReportData(reportIndex)));
|
|
1169
|
-
}
|
|
1170
|
-
);
|
|
1171
|
-
var getDeviceConnect = createAppAsyncThunk(
|
|
1172
|
-
`${sliceName3}/getDeviceConnect`,
|
|
1173
|
-
(id, { dispatch }) => general_api_default.get(`${deviceConnect}/devices/${id}`).then(
|
|
1174
|
-
({ data }) => Promise.all([dispatch(actions3.receivedDevice({ connect_status: data.status, connect_updated_ts: data.updated_ts, id })), Promise.resolve(data)])
|
|
1175
|
-
)
|
|
1176
|
-
);
|
|
1177
|
-
var updateTypeMap = { deploymentUpdate: "check-update", inventoryUpdate: "send-inventory" };
|
|
1178
|
-
var triggerDeviceUpdate = createAppAsyncThunk(
|
|
1179
|
-
`${sliceName3}/triggerDeviceUpdate`,
|
|
1180
|
-
({ id, type }, { dispatch }) => general_api_default.post(`${deviceConnect}/devices/${id}/${updateTypeMap[type] ?? updateTypeMap.deploymentUpdate}`).catch((err) => commonErrorHandler(err, `The request couldn\u2019t be sent.`, dispatch)).then(() => {
|
|
1181
|
-
dispatch(setSnackbar2("Request has been sent."));
|
|
1182
|
-
return new Promise((resolve) => setTimeout(() => resolve(dispatch(getDeviceById2(id))), TIMEOUTS.threeSeconds));
|
|
1183
|
-
})
|
|
1184
|
-
);
|
|
1185
|
-
var getSessionDetails = createAppAsyncThunk(
|
|
1186
|
-
`${sliceName3}/getSessionDetails`,
|
|
1187
|
-
({ sessionId, deviceId, userId, startDate, endDate }) => {
|
|
1188
|
-
const { start: startUnix, end: endUnix } = dateRangeToUnix(startDate, endDate);
|
|
1189
|
-
const createdAfter = startDate ? `&created_after=${startUnix}` : "";
|
|
1190
|
-
const createdBefore = endDate ? `&created_before=${endUnix}` : "";
|
|
1191
|
-
const objectSearch = `&object_id=${deviceId}`;
|
|
1192
|
-
return general_api_default.get(`${auditLogsApiUrl}/logs?per_page=500${createdAfter}${createdBefore}&actor_id=${userId}${objectSearch}`).then(
|
|
1193
|
-
({ data: auditLogEntries }) => {
|
|
1194
|
-
const { start, end } = auditLogEntries.reduce(
|
|
1195
|
-
(accu, item) => {
|
|
1196
|
-
if (item.meta?.session_id?.includes(sessionId)) {
|
|
1197
|
-
accu.start = new Date(item.action.startsWith("open") ? item.time : accu.start);
|
|
1198
|
-
accu.end = new Date(item.action.startsWith("close") ? item.time : accu.end);
|
|
1199
|
-
}
|
|
1200
|
-
return accu;
|
|
1201
|
-
},
|
|
1202
|
-
{ start: startDate || endDate, end: endDate || startDate }
|
|
1203
|
-
);
|
|
1204
|
-
return Promise.resolve({ start, end });
|
|
1205
|
-
}
|
|
1206
|
-
);
|
|
1207
|
-
}
|
|
1208
|
-
);
|
|
1209
|
-
var getDeviceFileDownloadLink = createAppAsyncThunk(
|
|
1210
|
-
`${sliceName3}/getDeviceFileDownloadLink`,
|
|
1211
|
-
({ deviceId, path }) => Promise.resolve(`${window.location.origin}${deviceConnect}/devices/${deviceId}/download?path=${encodeURIComponent(path)}`)
|
|
1212
|
-
);
|
|
1213
|
-
var deviceFileUpload = createAppAsyncThunk(
|
|
1214
|
-
`${sliceName3}/deviceFileUpload`,
|
|
1215
|
-
({ deviceId, path, file }, { dispatch }) => {
|
|
1216
|
-
const formData = new FormData();
|
|
1217
|
-
formData.append("path", path);
|
|
1218
|
-
formData.append("file", file);
|
|
1219
|
-
const uploadId = uuid();
|
|
1220
|
-
const cancelSource = new AbortController();
|
|
1221
|
-
return Promise.all([
|
|
1222
|
-
dispatch(setSnackbar2("Uploading file")),
|
|
1223
|
-
dispatch(initUpload({ id: uploadId, upload: { progress: 0, cancelSource } })),
|
|
1224
|
-
general_api_default.uploadPut(
|
|
1225
|
-
`${deviceConnect}/devices/${deviceId}/upload`,
|
|
1226
|
-
formData,
|
|
1227
|
-
(e) => dispatch(uploadProgress({ id: uploadId, progress: progress(e) })),
|
|
1228
|
-
cancelSource.signal
|
|
1229
|
-
)
|
|
1230
|
-
]).then(() => Promise.resolve(dispatch(setSnackbar2({ message: "Upload successful", autoHideDuration: TIMEOUTS.fiveSeconds })))).catch((err) => {
|
|
1231
|
-
if (isCancel(err)) {
|
|
1232
|
-
return dispatch(setSnackbar2({ message: "The upload has been cancelled", autoHideDuration: TIMEOUTS.fiveSeconds }));
|
|
1233
|
-
}
|
|
1234
|
-
return commonErrorHandler(err, `Error uploading file to device.`, dispatch);
|
|
1235
|
-
}).finally(() => dispatch(cleanUpUpload(uploadId)));
|
|
1236
|
-
}
|
|
1237
|
-
);
|
|
1238
|
-
var getDeviceAuth = createAppAsyncThunk(
|
|
1239
|
-
`${sliceName3}/getDeviceAuth`,
|
|
1240
|
-
(id, { dispatch }) => dispatch(getDevicesWithAuth([{ id }])).unwrap().then((results) => {
|
|
1241
|
-
if (results[results.length - 1]) {
|
|
1242
|
-
return Promise.resolve(results[results.length - 1][0]);
|
|
1243
|
-
}
|
|
1244
|
-
return Promise.resolve();
|
|
1245
|
-
})
|
|
1246
|
-
);
|
|
1247
|
-
var getDevicesWithAuth = createAppAsyncThunk(
|
|
1248
|
-
`${sliceName3}/getDevicesWithAuth`,
|
|
1249
|
-
(devices, { dispatch, getState }) => devices.length ? general_api_default.get(`${deviceAuthV2}/devices?id=${devices.map((device) => device.id).join("&id=")}`).then(({ data: receivedDevices }) => {
|
|
1250
|
-
const { devicesById } = reduceReceivedDevices(receivedDevices, [], getState());
|
|
1251
|
-
return Promise.all([dispatch(actions3.receivedDevices(devicesById)), Promise.resolve(receivedDevices)]);
|
|
1252
|
-
}).catch((err) => commonErrorHandler(err, `Error: ${err}`, dispatch)) : Promise.resolve([[], []])
|
|
1253
|
-
);
|
|
1254
|
-
var updateDeviceAuth = createAppAsyncThunk(
|
|
1255
|
-
`${sliceName3}/updateDeviceAuth`,
|
|
1256
|
-
({ deviceId, authId, status }, { dispatch, getState }) => general_api_default.put(`${deviceAuthV2}/devices/${deviceId}/auth/${authId}/status`, { status }).then(() => Promise.all([dispatch(getDeviceAuth(deviceId)), dispatch(setSnackbar2("Device authorization status was updated successfully"))])).catch((err) => commonErrorHandler(err, "There was a problem updating the device authorization status:", dispatch)).then(() => Promise.resolve(dispatch(actions3.maybeUpdateDevicesByStatus({ deviceId, authId })))).finally(() => dispatch(setDeviceListState({ refreshTrigger: !getDeviceListState(getState()).refreshTrigger })))
|
|
1257
|
-
);
|
|
1258
|
-
var updateDevicesAuth = createAppAsyncThunk(
|
|
1259
|
-
`${sliceName3}/updateDevicesAuth`,
|
|
1260
|
-
({ deviceIds, status }, { dispatch, getState }) => {
|
|
1261
|
-
let devices = getDevicesById(getState());
|
|
1262
|
-
const deviceIdsWithoutAuth = deviceIds.reduce((accu, id) => devices[id].auth_sets ? accu : [...accu, { id }], []);
|
|
1263
|
-
return dispatch(getDevicesWithAuth(deviceIdsWithoutAuth)).then(() => {
|
|
1264
|
-
devices = getDevicesById(getState());
|
|
1265
|
-
const deviceAuthUpdates = deviceIds.map((id) => {
|
|
1266
|
-
const device = devices[id];
|
|
1267
|
-
if (device.auth_sets && device.auth_sets.length !== 1) {
|
|
1268
|
-
return Promise.reject();
|
|
1269
|
-
}
|
|
1270
|
-
return dispatch(updateDeviceAuth({ authId: device.auth_sets[0].id, deviceId: device.id, status })).unwrap().catch((err) => commonErrorHandler(err, "The action was stopped as there was a problem updating a device authorization status: ", dispatch, "", false));
|
|
1271
|
-
});
|
|
1272
|
-
return Promise.allSettled(deviceAuthUpdates).then((results) => {
|
|
1273
|
-
const { skipped, count } = results.reduce(
|
|
1274
|
-
(accu, item) => {
|
|
1275
|
-
if (item.status === "rejected") {
|
|
1276
|
-
accu.skipped = accu.skipped + 1;
|
|
1277
|
-
} else {
|
|
1278
|
-
accu.count = accu.count + 1;
|
|
1279
|
-
}
|
|
1280
|
-
return accu;
|
|
1281
|
-
},
|
|
1282
|
-
{ skipped: 0, count: 0 }
|
|
1283
|
-
);
|
|
1284
|
-
const message = getSnackbarMessage(skipped, count);
|
|
1285
|
-
return dispatch(setSnackbar2(message));
|
|
1286
|
-
});
|
|
1287
|
-
});
|
|
1288
|
-
}
|
|
1289
|
-
);
|
|
1290
|
-
var deleteAuthset = createAppAsyncThunk(
|
|
1291
|
-
`${sliceName3}/deleteAuthset`,
|
|
1292
|
-
({ deviceId, authId }, { dispatch, getState }) => general_api_default.delete(`${deviceAuthV2}/devices/${deviceId}/auth/${authId}`).then(() => Promise.all([dispatch(setSnackbar2("Device authorization status was updated successfully"))])).catch((err) => commonErrorHandler(err, "There was a problem updating the device authorization status:", dispatch)).then(() => Promise.resolve(dispatch(actions3.maybeUpdateDevicesByStatus({ deviceId, authId })))).finally(() => dispatch(setDeviceListState({ refreshTrigger: !getState().devices.deviceList.refreshTrigger })))
|
|
1293
|
-
);
|
|
1294
|
-
var preauthDevice = createAppAsyncThunk(
|
|
1295
|
-
`${sliceName3}/preauthDevice`,
|
|
1296
|
-
(authset, { dispatch, rejectWithValue }) => general_api_default.post(`${deviceAuthV2}/devices`, authset).then(
|
|
1297
|
-
() => Promise.resolve(dispatch(setSnackbar2({ message: "Device was successfully added to the preauthorization list", autoHideDuration: TIMEOUTS.fiveSeconds })))
|
|
1298
|
-
).catch((err) => {
|
|
1299
|
-
if (err.response.status === 409) {
|
|
1300
|
-
return rejectWithValue("A device with a matching identity data set already exists");
|
|
1301
|
-
}
|
|
1302
|
-
return commonErrorHandler(err, "The device could not be added:", dispatch);
|
|
1303
|
-
})
|
|
1304
|
-
);
|
|
1305
|
-
var decommissionDevice = createAppAsyncThunk(
|
|
1306
|
-
`${sliceName3}/decommissionDevice`,
|
|
1307
|
-
({ deviceId, authId }, { dispatch, getState }) => general_api_default.delete(`${deviceAuthV2}/devices/${deviceId}`).then(() => Promise.resolve(dispatch(setSnackbar2("Device was decommissioned successfully")))).catch((err) => commonErrorHandler(err, "There was a problem decommissioning the device:", dispatch)).then(() => Promise.resolve(dispatch(actions3.maybeUpdateDevicesByStatus({ deviceId, authId })))).finally(() => dispatch(setDeviceListState({ refreshTrigger: !getState().devices.deviceList.refreshTrigger })))
|
|
1308
|
-
);
|
|
1309
|
-
var getDeviceConfig = createAppAsyncThunk(
|
|
1310
|
-
`${sliceName3}/getDeviceConfig`,
|
|
1311
|
-
(deviceId, { dispatch }) => general_api_default.get(`${deviceConfig}/${deviceId}`).then(({ data }) => Promise.all([dispatch(actions3.receivedDevice({ id: deviceId, config: data })), Promise.resolve(data)])).catch((err) => {
|
|
1312
|
-
if (err.response?.data?.error.status_code !== 404) {
|
|
1313
|
-
return commonErrorHandler(err, `There was an error retrieving the configuration for device ${deviceId}.`, dispatch, commonErrorFallback);
|
|
1314
|
-
}
|
|
1315
|
-
})
|
|
1316
|
-
);
|
|
1317
|
-
var setDeviceConfig = createAppAsyncThunk(
|
|
1318
|
-
`${sliceName3}/setDeviceConfig`,
|
|
1319
|
-
({ deviceId, config }, { dispatch }) => general_api_default.put(`${deviceConfig}/${deviceId}`, config).catch((err) => commonErrorHandler(err, `There was an error setting the configuration for device ${deviceId}.`, dispatch, commonErrorFallback)).then(() => Promise.resolve(dispatch(getDeviceConfig(deviceId))))
|
|
1320
|
-
);
|
|
1321
|
-
var applyDeviceConfig = createAppAsyncThunk(
|
|
1322
|
-
`${sliceName3}/applyDeviceConfig`,
|
|
1323
|
-
({ deviceId, configDeploymentConfiguration, isDefault, config }, { dispatch, getState }) => general_api_default.post(`${deviceConfig}/${deviceId}/deploy`, configDeploymentConfiguration).catch((err) => commonErrorHandler(err, `There was an error deploying the configuration to device ${deviceId}.`, dispatch, commonErrorFallback)).then(({ data }) => {
|
|
1324
|
-
const device = getDeviceById(getState(), deviceId);
|
|
1325
|
-
const { canManageUsers } = getUserCapabilities(getState());
|
|
1326
|
-
const tasks = [
|
|
1327
|
-
dispatch(actions3.receivedDevice({ ...device, config: { ...device.config, deployment_id: data.deployment_id } })),
|
|
1328
|
-
new Promise((resolve) => setTimeout(() => resolve(dispatch(getSingleDeployment(data.deployment_id))), TIMEOUTS.oneSecond))
|
|
1329
|
-
];
|
|
1330
|
-
if (isDefault && canManageUsers) {
|
|
1331
|
-
const { previous } = getGlobalSettings(getState()).defaultDeviceConfig ?? {};
|
|
1332
|
-
tasks.push(dispatch(saveGlobalSettings({ defaultDeviceConfig: { current: config, previous } })));
|
|
1333
|
-
}
|
|
1334
|
-
return Promise.all(tasks);
|
|
1335
|
-
})
|
|
1336
|
-
);
|
|
1337
|
-
var setDeviceTags = createAppAsyncThunk(
|
|
1338
|
-
`${sliceName3}/setDeviceTags`,
|
|
1339
|
-
({ deviceId, tags }, { dispatch }) => (
|
|
1340
|
-
// to prevent tag set failures, retrieve the device & use the freshest etag we can get
|
|
1341
|
-
dispatch(getDeviceById2(deviceId)).unwrap().then((device) => {
|
|
1342
|
-
const headers = device.etag ? { "If-Match": device.etag } : {};
|
|
1343
|
-
const tagList = Object.entries(tags).map(([name, value]) => ({ name, value }));
|
|
1344
|
-
const isNameChange = tagList.some(({ name }) => name === "name");
|
|
1345
|
-
return general_api_default.put(`${inventoryApiUrl}/devices/${deviceId}/tags`, tagList, { headers }).catch((err) => commonErrorHandler(err, `There was an error setting tags for device ${deviceId}.`, dispatch, "Please check your connection.")).then(
|
|
1346
|
-
() => Promise.all([
|
|
1347
|
-
dispatch(actions3.receivedDevice({ ...device, id: deviceId, tags })),
|
|
1348
|
-
dispatch(setSnackbar2(`Device ${tagList.length === 1 && isNameChange ? "name" : "tags"} changed`))
|
|
1349
|
-
])
|
|
1350
|
-
);
|
|
1351
|
-
})
|
|
1352
|
-
)
|
|
1353
|
-
);
|
|
1354
|
-
var getDeviceTwin = createAppAsyncThunk(`${sliceName3}/getDeviceTwin`, ({ deviceId, integration }, { dispatch, getState }) => {
|
|
1355
|
-
let providerResult = {};
|
|
1356
|
-
return general_api_default.get(`${iotManagerBaseURL}/devices/${deviceId}/state`).then(({ data }) => {
|
|
1357
|
-
providerResult = { ...data, twinError: "" };
|
|
1358
|
-
}).catch((err) => {
|
|
1359
|
-
providerResult = {
|
|
1360
|
-
twinError: `There was an error getting the ${EXTERNAL_PROVIDER[integration.provider].twinTitle.toLowerCase()} for device ${deviceId}. ${err}`
|
|
1361
|
-
};
|
|
1362
|
-
}).finally(() => {
|
|
1363
|
-
const device = getDeviceById(getState(), deviceId);
|
|
1364
|
-
Promise.resolve(dispatch(actions3.receivedDevice({ ...device, twinsByIntegration: { ...device.twinsByIntegration, ...providerResult } })));
|
|
1365
|
-
});
|
|
1366
|
-
});
|
|
1367
|
-
var setDeviceTwin = createAppAsyncThunk(
|
|
1368
|
-
`${sliceName3}/setDeviceTwin`,
|
|
1369
|
-
({ deviceId, integration, settings }, { dispatch, getState }) => general_api_default.put(`${iotManagerBaseURL}/devices/${deviceId}/state/${integration.id}`, { desired: settings }).catch(
|
|
1370
|
-
(err) => commonErrorHandler(
|
|
1371
|
-
err,
|
|
1372
|
-
`There was an error updating the ${EXTERNAL_PROVIDER[integration.provider].twinTitle.toLowerCase()} for device ${deviceId}.`,
|
|
1373
|
-
dispatch
|
|
1374
|
-
)
|
|
1375
|
-
).then(() => {
|
|
1376
|
-
const device = getDeviceById(getState(), deviceId);
|
|
1377
|
-
const { twinsByIntegration = {} } = device;
|
|
1378
|
-
const { [integration.id]: currentState = {} } = twinsByIntegration;
|
|
1379
|
-
return Promise.resolve(
|
|
1380
|
-
dispatch(
|
|
1381
|
-
actions3.receivedDevice({ ...device, twinsByIntegration: { ...twinsByIntegration, [integration.id]: { ...currentState, desired: settings } } })
|
|
1382
|
-
)
|
|
1383
|
-
);
|
|
1384
|
-
})
|
|
1385
|
-
);
|
|
1386
|
-
var prepareSearchArguments = ({ filters, group, state, status }) => {
|
|
1387
|
-
const { filterTerms } = convertDeviceListStateToFilters({ filters, group, offlineThreshold: state.app.offlineThreshold, selectedIssues: [], status });
|
|
1388
|
-
const { columnSelection = [] } = getUserSettings(state);
|
|
1389
|
-
const selectedAttributes = columnSelection.map((column) => ({ attribute: column.key, scope: column.scope }));
|
|
1390
|
-
const attributes = [...defaultAttributes, getIdAttribute(state), ...selectedAttributes];
|
|
1391
|
-
return { attributes, filterTerms };
|
|
1392
|
-
};
|
|
1393
|
-
var getSystemDevices = createAppAsyncThunk(`${sliceName3}/getSystemDevices`, (options, { dispatch, getState }) => {
|
|
1394
|
-
const { id, page = defaultPage2, perPage = defaultPerPage2, sortOptions = [] } = options;
|
|
1395
|
-
const state = getState();
|
|
1396
|
-
const { hasFullFiltering } = getTenantCapabilities(state);
|
|
1397
|
-
if (!hasFullFiltering) {
|
|
1398
|
-
return Promise.resolve();
|
|
1399
|
-
}
|
|
1400
|
-
const { attributes: deviceAttributes = {} } = getDeviceById(state, id);
|
|
1401
|
-
const { mender_gateway_system_id = "" } = deviceAttributes;
|
|
1402
|
-
const filters = [
|
|
1403
|
-
{ ...emptyFilter, key: "mender_is_gateway", operator: DEVICE_FILTERING_OPTIONS.$ne.key, value: "true", scope: "inventory" },
|
|
1404
|
-
{ ...emptyFilter, key: "mender_gateway_system_id", value: mender_gateway_system_id, scope: "inventory" }
|
|
1405
|
-
];
|
|
1406
|
-
const { attributes, filterTerms } = prepareSearchArguments({ filters, state });
|
|
1407
|
-
return general_api_default.post(`${inventoryApiUrlV2}/filters/search`, {
|
|
1408
|
-
page,
|
|
1409
|
-
per_page: perPage,
|
|
1410
|
-
filters: filterTerms,
|
|
1411
|
-
sort: sortOptions,
|
|
1412
|
-
attributes
|
|
1413
|
-
}).catch((err) => commonErrorHandler(err, `There was an error getting system devices device ${id}.`, dispatch, "Please check your connection.")).then(({ data, headers }) => {
|
|
1414
|
-
const state2 = getState();
|
|
1415
|
-
const { devicesById, ids } = reduceReceivedDevices(data, [], state2);
|
|
1416
|
-
const device = {
|
|
1417
|
-
...getDeviceById(state2, id),
|
|
1418
|
-
systemDeviceIds: ids,
|
|
1419
|
-
systemDeviceTotal: Number(headers[headerNames.total])
|
|
1420
|
-
};
|
|
1421
|
-
return Promise.resolve(dispatch(actions3.receivedDevices({ ...devicesById, [id]: device })));
|
|
1422
|
-
});
|
|
1423
|
-
});
|
|
1424
|
-
var getGatewayDevices = createAppAsyncThunk(`${sliceName3}/getGatewayDevices`, (deviceId, { dispatch, getState }) => {
|
|
1425
|
-
const state = getState();
|
|
1426
|
-
const { attributes = {} } = getDeviceById(state, deviceId);
|
|
1427
|
-
const { mender_gateway_system_id = "" } = attributes;
|
|
1428
|
-
const filters = [
|
|
1429
|
-
{ ...emptyFilter, key: "id", operator: DEVICE_FILTERING_OPTIONS.$ne.key, value: deviceId, scope: "identity" },
|
|
1430
|
-
{ ...emptyFilter, key: "mender_is_gateway", value: "true", scope: "inventory" },
|
|
1431
|
-
{ ...emptyFilter, key: "mender_gateway_system_id", value: mender_gateway_system_id, scope: "inventory" }
|
|
1432
|
-
];
|
|
1433
|
-
const { attributes: attributeSelection, filterTerms } = prepareSearchArguments({ filters, state });
|
|
1434
|
-
return general_api_default.post(`${inventoryApiUrlV2}/filters/search`, {
|
|
1435
|
-
page: 1,
|
|
1436
|
-
per_page: MAX_PAGE_SIZE,
|
|
1437
|
-
filters: filterTerms,
|
|
1438
|
-
attributes: attributeSelection
|
|
1439
|
-
}).then(({ data }) => {
|
|
1440
|
-
const { ids } = reduceReceivedDevices(data, [], getState());
|
|
1441
|
-
const tasks = ids.map((deviceId2) => dispatch(getDeviceInfo(deviceId2)));
|
|
1442
|
-
tasks.push(dispatch(actions3.receivedDevice({ id: deviceId, gatewayIds: ids })));
|
|
1443
|
-
return Promise.all(tasks);
|
|
1444
|
-
});
|
|
1445
|
-
});
|
|
1446
|
-
|
|
1447
|
-
// src/onboardingSlice/thunks.ts
|
|
1448
|
-
import { getDemoDeviceAddress } from "@northern.tech/utils/helpers";
|
|
1449
|
-
import Tracking2 from "@northern.tech/utils/tracking";
|
|
1450
|
-
import Cookies from "universal-cookie";
|
|
1451
|
-
var cookies = new Cookies();
|
|
1452
|
-
var applyOnboardingFallbacks = (progress2) => {
|
|
1453
|
-
const step = orderedOnboardingSteps[progress2];
|
|
1454
|
-
if (step && step.fallbackStep) {
|
|
1455
|
-
return step.fallbackStep;
|
|
1456
|
-
}
|
|
1457
|
-
return progress2;
|
|
1458
|
-
};
|
|
1459
|
-
var determineProgress = (acceptedDevices, pendingDevices, releases, pastDeployments) => {
|
|
1460
|
-
const steps = orderedOnboardingSteps;
|
|
1461
|
-
let progress2 = -1;
|
|
1462
|
-
progress2 = pendingDevices.length > 1 ? steps.findIndex((step) => step === onboardingSteps.DEVICES_PENDING_ACCEPTING_ONBOARDING) : progress2;
|
|
1463
|
-
progress2 = acceptedDevices.length >= 1 ? steps.findIndex((step) => step === onboardingSteps.DEVICES_ACCEPTED_ONBOARDING) : progress2;
|
|
1464
|
-
progress2 = acceptedDevices.length > 1 && releases.length > 1 && pastDeployments.length > 1 ? steps.findIndex((step) => step === onboardingSteps.DEPLOYMENTS_PAST_COMPLETED) : progress2;
|
|
1465
|
-
return steps[progress2];
|
|
1466
|
-
};
|
|
1467
|
-
var deductOnboardingState = ({ devicesById, devicesByStatus, onboardingState, pastDeployments, releases, userCapabilities, userId }) => {
|
|
1468
|
-
const { canDeploy, canManageDevices, canReadDeployments, canReadDevices, canReadReleases, canUploadReleases } = userCapabilities;
|
|
1469
|
-
const userCookie = cookies.get(`${userId}-onboarded`);
|
|
1470
|
-
const acceptedDevices = devicesByStatus[DEVICE_STATES.accepted].deviceIds;
|
|
1471
|
-
const pendingDevices = devicesByStatus[DEVICE_STATES.pending].deviceIds;
|
|
1472
|
-
let deviceType = onboardingState.deviceType ?? [];
|
|
1473
|
-
deviceType = !deviceType.length && acceptedDevices.length && devicesById[acceptedDevices[0]].hasOwnProperty("attributes") ? devicesById[acceptedDevices[0]].attributes.device_type : deviceType;
|
|
1474
|
-
const deviceTier = acceptedDevices.length && devicesById[acceptedDevices[0]].tier;
|
|
1475
|
-
let approach = null;
|
|
1476
|
-
if (deviceType.some((type) => type.startsWith("qemu"))) {
|
|
1477
|
-
approach = "virtual";
|
|
1478
|
-
} else if (deviceType.some((type) => type.startsWith("esp32")) || deviceTier === "micro") {
|
|
1479
|
-
approach = "mcu";
|
|
1480
|
-
} else if (deviceType.length) {
|
|
1481
|
-
approach = "physical";
|
|
1482
|
-
}
|
|
1483
|
-
const progress2 = applyOnboardingFallbacks(onboardingState.progress || determineProgress(acceptedDevices, pendingDevices, releases, pastDeployments));
|
|
1484
|
-
return {
|
|
1485
|
-
...onboardingState,
|
|
1486
|
-
complete: !!(Boolean(userCookie) || onboardingState.complete || acceptedDevices.length > 1 && pendingDevices.length > 0 && releases.length > 1 && pastDeployments.length > 1 || acceptedDevices.length >= 1 && releases.length >= 2 && pastDeployments.length > 2 || acceptedDevices.length >= 1 && pendingDevices.length > 0 && releases.length >= 2 && pastDeployments.length >= 2 || orderedOnboardingSteps.findIndex((step) => step === progress2) >= orderedOnboardingSteps.length - 1 || onboardingState.disable || ![canDeploy, canManageDevices, canReadDeployments, canReadDevices, canReadReleases, canUploadReleases].every((i) => i)),
|
|
1487
|
-
showTips: onboardingState.showTips != null ? onboardingState.showTips : true,
|
|
1488
|
-
deviceType,
|
|
1489
|
-
approach: onboardingState.approach || approach,
|
|
1490
|
-
progress: progress2
|
|
1491
|
-
};
|
|
1492
|
-
};
|
|
1493
|
-
var getOnboardingState2 = createAppAsyncThunk(`${sliceName4}/getOnboardingState`, (_, { dispatch, getState }) => {
|
|
1494
|
-
const state = getState();
|
|
1495
|
-
let onboardingState = getOnboardingState(state);
|
|
1496
|
-
if (!onboardingState.complete) {
|
|
1497
|
-
const userId = state.users.currentUser;
|
|
1498
|
-
onboardingState = deductOnboardingState({
|
|
1499
|
-
devicesById: state.devices.byId,
|
|
1500
|
-
devicesByStatus: state.devices.byStatus,
|
|
1501
|
-
onboardingState,
|
|
1502
|
-
pastDeployments: state.deployments.byStatus.finished.deploymentIds,
|
|
1503
|
-
releases: Object.values(state.releases.byId),
|
|
1504
|
-
userCapabilities: getUserCapabilities(state),
|
|
1505
|
-
userId
|
|
1506
|
-
});
|
|
1507
|
-
}
|
|
1508
|
-
onboardingState.progress = onboardingState.progress || onboardingSteps.DASHBOARD_ONBOARDING_START;
|
|
1509
|
-
const demoDeviceAddress = `http://${getDemoDeviceAddress(Object.values(state.devices.byId), onboardingState.approach)}`;
|
|
1510
|
-
onboardingState.address = state.onboarding.demoArtifactPort ? `${demoDeviceAddress}:${state.onboarding.demoArtifactPort}` : demoDeviceAddress;
|
|
1511
|
-
return Promise.all([
|
|
1512
|
-
dispatch(actions4.setOnboardingComplete(onboardingState.complete)),
|
|
1513
|
-
dispatch(actions4.setOnboardingState(onboardingState)),
|
|
1514
|
-
dispatch(saveUserSettings({ onboarding: onboardingState }))
|
|
1515
|
-
]);
|
|
1516
|
-
});
|
|
1517
|
-
var setOnboardingDeviceType = createAppAsyncThunk(
|
|
1518
|
-
`${sliceName4}/setOnboardingDeviceType`,
|
|
1519
|
-
(value, { dispatch }) => Promise.all([dispatch(actions4.setOnboardingDeviceType(value)), dispatch(saveUserSettings({ onboarding: { deviceType: value } }))])
|
|
1520
|
-
);
|
|
1521
|
-
var setOnboardingApproach = createAppAsyncThunk(
|
|
1522
|
-
`${sliceName4}/setOnboardingApproach`,
|
|
1523
|
-
(value, { dispatch }) => Promise.all([dispatch(actions4.setOnboardingApproach(value)), dispatch(saveUserSettings({ onboarding: { approach: value } }))])
|
|
1524
|
-
);
|
|
1525
|
-
var setOnboardingComplete = createAppAsyncThunk(`${sliceName4}/setOnboardingComplete`, (value, { dispatch }) => {
|
|
1526
|
-
const tasks = [Promise.resolve(dispatch(actions4.setOnboardingComplete(value)))];
|
|
1527
|
-
if (value) {
|
|
1528
|
-
tasks.push(Promise.resolve(dispatch(actions4.setShowOnboardingHelp(false))));
|
|
1529
|
-
tasks.push(Promise.resolve(dispatch(advanceOnboarding(onboardingSteps.DEPLOYMENTS_PAST_COMPLETED))));
|
|
1530
|
-
}
|
|
1531
|
-
return Promise.all(tasks);
|
|
1532
|
-
});
|
|
1533
|
-
var setOnboardingCanceled = createAppAsyncThunk(
|
|
1534
|
-
`${sliceName4}/setOnboardingCanceled`,
|
|
1535
|
-
(_, { dispatch }) => Promise.all([
|
|
1536
|
-
Promise.resolve(dispatch(actions4.setShowOnboardingHelp(false))),
|
|
1537
|
-
Promise.resolve(dispatch(actions4.setShowDismissOnboardingTipsDialog(false))),
|
|
1538
|
-
Promise.resolve(dispatch(actions4.setOnboardingComplete(true)))
|
|
1539
|
-
]).then(() => dispatch(advanceOnboarding(onboardingSteps.DEPLOYMENTS_PAST_COMPLETED_FAILURE))).then(() => Tracking2.event({ category: "onboarding", action: onboardingSteps.ONBOARDING_CANCELED }))
|
|
1540
|
-
);
|
|
1541
|
-
var advanceOnboarding = createAppAsyncThunk(`${sliceName4}/advanceOnboarding`, (stepId, { dispatch, getState }) => {
|
|
1542
|
-
const steps = orderedOnboardingSteps;
|
|
1543
|
-
const progress2 = steps.findIndex((step) => step === getState().onboarding.progress);
|
|
1544
|
-
const stepIndex = steps.findIndex((step) => step === stepId);
|
|
1545
|
-
if (progress2 > stepIndex || getState().onboarding.progress === null) {
|
|
1546
|
-
return;
|
|
1547
|
-
}
|
|
1548
|
-
const madeProgress = steps[stepIndex + 1];
|
|
1549
|
-
const state = { ...getOnboardingState(getState()), progress: madeProgress };
|
|
1550
|
-
state.complete = stepIndex + 1 >= orderedOnboardingSteps.findIndex((step) => step === onboardingSteps.DEPLOYMENTS_PAST_COMPLETED_FAILURE) ? true : state.complete;
|
|
1551
|
-
Tracking2.event({ category: "onboarding", action: stepId });
|
|
1552
|
-
return Promise.all([dispatch(actions4.setOnboardingProgress(madeProgress)), dispatch(saveUserSettings({ onboarding: state }))]);
|
|
1553
|
-
});
|
|
1554
|
-
|
|
1555
|
-
// src/organizationSlice/thunks.ts
|
|
1556
|
-
import { dateRangeToUnix as dateRangeToUnix2, deepCompare as deepCompare3 } from "@northern.tech/utils/helpers";
|
|
1557
|
-
import dayjs from "dayjs";
|
|
1558
|
-
import utc from "dayjs/plugin/utc.js";
|
|
1559
|
-
import hashString from "md5";
|
|
1560
|
-
import Cookies2 from "universal-cookie";
|
|
1561
|
-
var cookies2 = new Cookies2();
|
|
1562
|
-
dayjs.extend(utc);
|
|
1563
|
-
var { setAnnouncement, setSnackbar: setSnackbar3 } = actions_default;
|
|
1564
|
-
var { page: defaultPage3, perPage: defaultPerPage3 } = DEVICE_LIST_DEFAULTS;
|
|
1565
|
-
var cancelRequest = createAppAsyncThunk(`${sliceName5}/cancelRequest`, (reason, { dispatch, getState }) => {
|
|
1566
|
-
const { id: tenantId } = getOrganization(getState());
|
|
1567
|
-
return general_api_default.post(`${tenantadmApiUrlv2}/tenants/${tenantId}/cancel`, { reason }).then(
|
|
1568
|
-
() => Promise.resolve(dispatch(setSnackbar3({ message: "Deactivation request was sent successfully", autoHideDuration: TIMEOUTS.fiveSeconds })))
|
|
1569
|
-
);
|
|
1570
|
-
});
|
|
1571
|
-
var getTierId = (tierName) => tierName.replace("mender_", "");
|
|
1572
|
-
var getProductPlans = (products) => {
|
|
1573
|
-
const backendPlansById = products.reduce(
|
|
1574
|
-
(plansById, product) => {
|
|
1575
|
-
const { name, prices } = product;
|
|
1576
|
-
const tierId = getTierId(name);
|
|
1577
|
-
prices.forEach((price) => {
|
|
1578
|
-
const existing = plansById[price.plan] ?? { ...PLANS[price.plan], tierLimitsConstrains: {} };
|
|
1579
|
-
const tierConstraints = price.constraints ? { [tierId]: { min: price.constraints.min, max: price.constraints.max, div: price.constraints.div } } : {};
|
|
1580
|
-
plansById[price.plan] = {
|
|
1581
|
-
...existing,
|
|
1582
|
-
tierLimitsConstrains: {
|
|
1583
|
-
...existing.tierLimitsConstrains,
|
|
1584
|
-
...tierConstraints
|
|
1585
|
-
}
|
|
1586
|
-
};
|
|
1587
|
-
});
|
|
1588
|
-
return plansById;
|
|
1589
|
-
},
|
|
1590
|
-
{}
|
|
1591
|
-
);
|
|
1592
|
-
return { ...backendPlansById, enterprise: { ...PLANS.enterprise } };
|
|
1593
|
-
};
|
|
1594
|
-
var getProductAddons = (products) => products.reduce((accu, product) => {
|
|
1595
|
-
const { addons = [] } = product;
|
|
1596
|
-
addons.forEach((addon) => {
|
|
1597
|
-
const { name: addonName = "", prices: addonPrices = [] } = addon;
|
|
1598
|
-
const existingEligible = accu[addonName]?.eligible ?? [];
|
|
1599
|
-
const newEligible = addonPrices.map((p) => p.plan);
|
|
1600
|
-
accu[addonName] = {
|
|
1601
|
-
...ADDONS[addonName],
|
|
1602
|
-
eligible: [.../* @__PURE__ */ new Set([...existingEligible, ...newEligible, PLANS.enterprise.id])]
|
|
1603
|
-
};
|
|
1604
|
-
});
|
|
1605
|
-
return accu;
|
|
1606
|
-
}, {});
|
|
1607
|
-
var transformProductResponse = (products) => {
|
|
1608
|
-
const tiers = [];
|
|
1609
|
-
const sortedProducts = products.sort((a, b) => a.name.localeCompare(b.name));
|
|
1610
|
-
sortedProducts.forEach((tier) => {
|
|
1611
|
-
const addonsSupported = Object.fromEntries((tier.addons || []).map((addon) => [addon.name, addon.prices?.map((p) => p.plan)]));
|
|
1612
|
-
const allPlans = tier.prices.map((price) => price.plan);
|
|
1613
|
-
const addonsTransposed = allPlans.reduce((acc, plan) => {
|
|
1614
|
-
acc[plan] = Object.entries(addonsSupported).filter(([, addonSupportedPlans]) => addonSupportedPlans.includes(plan)).map(([addon]) => addon);
|
|
1615
|
-
return acc;
|
|
1616
|
-
}, {});
|
|
1617
|
-
const tierId = getTierId(tier.name);
|
|
1618
|
-
tiers.push({
|
|
1619
|
-
id: tierId,
|
|
1620
|
-
title: tierId,
|
|
1621
|
-
stripeProductName: tier.name,
|
|
1622
|
-
limitConstrains: Object.fromEntries(tier.prices.map((p) => [p.plan, p.constraints])),
|
|
1623
|
-
addons: addonsSupported,
|
|
1624
|
-
addonsByPlan: addonsTransposed
|
|
1625
|
-
});
|
|
1626
|
-
});
|
|
1627
|
-
const plans = getProductPlans(products);
|
|
1628
|
-
const addons = getProductAddons(products);
|
|
1629
|
-
return { plans, tiers, addons };
|
|
1630
|
-
};
|
|
1631
|
-
var getTargetLocation = (key) => {
|
|
1632
|
-
if (devLocations.includes(window.location.hostname)) {
|
|
1633
|
-
return "";
|
|
1634
|
-
}
|
|
1635
|
-
let subdomainSections = window.location.hostname.substring(0, window.location.hostname.indexOf(locations.us.location)).split(".");
|
|
1636
|
-
subdomainSections = subdomainSections.splice(0, subdomainSections.length - 1);
|
|
1637
|
-
if (!subdomainSections.find((section) => section === key)) {
|
|
1638
|
-
subdomainSections = key === locations.us.key ? subdomainSections.filter((section) => !locations[section]) : [...subdomainSections, key];
|
|
1639
|
-
return `https://${[...subdomainSections, ...locations.us.location.split(".")].join(".")}`;
|
|
1640
|
-
}
|
|
1641
|
-
return `https://${window.location.hostname}`;
|
|
1642
|
-
};
|
|
1643
|
-
var devLocations = ["localhost", "docker.mender.io"];
|
|
1644
|
-
var createOrganizationTrial = createAppAsyncThunk(`${sliceName5}/createOrganizationTrial`, (data, { dispatch }) => {
|
|
1645
|
-
const { key } = locations[data.location];
|
|
1646
|
-
const targetLocation = getTargetLocation(key);
|
|
1647
|
-
const target = `${targetLocation}${tenantadmApiUrlv2}/tenants/trial`;
|
|
1648
|
-
return general_api_default.postUnauthorized(target, data).catch((err) => {
|
|
1649
|
-
if (err.response?.status >= 400 && err.response?.status < 500) {
|
|
1650
|
-
dispatch(setSnackbar3({ message: err.response.data.error, autoHideDuration: TIMEOUTS.fiveSeconds }));
|
|
1651
|
-
} else {
|
|
1652
|
-
dispatch(setSnackbar3({ message: "There was an error creating your account", autoHideDuration: TIMEOUTS.fiveSeconds }));
|
|
1653
|
-
}
|
|
1654
|
-
return Promise.reject(err);
|
|
1655
|
-
}).then(({ headers }) => {
|
|
1656
|
-
cookies2.remove("oauth");
|
|
1657
|
-
cookies2.remove("externalID");
|
|
1658
|
-
cookies2.remove("email");
|
|
1659
|
-
dispatch(setFirstLoginAfterSignup(true));
|
|
1660
|
-
return new Promise(
|
|
1661
|
-
(resolve) => setTimeout(() => {
|
|
1662
|
-
window.location.assign(`${targetLocation}${headers.location || ""}`);
|
|
1663
|
-
return resolve();
|
|
1664
|
-
}, TIMEOUTS.fiveSeconds)
|
|
1665
|
-
);
|
|
1666
|
-
});
|
|
1667
|
-
});
|
|
1668
|
-
var startCardUpdate = createAppAsyncThunk(
|
|
1669
|
-
`${sliceName5}/startCardUpdate`,
|
|
1670
|
-
(_, { dispatch }) => general_api_default.post(`${tenantadmApiUrlv2}/billing/card`).then(({ data }) => {
|
|
1671
|
-
dispatch(actions5.receiveSetupIntent(data.intent_id));
|
|
1672
|
-
return Promise.resolve(data.secret);
|
|
1673
|
-
}).catch((err) => commonErrorHandler(err, `Updating the card failed:`, dispatch))
|
|
1674
|
-
);
|
|
1675
|
-
var confirmCardUpdate = createAppAsyncThunk(
|
|
1676
|
-
`${sliceName5}/confirmCardUpdate`,
|
|
1677
|
-
(_, { dispatch, getState }) => general_api_default.post(`${tenantadmApiUrlv2}/billing/card/${getState().organization.intentId}/confirm`).then(() => Promise.all([dispatch(setSnackbar3("Payment card was updated successfully")), dispatch(actions5.receiveSetupIntent(null))])).catch((err) => commonErrorHandler(err, `Updating the card failed:`, dispatch))
|
|
1678
|
-
);
|
|
1679
|
-
var getCurrentCard = createAppAsyncThunk(
|
|
1680
|
-
`${sliceName5}/getCurrentCard`,
|
|
1681
|
-
(_, { dispatch }) => general_api_default.get(`${tenantadmApiUrlv2}/billing`).then((res) => {
|
|
1682
|
-
const { last4, exp_month, exp_year, brand } = res.data.card || {};
|
|
1683
|
-
return Promise.resolve(dispatch(actions5.receiveCurrentCard({ brand, last4, expiration: { month: exp_month, year: exp_year } })));
|
|
1684
|
-
})
|
|
1685
|
-
);
|
|
1686
|
-
var startUpgrade = createAppAsyncThunk(
|
|
1687
|
-
`${sliceName5}/startUpgrade`,
|
|
1688
|
-
(tenantId, { dispatch }) => general_api_default.post(`${tenantadmApiUrlv2}/tenants/${tenantId}/upgrade/start`).then(({ data }) => Promise.resolve(data.secret)).catch((err) => commonErrorHandler(err, `There was an error upgrading your account:`, dispatch))
|
|
1689
|
-
);
|
|
1690
|
-
var cancelUpgrade = createAppAsyncThunk(
|
|
1691
|
-
`${sliceName5}/cancelUpgrade`,
|
|
1692
|
-
(tenantId) => general_api_default.post(`${tenantadmApiUrlv2}/tenants/${tenantId}/upgrade/cancel`)
|
|
1693
|
-
);
|
|
1694
|
-
var completeUpgrade = createAppAsyncThunk(
|
|
1695
|
-
`${sliceName5}/completeUpgrade`,
|
|
1696
|
-
({ tenantId, plan, billing_profile }, { dispatch }) => general_api_default.post(`${tenantadmApiUrlv2}/tenants/${tenantId}/upgrade/complete`, { plan, billing_profile }).catch((err) => commonErrorHandler(err, `There was an error upgrading your account:`, dispatch)).then(() => Promise.all([dispatch(getDeviceLimits()), dispatch(getUserOrganization())]))
|
|
1697
|
-
);
|
|
1698
|
-
var prepareAuditlogQuery = ({
|
|
1699
|
-
startDate,
|
|
1700
|
-
endDate,
|
|
1701
|
-
user: userFilter,
|
|
1702
|
-
type,
|
|
1703
|
-
detail: detailFilter,
|
|
1704
|
-
sort = { direction: SORTING_OPTIONS.desc }
|
|
1705
|
-
}) => {
|
|
1706
|
-
const userId = typeof userFilter === "object" && userFilter ? userFilter.id : userFilter;
|
|
1707
|
-
const detail = typeof detailFilter === "object" && detailFilter ? detailFilter.id : detailFilter;
|
|
1708
|
-
const { start: startUnix, end: endUnix } = dateRangeToUnix2(startDate, endDate);
|
|
1709
|
-
const createdAfter = startDate ? `&created_after=${startUnix}` : "";
|
|
1710
|
-
const createdBefore = endDate ? `&created_before=${endUnix}` : "";
|
|
1711
|
-
const typeSearch = type ? `&object_type=${type.value}`.toLowerCase() : "";
|
|
1712
|
-
const userSearch = userId ? `&actor_id=${userId}` : "";
|
|
1713
|
-
const objectSearch = type && detail ? `&${type.queryParameter}=${encodeURIComponent(detail)}` : "";
|
|
1714
|
-
const { direction = SORTING_OPTIONS.desc } = sort;
|
|
1715
|
-
return `${createdAfter}${createdBefore}${userSearch}${typeSearch}${objectSearch}&sort=${direction}`;
|
|
1716
|
-
};
|
|
1717
|
-
var getAuditLogs = createAppAsyncThunk(`${sliceName5}/getAuditLogs`, (selectionState, { dispatch, getState }) => {
|
|
1718
|
-
const { page, perPage } = selectionState;
|
|
1719
|
-
const { hasAuditlogs } = getTenantCapabilities(getState());
|
|
1720
|
-
if (!hasAuditlogs) {
|
|
1721
|
-
return Promise.resolve();
|
|
1722
|
-
}
|
|
1723
|
-
return general_api_default.get(`${auditLogsApiUrl}/logs?page=${page}&per_page=${perPage}${prepareAuditlogQuery(selectionState)}`).then(({ data, headers }) => {
|
|
1724
|
-
let total = headers[headerNames.total];
|
|
1725
|
-
total = Number(total || data.length);
|
|
1726
|
-
return Promise.resolve(dispatch(actions5.receiveAuditLogs({ events: data, total })));
|
|
1727
|
-
}).catch((err) => commonErrorHandler(err, `There was an error retrieving audit logs:`, dispatch));
|
|
1728
|
-
});
|
|
1729
|
-
var getAuditLogsCsvLink = createAppAsyncThunk(
|
|
1730
|
-
`${sliceName5}/getAuditLogsCsvLink`,
|
|
1731
|
-
(_, { getState }) => Promise.resolve(`${window.location.origin}${auditLogsApiUrl}/logs/export?limit=20000${prepareAuditlogQuery(getAuditlogState(getState()))}`)
|
|
1732
|
-
);
|
|
1733
|
-
var setAuditlogsState = createAppAsyncThunk(
|
|
1734
|
-
`${sliceName5}/setAuditlogsState`,
|
|
1735
|
-
(selectionState, { dispatch, getState }) => {
|
|
1736
|
-
const currentState = getAuditlogState(getState());
|
|
1737
|
-
const nextState = {
|
|
1738
|
-
...currentState,
|
|
1739
|
-
...selectionState,
|
|
1740
|
-
sort: { ...currentState.sort, ...selectionState.sort }
|
|
1741
|
-
};
|
|
1742
|
-
const tasks = [];
|
|
1743
|
-
const { isLoading: currentLoading, selectedIssue: currentIssue, ...currentRequestState } = currentState;
|
|
1744
|
-
const { isLoading: selectionLoading, selectedIssue: selectionIssue, ...selectionRequestState } = nextState;
|
|
1745
|
-
if (!deepCompare3(currentRequestState, selectionRequestState)) {
|
|
1746
|
-
nextState.isLoading = true;
|
|
1747
|
-
tasks.push(dispatch(getAuditLogs(nextState)).finally(() => dispatch(actions5.setAuditLogState({ isLoading: false }))));
|
|
1748
|
-
}
|
|
1749
|
-
tasks.push(dispatch(actions5.setAuditLogState(nextState)));
|
|
1750
|
-
return Promise.all(tasks);
|
|
1751
|
-
}
|
|
1752
|
-
);
|
|
1753
|
-
var tenantDataDivergedMessage = "The system detected there is a change in your plan or purchased add-ons. Please log out and log in again";
|
|
1754
|
-
var addTenant = createAppAsyncThunk(
|
|
1755
|
-
`${sliceName5}/createTenant`,
|
|
1756
|
-
(selectionState, { dispatch, getState }) => {
|
|
1757
|
-
const spLimits = getSpLimits(getState());
|
|
1758
|
-
const { deviceLimits, ...rest } = selectionState;
|
|
1759
|
-
const device_limits = convertToBackendSPLimits(deviceLimits, spLimits);
|
|
1760
|
-
return general_api_default.post(`${tenantadmApiUrlv2}/tenants`, { ...rest, device_limits }).then(
|
|
1761
|
-
() => Promise.all([
|
|
1762
|
-
dispatch(setSnackbar3("Tenant was created successfully.")),
|
|
1763
|
-
new Promise((resolve) => setTimeout(() => resolve(dispatch(getTenants())), TIMEOUTS.oneSecond))
|
|
1764
|
-
])
|
|
1765
|
-
).catch((err) => commonErrorHandler(err, "There was an error creating tenant", dispatch, commonErrorFallback));
|
|
1766
|
-
}
|
|
1767
|
-
);
|
|
1768
|
-
var tenantListRetrieval = async (config) => {
|
|
1769
|
-
const { page, perPage } = config;
|
|
1770
|
-
const params = new URLSearchParams({ page, per_page: perPage, tiers: "true" }).toString();
|
|
1771
|
-
const tenantList = await general_api_default.get(`${tenantadmApiUrlv2}/tenants?${params}`);
|
|
1772
|
-
const totalCount = tenantList.headers[headerNames.total] || TENANT_LIST_DEFAULT.perPage;
|
|
1773
|
-
return [tenantList.data, Number(totalCount)];
|
|
1774
|
-
};
|
|
1775
|
-
var getTenants = createAppAsyncThunk(`${sliceName5}/getTenants`, async (_, { dispatch, getState }) => {
|
|
1776
|
-
const currentState = getTenantsList(getState());
|
|
1777
|
-
const [tenants, pageCount] = await tenantListRetrieval(currentState);
|
|
1778
|
-
dispatch(actions5.setTenantListState({ ...currentState, total: pageCount, tenants }));
|
|
1779
|
-
});
|
|
1780
|
-
var setTenantsListState = createAppAsyncThunk(
|
|
1781
|
-
`${sliceName5}/setTenantsListState`,
|
|
1782
|
-
async (selectionState, { dispatch, getState }) => {
|
|
1783
|
-
const currentState = getTenantsList(getState());
|
|
1784
|
-
const nextState = {
|
|
1785
|
-
...currentState,
|
|
1786
|
-
...selectionState
|
|
1787
|
-
};
|
|
1788
|
-
if (!deepCompare3(currentState, selectionState)) {
|
|
1789
|
-
const [tenants, pageCount] = await tenantListRetrieval(nextState);
|
|
1790
|
-
return dispatch(actions5.setTenantListState({ ...nextState, tenants, total: pageCount }));
|
|
1791
|
-
}
|
|
1792
|
-
return dispatch(actions5.setTenantListState({ ...nextState }));
|
|
1793
|
-
}
|
|
1794
|
-
);
|
|
1795
|
-
var editTenant = createAppAsyncThunk(`${sliceName5}/editDeviceLimit`, ({ deviceLimits, id, name }, { dispatch, getState }) => {
|
|
1796
|
-
const spLimits = getSpLimits(getState());
|
|
1797
|
-
const device_limits = convertToBackendSPLimits(deviceLimits, spLimits);
|
|
1798
|
-
return general_api_default.put(`${tenantadmApiUrlv2}/tenants/${id}/child`, { device_limits, name }).catch((err) => commonErrorHandler(err, `Device Limit cannot be changed`, dispatch)).then(
|
|
1799
|
-
() => Promise.all([
|
|
1800
|
-
dispatch(setSnackbar3("Tenant was changed successfully")),
|
|
1801
|
-
dispatch(getUserOrganization()),
|
|
1802
|
-
new Promise((resolve) => setTimeout(() => resolve(dispatch(getTenants())), TIMEOUTS.oneSecond))
|
|
1803
|
-
])
|
|
1804
|
-
);
|
|
1805
|
-
});
|
|
1806
|
-
var editBillingProfile = createAppAsyncThunk(
|
|
1807
|
-
`${sliceName5}/editBillingProfileEmail`,
|
|
1808
|
-
({ billingProfile }, { dispatch }) => general_api_default.patch(`${tenantadmApiUrlv2}/billing/profile`, billingProfile).catch((err) => commonErrorHandler(err, `Failed to change billing profile`, dispatch)).then(() => Promise.all([dispatch(setSnackbar3("Billing Profile was changed successfully")), dispatch(getUserBilling())]))
|
|
1809
|
-
);
|
|
1810
|
-
var createBillingProfile = createAppAsyncThunk(
|
|
1811
|
-
`${sliceName5}/createBillingProfileEmail`,
|
|
1812
|
-
({ billingProfile }, { dispatch }) => general_api_default.post(`${tenantadmApiUrlv2}/billing/profile`, billingProfile).catch((err) => commonErrorHandler(err, `Failed to create billing profile`, dispatch)).then(() => Promise.all([dispatch(setSnackbar3("Billing Profile was created successfully")), dispatch(getUserBilling())]))
|
|
1813
|
-
);
|
|
1814
|
-
var removeTenant = createAppAsyncThunk(
|
|
1815
|
-
`${sliceName5}/editDeviceLimit`,
|
|
1816
|
-
({ id }, { dispatch }) => general_api_default.post(`${tenantadmApiUrlv2}/tenants/${id}/remove/start`).catch((err) => commonErrorHandler(err, `There was an error removing the tenant`, dispatch)).then(
|
|
1817
|
-
() => Promise.all([
|
|
1818
|
-
dispatch(setSnackbar3("The tenant was removed successfully")),
|
|
1819
|
-
dispatch(getUserOrganization()),
|
|
1820
|
-
new Promise((resolve) => setTimeout(() => resolve(dispatch(getTenants())), TIMEOUTS.oneSecond))
|
|
1821
|
-
])
|
|
1822
|
-
)
|
|
1823
|
-
);
|
|
1824
|
-
var getUserOrganization = createAppAsyncThunk(
|
|
1825
|
-
`${sliceName5}/getUserOrganization`,
|
|
1826
|
-
(_, { dispatch, getState }) => general_api_default.get(`${tenantadmApiUrlv1}/user/tenant?tiers=true`).then((res) => {
|
|
1827
|
-
const { addons, plan, trial } = res.data;
|
|
1828
|
-
const { addons: currentAddons, id: currentId, plan: currentPlan, trial: currentTrial } = getOrganization(getState());
|
|
1829
|
-
const tasks = [dispatch(actions5.setOrganization(res.data))];
|
|
1830
|
-
if (currentId && !deepCompare3({ addons, plan, trial }, { addons: currentAddons, plan: currentPlan, trial: currentTrial })) {
|
|
1831
|
-
const hash = hashString(tenantDataDivergedMessage);
|
|
1832
|
-
const { id: currentUserId } = getCurrentUser(getState());
|
|
1833
|
-
cookies2.remove(`${currentUserId}${hash}`);
|
|
1834
|
-
tasks.push(dispatch(setAnnouncement(tenantDataDivergedMessage)));
|
|
1835
|
-
}
|
|
1836
|
-
return Promise.all(tasks);
|
|
1837
|
-
})
|
|
1838
|
-
);
|
|
1839
|
-
var getUserBilling = createAppAsyncThunk(
|
|
1840
|
-
`${sliceName5}/getUserBilling`,
|
|
1841
|
-
(_, { dispatch }) => general_api_default.get(`${tenantadmApiUrlv2}/billing/profile`).catch((err) => commonErrorHandler(err, "There was an error getting your billing profile:", dispatch, commonErrorFallback)).then((res) => dispatch(actions5.setBillingProfile(res.data)))
|
|
1842
|
-
);
|
|
1843
|
-
var getUserSubscription = createAppAsyncThunk(`${sliceName5}/getUserSubscription`, async (_, { dispatch }) => {
|
|
1844
|
-
const currentSubscription = await dispatch(getCurrentSubscription()).unwrap();
|
|
1845
|
-
const currentPreview = await dispatch(getBillingPreview({ preview_mode: "next" })).unwrap();
|
|
1846
|
-
return dispatch(actions5.setSubscription({ ...currentPreview, ...currentSubscription }));
|
|
1847
|
-
});
|
|
1848
|
-
var getBillingPreview = createAppAsyncThunk(
|
|
1849
|
-
`${sliceName5}/getBillingPreview`,
|
|
1850
|
-
(order, { dispatch }) => general_api_default.post(`${tenantadmApiUrlv2}/billing/subscription/invoices/preview`, order).catch((err) => commonErrorHandler(err, "There was an error getting your billing information:", dispatch, commonErrorFallback)).then(({ data }) => order.preview_mode === "recurring" ? { items: parseSubscriptionPreview(data.lines), total: data.total } : data)
|
|
1851
|
-
);
|
|
1852
|
-
var getCurrentSubscription = createAppAsyncThunk(
|
|
1853
|
-
`${sliceName5}/getCurrentSubscription`,
|
|
1854
|
-
(_, { dispatch }) => general_api_default.get(`${tenantadmApiUrlv2}/billing/subscription`).then((res) => res.data).catch((err) => {
|
|
1855
|
-
if (err.response && err.response.status === 404) {
|
|
1856
|
-
throw new Error("Request failed with status code 404");
|
|
1857
|
-
}
|
|
1858
|
-
return commonErrorHandler(err, "There was an error retrieving your current subscription", dispatch, commonErrorFallback);
|
|
1859
|
-
})
|
|
1860
|
-
);
|
|
1861
|
-
var getProducts = createAppAsyncThunk(
|
|
1862
|
-
`${sliceName5}/getEnabledTiers`,
|
|
1863
|
-
(_, { dispatch }) => general_api_default.get(`${tenantadmApiUrlv2}/billing/products`).catch((err) => commonErrorHandler(err, "There was an error getting Mender products:", dispatch, commonErrorFallback)).then((res) => dispatch(actions5.setProducts(transformProductResponse(res.data))))
|
|
1864
|
-
);
|
|
1865
|
-
var requestPlanUpgrade = createAppAsyncThunk(
|
|
1866
|
-
`${sliceName5}/requestPlanUpgrade`,
|
|
1867
|
-
(order, { dispatch }) => general_api_default.post(`${tenantadmApiUrlv2}/billing/subscription`, order).catch((err) => commonErrorHandler(err, "There was an error sending your request", dispatch, commonErrorFallback)).then(() => Promise.all([setTimeout(() => dispatch(getDeviceLimits()), TIMEOUTS.threeSeconds), dispatch(getUserOrganization())]))
|
|
1868
|
-
);
|
|
1869
|
-
var sendSupportMessage = createAppAsyncThunk(
|
|
1870
|
-
`${sliceName5}/sendSupportMessage`,
|
|
1871
|
-
(content, { dispatch }) => general_api_default.post(`${tenantadmApiUrlv2}/contact/support`, content).catch((err) => commonErrorHandler(err, "There was an error sending your request", dispatch, commonErrorFallback)).then(() => Promise.resolve(dispatch(setSnackbar3({ message: "Your request was sent successfully", autoHideDuration: TIMEOUTS.fiveSeconds }))))
|
|
1872
|
-
);
|
|
1873
|
-
var requestPlanChange = createAppAsyncThunk(
|
|
1874
|
-
`${sliceName5}/requestPlanChange`,
|
|
1875
|
-
({ content, tenantId }, { dispatch, rejectWithValue }) => general_api_default.post(`${tenantadmApiUrlv2}/tenants/${tenantId}/plan`, content).catch(async (err) => {
|
|
1876
|
-
await commonErrorHandler(err, "There was an error sending your request", dispatch, commonErrorFallback);
|
|
1877
|
-
rejectWithValue(err);
|
|
1878
|
-
}).then(() => Promise.resolve(dispatch(setSnackbar3({ message: "Your request was sent successfully", autoHideDuration: TIMEOUTS.fiveSeconds }))))
|
|
1879
|
-
);
|
|
1880
|
-
var downloadLicenseReport = createAppAsyncThunk(
|
|
1881
|
-
`${sliceName5}/downloadLicenseReport`,
|
|
1882
|
-
(_, { dispatch }) => general_api_default.get(`${deviceAuthV2}/license`).catch((err) => commonErrorHandler(err, "There was an error downloading the report", dispatch, commonErrorFallback)).then((res) => res.data)
|
|
1883
|
-
);
|
|
1884
|
-
var createIntegration = createAppAsyncThunk(
|
|
1885
|
-
`${sliceName5}/createIntegration`,
|
|
1886
|
-
({ id, ...integration }, { dispatch }) => general_api_default.post(`${iotManagerBaseURL}/integrations`, integration).catch((err) => commonErrorHandler(err, "There was an error creating the integration", dispatch, commonErrorFallback)).then(() => Promise.all([dispatch(setSnackbar3("The integration was set up successfully")), dispatch(getIntegrations())]))
|
|
1887
|
-
);
|
|
1888
|
-
var changeIntegration = createAppAsyncThunk(
|
|
1889
|
-
`${sliceName5}/changeIntegration`,
|
|
1890
|
-
({ id, credentials }, { dispatch }) => general_api_default.put(`${iotManagerBaseURL}/integrations/${id}/credentials`, credentials).catch((err) => commonErrorHandler(err, "There was an error updating the integration", dispatch, commonErrorFallback)).then(() => Promise.all([dispatch(setSnackbar3("The integration was updated successfully")), dispatch(getIntegrations())]))
|
|
1891
|
-
);
|
|
1892
|
-
var deleteIntegration = createAppAsyncThunk(
|
|
1893
|
-
`${sliceName5}/deleteIntegration`,
|
|
1894
|
-
({ id, provider }, { dispatch, getState }) => general_api_default.delete(`${iotManagerBaseURL}/integrations/${id}`, {}).catch((err) => commonErrorHandler(err, "There was an error removing the integration", dispatch, commonErrorFallback)).then(() => {
|
|
1895
|
-
const integrations = getState().organization.externalDeviceIntegrations.filter((item) => provider !== item.provider);
|
|
1896
|
-
return Promise.all([
|
|
1897
|
-
dispatch(setSnackbar3("The integration was removed successfully")),
|
|
1898
|
-
dispatch(actions5.receiveExternalDeviceIntegrations(integrations))
|
|
1899
|
-
]);
|
|
1900
|
-
})
|
|
1901
|
-
);
|
|
1902
|
-
var getIntegrations = createAppAsyncThunk(
|
|
1903
|
-
`${sliceName5}/getIntegrations`,
|
|
1904
|
-
(_, { dispatch, getState }) => general_api_default.get(`${iotManagerBaseURL}/integrations`).catch((err) => commonErrorHandler(err, "There was an error retrieving the integration", dispatch, commonErrorFallback)).then(({ data }) => {
|
|
1905
|
-
const existingIntegrations = getState().organization.externalDeviceIntegrations;
|
|
1906
|
-
const integrations = data.reduce((accu, item) => {
|
|
1907
|
-
const existingIntegration = existingIntegrations.find((integration2) => item.id === integration2.id) ?? {};
|
|
1908
|
-
const integration = { ...existingIntegration, ...item };
|
|
1909
|
-
accu.push(integration);
|
|
1910
|
-
return accu;
|
|
1911
|
-
}, []);
|
|
1912
|
-
return Promise.resolve(dispatch(actions5.receiveExternalDeviceIntegrations(integrations)));
|
|
1913
|
-
})
|
|
1914
|
-
);
|
|
1915
|
-
var getWebhookEvents = createAppAsyncThunk(`${sliceName5}/getWebhookEvents`, (config = {}, { dispatch, getState }) => {
|
|
1916
|
-
const { isFollowUp, page = defaultPage3, perPage = defaultPerPage3 } = config;
|
|
1917
|
-
return general_api_default.get(`${iotManagerBaseURL}/events?page=${page}&per_page=${perPage}`).catch((err) => commonErrorHandler(err, "There was an error retrieving activity for this integration", dispatch, commonErrorFallback)).then(({ data }) => {
|
|
1918
|
-
const tasks = [
|
|
1919
|
-
dispatch(
|
|
1920
|
-
actions5.receiveWebhookEvents({
|
|
1921
|
-
value: isFollowUp ? getState().organization.webhooks.events : data,
|
|
1922
|
-
total: (page - 1) * perPage + data.length
|
|
1923
|
-
})
|
|
1924
|
-
)
|
|
1925
|
-
];
|
|
1926
|
-
if (data.length >= perPage && !isFollowUp) {
|
|
1927
|
-
tasks.push(dispatch(getWebhookEvents({ isFollowUp: true, page: page + 1, perPage: 1 })));
|
|
1928
|
-
}
|
|
1929
|
-
return Promise.all(tasks);
|
|
1930
|
-
});
|
|
1931
|
-
});
|
|
1932
|
-
var ssoConfigActions = {
|
|
1933
|
-
create: { success: "stored", error: "storing" },
|
|
1934
|
-
edit: { success: "updated", error: "updating" },
|
|
1935
|
-
read: { success: "", error: "retrieving" },
|
|
1936
|
-
remove: { success: "removed", error: "removing" },
|
|
1937
|
-
readMultiple: { success: "", error: "retrieving" }
|
|
1938
|
-
};
|
|
1939
|
-
var ssoConfigActionErrorHandler = (err, type) => (dispatch) => commonErrorHandler(err, `There was an error ${ssoConfigActions[type].error} the SSO configuration.`, dispatch, commonErrorFallback);
|
|
1940
|
-
var ssoConfigActionSuccessHandler = (type) => (dispatch) => dispatch(setSnackbar3(`The SSO configuration was ${ssoConfigActions[type].success} successfully`));
|
|
1941
|
-
var storeSsoConfig = createAppAsyncThunk(
|
|
1942
|
-
`${sliceName5}/storeSsoConfig`,
|
|
1943
|
-
({ config, contentType }, { dispatch }) => general_api_default.post(ssoIdpApiUrlv1, config, { headers: { "Content-Type": contentType, Accept: "application/json" } }).catch((err) => dispatch(ssoConfigActionErrorHandler(err, "create"))).then(() => Promise.all([dispatch(ssoConfigActionSuccessHandler("create")), dispatch(getSsoConfigs())]))
|
|
1944
|
-
);
|
|
1945
|
-
var changeSsoConfig = createAppAsyncThunk(
|
|
1946
|
-
`${sliceName5}/changeSsoConfig`,
|
|
1947
|
-
({ config, contentType }, { dispatch }) => general_api_default.put(`${ssoIdpApiUrlv1}/${config.id}`, config.config, { headers: { "Content-Type": contentType, Accept: "application/json" } }).catch((err) => dispatch(ssoConfigActionErrorHandler(err, "edit"))).then(() => Promise.all([dispatch(ssoConfigActionSuccessHandler("edit")), dispatch(getSsoConfigs())]))
|
|
1948
|
-
);
|
|
1949
|
-
var deleteSsoConfig = createAppAsyncThunk(
|
|
1950
|
-
`${sliceName5}/deleteSsoConfig`,
|
|
1951
|
-
({ id }, { dispatch, getState }) => general_api_default.delete(`${ssoIdpApiUrlv1}/${id}`).catch((err) => dispatch(ssoConfigActionErrorHandler(err, "remove"))).then(() => {
|
|
1952
|
-
const configs = getState().organization.ssoConfigs.filter((item) => id !== item.id);
|
|
1953
|
-
return Promise.all([dispatch(ssoConfigActionSuccessHandler("remove")), dispatch(actions5.receiveSsoConfigs(configs))]);
|
|
1954
|
-
})
|
|
1955
|
-
);
|
|
1956
|
-
var getSsoConfigById = createAppAsyncThunk(
|
|
1957
|
-
`${sliceName5}/getSsoConfigById`,
|
|
1958
|
-
(config, { dispatch }) => general_api_default.get(`${ssoIdpApiUrlv1}/${config.id}`).catch((err) => dispatch(ssoConfigActionErrorHandler(err, "read"))).then(({ data, headers }) => {
|
|
1959
|
-
const sso = Object.values(SSO_TYPES).find(({ contentType }) => contentType === headers["content-type"]);
|
|
1960
|
-
return sso ? Promise.resolve({ ...config, config: data, type: sso.id }) : Promise.reject("Unsupported SSO config content type.");
|
|
1961
|
-
})
|
|
1962
|
-
);
|
|
1963
|
-
var getSsoConfigs = createAppAsyncThunk(
|
|
1964
|
-
`${sliceName5}/getSsoConfigs`,
|
|
1965
|
-
(_, { dispatch }) => general_api_default.get(ssoIdpApiUrlv1).catch((err) => dispatch(ssoConfigActionErrorHandler(err, "readMultiple"))).then(
|
|
1966
|
-
({ data }) => Promise.all(data.map((config) => dispatch(getSsoConfigById(config)).unwrap())).then((configs) => dispatch(actions5.receiveSsoConfigs(configs))).catch((err) => commonErrorHandler(err, err, dispatch, ""))
|
|
1967
|
-
)
|
|
1968
|
-
);
|
|
1969
|
-
|
|
1970
|
-
// src/usersSlice/thunks.ts
|
|
1971
|
-
import { duplicateFilter, extractErrorMessage as extractErrorMessage2, isEmpty as isEmpty2 } from "@northern.tech/utils/helpers";
|
|
1972
|
-
import { clearAllRetryTimers } from "@northern.tech/utils/retrytimer";
|
|
1973
|
-
import dayjs2 from "dayjs";
|
|
1974
|
-
import hashString2 from "md5";
|
|
1975
|
-
import Cookies3 from "universal-cookie";
|
|
1976
|
-
var cookies3 = new Cookies3();
|
|
1977
|
-
var { setAnnouncement: setAnnouncement2, setSnackbar: setSnackbar4 } = actions_default;
|
|
1978
|
-
var handleLoginError = (err, { token2fa: has2FA, password }, rejectWithValue) => () => {
|
|
1979
|
-
const errorText = extractErrorMessage2(err);
|
|
1980
|
-
const is2FABackend = errorText.includes("2fa");
|
|
1981
|
-
if (is2FABackend && !has2FA) {
|
|
1982
|
-
return rejectWithValue({ error: "2fa code missing" });
|
|
1983
|
-
}
|
|
1984
|
-
if (password === void 0) {
|
|
1985
|
-
return Promise.reject();
|
|
1986
|
-
}
|
|
1987
|
-
const twoFAError = is2FABackend ? " and verification code" : "";
|
|
1988
|
-
const errorMessage = `There was a problem logging in. Please check your email${twoFAError ? "," : " and"} password${twoFAError}. If you still have problems, contact an administrator.`;
|
|
1989
|
-
return rejectWithValue({ error: errorMessage });
|
|
1990
|
-
};
|
|
1991
|
-
var loginUser = createAppAsyncThunk(
|
|
1992
|
-
`${sliceName6}/loginUser`,
|
|
1993
|
-
({ stayLoggedIn, ...userData }, { dispatch, rejectWithValue }) => users_api_default.postLogin(`${useradmApiUrl}/auth/login`, { ...userData, no_expiry: stayLoggedIn }).catch((err) => {
|
|
1994
|
-
cleanUp();
|
|
1995
|
-
return Promise.reject(dispatch(handleLoginError(err, userData, rejectWithValue)));
|
|
1996
|
-
}).then(({ text: token, contentType }) => {
|
|
1997
|
-
if (contentType.includes(APPLICATION_JSON_CONTENT_TYPE)) {
|
|
1998
|
-
const { id, kind } = token;
|
|
1999
|
-
const type = kind.split("/")[1];
|
|
2000
|
-
const ssoLoginUrl = SSO_TYPES[type].getStartUrl(id);
|
|
2001
|
-
window.location.replace(ssoLoginUrl);
|
|
2002
|
-
return;
|
|
2003
|
-
}
|
|
2004
|
-
if (contentType !== APPLICATION_JWT_CONTENT_TYPE || !token) {
|
|
2005
|
-
return;
|
|
2006
|
-
}
|
|
2007
|
-
const now = /* @__PURE__ */ new Date();
|
|
2008
|
-
now.setSeconds(now.getSeconds() + maxSessionAge);
|
|
2009
|
-
const expiresAt = stayLoggedIn ? void 0 : now.toISOString();
|
|
2010
|
-
setSessionInfo({ token, expiresAt });
|
|
2011
|
-
cookies3.remove("JWT", { path: "/" });
|
|
2012
|
-
return dispatch(getUser(OWN_USER_ID)).unwrap().catch((e) => {
|
|
2013
|
-
cleanUp();
|
|
2014
|
-
return Promise.reject(dispatch(setSnackbar4(extractErrorMessage2(e))));
|
|
2015
|
-
}).then(() => {
|
|
2016
|
-
window.sessionStorage.removeItem("pendings-redirect");
|
|
2017
|
-
if (window.location.pathname !== "/ui/") {
|
|
2018
|
-
window.location.replace("/ui/");
|
|
2019
|
-
}
|
|
2020
|
-
return Promise.resolve(dispatch(actions6.successfullyLoggedIn({ expiresAt, token })));
|
|
2021
|
-
});
|
|
2022
|
-
})
|
|
2023
|
-
);
|
|
2024
|
-
var logoutUser = createAppAsyncThunk(`${sliceName6}/logoutUser`, (_, { dispatch, getState }) => {
|
|
2025
|
-
if (Object.keys(getState().app.uploadsById).length) {
|
|
2026
|
-
return Promise.reject();
|
|
2027
|
-
}
|
|
2028
|
-
return general_api_default.post(`${useradmApiUrl}/auth/logout`).finally(() => {
|
|
2029
|
-
cleanUp();
|
|
2030
|
-
clearAllRetryTimers(setSnackbar4);
|
|
2031
|
-
return Promise.resolve(dispatch({ type: USER_LOGOUT }));
|
|
2032
|
-
});
|
|
2033
|
-
});
|
|
2034
|
-
var switchUserOrganization = createAppAsyncThunk(`${sliceName6}/switchUserOrganization`, (tenantId, { getState }) => {
|
|
2035
|
-
if (Object.keys(getState().app.uploadsById).length) {
|
|
2036
|
-
return Promise.reject();
|
|
2037
|
-
}
|
|
2038
|
-
return general_api_default.get(`${useradmApiUrl}/users/tenants/${tenantId}/token`).then(({ data: token }) => {
|
|
2039
|
-
window.sessionStorage.setItem("tenantChanged", "true");
|
|
2040
|
-
setSessionInfo({ ...getSessionInfo(), token });
|
|
2041
|
-
window.location.reload();
|
|
2042
|
-
});
|
|
2043
|
-
});
|
|
2044
|
-
var passwordResetStart = createAppAsyncThunk(
|
|
2045
|
-
`${sliceName6}/passwordResetStart`,
|
|
2046
|
-
(email, { dispatch }) => general_api_default.post(`${useradmApiUrl}/auth/password-reset/start`, { email }).catch(
|
|
2047
|
-
(err) => commonErrorHandler(err, `The password reset request cannot be processed:`, dispatch, void 0, true)
|
|
2048
|
-
)
|
|
2049
|
-
);
|
|
2050
|
-
var passwordResetComplete = createAppAsyncThunk(
|
|
2051
|
-
`${sliceName6}/passwordResetComplete`,
|
|
2052
|
-
({ secretHash, newPassword }, { dispatch }) => general_api_default.post(`${useradmApiUrl}/auth/password-reset/complete`, { secret_hash: secretHash, password: newPassword }).catch((err = {}) => {
|
|
2053
|
-
const { error, response = {} } = err;
|
|
2054
|
-
let errorMsg = "";
|
|
2055
|
-
if (response.status == 400) {
|
|
2056
|
-
errorMsg = "the link you are using expired or the request is not valid, please try again.";
|
|
2057
|
-
} else {
|
|
2058
|
-
errorMsg = error;
|
|
2059
|
-
}
|
|
2060
|
-
dispatch(setSnackbar4("The password reset request cannot be processed: " + errorMsg));
|
|
2061
|
-
return Promise.reject(err);
|
|
2062
|
-
})
|
|
2063
|
-
);
|
|
2064
|
-
var verifyEmailStart = createAppAsyncThunk(
|
|
2065
|
-
`${sliceName6}/verifyEmailStart`,
|
|
2066
|
-
(_, { dispatch, getState }) => general_api_default.post(`${useradmApiUrl}/auth/verify-email/start`, { email: getCurrentUser(getState()).email }).catch((err) => commonErrorHandler(err, "An error occured starting the email verification process:", dispatch)).finally(() => Promise.resolve(dispatch(getUser(OWN_USER_ID))))
|
|
2067
|
-
);
|
|
2068
|
-
var verifyEmailComplete = createAppAsyncThunk(
|
|
2069
|
-
`${sliceName6}/verifyEmailComplete`,
|
|
2070
|
-
(secret_hash, { dispatch, rejectWithValue }) => general_api_default.post(`${useradmApiUrl}/auth/verify-email/complete`, { secret_hash }).catch((err) => rejectWithValue({ status: err.response?.status, data: err.response?.data })).finally(() => Promise.resolve(dispatch(getUser(OWN_USER_ID))))
|
|
2071
|
-
);
|
|
2072
|
-
var verify2FA = createAppAsyncThunk(
|
|
2073
|
-
`${sliceName6}/verify2FA`,
|
|
2074
|
-
(tfaData, { dispatch }) => users_api_default.putVerifyTFA(`${useradmApiUrl}/2faverify`, tfaData).then(() => Promise.resolve(dispatch(getUser(OWN_USER_ID)))).catch(
|
|
2075
|
-
(err) => commonErrorHandler(err, "An error occured validating the verification code: failed to verify token, please try again.", dispatch, void 0, true)
|
|
2076
|
-
)
|
|
2077
|
-
);
|
|
2078
|
-
var getUserList = createAppAsyncThunk(
|
|
2079
|
-
`${sliceName6}/getUserList`,
|
|
2080
|
-
(_, { dispatch, getState }) => general_api_default.get(`${useradmApiUrl}/users`).then((res) => {
|
|
2081
|
-
const currentUsersById = getUsersById(getState());
|
|
2082
|
-
const users = res.data.reduce(
|
|
2083
|
-
(accu, item) => {
|
|
2084
|
-
accu[item.id] = {
|
|
2085
|
-
...accu[item.id],
|
|
2086
|
-
...item
|
|
2087
|
-
};
|
|
2088
|
-
return accu;
|
|
2089
|
-
},
|
|
2090
|
-
{ ...currentUsersById }
|
|
2091
|
-
);
|
|
2092
|
-
return dispatch(actions6.receivedUserList(users));
|
|
2093
|
-
}).catch((err) => commonErrorHandler(err, `Users couldn't be loaded.`, dispatch, commonErrorFallback))
|
|
2094
|
-
);
|
|
2095
|
-
var getUser = createAppAsyncThunk(
|
|
2096
|
-
`${sliceName6}/getUser`,
|
|
2097
|
-
(id, { dispatch, rejectWithValue }) => general_api_default.get(`${useradmApiUrl}/users/${id}`).then(
|
|
2098
|
-
({ data: user }) => Promise.all([
|
|
2099
|
-
dispatch(actions6.receivedUser(user)),
|
|
2100
|
-
dispatch(setHideAnnouncement({ shouldHide: false, userId: user.id })),
|
|
2101
|
-
dispatch(updateUserColumnSettings({ currentUserId: user.id })),
|
|
2102
|
-
user
|
|
2103
|
-
])
|
|
2104
|
-
).catch((e) => rejectWithValue(e))
|
|
2105
|
-
);
|
|
2106
|
-
var initializeSelf = createAppAsyncThunk(`${sliceName6}/initializeSelf`, (_, { dispatch }) => dispatch(getUser(OWN_USER_ID)));
|
|
2107
|
-
var updateUserColumnSettings = createAppAsyncThunk(
|
|
2108
|
-
`${sliceName6}/updateUserColumnSettings`,
|
|
2109
|
-
({ columns, currentUserId }, { dispatch, getState }) => {
|
|
2110
|
-
const userId = currentUserId ?? getCurrentUser(getState()).id;
|
|
2111
|
-
const storageKey = `${userId}-column-widths`;
|
|
2112
|
-
let customColumns = [];
|
|
2113
|
-
if (!columns) {
|
|
2114
|
-
try {
|
|
2115
|
-
customColumns = JSON.parse(window.localStorage.getItem(storageKey) || "") || customColumns;
|
|
2116
|
-
} catch {
|
|
2117
|
-
}
|
|
2118
|
-
} else {
|
|
2119
|
-
customColumns = columns;
|
|
2120
|
-
}
|
|
2121
|
-
window.localStorage.setItem(storageKey, JSON.stringify(customColumns));
|
|
2122
|
-
return Promise.resolve(dispatch(actions6.setCustomColumns(customColumns)));
|
|
2123
|
-
}
|
|
2124
|
-
);
|
|
2125
|
-
var userActions = {
|
|
2126
|
-
add: {
|
|
2127
|
-
successMessage: "The user was added successfully.",
|
|
2128
|
-
errorMessage: "adding"
|
|
2129
|
-
},
|
|
2130
|
-
create: {
|
|
2131
|
-
successMessage: "The user was created successfully.",
|
|
2132
|
-
errorMessage: "creating"
|
|
2133
|
-
},
|
|
2134
|
-
edit: {
|
|
2135
|
-
successMessage: "The user has been updated.",
|
|
2136
|
-
errorMessage: "editing"
|
|
2137
|
-
},
|
|
2138
|
-
remove: {
|
|
2139
|
-
successMessage: "The user was removed from the system.",
|
|
2140
|
-
errorMessage: "removing"
|
|
2141
|
-
}
|
|
2142
|
-
};
|
|
2143
|
-
var userActionErrorHandler = (err, type, dispatch) => commonErrorHandler(err, `There was an error ${userActions[type].errorMessage} the user.`, dispatch);
|
|
2144
|
-
var createUser = createAppAsyncThunk(
|
|
2145
|
-
`${sliceName6}/createUser`,
|
|
2146
|
-
({ shouldResetPassword, ...userData }, { dispatch }) => general_api_default.post(`${useradmApiUrl}/users`, { ...userData, send_reset_password: shouldResetPassword }).then(() => Promise.all([dispatch(getUserList()), dispatch(setSnackbar4(userActions.create.successMessage))])).catch((err) => userActionErrorHandler(err, "create", dispatch))
|
|
2147
|
-
);
|
|
2148
|
-
var removeUser = createAppAsyncThunk(
|
|
2149
|
-
`${sliceName6}/removeUser`,
|
|
2150
|
-
(userId, { dispatch }) => general_api_default.delete(`${useradmApiUrl}/users/${userId}`).then(() => Promise.all([dispatch(actions6.removedUser(userId)), dispatch(getUserList()), dispatch(setSnackbar4(userActions.remove.successMessage))])).catch((err) => userActionErrorHandler(err, "remove", dispatch))
|
|
2151
|
-
);
|
|
2152
|
-
var editUser = createAppAsyncThunk(
|
|
2153
|
-
`${sliceName6}/editUser`,
|
|
2154
|
-
({ id, ...userData }, { dispatch, getState }) => general_api_default.put(`${useradmApiUrl}/users/${id}`, userData).then(
|
|
2155
|
-
() => Promise.all([
|
|
2156
|
-
dispatch(actions6.updatedUser({ ...userData, id: id === OWN_USER_ID ? getCurrentUser(getState()).id : id })),
|
|
2157
|
-
dispatch(setSnackbar4(userActions.edit.successMessage))
|
|
2158
|
-
])
|
|
2159
|
-
).catch((err) => userActionErrorHandler(err, "edit", dispatch))
|
|
2160
|
-
);
|
|
2161
|
-
var checkEmailExists = createAppAsyncThunk(`${sliceName6}/checkEmailExists`, async (email) => {
|
|
2162
|
-
const response = await general_api_default.get(`${useradmApiUrl}/users/exists?email=${encodeURIComponent(email)}`);
|
|
2163
|
-
return response.data.exists;
|
|
2164
|
-
});
|
|
2165
|
-
var addUserToCurrentTenant = createAppAsyncThunk(`${sliceName6}/addUserToTenant`, (userId, { dispatch, getState }) => {
|
|
2166
|
-
const { id } = getOrganization(getState());
|
|
2167
|
-
return general_api_default.post(`${useradmApiUrl}/users/${userId}/assign`, { tenant_ids: [id] }).catch((err) => commonErrorHandler(err, `There was an error adding the user to your organization:`, dispatch)).then(() => Promise.all([dispatch(setSnackbar4(userActions.add.successMessage)), dispatch(getUserList())]));
|
|
2168
|
-
});
|
|
2169
|
-
var enableUser2fa = createAppAsyncThunk(
|
|
2170
|
-
`${sliceName6}/enableUser2fa`,
|
|
2171
|
-
(userId = OWN_USER_ID, { dispatch }) => general_api_default.post(`${useradmApiUrl}/users/${userId}/2fa/enable`).catch((err) => commonErrorHandler(err, `There was an error enabling Two Factor authentication for the user.`, dispatch)).then(() => Promise.resolve(dispatch(getUser(userId))))
|
|
2172
|
-
);
|
|
2173
|
-
var disableUser2fa = createAppAsyncThunk(
|
|
2174
|
-
`${sliceName6}/disableUser2fa`,
|
|
2175
|
-
(userId = OWN_USER_ID, { dispatch }) => general_api_default.post(`${useradmApiUrl}/users/${userId}/2fa/disable`).catch((err) => commonErrorHandler(err, `There was an error disabling Two Factor authentication for the user.`, dispatch)).then(() => Promise.all([dispatch(getUser(userId)), dispatch(actions6.receivedQrCode(null))]))
|
|
2176
|
-
);
|
|
2177
|
-
var mapHttpPermission = (permission) => Object.entries(uiPermissionsByArea).reduce(
|
|
2178
|
-
(accu, [area, definition]) => {
|
|
2179
|
-
const endpointMatches = definition.endpoints.filter(
|
|
2180
|
-
(endpoint) => endpoint.path.test(permission.value) && (endpoint.types.includes(permission.type) || permission.type === PermissionTypes.Any)
|
|
2181
|
-
);
|
|
2182
|
-
if (permission.value === PermissionTypes.Any || permission.value.includes(apiRoot) && endpointMatches.length) {
|
|
2183
|
-
const endpointUiPermission = endpointMatches.reduce((endpointAccu, endpoint) => [...endpointAccu, ...endpoint.uiPermissions], []);
|
|
2184
|
-
const collector = (endpointUiPermission || definition.uiPermissions).reduce((permissionsAccu, uiPermission) => {
|
|
2185
|
-
if (permission.type === PermissionTypes.Any || !endpointMatches.length && uiPermission.verbs.some((verb) => verb === permission.type)) {
|
|
2186
|
-
permissionsAccu.push(uiPermission.value);
|
|
2187
|
-
}
|
|
2188
|
-
return permissionsAccu;
|
|
2189
|
-
}, []).filter(duplicateFilter);
|
|
2190
|
-
if (Array.isArray(accu[area])) {
|
|
2191
|
-
accu[area] = [...accu[area], ...collector].filter(duplicateFilter);
|
|
2192
|
-
} else {
|
|
2193
|
-
accu[area] = mergePermissions(accu[area], { [scopedPermissionAreas[area].excessiveAccessSelector]: collector });
|
|
2194
|
-
}
|
|
2195
|
-
}
|
|
2196
|
-
return accu;
|
|
2197
|
-
},
|
|
2198
|
-
{ ...emptyUiPermissions }
|
|
2199
|
-
);
|
|
2200
|
-
var permissionActionTypes = {
|
|
2201
|
-
any: mapHttpPermission,
|
|
2202
|
-
CREATE_DEPLOYMENT: (permission) => permission.type === PermissionTypes.DeviceGroup ? {
|
|
2203
|
-
deployments: [uiPermissionsById.deploy.value],
|
|
2204
|
-
groups: { [permission.value]: [uiPermissionsById.deploy.value] }
|
|
2205
|
-
} : {},
|
|
2206
|
-
http: mapHttpPermission,
|
|
2207
|
-
REMOTE_TERMINAL: (permission) => permission.type === PermissionTypes.DeviceGroup ? {
|
|
2208
|
-
groups: { [permission.value]: [uiPermissionsById.connect.value] }
|
|
2209
|
-
} : {},
|
|
2210
|
-
VIEW_DEVICE: (permission) => permission.type === PermissionTypes.DeviceGroup ? {
|
|
2211
|
-
groups: { [permission.value]: [uiPermissionsById.read.value] }
|
|
2212
|
-
} : {}
|
|
2213
|
-
};
|
|
2214
|
-
var combinePermissions = (existingPermissions, additionalPermissions = {}) => Object.entries(additionalPermissions).reduce((accu, [name, permissions]) => {
|
|
2215
|
-
const maybeExistingPermissions = accu[name] || [];
|
|
2216
|
-
accu[name] = [...permissions, ...maybeExistingPermissions].filter(duplicateFilter);
|
|
2217
|
-
return accu;
|
|
2218
|
-
}, existingPermissions);
|
|
2219
|
-
var tryParseCustomPermission = (permission) => {
|
|
2220
|
-
const uiPermissions = permissionActionTypes[permission.action](permission.object);
|
|
2221
|
-
const result = mergePermissions({ ...emptyUiPermissions }, uiPermissions);
|
|
2222
|
-
return { isCustom: true, permission, result };
|
|
2223
|
-
};
|
|
2224
|
-
var customPermissionHandler = (accu, permission) => {
|
|
2225
|
-
const processor = tryParseCustomPermission(permission);
|
|
2226
|
-
return {
|
|
2227
|
-
...accu,
|
|
2228
|
-
isCustom: accu.isCustom || processor.isCustom,
|
|
2229
|
-
uiPermissions: mergePermissions(accu.uiPermissions, processor.result)
|
|
2230
|
-
};
|
|
2231
|
-
};
|
|
2232
|
-
var mapPermissionSet = (permissionSetName, names, scope, existingGroupsPermissions = {}) => {
|
|
2233
|
-
const permission = Object.values(uiPermissionsById).find((permission2) => permission2.permissionSets[scope] === permissionSetName)?.value;
|
|
2234
|
-
const scopedPermissions = names.reduce((accu, name) => combinePermissions(accu, { [name]: [permission] }), existingGroupsPermissions);
|
|
2235
|
-
return Object.entries(scopedPermissions).reduce((accu, [key, permissions]) => ({ ...accu, [key]: deriveImpliedAreaPermissions(scope, permissions) }), {});
|
|
2236
|
-
};
|
|
2237
|
-
var isEmptyPermissionSet = (permissionSet) => !Object.values(permissionSet).reduce((accu, permissions) => {
|
|
2238
|
-
if (Array.isArray(permissions)) {
|
|
2239
|
-
return accu || !!permissions.length;
|
|
2240
|
-
}
|
|
2241
|
-
return accu || !isEmpty2(permissions);
|
|
2242
|
-
}, false);
|
|
2243
|
-
var parseRolePermissions = ({ permission_sets_with_scope = [], permissions = [] }, permissionSets) => {
|
|
2244
|
-
const preliminaryResult = permission_sets_with_scope.reduce(
|
|
2245
|
-
(accu, permissionSet) => {
|
|
2246
|
-
if (!permissionSet.name) {
|
|
2247
|
-
return accu;
|
|
2248
|
-
}
|
|
2249
|
-
const processor = permissionSets[permissionSet.name];
|
|
2250
|
-
if (!processor) {
|
|
2251
|
-
return accu;
|
|
2252
|
-
}
|
|
2253
|
-
const scope = Object.keys(scopedPermissionAreas).find((scope2) => uiPermissionsByArea[scope2].scope === permissionSet.scope?.type);
|
|
2254
|
-
if (scope) {
|
|
2255
|
-
const result = mapPermissionSet(
|
|
2256
|
-
permissionSet.name,
|
|
2257
|
-
permissionSet.scope?.value ?? [],
|
|
2258
|
-
scope,
|
|
2259
|
-
accu.uiPermissions[scope]
|
|
2260
|
-
);
|
|
2261
|
-
return { ...accu, uiPermissions: { ...accu.uiPermissions, [scope]: result } };
|
|
2262
|
-
} else if (isEmptyPermissionSet(processor.result)) {
|
|
2263
|
-
return processor.permissions?.reduce(customPermissionHandler, accu);
|
|
2264
|
-
}
|
|
2265
|
-
return {
|
|
2266
|
-
...accu,
|
|
2267
|
-
isCustom: accu.isCustom || processor.isCustom,
|
|
2268
|
-
uiPermissions: mergePermissions(accu.uiPermissions, processor.result)
|
|
2269
|
-
};
|
|
2270
|
-
},
|
|
2271
|
-
{ isCustom: false, uiPermissions: { ...emptyUiPermissions, groups: {}, releases: {} } }
|
|
2272
|
-
);
|
|
2273
|
-
return permissions.reduce(customPermissionHandler, preliminaryResult);
|
|
2274
|
-
};
|
|
2275
|
-
var normalizeRbacRoles = (roles, rolesById2, permissionSets) => roles.reduce(
|
|
2276
|
-
(accu, role) => {
|
|
2277
|
-
let normalizedPermissions;
|
|
2278
|
-
let isCustom = false;
|
|
2279
|
-
if (rolesById2[role.name]) {
|
|
2280
|
-
normalizedPermissions = {
|
|
2281
|
-
...rolesById2[role.name].uiPermissions,
|
|
2282
|
-
groups: { ...rolesById2[role.name].uiPermissions.groups },
|
|
2283
|
-
releases: { ...rolesById2[role.name].uiPermissions.releases }
|
|
2284
|
-
};
|
|
2285
|
-
} else {
|
|
2286
|
-
const result = parseRolePermissions(role, permissionSets);
|
|
2287
|
-
normalizedPermissions = result.uiPermissions;
|
|
2288
|
-
isCustom = result.isCustom;
|
|
2289
|
-
}
|
|
2290
|
-
const roleState = accu[role.name] ?? { ...emptyRole };
|
|
2291
|
-
accu[role.name] = {
|
|
2292
|
-
...roleState,
|
|
2293
|
-
...role,
|
|
2294
|
-
description: roleState.description ? roleState.description : role.description,
|
|
2295
|
-
editable: !rolesById[role.name] && !isCustom && (typeof roleState.editable !== "undefined" ? roleState.editable : true),
|
|
2296
|
-
isCustom,
|
|
2297
|
-
name: roleState.name ? roleState.name : role.name,
|
|
2298
|
-
uiPermissions: normalizedPermissions
|
|
2299
|
-
};
|
|
2300
|
-
return accu;
|
|
2301
|
-
},
|
|
2302
|
-
{ ...rolesById2 }
|
|
2303
|
-
);
|
|
2304
|
-
var getPermissionSets = createAppAsyncThunk(
|
|
2305
|
-
`${sliceName6}/getPermissionSets`,
|
|
2306
|
-
(_, { dispatch, getState }) => general_api_default.get(`${useradmApiUrlv2}/permission_sets?per_page=500`).then(({ data }) => {
|
|
2307
|
-
const permissionSets = data.reduce(
|
|
2308
|
-
(accu, permissionSet) => {
|
|
2309
|
-
const permissionSetState = accu[permissionSet.name] ?? {};
|
|
2310
|
-
let permissionSetObject = { ...permissionSetState, ...permissionSet };
|
|
2311
|
-
permissionSetObject.result = Object.values(uiPermissionsById).reduce(
|
|
2312
|
-
(accu2, item) => Object.entries(item.permissionSets).reduce((collector, [area, permissionSet2]) => {
|
|
2313
|
-
if (scopedPermissionAreas[area]) {
|
|
2314
|
-
return collector;
|
|
2315
|
-
}
|
|
2316
|
-
if (permissionSet2 === permissionSetObject.name) {
|
|
2317
|
-
collector[area] = [...collector[area], item.value].filter(duplicateFilter);
|
|
2318
|
-
}
|
|
2319
|
-
return collector;
|
|
2320
|
-
}, accu2),
|
|
2321
|
-
{ ...emptyUiPermissions, ...permissionSetObject.result ?? {} }
|
|
2322
|
-
);
|
|
2323
|
-
const scopes = Object.values(scopedPermissionAreas).reduce((accu2, { key, scopeType }) => {
|
|
2324
|
-
if (permissionSetObject.supported_scope_types?.includes(key) || permissionSetObject.supported_scope_types?.includes(scopeType)) {
|
|
2325
|
-
accu2.push(key);
|
|
2326
|
-
}
|
|
2327
|
-
return accu2;
|
|
2328
|
-
}, []);
|
|
2329
|
-
permissionSetObject = scopes.reduce((accu2, scope) => {
|
|
2330
|
-
accu2.result = {
|
|
2331
|
-
...accu2.result,
|
|
2332
|
-
[scope]: mapPermissionSet(permissionSetObject.name, [scopedPermissionAreas[scope].excessiveAccessSelector], scope)
|
|
2333
|
-
};
|
|
2334
|
-
return accu2;
|
|
2335
|
-
}, permissionSetObject);
|
|
2336
|
-
accu[permissionSet.name] = permissionSetObject;
|
|
2337
|
-
return accu;
|
|
2338
|
-
},
|
|
2339
|
-
{ ...getState().users.permissionSetsById }
|
|
2340
|
-
);
|
|
2341
|
-
return Promise.all([dispatch(actions6.receivedPermissionSets(permissionSets)), permissionSets]);
|
|
2342
|
-
}).catch(() => console.log("Permission set retrieval failed - likely accessing a non-RBAC backend"))
|
|
2343
|
-
);
|
|
2344
|
-
var getRoles = createAppAsyncThunk(
|
|
2345
|
-
`${sliceName6}/getRoles`,
|
|
2346
|
-
(_, { dispatch, getState }) => Promise.all([general_api_default.get(`${useradmApiUrlv2}/roles?per_page=500`), dispatch(getPermissionSets())]).then((results) => {
|
|
2347
|
-
if (!results) {
|
|
2348
|
-
return Promise.resolve();
|
|
2349
|
-
}
|
|
2350
|
-
const [{ data: roles }, { payload: permissionSetTasks }] = results;
|
|
2351
|
-
const rolesById2 = normalizeRbacRoles(roles, getRolesById(getState()), permissionSetTasks[permissionSetTasks.length - 1]);
|
|
2352
|
-
return Promise.resolve(dispatch(actions6.receivedRoles(rolesById2)));
|
|
2353
|
-
}).catch(() => console.log("Role retrieval failed - likely accessing a non-RBAC backend")).finally(() => Promise.resolve(dispatch(actions6.finishedRoleInitialization(true))))
|
|
2354
|
-
);
|
|
2355
|
-
var deriveImpliedAreaPermissions = (area, areaPermissions, skipPermissions = []) => {
|
|
2356
|
-
const highestAreaPermissionLevelSelected = areaPermissions.reduce(
|
|
2357
|
-
(highest, current) => uiPermissionsById[current].permissionLevel > highest ? uiPermissionsById[current].permissionLevel : highest,
|
|
2358
|
-
1
|
|
2359
|
-
);
|
|
2360
|
-
return uiPermissionsByArea[area].uiPermissions.reduce((permissions, current) => {
|
|
2361
|
-
if ((current.permissionLevel < highestAreaPermissionLevelSelected || areaPermissions.includes(current.value)) && !skipPermissions.includes(current.value)) {
|
|
2362
|
-
permissions.push(current.value);
|
|
2363
|
-
}
|
|
2364
|
-
return permissions;
|
|
2365
|
-
}, []);
|
|
2366
|
-
};
|
|
2367
|
-
var transformAreaRoleDataToScopedPermissionsSets = (area, areaPermissions, excessiveAccessSelector) => {
|
|
2368
|
-
const permissionSetObject = areaPermissions.reduce((accu, { item, uiPermissions }) => {
|
|
2369
|
-
const skipPermissions = scopedPermissionAreas.releases.key === area && item !== ALL_RELEASES ? [uiPermissionsById.upload.value] : [];
|
|
2370
|
-
const impliedPermissions = deriveImpliedAreaPermissions(area, uiPermissions, skipPermissions);
|
|
2371
|
-
accu = impliedPermissions.reduce((itemPermissionAccu, impliedPermission) => {
|
|
2372
|
-
const permissionSetState = itemPermissionAccu[uiPermissionsById[impliedPermission].permissionSets[area]] ?? {
|
|
2373
|
-
type: uiPermissionsByArea[area].scope,
|
|
2374
|
-
value: []
|
|
2375
|
-
};
|
|
2376
|
-
itemPermissionAccu[uiPermissionsById[impliedPermission].permissionSets[area]] = {
|
|
2377
|
-
...permissionSetState,
|
|
2378
|
-
value: [...permissionSetState.value, item]
|
|
2379
|
-
};
|
|
2380
|
-
return itemPermissionAccu;
|
|
2381
|
-
}, accu);
|
|
2382
|
-
return accu;
|
|
2383
|
-
}, {});
|
|
2384
|
-
return Object.entries(permissionSetObject).map(([name, { value, ...scope }]) => {
|
|
2385
|
-
if (value.includes(excessiveAccessSelector)) {
|
|
2386
|
-
return { name };
|
|
2387
|
-
}
|
|
2388
|
-
return { name, scope: { ...scope, value: value.filter(duplicateFilter) } };
|
|
2389
|
-
});
|
|
2390
|
-
};
|
|
2391
|
-
var transformRoleDataToRole = (roleData, roleState = {}) => {
|
|
2392
|
-
const role = { ...roleState, ...roleData };
|
|
2393
|
-
const { description = "", name, uiPermissions = emptyUiPermissions } = role;
|
|
2394
|
-
const { maybeUiPermissions, remainderKeys } = Object.entries(emptyUiPermissions).reduce(
|
|
2395
|
-
(accu, [key, emptyPermissions]) => {
|
|
2396
|
-
if (!scopedPermissionAreas[key]) {
|
|
2397
|
-
accu.remainderKeys.push(key);
|
|
2398
|
-
} else if (uiPermissions[key]) {
|
|
2399
|
-
accu.maybeUiPermissions[key] = uiPermissions[key].reduce(itemUiPermissionsReducer, emptyPermissions);
|
|
2400
|
-
}
|
|
2401
|
-
return accu;
|
|
2402
|
-
},
|
|
2403
|
-
{ maybeUiPermissions: {}, remainderKeys: [] }
|
|
2404
|
-
);
|
|
2405
|
-
const { permissionSetsWithScope, roleUiPermissions } = remainderKeys.reduce(
|
|
2406
|
-
(accu, area) => {
|
|
2407
|
-
const areaPermissions = role.uiPermissions[area];
|
|
2408
|
-
if (!Array.isArray(areaPermissions)) {
|
|
2409
|
-
return accu;
|
|
2410
|
-
}
|
|
2411
|
-
const impliedPermissions = deriveImpliedAreaPermissions(area, areaPermissions);
|
|
2412
|
-
accu.roleUiPermissions[area] = impliedPermissions;
|
|
2413
|
-
const mappedPermissions = impliedPermissions.map((uiPermission) => ({ name: uiPermissionsById[uiPermission].permissionSets[area] }));
|
|
2414
|
-
accu.permissionSetsWithScope.push(...mappedPermissions);
|
|
2415
|
-
return accu;
|
|
2416
|
-
},
|
|
2417
|
-
{ permissionSetsWithScope: [{ name: defaultPermissionSets.Basic.name }], roleUiPermissions: {} }
|
|
2418
|
-
);
|
|
2419
|
-
const scopedPermissionSets = Object.values(scopedPermissionAreas).reduce((accu, { key, excessiveAccessSelector }) => {
|
|
2420
|
-
if (!uiPermissions[key]) {
|
|
2421
|
-
return accu;
|
|
2422
|
-
}
|
|
2423
|
-
accu.push(
|
|
2424
|
-
...transformAreaRoleDataToScopedPermissionsSets(
|
|
2425
|
-
key,
|
|
2426
|
-
uiPermissions[key],
|
|
2427
|
-
excessiveAccessSelector
|
|
2428
|
-
)
|
|
2429
|
-
);
|
|
2430
|
-
return accu;
|
|
2431
|
-
}, []);
|
|
2432
|
-
return {
|
|
2433
|
-
permissionSetsWithScope: [...permissionSetsWithScope, ...scopedPermissionSets],
|
|
2434
|
-
role: {
|
|
2435
|
-
...emptyRole,
|
|
2436
|
-
name,
|
|
2437
|
-
description: description ? description : roleState.description || "",
|
|
2438
|
-
uiPermissions: {
|
|
2439
|
-
...emptyUiPermissions,
|
|
2440
|
-
...roleUiPermissions,
|
|
2441
|
-
...maybeUiPermissions
|
|
2442
|
-
}
|
|
2443
|
-
}
|
|
2444
|
-
};
|
|
2445
|
-
};
|
|
2446
|
-
var roleActions = {
|
|
2447
|
-
create: {
|
|
2448
|
-
successMessage: "The role was created successfully.",
|
|
2449
|
-
errorMessage: "creating"
|
|
2450
|
-
},
|
|
2451
|
-
edit: {
|
|
2452
|
-
successMessage: "The role has been updated.",
|
|
2453
|
-
errorMessage: "editing"
|
|
2454
|
-
},
|
|
2455
|
-
remove: {
|
|
2456
|
-
successMessage: "The role was deleted successfully.",
|
|
2457
|
-
errorMessage: "removing"
|
|
2458
|
-
}
|
|
2459
|
-
};
|
|
2460
|
-
var roleActionErrorHandler = (err, type, dispatch, meta) => {
|
|
2461
|
-
let errorContext = `There was an error ${roleActions[type].errorMessage} the role.`;
|
|
2462
|
-
if (meta) {
|
|
2463
|
-
const { permissionSetsCreated, name } = meta;
|
|
2464
|
-
errorContext += ` Tried to ${type} role ${name} with ${permissionSetsCreated} permission sets.`;
|
|
2465
|
-
}
|
|
2466
|
-
return commonErrorHandler(err, errorContext, dispatch);
|
|
2467
|
-
};
|
|
2468
|
-
var createRole = createAppAsyncThunk(`${sliceName6}/createRole`, (roleData, { dispatch }) => {
|
|
2469
|
-
const { permissionSetsWithScope, role } = transformRoleDataToRole(roleData);
|
|
2470
|
-
return general_api_default.post(`${useradmApiUrlv2}/roles`, {
|
|
2471
|
-
name: role.name,
|
|
2472
|
-
description: role.description,
|
|
2473
|
-
permission_sets_with_scope: permissionSetsWithScope
|
|
2474
|
-
}).then(() => Promise.all([dispatch(actions6.createdRole(role)), dispatch(getRoles()), dispatch(setSnackbar4(roleActions.create.successMessage))])).catch((err) => roleActionErrorHandler(err, "create", dispatch, { permissionSetsCreated: permissionSetsWithScope.length, name: role.name }));
|
|
2475
|
-
});
|
|
2476
|
-
var editRole = createAppAsyncThunk(`${sliceName6}/editRole`, (roleData, { dispatch, getState }) => {
|
|
2477
|
-
const { permissionSetsWithScope, role } = transformRoleDataToRole(roleData, getRolesById(getState())[roleData.name]);
|
|
2478
|
-
return general_api_default.put(`${useradmApiUrlv2}/roles/${role.name}`, {
|
|
2479
|
-
description: role.description,
|
|
2480
|
-
name: role.name,
|
|
2481
|
-
permission_sets_with_scope: permissionSetsWithScope
|
|
2482
|
-
}).then(() => Promise.all([dispatch(actions6.createdRole(role)), dispatch(getRoles()), dispatch(setSnackbar4(roleActions.edit.successMessage))])).catch((err) => roleActionErrorHandler(err, "edit", dispatch, { permissionSetsCreated: permissionSetsWithScope.length, name: role.name }));
|
|
2483
|
-
});
|
|
2484
|
-
var removeRole = createAppAsyncThunk(
|
|
2485
|
-
`${sliceName6}/removeRole`,
|
|
2486
|
-
(roleId, { dispatch }) => general_api_default.delete(`${useradmApiUrlv2}/roles/${roleId}`).then(() => Promise.all([dispatch(actions6.removedRole(roleId)), dispatch(getRoles()), dispatch(setSnackbar4(roleActions.remove.successMessage))])).catch((err) => roleActionErrorHandler(err, "remove", dispatch))
|
|
2487
|
-
);
|
|
2488
|
-
var getGlobalSettings2 = createAppAsyncThunk(
|
|
2489
|
-
`${sliceName6}/getGlobalSettings`,
|
|
2490
|
-
(_, { dispatch }) => general_api_default.get(`${useradmApiUrl}/settings`).then(({ data: settings, headers: { etag } }) => {
|
|
2491
|
-
window.sessionStorage.setItem(settingsKeys.initialized, "true");
|
|
2492
|
-
return Promise.all([dispatch(actions6.setGlobalSettings(settings)), dispatch(setOfflineThreshold()), etag]);
|
|
2493
|
-
})
|
|
2494
|
-
);
|
|
2495
|
-
var saveGlobalSettings = createAppAsyncThunk(
|
|
2496
|
-
`${sliceName6}/saveGlobalSettings`,
|
|
2497
|
-
({ beOptimistic = false, notify = false, ...settings }, { dispatch, getState }) => {
|
|
2498
|
-
if (!window.sessionStorage.getItem(settingsKeys.initialized) && !beOptimistic) {
|
|
2499
|
-
return;
|
|
2500
|
-
}
|
|
2501
|
-
return dispatch(getGlobalSettings2()).unwrap().then((result) => {
|
|
2502
|
-
const updatedSettings = { ...getState().users.globalSettings, ...settings };
|
|
2503
|
-
if (getCurrentUser(getState()).verified) {
|
|
2504
|
-
updatedSettings["2fa"] = twoFAStates.enabled;
|
|
2505
|
-
} else {
|
|
2506
|
-
delete updatedSettings["2fa"];
|
|
2507
|
-
}
|
|
2508
|
-
const tasks = [dispatch(actions6.setGlobalSettings(updatedSettings))];
|
|
2509
|
-
const headers = result[result.length - 1] ? { "If-Match": result[result.length - 1] } : {};
|
|
2510
|
-
return general_api_default.post(`${useradmApiUrl}/settings`, updatedSettings, { headers }).then(() => {
|
|
2511
|
-
if (notify) {
|
|
2512
|
-
tasks.push(dispatch(setSnackbar4("Settings saved successfully")));
|
|
2513
|
-
}
|
|
2514
|
-
return Promise.all(tasks);
|
|
2515
|
-
}).catch((err) => {
|
|
2516
|
-
if (beOptimistic) {
|
|
2517
|
-
return Promise.all([tasks]);
|
|
2518
|
-
}
|
|
2519
|
-
console.log(err);
|
|
2520
|
-
return commonErrorHandler(err, `The settings couldn't be saved.`, dispatch);
|
|
2521
|
-
});
|
|
2522
|
-
});
|
|
2523
|
-
}
|
|
2524
|
-
);
|
|
2525
|
-
var getUserSettings2 = createAppAsyncThunk(
|
|
2526
|
-
`${sliceName6}/getUserSettings`,
|
|
2527
|
-
(_, { dispatch }) => general_api_default.get(`${useradmApiUrl}/settings/me`).then(({ data: settings, headers: { etag } }) => {
|
|
2528
|
-
window.sessionStorage.setItem(settingsKeys.initialized, "true");
|
|
2529
|
-
return Promise.all([dispatch(actions6.setUserSettings(settings)), etag]);
|
|
2530
|
-
})
|
|
2531
|
-
);
|
|
2532
|
-
var saveUserSettings = createAppAsyncThunk(
|
|
2533
|
-
`${sliceName6}/saveUserSettings`,
|
|
2534
|
-
(settings = { onboarding: {} }, { dispatch, getState }) => {
|
|
2535
|
-
if (!getCurrentUser(getState()).id) {
|
|
2536
|
-
return Promise.resolve();
|
|
2537
|
-
}
|
|
2538
|
-
return dispatch(getUserSettings2()).unwrap().then((result) => {
|
|
2539
|
-
const userSettings = getUserSettings(getState());
|
|
2540
|
-
const onboardingState = getOnboardingState(getState());
|
|
2541
|
-
const tooltipState = getTooltipsState(getState());
|
|
2542
|
-
const updatedSettings = {
|
|
2543
|
-
...userSettings,
|
|
2544
|
-
...settings,
|
|
2545
|
-
firstLoginTimestamp: userSettings.firstLoginTimestamp ?? dayjs2().format(),
|
|
2546
|
-
onboarding: {
|
|
2547
|
-
...onboardingState,
|
|
2548
|
-
...settings.onboarding
|
|
2549
|
-
},
|
|
2550
|
-
tooltips: tooltipState
|
|
2551
|
-
};
|
|
2552
|
-
const headers = result[result.length - 1] ? { "If-Match": result[result.length - 1] } : {};
|
|
2553
|
-
return Promise.all([
|
|
2554
|
-
Promise.resolve(dispatch(actions6.setUserSettings(updatedSettings))),
|
|
2555
|
-
general_api_default.post(`${useradmApiUrl}/settings/me`, updatedSettings, { headers })
|
|
2556
|
-
]).catch(() => dispatch(actions6.setUserSettings(userSettings)));
|
|
2557
|
-
});
|
|
2558
|
-
}
|
|
2559
|
-
);
|
|
2560
|
-
var get2FAQRCode = createAppAsyncThunk(
|
|
2561
|
-
`${sliceName6}/get2FAQRCode`,
|
|
2562
|
-
(_, { dispatch }) => general_api_default.get(`${useradmApiUrl}/2faqr`).then((res) => dispatch(actions6.receivedQrCode(res.data.qr)))
|
|
2563
|
-
);
|
|
2564
|
-
var setHideAnnouncement = createAppAsyncThunk(
|
|
2565
|
-
`${sliceName6}/setHideAnnouncement`,
|
|
2566
|
-
({ shouldHide, userId }, { dispatch, getState }) => {
|
|
2567
|
-
const currentUserId = userId || getCurrentUser(getState()).id;
|
|
2568
|
-
const announcement = getHostedAnnouncement(getState());
|
|
2569
|
-
const hash = announcement ? hashString2(announcement) : "";
|
|
2570
|
-
const announceCookie = cookies3.get(`${currentUserId}${hash}`);
|
|
2571
|
-
if (shouldHide || hash.length && typeof announceCookie !== "undefined") {
|
|
2572
|
-
cookies3.set(`${currentUserId}${hash}`, true, { maxAge: 604800 });
|
|
2573
|
-
dispatch(setAnnouncement2(""));
|
|
2574
|
-
}
|
|
2575
|
-
}
|
|
2576
|
-
);
|
|
2577
|
-
var getTokens = createAppAsyncThunk(
|
|
2578
|
-
`${sliceName6}/getTokens`,
|
|
2579
|
-
(_, { dispatch, getState }) => general_api_default.get(`${useradmApiUrl}/settings/tokens`).then(({ data: tokens }) => {
|
|
2580
|
-
const user = getCurrentUser(getState());
|
|
2581
|
-
const updatedUser = {
|
|
2582
|
-
...user,
|
|
2583
|
-
tokens
|
|
2584
|
-
};
|
|
2585
|
-
return Promise.resolve(dispatch(actions6.updatedUser(updatedUser)));
|
|
2586
|
-
})
|
|
2587
|
-
);
|
|
2588
|
-
var ONE_YEAR = 31536e3;
|
|
2589
|
-
var generateToken = createAppAsyncThunk(
|
|
2590
|
-
`${sliceName6}/generateToken`,
|
|
2591
|
-
({ expiresIn = ONE_YEAR, name }, { dispatch }) => general_api_default.post(`${useradmApiUrl}/settings/tokens`, { name, expires_in: expiresIn }).then(({ data: token }) => Promise.all([dispatch(getTokens()), token])).catch((err) => commonErrorHandler(err, "There was an error creating the token:", dispatch))
|
|
2592
|
-
);
|
|
2593
|
-
var revokeToken = createAppAsyncThunk(
|
|
2594
|
-
`${sliceName6}/revokeToken`,
|
|
2595
|
-
(token, { dispatch }) => general_api_default.delete(`${useradmApiUrl}/settings/tokens/${token.id}`).then(() => Promise.resolve(dispatch(getTokens())))
|
|
2596
|
-
);
|
|
2597
|
-
var setTooltipReadState = createAppAsyncThunk(
|
|
2598
|
-
`${sliceName6}/setTooltipReadState`,
|
|
2599
|
-
async ({ persist, ...remainder }, { dispatch }) => {
|
|
2600
|
-
dispatch(actions6.setTooltipState(remainder));
|
|
2601
|
-
if (persist) {
|
|
2602
|
-
await dispatch(saveUserSettings());
|
|
2603
|
-
}
|
|
2604
|
-
}
|
|
2605
|
-
);
|
|
2606
|
-
var setAllTooltipsReadState = createAppAsyncThunk(
|
|
2607
|
-
`${sliceName6}/toggleHelptips`,
|
|
2608
|
-
({ readState = READ_STATES.read, tooltipIds }, { dispatch }) => {
|
|
2609
|
-
const updatedTips = tooltipIds.reduce((accu, id) => ({ ...accu, [id]: { readState } }), {});
|
|
2610
|
-
return Promise.resolve(dispatch(actions6.setTooltipsState(updatedTips))).then(() => dispatch(saveUserSettings()));
|
|
2611
|
-
}
|
|
2612
|
-
);
|
|
2613
|
-
var submitUserFeedback = createAppAsyncThunk(
|
|
2614
|
-
`${sliceName6}/submitFeedback`,
|
|
2615
|
-
({ formId, feedback }, { dispatch }) => general_api_default.post(`${useradmApiUrlv2}/support/feedback/${formId}`, feedback).then(() => {
|
|
2616
|
-
if (formId === "product") {
|
|
2617
|
-
const today = /* @__PURE__ */ new Date();
|
|
2618
|
-
dispatch(saveUserSettings({ feedbackCollectedAt: today.toISOString().split("T")[0] }));
|
|
2619
|
-
setTimeout(() => dispatch(actions6.setShowFeedbackDialog(false)), TIMEOUTS.threeSeconds);
|
|
2620
|
-
}
|
|
2621
|
-
})
|
|
2622
|
-
);
|
|
2623
|
-
|
|
2624
|
-
// src/appSlice/thunks.ts
|
|
2625
|
-
var cookies4 = new Cookies4();
|
|
2626
|
-
var setFirstLoginAfterSignup = createAppAsyncThunk(`${sliceName}/setFirstLoginAfterSignup`, (firstLoginAfterSignup, { dispatch }) => {
|
|
2627
|
-
cookies4.set("firstLoginAfterSignup", !!firstLoginAfterSignup, { maxAge: 60, path: "/", domain: ".mender.io", sameSite: false });
|
|
2628
|
-
dispatch(actions.setFirstLoginAfterSignup(!!firstLoginAfterSignup));
|
|
2629
|
-
});
|
|
2630
|
-
var dateFunctionMap = {
|
|
2631
|
-
getDays: "getDate",
|
|
2632
|
-
setDays: "setDate"
|
|
2633
|
-
};
|
|
2634
|
-
var setOfflineThreshold = createAppAsyncThunk(`${sliceName}/setOfflineThreshold`, (_, { dispatch, getState }) => {
|
|
2635
|
-
const { interval, intervalUnit } = getOfflineThresholdSettings(getState());
|
|
2636
|
-
const today = /* @__PURE__ */ new Date();
|
|
2637
|
-
const intervalName = `${intervalUnit.charAt(0).toUpperCase()}${intervalUnit.substring(1)}`;
|
|
2638
|
-
const setter = dateFunctionMap[`set${intervalName}`] ?? `set${intervalName}`;
|
|
2639
|
-
const getter = dateFunctionMap[`get${intervalName}`] ?? `get${intervalName}`;
|
|
2640
|
-
today[setter](today[getter]() - interval);
|
|
2641
|
-
let value;
|
|
2642
|
-
try {
|
|
2643
|
-
value = today.toISOString();
|
|
2644
|
-
} catch {
|
|
2645
|
-
return Promise.resolve(dispatch(actions.setSnackbar("There was an error saving the offline threshold, please check your settings.")));
|
|
2646
|
-
}
|
|
2647
|
-
return Promise.resolve(dispatch(actions.setOfflineThreshold(value)));
|
|
2648
|
-
});
|
|
2649
|
-
var versionRegex = new RegExp(/\d+\.\d+/);
|
|
2650
|
-
var getLatestRelease = (thing) => {
|
|
2651
|
-
const latestKey = Object.keys(thing).filter((key) => versionRegex.test(key)).sort().reverse()[0];
|
|
2652
|
-
return thing[latestKey];
|
|
2653
|
-
};
|
|
2654
|
-
var repoKeyMap = {
|
|
2655
|
-
integration: "Integration",
|
|
2656
|
-
"mender-artifact": "Mender-Artifact"
|
|
2657
|
-
};
|
|
2658
|
-
var deductSaasState = (latestRelease, guiTags) => {
|
|
2659
|
-
const latestGuiTag = guiTags.length ? guiTags[0].name : "";
|
|
2660
|
-
return latestGuiTag ? latestGuiTag : latestRelease.release;
|
|
2661
|
-
};
|
|
2662
|
-
var getLatestReleaseInfo = createAppAsyncThunk(`${sliceName}/getLatestReleaseInfo`, (_, { dispatch, getState }) => {
|
|
2663
|
-
if (!getFeatures(getState()).isHosted) {
|
|
2664
|
-
return Promise.resolve();
|
|
2665
|
-
}
|
|
2666
|
-
return Promise.all([general_api_default.get("/versions.json"), general_api_default.get("/tags.json")]).catch((err) => {
|
|
2667
|
-
console.log("init error:", extractErrorMessage3(err));
|
|
2668
|
-
return Promise.resolve([{ data: {} }, { data: [] }]);
|
|
2669
|
-
}).then(([{ data }, { data: guiTags }]) => {
|
|
2670
|
-
if (!guiTags.length) {
|
|
2671
|
-
return Promise.resolve();
|
|
2672
|
-
}
|
|
2673
|
-
const { releases } = data;
|
|
2674
|
-
const latestRelease = getLatestRelease(getLatestRelease(releases));
|
|
2675
|
-
const { latestRepos, latestVersions } = latestRelease.repos.reduce(
|
|
2676
|
-
(accu, item) => {
|
|
2677
|
-
if (repoKeyMap[item.name]) {
|
|
2678
|
-
accu.latestVersions[repoKeyMap[item.name]] = getComparisonCompatibleVersion(item.version);
|
|
2679
|
-
}
|
|
2680
|
-
accu.latestRepos[item.name] = getComparisonCompatibleVersion(item.version);
|
|
2681
|
-
return accu;
|
|
2682
|
-
},
|
|
2683
|
-
{ latestVersions: { ...getState().app.versionInformation }, latestRepos: {} }
|
|
2684
|
-
);
|
|
2685
|
-
const info = deductSaasState(latestRelease, guiTags);
|
|
2686
|
-
return Promise.resolve(
|
|
2687
|
-
dispatch(
|
|
2688
|
-
actions.setVersionInformation({
|
|
2689
|
-
...latestVersions,
|
|
2690
|
-
Server: info,
|
|
2691
|
-
latestRelease: {
|
|
2692
|
-
releaseDate: latestRelease.release_date,
|
|
2693
|
-
repos: latestRepos
|
|
2694
|
-
}
|
|
2695
|
-
})
|
|
2696
|
-
)
|
|
2697
|
-
);
|
|
2698
|
-
});
|
|
2699
|
-
});
|
|
2700
|
-
var setSearchState = createAppAsyncThunk(`${sliceName}/setSearchState`, (searchState, { dispatch, getState }) => {
|
|
2701
|
-
const currentState = getSearchState(getState());
|
|
2702
|
-
const nextState = {
|
|
2703
|
-
...currentState,
|
|
2704
|
-
...searchState,
|
|
2705
|
-
sort: {
|
|
2706
|
-
...currentState.sort,
|
|
2707
|
-
...searchState.sort
|
|
2708
|
-
}
|
|
2709
|
-
};
|
|
2710
|
-
const tasks = [];
|
|
2711
|
-
const { isSearching: currentSearching, deviceIds: currentDevices, searchTotal: currentTotal, ...currentRequestState } = currentState;
|
|
2712
|
-
const { isSearching: nextSearching, deviceIds: nextDevices, searchTotal: nextTotal, ...nextRequestState } = nextState;
|
|
2713
|
-
if (nextRequestState.searchTerm && !deepCompare4(currentRequestState, nextRequestState)) {
|
|
2714
|
-
nextState.isSearching = true;
|
|
2715
|
-
tasks.push(
|
|
2716
|
-
dispatch(searchDevices(nextState)).unwrap().then((results) => {
|
|
2717
|
-
const searchResult = results[results.length - 1];
|
|
2718
|
-
return dispatch(actions.setSearchState({ ...searchResult, isSearching: false }));
|
|
2719
|
-
}).catch(() => dispatch(actions.setSearchState({ isSearching: false, searchTotal: 0 })))
|
|
2720
|
-
);
|
|
2721
|
-
}
|
|
2722
|
-
tasks.push(dispatch(actions.setSearchState(nextState)));
|
|
2723
|
-
return Promise.all(tasks);
|
|
2724
|
-
});
|
|
2725
|
-
|
|
2726
|
-
export {
|
|
2727
|
-
setFirstLoginAfterSignup,
|
|
2728
|
-
setOfflineThreshold,
|
|
2729
|
-
getLatestReleaseInfo,
|
|
2730
|
-
setSearchState,
|
|
2731
|
-
deriveDeploymentGroup,
|
|
2732
|
-
getDeploymentsByStatus2 as getDeploymentsByStatus,
|
|
2733
|
-
createDeployment,
|
|
2734
|
-
getDeploymentDevices,
|
|
2735
|
-
getDeviceDeployments,
|
|
2736
|
-
resetDeviceDeployments,
|
|
2737
|
-
getSingleDeployment,
|
|
2738
|
-
getDeviceLog,
|
|
2739
|
-
abortDeployment,
|
|
2740
|
-
updateDeploymentControlMap,
|
|
2741
|
-
setDeploymentsState,
|
|
2742
|
-
getDeploymentsConfig,
|
|
2743
|
-
saveDeltaDeploymentsConfig,
|
|
2744
|
-
generateDeploymentLogAnalysis,
|
|
2745
|
-
getGroups,
|
|
2746
|
-
addDevicesToGroup,
|
|
2747
|
-
removeDevicesFromGroup,
|
|
2748
|
-
addStaticGroup,
|
|
2749
|
-
removeReportsByGroupName,
|
|
2750
|
-
removeStaticGroup,
|
|
2751
|
-
getDynamicGroup,
|
|
2752
|
-
getDynamicGroups,
|
|
2753
|
-
addDynamicGroup,
|
|
2754
|
-
updateDynamicGroup,
|
|
2755
|
-
removeDynamicGroup,
|
|
2756
|
-
selectGroup,
|
|
2757
|
-
getGroupDevices,
|
|
2758
|
-
getAllGroupDevices,
|
|
2759
|
-
getAllDynamicGroupDevices,
|
|
2760
|
-
getDeviceById2 as getDeviceById,
|
|
2761
|
-
getDeviceInfo,
|
|
2762
|
-
getAllDeviceCounts,
|
|
2763
|
-
getDeviceLimits,
|
|
2764
|
-
setDeviceListState,
|
|
2765
|
-
getDevicesByStatus,
|
|
2766
|
-
getAllDevicesByStatus,
|
|
2767
|
-
searchDevices,
|
|
2768
|
-
getDeviceAttributes,
|
|
2769
|
-
updateReportData,
|
|
2770
|
-
getReportDataWithoutBackendSupport,
|
|
2771
|
-
getDeviceConnect,
|
|
2772
|
-
triggerDeviceUpdate,
|
|
2773
|
-
getSessionDetails,
|
|
2774
|
-
getDeviceFileDownloadLink,
|
|
2775
|
-
deviceFileUpload,
|
|
2776
|
-
getDeviceAuth,
|
|
2777
|
-
getDevicesWithAuth,
|
|
2778
|
-
updateDeviceAuth,
|
|
2779
|
-
updateDevicesAuth,
|
|
2780
|
-
deleteAuthset,
|
|
2781
|
-
preauthDevice,
|
|
2782
|
-
decommissionDevice,
|
|
2783
|
-
getDeviceConfig,
|
|
2784
|
-
setDeviceConfig,
|
|
2785
|
-
applyDeviceConfig,
|
|
2786
|
-
setDeviceTags,
|
|
2787
|
-
getDeviceTwin,
|
|
2788
|
-
setDeviceTwin,
|
|
2789
|
-
getSystemDevices,
|
|
2790
|
-
getGatewayDevices,
|
|
2791
|
-
getOnboardingState2 as getOnboardingState,
|
|
2792
|
-
setOnboardingDeviceType,
|
|
2793
|
-
setOnboardingApproach,
|
|
2794
|
-
setOnboardingComplete,
|
|
2795
|
-
setOnboardingCanceled,
|
|
2796
|
-
advanceOnboarding,
|
|
2797
|
-
cancelRequest,
|
|
2798
|
-
transformProductResponse,
|
|
2799
|
-
getTargetLocation,
|
|
2800
|
-
createOrganizationTrial,
|
|
2801
|
-
startCardUpdate,
|
|
2802
|
-
confirmCardUpdate,
|
|
2803
|
-
getCurrentCard,
|
|
2804
|
-
startUpgrade,
|
|
2805
|
-
cancelUpgrade,
|
|
2806
|
-
completeUpgrade,
|
|
2807
|
-
getAuditLogs,
|
|
2808
|
-
getAuditLogsCsvLink,
|
|
2809
|
-
setAuditlogsState,
|
|
2810
|
-
tenantDataDivergedMessage,
|
|
2811
|
-
addTenant,
|
|
2812
|
-
getTenants,
|
|
2813
|
-
setTenantsListState,
|
|
2814
|
-
editTenant,
|
|
2815
|
-
editBillingProfile,
|
|
2816
|
-
createBillingProfile,
|
|
2817
|
-
removeTenant,
|
|
2818
|
-
getUserOrganization,
|
|
2819
|
-
getUserBilling,
|
|
2820
|
-
getUserSubscription,
|
|
2821
|
-
getBillingPreview,
|
|
2822
|
-
getCurrentSubscription,
|
|
2823
|
-
getProducts,
|
|
2824
|
-
requestPlanUpgrade,
|
|
2825
|
-
sendSupportMessage,
|
|
2826
|
-
requestPlanChange,
|
|
2827
|
-
downloadLicenseReport,
|
|
2828
|
-
createIntegration,
|
|
2829
|
-
changeIntegration,
|
|
2830
|
-
deleteIntegration,
|
|
2831
|
-
getIntegrations,
|
|
2832
|
-
getWebhookEvents,
|
|
2833
|
-
storeSsoConfig,
|
|
2834
|
-
changeSsoConfig,
|
|
2835
|
-
deleteSsoConfig,
|
|
2836
|
-
getSsoConfigById,
|
|
2837
|
-
getSsoConfigs,
|
|
2838
|
-
loginUser,
|
|
2839
|
-
logoutUser,
|
|
2840
|
-
switchUserOrganization,
|
|
2841
|
-
passwordResetStart,
|
|
2842
|
-
passwordResetComplete,
|
|
2843
|
-
verifyEmailStart,
|
|
2844
|
-
verifyEmailComplete,
|
|
2845
|
-
verify2FA,
|
|
2846
|
-
getUserList,
|
|
2847
|
-
getUser,
|
|
2848
|
-
initializeSelf,
|
|
2849
|
-
updateUserColumnSettings,
|
|
2850
|
-
createUser,
|
|
2851
|
-
removeUser,
|
|
2852
|
-
editUser,
|
|
2853
|
-
checkEmailExists,
|
|
2854
|
-
addUserToCurrentTenant,
|
|
2855
|
-
enableUser2fa,
|
|
2856
|
-
disableUser2fa,
|
|
2857
|
-
normalizeRbacRoles,
|
|
2858
|
-
getPermissionSets,
|
|
2859
|
-
getRoles,
|
|
2860
|
-
createRole,
|
|
2861
|
-
editRole,
|
|
2862
|
-
removeRole,
|
|
2863
|
-
getGlobalSettings2 as getGlobalSettings,
|
|
2864
|
-
saveGlobalSettings,
|
|
2865
|
-
getUserSettings2 as getUserSettings,
|
|
2866
|
-
saveUserSettings,
|
|
2867
|
-
get2FAQRCode,
|
|
2868
|
-
setHideAnnouncement,
|
|
2869
|
-
getTokens,
|
|
2870
|
-
generateToken,
|
|
2871
|
-
revokeToken,
|
|
2872
|
-
setTooltipReadState,
|
|
2873
|
-
setAllTooltipsReadState,
|
|
2874
|
-
submitUserFeedback
|
|
2875
|
-
};
|
|
2876
|
-
//# sourceMappingURL=chunk-FCY7BUGK.js.map
|