@bytenew/bn-bus-ui 1.1.462 → 1.1.463
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/install.js +134 -0
- package/package.json +20 -4
- package/packages/BnAddress/index.vue +141 -0
- package/packages/BnAddressParse/index.vue +75 -0
- package/packages/BnAdvancedFilter/BnFilterView.vue +145 -0
- package/packages/BnAdvancedFilter/index.vue +345 -0
- package/packages/BnAdvancedFilter/util.js +171 -0
- package/packages/BnCascader/BnCascader.vue +543 -0
- package/packages/BnCascader/BnCascaderPanel.vue +1331 -0
- package/packages/BnCascader/cascaderDisplay.js +102 -0
- package/packages/BnCheck/BnCheck.vue +253 -0
- package/packages/BnColumnConfig/columnConfigDialog.vue +134 -0
- package/packages/BnColumnConfig/component/childrenFormSetting/assocTable.vue +143 -0
- package/packages/BnColumnConfig/component/childrenFormSetting/assocTableSearch.vue +314 -0
- package/packages/BnColumnConfig/component/childrenFormSetting/index.vue +243 -0
- package/packages/BnColumnConfig/component/defaultSet/defaultSet.vue +114 -0
- package/packages/BnColumnConfig/component/defaultSet/stringDefault.vue +210 -0
- package/packages/BnColumnConfig/component/funcExprDialog/funcExprDialog.vue +126 -0
- package/packages/BnColumnConfig/component/packageFilter/index.vue +141 -0
- package/packages/BnColumnConfig/component/paraExplainSet/index.vue +156 -0
- package/packages/BnColumnConfig/component/setOption/setOption.vue +321 -0
- package/packages/BnColumnConfig/component/setRelationOption/ConditionList.vue +277 -0
- package/packages/BnColumnConfig/component/setRelationOption/LevelHeader.vue +144 -0
- package/packages/BnColumnConfig/component/setRelationOption/setRelationOption.vue +642 -0
- package/packages/BnColumnConfig/data.js +129 -0
- package/packages/BnColumnConfig/index.scss +23 -0
- package/packages/BnColumnConfig/index.vue +309 -0
- package/packages/BnCondVal/BnCondVal.vue +112 -0
- package/packages/BnCondVal/itemVal/dateRegVal.vue +39 -0
- package/packages/BnCondVal/itemVal/dateVal.vue +39 -0
- package/packages/BnCondVal/itemVal/numRegVal.vue +67 -0
- package/packages/BnCondVal/itemVal/numVal.vue +44 -0
- package/packages/BnCondVal/itemVal/relationVal.vue +73 -0
- package/packages/BnCondVal/itemVal/selectColumnVal.vue +58 -0
- package/packages/BnCondVal/itemVal/selectVal.vue +59 -0
- package/packages/BnCondVal/itemVal/stringVal.vue +156 -0
- package/packages/BnCondition/index.vue +551 -0
- package/packages/BnCondition/util.js +232 -0
- package/packages/BnDatePicker/BnDatePicker.vue +194 -0
- package/packages/BnDrop/BnDrop.vue +917 -0
- package/packages/BnEmptyTip/BnEmptyTip.vue +107 -0
- package/packages/BnExportOrder/BnExportOrder.vue +241 -0
- package/packages/BnExportOrder/validatorCode.vue +94 -0
- package/packages/BnFileView/BnFileView.vue +271 -0
- package/packages/BnFileView/FileDetail.vue +125 -0
- package/packages/BnFileView/videoPreview.vue +70 -0
- package/packages/BnFilterOption/BnFilterOption.vue +160 -0
- package/packages/BnFunExpr/BnFunExpr.vue +608 -0
- package/packages/BnImportOrder/BnImportOrder.vue +323 -0
- package/packages/BnImportTemplate/BnImportTemplate.vue +866 -0
- package/packages/BnImportTemplate/assets/merge_tip_img.png +0 -0
- package/packages/BnImportTemplate/assets/sheet_tip.png +0 -0
- package/packages/BnImportTemplate/assets/xls.png +0 -0
- package/packages/BnImportTemplate/components/ImportTemplateTrigger.vue +198 -0
- package/packages/BnImportTemplate/components/TemplateEditDialog.vue +340 -0
- package/packages/BnImportTemplate/components/TemplateFieldsConfig.vue +401 -0
- package/packages/BnImportTemplate/components/TemplateListDialog.vue +297 -0
- package/packages/BnInpNum/BnInpNum.vue +165 -0
- package/packages/BnMenus/BnMenus.vue +502 -0
- package/packages/BnMenus/MenuItem.vue +321 -0
- package/packages/BnOrderCard/BnOrderCard.vue +389 -0
- package/packages/BnOrderCard/orderRemark.vue +178 -0
- package/packages/BnOrderCard/util.js +94 -0
- package/packages/BnOrderDetail/BnOrderDetail.vue +338 -0
- package/packages/BnOrderDetail/filterLogByUser.vue +108 -0
- package/packages/BnOrderDetail/orderLogs.vue +53 -0
- package/packages/BnOrderDetail/showSubForm/index.vue +41 -0
- package/packages/BnOrderDetail/showSubForm/showChildTable.vue +61 -0
- package/packages/BnOrderDetail/showSubForm/showTimeLine.vue +131 -0
- package/packages/BnOrderDetail/showSubForm/tableCellCopy.vue +84 -0
- package/packages/BnOrderShare/index.vue +378 -0
- package/packages/BnOrderShare/shareUrlInp.vue +54 -0
- package/packages/BnRadio/BnRadio.vue +181 -0
- package/packages/BnRelation/BnRelation.vue +120 -0
- package/packages/BnSelect/BnSelect.vue +485 -0
- package/packages/BnSmartForm/BnBatchForm.vue +334 -0
- package/packages/BnSmartForm/BnBatchFormDialog.vue +423 -0
- package/packages/BnSmartForm/BnSmartElf/elfLog/index.vue +57 -0
- package/packages/BnSmartForm/BnSmartElf/index.vue +95 -0
- package/packages/BnSmartForm/BnSmartFormPsychic.js +629 -0
- package/packages/BnSmartForm/BnSmartFormUtil.js +524 -0
- package/packages/BnSmartForm/addressForm/index.vue +73 -0
- package/packages/BnSmartForm/checkboxForm/index.vue +99 -0
- package/packages/BnSmartForm/childrenForm/childFormFile.vue +237 -0
- package/packages/BnSmartForm/childrenForm/childrenFormBody.vue +260 -0
- package/packages/BnSmartForm/childrenForm/index.vue +110 -0
- package/packages/BnSmartForm/childrenForm/searchInventory.vue +115 -0
- package/packages/BnSmartForm/chooseAssocTable/chooseAssocTable.vue +451 -0
- package/packages/BnSmartForm/chooseAssocTable/chooseChildGood.vue +229 -0
- package/packages/BnSmartForm/chooseAssocTable/tableCellCopy.vue +84 -0
- package/packages/BnSmartForm/chooseChildOrder/chooseChildOrder.vue +158 -0
- package/packages/BnSmartForm/chooseIPaasData/chooseIPaasData.vue +307 -0
- package/packages/BnSmartForm/chooseIPaasData/tableCellCopy.vue +84 -0
- package/packages/BnSmartForm/choosePackage/choosePackage.vue +361 -0
- package/packages/BnSmartForm/dateDualForm/index.vue +37 -0
- package/packages/BnSmartForm/dateForm/index.vue +38 -0
- package/packages/BnSmartForm/fileForm/fileFormData.js +50 -0
- package/packages/BnSmartForm/fileForm/index.vue +240 -0
- package/packages/BnSmartForm/formItemFooter/formItemFooter.vue +38 -0
- package/packages/BnSmartForm/formItemTop/formItemTop.vue +42 -0
- package/packages/BnSmartForm/index.vue +1201 -0
- package/packages/BnSmartForm/numberForm/index.vue +63 -0
- package/packages/BnSmartForm/radioForm/index.vue +72 -0
- package/packages/BnSmartForm/receiveForm/index.vue +112 -0
- package/packages/BnSmartForm/relationForm/index.vue +82 -0
- package/packages/BnSmartForm/scoreForm/index.vue +39 -0
- package/packages/BnSmartForm/selectForm/index.vue +55 -0
- package/packages/BnSmartForm/showValForm/index.vue +42 -0
- package/packages/BnSmartForm/showValForm/showValFormTable.vue +104 -0
- package/packages/BnSmartForm/smartFormsCommon.scss +43 -0
- package/packages/BnSmartForm/stringForm/index.vue +170 -0
- package/packages/BnVirtPopover/index.vue +319 -0
- package/packages/BnWebLog/BnWebLog.vue +140 -0
- package/packages/BnWorkSettingDrop/advancedOptions.js +112 -0
- package/packages/BnWorkSettingDrop/benBenAIUtil.js +89 -0
- package/packages/BnWorkSettingDrop/index.vue +292 -0
- package/packages/font/iconfont.css +243 -0
- package/packages/font/iconfont.ttf +0 -0
- package/packages/font/iconfont.woff +0 -0
- package/packages/font/iconfont.woff2 +0 -0
- package/utils/addressParse-old.js +645 -0
- package/utils/addressParse.js +735 -0
- package/utils/config.js +68 -0
- package/utils/index.js +1171 -0
- package/dist/assocTableSearch-CmzOXI5w.js +0 -349
- package/dist/assocTableSearch.css +0 -1
- package/dist/bn-bus-ui.es.js +0 -65
- package/dist/bn-bus-ui.umd.js +0 -49
- package/dist/chooseIPaasData-jkTJEMKT.js +0 -391
- package/dist/chooseIPaasData.css +0 -1
- package/dist/defaultSet-CiYuSOzT.js +0 -297
- package/dist/defaultSet.css +0 -1
- package/dist/fileFormData-D_Q1vylE.js +0 -53
- package/dist/formItemFooter-BpnVUUgV.js +0 -108
- package/dist/formItemFooter.css +0 -1
- package/dist/funcExprDialog-BMc-n5FL.js +0 -139
- package/dist/funcExprDialog.css +0 -1
- package/dist/index-8GQJARcF.js +0 -44
- package/dist/index-8apT0r8m.js +0 -66
- package/dist/index-BOFu3qAH.js +0 -183
- package/dist/index-BSKXuSid.js +0 -89
- package/dist/index-BhYvDd_Q.js +0 -45
- package/dist/index-BhqkeVFc.js +0 -45
- package/dist/index-CK7_Ou7F.js +0 -89
- package/dist/index-Cfb8D3Fg.js +0 -58
- package/dist/index-D1fGD0mX.js +0 -51
- package/dist/index-DE_eQGbT.js +0 -746
- package/dist/index-DfgiBqzS.js +0 -221
- package/dist/index-Dobi0ms9.js +0 -66
- package/dist/index-DuyQNxe0.js +0 -118
- package/dist/index-DxpJkrN7.js +0 -64
- package/dist/index-FGHeG46m.js +0 -109
- package/dist/index-P2M7CUTe.js +0 -178
- package/dist/index-xCz2zysE.js +0 -135
- package/dist/index.css +0 -1
- package/dist/index2.css +0 -1
- package/dist/index3.css +0 -1
- package/dist/index4.css +0 -1
- package/dist/index5.css +0 -1
- package/dist/index6.css +0 -1
- package/dist/index7.css +0 -1
- package/dist/install--7IU60oV.js +0 -23103
- package/dist/install.css +0 -1
- package/dist/setOption-DehYZpZr.js +0 -329
- package/dist/setOption.css +0 -1
- package/dist/setRelationOption-BL-AFUoF.js +0 -5217
- package/dist/setRelationOption.css +0 -1
|
@@ -0,0 +1,645 @@
|
|
|
1
|
+
let defaultData = []; //不包括省市级code的数据
|
|
2
|
+
|
|
3
|
+
const mCity = {}; //以市为层级的数据 里面包括 p:省 c:市 a:区列表
|
|
4
|
+
|
|
5
|
+
const mArea = {}; //以区为级别的数据 里面包括 p:省 c:市
|
|
6
|
+
|
|
7
|
+
const mStreet = {}; //以街道为级别的数据 里面包括 c:市 a:区
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* 处理原始地址数据转换成专用数据
|
|
11
|
+
* @param list 原始数据
|
|
12
|
+
* @param init 是否初始化 如传空 已转换过不会再次转换
|
|
13
|
+
* @returns {boolean}
|
|
14
|
+
*/
|
|
15
|
+
function parseArea(list, init) {
|
|
16
|
+
if (!init && defaultData.length) {
|
|
17
|
+
return true;
|
|
18
|
+
}
|
|
19
|
+
defaultData = list;
|
|
20
|
+
defaultData.forEach(province => {
|
|
21
|
+
if (province.city) {
|
|
22
|
+
province.city.forEach(city => {
|
|
23
|
+
if (city.name !== '其他') {
|
|
24
|
+
if (!mCity[city.name]) {
|
|
25
|
+
mCity[city.name] = [];
|
|
26
|
+
}
|
|
27
|
+
mCity[city.name].push({
|
|
28
|
+
p: province.name,
|
|
29
|
+
c: city.name,
|
|
30
|
+
a: city.area || [],
|
|
31
|
+
s: city.street || [],
|
|
32
|
+
});
|
|
33
|
+
}
|
|
34
|
+
if (city.area) {
|
|
35
|
+
city.area.forEach(area => {
|
|
36
|
+
if (area !== '其他') {
|
|
37
|
+
if (!mArea[area]) {
|
|
38
|
+
mArea[area] = [];
|
|
39
|
+
}
|
|
40
|
+
mArea[area].push({
|
|
41
|
+
p: province.name,
|
|
42
|
+
c: city.name
|
|
43
|
+
})
|
|
44
|
+
}
|
|
45
|
+
if (city.street && city.street[area]) {
|
|
46
|
+
city.street[area].forEach(street => {
|
|
47
|
+
if (street !== '其他') {
|
|
48
|
+
if (!mStreet[street]) {
|
|
49
|
+
mStreet[street] = [];
|
|
50
|
+
}
|
|
51
|
+
mStreet[street].push({
|
|
52
|
+
c: city.name,
|
|
53
|
+
a: area
|
|
54
|
+
})
|
|
55
|
+
}
|
|
56
|
+
})
|
|
57
|
+
}
|
|
58
|
+
})
|
|
59
|
+
}
|
|
60
|
+
})
|
|
61
|
+
}
|
|
62
|
+
});
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* 解析地址详情(内部方法,需先调用 parseArea 初始化地址库)
|
|
67
|
+
* @param address 任意地址字符串
|
|
68
|
+
* @param sourceData 组件配置,如 extraInfo.isFourAddress
|
|
69
|
+
* @returns {{name: string, mobile: string, detail: string, zip_code: string, phone: string}}
|
|
70
|
+
*/
|
|
71
|
+
function parseAddressDetail(address, sourceData) {
|
|
72
|
+
const parse = {
|
|
73
|
+
name: '',
|
|
74
|
+
mobile: '',
|
|
75
|
+
detail: '',
|
|
76
|
+
zip_code: '',
|
|
77
|
+
phone: '',
|
|
78
|
+
extensionNumber:'', // 淘宝分机号码
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
address = joinAddressLines(address);
|
|
82
|
+
var presetName = address.name;
|
|
83
|
+
address = stripAddressLabels(address.text);
|
|
84
|
+
|
|
85
|
+
const search = ['详细地址', '收货地址', '联系地址', '收件地址', '邮政编码', '手机号码', '联系电话', '联系方式', '收货人', '收件人', '联系人', '姓名', '名字', '手机号', '邮编', '收货', '地址', '详细', '电话', '固话', ':', ':', ';', ';', ',', ',', '。',];
|
|
86
|
+
search.forEach(str => {
|
|
87
|
+
address = address.replace(new RegExp(str, 'g'), ' ')
|
|
88
|
+
});
|
|
89
|
+
|
|
90
|
+
address = address.replace(/ {2,}/g, ' ');
|
|
91
|
+
|
|
92
|
+
address = address.replace(/(\d{3})-(\d{4})-(\d{4})/g, '$1$2$3');
|
|
93
|
+
|
|
94
|
+
address = address.replace(/(\d{3}) (\d{4}) (\d{4})/g, '$1$2$3');
|
|
95
|
+
|
|
96
|
+
// const mobileReg = /(86-[1][0-9]{10})|(86[1][0-9]{10})|([1][0-9]{10})/g;
|
|
97
|
+
const mobileReg = /([1][0-9]{10}((-[0-9]{4})?))|((86-?)?[1][0-9]{10})/g;
|
|
98
|
+
const mobile = mobileReg.exec(address);
|
|
99
|
+
if (mobile) {
|
|
100
|
+
parse.mobile = mobile[0];
|
|
101
|
+
address = address.replace(mobile[0], ' ')
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
const phoneReg = /(([0-9]{3,4}-)[0-9]{7,8})|([0-9]{12})|([0-9]{11})|([0-9]{10})|([0-9]{9})|([0-9]{8})|([0-9]{7})/g;
|
|
105
|
+
const phone = phoneReg.exec(address);
|
|
106
|
+
if (phone) {
|
|
107
|
+
//获取分机号码 例:16601795913-9385(11位手机号-xxxx)
|
|
108
|
+
var addressArry = address.split(' ')
|
|
109
|
+
var ext = addressArry.filter((item) => (item.length == 16 && item.indexOf('-')));
|
|
110
|
+
if(ext.length>0){
|
|
111
|
+
//截取分机号赋值
|
|
112
|
+
parse.extensionNumber = ext[0].split('-')[1]
|
|
113
|
+
//空格替换分机号
|
|
114
|
+
var extVal = '-'+parse.extensionNumber
|
|
115
|
+
address = address.replace(extVal, ' ')
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
|
|
119
|
+
parse.phone = phone[0];
|
|
120
|
+
address = address.replace(phone[0], ' ')
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
const zipReg = /([0-9]{6})/g;
|
|
124
|
+
const zip = zipReg.exec(address);
|
|
125
|
+
if (zip) {
|
|
126
|
+
parse.zip_code = zip[0];
|
|
127
|
+
address = address.replace(zip[0], '')
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
address = address.replace(/ {2,}/, ' ');
|
|
131
|
+
|
|
132
|
+
let detail = detail_parse_forward(address.trim(), sourceData);
|
|
133
|
+
if (!detail.city) {
|
|
134
|
+
detail = detail_parse(address.trim());
|
|
135
|
+
if (detail.area && !detail.city) {
|
|
136
|
+
detail = detail_parse(address.trim(), {
|
|
137
|
+
ignoreArea: true
|
|
138
|
+
});
|
|
139
|
+
// console.log('smart_parse->ignoreArea');
|
|
140
|
+
} else {
|
|
141
|
+
// console.log('smart_parse');
|
|
142
|
+
}
|
|
143
|
+
//这个待完善
|
|
144
|
+
const list = address.replace(detail.province, '').replace(detail.city, '').replace(detail.area, '').split(' ').filter(str => str);
|
|
145
|
+
if (list.length > 1) {
|
|
146
|
+
list.forEach(str => {
|
|
147
|
+
if (!parse.name || str && str.length < parse.name.length) {
|
|
148
|
+
parse.name = str.trim()
|
|
149
|
+
}
|
|
150
|
+
});
|
|
151
|
+
if (parse.name) {
|
|
152
|
+
detail.addr = detail.addr.replace(parse.name, '').trim()
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
} else {
|
|
156
|
+
if (detail.name) {
|
|
157
|
+
parse.name = detail.name
|
|
158
|
+
} else {
|
|
159
|
+
const list = detail.addr.split(' ').filter(str => str);
|
|
160
|
+
if (list.length > 1) {
|
|
161
|
+
parse.name = list[list.length - 1]
|
|
162
|
+
}
|
|
163
|
+
//详细地址中去掉 姓名
|
|
164
|
+
if (parse.name) {
|
|
165
|
+
detail.addr = detail.addr.replace(parse.name, '').trim()
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
//将分机号自动粘贴在收件人姓名后
|
|
170
|
+
if(parse.extensionNumber){
|
|
171
|
+
parse.name = parse.name+'[转'+parse.extensionNumber+']'
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
parse.province = detail.province;
|
|
176
|
+
parse.city = detail.city;
|
|
177
|
+
parse.area = detail.area;
|
|
178
|
+
parse.street = detail.street;
|
|
179
|
+
parse.addr = detail.addr;
|
|
180
|
+
parse.result = detail.result;
|
|
181
|
+
|
|
182
|
+
if (presetName) {
|
|
183
|
+
parse.name = presetName;
|
|
184
|
+
if (parse.addr) {
|
|
185
|
+
parse.addr = parse.addr.replace(presetName, '').trim();
|
|
186
|
+
}
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
if (parse.province === "澳门" || parse.province === "香港") {
|
|
190
|
+
parse.province += "特别行政区"
|
|
191
|
+
} else if (parse.province === "新疆") {
|
|
192
|
+
parse.province = "新疆维吾尔自治区"
|
|
193
|
+
} else if (parse.province === "西藏") {
|
|
194
|
+
parse.province = "西藏自治区"
|
|
195
|
+
} else if (parse.province === "广西") {
|
|
196
|
+
parse.province = "广西壮族自治区"
|
|
197
|
+
} else if (parse.province === "宁夏") {
|
|
198
|
+
parse.province = "宁夏回族自治区"
|
|
199
|
+
} else if (parse.province === "内蒙古") {
|
|
200
|
+
parse.province = "内蒙古自治区"
|
|
201
|
+
} else {
|
|
202
|
+
if ("北京市上海市天津市重庆市".indexOf(parse.province) === -1) {
|
|
203
|
+
// parse.province += "省";
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
if (parse.city.indexOf("市") === -1) {
|
|
207
|
+
// parse.city += "市";
|
|
208
|
+
}
|
|
209
|
+
return parse;
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
/**
|
|
213
|
+
* 正向解析模式
|
|
214
|
+
* 从前到后按 province city addr 逐级筛选
|
|
215
|
+
* 有city的值即可说明解析成功
|
|
216
|
+
* 此模式对地址顺序有要求
|
|
217
|
+
* @param address
|
|
218
|
+
* @returns {{province: string, city: string, area: string, addr: string}}
|
|
219
|
+
*/
|
|
220
|
+
function detail_parse_forward(address, sourceData) {
|
|
221
|
+
const parse = {
|
|
222
|
+
province: '',
|
|
223
|
+
city: '',
|
|
224
|
+
area: '',
|
|
225
|
+
street: '',
|
|
226
|
+
addr: '',
|
|
227
|
+
name: '',
|
|
228
|
+
};
|
|
229
|
+
const addressCopy = address;
|
|
230
|
+
const provinceKey = ['特别行政区', '古自治区', '维吾尔自治区', '壮族自治区', '回族自治区', '自治区', '省省直辖', '省', '市'];
|
|
231
|
+
const cityKey = ['布依族苗族自治州', '苗族侗族自治州', '自治州', '州', '市', '县'];
|
|
232
|
+
|
|
233
|
+
for (let i in defaultData) {
|
|
234
|
+
const province = defaultData[i];
|
|
235
|
+
const provinceSimple = province.name.replace('省','')
|
|
236
|
+
let index = address.indexOf(province.name);
|
|
237
|
+
if(index == -1){
|
|
238
|
+
if(address.indexOf(provinceSimple)>-1){
|
|
239
|
+
// address= address.replace(provinceSimple,province.name);
|
|
240
|
+
index = address.indexOf(provinceSimple);
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
if (index > -1) {
|
|
244
|
+
if (index > 0) {
|
|
245
|
+
//省份不是在第一位,在省份之前的字段识别为名称
|
|
246
|
+
parse.name = address.substr(0, index).trim();
|
|
247
|
+
}
|
|
248
|
+
parse.province = province.name;
|
|
249
|
+
address = address.substr(index + provinceSimple.length);
|
|
250
|
+
for (let k in provinceKey) {
|
|
251
|
+
if (address.indexOf(provinceKey[k]) === 0) {
|
|
252
|
+
address = address.substr(provinceKey[k].length);
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
for (let j in province.city) {
|
|
256
|
+
const city = province.city[j];
|
|
257
|
+
index = address.indexOf(city.name);
|
|
258
|
+
const citySimple = city.name.replace('市','')
|
|
259
|
+
if(index == -1){
|
|
260
|
+
if(address.indexOf(citySimple)>-1){
|
|
261
|
+
// address= address.replace(citySimple,city.name);
|
|
262
|
+
index = address.indexOf(citySimple);
|
|
263
|
+
}
|
|
264
|
+
}
|
|
265
|
+
if (index > -1 && index < 3) {
|
|
266
|
+
parse.city = city.name;
|
|
267
|
+
address = address.substr(index + citySimple.length);
|
|
268
|
+
for (let k in cityKey) {
|
|
269
|
+
if (address.indexOf(cityKey[k]) === 0) {
|
|
270
|
+
address = address.substr(cityKey[k].length);
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
if (city.area) {
|
|
274
|
+
// 对区域进行排序,优先匹配较长的区域名(如:临澧县优先于澧县)
|
|
275
|
+
const sortedAreas = [...city.area].sort((a, b) => b.length - a.length);
|
|
276
|
+
for (let k in sortedAreas) {
|
|
277
|
+
const area = sortedAreas[k];
|
|
278
|
+
index = address.indexOf(area);
|
|
279
|
+
if (index > -1 && index < 3) {
|
|
280
|
+
parse.area = area;
|
|
281
|
+
address = address.substr(index + parse.area.length);
|
|
282
|
+
if (city.street && city.street[area] && sourceData && sourceData.extraInfo && sourceData.extraInfo.isFourAddress) {
|
|
283
|
+
for (let m in city.street[area]) {
|
|
284
|
+
const street = city.street[area][m];
|
|
285
|
+
let indexStreet = address.indexOf(street);
|
|
286
|
+
if (indexStreet > -1) {
|
|
287
|
+
parse.street = street;
|
|
288
|
+
address = address.substr(indexStreet + parse.street.length);
|
|
289
|
+
break;
|
|
290
|
+
}
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
break;
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
}
|
|
297
|
+
break;
|
|
298
|
+
}
|
|
299
|
+
}
|
|
300
|
+
parse.addr = address.trim();
|
|
301
|
+
if(parse.city){
|
|
302
|
+
break;
|
|
303
|
+
}else if(parse.province){
|
|
304
|
+
address = addressCopy;
|
|
305
|
+
}
|
|
306
|
+
}
|
|
307
|
+
}
|
|
308
|
+
return parse;
|
|
309
|
+
}
|
|
310
|
+
|
|
311
|
+
/**
|
|
312
|
+
* 逆向解析 从后【县,区,旗】往前解析
|
|
313
|
+
* 有地区就能大概返回地址了
|
|
314
|
+
* @param address
|
|
315
|
+
* @param ignoreArea 是否忽视区 因为地址中含有区容易导致匹配错误 例:山东省蓬莱市黄海花园东区西门宝威学堂 曲荣声收15753572456
|
|
316
|
+
* @returns {{province: string, city: string, area: string, name: string, _area: string, addr: string}}
|
|
317
|
+
*/
|
|
318
|
+
function detail_parse(address, {ignoreArea = false} = {}) {
|
|
319
|
+
const parse = {
|
|
320
|
+
province: '',
|
|
321
|
+
city: '',
|
|
322
|
+
area: '',
|
|
323
|
+
name: '',
|
|
324
|
+
_area: '',
|
|
325
|
+
addr: '',
|
|
326
|
+
};
|
|
327
|
+
let areaIndex = -1,
|
|
328
|
+
cityIndex = -1;
|
|
329
|
+
|
|
330
|
+
address = address.replace(' ', ' ');
|
|
331
|
+
|
|
332
|
+
if (!ignoreArea && address.indexOf('县') > -1 || !ignoreArea && address.indexOf('区') > -1 || !ignoreArea && address.indexOf('旗') > -1) {
|
|
333
|
+
if (address.indexOf('旗') > -1) {
|
|
334
|
+
areaIndex = address.indexOf('旗');
|
|
335
|
+
parse.area = address.substr(areaIndex - 1, 2);
|
|
336
|
+
}
|
|
337
|
+
if (address.indexOf('区') > -1) {
|
|
338
|
+
// 改进区名识别逻辑,优先匹配地址库中存在的完整区名
|
|
339
|
+
areaIndex = address.indexOf('区');
|
|
340
|
+
if (address.lastIndexOf('市', areaIndex) > -1) {
|
|
341
|
+
cityIndex = address.lastIndexOf('市', areaIndex);
|
|
342
|
+
parse.area = address.substr(cityIndex + 1, areaIndex - cityIndex);
|
|
343
|
+
} else {
|
|
344
|
+
// 查找所有可能的区名,优先选择较长的匹配项
|
|
345
|
+
let possibleAreas = [];
|
|
346
|
+
// 从地址中寻找所有可能的区名
|
|
347
|
+
for (let areaName in mArea) {
|
|
348
|
+
if (address.includes(areaName) && areaName.endsWith('区')) {
|
|
349
|
+
const pos = address.indexOf(areaName);
|
|
350
|
+
if (pos !== -1 && pos <= areaIndex && pos >= Math.max(0, areaIndex - 6)) {
|
|
351
|
+
possibleAreas.push(areaName);
|
|
352
|
+
}
|
|
353
|
+
}
|
|
354
|
+
}
|
|
355
|
+
if (possibleAreas.length > 0) {
|
|
356
|
+
// 按长度降序排列,优先选择较长的匹配项
|
|
357
|
+
possibleAreas.sort((a, b) => b.length - a.length);
|
|
358
|
+
parse.area = possibleAreas[0];
|
|
359
|
+
areaIndex = address.lastIndexOf(parse.area);
|
|
360
|
+
} else {
|
|
361
|
+
parse.area = address.substr(areaIndex - 2, 3);
|
|
362
|
+
}
|
|
363
|
+
}
|
|
364
|
+
}
|
|
365
|
+
if (address.indexOf('县') > -1) {
|
|
366
|
+
// 改进县名识别逻辑,优先匹配地址库中存在的完整县名
|
|
367
|
+
areaIndex = address.lastIndexOf('县');
|
|
368
|
+
if (address.lastIndexOf('市', areaIndex) > -1) {
|
|
369
|
+
cityIndex = address.lastIndexOf('市', areaIndex);
|
|
370
|
+
parse.area = address.substr(cityIndex + 1, areaIndex - cityIndex);
|
|
371
|
+
} else {
|
|
372
|
+
// 查找所有可能的县名,优先选择较长的匹配项
|
|
373
|
+
let possibleAreas = [];
|
|
374
|
+
// 从地址中寻找所有可能的县名
|
|
375
|
+
for (let areaName in mArea) {
|
|
376
|
+
if (address.includes(areaName) && areaName.endsWith('县')) {
|
|
377
|
+
const pos = address.indexOf(areaName);
|
|
378
|
+
if (pos !== -1 && pos <= areaIndex && pos >= Math.max(0, areaIndex - 6)) {
|
|
379
|
+
possibleAreas.push(areaName);
|
|
380
|
+
}
|
|
381
|
+
}
|
|
382
|
+
}
|
|
383
|
+
if (possibleAreas.length > 0) {
|
|
384
|
+
// 按长度降序排列,优先选择较长的匹配项
|
|
385
|
+
possibleAreas.sort((a, b) => b.length - a.length);
|
|
386
|
+
parse.area = possibleAreas[0];
|
|
387
|
+
areaIndex = address.lastIndexOf(parse.area);
|
|
388
|
+
} else {
|
|
389
|
+
parse.area = address.substr(areaIndex - 2, 3);
|
|
390
|
+
}
|
|
391
|
+
}
|
|
392
|
+
}
|
|
393
|
+
parse.addr = address.substr(areaIndex + 1);
|
|
394
|
+
|
|
395
|
+
} else {
|
|
396
|
+
if (address.indexOf('市') > -1) {
|
|
397
|
+
areaIndex = address.indexOf('市');
|
|
398
|
+
parse.area = address.substr(areaIndex - 2, 3);
|
|
399
|
+
parse.addr = address.substr(areaIndex + 1);
|
|
400
|
+
} else {
|
|
401
|
+
parse.addr = address
|
|
402
|
+
}
|
|
403
|
+
}
|
|
404
|
+
|
|
405
|
+
if (address.indexOf('市') > -1 || address.indexOf('盟') > -1 || address.indexOf('州') > -1) {
|
|
406
|
+
if (address.indexOf('市') > -1) {
|
|
407
|
+
parse._area = address.substr(address.indexOf('市') - 2, 2);
|
|
408
|
+
}
|
|
409
|
+
if (address.indexOf('盟') > -1 && !mCity[parse._area]) {
|
|
410
|
+
parse._area = address.substr(address.indexOf('盟') - 2, 2);
|
|
411
|
+
}
|
|
412
|
+
if (address.indexOf('州') > -1 && !mCity[parse._area]) {
|
|
413
|
+
parse._area = address.substr(address.indexOf('州') - 2, 2);
|
|
414
|
+
}
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
parse.area = parse.area.trim();
|
|
418
|
+
|
|
419
|
+
// 确保选择最长的匹配项
|
|
420
|
+
if (parse.area && mArea[parse.area]) {
|
|
421
|
+
// 检查是否有更长的匹配项
|
|
422
|
+
const checkLongerMatch = (currentArea, addressSubstring, endIndex) => {
|
|
423
|
+
let longerMatch = currentArea;
|
|
424
|
+
// 检查在当前地址片段中是否存在更长的匹配项
|
|
425
|
+
for (let areaName in mArea) {
|
|
426
|
+
if (addressSubstring.includes(areaName) && areaName.length > longerMatch.length && (areaName.endsWith('县') || areaName.endsWith('区') || areaName.endsWith('旗'))) {
|
|
427
|
+
const pos = addressSubstring.lastIndexOf(areaName);
|
|
428
|
+
if (pos !== -1 && pos <= endIndex) {
|
|
429
|
+
longerMatch = areaName;
|
|
430
|
+
}
|
|
431
|
+
}
|
|
432
|
+
}
|
|
433
|
+
return longerMatch;
|
|
434
|
+
};
|
|
435
|
+
|
|
436
|
+
// 更新区域名称为最长匹配项
|
|
437
|
+
const originalArea = parse.area;
|
|
438
|
+
if (address) {
|
|
439
|
+
parse.area = checkLongerMatch(parse.area, address, areaIndex);
|
|
440
|
+
// 如果区域名称发生变化,更新areaIndex
|
|
441
|
+
if (parse.area !== originalArea) {
|
|
442
|
+
areaIndex = address.lastIndexOf(parse.area);
|
|
443
|
+
}
|
|
444
|
+
}
|
|
445
|
+
|
|
446
|
+
if (mArea[parse.area].length === 1) {
|
|
447
|
+
parse.province = mArea[parse.area][0].p;
|
|
448
|
+
parse.city = mArea[parse.area][0].c
|
|
449
|
+
} else {
|
|
450
|
+
parse._area = parse._area.trim();
|
|
451
|
+
const addr = address.substr(0, areaIndex);
|
|
452
|
+
const d = mArea[parse.area].find(item => {
|
|
453
|
+
return item.p.indexOf(addr) > -1 || item.c === parse._area;
|
|
454
|
+
});
|
|
455
|
+
if (d) {
|
|
456
|
+
parse.province = d.p;
|
|
457
|
+
parse.city = d.c
|
|
458
|
+
} else {
|
|
459
|
+
parse.result = mArea[parse.area];
|
|
460
|
+
}
|
|
461
|
+
}
|
|
462
|
+
} else {
|
|
463
|
+
if (parse._area) {
|
|
464
|
+
const city = mCity[parse._area];
|
|
465
|
+
if (city) {
|
|
466
|
+
parse.province = city[0].p;
|
|
467
|
+
parse.city = city[0].c;
|
|
468
|
+
parse.addr = address.substr(address.indexOf(parse.city) + parse.city.length + 1);
|
|
469
|
+
parse.area = '';
|
|
470
|
+
for (let i in city[0].a) {
|
|
471
|
+
if (parse.addr.indexOf(city[0].a[i]) === 0) {
|
|
472
|
+
parse.area = city[0].a[i];
|
|
473
|
+
parse.addr = parse.addr.replace(city[0].a[i], '');
|
|
474
|
+
break;
|
|
475
|
+
}
|
|
476
|
+
}
|
|
477
|
+
}
|
|
478
|
+
} else {
|
|
479
|
+
parse.area = '';
|
|
480
|
+
}
|
|
481
|
+
}
|
|
482
|
+
parse.addr = parse.addr.trim();
|
|
483
|
+
return parse
|
|
484
|
+
}
|
|
485
|
+
|
|
486
|
+
const MUNICIPALITIES = ['上海', '北京', '天津', '重庆'];
|
|
487
|
+
|
|
488
|
+
/**
|
|
489
|
+
* 统一换行符格式
|
|
490
|
+
*/
|
|
491
|
+
function normalizeLineBreaks(address) {
|
|
492
|
+
return String(address || '')
|
|
493
|
+
.replace(/\r\n/g, '\n')
|
|
494
|
+
.replace(/\r/g, '\n')
|
|
495
|
+
.replace(/\t/g, ' ');
|
|
496
|
+
}
|
|
497
|
+
|
|
498
|
+
/**
|
|
499
|
+
* 常见地址字段标签(姓名:、详细地址: 等),较长标签优先匹配
|
|
500
|
+
*/
|
|
501
|
+
var ADDRESS_LABEL_PATTERN = '(?:详细地址|收货地址|联系地址|收件地址|邮政编码|手机号码|联系电话|联系方式|收货人|收件人|联系人|姓名|名字|手机号|邮编|收货|地址|详细|固话|电话)[::]';
|
|
502
|
+
var ADDRESS_LABEL_REG = new RegExp(ADDRESS_LABEL_PATTERN, 'g');
|
|
503
|
+
var ADDRESS_LABEL_TEST_REG = new RegExp(ADDRESS_LABEL_PATTERN);
|
|
504
|
+
|
|
505
|
+
/**
|
|
506
|
+
* 去除「姓名:」「详细地址:」等字段标签前缀
|
|
507
|
+
*/
|
|
508
|
+
function stripAddressLabels(text) {
|
|
509
|
+
return String(text || '').replace(ADDRESS_LABEL_REG, ' ');
|
|
510
|
+
}
|
|
511
|
+
|
|
512
|
+
var NAME_LABELS = ['姓名', '名字', '联系人', '收货人', '收件人'];
|
|
513
|
+
var PHONE_LABELS = ['电话', '手机号', '手机号码', '联系电话', '联系方式', '固话'];
|
|
514
|
+
|
|
515
|
+
/**
|
|
516
|
+
* 解析「标签:值」格式的单行
|
|
517
|
+
*/
|
|
518
|
+
function matchLabeledLine(line) {
|
|
519
|
+
var match = line.match(/^([\u4e00-\u9fa5A-Za-z0-9]+)[::]\s*(.+)$/);
|
|
520
|
+
if (!match) {
|
|
521
|
+
return null;
|
|
522
|
+
}
|
|
523
|
+
return { label: match[1], value: match[2].trim() };
|
|
524
|
+
}
|
|
525
|
+
|
|
526
|
+
/**
|
|
527
|
+
* 按换行符拆分段落,去除行内空白后用空格拼接为单行
|
|
528
|
+
* 若每行是「标签:值」格式,则按标签分类提取姓名、电话和地址
|
|
529
|
+
*/
|
|
530
|
+
function joinAddressLines(address) {
|
|
531
|
+
var normalized = normalizeLineBreaks(address);
|
|
532
|
+
var lines = normalized.split('\n').filter(function(line) {
|
|
533
|
+
return line.replace(/[ \t\f\v]+/g, ' ').trim();
|
|
534
|
+
});
|
|
535
|
+
if (lines.length === 1) {
|
|
536
|
+
var singleLine = lines[0].replace(/[ \t\f\v]+/g, ' ').trim();
|
|
537
|
+
if ((singleLine.match(/[::]/g) || []).length > 1 && ADDRESS_LABEL_TEST_REG.test(singleLine)) {
|
|
538
|
+
return {
|
|
539
|
+
text: stripAddressLabels(singleLine).replace(/ {2,}/g, ' ').trim(),
|
|
540
|
+
name: '',
|
|
541
|
+
phoneHint: '',
|
|
542
|
+
};
|
|
543
|
+
}
|
|
544
|
+
}
|
|
545
|
+
var parts = [];
|
|
546
|
+
var extracted = { name: '', phoneHint: '' };
|
|
547
|
+
for (var i = 0; i < lines.length; i++) {
|
|
548
|
+
var line = lines[i].replace(/[ \t\f\v]+/g, ' ').trim();
|
|
549
|
+
if (!line) {
|
|
550
|
+
continue;
|
|
551
|
+
}
|
|
552
|
+
var labeled = matchLabeledLine(line);
|
|
553
|
+
if (labeled) {
|
|
554
|
+
if (NAME_LABELS.indexOf(labeled.label) > -1) {
|
|
555
|
+
extracted.name = labeled.value;
|
|
556
|
+
} else if (PHONE_LABELS.indexOf(labeled.label) > -1) {
|
|
557
|
+
extracted.phoneHint = labeled.value;
|
|
558
|
+
} else {
|
|
559
|
+
parts.push(labeled.value);
|
|
560
|
+
}
|
|
561
|
+
} else {
|
|
562
|
+
parts.push(line);
|
|
563
|
+
}
|
|
564
|
+
}
|
|
565
|
+
return {
|
|
566
|
+
text: parts.join(' '),
|
|
567
|
+
name: extracted.name,
|
|
568
|
+
phoneHint: extracted.phoneHint,
|
|
569
|
+
};
|
|
570
|
+
}
|
|
571
|
+
|
|
572
|
+
/**
|
|
573
|
+
* 从全局变量或 options 中获取 areaList(CDN 加载后挂载在 window.areaList)
|
|
574
|
+
* @param {object} options
|
|
575
|
+
* @param {array} [options.areaList] 地址库原始数据,不传则从全局 areaList 读取
|
|
576
|
+
* @returns {array|null}
|
|
577
|
+
*/
|
|
578
|
+
function getGlobalAreaList(options = {}) {
|
|
579
|
+
if (options.areaList) {
|
|
580
|
+
return options.areaList;
|
|
581
|
+
}
|
|
582
|
+
if (typeof window !== 'undefined' && window.areaList) {
|
|
583
|
+
return window.areaList;
|
|
584
|
+
}
|
|
585
|
+
try {
|
|
586
|
+
// CDN 场景下 areaList 为全局变量
|
|
587
|
+
// eslint-disable-next-line no-undef
|
|
588
|
+
if (typeof areaList !== 'undefined') {
|
|
589
|
+
// eslint-disable-next-line no-undef
|
|
590
|
+
return areaList;
|
|
591
|
+
}
|
|
592
|
+
} catch (e) {
|
|
593
|
+
// areaList 未定义时忽略
|
|
594
|
+
}
|
|
595
|
+
return null;
|
|
596
|
+
}
|
|
597
|
+
|
|
598
|
+
/**
|
|
599
|
+
* 判断直辖市名称在前 8 个字符中是否只出现一次(用于补全省份前缀)
|
|
600
|
+
*/
|
|
601
|
+
function checkMunicipalityChars(str, name) {
|
|
602
|
+
const prefix = str.substring(0, 8);
|
|
603
|
+
const firstIndex = prefix.indexOf(name);
|
|
604
|
+
const lastIndex = prefix.lastIndexOf(name);
|
|
605
|
+
return firstIndex !== -1 && firstIndex === lastIndex;
|
|
606
|
+
}
|
|
607
|
+
|
|
608
|
+
/**
|
|
609
|
+
* 预处理地址字符串:去空格,并为缺少省份前缀的直辖市地址补全
|
|
610
|
+
*/
|
|
611
|
+
function preprocessAddress(address) {
|
|
612
|
+
var cleanAddress = normalizeLineBreaks(address).replace(/[ \t\f\v]+/g, '');
|
|
613
|
+
cleanAddress = cleanAddress.replace(/\n+/g, '\n').replace(/^\n+|\n+$/g, '');
|
|
614
|
+
MUNICIPALITIES.forEach(function(name) {
|
|
615
|
+
if (cleanAddress.indexOf('\n') > -1) {
|
|
616
|
+
var lines = cleanAddress.split('\n');
|
|
617
|
+
for (var i = 0; i < lines.length; i++) {
|
|
618
|
+
if (checkMunicipalityChars(lines[i], name)) {
|
|
619
|
+
lines[i] = name + lines[i];
|
|
620
|
+
}
|
|
621
|
+
}
|
|
622
|
+
cleanAddress = lines.join('\n');
|
|
623
|
+
} else if (checkMunicipalityChars(cleanAddress, name)) {
|
|
624
|
+
cleanAddress = name + cleanAddress;
|
|
625
|
+
}
|
|
626
|
+
});
|
|
627
|
+
return cleanAddress;
|
|
628
|
+
}
|
|
629
|
+
|
|
630
|
+
/**
|
|
631
|
+
* 自动识别地址信息,格式化为省市区街道和收件人等信息
|
|
632
|
+
* @param {string} address 原始地址字符串(可含空格、姓名、手机号等)
|
|
633
|
+
* @param {object} [sourceData] 组件 sourceData,用于四级地址等配置(extraInfo.isFourAddress)
|
|
634
|
+
* @param {object} [options] 可选配置
|
|
635
|
+
* @param {array} [options.areaList] 地址库原始数据,默认从全局 areaList 获取
|
|
636
|
+
* @returns {{name: string, mobile: string, phone: string, zip_code: string, extensionNumber: string, province: string, city: string, area: string, street: string, addr: string, result: *}}
|
|
637
|
+
*/
|
|
638
|
+
export function addressParse(address, sourceData, options = {}) {
|
|
639
|
+
const list = getGlobalAreaList(options);
|
|
640
|
+
if (list) {
|
|
641
|
+
parseArea(list);
|
|
642
|
+
}
|
|
643
|
+
const cleanAddress = preprocessAddress(address);
|
|
644
|
+
return parseAddressDetail(cleanAddress, sourceData || {});
|
|
645
|
+
}
|