vue2-client 1.7.20 → 1.8.0-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.
Files changed (44) hide show
  1. package/.eslintrc.js +19 -14
  2. package/babel.config.js +5 -5
  3. package/package.json +23 -35
  4. package/src/App.vue +1 -1
  5. package/src/base-client/components/common/AddressSearchCombobox/AddressSearchCombobox.vue +2 -2
  6. package/src/base-client/components/common/PersonSetting/PersonSetting.vue +4 -6
  7. package/src/base-client/components/common/Upload/Upload.vue +1 -1
  8. package/src/base-client/components/common/XAddNativeForm/XAddNativeForm.vue +2 -0
  9. package/src/base-client/components/common/XForm/XForm.vue +2 -0
  10. package/src/base-client/components/system/DictionaryDetailsView/DictionaryDetailsView.vue +3 -3
  11. package/src/base-client/plugins/AppData.js +1 -1
  12. package/src/base-client/plugins/Config.js +0 -1
  13. package/src/base-client/plugins/GetLoginInfoService.js +4 -2
  14. package/src/base-client/plugins/tabs-page-plugin.js +5 -4
  15. package/src/components/FilePreview/FilePreview.vue +2 -2
  16. package/src/components/NumberInfo/NumberInfo.vue +1 -1
  17. package/src/components/checkbox/ColorCheckbox.vue +1 -1
  18. package/src/components/checkbox/ImgCheckbox.vue +2 -2
  19. package/src/components/menu/menu.js +1 -1
  20. package/src/components/tool/AStepItem.vue +1 -1
  21. package/src/config/default/antd.config.js +11 -6
  22. package/src/layouts/PageLayout.vue +1 -1
  23. package/src/layouts/SinglePageView.vue +3 -2
  24. package/src/layouts/header/HeaderNotice.vue +3 -2
  25. package/src/layouts/tabs/TabsHead.vue +1 -2
  26. package/src/layouts/tabs/TabsView.vue +10 -10
  27. package/src/mock/extend/index.js +2 -1
  28. package/src/mock/goods/index.js +6 -6
  29. package/src/pages/login/Login.vue +2 -2
  30. package/src/pages/system/monitor/loginInfor/index.vue +1 -1
  31. package/src/pages/system/monitor/operLog/index.vue +1 -1
  32. package/src/pages/system/settings/modifyPassword.vue +1 -1
  33. package/src/pages/system/ticket/index.vue +2 -2
  34. package/src/pages/system/ticket/submitTicketSuccess.vue +1 -1
  35. package/src/services/api/common.js +1 -1
  36. package/src/utils/authority-utils.js +12 -12
  37. package/src/utils/errorCode.js +4 -4
  38. package/src/utils/login.js +8 -5
  39. package/src/utils/map-utils.js +20 -12
  40. package/src/utils/request.js +2 -2
  41. package/src/utils/routerUtil.js +6 -3
  42. package/src/utils/util.js +3 -2
  43. package/vue.config.js +20 -10
  44. package//350/277/201/347/247/273/346/227/245/345/277/227.md +15 -0
package/.eslintrc.js CHANGED
@@ -3,7 +3,7 @@ module.exports = {
3
3
  env: {
4
4
  node: true
5
5
  },
6
- 'extends': [
6
+ extends: [
7
7
  'plugin:vue/essential',
8
8
  'plugin:vue/strongly-recommended',
9
9
  '@vue/standard'
@@ -17,10 +17,11 @@ module.exports = {
17
17
  'vue/max-attributes-per-line': [
18
18
  2,
19
19
  {
20
- 'singleline': 5,
21
- 'multiline': {
22
- 'max': 1,
23
- 'allowFirstLine': false
20
+ singleline: {
21
+ max: 5
22
+ },
23
+ multiline: {
24
+ max: 1,
24
25
  }
25
26
  }
26
27
  ],
@@ -35,38 +36,42 @@ module.exports = {
35
36
  'vue/html-closing-bracket-newline': 0,
36
37
  'vue/no-parsing-error': 0,
37
38
  'vue/name-property-casing': 0,
39
+ 'vue/multi-word-component-names': 0,
40
+ 'vue/no-mutating-props': 0,
38
41
  'no-tabs': 0,
39
- 'quotes': [
42
+ 'multiline-ternary': 0,
43
+ 'object-shorthand': 0,
44
+ quotes: [
40
45
  2,
41
46
  'single',
42
47
  {
43
- 'avoidEscape': true,
44
- 'allowTemplateLiterals': true
48
+ avoidEscape: true,
49
+ allowTemplateLiterals: true
45
50
  }
46
51
  ],
47
- 'semi': [
52
+ semi: [
48
53
  2,
49
54
  'never',
50
55
  {
51
- 'beforeStatementContinuationChars': 'never'
56
+ beforeStatementContinuationChars: 'never'
52
57
  }
53
58
  ],
54
59
  'no-delete-var': 2,
55
60
  'prefer-const': [
56
61
  2,
57
62
  {
58
- 'ignoreReadBeforeAssign': false
63
+ ignoreReadBeforeAssign: false
59
64
  }
60
65
  ],
61
66
  'template-curly-spacing': 'off',
62
- 'indent': 'off',
67
+ indent: 'off',
63
68
  // 必须使用全等: false
64
- 'eqeqeq': 0,
69
+ eqeqeq: 0,
65
70
  // 可以使用!! 双重否定
66
71
  'no-extra-boolean-cast': 'off'
67
72
  },
68
73
  parserOptions: {
69
- parser: 'babel-eslint'
74
+ parser: '@babel/eslint-parser'
70
75
  },
71
76
  overrides: [
72
77
  {
package/babel.config.js CHANGED
@@ -9,13 +9,13 @@ if (IS_PROD) {
9
9
  module.exports = {
10
10
  presets: [
11
11
  '@vue/cli-plugin-babel/preset',
12
- ['@vue/babel-preset-jsx', { 'injectH': false }]
12
+ ['@vue/babel-preset-jsx', { injectH: false }]
13
13
  ],
14
14
  plugins,
15
- 'env': {
16
- 'test': {
17
- 'presets': ['@babel/preset-env'],
18
- 'plugins': ['istanbul']
15
+ env: {
16
+ test: {
17
+ presets: ['@babel/preset-env'],
18
+ plugins: ['istanbul']
19
19
  }
20
20
  }
21
21
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "vue2-client",
3
- "version": "1.7.20",
3
+ "version": "1.8.0-2",
4
4
  "private": false,
5
5
  "scripts": {
6
6
  "serve": "SET NODE_OPTIONS=--openssl-legacy-provider && vue-cli-service serve",
@@ -21,7 +21,7 @@
21
21
  "ant-design-vue": "^1.7.8",
22
22
  "axios": "^0.27.2",
23
23
  "clipboard": "^2.0.11",
24
- "core-js": "^3.30.1",
24
+ "core-js": "^3.33.0",
25
25
  "crypto-js": "^4.1.1",
26
26
  "date-fns": "^2.29.3",
27
27
  "default-passive-events": "^2.0.0",
@@ -32,12 +32,14 @@
32
32
  "js-base64": "^3.7.5",
33
33
  "js-cookie": "^2.2.1",
34
34
  "jsencrypt": "^3.3.2",
35
+ "lodash.clonedeep": "^4.5.0",
35
36
  "lodash.get": "^4.4.2",
36
37
  "mockjs": "^1.1.0",
37
38
  "nprogress": "^0.2.0",
39
+ "regenerator-runtime": "^0.14.0",
38
40
  "videojs-contrib-hls": "^5.15.0",
39
41
  "viser-vue": "^2.4.8",
40
- "vue": "2.6.14",
42
+ "vue": "^2.7.14",
41
43
  "vue-i18n": "^8.28.2",
42
44
  "vue-json-viewer": "^2.2.22",
43
45
  "vue-router": "^3.6.5",
@@ -48,40 +50,27 @@
48
50
  },
49
51
  "devDependencies": {
50
52
  "@ant-design/colors": "^7.0.0",
51
- "@babel/core": "^7.21.4",
53
+ "@babel/core": "^7.22.20",
54
+ "@babel/eslint-parser": "^7.22.15",
52
55
  "@babel/preset-env": "^7.22.20",
53
- "@vue/cli-plugin-babel": "^4.5.19",
54
- "@vue/cli-plugin-eslint": "^4.5.19",
55
- "@vue/cli-service": "^4.5.19",
56
- "@vue/eslint-config-standard": "^4.0.0",
56
+ "@vue/cli-plugin-babel": "^5.0.8",
57
+ "@vue/cli-plugin-eslint": "^5.0.8",
58
+ "@vue/cli-service": "^5.0.8",
59
+ "@vue/eslint-config-standard": "^8.0.1",
57
60
  "@vue/test-utils": "^1.3.6",
58
- "@vuepress/plugin-back-to-top": "^1.9.9",
59
- "babel-core": "^6.22.1",
60
- "babel-eslint": "^10.1.0",
61
- "babel-jest": "^25.5.1",
62
- "babel-loader": "^6.0.0",
63
- "babel-plugin-component": "^1.1.1",
64
- "babel-plugin-istanbul": "^4.1.1",
65
- "babel-plugin-transform-es2015-modules-commonjs": "^6.26.2",
61
+ "babel-jest": "^26.6.3",
66
62
  "babel-plugin-transform-remove-console": "^6.9.4",
67
- "babel-plugin-transform-runtime": "^6.22.0",
68
- "babel-polyfill": "^6.26.0",
69
- "babel-preset-env": "^1.3.2",
70
- "babel-preset-react": "^6.24.1",
71
- "babel-register": "^6.22.0",
72
- "compression-webpack-plugin": "^4.0.1",
63
+ "compression-webpack-plugin": "^10.0.0",
64
+ "css-minimizer-webpack-plugin": "^5.0.1",
73
65
  "deepmerge": "^4.3.1",
74
- "document-register-element": "^1.14.10",
75
- "escope": "^4.0.0",
76
- "eslint": "^6.8.0",
77
- "eslint-plugin-import": "^2.26.0",
66
+ "eslint": "^8.51.0",
67
+ "eslint-plugin-import": "^2.28.1",
78
68
  "eslint-plugin-node": "^11.1.0",
79
- "eslint-plugin-promise": "^4.3.1",
80
- "eslint-plugin-standard": "^4.1.0",
81
- "eslint-plugin-vue": "^6.2.2",
69
+ "eslint-plugin-promise": "^6.1.1",
70
+ "eslint-plugin-vue": "^9.17.0",
82
71
  "fast-deep-equal": "^3.1.3",
83
- "jest": "^24.0.0",
84
- "jest-environment-jsdom": "^23.4.0",
72
+ "jest": "^26.6.3",
73
+ "jest-environment-jsdom": "^26.6.2",
85
74
  "jest-transform-stub": "^2.0.0",
86
75
  "less-loader": "^6.2.0",
87
76
  "script-loader": "^0.7.2",
@@ -89,11 +78,10 @@
89
78
  "vue-cli-plugin-style-resources-loader": "^0.1.5",
90
79
  "vue-custom-element": "^3.3.0",
91
80
  "vue-jest": "^4.0.1",
92
- "vue-template-compiler": "2.6.14",
93
- "vuepress": "^1.9.9",
94
- "webpack": "^4.46.0",
81
+ "vue-template-compiler": "^2.7.14",
82
+ "webpack": "^5.88.2",
95
83
  "webpack-theme-color-replacer": "^1.4.7",
96
- "whatwg-fetch": "^3.6.2"
84
+ "whatwg-fetch": "^3.6.19"
97
85
  },
98
86
  "browserslist": [
99
87
  "> 1%",
package/src/App.vue CHANGED
@@ -53,7 +53,7 @@ export default {
53
53
  themeUtil.changeThemeColor(val, this.theme.mode).then(closeMessage)
54
54
  }
55
55
  },
56
- 'layout': function () {
56
+ layout: function () {
57
57
  window.dispatchEvent(new Event('resize'))
58
58
  }
59
59
  },
@@ -25,7 +25,7 @@
25
25
  <a-icon type="bank" /> {{ group.title }}
26
26
  </span>
27
27
  <a-select-option v-for="address in group.children" :key="address.label + ' <' + address.value + '>'">
28
- <p class="addressName"><a-icon type="environment" /> <span v-html="highLight(address.label, address.word)">{{ address.label }}</span></p>
28
+ <p class="addressName"><a-icon type="environment" /><span v-html="highLight(address.label, address.word)"></span></p>
29
29
  <p v-if="address.address !== '[]'" class="addressRemark">
30
30
  {{ address.address }}
31
31
  </p>
@@ -169,7 +169,7 @@ export default {
169
169
  const addressMap = {}
170
170
  result.tips.forEach((res) => {
171
171
  if (res.location) {
172
- if (!addressMap.hasOwnProperty(res.district)) {
172
+ if (!Object.prototype.hasOwnProperty.call(addressMap, res.district)) {
173
173
  addressMap[res.district] = []
174
174
  }
175
175
  addressMap[res.district].push({
@@ -191,13 +191,11 @@ export default {
191
191
  }
192
192
 
193
193
  .ant-card-body {
194
- :global {
195
- .ant-tree {
196
- line-height: 3;
194
+ .ant-tree {
195
+ line-height: 3;
197
196
 
198
- li {
199
- position: relative;
200
- }
197
+ li {
198
+ position: relative;
201
199
  }
202
200
  }
203
201
  }
@@ -39,7 +39,7 @@ import { mapState } from 'vuex'
39
39
  import { fileDelete, upload } from '@vue2-client/services/api/common'
40
40
 
41
41
  export default {
42
- name: 'uploads',
42
+ name: 'Uploads',
43
43
  data () {
44
44
  return {
45
45
  uploadedFileList: [],
@@ -233,7 +233,9 @@ export default {
233
233
  case 'number':
234
234
  case 'integer':
235
235
  case 'float':
236
+ // eslint-disable-next-line no-case-declarations
236
237
  let defaultValue
238
+ // eslint-disable-next-line no-case-declarations
237
239
  let message
238
240
  switch (item.rule.type) {
239
241
  case 'number':
@@ -145,7 +145,9 @@ export default {
145
145
  case 'number':
146
146
  case 'integer':
147
147
  case 'float':
148
+ // eslint-disable-next-line no-case-declarations
148
149
  let defaultValue
150
+ // eslint-disable-next-line no-case-declarations
149
151
  let message
150
152
  switch (item.rule.type) {
151
153
  case 'number':
@@ -27,7 +27,7 @@
27
27
  </div>
28
28
  </div>
29
29
  <!-- actions -->
30
- <template v-slot:extra>
30
+ <template #extra>
31
31
  <a-button-group style="margin-right: 4px;">
32
32
  <a-button type="dashed" @click="initView" :loading="loadDetails">刷新</a-button>
33
33
  </a-button-group>
@@ -114,8 +114,8 @@ export default {
114
114
  // 初始化组件
115
115
  initView () {
116
116
  this.tabActiveKey = '1'
117
- this.fixedQueryForm['v_f_dictionary_id'] = this.id
118
- this.fixedAddForm['v_f_dictionary_id'] = this.id
117
+ this.fixedQueryForm.v_f_dictionary_id = this.id
118
+ this.fixedAddForm.v_f_dictionary_id = this.id
119
119
  this.getDetails(this.id)
120
120
  },
121
121
  onClose () {
@@ -56,7 +56,7 @@ const GetAppDataService = {
56
56
  const str = localStorage.getItem(process.env.VUE_APP_BADGE_KEY)
57
57
  const object = JSON.parse(str)
58
58
  const result = object[key]
59
- if (result && result.hasOwnProperty(value)) {
59
+ if (result && Object.prototype.hasOwnProperty.call(result, value)) {
60
60
  return result[value]
61
61
  } else {
62
62
  return null
@@ -1,4 +1,3 @@
1
-
2
1
  const asyncReady = async function (vm, name) {
3
2
  // 获取配置信息
4
3
  try {
@@ -51,10 +51,12 @@ async function getGasman () {
51
51
  // eslint-disable-next-line
52
52
  async function getLic () {
53
53
  try {
54
- const getLic = await post(SEARCH, { data: {
54
+ const getLic = await post(SEARCH, {
55
+ data: {
55
56
  source: 'this.getRights().where(row.getType()==$function$ && row.getPath($name$).indexOf($资源操作$) != -1)',
56
57
  userid: Vue.$login.f.id
57
- } }, { resolveMsg: null, rejectMsg: null })
58
+ }
59
+ }, { resolveMsg: null, rejectMsg: null })
58
60
  const arry = []
59
61
  getLic.forEach((item) => {
60
62
  arry.push(item.name)
@@ -17,8 +17,9 @@ const TabsPagePlugin = {
17
17
  },
18
18
  $setPageTitle (route, title) {
19
19
  if (title) {
20
- let path = typeof route === 'object' ? route.path : route
21
- path = path && path.split('?')[0]
20
+ // let path = typeof route === 'object' ? route.path : route
21
+ // path = path && path.split('?')[0]
22
+ const path = typeof route === 'object' ? this.$router.resolve(route).route.fullPath : route
22
23
  this.$store.commit('setting/setCustomTitle', { path, title })
23
24
  }
24
25
  }
@@ -26,8 +27,8 @@ const TabsPagePlugin = {
26
27
  computed: {
27
28
  customTitle () {
28
29
  const customTitles = this.$store.state.setting.customTitles
29
- const path = this.$route.path.split('?')[0]
30
- const custom = customTitles.find(item => item.path === path)
30
+ // const path = this.$route.path.split('?')[0]
31
+ const custom = customTitles.find(item => item.path === this.$route.fullPath)
31
32
  return custom && custom.title
32
33
  }
33
34
  }
@@ -111,8 +111,8 @@ export default {
111
111
  this.previewImageSrc = this.path
112
112
  this.showImagePreview = 2
113
113
  } else if (this.isVideo()) {
114
- this.playerOptions['sources'][0]['type'] = 'video/' + this.path.substring(this.path.lastIndexOf('.') + 1)
115
- this.playerOptions['sources'][0]['src'] = this.path
114
+ this.playerOptions.sources[0].type = 'video/' + this.path.substring(this.path.lastIndexOf('.') + 1)
115
+ this.playerOptions.sources[0].src = this.path
116
116
  this.showImagePreview = 3
117
117
  } else {
118
118
  const previewDocUrl = this.previewDocService + encodeURIComponent(Base64.encode(this.fileServer + this.path))
@@ -50,5 +50,5 @@ export default {
50
50
  </script>
51
51
 
52
52
  <style lang="less" scoped>
53
- @import "index";
53
+ //@import "index";
54
54
  </style>
@@ -103,7 +103,7 @@ export default {
103
103
  },
104
104
  inject: ['groupContext'],
105
105
  watch: {
106
- 'sChecked': function () {
106
+ sChecked: function () {
107
107
  const value = {
108
108
  value: this.value,
109
109
  color: this.color,
@@ -36,7 +36,7 @@ const Group = {
36
36
  }
37
37
  },
38
38
  watch: {
39
- 'values': function (value) {
39
+ values: function (value) {
40
40
  this.$emit('change', value)
41
41
  // // 此条件是为解决单选时,触发两次chang事件问题
42
42
  // if (!(newVal.length === 1 && oldVal.length === 1 && newVal[0] === oldVal[0])) {
@@ -102,7 +102,7 @@ export default {
102
102
  },
103
103
  inject: ['groupContext'],
104
104
  watch: {
105
- 'sChecked': function () {
105
+ sChecked: function () {
106
106
  const option = {
107
107
  value: this.value,
108
108
  checked: this.sChecked
@@ -134,7 +134,7 @@ export default {
134
134
  this.sOpenKeys = this.cachedOpenKeys
135
135
  }
136
136
  },
137
- '$route': function () {
137
+ $route: function () {
138
138
  if (this.$route.meta && this.$route.meta.singlePage) {
139
139
  this.setSingle(this.$route)
140
140
  }
@@ -53,7 +53,7 @@ export default {
53
53
  :global{
54
54
  .ant-steps-item-process{
55
55
  .linkable{
56
- color: @primary-color;
56
+ //color: @primary-color;
57
57
  }
58
58
  }
59
59
  }
@@ -22,10 +22,11 @@ const ANTD = {
22
22
  'component-background': '#fff',
23
23
  'heading-color': 'rgba(0, 0, 0, 0.85)',
24
24
  'text-color': 'rgba(0, 0, 0, 0.65)',
25
- 'text-color-inverse': '#fff',
25
+ 'text-color-inverse': '#fefefe',
26
26
  'text-color-secondary': 'rgba(0, 0, 0, 0.45)',
27
27
  'shadow-color': 'rgba(0, 0, 0, 0.15)',
28
28
  'border-color-split': '#f0f0f0',
29
+ 'border-color-base': '#d9d9d9',
29
30
  'background-color-light': '#fafafa',
30
31
  'background-color-base': '#f5f5f5',
31
32
  'table-selected-row-bg': '#fafafa',
@@ -34,8 +35,9 @@ const ANTD = {
34
35
  'disabled-color': 'rgba(0, 0, 0, 0.25)',
35
36
  'menu-dark-color': 'rgba(254, 254, 254, 0.65)',
36
37
  'menu-dark-highlight-color': '#fefefe',
38
+ 'menu-dark-selected-item-icon-color': '#fefefe',
37
39
  'menu-dark-arrow-color': '#fefefe',
38
- 'btn-primary-color': '#fff'
40
+ 'btn-primary-color': '#fefefe'
39
41
  },
40
42
  light: {
41
43
  'layout-body-background': '#f0f2f5',
@@ -43,10 +45,11 @@ const ANTD = {
43
45
  'component-background': '#fff',
44
46
  'heading-color': 'rgba(0, 0, 0, 0.85)',
45
47
  'text-color': 'rgba(0, 0, 0, 0.65)',
46
- 'text-color-inverse': '#fff',
48
+ 'text-color-inverse': '#fefefe',
47
49
  'text-color-secondary': 'rgba(0, 0, 0, 0.45)',
48
50
  'shadow-color': 'rgba(0, 0, 0, 0.15)',
49
51
  'border-color-split': '#f0f0f0',
52
+ 'border-color-base': '#d9d9d9',
50
53
  'background-color-light': '#fafafa',
51
54
  'background-color-base': '#f5f5f5',
52
55
  'table-selected-row-bg': '#fafafa',
@@ -56,7 +59,7 @@ const ANTD = {
56
59
  'menu-dark-color': 'rgba(1, 1, 1, 0.65)',
57
60
  'menu-dark-highlight-color': '#fefefe',
58
61
  'menu-dark-arrow-color': '#fefefe',
59
- 'btn-primary-color': '#fff'
62
+ 'btn-primary-color': '#fefefe'
60
63
  },
61
64
  night: {
62
65
  'layout-body-background': '#000',
@@ -64,10 +67,11 @@ const ANTD = {
64
67
  'component-background': '#141414',
65
68
  'heading-color': 'rgba(255, 255, 255, 0.85)',
66
69
  'text-color': 'rgba(255, 255, 255, 0.85)',
67
- 'text-color-inverse': '#141414',
70
+ 'text-color-inverse': '#fefefe',
68
71
  'text-color-secondary': 'rgba(255, 255, 255, 0.45)',
69
72
  'shadow-color': 'rgba(255, 255, 255, 0.15)',
70
73
  'border-color-split': '#303030',
74
+ 'border-color-base': '#282828',
71
75
  'background-color-light': '#ffffff0a',
72
76
  'background-color-base': '#2a2a2a',
73
77
  'table-selected-row-bg': '#ffffff0a',
@@ -76,8 +80,9 @@ const ANTD = {
76
80
  'disabled-color': 'rgba(255, 255, 255, 0.25)',
77
81
  'menu-dark-color': 'rgba(254, 254, 254, 0.65)',
78
82
  'menu-dark-highlight-color': '#fefefe',
83
+ 'menu-dark-selected-item-icon-color': '#fefefe',
79
84
  'menu-dark-arrow-color': '#fefefe',
80
- 'btn-primary-color': '#141414'
85
+ 'btn-primary-color': '#fefefe'
81
86
  }
82
87
  }
83
88
  }
@@ -99,7 +99,7 @@ export default {
99
99
  const routes = this.$route.matched
100
100
  const path = this.$route.path
101
101
  const breadcrumb = []
102
- routes.filter(item => path.includes(item.path))
102
+ routes.filter(item => path.includes(item.path) || item.regex.test(path))
103
103
  .forEach(route => {
104
104
  const path = route.path.length === 0 ? '/home' : route.path
105
105
  breadcrumb.push(this.$t(getI18nKey(path)))
@@ -67,9 +67,10 @@ export default {
67
67
  })
68
68
  } else if (this.singlePageUrl.indexOf('http') !== -1) {
69
69
  if (this.singlePageUrl.indexOf('?goto=') !== -1) {
70
- this.singlePageUrl = this.singlePageUrl + '&f_user_id=' + this.currUser.username + '&password=' + this.currUser.password
70
+ this.url = this.singlePageUrl + '&f_user_id=' + this.currUser.username + '&password=' + this.currUser.password
71
+ } else {
72
+ this.url = this.singlePageUrl
71
73
  }
72
- this.url = this.singlePageUrl
73
74
  } else {
74
75
  this.url = this.iframeSrc
75
76
  }
@@ -135,9 +135,10 @@ export default {
135
135
  this.loading = false
136
136
  return
137
137
  }
138
- this.loadding = true
138
+ if (this.show) return
139
+ this.loading = true
139
140
  setTimeout(() => {
140
- this.loadding = false
141
+ this.loading = false
141
142
  }, 1000)
142
143
  }
143
144
  }
@@ -97,8 +97,7 @@
97
97
  this.$emit('contextmenu', pageKey, e)
98
98
  },
99
99
  pageName (page) {
100
- const pagePath = page.fullPath.split('?')[0]
101
- const custom = this.customTitles.find(item => item.path === pagePath)
100
+ const custom = this.customTitles.find(item => item.path === page.path)
102
101
  return (custom && custom.title) || page.title || this.$t(getI18nKey(page.keyPath))
103
102
  }
104
103
  }
@@ -14,7 +14,7 @@
14
14
  <div :class="['tabs-view-content', layout, pageWidth]" :style="`margin-top: ${multiPage ? -24 : 0}px`">
15
15
  <page-toggle-transition v-show="!$route.meta.singlePage" :disabled="animate.disabled" :animate="animate.name" :direction="animate.direction">
16
16
  <a-keep-alive :exclude-keys="excludeKeys" v-if="multiPage && cachePage" v-model="clearCaches">
17
- <router-view v-if="!refreshing" ref="tabContent" :key="$route.path" />
17
+ <router-view v-if="!refreshing" ref="tabContent" :key="$route.fullPath" />
18
18
  </a-keep-alive>
19
19
  <router-view ref="tabContent" v-else-if="!refreshing" />
20
20
  </page-toggle-transition>
@@ -75,10 +75,10 @@ export default {
75
75
  this.loadCacheConfig(this.$router?.options?.routes)
76
76
  this.loadCachedTabs()
77
77
  const route = this.$route
78
- if (this.pageList.findIndex(item => item.path === route.path) === -1) {
78
+ if (this.pageList.findIndex(item => item.path === route.fullPath) === -1) {
79
79
  this.pageList.push(this.createPage(route))
80
80
  }
81
- this.activePage = route.path
81
+ this.activePage = route.fullPath
82
82
  if (this.multiPage) {
83
83
  this.$nextTick(() => {
84
84
  this.setCachedKey(route)
@@ -98,9 +98,9 @@ export default {
98
98
  this.excludeKeys = []
99
99
  this.loadCacheConfig(val)
100
100
  },
101
- '$route': function (newRoute) {
102
- this.activePage = newRoute.path
103
- const page = this.pageList.find(item => item.path === newRoute.path)
101
+ $route: function (newRoute) {
102
+ this.activePage = newRoute.fullPath
103
+ const page = this.pageList.find(item => item.path === newRoute.fullPath)
104
104
  if (!this.multiPage) {
105
105
  this.pageList = [this.createPage(newRoute)]
106
106
  } else if (page) {
@@ -114,7 +114,7 @@ export default {
114
114
  })
115
115
  }
116
116
  },
117
- 'multiPage': function (newVal) {
117
+ multiPage: function (newVal) {
118
118
  if (!newVal) {
119
119
  this.pageList = [this.createPage(this.$route)]
120
120
  this.removeListener()
@@ -288,7 +288,7 @@ export default {
288
288
  keyPath: route.matched[route.matched.length - 1].path,
289
289
  fullPath: route.fullPath,
290
290
  loading: false,
291
- path: route.path,
291
+ path: route.fullPath,
292
292
  title: route.meta && route.meta.page && route.meta.page.title,
293
293
  unclose: route.meta && route.meta.page && (route.meta.page.closable === false)
294
294
  }
@@ -315,7 +315,7 @@ export default {
315
315
  try {
316
316
  // 加载缓存的单页面
317
317
  const allCachedPath = JSON.parse(cachedTabsStr).map(str => { return str.fullPath })
318
- this.allSinglePages.map(item => {
318
+ this.allSinglePages.forEach(item => {
319
319
  if (allCachedPath.includes(item.fullPath)) {
320
320
  // 如果缓存中有单页面 加载到 state.single
321
321
  this.setSingle(item)
@@ -340,7 +340,7 @@ export default {
340
340
  this.allSinglePages.push(item)
341
341
  }
342
342
  if (!cacheAble) {
343
- this.excludeKeys.push(new RegExp(`${item.path}\\d+$`))
343
+ this.excludeKeys.push(new RegExp(`${item.path.replace(/:[^/]*/g, '[^/]*')}(\\?.*)?\\d*$`))
344
344
  }
345
345
  if (item.children) {
346
346
  this.loadCacheConfig(item.children, cacheAble)
@@ -63,7 +63,8 @@ Random.extend({
63
63
  const time = new Date()
64
64
  const hour = time.getHours()
65
65
  return hour < 9
66
- ? timeList[0] : (hour <= 11 ? timeList[1] : (hour <= 13 ? timeList[2] : (hour <= 20 ? timeList[3] : timeList[4])))
66
+ ? timeList[0]
67
+ : (hour <= 11 ? timeList[1] : (hour <= 13 ? timeList[2] : (hour <= 20 ? timeList[3] : timeList[4])))
67
68
  },
68
69
  avatar () {
69
70
  return this.pick(avatars)
@@ -7,13 +7,13 @@ const current = new Date().getTime()
7
7
  const goodsList = Mock.mock({
8
8
  'list|100': [{
9
9
  'id|+1': 0,
10
- 'name': '@GOODS',
11
- 'orderId': `${current}-@integer(1,100)`,
10
+ name: '@GOODS',
11
+ orderId: `${current}-@integer(1,100)`,
12
12
  'status|1-4': 1,
13
- 'send': '@BOOLEAN',
14
- 'sendTime': '@DATETIME',
15
- 'orderDate': '@DATE',
16
- 'auditTime': '@TIME'
13
+ send: '@BOOLEAN',
14
+ sendTime: '@DATETIME',
15
+ orderDate: '@DATE',
16
+ auditTime: '@TIME'
17
17
  }]
18
18
  })
19
19
 
@@ -229,7 +229,7 @@ export default {
229
229
 
230
230
  <style lang="less" scoped>
231
231
  .common-layout {
232
- background-image: url('/img/login/background.webp');
232
+ background-image: url('/public/img/login/background.webp');
233
233
  background-size: cover;
234
234
  background-position: center;
235
235
  .content {
@@ -248,7 +248,7 @@ export default {
248
248
  display: flex;
249
249
  .illustration {
250
250
  flex: 1;
251
- background-image: url("/img/login/illustration.webp");
251
+ background-image: url("/public/img/login/illustration.webp");
252
252
  background-size: contain;
253
253
  background-position: center;
254
254
  background-repeat: no-repeat;
@@ -12,7 +12,7 @@
12
12
  import XFormTable from '@vue2-client/base-client/components/common/XFormTable/XFormTable'
13
13
 
14
14
  export default {
15
- name: 'loginInfor',
15
+ name: 'LoginInfor',
16
16
  components: {
17
17
  XFormTable
18
18
  },
@@ -12,7 +12,7 @@
12
12
  import XFormTable from '@vue2-client/base-client/components/common/XFormTable/XFormTable'
13
13
 
14
14
  export default {
15
- name: 'operLog',
15
+ name: 'OperLog',
16
16
  components: {
17
17
  XFormTable
18
18
  },
@@ -34,7 +34,7 @@ import { logout, modifyPassword } from '@vue2-client/services/user'
34
34
  import { mapState } from 'vuex'
35
35
 
36
36
  export default {
37
- name: 'modifyPassword',
37
+ name: 'ModifyPassword',
38
38
  computed: {
39
39
  ...mapState('account', { currUser: 'user' })
40
40
  },
@@ -257,7 +257,7 @@ import submitTicketSuccess from './submitTicketSuccess'
257
257
  import Upload from '@vue2-client/base-client/components/common/Upload'
258
258
 
259
259
  export default {
260
- name: 'submitTicket',
260
+ name: 'SubmitTicket',
261
261
  components: {
262
262
  XFormTable,
263
263
  submitTicketSuccess,
@@ -322,7 +322,7 @@ export default {
322
322
  this.form.name = this.$route.query.orgName
323
323
  this.form.contact = this.$route.query.contact
324
324
  this.form.phone = this.$route.query.phone
325
- this.fixedQueryForm['t_uploader'] = this.currUser.orgName
325
+ this.fixedQueryForm.t_uploader = this.currUser.orgName
326
326
  },
327
327
  methods: {
328
328
  toDetail (record, id) {
@@ -77,7 +77,7 @@ const AStepItemGroup = AStepItem.Group
77
77
  const DetailListItem = DetailList.Item
78
78
 
79
79
  export default {
80
- name: 'submitTicketSuccess',
80
+ name: 'SubmitTicketSuccess',
81
81
  components: { AStepItemGroup, AStepItem, DetailListItem, DetailList, Result, FileItem, ImageItem, FilePreview },
82
82
  props: {
83
83
  // 工单序列号
@@ -180,7 +180,7 @@ export function download (parameter, filename, serviceName = setting.state.defau
180
180
  } else {
181
181
  const resText = await data.text()
182
182
  const rspObj = JSON.parse(resText)
183
- const errMsg = errorCode[rspObj.code] || rspObj.msg || errorCode['default']
183
+ const errMsg = errorCode[rspObj.code] || rspObj.msg || errorCode.default
184
184
  message.error(errMsg)
185
185
  }
186
186
  notification.close(notificationKey)
@@ -8,10 +8,12 @@ function hasPermission (authority, permissions) {
8
8
  let required = '*'
9
9
  if (typeof authority === 'string') {
10
10
  required = authority
11
+ } else if (Array.isArray(authority)) {
12
+ required = authority
11
13
  } else if (typeof authority === 'object') {
12
14
  required = authority.permission
13
15
  }
14
- return required === '*' || (permissions && permissions.findIndex(item => item === required || item.id === required) !== -1)
16
+ return required === '*' || hasAnyItem(required, permissions, (r, t) => !!(r === t || r === t.id))
15
17
  }
16
18
 
17
19
  /**
@@ -24,25 +26,23 @@ function hasRole (authority, roles) {
24
26
  if (typeof authority === 'object') {
25
27
  required = authority.role
26
28
  }
27
- return authority === '*' || hasAnyRole(required, roles)
29
+ return authority === '*' || hasAnyItem(required, roles, (r, t) => !!(r === t || r === t.id))
28
30
  }
29
31
 
30
32
  /**
31
- * 判断是否有需要的任意一个角色
32
- * @param required {String | Array[String]} 需要的角色,可以是单个角色或者一个角色数组
33
- * @param roles 拥有的角色
33
+ * 判断目标数组是否有所需元素
34
+ * @param {String | String[]}required 所需元素,数组或单个元素
35
+ * @param {String[]|Object[]} source 目标数组
36
+ * @param {Function} filter 匹配条件
37
+ * (r: String, s: String|Object) => boolean
34
38
  * @returns {boolean}
35
39
  */
36
- function hasAnyRole (required, roles) {
40
+ function hasAnyItem (required, source, filter) {
37
41
  if (!required) {
38
42
  return false
39
- } else if (Array.isArray(required)) {
40
- return roles.findIndex(role => {
41
- return required.findIndex(item => item === role || item === role.id) !== -1
42
- }) !== -1
43
- } else {
44
- return roles.findIndex(role => role === required || role.id === required) !== -1
45
43
  }
44
+ const checkedList = Array.isArray(required) ? required : [required]
45
+ return !!source.find(s => checkedList.find(r => filter(r, s)))
46
46
  }
47
47
 
48
48
  /**
@@ -1,6 +1,6 @@
1
1
  export default {
2
- '401': '认证失败,无法访问系统资源',
3
- '403': '当前操作没有权限',
4
- '404': '访问资源不存在',
5
- 'default': '系统未知错误,请反馈给管理员'
2
+ 401: '认证失败,无法访问系统资源',
3
+ 403: '当前操作没有权限',
4
+ 404: '访问资源不存在',
5
+ default: '系统未知错误,请反馈给管理员'
6
6
  }
@@ -109,16 +109,19 @@ function afterLogin (res, options) {
109
109
  afterGeneral(result, options)
110
110
  setAccessToken(data)
111
111
  if (result.deps === '用户工单登记') {
112
- router.push(setting.ticketPage).catch(() => {})
112
+ router.push(setting.ticketPage).catch(() => {
113
+ })
113
114
  } else {
114
115
  console.log('去往的页面', pathname)
115
- router.push(pathname).catch(() => {})
116
+ router.push(pathname).catch(() => {
117
+ })
116
118
  }
117
119
  })
118
- .finally(() => {})
120
+ .finally(() => {
121
+ })
122
+ })
123
+ .catch((res) => {
119
124
  })
120
- .catch((res) => {})
121
- } else {
122
125
  }
123
126
  }
124
127
  export function startLogin (options) {
@@ -19,19 +19,27 @@ async function GetGDMap (secretKey, key) {
19
19
  }
20
20
  return Amap
21
21
  }
22
+
23
+ async function getGDMap (address) {
24
+ new (await GetGDMap()).Geocoder({
25
+ radius: 500 // 范围,默认:500
26
+ }).getLocation(address, function (status, result) {
27
+ if (status === 'complete' && result.geocodes.length) {
28
+ return ({ lng: result.geocodes[0].location.lng, lat: result.geocodes[0].location.lat })
29
+ } else {
30
+ // eslint-disable-next-line prefer-promise-reject-errors
31
+ throw new Error('根据经纬度查询地址失败')
32
+ }
33
+ })
34
+ }
35
+
22
36
  async function GetLocation (address) {
23
- return new Promise(async (resolve, reject) => {
24
- new (await GetGDMap()).Geocoder({
25
- radius: 500 // 范围,默认:500
26
- }).getLocation(address, function (status, result) {
27
- console.log(result)
28
- if (status === 'complete' && result.geocodes.length) {
29
- resolve({ lng: result.geocodes[0].location.lng, lat: result.geocodes[0].location.lat })
30
- } else {
31
- // eslint-disable-next-line prefer-promise-reject-errors
32
- reject('根据经纬度查询地址失败')
33
- }
34
- })
37
+ return new Promise((resolve, reject) => {
38
+ try {
39
+ resolve(getGDMap(address))
40
+ } catch (e) {
41
+ reject(e)
42
+ }
35
43
  })
36
44
  }
37
45
  export { GetGDMap, GetLocation }
@@ -161,7 +161,7 @@ function loadInterceptors () {
161
161
  // 判断是否为V4环境,不为compatible赋初始值
162
162
  // 其有可能是undefined未定义,或第一次使用本系统LocalStorage在初始化,获得的值为null
163
163
  const compatible = getSystemVersion()
164
- if (compatible === 'V4' || (res.data.code && res.data.hasOwnProperty('msg'))) {
164
+ if (compatible === 'V4' || (res.data.code && Object.prototype.hasOwnProperty.call(res.data, 'msg'))) {
165
165
  // 请求rul
166
166
  const requestUrl = res.config.url
167
167
  if (res.data.data) {
@@ -170,7 +170,7 @@ function loadInterceptors () {
170
170
  // 未设置状态码则默认成功状态
171
171
  const code = res.data.code || 200
172
172
  // 获取错误信息
173
- const msg = errorCode[code] || res.data.msg || errorCode['default']
173
+ const msg = errorCode[code] || res.data.msg || errorCode.default
174
174
  // 二进制数据则直接返回
175
175
  if (res.request.responseType === 'blob' || res.request.responseType === 'arraybuffer') {
176
176
  return res.data
@@ -67,14 +67,14 @@ function parseRoutes (routesConfig, routerMap) {
67
67
  } else if (typeof item === 'object') {
68
68
  // 当没有设置路由对象名或者设置的是blank路由对象时, 给空界面, path为名称
69
69
  if (!item.router || item.router === 'blank') {
70
- router = routerMap['blank']
70
+ router = routerMap.blank
71
71
  item.path = encodeURI(item.name)
72
72
  } else {
73
73
  router = routerMap[item.router]
74
74
  }
75
75
  // 查看是否是单页面
76
76
  if (item.meta && item.meta.singlePage) {
77
- router = routerMap['singlePage']
77
+ router = routerMap.singlePage
78
78
  item.path = encodeURI(item.name)
79
79
  }
80
80
  // 当没在动态路由对象中找到时, 不添加到路由
@@ -117,6 +117,9 @@ function parseRoutes (routesConfig, routerMap) {
117
117
  redirect: routeCfg.redirect || router.redirect,
118
118
  meta: { ...meta, authority: meta.authority || '*' }
119
119
  }
120
+ if (router.beforeEnter) {
121
+ route.beforeEnter = router.beforeEnter
122
+ }
120
123
  if (routeCfg.invisible || router.invisible) {
121
124
  route.meta.invisible = true
122
125
  }
@@ -265,7 +268,7 @@ function formatAuthority (routes, pAuthorities = []) {
265
268
  let authority = {}
266
269
  if (!meta.authority) {
267
270
  authority = defaultAuthority
268
- } else if (typeof meta.authority === 'string') {
271
+ } else if (typeof meta.authority === 'string' || Array.isArray(meta.authority)) {
269
272
  authority.permission = meta.authority
270
273
  } else if (typeof meta.authority === 'object') {
271
274
  authority = meta.authority
package/src/utils/util.js CHANGED
@@ -57,7 +57,7 @@ export function formatDate (dateStr, fmt) {
57
57
  'm+': date.getMinutes(),
58
58
  's+': date.getSeconds(),
59
59
  'q+': Math.floor((date.getMonth() + 3) / 3),
60
- 'S': date.getMilliseconds()
60
+ S: date.getMilliseconds()
61
61
  }
62
62
  if (!fmt) {
63
63
  fmt = 'yyyy-MM-dd hh:mm:ss'
@@ -91,7 +91,8 @@ export function timeFix () {
91
91
  const time = new Date()
92
92
  const hour = time.getHours()
93
93
  return hour < 9
94
- ? timeList[0] : (hour <= 11 ? timeList[1] : (hour <= 13 ? timeList[2] : (hour <= 20 ? timeList[3] : timeList[4])))
94
+ ? timeList[0]
95
+ : (hour <= 11 ? timeList[1] : (hour <= 13 ? timeList[2] : (hour <= 20 ? timeList[3] : timeList[4])))
95
96
  }
96
97
 
97
98
  /**
package/vue.config.js CHANGED
@@ -4,12 +4,13 @@ const ThemeColorReplacer = require('webpack-theme-color-replacer')
4
4
  const { getThemeColors, modifyVars } = require('./src/utils/themeUtil')
5
5
  const { resolveCss } = require('./src/utils/theme-color-replacer-extend')
6
6
  const CompressionWebpackPlugin = require('compression-webpack-plugin')
7
+ const CssMinimizerPlugin = require('css-minimizer-webpack-plugin')
7
8
 
8
9
  const productionGzipExtensions = ['js', 'css']
9
10
  const isProd = process.env.NODE_ENV === 'production'
10
11
 
11
- const server = 'http://221.193.244.147:9600'
12
- const local = 'http://221.193.244.147:9600/webmeter'
12
+ const server = 'http://61.134.55.234:8405'
13
+ const local = 'http://61.134.55.234:8456/webmeter'
13
14
  // const local = 'http://localhost:8080'
14
15
 
15
16
  module.exports = {
@@ -48,7 +49,7 @@ module.exports = {
48
49
  }
49
50
  },
50
51
  configureWebpack: config => {
51
- config.entry.app = ['babel-polyfill', 'whatwg-fetch', './src/main.js']
52
+ config.entry.app = ['core-js/stable', 'regenerator-runtime/runtime', 'whatwg-fetch', './src/main.js']
52
53
  config.performance = {
53
54
  hints: false
54
55
  }
@@ -61,12 +62,15 @@ module.exports = {
61
62
  })
62
63
  )
63
64
  // Ignore all locale files of moment.js
64
- config.plugins.push(new webpack.IgnorePlugin(/^\.\/locale$/, /moment$/))
65
+ config.plugins.push(new webpack.IgnorePlugin({
66
+ resourceRegExp: /^\.\/locale$/,
67
+ contextRegExp: /moment$/
68
+ }))
65
69
  // 生产环境下将资源压缩成gzip格式
66
70
  if (isProd) {
67
71
  // add `CompressionWebpack` plugin to webpack plugins
68
72
  config.plugins.push(new CompressionWebpackPlugin({
69
- algorithm: 'gzip',
73
+ algorithm: require('zlib').createGzip,
70
74
  test: new RegExp('\\.(' + productionGzipExtensions.join('|') + ')$'),
71
75
  threshold: 10240,
72
76
  minRatio: 0.8
@@ -80,11 +84,17 @@ module.exports = {
80
84
  chainWebpack: config => {
81
85
  // 生产环境下关闭css压缩的 colormin 项,因为此项优化与主题色替换功能冲突
82
86
  if (isProd) {
83
- config.plugin('optimize-css')
84
- .tap(args => {
85
- args[0].cssnanoOptions.preset[1].colormin = false
86
- return args
87
- })
87
+ config.optimization.minimizer('css').use(CssMinimizerPlugin, [{
88
+ minimizerOptions: {
89
+ preset: [
90
+ 'default',
91
+ {
92
+ discardComments: { removeAll: true },
93
+ colormin: false,
94
+ }
95
+ ]
96
+ }
97
+ }])
88
98
  }
89
99
  config.resolve.alias.set('@vue2-client', path.resolve(__dirname, 'src'))
90
100
  },
@@ -0,0 +1,15 @@
1
+ # vue2迁移vue3
2
+
3
+ 1. 完成vue-cli,webpack,babel,eslint的升级
4
+ - core-js 3.30.1 -> 3.33.0
5
+ - add regenerator-runtime
6
+ - @babel/core 7.21.4 -> 7.22.20
7
+ - babel-eslint 10.1.0 -> @babel/eslint-parser 7.22.15
8
+ - @vue/cli 4.5.19 -> 5.0.8
9
+ - babel-jest 25.5.1 -> 26.6.3
10
+ - eslint 6.8.0 -> 7.32.0
11
+ - jest 24.0.0 -> 26.6.3
12
+ - webpack 4.46.0 -> 5.88.2
13
+ 2. 完成vue2的2.7升级
14
+ - vue 2.6.14 -> 2.7.14
15
+ - eslint 7.32.0 -> 8.51.0