w-web-perm 1.0.48 → 1.0.49

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (95) hide show
  1. package/.github/workflows/ci-test.yml +2 -2
  2. package/_gh-pages-deploy/.nojekyll +0 -0
  3. package/_gh-pages-deploy/WWebPerm.html +938 -0
  4. package/_gh-pages-deploy/WWebPerm.mjs.html +1228 -0
  5. package/_gh-pages-deploy/fonts/Montserrat/Montserrat-Bold.eot +0 -0
  6. package/_gh-pages-deploy/fonts/Montserrat/Montserrat-Bold.ttf +0 -0
  7. package/_gh-pages-deploy/fonts/Montserrat/Montserrat-Bold.woff +0 -0
  8. package/_gh-pages-deploy/fonts/Montserrat/Montserrat-Bold.woff2 +0 -0
  9. package/_gh-pages-deploy/fonts/Montserrat/Montserrat-Regular.eot +0 -0
  10. package/_gh-pages-deploy/fonts/Montserrat/Montserrat-Regular.ttf +0 -0
  11. package/_gh-pages-deploy/fonts/Montserrat/Montserrat-Regular.woff +0 -0
  12. package/_gh-pages-deploy/fonts/Montserrat/Montserrat-Regular.woff2 +0 -0
  13. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-light-webfont.eot +0 -0
  14. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-light-webfont.svg +978 -0
  15. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-light-webfont.ttf +0 -0
  16. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-light-webfont.woff +0 -0
  17. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-light-webfont.woff2 +0 -0
  18. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-regular-webfont.eot +0 -0
  19. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-regular-webfont.svg +1049 -0
  20. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-regular-webfont.ttf +0 -0
  21. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-regular-webfont.woff +0 -0
  22. package/_gh-pages-deploy/fonts/Source-Sans-Pro/sourcesanspro-regular-webfont.woff2 +0 -0
  23. package/_gh-pages-deploy/index.html +84 -0
  24. package/_gh-pages-deploy/scripts/collapse.js +39 -0
  25. package/_gh-pages-deploy/scripts/commonNav.js +28 -0
  26. package/_gh-pages-deploy/scripts/linenumber.js +25 -0
  27. package/_gh-pages-deploy/scripts/nav.js +12 -0
  28. package/_gh-pages-deploy/scripts/polyfill.js +4 -0
  29. package/_gh-pages-deploy/scripts/prettify/Apache-License-2.0.txt +202 -0
  30. package/_gh-pages-deploy/scripts/prettify/lang-css.js +2 -0
  31. package/_gh-pages-deploy/scripts/prettify/prettify.js +28 -0
  32. package/_gh-pages-deploy/scripts/search.js +99 -0
  33. package/_gh-pages-deploy/styles/jsdoc.css +776 -0
  34. package/_gh-pages-deploy/styles/prettify.css +80 -0
  35. package/dist/css/app.d8b16216.css +1 -0
  36. package/dist/css/{chunk-vendors.f149e124.css → chunk-vendors.2d3ef2ba.css} +1 -1
  37. package/dist/index.tmp +2 -2
  38. package/dist/js/app-legacy.fb48310a.js +1 -0
  39. package/dist/js/app.fb48310a.js +1 -0
  40. package/dist/js/chunk-vendors-legacy.8fdd4435.js +21 -0
  41. package/dist/js/chunk-vendors.8fdd4435.js +21 -0
  42. package/dist/w-web-perm.umd.js +2 -2
  43. package/dist/w-web-perm.umd.js.map +1 -1
  44. package/docs/WWebPerm.html +2 -2
  45. package/docs/WWebPerm.mjs.html +138 -199
  46. package/docs/index.html +1 -1
  47. package/package.json +15 -11
  48. package/public/index.html +2 -2
  49. package/server/WWebPerm.mjs +137 -198
  50. package/server/procCore.mjs +169 -0
  51. package/server/procLang.mjs +197 -0
  52. package/server/procStaInfor.mjs +118 -0
  53. package/server/provideTabs.mjs +1 -1
  54. package/server/srLog.mjs +30 -0
  55. package/server/staLogs/staEvent.callWorker.mjs +46 -0
  56. package/server/staLogs/staEvent.mjs +116 -0
  57. package/server/staLogs/staEvent.shellWorker.mjs +19 -0
  58. package/server/staLogs/staEventTable.mjs +100 -0
  59. package/server/staLogs/test_staEvent.mjs +22 -0
  60. package/settings.json +40 -0
  61. package/src/components/Common/CheckYes.vue +18 -1
  62. package/src/components/Layout.vue +1 -1
  63. package/src/components/LayoutContent.vue +13 -1
  64. package/src/components/LayoutContentGrups.vue +32 -23
  65. package/src/components/LayoutContentPemis.vue +32 -23
  66. package/src/components/LayoutContentStaInfor.vue +536 -0
  67. package/src/components/LayoutContentTargets.vue +32 -23
  68. package/src/components/LayoutContentUsers.vue +32 -23
  69. package/src/components/LayoutState.vue +5 -0
  70. package/src/components/VeCgrups.vue +12 -3
  71. package/src/components/VeCpemis.vue +12 -3
  72. package/src/components/VeCrules.vue +12 -3
  73. package/src/components/VeGrupBlngUsers.vue +18 -6
  74. package/src/components/VePemiBlngGrups.vue +18 -6
  75. package/src/getPerm.mjs +7 -17
  76. package/src/getPermUserInfor.mjs +8 -18
  77. package/src/main.js +1 -0
  78. package/src/plugins/mShare.mjs +8 -13
  79. package/src/plugins/mUI.mjs +11 -0
  80. package/srv.mjs +76 -101
  81. package/tableTags.json +1 -1
  82. package/db/wperm/grups/data.mdb +0 -0
  83. package/db/wperm/grups/lock.mdb +0 -0
  84. package/db/wperm/pemis/data.mdb +0 -0
  85. package/db/wperm/pemis/lock.mdb +0 -0
  86. package/db/wperm/targets/data.mdb +0 -0
  87. package/db/wperm/targets/lock.mdb +0 -0
  88. package/db/wperm/users/data.mdb +0 -0
  89. package/db/wperm/users/lock.mdb +0 -0
  90. package/dist/css/app.30e81bfe.css +0 -1
  91. package/dist/js/app-legacy.3324392e.js +0 -1
  92. package/dist/js/app.3324392e.js +0 -1
  93. package/dist/js/chunk-vendors-legacy.e8703728.js +0 -21
  94. package/dist/js/chunk-vendors.e8703728.js +0 -21
  95. package/test/getUserRules.test.mjs +0 -899
@@ -39,6 +39,7 @@
39
39
 
40
40
  <!-- 功能區 -->
41
41
  <div
42
+ data-fmid="users-toolbar"
42
43
  style="padding:5px; border-top:1px solid #ddd; display:flex; align-items:center;"
43
44
  _v-if="showIsEditable || isEditable"
44
45
  >
@@ -185,6 +186,7 @@
185
186
  :iconColor="'#eee'"
186
187
  :iconColorHover="'#fff'"
187
188
  :shadow="false"
189
+ :promiseUnlock="true"
188
190
  @click="saveUsers"
189
191
  ></WButtonCircle>
190
192
 
@@ -1148,20 +1150,28 @@ export default {
1148
1150
 
1149
1151
  },
1150
1152
 
1151
- saveUsers: function() {
1152
- // console.log('method saveUsers')
1153
+ saveUsers: function(msg) {
1153
1154
 
1154
1155
  let vo = this
1155
1156
 
1156
- async function core() {
1157
- let errTemp = null
1157
+ //第一行立刻釋放按鈕視覺鎖
1158
+ msg.pm.resolve()
1158
1159
 
1159
- //show loading
1160
- vo.$ui.updateLoading(true)
1160
+ //fire-and-forget, 不 await
1161
+ vo.doSaveUsers()
1161
1162
 
1162
- //check
1163
+ },
1164
+
1165
+ doSaveUsers: function() {
1166
+ // console.log('method doSaveUsers')
1167
+
1168
+ let vo = this
1169
+
1170
+ async function core() {
1171
+
1172
+ //1) 同步檢測 (在開 loading 之前)
1163
1173
  if (isestr(vo.isError)) {
1164
- vo.$alert(`${vo.isError}`, { type: 'error' })
1174
+ await vo.$dg.showCheckYes(`${vo.isError}`)
1165
1175
  return
1166
1176
  }
1167
1177
 
@@ -1170,35 +1180,34 @@ export default {
1170
1180
 
1171
1181
  //check
1172
1182
  if (size(rows) === 0) {
1173
- vo.$alert(`${vo.$t('userAddEmpty')}`, { type: 'error' })
1183
+ await vo.$dg.showCheckYes(`${vo.$t('userAddEmpty')}`)
1174
1184
  return
1175
1185
  }
1176
1186
 
1177
- //updateUsers
1187
+ //2) 確定打 API 才開 loading
1188
+ vo.$ui.updateLoading(true)
1189
+
1190
+ //3) updateUsers, 各自 catch + 旗標短路
1191
+ let okSave = false
1178
1192
  await vo.$fapi.updateUsers(rows)
1179
- .catch((err) => {
1180
- errTemp = err
1193
+ .then(() => { okSave = true })
1194
+ .catch(async (err) => {
1195
+ vo.$ui.updateLoading(false) //showCheckYes 前關 loading(modal 阻斷期間避免 loading 疊在底下)
1196
+ await vo.$dg.showCheckYes(`${vo.$t('userSaveUsersFail')}: ${vo.$tErr(err)}`)
1181
1197
  })
1182
-
1183
- //check
1184
- if (errTemp !== null) {
1185
- vo.$alert(`${vo.$t('userSaveUsersFail')}: ${errTemp}`, { type: 'error' })
1186
- return
1187
- }
1198
+ if (!okSave) return
1188
1199
 
1189
1200
  //isModified
1190
1201
  vo.isModified = false
1191
1202
 
1192
- //alert
1193
- vo.$alert(vo.$t('userSaveUsersSuccess'))
1203
+ //alert(showCheckYes 前關 loading,避免 modal 等待期間 loading 疊在底下)
1204
+ vo.$ui.updateLoading(false)
1205
+ await vo.$dg.showCheckYes(vo.$t('userSaveUsersSuccess'), { type: 'success' })
1194
1206
 
1195
1207
  }
1196
1208
 
1197
1209
  //core
1198
1210
  core()
1199
- // .then((res) => {
1200
- // console.log('then', res)
1201
- // })
1202
1211
  .catch((err) => {
1203
1212
  console.log('catch', err)
1204
1213
  vo.$alert(vo.$t('anUnexpectedErrorOccurred'), { type: 'error' })
@@ -3,6 +3,9 @@
3
3
  :style="`position:absolute; top:0px; left:0px; width:100%; height:100%; transition:all 0.5s linear; display:flex; align-items:center; justify-content:center;`"
4
4
  >
5
5
 
6
+ <!-- conn-state 觀看區包覆層(e2e 紅框標注用;display:flex 與原置中內容布局一致,不改視覺) -->
7
+ <div data-fmid="conn-state" style="display:flex; align-items:center;">
8
+
6
9
  <template v-if="connState==='csIng'">
7
10
 
8
11
  <img style="width:100px; height:100px;" :src="img_connection">
@@ -63,6 +66,8 @@
63
66
 
64
67
  </template>
65
68
 
69
+ </div>
70
+
66
71
  </div>
67
72
  </template>
68
73
 
@@ -747,6 +747,18 @@ export default {
747
747
 
748
748
  let vo = this
749
749
 
750
+ //save按鈕第一行立刻釋放視覺鎖
751
+ msg.pm.resolve()
752
+
753
+ //fire-and-forget, 不 await
754
+ vo.doSave()
755
+
756
+ },
757
+
758
+ doSave: function() {
759
+
760
+ let vo = this
761
+
750
762
  async function core() {
751
763
 
752
764
  //show loading
@@ -805,9 +817,6 @@ export default {
805
817
  .catch(() => { })
806
818
  .finally(() => {
807
819
 
808
- //save按鈕解除loading
809
- msg.pm.resolve()
810
-
811
820
  //hide loading
812
821
  vo.$ui.updateLoading(false)
813
822
 
@@ -747,6 +747,18 @@ export default {
747
747
 
748
748
  let vo = this
749
749
 
750
+ //save按鈕第一行立刻釋放視覺鎖
751
+ msg.pm.resolve()
752
+
753
+ //fire-and-forget, 不 await
754
+ vo.doSave()
755
+
756
+ },
757
+
758
+ doSave: function() {
759
+
760
+ let vo = this
761
+
750
762
  async function core() {
751
763
 
752
764
  //show loading
@@ -805,9 +817,6 @@ export default {
805
817
  .catch(() => { })
806
818
  .finally(() => {
807
819
 
808
- //save按鈕解除loading
809
- msg.pm.resolve()
810
-
811
820
  //hide loading
812
821
  vo.$ui.updateLoading(false)
813
822
 
@@ -690,6 +690,18 @@ export default {
690
690
 
691
691
  let vo = this
692
692
 
693
+ //save按鈕第一行立刻釋放視覺鎖
694
+ msg.pm.resolve()
695
+
696
+ //fire-and-forget, 不 await
697
+ vo.doSave()
698
+
699
+ },
700
+
701
+ doSave: function() {
702
+
703
+ let vo = this
704
+
693
705
  async function core() {
694
706
 
695
707
  //show loading
@@ -740,9 +752,6 @@ export default {
740
752
  .catch(() => { })
741
753
  .finally(() => {
742
754
 
743
- //save按鈕解除loading
744
- msg.pm.resolve()
745
-
746
755
  //hide loading
747
756
  vo.$ui.updateLoading(false)
748
757
 
@@ -965,7 +965,8 @@ export default {
965
965
 
966
966
  //check
967
967
  if (size(rows) === 0) {
968
- vo.$alert(`${vo.$t('userSaveUsersEmpty')}`, { type: 'error' })
968
+ vo.$ui.updateLoading(false) //showCheckYes 前關 loading(modal 阻斷、避免 clickSave 包裝層 loading 疊在 modal 後)
969
+ await vo.$dg.showCheckYes(`${vo.$t('userSaveUsersEmpty')}`)
969
970
  return
970
971
  }
971
972
 
@@ -977,12 +978,14 @@ export default {
977
978
 
978
979
  //check
979
980
  if (errTemp !== null) {
980
- vo.$alert(`${vo.$t('userSaveUsersFail')}: ${errTemp}`, { type: 'error' })
981
+ vo.$ui.updateLoading(false)
982
+ await vo.$dg.showCheckYes(`${vo.$t('userSaveUsersFail')}: ${vo.$tErr(errTemp)}`)
981
983
  return
982
984
  }
983
985
 
984
986
  //alert
985
- vo.$alert(vo.$t('userSaveUsersSuccess'))
987
+ vo.$ui.updateLoading(false)
988
+ await vo.$dg.showCheckYes(vo.$t('userSaveUsersSuccess'), { type: 'success' })
986
989
 
987
990
  },
988
991
 
@@ -1006,6 +1009,18 @@ export default {
1006
1009
 
1007
1010
  let vo = this
1008
1011
 
1012
+ //save按鈕第一行立刻釋放視覺鎖
1013
+ msg.pm.resolve()
1014
+
1015
+ //fire-and-forget, 不 await
1016
+ vo.doSave()
1017
+
1018
+ },
1019
+
1020
+ doSave: function() {
1021
+
1022
+ let vo = this
1023
+
1009
1024
  async function core() {
1010
1025
 
1011
1026
  //show loading
@@ -1087,9 +1102,6 @@ export default {
1087
1102
  .catch(() => { })
1088
1103
  .finally(() => {
1089
1104
 
1090
- //save按鈕解除loading
1091
- msg.pm.resolve()
1092
-
1093
1105
  //hide loading
1094
1106
  vo.$ui.updateLoading(false)
1095
1107
 
@@ -965,7 +965,8 @@ export default {
965
965
 
966
966
  //check
967
967
  if (size(rows) === 0) {
968
- vo.$alert(`${vo.$t('grupSaveGrupsEmpty')}`, { type: 'error' })
968
+ vo.$ui.updateLoading(false) //showCheckYes 前關 loading(modal 阻斷、避免 clickSave 包裝層 loading 疊在 modal 後)
969
+ await vo.$dg.showCheckYes(`${vo.$t('grupSaveGrupsEmpty')}`)
969
970
  return
970
971
  }
971
972
 
@@ -977,12 +978,14 @@ export default {
977
978
 
978
979
  //check
979
980
  if (errTemp !== null) {
980
- vo.$alert(`${vo.$t('grupSaveGrupsFail')}: ${errTemp}`, { type: 'error' })
981
+ vo.$ui.updateLoading(false)
982
+ await vo.$dg.showCheckYes(`${vo.$t('grupSaveGrupsFail')}: ${vo.$tErr(errTemp)}`)
981
983
  return
982
984
  }
983
985
 
984
986
  //alert
985
- vo.$alert(vo.$t('grupSaveGrupsSuccess'))
987
+ vo.$ui.updateLoading(false)
988
+ await vo.$dg.showCheckYes(vo.$t('grupSaveGrupsSuccess'), { type: 'success' })
986
989
 
987
990
  },
988
991
 
@@ -1006,6 +1009,18 @@ export default {
1006
1009
 
1007
1010
  let vo = this
1008
1011
 
1012
+ //save按鈕第一行立刻釋放視覺鎖
1013
+ msg.pm.resolve()
1014
+
1015
+ //fire-and-forget, 不 await
1016
+ vo.doSave()
1017
+
1018
+ },
1019
+
1020
+ doSave: function() {
1021
+
1022
+ let vo = this
1023
+
1009
1024
  async function core() {
1010
1025
 
1011
1026
  //show loading
@@ -1087,9 +1102,6 @@ export default {
1087
1102
  .catch(() => { })
1088
1103
  .finally(() => {
1089
1104
 
1090
- //save按鈕解除loading
1091
- msg.pm.resolve()
1092
-
1093
1105
  //hide loading
1094
1106
  vo.$ui.updateLoading(false)
1095
1107
 
package/src/getPerm.mjs CHANGED
@@ -12,10 +12,10 @@ async function getPerm(url, tokenTar, opt = {}) {
12
12
 
13
13
  //check
14
14
  if (!isestr(url)) {
15
- return Promise.reject('invalid url')
15
+ return Promise.reject('invalidUrl')
16
16
  }
17
17
  if (!isestr(tokenTar)) {
18
- return Promise.reject('invalid tokenTar')
18
+ return Promise.reject('invalidTokenTar')
19
19
  }
20
20
 
21
21
  //funConvertPerm
@@ -23,7 +23,7 @@ async function getPerm(url, tokenTar, opt = {}) {
23
23
 
24
24
  //url
25
25
  if (url.indexOf('token={token}') < 0) {
26
- return Promise.reject(`no 'token={token}' in url`)
26
+ return Promise.reject('noTokenInUrl')
27
27
  }
28
28
  url = url.replaceAll('{token}', tokenTar)
29
29
  // console.log('getPerm: url', url)
@@ -36,10 +36,7 @@ async function getPerm(url, tokenTar, opt = {}) {
36
36
 
37
37
  //check
38
38
  if (errTemp !== null) {
39
- console.log('res', res)
40
- console.log('errTemp', errTemp)
41
- console.log(`can not get user by url[${url}]`)
42
- return Promise.reject(`can not get user by url[${url}]`) //由SSO取得使用者資訊錯誤
39
+ return Promise.reject('cannotGetUserByUrl') //由SSO取得使用者資訊錯誤
43
40
  }
44
41
 
45
42
  //data
@@ -53,12 +50,7 @@ async function getPerm(url, tokenTar, opt = {}) {
53
50
 
54
51
  //check
55
52
  if (state !== 'success') {
56
- console.log('res', res)
57
- console.log('data', data)
58
- console.log('state', state)
59
- console.log('errTemp', msg)
60
- console.log(`can not get user data by url[${url}]`)
61
- return Promise.reject(`can not get user data by url[${url}]`) //取得使用者資訊失敗
53
+ return Promise.reject('cannotGetUserDataByUrl') //取得使用者資訊失敗
62
54
  }
63
55
 
64
56
  //ur
@@ -67,8 +59,7 @@ async function getPerm(url, tokenTar, opt = {}) {
67
59
 
68
60
  //check
69
61
  if (!iseobj(ur)) {
70
- console.log(`no user data by url[${url}]`)
71
- return Promise.reject(`no user data by url[${url}]`)
62
+ return Promise.reject('noUserDataByUrl')
72
63
  }
73
64
 
74
65
  //check
@@ -83,8 +74,7 @@ async function getPerm(url, tokenTar, opt = {}) {
83
74
 
84
75
  //check
85
76
  if (!iseobj(ur)) {
86
- console.log(`no user data after funConvertPerm`)
87
- return Promise.reject(`no user data after funConvertPerm`)
77
+ return Promise.reject('noUserDataAfterConvert')
88
78
  }
89
79
 
90
80
  }
@@ -12,13 +12,13 @@ async function getPermUserInfor(url, tokenSelf, userIdTar, opt = {}) {
12
12
 
13
13
  //check
14
14
  if (!isestr(url)) {
15
- return Promise.reject('invalid url')
15
+ return Promise.reject('invalidUrl')
16
16
  }
17
17
  if (!isestr(tokenSelf)) {
18
- return Promise.reject('invalid tokenSelf')
18
+ return Promise.reject('invalidTokenSelf')
19
19
  }
20
20
  if (!isestr(userIdTar)) {
21
- return Promise.reject('invalid userIdTar')
21
+ return Promise.reject('invalidUserIdTar')
22
22
  }
23
23
 
24
24
  //funConvertPerm
@@ -26,7 +26,7 @@ async function getPermUserInfor(url, tokenSelf, userIdTar, opt = {}) {
26
26
 
27
27
  //url
28
28
  if (url.indexOf('token={sysToken}') < 0 && url.indexOf('userId={userId}') < 0) {
29
- return Promise.reject(`no 'token={sysToken}', 'userId={userId}' in url`)
29
+ return Promise.reject('noTokenUserIdInUrl')
30
30
  }
31
31
  url = url.replaceAll('{sysToken}', tokenSelf) //系統介接用permToken
32
32
  url = url.replaceAll('{userId}', userIdTar)
@@ -40,10 +40,7 @@ async function getPermUserInfor(url, tokenSelf, userIdTar, opt = {}) {
40
40
 
41
41
  //check
42
42
  if (errTemp !== null) {
43
- console.log('res', res)
44
- console.log('errTemp', errTemp)
45
- console.log(`can not get user by url[${url}]`)
46
- return Promise.reject(`can not get user by url[${url}]`) //由SSO取得使用者資訊錯誤
43
+ return Promise.reject('cannotGetUserByUrl') //由SSO取得使用者資訊錯誤
47
44
  }
48
45
 
49
46
  //data
@@ -57,12 +54,7 @@ async function getPermUserInfor(url, tokenSelf, userIdTar, opt = {}) {
57
54
 
58
55
  //check
59
56
  if (state !== 'success') {
60
- console.log('res', res)
61
- console.log('data', data)
62
- console.log('state', state)
63
- console.log('errTemp', msg)
64
- console.log(`can not get user data by url[${url}]`)
65
- return Promise.reject(`can not get user data by url[${url}]`) //取得使用者資訊失敗
57
+ return Promise.reject('cannotGetUserDataByUrl') //取得使用者資訊失敗
66
58
  }
67
59
 
68
60
  //ur
@@ -71,8 +63,7 @@ async function getPermUserInfor(url, tokenSelf, userIdTar, opt = {}) {
71
63
 
72
64
  //check
73
65
  if (!iseobj(ur)) {
74
- console.log(`no user data by url[${url}]`)
75
- return Promise.reject(`no user data by url[${url}]`)
66
+ return Promise.reject('noUserDataByUrl')
76
67
  }
77
68
 
78
69
  //check
@@ -87,8 +78,7 @@ async function getPermUserInfor(url, tokenSelf, userIdTar, opt = {}) {
87
78
 
88
79
  //check
89
80
  if (!iseobj(ur)) {
90
- console.log(`no user data after funConvertPerm`)
91
- return Promise.reject(`no user data after funConvertPerm`)
81
+ return Promise.reject('noUserDataAfterConvert')
92
82
  }
93
83
 
94
84
  }
package/src/main.js CHANGED
@@ -32,6 +32,7 @@ let dssm = mDataSelectorSchema(ds)
32
32
  //prototype
33
33
  Vue.prototype.$ui = ui
34
34
  Vue.prototype.$t = ui.getKpText
35
+ Vue.prototype.$tErr = ui.tErr
35
36
  Vue.prototype.$s = s
36
37
  Vue.prototype.$dssm = dssm
37
38
  Vue.prototype.$ds = ds
@@ -479,25 +479,20 @@ function getUserRules(user, grups, pemis, targets) {
479
479
  }
480
480
  // console.log('merge _rules', cloneDeep(_rules))
481
481
 
482
- //expand _rules
482
+ //expand _rules:以「當前 targets」為輸出主軸——逐 target 取其解析後 isActive(取自合併 crules 的 kp、預設 'n')。
483
+ //如此只列現存管控對象;crules 仍引用但已從 targets 刪除的「孤兒 target」自然被濾掉,不再殘留於權限樹。
484
+ //(修正前:輸出 kp 全部 keys = crules keys ∪ targets,導致已刪 target 因 crules 殘留引用而仍出現在權限樹。)
483
485
  if (true) {
484
486
  let kp = {}
485
487
  each(_rules, (v) => {
486
488
  kp[v.name] = v.isActive
487
489
  })
488
- each(targets, (t) => {
489
- // console.log('t', t)
490
- if (!haskey(kp, t.id)) {
491
- kp[t.id] = 'n'
492
- }
493
- })
494
490
  let rs = []
495
- each(kp, (v, k) => {
496
- let r = {
497
- name: k,
498
- isActive: v,
499
- }
500
- rs.push(r)
491
+ each(targets, (t) => {
492
+ rs.push({
493
+ name: t.id,
494
+ isActive: get(kp, t.id, 'n'),
495
+ })
501
496
  })
502
497
  _rules = rs
503
498
  }
@@ -215,6 +215,16 @@ function getKpText(key) {
215
215
  }
216
216
 
217
217
 
218
+ function tErr(err) {
219
+ let key = isestr(err) ? err : 'anUnexpectedErrorOccurred'
220
+ let msg = getKpText(key) //後端 err key → 翻譯
221
+ if (msg === key) { //getKpText 查無 → 回傳 key 本身 → 非 procLang key (連線層 raw 等)
222
+ msg = getKpText('cannotConnectServer')
223
+ }
224
+ return msg
225
+ }
226
+
227
+
218
228
  function gv(o, k, cv = null) {
219
229
  let r = get(o, k, '')
220
230
  if (!isestr(r)) {
@@ -290,6 +300,7 @@ let mUI = {
290
300
 
291
301
  setLang,
292
302
  getKpText,
303
+ tErr,
293
304
 
294
305
  gv,
295
306
  syncHeight,