vue2-client 1.2.82 → 1.2.85

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/CHANGELOG.md CHANGED
@@ -1,7 +1,7 @@
1
1
  # Change Log
2
2
  > 所有关于本项目的变化都在该文档里。
3
3
 
4
- **1.2.81 - 1.2.82 -2022-07-21 @朱子峰**
4
+ **1.2.81 - 1.2.85 -2022-07-21 @朱子峰**
5
5
  - 功能新增:
6
6
  - 兼容V4登陆
7
7
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "vue2-client",
3
- "version": "1.2.82",
3
+ "version": "1.2.85",
4
4
  "private": false,
5
5
  "scripts": {
6
6
  "serve": "vue-cli-service serve",
@@ -1,225 +1,225 @@
1
- <template>
2
- <div class="certain-category-search-wrapper">
3
- <a-auto-complete
4
- :disabled="!mapAutocomplete"
5
- :dropdown-match-select-width="false"
6
- :dropdown-style="{ width: '400px' }"
7
- class="certain-category-search"
8
- dropdown-class-name="certain-category-search-dropdown"
9
- option-label-prop="value"
10
- placeholder="输入地址关键字搜索"
11
- @search="fetchFunction"
12
- @select="onSelect"
13
- >
14
- <a-spin v-if="searching" slot="notFoundContent" size="small" />
15
- <template slot="dataSource">
16
- <a-select-opt-group v-for="group in option" :key="group.title">
17
- <span
18
- slot="label">
19
- <a-icon type="bank" /> {{ group.title }}
20
- </span>
21
- <a-select-option v-for="address in group.children" :key="address.label + ' (' + address.value + ')'">
22
- <p class="addressName"><a-icon type="environment" /> <span v-html="highLight(address.label, address.word)">{{ address.label }}</span></p>
23
- <p v-if="address.address !== '[]'" class="addressRemark">
24
- {{ address.address }}
25
- </p>
26
- </a-select-option>
27
- </a-select-opt-group>
28
- </template>
29
- <a-input>
30
- <a-icon slot="suffix" class="certain-category-icon" type="search"/>
31
- </a-input>
32
- </a-auto-complete>
33
- </div>
34
- </template>
35
- <script>
36
-
37
- import { post } from '@vue2-client/services/api'
38
- import { GetGDMap } from '@vue2-client/utils/map-utils'
39
- import { debounce } from 'ant-design-vue/lib/vc-table/src/utils'
40
-
41
- export default {
42
- name: 'AddressSearchCombobox',
43
- data () {
44
- // 检索去抖
45
- this.fetchFunction = debounce(this.fetchFunction, 300)
46
- return {
47
- // 地址搜索联想
48
- mapAutocomplete: undefined,
49
- // 检索结果
50
- option: [],
51
- // 最后检索版本
52
- lastFetchId: 0,
53
- // 检索中
54
- searching: false
55
- }
56
- },
57
- model: {
58
- prop: 'searchResult',
59
- event: 'onSelect'
60
- },
61
- props: {
62
- searchResult: {
63
- type: String,
64
- default: undefined
65
- },
66
- // 返回数据格式
67
- searchResultType: {
68
- type: String,
69
- default: 'Default'
70
- // default: 'Array'
71
- // default: 'Object'
72
- },
73
- // Object 返回格式时 可以自定义key
74
- resultKeys: {
75
- type: Object,
76
- default: () => { return { address: 'address', coords: 'coords' } }
77
- }
78
- },
79
- created () {
80
- },
81
- mounted () {
82
- GetGDMap().then(aMap => {
83
- this.mapAutocomplete = new (aMap).Autocomplete({})
84
- })
85
- },
86
- methods: {
87
- onSelect (value) {
88
- let result
89
- if (this.searchResultType !== 'Default') {
90
- const _arr = value.replace(')', '').split('(')
91
- if (this.searchResultType === 'Array') {
92
- result = _arr
93
- } else {
94
- result = {}
95
- result[this.resultKeys.address] = _arr[0]
96
- result[this.resultKeys.coords] = _arr[1]
97
- }
98
- }
99
- this.$emit('onSelect', JSON.stringify(result) || value)
100
- // this.$emit('onClick', result || value)
101
- },
102
- // 懒加载检索方法
103
- fetchFunction (value) {
104
- if (value && this.mapAutocomplete) {
105
- this.searching = true
106
- this.lastFetchId += 1
107
- const fetchId = this.lastFetchId
108
- this.mapAutocomplete.search(value, (status, result) => {
109
- if (fetchId !== this.lastFetchId) {
110
- return
111
- }
112
- if (status === 'complete') {
113
- this.option = []
114
- const addressMap = {}
115
- result.tips.forEach((res) => {
116
- if (res.location) {
117
- if (!addressMap.hasOwnProperty(res.district)) {
118
- addressMap[res.district] = []
119
- }
120
- addressMap[res.district].push({
121
- label: res.name,
122
- value: res.location.lng + ',' + res.location.lat + ',',
123
- address: res.address + '',
124
- word: value
125
- })
126
- }
127
- })
128
- for (const key of Object.keys(addressMap)) {
129
- this.option.push({
130
- title: key,
131
- children: addressMap[key]
132
- })
133
- }
134
- }
135
- this.searching = false
136
- })
137
- }
138
- },
139
- // 获取数据
140
- getData (value, callback) {
141
- if (value !== '') {
142
- const logicName = this.attr.keyName
143
- const logic = logicName.substring(6)
144
- post('/webmeterapi/' + logic, value).then(res => {
145
- callback(res)
146
- })
147
- }
148
- },
149
- // 关键字高亮
150
- highLight (value, word) {
151
- // 如果标题中包含,关键字就替换一下
152
- if (value.includes(word)) {
153
- value = value.replace(word,
154
- // 这里是替换成html格式的数据,最好再加一个样式权重,保险一点
155
- '<span style="color:red!important;">' + word + '</span>'
156
- )
157
- return value
158
- // eslint-disable-next-line brace-style
159
- }
160
- // 不包含的话还用这个
161
- else {
162
- return value
163
- }
164
- }
165
- }
166
- }
167
- </script>
168
-
169
- <style>
170
- .certain-category-search-dropdown .ant-select-dropdown-menu-item-group-title {
171
- color: #666;
172
- font-weight: bold;
173
- font-size: 14px;
174
- }
175
-
176
- .certain-category-search-dropdown .ant-select-dropdown-menu-item-group {
177
- border-bottom: 1px solid #f6f6f6;
178
- }
179
-
180
- .certain-category-search-dropdown .ant-select-dropdown-menu-item {
181
- padding-left: 16px;
182
- }
183
-
184
- .certain-category-search-dropdown .ant-select-dropdown-menu-item.show-all {
185
- text-align: center;
186
- cursor: default;
187
- }
188
-
189
- .certain-category-search-dropdown .ant-select-dropdown-menu {
190
- max-height: 300px;
191
- }
192
- </style>
193
- <style scoped>
194
- .certain-category-search-wrapper
195
- >>> .certain-category-search.ant-select-auto-complete
196
- .ant-input-affix-wrapper
197
- .ant-input-suffix {
198
- right: 12px;
199
- }
200
- .certain-category-search-wrapper >>> .certain-search-item-count {
201
- position: absolute;
202
- color: #999;
203
- right: 16px;
204
- }
205
- .certain-category-search-wrapper >>> .certain-category-search.ant-select-focused,
206
- .certain-category-icon {
207
- color: #108ee9;
208
- }
209
- .certain-category-search-wrapper >>> .certain-category-icon {
210
- color: #6e6e6e;
211
- transition: all 0.3s cubic-bezier(0.645, 0.045, 0.355, 1);
212
- font-size: 16px;
213
- }
214
-
215
- .addressName {
216
- margin-bottom: 0;
217
- font-size: 14px;
218
- font-weight: bold;
219
- }
220
-
221
- .addressRemark {
222
- margin-bottom: 0;
223
- font-size: 12px;
224
- }
225
- </style>
1
+ <template>
2
+ <div class="certain-category-search-wrapper">
3
+ <a-auto-complete
4
+ :disabled="!mapAutocomplete"
5
+ :dropdown-match-select-width="false"
6
+ :dropdown-style="{ width: '400px' }"
7
+ class="certain-category-search"
8
+ dropdown-class-name="certain-category-search-dropdown"
9
+ option-label-prop="value"
10
+ placeholder="输入地址关键字搜索"
11
+ @search="fetchFunction"
12
+ @select="onSelect"
13
+ >
14
+ <a-spin v-if="searching" slot="notFoundContent" size="small" />
15
+ <template slot="dataSource">
16
+ <a-select-opt-group v-for="group in option" :key="group.title">
17
+ <span
18
+ slot="label">
19
+ <a-icon type="bank" /> {{ group.title }}
20
+ </span>
21
+ <a-select-option v-for="address in group.children" :key="address.label + ' <' + address.value + '>'">
22
+ <p class="addressName"><a-icon type="environment" /> <span v-html="highLight(address.label, address.word)">{{ address.label }}</span></p>
23
+ <p v-if="address.address !== '[]'" class="addressRemark">
24
+ {{ address.address }}
25
+ </p>
26
+ </a-select-option>
27
+ </a-select-opt-group>
28
+ </template>
29
+ <a-input>
30
+ <a-icon slot="suffix" class="certain-category-icon" type="search"/>
31
+ </a-input>
32
+ </a-auto-complete>
33
+ </div>
34
+ </template>
35
+ <script>
36
+
37
+ import { post } from '@vue2-client/services/api'
38
+ import { GetGDMap } from '@vue2-client/utils/map-utils'
39
+ import { debounce } from 'ant-design-vue/lib/vc-table/src/utils'
40
+
41
+ export default {
42
+ name: 'AddressSearchCombobox',
43
+ data () {
44
+ // 检索去抖
45
+ this.fetchFunction = debounce(this.fetchFunction, 300)
46
+ return {
47
+ // 地址搜索联想
48
+ mapAutocomplete: undefined,
49
+ // 检索结果
50
+ option: [],
51
+ // 最后检索版本
52
+ lastFetchId: 0,
53
+ // 检索中
54
+ searching: false
55
+ }
56
+ },
57
+ model: {
58
+ prop: 'searchResult',
59
+ event: 'onSelect'
60
+ },
61
+ props: {
62
+ searchResult: {
63
+ type: String,
64
+ default: undefined
65
+ },
66
+ // 返回数据格式
67
+ searchResultType: {
68
+ type: String,
69
+ default: 'Default'
70
+ // default: 'Array'
71
+ // default: 'Object'
72
+ },
73
+ // Object 返回格式时 可以自定义key
74
+ resultKeys: {
75
+ type: Object,
76
+ default: () => { return { address: 'address', coords: 'coords' } }
77
+ }
78
+ },
79
+ created () {
80
+ },
81
+ mounted () {
82
+ GetGDMap().then(aMap => {
83
+ this.mapAutocomplete = new (aMap).Autocomplete({})
84
+ })
85
+ },
86
+ methods: {
87
+ onSelect (value) {
88
+ let result
89
+ if (this.searchResultType !== 'Default') {
90
+ const _arr = value.replace('>', '').split('<')
91
+ if (this.searchResultType === 'Array') {
92
+ result = _arr
93
+ } else {
94
+ result = {}
95
+ result[this.resultKeys.address] = _arr[0]
96
+ result[this.resultKeys.coords] = _arr[1]
97
+ }
98
+ }
99
+ this.$emit('onSelect', JSON.stringify(result) || value)
100
+ // this.$emit('onClick', result || value)
101
+ },
102
+ // 懒加载检索方法
103
+ fetchFunction (value) {
104
+ if (value && this.mapAutocomplete) {
105
+ this.searching = true
106
+ this.lastFetchId += 1
107
+ const fetchId = this.lastFetchId
108
+ this.mapAutocomplete.search(value, (status, result) => {
109
+ if (fetchId !== this.lastFetchId) {
110
+ return
111
+ }
112
+ if (status === 'complete') {
113
+ this.option = []
114
+ const addressMap = {}
115
+ result.tips.forEach((res) => {
116
+ if (res.location) {
117
+ if (!addressMap.hasOwnProperty(res.district)) {
118
+ addressMap[res.district] = []
119
+ }
120
+ addressMap[res.district].push({
121
+ label: res.name,
122
+ value: res.location.lng + ',' + res.location.lat,
123
+ address: res.address + '',
124
+ word: value
125
+ })
126
+ }
127
+ })
128
+ for (const key of Object.keys(addressMap)) {
129
+ this.option.push({
130
+ title: key,
131
+ children: addressMap[key]
132
+ })
133
+ }
134
+ }
135
+ this.searching = false
136
+ })
137
+ }
138
+ },
139
+ // 获取数据
140
+ getData (value, callback) {
141
+ if (value !== '') {
142
+ const logicName = this.attr.keyName
143
+ const logic = logicName.substring(6)
144
+ post('/webmeterapi/' + logic, value).then(res => {
145
+ callback(res)
146
+ })
147
+ }
148
+ },
149
+ // 关键字高亮
150
+ highLight (value, word) {
151
+ // 如果标题中包含,关键字就替换一下
152
+ if (value.includes(word)) {
153
+ value = value.replace(word,
154
+ // 这里是替换成html格式的数据,最好再加一个样式权重,保险一点
155
+ '<span style="color:red!important;">' + word + '</span>'
156
+ )
157
+ return value
158
+ // eslint-disable-next-line brace-style
159
+ }
160
+ // 不包含的话还用这个
161
+ else {
162
+ return value
163
+ }
164
+ }
165
+ }
166
+ }
167
+ </script>
168
+
169
+ <style>
170
+ .certain-category-search-dropdown .ant-select-dropdown-menu-item-group-title {
171
+ color: #666;
172
+ font-weight: bold;
173
+ font-size: 14px;
174
+ }
175
+
176
+ .certain-category-search-dropdown .ant-select-dropdown-menu-item-group {
177
+ border-bottom: 1px solid #f6f6f6;
178
+ }
179
+
180
+ .certain-category-search-dropdown .ant-select-dropdown-menu-item {
181
+ padding-left: 16px;
182
+ }
183
+
184
+ .certain-category-search-dropdown .ant-select-dropdown-menu-item.show-all {
185
+ text-align: center;
186
+ cursor: default;
187
+ }
188
+
189
+ .certain-category-search-dropdown .ant-select-dropdown-menu {
190
+ max-height: 300px;
191
+ }
192
+ </style>
193
+ <style scoped>
194
+ .certain-category-search-wrapper
195
+ >>> .certain-category-search.ant-select-auto-complete
196
+ .ant-input-affix-wrapper
197
+ .ant-input-suffix {
198
+ right: 12px;
199
+ }
200
+ .certain-category-search-wrapper >>> .certain-search-item-count {
201
+ position: absolute;
202
+ color: #999;
203
+ right: 16px;
204
+ }
205
+ .certain-category-search-wrapper >>> .certain-category-search.ant-select-focused,
206
+ .certain-category-icon {
207
+ color: #108ee9;
208
+ }
209
+ .certain-category-search-wrapper >>> .certain-category-icon {
210
+ color: #6e6e6e;
211
+ transition: all 0.3s cubic-bezier(0.645, 0.045, 0.355, 1);
212
+ font-size: 16px;
213
+ }
214
+
215
+ .addressName {
216
+ margin-bottom: 0;
217
+ font-size: 14px;
218
+ font-weight: bold;
219
+ }
220
+
221
+ .addressRemark {
222
+ margin-bottom: 0;
223
+ font-size: 12px;
224
+ }
225
+ </style>
@@ -35,7 +35,7 @@
35
35
  <a-form-model-item
36
36
  v-if="item.formType ==='addressSearch'"
37
37
  label="坐标字段名">
38
- <a-input :value="`${item.key}_coords`" :disabled="true">
38
+ <a-input :value="`${item.key}_lng_lat`" :disabled="true">
39
39
  <a-popover slot="suffix" placement="bottom" title="坐标字段名">
40
40
  <template slot="content">
41
41
  <p>表单类型为地点搜索框时:</p>
@@ -35,7 +35,7 @@
35
35
  <a-form-model-item
36
36
  v-if="item.formType ==='addressSearch'"
37
37
  label="坐标字段名">
38
- <a-input :value="`${item.key}_coords`" :disabled="true">
38
+ <a-input :value="`${item.key}_lng_lat`" :disabled="true">
39
39
  <a-popover slot="suffix" placement="bottom" title="坐标字段名">
40
40
  <template slot="content">
41
41
  <p>表单类型为地点搜索框时:</p>
@@ -217,7 +217,7 @@
217
217
  v-model="searchResult"
218
218
  searchResultType="Object"
219
219
  @onSelect="form=Object.assign(form,JSON.parse(searchResult))"
220
- :resultKeys="{ address: attr.model, coords: `${attr.model}_coords` }"
220
+ :resultKeys="{ address: attr.model, coords: `${attr.model}_lng_lat` }"
221
221
  ></address-search-combobox>
222
222
  </a-form-model-item>
223
223
  </x-form-col>
@@ -1,6 +1,6 @@
1
1
  import { manageApi, post } from '@vue2-client/services/api'
2
2
  import { handleTree } from '@vue2-client/utils/util'
3
- const setting = require('../../config/default/setting.config')
3
+
4
4
  const GetAppDataService = {
5
5
  install (Vue) {
6
6
  // 给vue增添对话框显示方法
@@ -9,8 +9,10 @@ const GetAppDataService = {
9
9
  async load () {
10
10
  const params = {}
11
11
  await post(manageApi.getDictionaryValue, {}).then((res) => {
12
+ // 从本地缓存中读取compatible
13
+ const setting = localStorage.getItem('compatible')
12
14
  // 判断是否是V4环境
13
- if (setting.compatible === 'V4') {
15
+ if (setting === 'V4') {
14
16
  // 如果是V4,从返回值中,data取值
15
17
  Object.assign(params, res.data)
16
18
  } else {
@@ -116,9 +116,11 @@ export default {
116
116
  const password = this.form.getFieldValue('password')
117
117
  this.logging = false
118
118
  const loginRes = res
119
- const V4Token = { token: res.data.access_token, expire: res.data.expires_in }
119
+ const V4Token = { token: res.access_token, expire: res.expires_in }
120
120
  this.setV4AccessToken(V4Token)
121
- if (loginRes.code === 200) {
121
+ // 向本地缓存中临时存储compatible
122
+ localStorage.setItem('compatible', this.compatible)
123
+ if (loginRes.access_token) {
122
124
  const encrypt = new JSEncrypt()
123
125
  encrypt.setPublicKey('MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCqPvovSfXcwBbW8cKMCgwqNpsYuzF8RPAPFb7LGsnVo44JhM/xxzDyzoYtdfNmtbIuKVi9PzIsyp6rg+09gbuI6UGwBZ5DWBDBMqv5MPdOF5dCQkB2Bbr5yPfURPENypUz+pBFBg41d+BC+rwRiXELwKy7Y9caD/MtJyHydj8OUwIDAQAB')
124
126
  const data = encrypt.encrypt(JSON.stringify({ username: name, password: password }))
@@ -1,28 +1,31 @@
1
- import AMapLoader from '@amap/amap-jsapi-loader'
2
- let Amap
3
- async function GetGDMap () {
4
- if (!Amap) {
5
- Amap = await AMapLoader.load({
6
- key: '4889f1e58df01cb40415536c8907bf64', // 申请好的Web端开发者Key,首次调用 load 时必填
7
- version: '1.4.2', // 指定要加载的 JSAPI 的版本,缺省时默认为 1.4.15
8
- plugins: ['AMap.ToolBar', 'AMap.Geolocation', 'AMap.Geocoder', 'AMap.MarkerClusterer', 'AMap.Autocomplete'] // 需要使用的的插件列表,如比例尺'AMap.Scale'等
9
- })
10
- }
11
- return Amap
12
- }
13
- async function GetLocation (address) {
14
- return new Promise(async (resolve, reject) => {
15
- new (await GetGDMap()).Geocoder({
16
- radius: 500 // 范围,默认:500
17
- }).getLocation(address, function (status, result) {
18
- console.log(result)
19
- if (status === 'complete' && result.geocodes.length) {
20
- resolve({ lng: result.geocodes[0].location.lng, lat: result.geocodes[0].location.lat })
21
- } else {
22
- // eslint-disable-next-line prefer-promise-reject-errors
23
- reject('根据经纬度查询地址失败')
24
- }
25
- })
26
- })
27
- }
28
- export { GetGDMap, GetLocation }
1
+ import AMapLoader from '@amap/amap-jsapi-loader'
2
+ let Amap
3
+ async function GetGDMap () {
4
+ if (!Amap) {
5
+ window._AMapSecurityConfig = {
6
+ securityJsCode:'275e59edb26ab1f917cfe7f05bea7979'
7
+ }
8
+ Amap = await AMapLoader.load({
9
+ key: '55a4807a6fc3adca5510f69578b1ae4a', // 申请好的Web端开发者Key,首次调用 load 时必填
10
+ version: '1.4.2', // 指定要加载的 JSAPI 的版本,缺省时默认为 1.4.15
11
+ plugins: ['AMap.ToolBar', 'AMap.Geolocation', 'AMap.Geocoder', 'AMap.MarkerClusterer', 'AMap.Autocomplete'], // 需要使用的的插件列表,如比例尺'AMap.Scale'等
12
+ })
13
+ }
14
+ return Amap
15
+ }
16
+ async function GetLocation (address) {
17
+ return new Promise(async (resolve, reject) => {
18
+ new (await GetGDMap()).Geocoder({
19
+ radius: 500 // 范围,默认:500
20
+ }).getLocation(address, function (status, result) {
21
+ console.log(result)
22
+ if (status === 'complete' && result.geocodes.length) {
23
+ resolve({ lng: result.geocodes[0].location.lng, lat: result.geocodes[0].location.lat })
24
+ } else {
25
+ // eslint-disable-next-line prefer-promise-reject-errors
26
+ reject('根据经纬度查询地址失败')
27
+ }
28
+ })
29
+ })
30
+ }
31
+ export { GetGDMap, GetLocation }
@@ -171,7 +171,16 @@ function loadInterceptors () {
171
171
  }, errorHandler)
172
172
  // 加载响应拦截器
173
173
  axios.interceptors.response.use((response) => {
174
- return response.data
174
+ // 判断是否为V4环境
175
+ if (setting.compatible === 'V4') {
176
+ if (response.data.data) {
177
+ return response.data.data
178
+ } else {
179
+ return response.data
180
+ }
181
+ } else {
182
+ return response.data
183
+ }
175
184
  }, errorHandler)
176
185
  }
177
186
 
@@ -181,12 +190,12 @@ const errorHandler = (error) => {
181
190
  const data = error.response.data
182
191
  // 从 localstorage 获取 token
183
192
  const token = localStorage.getItem(ACCESS_TOKEN)
184
- if (error.response.status === 403) {
193
+ if (error.response.status === 403 || data.code === 403) {
185
194
  notification.error({
186
195
  message: '禁止访问',
187
196
  description: data
188
197
  })
189
- } else if (error.response.status === 401 && !(data.result && data.result.isLogin)) {
198
+ } else if ((error.response.status === 401 || data.code === 401) && !(data.result && data.result.isLogin)) {
190
199
  notification.error({
191
200
  message: '鉴权失败',
192
201
  description: data
@@ -198,7 +207,7 @@ const errorHandler = (error) => {
198
207
  }, 1500)
199
208
  })
200
209
  }
201
- } else if (error.response.status === 500) {
210
+ } else if (error.response.status === 500 || data.code === 500) {
202
211
  notification.error({
203
212
  message: '系统异常',
204
213
  description: data