@conecli/cone-render 0.8.20-shop.213 → 0.8.20-shop.215

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.
@@ -1 +1 @@
1
- import Taro from '@tarojs/taro';
2
1
  dealNativePixelToCssPixel,
3
2
  isAndroidDevice,
4
3
  isIosDevice,
5
4
  isJdAndAndroidDevice,
6
5
  isJdAndHarmonyDevice,
7
6
  isObject,
8
7
  isPc,
9
8
  isString,
10
9
  jdAppVersion,
11
10
  jdAppVersionStr,
12
11
  serialize,
13
12
  draBusinessCustomReport,
14
13
  isH5AndJingGouMini,
15
14
  languageNowType,
16
15
  urlCookie,
17
16
  BUSINESS_TYPE,
18
17
  LoadJsInitLoadEnvType,
19
18
  LoadJsInitLoadType,
20
19
  LoadJsInitTriggerType,
21
20
  MPAAS_CONFIG_APP_LOW_VERSION,
22
21
  MPAAS_CONFIG_APP_VERSION,
23
22
  SECTION_HOME_TAB_NAME_TYPE,
24
23
  SECTION_HOME_TAB_TYPE,
25
24
  TaroEventType,
26
25
  WX_BUSINESS_TYPE,
27
26
  WXAPP_BIZ_KEY,
28
27
  WXAPP_BIZ_SHOP_LIGHT_KEY,
29
28
  JSSDK_APP_WEBVIEW_CODE,
30
29
  cacheH5LbsAddressKey,
31
30
  languageTypeList,
32
31
  getSystemInfos,
33
32
  getTaroStorageKeyValue,
34
33
  ipLoc_djd,
35
34
  setTaroStorage,
36
35
  sgmCustomReport,
37
36
  getMPaasConfigByBussinessKey,
38
37
  callRouterAndroid,
39
38
  callRouterIOS,
40
39
  const designWidth = 750;
41
40
  return (
42
41
  Math.ceil((((parseInt(String(size), 10) / 40) * 750) / designWidth) * 10000) / 10000 + 'rem'
43
42
  );
44
43
  abTestLabels: {},
45
44
  nonSellableSkuids: {},
46
45
  loginState: false,
47
46
  cookiesStr: '',
48
47
  userInfo: userPinKey,
49
48
  isImmersive: false,
50
49
  isJingGouMiniViewState: false,
51
50
  isJingxiMiniViewState: false,
52
51
  pageInfo: {
53
52
  wxBusinessType: WX_BUSINESS_TYPE.NO,
54
53
  address: '',
55
54
  addressCommaStr: '',
56
55
  un_area: '',
57
56
  userLbsAddress: '',
58
57
  vapptype: '1',
59
58
  pageType: 'home',
60
59
  isExposureState: false,
61
60
  moduleId: '',
62
61
  entrance: '',
63
62
  dataType: BUSINESS_TYPE.ONLINE,
64
63
  floorExposureInfo: {},
65
64
  floorVideInfo: {},
66
65
  productVideInfo: {},
67
66
  tabsLoadAllDataInfo: {
68
67
  [SECTION_HOME_TAB_NAME_TYPE[SECTION_HOME_TAB_TYPE.HOME_WELL_CHOSEN]]: false,
69
68
  },
70
69
  updateShopInfosAllState: false,
71
70
  isVipShop: false,
72
71
  isJdShowNativeImmersivePlayer: false,
73
72
  ...shopConfig,
74
73
  pageScrollTop: 0,
75
74
  pageIdxHeightInfo: {
76
75
  list: [],
77
76
  },
78
77
  shopNavBarHeight: 0,
79
78
  },
80
79
  defaultQueryLogInfo: {
81
80
  sourceType: 'JDshop',
82
81
  sourceValue: '',
83
82
  moduleId: 'none',
84
83
  entrance: 'none',
85
84
  },
86
85
  sysInfo: {
87
86
  windowWidth: isPc ? 375 : 0,
88
87
  containerWidth: isPc ? 375 : 0,
89
88
  windowHeight: 0,
90
89
  netWorkType: '4g',
91
90
  jdBottomBarHeight: 0,
92
91
  jdNativeHeaderHeight: 0,
93
92
  isJdTabletDevice: false,
94
93
  isJdTabletLandscape: false,
95
94
  },
96
95
  queryInfo: {},
97
96
  shopInfo: {},
98
97
  openAppData: {},
99
98
  public info: CommonInterFace.BaseConfigInfo;
100
99
  public config: {
101
100
  [key: string]: any;
102
101
  };
103
102
  public lazyContainer: CommonInterFace.lazyContainer;
104
103
  public renderedIsvComponents: CommonInterFace.renderedIsvComponents;
105
104
  public rootEleNode: HTMLElement | null;
106
105
  public checkStatusAndLoginPromise: object | null;
107
106
  private jmfeRegisterStatePromise: Promise<any> | null;
108
107
  private jdScreenSizeInfoPromise: Promise<any> | null;
109
108
  private rootEleWidthRegisterPromise: Promise<any> | null;
110
109
  private jmfeRegisterState: boolean;
111
110
  public loadJsSdkList: Array<any>;
112
111
  public loadJsSdkListCachePromise: any;
113
112
  public rootEleInitWidth: number;
114
113
  public lbsAddressCachePromise: Promise<any> | null;
115
114
  public languageCacheProimse: Promise<any> | null;
116
115
  public languageJsonData: any | null;
117
116
  constructor(opt) {
118
117
  this.info = this._getConfig(opt);
119
118
  this.config = {};
120
119
  this.loadJsSdkList = [];
121
120
  this.loadJsSdkListCachePromise = {};
122
121
  this.lazyContainer = {
123
122
  [SECTION_HOME_TAB_NAME_TYPE[SECTION_HOME_TAB_TYPE.HOME_WELL_CHOSEN]]: {
124
123
  appLazyContainerList: [],
125
124
  appLazyFinishContainerList: [],
126
125
  },
127
126
  [SECTION_HOME_TAB_NAME_TYPE[SECTION_HOME_TAB_TYPE.HOME_PROMOTION]]: {
128
127
  appLazyContainerList: [],
129
128
  appLazyFinishContainerList: [],
130
129
  },
131
130
  };
132
131
  this.renderedIsvComponents = {};
133
132
  this.rootEleNode = document.querySelector('body');
134
133
  this.checkStatusAndLoginPromise = null;
135
134
  this.jmfeRegisterStatePromise = null;
136
135
  this.jdScreenSizeInfoPromise = null;
137
136
  this.rootEleWidthRegisterPromise = null;
138
137
  this.lbsAddressCachePromise = null;
139
138
  this.languageCacheProimse = null;
140
139
  this.languageJsonData = langeJsonDataForCn;
141
140
  this.rootEleInitWidth = this.getRootEleWindowWidthInfo().getRootEleWidth || -1;
142
141
  this.loadOtherSdk();
143
142
  if (isJdApp) {
144
143
  this.jmfeReayPromise();
145
144
  this._getJdPadMinWidthForListen() && this.getPadWindowRootEleWidthPromise();
146
145
  }
147
146
  }
148
147
  _getConfig(opt) {
149
148
  return Object.assign({}, DefaultConfig, opt);
150
149
  }
151
150
  _getJdPadMinWidthForListen() {
152
151
  return (
153
152
  isJdApp &&
154
153
  Math.min(window.screen.width, window.screen.height) >
155
154
  (window?.shopGlobalSwitch?.checkPadRootEleMinWidth || 600)
156
155
  );
157
156
  }
158
157
 
159
158
  jmfeReayPromise(): Promise<any> {
160
159
  if (isJdApp) {
161
160
  if (this.jmfeRegisterState) {
162
161
  return Promise.resolve(true);
163
162
  } else {
164
163
  !this.jmfeRegisterStatePromise &&
165
164
  (this.jmfeRegisterStatePromise = new Promise((resolve, reject) => {
166
165
  ready('jmfe', 3000)
167
166
  .then(() => {
168
167
  window?.jmfe && window.jmfe.registerCode(JSSDK_APP_WEBVIEW_CODE);
169
168
  this.jmfeRegisterState = true;
170
169
  resolve(true);
171
170
  console.log(
172
171
  '松果app内初始化注册jmfe认证完成',
173
172
  window?.jmfe,
174
173
  '当前版本',
175
174
  window?.jmfe?.VERSION,
176
175
  );
177
176
  })
178
177
  .catch((err) => {
179
178
  console.error('jmfe ready error', err);
180
179
  reject(false);
181
180
  });
182
181
  }));
183
182
  return this.jmfeRegisterStatePromise;
184
183
  }
185
184
  } else {
186
185
  return Promise.reject(false);
187
186
  }
188
187
  }
189
188
 
190
189
  getJdScreenSizeInfoPromise() {
191
190
  !this.jdScreenSizeInfoPromise &&
192
191
  (this.jdScreenSizeInfoPromise = new Promise((resolve) => {
193
192
  const getThisTime = Date.now();
194
193
  this.jmfeReayPromise().then(() => {
195
194
  return Promise.race([
196
195
  window.jmfe.getScreenSize(),
197
196
  this.taskTimeoutPromise(() => {
198
197
  return {
199
198
  status: '-10',
200
199
  msg: '获取大屏信息2s超时',
201
200
  };
202
201
  }),
203
202
  ])
204
203
  .then((res) => {
205
204
  console.warn('===获取app大屏信息====', res);
206
205
  const { status, data } = res;
207
206
  if (status === '0' && data) {
208
207
  const { sizeType, isLandscape, pageHeight, pageWidth } = data;
209
208
  const getPageInfo = dealNativePixelToCssPixel({
210
209
  pageWidth,
211
210
  pageHeight,
212
211
  });
213
212
  this.info.sysInfo.jdScreenSizeType = sizeType;
214
213
  const getUseTime = Date.now() - getThisTime;
215
214
  console.warn(
216
215
  '===计算是否是app大屏信息,需满足宽度最新720===',
217
216
  getPageInfo,
218
217
  '原始数据',
219
218
  data,
220
219
  '是否是横屏isLandscape为1=',
221
220
  isLandscape,
222
221
  '用时',
223
222
  getUseTime,
224
223
  );
225
224
  if (getPageInfo?.pageWidth > 0) {
226
225
  this.rootEleInitWidth = getPageInfo?.pageWidth;
227
226
  draBusinessCustomReport({
228
227
  type: 'rootEle_width_getJdScreenSizeInfo',
229
228
  errMsg: `根元素获取宽度初始化为0,通过getJdScreenSizeInfo获取结果,用时${getUseTime}`,
230
229
  originReqDataStr: JSON.stringify({
231
230
  isJdApp,
232
231
  getPageInfo,
233
232
  originData: res,
234
233
  }),
235
234
  });
236
235
  resolve(getPageInfo);
237
236
  } else {
238
237
  resolve({
239
238
  pageWidth: 0,
240
239
  pageHeight: 0,
241
240
  msg: '转换异常',
242
241
  });
243
242
  }
244
243
  } else {
245
244
  resolve({
246
245
  pageWidth: 0,
247
246
  pageHeight: 0,
248
247
  msg: '获取大屏信息异常或者超时',
249
248
  });
250
249
  }
251
250
  })
252
251
  .catch((err) => {
253
252
  console.log('获取大屏信息异常', err);
254
253
  resolve({
255
254
  pageWidth: 0,
256
255
  pageHeight: 0,
257
256
  msg: '获取大屏信息异常',
258
257
  });
259
258
  });
260
259
  });
261
260
  }));
262
261
  return this.jdScreenSizeInfoPromise;
263
262
  }
264
263
 
265
264
  listenJdTabletScreenChange() {
266
265
  this.jmfeReayPromise().then(() => {
267
266
  try {
268
267
  console.log('初始化监听大屏信息变化', window.jmfe.listenDeviceScreenChange);
269
268
  window.jmfe.listenDeviceScreenChange((event) => {
270
269
  console.log(
271
270
  '监听app大屏信息变化,orientation为landscape表示横屏,multiScreen为1表示android端分屏',
272
271
  event,
273
272
  '通过前端判断是不是横屏',
274
273
  window.matchMedia('(orientation: landscape)')?.matches,
275
274
  );
276
275
  const { orientation } = event?.data;
277
276
  if (orientation) {
278
277
  this.info.sysInfo.isJdTabletLandscape = orientation === 'landscape';
279
278
  Taro.eventCenter.trigger(
280
279
  TaroEventType.TABLE_SCREEN_CHANGE,
281
280
  this.info.sysInfo.isJdTabletLandscape,
282
281
  orientation,
283
282
  );
284
283
  }
285
284
  });
286
285
  } catch (error) {
287
286
  console.log('listenScreenChange的打印error:', error);
288
287
  }
289
288
  });
290
289
  }
291
290
 
292
291
  updateBusinessDomainAndApi(domain, api) {
293
292
  }
294
293
 
295
294
  formatNativeScreenPageData(action) {
296
295
  let getChangePageInfo: any = null;
297
296
  try {
298
297
  const getNativeScreenPageInfoStr = window.XWebView?._callNative(
299
298
  JSON.stringify({
300
299
  plugin: 'JDHybridScreenPlugin',
301
300
  action,
302
301
  sync: '1',
303
302
  }),
304
303
  );
305
304
  const getChangePageInfoData =
306
305
  typeof getNativeScreenPageInfoStr === 'string'
307
306
  ? JSON.parse(getNativeScreenPageInfoStr)
308
307
  : null;
309
308
  if (getChangePageInfoData && typeof getChangePageInfoData === 'object') {
310
309
  const { code, data } = getChangePageInfoData;
311
310
  getChangePageInfo = code && code === '0' ? data : null;
312
311
  }
313
312
  } catch (e) {
314
313
  console.log('JDHybridScreenPlugin转换异常', e);
315
314
  }
316
315
  return getChangePageInfo;
317
316
  }
318
317
 
319
318
  isAndroidFoldScreen() {
320
319
  return this.formatNativeScreenPageData('isFoldScreen') === '1';
321
320
  }
322
321
 
323
322
  getJdAndroidPageChangeScreenInfo() {
324
323
  const getPageScreenInfo = this.formatNativeScreenPageData('getScreenSize');
325
324
  if (getPageScreenInfo && getPageScreenInfo?.pageWidth && getPageScreenInfo?.pageHeight) {
326
325
  const { pageWidth, pageHeight } = dealNativePixelToCssPixel({
327
326
  pageWidth: getPageScreenInfo.pageWidth,
328
327
  pageHeight: getPageScreenInfo.pageHeight,
329
328
  });
330
329
  getPageScreenInfo.pageWidth = pageWidth;
331
330
  getPageScreenInfo.pageHeight = pageHeight;
332
331
  }
333
332
  return getPageScreenInfo;
334
333
  }
335
334
 
336
335
  getRootEleWindowWidthInfo() {
337
336
  const getRootEleWidth = document.documentElement.getBoundingClientRect().width;
338
337
  const getWindowWidth = window.innerWidth;
339
338
  const getScreenWidth = window.screen.width;
340
339
  return {
341
340
  getRootEleWidth,
342
341
  getWindowWidth,
343
342
  getScreenWidth,
344
343
  };
345
344
  }
346
345
 
347
346
  dealRootEleWidthFn(reportParam = {}, timeout = 0) {
348
347
  const { getRootEleWidth, getWindowWidth, getScreenWidth } = this.getRootEleWindowWidthInfo();
349
348
  console.log(
350
349
  '当前获取根元素的宽度',
351
350
  getRootEleWidth,
352
351
  'getWindowWidth',
353
352
  getWindowWidth,
354
353
  'getScreenWidth',
355
354
  getScreenWidth,
356
355
  );
357
356
  const getLastWidth =
358
357
  getRootEleWidth > 0
359
358
  ? Math.round(getRootEleWidth)
360
359
  : Math.round(getWindowWidth > 0 ? getWindowWidth : getScreenWidth);
361
360
  console.warn(
362
361
  `根元素获取宽度初始化为0,通过getJdScreenSizeInfo获取结果超时,超时时间超时时间${timeout}ms,最终兜底再获取一次根元素宽度${getLastWidth}`,
363
362
  );
364
363
  timeout > 0 &&
365
364
  draBusinessCustomReport({
366
365
  type: 'rootEle_width_timeout_getJdScreenSizeInfo',
367
366
  errMsg: `根元素获取宽度初始化为0,通过getJdScreenSizeInfo获取结果超时,超时时间${timeout}ms,最终兜底再获取一次根元素宽度${getLastWidth}`,
368
367
  originReqDataStr: JSON.stringify({
369
368
  isJdApp,
370
369
  getRootEleWidth,
371
370
  getWindowWidth,
372
371
  getScreenWidth,
373
372
  ...reportParam,
374
373
  }),
375
374
  });
376
375
  return getLastWidth;
377
376
  }
378
377
 
379
378
  getPadWindowRootEleWidthPromise() {
380
379
  if (this.rootEleInitWidth > 0) {
381
380
  return Promise.resolve(this.rootEleInitWidth);
382
381
  } else {
383
382
  !this.rootEleWidthRegisterPromise &&
384
383
  (this.rootEleWidthRegisterPromise = new Promise((resolve) => {
385
384
  const getRootEleInitWidth = this.getRootEleWindowWidthInfo().getRootEleWidth;
386
385
  if (getRootEleInitWidth > 0) {
387
386
  console.log('初始化获取根元素宽度正常,为', getRootEleInitWidth);
388
387
  this.rootEleInitWidth = Math.round(getRootEleInitWidth);
389
388
  resolve(this.rootEleInitWidth);
390
389
  } else {
391
390
  const timerPromise = () => {
392
391
  return new Promise((resolve2) => {
393
392
  window.setTimeout(() => {
394
393
  const { getRootEleWidth, getWindowWidth, getScreenWidth } =
395
394
  this.getRootEleWindowWidthInfo();
396
395
  if (getRootEleWidth > 0 || getWindowWidth > 0) {
397
396
  console.warn(
398
397
  `根元素获取宽度初始化为0,200ms后尝试获取最新结果,getRootEleWidth为${getRootEleWidth},getWindowWidth为${getWindowWidth},getScreenWidth为${getScreenWidth}`,
399
398
  );
400
399
  draBusinessCustomReport({
401
400
  type: 'rootEle_width_200_timeout_info',
402
401
  errMsg: `根元素获取宽度初始化为0,200ms后尝试获取最新结果,getRootEleWidth为${getRootEleWidth},getWindowWidth为${getWindowWidth}`,
403
402
  originReqDataStr: JSON.stringify({
404
403
  isJdApp,
405
404
  getRootEleWidth,
406
405
  getWindowWidth,
407
406
  getScreenWidth,
408
407
  }),
409
408
  });
410
409
  const getRes =
411
410
  getRootEleWidth > 0 && getWindowWidth > 0
412
411
  ? Math.min(getRootEleWidth, getWindowWidth)
413
412
  : Math.max(getRootEleWidth, getWindowWidth);
414
413
  resolve2({
415
414
  pageWidth: Math.round(getRes),
416
415
  });
417
416
  }
418
417
  }, 200);
419
418
  });
420
419
  };
421
420
  Promise.race([timerPromise(), this.getJdScreenSizeInfoPromise()]).then((res) => {
422
421
  const { pageWidth } = res;
423
422
  console.log('获取结果Promise.race getJdScreenSizeInfo', res);
424
423
  pageWidth > 0 ? resolve(pageWidth) : resolve(this.dealRootEleWidthFn(res, 2000));
425
424
  });
426
425
  }
427
426
  }));
428
427
  return this.rootEleWidthRegisterPromise;
429
428
  }
430
429
  }
431
430
 
432
431
  async getSystemInfo(params) {
433
432
  const getParams = Object.assign({}, params || {});
434
433
  if (this.rootEleInitWidth > 0) {
435
434
  getParams['rootEleInitWidth'] = this.rootEleInitWidth;
436
435
  console.log('获取当前系统信息的时候已经获取到根元素宽度,值为', this.rootEleInitWidth);
437
436
  } else {
438
437
  if (this._getJdPadMinWidthForListen()) {
439
438
  getParams['rootEleInitWidth'] = await this.getPadWindowRootEleWidthPromise();
440
439
  getParams['replaceSystemWidth'] = true;
441
440
  }
442
441
  }
443
442
  isJdApp && this.createLanguagePromise();
444
443
  let info: UtilsInterFace.taroGetSystemInfoSyncRes | any = getSystemInfos(getParams);
445
444
  if (isJdAndAndroidDevice && info?.initWindowWidth <= 0) {
446
445
  let _isfoldScreen = false;
447
446
  const getStorageData = getTaroStorageKeyValue('jd_shopx_androidIsFoldScreen');
448
447
  console.info(
449
448
  '获取当前本地存储是否有jd_shopx_androidIsFoldScreen',
450
449
  getStorageData,
451
450
  '通过缓存值第一次判断是否是折叠屏',
452
451
  getStorageData === 'true',
453
452
  );
454
453
  if (!getStorageData) {
455
454
  _isfoldScreen = this.isAndroidFoldScreen();
456
455
  setTaroStorage('jd_shopx_androidIsFoldScreen', `${_isfoldScreen}`);
457
456
  } else {
458
457
  _isfoldScreen = getStorageData === 'true';
459
458
  }
460
459
  if (_isfoldScreen) {
461
460
  const getJdAndroidPageInfo = this.getJdAndroidPageChangeScreenInfo();
462
461
  if (getJdAndroidPageInfo) {
463
462
  info = getSystemInfos(getJdAndroidPageInfo);
464
463
  console.warn(
465
464
  '当前为松果安卓折叠屏app,获取折叠屏信息',
466
465
  getJdAndroidPageInfo,
467
466
  '获取转换后的系统信息',
468
467
  info,
469
468
  );
470
469
  sgmCustomReport({
471
470
  type: 2,
472
471
  code: 'android_jdapp_foldScreen_info',
473
472
  msg: {
474
473
  title: `松果安卓app为折叠屏,重置获取的系统宽高信息,因为获取宽高度信息初始化内部可能存在横竖屏差异`,
475
474
  androidPageInfo: getJdAndroidPageInfo,
476
475
  jdAppVersionStr,
477
476
  taroSysInfo: info,
478
477
  },
479
478
  });
480
479
  }
481
480
  }
482
481
  }
483
482
  if (isJdApp) {
484
483
  info?.isJdTabletDevice && this.listenJdTabletScreenChange();
485
484
  }
486
485
  this.info.sysInfo = {
487
486
  actualNavBarHeight: 0,
488
487
  ...this.info.sysInfo,
489
488
  ...info,
490
489
  safeContentHeight: info?.screenHeight,
491
490
  headerHeight: 0,
492
491
  tabBarHeight: 0,
493
492
  languageType: languageNowType,
494
493
  };
495
494
  if (isJdApp || isH5AndJingGouMini) {
496
495
  this.getLbsAddressCachePromise();
497
496
  }
498
497
  if (isJdApp) {
499
498
  this.info.sysInfo['hostVersionName'] = jdAppVersionStr;
500
499
  this.info.sysInfo['hostAppVersion'] = jdAppVersion;
501
500
  this.getAddressCachePromise();
502
501
  this.getElderModePromise();
503
502
  this.getJDAppearanceStatePromise();
504
503
  this.createJdAndroidRquestEventForTouchStart();
505
504
  }
506
505
  this.getWifiVideoAutoPlayAsync();
507
506
  this.getMPaasConfigAsync();
508
507
  this.getNetWorkType();
509
508
  }
510
509
 
511
510
  taskTimeoutPromise(callBack, timeout = 2000) {
512
511
  return new Promise((resolve) => {
513
512
  setTimeout(() => {
514
513
  const getCallBackRes = typeof callBack === 'function' && callBack();
515
514
  return resolve(getCallBackRes || false);
516
515
  }, timeout);
517
516
  });
518
517
  }
519
518
 
520
519
  getElderModePromise() {
521
520
  if (this.info.sysInfo.hasOwnProperty('jdAppModeType')) {
522
521
  return Promise.resolve(this.info.sysInfo.jdAppModeType);
523
522
  } else {
524
523
  if (isJdAndAndroidDevice) {
525
524
  this.info.sysInfo.jdAppModeType = '0';
526
525
  return Promise.resolve(this.info.sysInfo.jdAppModeType);
527
526
  } else {
528
527
  return Promise.race([
529
528
  this.taskTimeoutPromise(() => {
530
529
  this.info.sysInfo.jdAppModeType = '0';
531
530
  return this.info.sysInfo.jdAppModeType;
532
531
  }),
533
532
  new Promise((resolve) => {
534
533
  const getCallBackName = `getJdCurrentModeType${Date.now()}`;
535
534
  if (!window[getCallBackName]) {
536
535
  window[getCallBackName] = (res) => {
537
536
  try {
538
537
  const getResJson = typeof res === 'string' ? JSON.parse(res) : res;
539
538
  const { status, data, msg } = getResJson;
540
539
  console.log(`获取松果app展示模式成功,返回结果${data}`);
541
540
  if (status === '0') {
542
541
  this.info.sysInfo.jdAppModeType = data;
543
542
  resolve(data);
544
543
  } else {
545
544
  resolve('0');
546
545
  }
547
546
  } catch (e) {
548
547
  resolve('0');
549
548
  }
550
549
  window[getCallBackName] = null;
551
550
  };
552
551
  }
553
552
  window?.webkit?.messageHandlers?.JDAppUnite?.postMessage({
554
553
  method: 'callSyncRouterModuleWithParams',
555
554
  params: JSON.stringify({
556
555
  routerURL: 'router://JDBModeModule/getCurrentMode',
557
556
  routerParam: {},
558
557
  callBackName: `window.${getCallBackName}`,
559
558
  callBackId: `${getCallBackName}Ios`,
560
559
  }),
561
560
  });
562
561
  }),
563
562
  ]);
564
563
  }
565
564
  }
566
565
  }
567
566
  getAPPUseStraightCorner() {
568
567
  const routerURL = 'router://JDBaseUtilsModule/isUI14Enable';
569
568
  const params = {
570
569
  routerURL,
571
570
  routerParam: {},
572
571
  jdRouter: '1',
573
572
  };
574
573
  if (this.info.sysInfo.hasOwnProperty('jdStraightCorner')) {
575
574
  return Promise.resolve(this.info.sysInfo.jdStraightCorner);
576
575
  } else {
577
576
  return this.jmfeReayPromise()
578
577
  .then(() => {
579
578
  if (isJdAndHarmonyDevice || !isJdApp) {
580
579
  console.log('not APP or is Harmony');
581
580
  return Promise.resolve(false);
582
581
  }
583
582
  console.log('jmfe setShareInfo', params);
584
583
  return Promise.race([
585
584
  window.jmfe.callRouter(params),
586
585
  this.taskTimeoutPromise(() => {
587
586
  return false;
588
587
  }),
589
588
  ]).then(({ status, data }) => {
590
589
  console.log('004 ~ file: index.tsx:133 ~ .then ~ data:', data);
591
590
  console.log('004 ~ file: index.tsx:133 ~ .then ~ status:', status);
592
591
  this.info.sysInfo.jdStraightCorner = status === '0' && Number(data) === 1;
593
592
  return Promise.resolve(status === '0' && Number(data) === 1);
594
593
  });
595
594
  })
596
595
  .catch((e) => {
597
596
  console.log('jmfe error', e);
598
597
  return Promise.resolve(false);
599
598
  });
600
599
  }
601
600
  }
602
601
 
603
602
  getJDAppearanceStatePromise() {
604
603
  if (this.info.sysInfo.hasOwnProperty('jdAppearanceState')) {
605
604
  return Promise.resolve(this.info.sysInfo.jdAppearanceState);
606
605
  } else {
607
606
  return Promise.race([
608
607
  this.taskTimeoutPromise(() => {
609
608
  this.info.sysInfo.jdAppearanceState = '0';
610
609
  return this.info.sysInfo.jdAppearanceState;
611
610
  }),
612
611
  new Promise((resolve) => {
613
612
  const getCallBackName = `getJdCurrentAppearanceState${Date.now()}`;
614
613
  if (!window[getCallBackName]) {
615
614
  window[getCallBackName] = (res) => {
616
615
  try {
617
616
  console.log('getJDAppearanceStatePromise', res);
618
617
  const getResJson = typeof res === 'string' ? JSON.parse(res) : res;
619
618
  const { status, data, msg } = getResJson;
620
619
  console.log(`获取松果app是否开启黑暗模式成功,返回结果${data}`);
621
620
  if (status === '0') {
622
621
  this.info.sysInfo.jdAppearanceState = data;
623
622
  resolve(data);
624
623
  } else {
625
624
  resolve('0');
626
625
  }
627
626
  } catch (e) {
628
627
  resolve('0');
629
628
  }
630
629
  window[getCallBackName] = null;
631
630
  };
632
631
  }
633
632
  if (isAndroidDevice) {
634
633
  const jsonString = JSON.stringify({
635
634
  callBackName: `window.${getCallBackName}`,
636
635
  });
637
636
  console.log('window.JDAppearance', window?.JDAppearance);
638
637
  window?.JDAppearance &&
639
638
  window?.JDAppearance?.getUiState &&
640
639
  window.JDAppearance.getUiState(jsonString);
641
640
  } else {
642
641
  window?.webkit?.messageHandlers?.JDAppUnite?.postMessage({
643
642
  method: 'callSyncRouterModuleWithParams',
644
643
  params: JSON.stringify({
645
644
  routerURL: 'router://JDWebViewBusinessModule/getJDAppearanceState',
646
645
  routerParam: {},
647
646
  callBackName: `window.${getCallBackName}`,
648
647
  callBackId: `${getCallBackName}Ios`,
649
648
  }),
650
649
  });
651
650
  }
652
651
  }),
653
652
  ]);
654
653
  }
655
654
  }
656
655
 
657
656
  createJdAndroidRquestEventForTouchStart() {
658
657
  if (isJdAndAndroidDevice && window?.JdAndroid) {
659
658
  const rootEleNode = document.querySelector('body');
660
659
  if (rootEleNode) {
661
660
  rootEleNode.addEventListener('touchstart', this.jdAndroidAddEventListenerTouchStart, false);
662
661
  }
663
662
  }
664
663
  }
665
664
  jdAndroidAddEventListenerTouchStart(e) {
666
665
  const isH5SwiperCustomEle = e?.target?.closest('.J_h5SwiperCustom');
667
666
  if (!isH5SwiperCustomEle && window?.JdAndroid) {
668
667
  const hasCustomEle = e
669
668
  ? e?.target?.closest('.J_customScroll') || e?.target?.closest('.J_customLayout')
670
669
  : false;
671
670
  if (!hasCustomEle) {
672
671
  window?.JdAndroid?.requestEvent && window.JdAndroid.requestEvent(false);
673
672
  console.log(
674
673
  'createJdAndroidRquestEvent 所有松果安卓APP内的document touch start事件执行检测requestEvent并重置为false',
675
674
  );
676
675
  }
677
676
  }
678
677
  }
679
678
  removeJdAndroidRquestEventForTouchStart() {
680
679
  if (isJdAndAndroidDevice && window.JdAndroid) {
681
680
  const rootEleNode = document.querySelector('body');
682
681
  if (rootEleNode) {
683
682
  rootEleNode.removeEventListener(
684
683
  'touchstart',
685
684
  this.jdAndroidAddEventListenerTouchStart,
686
685
  false,
687
686
  );
688
687
  }
689
688
  }
690
689
  }
691
690
 
692
691
  getNetWorkType() {
693
692
  if (isJdApp) {
694
693
  this.jmfeReayPromise().then(() => {
695
694
  window.jmfe
696
695
  .getNetworkStatus()
697
696
  .then(({ status, data }) => {
698
697
  console.log('在app内初始化通过jmfe对象获取网络状态完成,当前网络状态====', data);
699
698
  if (status === '0') {
700
699
  this.info.sysInfo['netWorkType'] = data;
701
700
  } else {
702
701
  this._taroGetNetworkType();
703
702
  }
704
703
  })
705
704
  .catch((err) => {
706
705
  console.log('在app内初始化通过jmfe对象获取网络状态异常====', err);
707
706
  this._taroGetNetworkType();
708
707
  });
709
708
  });
710
709
  } else {
711
710
  this._taroGetNetworkType();
712
711
  }
713
712
  }
714
713
  _taroGetNetworkType() {
715
714
  Taro.getNetworkType().then((getRes) => {
716
715
  if (getRes && getRes.networkType) {
717
716
  this.info.sysInfo['netWorkType'] = getRes.networkType;
718
717
  console.log(
719
718
  '在app内通过taro对象获取网络状态完成,当前网络状态',
720
719
  this.info.sysInfo['netWorkType'],
721
720
  );
722
721
  }
723
722
  });
724
723
  }
725
724
 
726
725
  getCacheAddressRouter() {
727
726
  if (isJdApp) {
728
727
  if (!isJdAndHarmonyDevice) {
729
728
  return Promise.race([
730
729
  new Promise((resolve) => {
731
730
  const getCallBackName = `getJdCacheAddress${Date.now()}`;
732
731
  if (!window[getCallBackName]) {
733
732
  window[getCallBackName] = (res) => {
734
733
  console.warn(`获取松果appGetJdCacheAddressRes,返回结果`, res);
735
734
  try {
736
735
  const getResJson = typeof res === 'string' ? JSON.parse(res) : res;
737
736
  resolve(getResJson);
738
737
  } catch (e) {
739
738
  resolve({
740
739
  status: '-1002',
741
740
  msg: '地址信息解析json异常',
742
741
  res,
743
742
  });
744
743
  }
745
744
  window[getCallBackName] = null;
746
745
  };
747
746
  }
748
747
  const getRouterParam = {
749
748
  sceneId: 'basicShoppingProcess',
750
749
  };
751
750
  if (isAndroidDevice) {
752
751
  return callRouterAndroid({
753
752
  routerURL: 'router://JDAddressModule/getCacheAddress',
754
753
  routerParam: getRouterParam,
755
754
  callBackName: getCallBackName,
756
755
  isSync: true,
757
756
  });
758
757
  } else {
759
758
  return callRouterIOS({
760
759
  routerURL: 'router://JDBAddressCacheManagerModule/getCacheAddress',
761
760
  routerParam: getRouterParam,
762
761
  callBackName: getCallBackName,
763
762
  });
764
763
  }
765
764
  }),
766
765
  this.taskTimeoutPromise(() => {
767
766
  return {
768
767
  status: '-1000',
769
768
  msg: '原生router协议获取地址信息超时',
770
769
  };
771
770
  }, 3000),
772
771
  ]);
773
772
  } else {
774
773
  return Promise.resolve({
775
774
  status: '-1001',
776
775
  msg: '鸿蒙系统调用jmfe异常,获取失败',
777
776
  });
778
777
  }
779
778
  } else if (isH5AndJingGouMini) {
780
779
  return Promise.resolve({
781
780
  status: '-1002',
782
781
  msg: '普通h5暂无业务需要,未实现,获取失败',
783
782
  });
784
783
  } else {
785
784
  return Promise.resolve({
786
785
  status: '-1002',
787
786
  msg: '普通h5暂无业务需要,未实现,获取失败',
788
787
  });
789
788
  }
790
789
  }
791
790
 
792
791
  getAddressCachePromise() {
793
792
  return new Promise((resolve) => {
794
793
  if (this?.info?.sysInfo?.lat && this?.info?.sysInfo?.lng && this?.info?.sysInfo?.area) {
795
794
  resolve({
796
795
  lat: this.info.sysInfo.lat,
797
796
  lng: this.info.sysInfo.lng,
798
797
  area: this?.info?.sysInfo?.area,
799
798
  });
800
799
  } else {
801
800
  this.getCacheAddressRouter()
802
801
  .then((res) => {
803
802
  const { status, data } = res;
804
803
  console.log('原生端获取经纬度及四级地址原始数据结果', status, data, res);
805
804
  if (status === '0' && data) {
806
805
  const { lat, latitude, lng, longitude, provinceId, cityId, countyId, townId } =
807
806
  data || {};
808
807
  let area = '';
809
808
  this.info.sysInfo['lat'] = `${lat || latitude || ''}`;
810
809
  this.info.sysInfo['lng'] = `${lng || longitude || ''}`;
811
810
  const getProvinceIdNum = provinceId ? Number(provinceId) : 0;
812
811
  if (getProvinceIdNum && getProvinceIdNum > 0) {
813
812
  area = `${provinceId}_${cityId || 0}_${countyId || 0}_${townId || 0}`;
814
813
  this.info.pageInfo['address'] = area;
815
814
  this.info.pageInfo['addressCommaStr'] = area.replace(/_/g, ',');
816
815
  this.info.sysInfo['area'] = area;
817
816
  Taro.eventCenter.trigger(TaroEventType.USER_AREA_UPDATE, {
818
817
  area: this.info.pageInfo.address,
819
818
  });
820
819
  }
821
820
  resolve({
822
821
  lat: this.info.sysInfo['lat'],
823
822
  lng: this.info.sysInfo['lng'],
824
823
  area: area,
825
824
  });
826
825
  } else {
827
826
  if (typeof res === 'object') {
828
827
  draBusinessCustomReport({
829
828
  type: 'jdapp_getCacheAddress_info_err',
830
829
  errMsg: '松果app内通过router协议获取用户地址及经纬度信息异常',
831
830
  originReqDataStr: JSON.stringify({
832
831
  isJdApp,
833
832
  jdAppVersion: jdAppVersionStr,
834
833
  ...res,
835
834
  }),
836
835
  });
837
836
  }
838
837
  resolve({ lat: '', lng: '', area: '' });
839
838
  }
840
839
  })
841
840
  .catch((e) => {
842
841
  console.log('getCacheAddressRouter catch e,获取经纬度信息异常e', e);
843
842
  draBusinessCustomReport({
844
843
  type: 'jdapp_getCacheAddress_info_catch_err',
845
844
  errMsg: '松果app内通过router协议获取用户地址及经纬度信息catch异常',
846
845
  originReqDataStr: JSON.stringify({
847
846
  isJdApp,
848
847
  jdAppVersion: jdAppVersionStr,
849
848
  }),
850
849
  });
851
850
  resolve({ lat: '', lng: '', area: '' });
852
851
  });
853
852
  }
854
853
  });
855
854
  }
856
855
 
857
856
  getLbsCacheAddressRouter() {
858
857
  if (isJdApp) {
859
858
  if (!isJdAndHarmonyDevice) {
860
859
  return Promise.race([
861
860
  new Promise((resolve) => {
862
861
  const getCallBackName = `getJdLbsCacheAddress${Date.now()}`;
863
862
  if (!window[getCallBackName]) {
864
863
  window[getCallBackName] = (res) => {
865
864
  console.warn(`获取松果appGetJdLbsCacheAddressRes,返回结果`, res);
866
865
  try {
867
866
  const getResJson = typeof res === 'string' ? JSON.parse(res) : res;
868
867
  resolve(getResJson);
869
868
  } catch (e) {
870
869
  resolve({
871
870
  status: '-1002',
872
871
  msg: '地址信息解析json异常',
873
872
  res,
874
873
  });
875
874
  }
876
875
  window[getCallBackName] = null;
877
876
  };
878
877
  }
879
878
  const getRouterParam = {
880
879
  appid: '219f70bbbf7e4ede7968bedaa1beafb4',
881
880
  sceneId: 'basicShoppingProcess',
882
881
  };
883
882
  if (isAndroidDevice) {
884
883
  return callRouterAndroid({
885
884
  routerURL: 'router://com.jingdong.app.mall.location.JSLocationManager/getLocation',
886
885
  routerParam: getRouterParam,
887
886
  callBackName: getCallBackName,
888
887
  isSync: true,
889
888
  hasJdRouter: false,
890
889
  });
891
890
  } else {
892
891
  return callRouterIOS({
893
892
  routerURL: 'router://JDBLBSKitModule/getCacheAddressInfo',
894
893
  routerParam: getRouterParam,
895
894
  callBackName: getCallBackName,
896
895
  isSync: true,
897
896
  });
898
897
  }
899
898
  }),
900
899
  this.taskTimeoutPromise(() => {
901
900
  return {
902
901
  status: '-1000',
903
902
  msg: '原生router协议获取lbs地址信息3s超时',
904
903
  };
905
904
  }, 3000),
906
905
  ]);
907
906
  } else {
908
907
  return Promise.resolve({
909
908
  status: '-1001',
910
909
  msg: '鸿蒙系统调用未实现,获取失败',
911
910
  });
912
911
  }
913
912
  } else if (isH5AndJingGouMini) {
914
913
  return this.getLocationForGpsPromise();
915
914
  } else {
916
915
  return Promise.resolve({
917
916
  status: '-1002',
918
917
  msg: '普通h5暂无业务需要,未实现,获取失败',
919
918
  });
920
919
  }
921
920
  }
922
921
  getLocationForGpsPromise() {
923
922
  return new Promise((resolve) => {
924
923
  let hasGetLocationForGps = true;
925
924
  if (urlCookie && urlCookie['loc']) {
926
925
  const [provinceid = 0, cityid = 0, districtid = 0, townid = 0] =
927
926
  urlCookie['loc'].split('_');
928
927
  const getProvinceIdNum = provinceid ? Number(provinceid) : 0;
929
928
  if (getProvinceIdNum && getProvinceIdNum > 0) {
930
929
  hasGetLocationForGps = false;
931
930
  resolve({
932
931
  status: '0',
933
932
  data: {
934
933
  provinceid,
935
934
  cityid,
936
935
  districtid,
937
936
  townid,
938
937
  origin: 'wxapp',
939
938
  },
940
939
  });
941
940
  }
942
941
  }
943
942
  if (hasGetLocationForGps && window?.navigator?.geolocation) {
944
943
  window.navigator.geolocation.getCurrentPosition(
945
944
  (position) => {
946
945
  console.log('h5 浏览器通过原生geolocation获取经纬度结果', position?.coords);
947
946
  if (position?.coords) {
948
947
  resolve({
949
948
  status: '0',
950
949
  data: {
951
950
  srclat: position.coords?.latitude,
952
951
  srclng: position.coords.longitude,
953
952
  origin: 'h5',
954
953
  },
955
954
  });
956
955
  } else {
957
956
  resolve({
958
957
  status: '-1001',
959
958
  msg: 'h5 浏览器通过原生geolocation获取经纬度结果异常,详情见position',
960
959
  position,
961
960
  });
962
961
  }
963
962
  },
964
963
  (error) => {
965
964
  resolve({
966
965
  status: '-1001',
967
966
  msg: 'h5 浏览器通过原生geolocation获取经纬度结果定位异常,详情见error',
968
967
  error,
969
968
  });
970
969
  },
971
970
  {
972
971
  enableHighAccuracy: false,
973
972
  timeout: 3 * 1000,
974
973
  maximumAge: 10 * 60 * 1000,
975
974
  },
976
975
  );
977
976
  } else {
978
977
  resolve({
979
978
  status: '-1001',
980
979
  msg: '您的浏览器不支持地理定位',
981
980
  });
982
981
  }
983
982
  });
984
983
  }
985
984
 
986
985
  createLbsCacheAddress(realTimeArea) {
987
986
  const getLbsAddressCacheMinuteTime = Number(
988
987
  window?.shopGlobalSwitch?.lbsAddressCacheToCookieMinuteTime || 0,
989
988
  );
990
989
  console.log(
991
990
  '获取lbs缓存到cookie的时间,分钟',
992
991
  getLbsAddressCacheMinuteTime,
993
992
  'lbsAddressCacheToCookieMinuteTime',
994
993
  window?.shopGlobalSwitch?.lbsAddressCacheToCookieMinuteTime,
995
994
  );
996
995
  if (getLbsAddressCacheMinuteTime > 0) {
997
996
  const expires = new Date(Date.now() + getLbsAddressCacheMinuteTime * 60 * 1000);
998
997
  realTimeArea &&
999
998
  cookie.set(cacheH5LbsAddressKey, realTimeArea, {
1000
999
  path: '/',
1001
1000
  expires,
1002
1001
  });
1003
1002
  }
1004
1003
  }
1005
1004
 
1006
1005
  getLbsAddressCachePromise() {
1007
1006
  if (!this.lbsAddressCachePromise) {
1008
1007
  this.lbsAddressCachePromise = new Promise((resolve) => {
1009
1008
  const getCookieForLbsAddress = window?.shopGlobalSwitch?.lbsAddressCacheToCookieMinuteTime
1010
1009
  ? cookie.get(cacheH5LbsAddressKey)
1011
1010
  : '';
1012
1011
  const getUserLbsAddress = this?.info?.pageInfo?.userLbsAddress;
1013
1012
  if (getUserLbsAddress && getUserLbsAddress !== '') {
1014
1013
  resolve({
1015
1014
  ok: true,
1016
1015
  realTimeArea: getUserLbsAddress,
1017
1016
  });
1018
1017
  } else if (getCookieForLbsAddress && getCookieForLbsAddress !== '') {
1019
1018
  console.info(
1020
1019
  `通过cookie获取缓存的userLbsAddress,${window?.shopGlobalSwitch?.lbsAddressCacheToCookieMinuteTime}分钟内有效`,
1021
1020
  getCookieForLbsAddress,
1022
1021
  );
1023
1022
  this.info.pageInfo['userLbsAddress'] = getCookieForLbsAddress;
1024
1023
  this.info.sysInfo['realTimeArea'] = getCookieForLbsAddress;
1025
1024
  Taro.eventCenter.trigger(TaroEventType.USER_AREA_UPDATE, {
1026
1025
  realTimeArea: getCookieForLbsAddress,
1027
1026
  });
1028
1027
  resolve({
1029
1028
  ok: true,
1030
1029
  realTimeArea: getCookieForLbsAddress,
1031
1030
  });
1032
1031
  } else {
1033
1032
  this.getLbsCacheAddressRouter()
1034
1033
  .then((res) => {
1035
1034
  const { status, data } = res;
1036
1035
  console.log(
1037
1036
  '原生或者内嵌京购端获取基于lbs的经纬度及四级地址原始数据结果',
1038
1037
  status,
1039
1038
  data,
1040
1039
  res,
1041
1040
  );
1042
1041
  if (status === '0' && data) {
1043
1042
  const { srclat, srclng, provinceid, cityid, districtid, townid, origin } =
1044
1043
  data || {};
1045
1044
  let realTimeArea = '';
1046
1045
  this.info.sysInfo['srclat'] = `${srclat || ''}`;
1047
1046
  this.info.sysInfo['srclng'] = `${srclng || ''}`;
1048
1047
  const getProvinceIdNum = provinceid ? Number(provinceid) : 0;
1049
1048
  if (getProvinceIdNum && getProvinceIdNum > 0) {
1050
1049
  realTimeArea = `${provinceid}_${cityid || 0}_${districtid || 0}_${townid || 0}`;
1051
1050
  this.info.pageInfo['userLbsAddress'] = realTimeArea;
1052
1051
  this.info.sysInfo['realTimeArea'] = realTimeArea;
1053
1052
  Taro.eventCenter.trigger(TaroEventType.USER_AREA_UPDATE, {
1054
1053
  realTimeArea: this.info.pageInfo.userLbsAddress,
1055
1054
  });
1056
1055
  this.createLbsCacheAddress(realTimeArea);
1057
1056
  } else {
1058
1057
  !origin && (this.lbsAddressCachePromise = null);
1059
1058
  }
1060
1059
  const getValidRealTimeArea = realTimeArea !== '';
1061
1060
  resolve({
1062
1061
  lat: this.info.sysInfo['srclat'],
1063
1062
  lng: this.info.sysInfo['srclng'],
1064
1063
  realTimeArea: realTimeArea,
1065
1064
  ok: getValidRealTimeArea,
1066
1065
  msg: getValidRealTimeArea
1067
1066
  ? '成功'
1068
1067
  : origin
1069
1068
  ? origin
1070
1069
  : '根据router底层获取lbs地址信息异常,详情见data',
1071
1070
  data: getValidRealTimeArea ? null : res,
1072
1071
  });
1073
1072
  if (!getValidRealTimeArea && !origin) {
1074
1073
  draBusinessCustomReport({
1075
1074
  type: 'h5_getLbsCacheAddress_info_err',
1076
1075
  errMsg: '松果app内通过router协议获取基于lbs实时用户地址及经纬度信息catch异常',
1077
1076
  originReqDataStr: JSON.stringify({
1078
1077
  isJdApp,
1079
1078
  jdAppVersion: jdAppVersionStr,
1080
1079
  }),
1081
1080
  });
1082
1081
  }
1083
1082
  } else {
1084
1083
  typeof res === 'object' &&
1085
1084
  draBusinessCustomReport({
1086
1085
  type: 'h5_getLbsCacheAddress_info_err',
1087
1086
  errMsg:
1088
1087
  'h5通过router协议或者浏览器gps获取基于lbs实时用户缓存地址及经纬度信息异常',
1089
1088
  originReqDataStr: JSON.stringify({
1090
1089
  isJdApp,
1091
1090
  jdAppVersion: jdAppVersionStr,
1092
1091
  ...res,
1093
1092
  }),
1094
1093
  });
1095
1094
  this.lbsAddressCachePromise = null;
1096
1095
  resolve({ realTimeArea: '', ok: false });
1097
1096
  }
1098
1097
  })
1099
1098
  .catch((e) => {
1100
1099
  console.log('getLbsAddressCachePromise catch e,获取经纬度信息异常e', e);
1101
1100
  this.lbsAddressCachePromise = null;
1102
1101
  draBusinessCustomReport({
1103
1102
  type: 'h5_getLbsCacheAddress_info_err',
1104
1103
  errMsg:
1105
1104
  'h5内通过router协议获取浏览器gps获取基于lbs实时用户地址及经纬度信息catch异常',
1106
1105
  originReqDataStr: JSON.stringify({
1107
1106
  isJdApp,
1108
1107
  jdAppVersion: jdAppVersionStr,
1109
1108
  }),
1110
1109
  });
1111
1110
  resolve({ realTimeArea: '', ok: false });
1112
1111
  });
1113
1112
  }
1114
1113
  });
1115
1114
  }
1116
1115
  return this.lbsAddressCachePromise;
1117
1116
  }
1118
1117
 
1119
1118
  async updateMPaasConfigAsync(isBeforePageReady: boolean) {
1120
1119
  console.log('updateMPaasConfigAsync isBeforePageReady:', isBeforePageReady);
1121
1120
  if (!isJdApp) {
1122
1121
  return;
1123
1122
  }
1124
1123
  const avifSwitch = await getMPaasConfigByBussinessKey('avifSwitch', isBeforePageReady);
1125
1124
  this.info.sysInfo.dynamicConfig['avifSwitch'] = avifSwitch;
1126
1125
  const hybridHttpSwitch = await getMPaasConfigByBussinessKey(
1127
1126
  'hybridHttpSwitch',
1128
1127
  isBeforePageReady,
1129
1128
  );
1130
1129
  this.info.sysInfo.dynamicConfig['hybridHttpSwitch'] = hybridHttpSwitch;
1131
1130
  const isFollowAppVideoPlayStatus = await getMPaasConfigByBussinessKey(
1132
1131
  'isFollowAppVideoPlayStatus',
1133
1132
  isBeforePageReady,
1134
1133
  );
1135
1134
  console.log(
1136
1135
  'isBeforePageReady:',
1137
1136
  isBeforePageReady,
1138
1137
  'isFollowAppVideoPlayStatus:',
1139
1138
  isFollowAppVideoPlayStatus,
1140
1139
  );
1141
1140
  if (isFollowAppVideoPlayStatus === true || isFollowAppVideoPlayStatus === 'true') {
1142
1141
  this.info.sysInfo.dynamicConfig['isFollowAppVideoPlayStatus'] = true;
1143
1142
  }
1144
1143
  }
1145
1144
 
1146
1145
  async getWifiVideoAutoPlayAsync() {
1147
1146
  this.info.sysInfo['wifiVideoAutoPlay'] = false;
1148
1147
  if (!isJdApp) {
1149
1148
  return;
1150
1149
  }
1151
1150
  const videoPlayStatus = await getWifiVideoAutoPlay().catch((e) => {
1152
1151
  return 0;
1153
1152
  });
1154
1153
  if (Number(videoPlayStatus) === 1) {
1155
1154
  this.info.sysInfo['wifiVideoAutoPlay'] = true;
1156
1155
  }
1157
1156
  }
1158
1157
 
1159
1158
  async getMPaasConfigAsync() {
1160
1159
  this.info.sysInfo.dynamicConfig = {};
1161
1160
  this.info.sysInfo.dynamicConfig['avifSwitch'] = {};
1162
1161
  this.info.sysInfo.dynamicConfig['hybridHttpSwitch'] = {};
1163
1162
  this.info.sysInfo.dynamicConfig['isFollowAppVideoPlayStatus'] = false;
1164
1163
  return this.updateMPaasConfigAsync(true);
1165
1164
  }
1166
1165
 
1167
1166
  getDynamicConfig(key: string) {
1168
1167
  return this.info.sysInfo?.dynamicConfig?.[key];
1169
1168
  }
1170
1169
  async updateMPaasConfig() {
1171
1170
  console.log('updateMPaasConfig');
1172
1171
  if (
1173
1172
  isIosDevice &&
1174
1173
  versionCompare(jdAppVersionStr, MPAAS_CONFIG_APP_VERSION) < 0 &&
1175
1174
  versionCompare(jdAppVersionStr, MPAAS_CONFIG_APP_LOW_VERSION) >= 0
1176
1175
  ) {
1177
1176
  try {
1178
1177
  await this.updateMPaasConfigAsync(false);
1179
1178
  } catch (e) {
1180
1179
  console.log('updateMPaasConfigAsync:', e);
1181
1180
  }
1182
1181
  }
1183
1182
  }
1184
1183
 
1185
1184
  toLogin(options) {
1186
1185
  return this.info.isJingGouMiniViewState || this.info.isJingxiMiniViewState
1187
1186
  ? this.toWxAppLogin(options)
1188
1187
  : this.toWebLogin(options);
1189
1188
  }
1190
1189
 
1191
1190
  doLogin(options) {
1192
1191
  return this.toLogin(options);
1193
1192
  }
1194
1193
 
1195
1194
  doLoginForJdPin(options = {}) {
1196
1195
  return this.doLogin({
1197
1196
  loginColor: {
1198
1197
  biz: WXAPP_BIZ_SHOP_LIGHT_KEY,
1199
1198
  dpin: 0,
1200
1199
  },
1201
1200
  ...options,
1202
1201
  });
1203
1202
  }
1204
1203
 
1205
1204
  toWebLogin(options) {
1206
1205
  let params: {
1207
1206
  returnurl: string;
1208
1207
  } = {
1209
1208
  returnurl: '',
1210
1209
  };
1211
1210
  const checkToPcLogin = options ? options?.isPc : isPc;
1212
1211
  const loginUrl = checkToPcLogin
1213
1212
  ? `//passport.jd.com/new/login.aspx`
1214
1213
  : `${domain.mobileLogin}/user/login.action`;
1215
1214
  const defaultParams = {
1216
1215
  appid: '100',
1217
1216
  returnurl: window.location.href,
1218
1217
  };
1219
1218
  if (isString(options)) {
1220
1219
  params = Object.assign({}, defaultParams, {
1221
1220
  returnurl: options,
1222
1221
  });
1223
1222
  } else if (isObject(options)) {
1224
1223
  const { loginColor, ...otherOptions } = options;
1225
1224
  params = Object.assign({}, defaultParams, otherOptions);
1226
1225
  } else {
1227
1226
  params = defaultParams;
1228
1227
  }
1229
1228
  params.returnurl = encodeURIComponent(params.returnurl);
1230
1229
  let getFullUrl = loginUrl + '?' + serialize(params);
1231
1230
  if (checkToPcLogin) {
1232
1231
  getFullUrl = getFullUrl.replace(/returnurl/, 'ReturnUrl');
1233
1232
  }
1234
1233
  return Promise.resolve({
1235
1234
  h5ToUrl: true,
1236
1235
  url: getFullUrl,
1237
1236
  }).then(() => {
1238
1237
  window.location.href = getFullUrl;
1239
1238
  });
1240
1239
  }
1241
1240
 
1242
1241
  toWxAppLogin(options = {}) {
1243
1242
  console.log('微信京购小程序中h5登录跳转', options);
1244
1243
  return Promise.resolve(true).then(() => {
1245
1244
  const { loginColor } = Object.assign(
1246
1245
  {},
1247
1246
  {
1248
1247
  loginColor: {
1249
1248
  biz: WXAPP_BIZ_KEY,
1250
1249
  dpin: 1,
1251
1250
  },
1252
1251
  },
1253
1252
  options,
1254
1253
  );
1255
1254
  window.location.href = `${domain.wq}/pinbind/pintokenredirect?biz=${
1256
1255
  loginColor.biz
1257
1256
  }&url=${encodeURIComponent(window.location.href)}`;
1258
1257
  });
1259
1258
  }
1260
1259
 
1261
1260
  getLoginCookie() {
1262
1261
  return Promise.resolve({
1263
1262
  pin: cookie.get('pin') || '',
1264
1263
  });
1265
1264
  }
1266
1265
 
1267
1266
  clearLoginCookie() {
1268
1267
  cookie.remove('pin');
1269
1268
  }
1270
1269
 
1271
1270
  checkStatusAndLogin(options = {}) {
1272
1271
  if (!this.checkStatusAndLoginPromise) {
1273
1272
  this.checkStatusAndLoginPromise = new Promise(async (resolve, reject) => {
1274
1273
  try {
1275
1274
  const getLoginState = await this.doCheckLoginStateAndForApiCheck(options);
1276
1275
  if (getLoginState) {
1277
1276
  resolve(true);
1278
1277
  } else {
1279
1278
  this.toLogin(options);
1280
1279
  reject(false);
1281
1280
  }
1282
1281
  } catch (e) {
1283
1282
  this.toLogin(options);
1284
1283
  reject(false);
1285
1284
  }
1286
1285
  });
1287
1286
  return this.checkStatusAndLoginPromise;
1288
1287
  } else {
1289
1288
  return this.checkStatusAndLoginPromise
1290
1289
  .then(() => {
1291
1290
  return Promise.resolve(true);
1292
1291
  })
1293
1292
  .catch(() => {
1294
1293
  this.toLogin(options);
1295
1294
  return Promise.reject(true);
1296
1295
  });
1297
1296
  }
1298
1297
  }
1299
1298
 
1300
1299
  checkJdStatusAndLogin(
1301
1300
  options = {
1302
1301
  loginColor: {
1303
1302
  biz: WXAPP_BIZ_SHOP_LIGHT_KEY,
1304
1303
  dpin: 0,
1305
1304
  },
1306
1305
  },
1307
1306
  ) {
1308
1307
  return this.checkStatusAndLogin(options);
1309
1308
  }
1310
1309
 
1311
1310
  doCheckLoginStateAndForApiCheck(options) {
1312
1311
  if (this.info.loginState) {
1313
1312
  return Promise.resolve(true);
1314
1313
  } else {
1315
1314
  return new Promise((resolve, reject) => {
1316
1315
  if (this.info.isJingGouMiniViewState || this.info.isJingxiMiniViewState) {
1317
1316
  const getWqAuthToken = cookie.get('wq_auth_token');
1318
1317
  const getWqSkey = cookie.get('wq_skey');
1319
1318
  const getWqUin = cookie.get('wq_uin');
1320
1319
  const isLoginState =
1321
1320
  options?.loginColor?.dpin === 0 ? getWqAuthToken : getWqSkey && getWqUin;
1322
1321
  if (isLoginState) {
1323
1322
  this.info.loginState = true;
1324
1323
  resolve(true);
1325
1324
  } else {
1326
1325
  reject(false);
1327
1326
  }
1328
1327
  } else {
1329
1328
  Taro.request({
1330
1329
  url: api.isLogin,
1331
1330
  jsonp: true,
1332
1331
  timeout: 3000,
1333
1332
  success: (res) => {
1334
1333
  const { statusCode, data } = res;
1335
1334
  if (statusCode === 200 && data?.islogin && Number(data.islogin) === 1) {
1336
1335
  this.info.loginState = true;
1337
1336
  resolve(true);
1338
1337
  } else {
1339
1338
  reject(false);
1340
1339
  }
1341
1340
  },
1342
1341
  fail: (err) => {
1343
1342
  console.log('登录检查异常', err);
1344
1343
  reject(false);
1345
1344
  },
1346
1345
  });
1347
1346
  }
1348
1347
  });
1349
1348
  }
1350
1349
  }
1351
1350
 
1352
1351
  checkLoginStatus(options) {
1353
1352
  return new Promise(async (resolve, reject) => {
1354
1353
  try {
1355
1354
  const getLoginState = await this.doCheckLoginStateAndForApiCheck(options);
1356
1355
  if (getLoginState) {
1357
1356
  const { pin } = await this.getLoginCookie();
1358
1357
  this.info.userInfo = {
1359
1358
  pin,
1360
1359
  encodePin: encodeURIComponent(pin),
1361
1360
  ptkey: '',
1362
1361
  };
1363
1362
  resolve(true);
1364
1363
  } else {
1365
1364
  reject(false);
1366
1365
  }
1367
1366
  } catch (e) {
1368
1367
  reject(false);
1369
1368
  }
1370
1369
  });
1371
1370
  }
1372
1371
 
1373
1372
  updatePageAndLogInfo(updateQuery = {}) {
1374
1373
  const createUpdateQueryInfo: {
1375
1374
  query: {
1376
1375
  shopId?: string | number;
1377
1376
  venderId?: string | number;
1378
1377
  };
1379
1378
  updateShopInfoState: boolean;
1380
1379
  } = Object.assign(
1381
1380
  {},
1382
1381
  {
1383
1382
  query: {},
1384
1383
  updateShopInfoState: false,
1385
1384
  },
1386
1385
  updateQuery,
1387
1386
  );
1388
1387
  console.log(
1389
1388
  '获取当前下发的店铺查询参数',
1390
1389
  updateQuery,
1391
1390
  '获取之前保存的shopInfo店铺查询参数',
1392
1391
  this.info?.shopInfo,
1393
1392
  );
1394
1393
  const { query, updateShopInfoState } = createUpdateQueryInfo;
1395
1394
  const { shopId, venderId, un_area } = query;
1396
1395
  if (updateShopInfoState) {
1397
1396
  this.info.queryInfo = {
1398
1397
  ...this.info.queryInfo,
1399
1398
  ...query,
1400
1399
  };
1401
1400
  if (shopId && venderId) {
1402
1401
  this.info.shopInfo = {
1403
1402
  shopId: `${shopId}`,
1404
1403
  venderId: `${venderId}`,
1405
1404
  };
1406
1405
  }
1407
1406
  } else {
1408
1407
  this.info.queryInfo = {
1409
1408
  ...query,
1410
1409
  };
1411
1410
  if (
1412
1411
  this.info.shopInfo?.shopId &&
1413
1412
  this.info.shopInfo?.venderId &&
1414
1413
  (this.info.shopInfo.shopId == shopId || this.info.shopInfo.venderId == venderId)
1415
1414
  ) {
1416
1415
  this.info.queryInfo.shopId = this.info.shopInfo.shopId;
1417
1416
  this.info.queryInfo.venderId = this.info.shopInfo.venderId;
1418
1417
  console.log(
1419
1418
  '当前存储的店铺shopId和venderId与下发的店铺信息shopId或者venderId为同一个,补充shopId或者venderId查询参数',
1420
1419
  this.info.queryInfo,
1421
1420
  );
1422
1421
  }
1423
1422
  }
1424
1423
  this.info.queryInfo['shopId'] &&
1425
1424
  (this.info.queryInfo['shopId'] = `${this.info.queryInfo['shopId']}`);
1426
1425
  this.info.queryInfo['venderId'] &&
1427
1426
  (this.info.queryInfo['venderId'] = `${this.info.queryInfo['venderId']}`);
1428
1427
  console.log(
1429
1428
  'h5==获取店铺下发查询参数\n',
1430
1429
  query,
1431
1430
  '\n获取店铺最后查询参数\n',
1432
1431
  this.info.queryInfo,
1433
1432
  '\n是否为更新店铺状态\n',
1434
1433
  updateShopInfoState,
1435
1434
  );
1436
1435
  const changeArea = un_area && un_area.length > 0 ? un_area : isPc && ipLoc_djd ? ipLoc_djd : '';
1437
1436
  if (changeArea) {
1438
1437
  const getBottomAreaStr = changeArea.replace(/-/g, '_');
1439
1438
  this.info.pageInfo.address = getBottomAreaStr;
1440
1439
  this.info.pageInfo.un_area = getBottomAreaStr;
1441
1440
  this.info.pageInfo.addressCommaStr = getBottomAreaStr.replace(/_/g, ',');
1442
1441
  }
1443
1442
  }
1444
1443
 
1445
1444
  dealLoadSdkList() {
1446
1445
  const globalLoadJsList = window?.shopGlobalSwitch?.asyncLoadJsList ?? [];
1447
1446
  const businessLoadJsList = window?.PAGE_DATA?.businessData?.asyncLoadJsList ?? [];
1448
1447
  const concatLoadJsList = [].concat(globalLoadJsList, businessLoadJsList);
1449
1448
  let mergeLoadJsList = globalLoadJsList;
1450
1449
  try {
1451
1450
  mergeLoadJsList = concatLoadJsList.reduce((accArr: any[], current: any) => {
1452
1451
  const getFindIndex = accArr.findIndex((item) => item?.fileName === current?.fileName);
1453
1452
  getFindIndex !== -1
1454
1453
  ? (accArr[getFindIndex] = { ...accArr[getFindIndex], ...current })
1455
1454
  : accArr.push(current);
1456
1455
  return accArr;
1457
1456
  }, []);
1458
1457
  } catch (e) {
1459
1458
  console.log('LoadJsList合并错误', e);
1460
1459
  }
1461
1460
  console.log(
1462
1461
  'globalLoadJsList',
1463
1462
  globalLoadJsList,
1464
1463
  'businessLoadJsList',
1465
1464
  businessLoadJsList,
1466
1465
  '两个加载jsList集合合并完成',
1467
1466
  mergeLoadJsList,
1468
1467
  );
1469
1468
  this.loadJsSdkList = mergeLoadJsList;
1470
1469
  return this.loadJsSdkList;
1471
1470
  }
1472
1471
 
1473
1472
  renderNextTickLoadSdk() {
1474
1473
  Taro.nextTick(() => {
1475
1474
  console.log(
1476
1475
  '页面渲染的下一帧执行的js加载方法,当前nextTick存在state的渲染问题,先延迟1s=======',
1477
1476
  );
1478
1477
  setTimeout(() => {
1479
1478
  this.loadOtherSdk(LoadJsInitTriggerType.NRXT_TICK, this.loadJsSdkList);
1480
1479
  }, 1000);
1481
1480
  });
1482
1481
  }
1483
1482
 
1484
1483
  loadOtherSdk(triggerType = LoadJsInitTriggerType.NOW, loadJsList: any[] = []) {
1485
1484
  const getLoadJsList =
1486
1485
  Array.isArray(loadJsList) && loadJsList.length > 0 ? loadJsList : this.dealLoadSdkList();
1487
1486
  const getLoadFilterList = getLoadJsList.filter((item) => {
1488
1487
  const getInitLoadEnvType = item?.initLoadEnvType || LoadJsInitLoadEnvType.ALL;
1489
1488
  let getLoastLoadEventState = true;
1490
1489
  if (getInitLoadEnvType === LoadJsInitLoadEnvType.JD_APP) {
1491
1490
  getLoastLoadEventState = isJdApp;
1492
1491
  }
1493
1492
  else if (getInitLoadEnvType === LoadJsInitLoadEnvType.M) {
1494
1493
  getLoastLoadEventState = !isJdApp || !!isJdAndHarmonyDevice;
1495
1494
  }
1496
1495
  const getInitTriggerType =
1497
1496
  isJdApp && item?.initJdAppTriggerType
1498
1497
  ? item?.initTriggerType
1499
1498
  : item?.initTriggerType || LoadJsInitTriggerType.NOW;
1500
1499
  const getInitLinkTriggerWay = window?.PAGE_DATA[item?.initLinkTriggerWay] || false;
1501
1500
  return getLoastLoadEventState && getInitTriggerType === triggerType && getInitLinkTriggerWay;
1502
1501
  });
1503
1502
  console.log(
1504
1503
  '获取当前触发方式',
1505
1504
  triggerType,
1506
1505
  '获取当前最后加载的js集合',
1507
1506
  getLoadFilterList,
1508
1507
  '过滤前的加载集合',
1509
1508
  getLoadJsList,
1510
1509
  );
1511
1510
  getLoadFilterList.length > 0 &&
1512
1511
  getLoadFilterList.forEach((item) => {
1513
1512
  const isLoadState = /sgm/.test(item?.fileName)
1514
1513
  ? window?.shopGlobalSwitch?.openSgm === 'true'
1515
1514
  : true;
1516
1515
  isLoadState &&
1517
1516
  this.loadItemSdkPromise(item)
1518
1517
  .then((res) => {
1519
1518
  console.info('当前js地址' + item?.src, '加载状态', res);
1520
1519
  const isFileNameNewDraSdkJs = res?.fileName === 'newDraSdkJs';
1521
1520
  if (isFileNameNewDraSdkJs && window?.dra?.run) {
1522
1521
  window.dra.run('init', { aid: res?.aid });
1523
1522
  window.dra.run('start');
1524
1523
  }
1525
1524
  })
1526
1525
  .catch((err) => {
1527
1526
  console.info('当前js地址加载异常', item?.src);
1528
1527
  window?.fetchErrorData &&
1529
1528
  window.fetchErrorData({
1530
1529
  title: '公共js加载异常',
1531
1530
  type: 'jsLoad',
1532
1531
  data: err,
1533
1532
  });
1534
1533
  });
1535
1534
  });
1536
1535
  }
1537
1536
  loadScriptEle(jsInfo, resolve, reject) {
1538
1537
  const getFileName = jsInfo?.fileName;
1539
1538
  if (getFileName) {
1540
1539
  const getEleId = `J_loadJs_${getFileName}`;
1541
1540
  const getEle = document.getElementById(getEleId);
1542
1541
  if (!getEle) {
1543
1542
  const jsLoadErrorSgmCode = `jsLoadError_${jsInfo?.fileName || 'customJs'}`;
1544
1543
  const _sgmEle = document.createElement('script');
1545
1544
  _sgmEle.id = getEleId;
1546
1545
  _sgmEle.onload = function () {
1547
1546
  resolve({
1548
1547
  ...jsInfo,
1549
1548
  jsTip: 'js加载成功',
1550
1549
  });
1551
1550
  };
1552
1551
  _sgmEle.onerror = function () {
1553
1552
  reject({
1554
1553
  ...jsInfo,
1555
1554
  env: getSgmCustomCode(jsLoadErrorSgmCode),
1556
1555
  jsReqError: '当前js创建标签触发onerror异常回调,请排查网络络错误或语法错误或运行时错误',
1557
1556
  });
1558
1557
  };
1559
1558
  const dataAttrList = ['timeout', 'fileName', 'env'];
1560
1559
  const getJsInfoKeyList = Object.keys(jsInfo);
1561
1560
  getJsInfoKeyList.forEach((key) => {
1562
1561
  if (key === 'async') {
1563
1562
  _sgmEle.async = jsInfo[key];
1564
1563
  } else if (key === 'crossOrigin') {
1565
1564
  _sgmEle.crossOrigin = jsInfo[key];
1566
1565
  } else if (key === 'src') {
1567
1566
  _sgmEle.src = `${jsInfo[key]}`;
1568
1567
  } else if (dataAttrList.includes(key) || /init/.test(key)) {
1569
1568
  _sgmEle.setAttribute(`data-${key}`, jsInfo[key]);
1570
1569
  } else {
1571
1570
  _sgmEle.setAttribute(key, jsInfo[key]);
1572
1571
  }
1573
1572
  });
1574
1573
  document.head.appendChild(_sgmEle);
1575
1574
  } else {
1576
1575
  console.log(`当前${jsInfo?.fileName || 'js'}已经存在页面中,可以直接调用相关方法`, jsInfo);
1577
1576
  resolve({
1578
1577
  ...jsInfo,
1579
1578
  jsTip: 'js本身已存在页面中',
1580
1579
  });
1581
1580
  }
1582
1581
  } else {
1583
1582
  console.warn('当前js资源信息缺少必要的参数fileName,请关注', jsInfo);
1584
1583
  }
1585
1584
  }
1586
1585
 
1587
1586
  loadItemSdkPromise(jsInfo = {}) {
1588
1587
  if (jsInfo?.src) {
1589
1588
  const getInitLoadType =
1590
1589
  isJdApp && jsInfo?.initJdAppLoadType
1591
1590
  ? jsInfo?.initJdAppLoadType
1592
1591
  : jsInfo?.initLoadType || LoadJsInitLoadType.ALL;
1593
1592
  if (getInitLoadType !== LoadJsInitLoadType.NONE) {
1594
1593
  const getFileKeyName = jsInfo?.fileName || jsInfo?.src;
1595
1594
  if (!this.loadJsSdkListCachePromise[getFileKeyName]) {
1596
1595
  if (getInitLoadType !== LoadJsInitLoadType.INSERT_ELE) {
1597
1596
  this.loadJsSdkListCachePromise[getFileKeyName] = new Promise((resolve, reject) => {
1598
1597
  const jsLoadErrorSgmCode = `jsLoadError_${jsInfo?.fileName || 'customJs'}`;
1599
1598
  try {
1600
1599
  const jsXhrRequest = new XMLHttpRequest();
1601
1600
  jsXhrRequest.timeout = jsInfo?.timeout ?? 2000;
1602
1601
  const jsUrl = `${jsInfo?.src}`;
1603
1602
  jsXhrRequest.open('GET', jsUrl, true);
1604
1603
  jsXhrRequest.onreadystatechange = () => {
1605
1604
  if (jsXhrRequest.readyState === 4) {
1606
1605
  const getReqStatus = jsXhrRequest.status;
1607
1606
  if ((getReqStatus >= 200 && getReqStatus < 300) || getReqStatus === 304) {
1608
1607
  const getInsetHeadState = getInitLoadType === LoadJsInitLoadType.ALL;
1609
1608
  if (getInsetHeadState) {
1610
1609
  this.loadScriptEle(jsInfo, resolve, reject);
1611
1610
  } else {
1612
1611
  resolve({
1613
1612
  ...jsInfo,
1614
1613
  jsTip: 'js请求成功,暂未插入head节点,业务自行单独插入',
1615
1614
  });
1616
1615
  }
1617
1616
  getReqStatus !== 200 &&
1618
1617
  sgmCustomReport({
1619
1618
  type: 3,
1620
1619
  code: 'js_load_special_code',
1621
1620
  msg: {
1622
1621
  msg: '当前js加载成功,状态非200,特殊上报观察',
1623
1622
  jsReqState: getReqStatus,
1624
1623
  env: getSgmCustomCode('js_load_special_code'),
1625
1624
  data: jsInfo,
1626
1625
  },
1627
1626
  });
1628
1627
  } else {
1629
1628
  const getRes = {
1630
1629
  ...jsInfo,
1631
1630
  env: getSgmCustomCode(jsLoadErrorSgmCode),
1632
1631
  jsReqError: `请求状态异常,状态码为${getReqStatus}`,
1633
1632
  jsReqState: getReqStatus,
1634
1633
  };
1635
1634
  console.log('当前js请求状态异常,具体信息见', getRes);
1636
1635
  reject(getRes);
1637
1636
  }
1638
1637
  }
1639
1638
  };
1640
1639
  jsXhrRequest.onerror = () => {
1641
1640
  const getRes = {
1642
1641
  ...jsInfo,
1643
1642
  env: getSgmCustomCode(jsLoadErrorSgmCode),
1644
1643
  jsReqError: '请求错误',
1645
1644
  };
1646
1645
  console.log('当前js请求错误', getRes);
1647
1646
  jsXhrRequest.abort();
1648
1647
  reject(getRes);
1649
1648
  };
1650
1649
  jsXhrRequest.ontimeout = () => {
1651
1650
  const getRes = {
1652
1651
  ...jsInfo,
1653
1652
  env: getSgmCustomCode(jsLoadErrorSgmCode),
1654
1653
  jsReqError: `请求${jsXhrRequest.timeout}ms超时异常`,
1655
1654
  jsReqState: jsXhrRequest.status,
1656
1655
  };
1657
1656
  console.log('当前js请求超时异常', getRes);
1658
1657
  jsXhrRequest.abort();
1659
1658
  reject(getRes);
1660
1659
  };
1661
1660
  jsXhrRequest.send();
1662
1661
  } catch (e) {
1663
1662
  console.log('执行js请求异常', e);
1664
1663
  reject({
1665
1664
  ...jsInfo,
1666
1665
  env: getSgmCustomCode(jsLoadErrorSgmCode),
1667
1666
  jsReqError: '未知异常',
1668
1667
  error: e,
1669
1668
  });
1670
1669
  }
1671
1670
  });
1672
1671
  } else {
1673
1672
  this.loadJsSdkListCachePromise[getFileKeyName] = new Promise((resolve, reject) => {
1674
1673
  return this.loadScriptEle(jsInfo, resolve, reject);
1675
1674
  });
1676
1675
  }
1677
1676
  }
1678
1677
  return this.loadJsSdkListCachePromise[getFileKeyName];
1679
1678
  } else {
1680
1679
  return Promise.resolve({
1681
1680
  ...jsInfo,
1682
1681
  jsTip: 'js加载方式设置为不加载,当前不做处理',
1683
1682
  });
1684
1683
  }
1685
1684
  } else {
1686
1685
  return Promise.reject(jsInfo);
1687
1686
  }
1688
1687
  }
1689
1688
 
1690
1689
  createLanguagePromise() {
1691
1690
  const getLanguageConfig = window?.shopGlobalSwitch?.language || {};
1692
1691
  if (!this.languageCacheProimse) {
1693
1692
  this.languageCacheProimse = new Promise((resolve, reject) => {
1694
1693
  const { fileName, prefixUrl } = getLanguageConfig;
1695
1694
  console.log('getLanguageConfig', getLanguageConfig, 'languageNowType', languageNowType);
1696
1695
  const dealLanguageFile = () => {
1697
1696
  this.getLanguageFilePromise(getLanguageConfig, languageNowType)
1698
1697
  .then((res) => {
1699
1698
  if (res && res?.data) {
1700
1699
  this.languageJsonData = res.data;
1701
1700
 
1702
1701
  setTimeout(() => {
1703
1702
  const getOtherLanguageList = languageTypeList.filter(
1704
1703
  (item) => item !== languageNowType,
1705
1704
  );
1706
1705
  getOtherLanguageList.length > 0 &&
1707
1706
  getOtherLanguageList.map((languageTypeKey) => {
1708
1707
  this.getLanguageFilePromise(getLanguageConfig, languageTypeKey);
1709
1708
  });
1710
1709
  }, 3000);
1711
1710
  resolve(res);
1712
1711
  } else {
1713
1712
  reject(res);
1714
1713
  }
1715
1714
  })
1716
1715
  .catch((err) => {
1717
1716
  reject(err);
1718
1717
  });
1719
1718
  };
1720
1719
  if (fileName && prefixUrl) {
1721
1720
  const getLangStorageKey = `jshopx_lang_${languageNowType}`;
1722
1721
  const getLocalLangRes = getTaroStorageKeyValue(getLangStorageKey);
1723
1722
  if (getLocalLangRes) {
1724
1723
  try {
1725
1724
  const getLocalLangJsonData =
1726
1725
  typeof getLocalLangRes === 'string' ? JSON.parse(getLocalLangRes) : getLocalLangRes;
1727
1726
  if (getLocalLangJsonData?.fileName && getLocalLangJsonData?.data) {
1728
1727
  if (getLocalLangJsonData?.fileName === fileName) {
1729
1728
  const geThisLangData = getLocalLangJsonData.data;
1730
1729
  this.languageJsonData = geThisLangData;
1731
1730
  return resolve({
1732
1731
  ...getLanguageConfig,
1733
1732
  languageNowType,
1734
1733
  data: geThisLangData,
1735
1734
  });
1736
1735
  } else {
1737
1736
  dealLanguageFile();
1738
1737
  }
1739
1738
  } else {
1740
1739
  dealLanguageFile();
1741
1740
  }
1742
1741
  } catch (e) {
1743
1742
  return reject({
1744
1743
  languageNowType,
1745
1744
  msg: '转换错误',
1746
1745
  ...getLanguageConfig,
1747
1746
  });
1748
1747
  }
1749
1748
  } else {
1750
1749
  dealLanguageFile();
1751
1750
  }
1752
1751
  } else {
1753
1752
  return reject({
1754
1753
  languageNowType,
1755
1754
  msg: '文件对象下发异常',
1756
1755
  ...getLanguageConfig,
1757
1756
  });
1758
1757
  }
1759
1758
  });
1760
1759
  }
1761
1760
  return this.languageCacheProimse;
1762
1761
  }
1763
1762
 
1764
1763
  getLanguageFilePromise(info, languageTypeKey) {
1765
1764
  const { fileName, prefixUrl, timeout } = info || {};
1766
1765
  const getUrl = `${prefixUrl}${fileName}_${languageTypeKey}.json`;
1767
1766
  return new Promise((resolve, reject) => {
1768
1767
  const langLoadErrorSgmCode = `languageLoadError_${fileName || 'lang.json'}`;
1769
1768
  try {
1770
1769
  const langXhrRequest = new XMLHttpRequest();
1771
1770
  langXhrRequest.timeout = timeout || 2000;
1772
1771
  langXhrRequest.open('GET', getUrl, true);
1773
1772
  langXhrRequest.responseType = 'json';
1774
1773
  langXhrRequest.onreadystatechange = () => {
1775
1774
  if (langXhrRequest.readyState === 4) {
1776
1775
  const getReqStatus = langXhrRequest.status;
1777
1776
  const statusText = langXhrRequest.statusText;
1778
1777
  if ((getReqStatus >= 200 && getReqStatus < 300) || getReqStatus === 304) {
1779
1778
  const getData = langXhrRequest?.response || false;
1780
1779
  if (getData) {
1781
1780
  setTaroStorage(`jshopx_lang_${languageTypeKey}`, {
1782
1781
  fileName,
1783
1782
  data: getData,
1784
1783
  });
1785
1784
  resolve({
1786
1785
  ...info,
1787
1786
  languageTypeKey,
1788
1787
  data: getData,
1789
1788
  });
1790
1789
  } else {
1791
1790
  reject({
1792
1791
  ...info,
1793
1792
  languageTypeKey,
1794
1793
  msg: '数据获取异常',
1795
1794
  });
1796
1795
  }
1797
1796
  } else {
1798
1797
  const getRes = {
1799
1798
  ...info,
1800
1799
  languageTypeKey,
1801
1800
  env: getSgmCustomCode(langLoadErrorSgmCode),
1802
1801
  msg: `请求状态异常,状态码为${getReqStatus},statusText:${statusText}`,
1803
1802
  };
1804
1803
  console.log('当前lang请求状态异常,具体信息见', getRes);
1805
1804
  reject(getRes);
1806
1805
  }
1807
1806
  }
1808
1807
  };
1809
1808
  langXhrRequest.onerror = () => {
1810
1809
  const getRes = {
1811
1810
  ...info,
1812
1811
  env: getSgmCustomCode(langLoadErrorSgmCode),
1813
1812
  msg: '请求错误',
1814
1813
  };
1815
1814
  console.log('当前lang请求错误', getRes);
1816
1815
  langXhrRequest.abort();
1817
1816
  reject(getRes);
1818
1817
  };
1819
1818
  langXhrRequest.ontimeout = () => {
1820
1819
  const getRes = {
1821
1820
  ...info,
1822
1821
  msg: `请求${langXhrRequest.timeout}ms超时异常,状态${langXhrRequest.status}`,
1823
1822
  };
1824
1823
  console.log('执行lang多语言请求超时异常', getRes);
1825
1824
  langXhrRequest.abort();
1826
1825
  reject(getRes);
1827
1826
  };
1828
1827
  langXhrRequest.send();
1829
1828
  } catch (e) {
1830
1829
  console.log('执行lang多语言请求异常', e);
1831
1830
  reject({
1832
1831
  ...info,
1833
1832
  env: getSgmCustomCode(langLoadErrorSgmCode),
1834
1833
  msg: '未知异常',
1835
1834
  error: e,
1836
1835
  });
1837
1836
  }
1838
1837
  });
1839
1838
  }
1839
+ import Taro from '@tarojs/taro';
1840
1840
  dealNativePixelToCssPixel,
1841
1841
  isAndroidDevice,
1842
1842
  isIosDevice,
1843
1843
  isJdAndAndroidDevice,
1844
1844
  isJdAndHarmonyDevice,
1845
1845
  isObject,
1846
1846
  isPc,
1847
1847
  isString,
1848
1848
  jdAppVersion,
1849
1849
  jdAppVersionStr,
1850
1850
  serialize,
1851
1851
  draBusinessCustomReport,
1852
1852
  isH5AndJingGouMini,
1853
1853
  languageNowType,
1854
1854
  urlCookie,
1855
1855
  BUSINESS_TYPE,
1856
1856
  LoadJsInitLoadEnvType,
1857
1857
  LoadJsInitLoadType,
1858
1858
  LoadJsInitTriggerType,
1859
1859
  MPAAS_CONFIG_APP_LOW_VERSION,
1860
1860
  MPAAS_CONFIG_APP_VERSION,
1861
1861
  SECTION_HOME_TAB_NAME_TYPE,
1862
1862
  SECTION_HOME_TAB_TYPE,
1863
1863
  TaroEventType,
1864
1864
  WX_BUSINESS_TYPE,
1865
1865
  WXAPP_BIZ_KEY,
1866
1866
  WXAPP_BIZ_SHOP_LIGHT_KEY,
1867
1867
  JSSDK_APP_WEBVIEW_CODE,
1868
1868
  cacheH5LbsAddressKey,
1869
1869
  languageTypeList,
1870
1870
  getSystemInfos,
1871
1871
  getTaroStorageKeyValue,
1872
1872
  ipLoc_djd,
1873
1873
  setTaroStorage,
1874
1874
  sgmCustomReport,
1875
1875
  getMPaasConfigByBussinessKey,
1876
1876
  callRouterAndroid,
1877
1877
  callRouterIOS,
1878
1878
  const designWidth = 750;
1879
1879
  return (
1880
1880
  Math.ceil((((parseInt(String(size), 10) / 40) * 750) / designWidth) * 10000) / 10000 + 'rem'
1881
1881
  );
1882
1882
  abTestLabels: {},
1883
1883
  nonSellableSkuids: {},
1884
1884
  loginState: false,
1885
1885
  cookiesStr: '',
1886
1886
  userInfo: userPinKey,
1887
1887
  isImmersive: false,
1888
1888
  isJingGouMiniViewState: false,
1889
1889
  isJingxiMiniViewState: false,
1890
1890
  pageInfo: {
1891
1891
  wxBusinessType: WX_BUSINESS_TYPE.NO,
1892
1892
  address: '',
1893
1893
  addressCommaStr: '',
1894
1894
  un_area: '',
1895
1895
  userLbsAddress: '',
1896
1896
  vapptype: '1',
1897
1897
  pageType: 'home',
1898
1898
  isExposureState: false,
1899
1899
  moduleId: '',
1900
1900
  entrance: '',
1901
1901
  dataType: BUSINESS_TYPE.ONLINE,
1902
1902
  floorExposureInfo: {},
1903
1903
  floorVideInfo: {},
1904
1904
  productVideInfo: {},
1905
1905
  tabsLoadAllDataInfo: {
1906
1906
  [SECTION_HOME_TAB_NAME_TYPE[SECTION_HOME_TAB_TYPE.HOME_WELL_CHOSEN]]: false,
1907
1907
  },
1908
1908
  updateShopInfosAllState: false,
1909
1909
  isVipShop: false,
1910
1910
  isJdShowNativeImmersivePlayer: false,
1911
1911
  ...shopConfig,
1912
1912
  pageScrollTop: 0,
1913
1913
  pageIdxHeightInfo: {
1914
1914
  list: [],
1915
1915
  },
1916
1916
  shopNavBarHeight: 0,
1917
1917
  },
1918
1918
  defaultQueryLogInfo: {
1919
1919
  sourceType: 'JDshop',
1920
1920
  sourceValue: '',
1921
1921
  moduleId: 'none',
1922
1922
  entrance: 'none',
1923
1923
  },
1924
1924
  sysInfo: {
1925
1925
  windowWidth: isPc ? 375 : 0,
1926
1926
  containerWidth: isPc ? 375 : 0,
1927
1927
  windowHeight: 0,
1928
1928
  netWorkType: '4g',
1929
1929
  jdBottomBarHeight: 0,
1930
1930
  jdNativeHeaderHeight: 0,
1931
1931
  isJdTabletDevice: false,
1932
1932
  isJdTabletLandscape: false,
1933
1933
  },
1934
1934
  queryInfo: {},
1935
1935
  shopInfo: {},
1936
1936
  openAppData: {},
1937
1937
  public info: CommonInterFace.BaseConfigInfo;
1938
1938
  public config: {
1939
1939
  [key: string]: any;
1940
1940
  };
1941
1941
  public lazyContainer: CommonInterFace.lazyContainer;
1942
1942
  public renderedIsvComponents: CommonInterFace.renderedIsvComponents;
1943
1943
  public rootEleNode: HTMLElement | null;
1944
1944
  public checkStatusAndLoginPromise: object | null;
1945
1945
  private jmfeRegisterStatePromise: Promise<any> | null;
1946
1946
  private jdScreenSizeInfoPromise: Promise<any> | null;
1947
1947
  private rootEleWidthRegisterPromise: Promise<any> | null;
1948
1948
  private jmfeRegisterState: boolean;
1949
1949
  public loadJsSdkList: Array<any>;
1950
1950
  public loadJsSdkListCachePromise: any;
1951
1951
  public rootEleInitWidth: number;
1952
1952
  public lbsAddressCachePromise: Promise<any> | null;
1953
1953
  public languageCacheProimse: Promise<any> | null;
1954
1954
  public languageJsonData: any | null;
1955
1955
  constructor(opt) {
1956
1956
  this.info = this._getConfig(opt);
1957
1957
  this.config = {};
1958
1958
  this.loadJsSdkList = [];
1959
1959
  this.loadJsSdkListCachePromise = {};
1960
1960
  this.lazyContainer = {
1961
1961
  [SECTION_HOME_TAB_NAME_TYPE[SECTION_HOME_TAB_TYPE.HOME_WELL_CHOSEN]]: {
1962
1962
  appLazyContainerList: [],
1963
1963
  appLazyFinishContainerList: [],
1964
1964
  },
1965
1965
  [SECTION_HOME_TAB_NAME_TYPE[SECTION_HOME_TAB_TYPE.HOME_PROMOTION]]: {
1966
1966
  appLazyContainerList: [],
1967
1967
  appLazyFinishContainerList: [],
1968
1968
  },
1969
1969
  };
1970
1970
  this.renderedIsvComponents = {};
1971
1971
  this.rootEleNode = document.querySelector('body');
1972
1972
  this.checkStatusAndLoginPromise = null;
1973
1973
  this.jmfeRegisterStatePromise = null;
1974
1974
  this.jdScreenSizeInfoPromise = null;
1975
1975
  this.rootEleWidthRegisterPromise = null;
1976
1976
  this.lbsAddressCachePromise = null;
1977
1977
  this.languageCacheProimse = null;
1978
1978
  this.languageJsonData = langeJsonDataForCn;
1979
1979
  this.rootEleInitWidth = this.getRootEleWindowWidthInfo().getRootEleWidth || -1;
1980
1980
  this.loadOtherSdk();
1981
1981
  if (isJdApp) {
1982
1982
  this.jmfeReayPromise();
1983
1983
  this._getJdPadMinWidthForListen() && this.getPadWindowRootEleWidthPromise();
1984
1984
  }
1985
1985
  }
1986
1986
  _getConfig(opt) {
1987
1987
  return Object.assign({}, DefaultConfig, opt);
1988
1988
  }
1989
1989
  _getJdPadMinWidthForListen() {
1990
1990
  return (
1991
1991
  isJdApp &&
1992
1992
  Math.min(window.screen.width, window.screen.height) >
1993
1993
  (window?.shopGlobalSwitch?.checkPadRootEleMinWidth || 600)
1994
1994
  );
1995
1995
  }
1996
1996
 
1997
1997
  jmfeReayPromise(): Promise<any> {
1998
1998
  if (isJdApp) {
1999
1999
  if (this.jmfeRegisterState) {
2000
2000
  return Promise.resolve(true);
2001
2001
  } else {
2002
2002
  !this.jmfeRegisterStatePromise &&
2003
2003
  (this.jmfeRegisterStatePromise = new Promise((resolve, reject) => {
2004
2004
  ready('jmfe', 3000)
2005
2005
  .then(() => {
2006
2006
  window?.jmfe && window.jmfe.registerCode(JSSDK_APP_WEBVIEW_CODE);
2007
2007
  this.jmfeRegisterState = true;
2008
2008
  resolve(true);
2009
2009
  console.log(
2010
2010
  '松果app内初始化注册jmfe认证完成',
2011
2011
  window?.jmfe,
2012
2012
  '当前版本',
2013
2013
  window?.jmfe?.VERSION,
2014
2014
  );
2015
2015
  })
2016
2016
  .catch((err) => {
2017
2017
  console.error('jmfe ready error', err);
2018
2018
  reject(false);
2019
2019
  });
2020
2020
  }));
2021
2021
  return this.jmfeRegisterStatePromise;
2022
2022
  }
2023
2023
  } else {
2024
2024
  return Promise.reject(false);
2025
2025
  }
2026
2026
  }
2027
2027
 
2028
2028
  getJdScreenSizeInfoPromise() {
2029
2029
  !this.jdScreenSizeInfoPromise &&
2030
2030
  (this.jdScreenSizeInfoPromise = new Promise((resolve) => {
2031
2031
  const getThisTime = Date.now();
2032
2032
  this.jmfeReayPromise().then(() => {
2033
2033
  return Promise.race([
2034
2034
  window.jmfe.getScreenSize(),
2035
2035
  this.taskTimeoutPromise(() => {
2036
2036
  return {
2037
2037
  status: '-10',
2038
2038
  msg: '获取大屏信息2s超时',
2039
2039
  };
2040
2040
  }),
2041
2041
  ])
2042
2042
  .then((res) => {
2043
2043
  console.warn('===获取app大屏信息====', res);
2044
2044
  const { status, data } = res;
2045
2045
  if (status === '0' && data) {
2046
2046
  const { sizeType, isLandscape, pageHeight, pageWidth } = data;
2047
2047
  const getPageInfo = dealNativePixelToCssPixel({
2048
2048
  pageWidth,
2049
2049
  pageHeight,
2050
2050
  });
2051
2051
  this.info.sysInfo.jdScreenSizeType = sizeType;
2052
2052
  const getUseTime = Date.now() - getThisTime;
2053
2053
  console.warn(
2054
2054
  '===计算是否是app大屏信息,需满足宽度最新720===',
2055
2055
  getPageInfo,
2056
2056
  '原始数据',
2057
2057
  data,
2058
2058
  '是否是横屏isLandscape为1=',
2059
2059
  isLandscape,
2060
2060
  '用时',
2061
2061
  getUseTime,
2062
2062
  );
2063
2063
  if (getPageInfo?.pageWidth > 0) {
2064
2064
  this.rootEleInitWidth = getPageInfo?.pageWidth;
2065
2065
  draBusinessCustomReport({
2066
2066
  type: 'rootEle_width_getJdScreenSizeInfo',
2067
2067
  errMsg: `根元素获取宽度初始化为0,通过getJdScreenSizeInfo获取结果,用时${getUseTime}`,
2068
2068
  originReqDataStr: JSON.stringify({
2069
2069
  isJdApp,
2070
2070
  getPageInfo,
2071
2071
  originData: res,
2072
2072
  }),
2073
2073
  });
2074
2074
  resolve(getPageInfo);
2075
2075
  } else {
2076
2076
  resolve({
2077
2077
  pageWidth: 0,
2078
2078
  pageHeight: 0,
2079
2079
  msg: '转换异常',
2080
2080
  });
2081
2081
  }
2082
2082
  } else {
2083
2083
  resolve({
2084
2084
  pageWidth: 0,
2085
2085
  pageHeight: 0,
2086
2086
  msg: '获取大屏信息异常或者超时',
2087
2087
  });
2088
2088
  }
2089
2089
  })
2090
2090
  .catch((err) => {
2091
2091
  console.log('获取大屏信息异常', err);
2092
2092
  resolve({
2093
2093
  pageWidth: 0,
2094
2094
  pageHeight: 0,
2095
2095
  msg: '获取大屏信息异常',
2096
2096
  });
2097
2097
  });
2098
2098
  });
2099
2099
  }));
2100
2100
  return this.jdScreenSizeInfoPromise;
2101
2101
  }
2102
2102
 
2103
2103
  listenJdTabletScreenChange() {
2104
2104
  this.jmfeReayPromise().then(() => {
2105
2105
  try {
2106
2106
  console.log('初始化监听大屏信息变化', window.jmfe.listenDeviceScreenChange);
2107
2107
  window.jmfe.listenDeviceScreenChange((event) => {
2108
2108
  console.log(
2109
2109
  '监听app大屏信息变化,orientation为landscape表示横屏,multiScreen为1表示android端分屏',
2110
2110
  event,
2111
2111
  '通过前端判断是不是横屏',
2112
2112
  window.matchMedia('(orientation: landscape)')?.matches,
2113
2113
  );
2114
2114
  const { orientation } = event?.data;
2115
2115
  if (orientation) {
2116
2116
  this.info.sysInfo.isJdTabletLandscape = orientation === 'landscape';
2117
2117
  Taro.eventCenter.trigger(
2118
2118
  TaroEventType.TABLE_SCREEN_CHANGE,
2119
2119
  this.info.sysInfo.isJdTabletLandscape,
2120
2120
  orientation,
2121
2121
  );
2122
2122
  }
2123
2123
  });
2124
2124
  } catch (error) {
2125
2125
  console.log('listenScreenChange的打印error:', error);
2126
2126
  }
2127
2127
  });
2128
2128
  }
2129
2129
 
2130
2130
  updateBusinessDomainAndApi(domain, api) {
2131
2131
  }
2132
2132
 
2133
2133
  formatNativeScreenPageData(action) {
2134
2134
  let getChangePageInfo: any = null;
2135
2135
  try {
2136
2136
  const getNativeScreenPageInfoStr = window.XWebView?._callNative(
2137
2137
  JSON.stringify({
2138
2138
  plugin: 'JDHybridScreenPlugin',
2139
2139
  action,
2140
2140
  sync: '1',
2141
2141
  }),
2142
2142
  );
2143
2143
  const getChangePageInfoData =
2144
2144
  typeof getNativeScreenPageInfoStr === 'string'
2145
2145
  ? JSON.parse(getNativeScreenPageInfoStr)
2146
2146
  : null;
2147
2147
  if (getChangePageInfoData && typeof getChangePageInfoData === 'object') {
2148
2148
  const { code, data } = getChangePageInfoData;
2149
2149
  getChangePageInfo = code && code === '0' ? data : null;
2150
2150
  }
2151
2151
  } catch (e) {
2152
2152
  console.log('JDHybridScreenPlugin转换异常', e);
2153
2153
  }
2154
2154
  return getChangePageInfo;
2155
2155
  }
2156
2156
 
2157
2157
  isAndroidFoldScreen() {
2158
2158
  return this.formatNativeScreenPageData('isFoldScreen') === '1';
2159
2159
  }
2160
2160
 
2161
2161
  getJdAndroidPageChangeScreenInfo() {
2162
2162
  const getPageScreenInfo = this.formatNativeScreenPageData('getScreenSize');
2163
2163
  if (getPageScreenInfo && getPageScreenInfo?.pageWidth && getPageScreenInfo?.pageHeight) {
2164
2164
  const { pageWidth, pageHeight } = dealNativePixelToCssPixel({
2165
2165
  pageWidth: getPageScreenInfo.pageWidth,
2166
2166
  pageHeight: getPageScreenInfo.pageHeight,
2167
2167
  });
2168
2168
  getPageScreenInfo.pageWidth = pageWidth;
2169
2169
  getPageScreenInfo.pageHeight = pageHeight;
2170
2170
  }
2171
2171
  return getPageScreenInfo;
2172
2172
  }
2173
2173
 
2174
2174
  getRootEleWindowWidthInfo() {
2175
2175
  const getRootEleWidth = document.documentElement.getBoundingClientRect().width;
2176
2176
  const getWindowWidth = window.innerWidth;
2177
2177
  const getScreenWidth = window.screen.width;
2178
2178
  return {
2179
2179
  getRootEleWidth,
2180
2180
  getWindowWidth,
2181
2181
  getScreenWidth,
2182
2182
  };
2183
2183
  }
2184
2184
 
2185
2185
  dealRootEleWidthFn(reportParam = {}, timeout = 0) {
2186
2186
  const { getRootEleWidth, getWindowWidth, getScreenWidth } = this.getRootEleWindowWidthInfo();
2187
2187
  console.log(
2188
2188
  '当前获取根元素的宽度',
2189
2189
  getRootEleWidth,
2190
2190
  'getWindowWidth',
2191
2191
  getWindowWidth,
2192
2192
  'getScreenWidth',
2193
2193
  getScreenWidth,
2194
2194
  );
2195
2195
  const getLastWidth =
2196
2196
  getRootEleWidth > 0
2197
2197
  ? Math.round(getRootEleWidth)
2198
2198
  : Math.round(getWindowWidth > 0 ? getWindowWidth : getScreenWidth);
2199
2199
  console.warn(
2200
2200
  `根元素获取宽度初始化为0,通过getJdScreenSizeInfo获取结果超时,超时时间超时时间${timeout}ms,最终兜底再获取一次根元素宽度${getLastWidth}`,
2201
2201
  );
2202
2202
  timeout > 0 &&
2203
2203
  draBusinessCustomReport({
2204
2204
  type: 'rootEle_width_timeout_getJdScreenSizeInfo',
2205
2205
  errMsg: `根元素获取宽度初始化为0,通过getJdScreenSizeInfo获取结果超时,超时时间${timeout}ms,最终兜底再获取一次根元素宽度${getLastWidth}`,
2206
2206
  originReqDataStr: JSON.stringify({
2207
2207
  isJdApp,
2208
2208
  getRootEleWidth,
2209
2209
  getWindowWidth,
2210
2210
  getScreenWidth,
2211
2211
  ...reportParam,
2212
2212
  }),
2213
2213
  });
2214
2214
  return getLastWidth;
2215
2215
  }
2216
2216
 
2217
2217
  getPadWindowRootEleWidthPromise() {
2218
2218
  if (this.rootEleInitWidth > 0) {
2219
2219
  return Promise.resolve(this.rootEleInitWidth);
2220
2220
  } else {
2221
2221
  !this.rootEleWidthRegisterPromise &&
2222
2222
  (this.rootEleWidthRegisterPromise = new Promise((resolve) => {
2223
2223
  const getRootEleInitWidth = this.getRootEleWindowWidthInfo().getRootEleWidth;
2224
2224
  if (getRootEleInitWidth > 0) {
2225
2225
  console.log('初始化获取根元素宽度正常,为', getRootEleInitWidth);
2226
2226
  this.rootEleInitWidth = Math.round(getRootEleInitWidth);
2227
2227
  resolve(this.rootEleInitWidth);
2228
2228
  } else {
2229
2229
  const timerPromise = () => {
2230
2230
  return new Promise((resolve2) => {
2231
2231
  window.setTimeout(() => {
2232
2232
  const { getRootEleWidth, getWindowWidth, getScreenWidth } =
2233
2233
  this.getRootEleWindowWidthInfo();
2234
2234
  if (getRootEleWidth > 0 || getWindowWidth > 0) {
2235
2235
  console.warn(
2236
2236
  `根元素获取宽度初始化为0,200ms后尝试获取最新结果,getRootEleWidth为${getRootEleWidth},getWindowWidth为${getWindowWidth},getScreenWidth为${getScreenWidth}`,
2237
2237
  );
2238
2238
  draBusinessCustomReport({
2239
2239
  type: 'rootEle_width_200_timeout_info',
2240
2240
  errMsg: `根元素获取宽度初始化为0,200ms后尝试获取最新结果,getRootEleWidth为${getRootEleWidth},getWindowWidth为${getWindowWidth}`,
2241
2241
  originReqDataStr: JSON.stringify({
2242
2242
  isJdApp,
2243
2243
  getRootEleWidth,
2244
2244
  getWindowWidth,
2245
2245
  getScreenWidth,
2246
2246
  }),
2247
2247
  });
2248
2248
  const getRes =
2249
2249
  getRootEleWidth > 0 && getWindowWidth > 0
2250
2250
  ? Math.min(getRootEleWidth, getWindowWidth)
2251
2251
  : Math.max(getRootEleWidth, getWindowWidth);
2252
2252
  resolve2({
2253
2253
  pageWidth: Math.round(getRes),
2254
2254
  });
2255
2255
  }
2256
2256
  }, 200);
2257
2257
  });
2258
2258
  };
2259
2259
  Promise.race([timerPromise(), this.getJdScreenSizeInfoPromise()]).then((res) => {
2260
2260
  const { pageWidth } = res;
2261
2261
  console.log('获取结果Promise.race getJdScreenSizeInfo', res);
2262
2262
  pageWidth > 0 ? resolve(pageWidth) : resolve(this.dealRootEleWidthFn(res, 2000));
2263
2263
  });
2264
2264
  }
2265
2265
  }));
2266
2266
  return this.rootEleWidthRegisterPromise;
2267
2267
  }
2268
2268
  }
2269
2269
 
2270
2270
  async getSystemInfo(params) {
2271
2271
  const getParams = Object.assign({}, params || {});
2272
2272
  if (this.rootEleInitWidth > 0) {
2273
2273
  getParams['rootEleInitWidth'] = this.rootEleInitWidth;
2274
2274
  console.log('获取当前系统信息的时候已经获取到根元素宽度,值为', this.rootEleInitWidth);
2275
2275
  } else {
2276
2276
  if (this._getJdPadMinWidthForListen()) {
2277
2277
  getParams['rootEleInitWidth'] = await this.getPadWindowRootEleWidthPromise();
2278
2278
  getParams['replaceSystemWidth'] = true;
2279
2279
  }
2280
2280
  }
2281
2281
  isJdApp && this.createLanguagePromise();
2282
2282
  let info: UtilsInterFace.taroGetSystemInfoSyncRes | any = getSystemInfos(getParams);
2283
2283
  if (isJdAndAndroidDevice && info?.initWindowWidth <= 0) {
2284
2284
  let _isfoldScreen = false;
2285
2285
  const getStorageData = getTaroStorageKeyValue('jd_shopx_androidIsFoldScreen');
2286
2286
  console.info(
2287
2287
  '获取当前本地存储是否有jd_shopx_androidIsFoldScreen',
2288
2288
  getStorageData,
2289
2289
  '通过缓存值第一次判断是否是折叠屏',
2290
2290
  getStorageData === 'true',
2291
2291
  );
2292
2292
  if (!getStorageData) {
2293
2293
  _isfoldScreen = this.isAndroidFoldScreen();
2294
2294
  setTaroStorage('jd_shopx_androidIsFoldScreen', `${_isfoldScreen}`);
2295
2295
  } else {
2296
2296
  _isfoldScreen = getStorageData === 'true';
2297
2297
  }
2298
2298
  if (_isfoldScreen) {
2299
2299
  const getJdAndroidPageInfo = this.getJdAndroidPageChangeScreenInfo();
2300
2300
  if (getJdAndroidPageInfo) {
2301
2301
  info = getSystemInfos(getJdAndroidPageInfo);
2302
2302
  console.warn(
2303
2303
  '当前为松果安卓折叠屏app,获取折叠屏信息',
2304
2304
  getJdAndroidPageInfo,
2305
2305
  '获取转换后的系统信息',
2306
2306
  info,
2307
2307
  );
2308
2308
  sgmCustomReport({
2309
2309
  type: 2,
2310
2310
  code: 'android_jdapp_foldScreen_info',
2311
2311
  msg: {
2312
2312
  title: `松果安卓app为折叠屏,重置获取的系统宽高信息,因为获取宽高度信息初始化内部可能存在横竖屏差异`,
2313
2313
  androidPageInfo: getJdAndroidPageInfo,
2314
2314
  jdAppVersionStr,
2315
2315
  taroSysInfo: info,
2316
2316
  },
2317
2317
  });
2318
2318
  }
2319
2319
  }
2320
2320
  }
2321
2321
  if (isJdApp) {
2322
2322
  info?.isJdTabletDevice && this.listenJdTabletScreenChange();
2323
2323
  }
2324
2324
  this.info.sysInfo = {
2325
2325
  actualNavBarHeight: 0,
2326
2326
  ...this.info.sysInfo,
2327
2327
  ...info,
2328
2328
  safeContentHeight: info?.screenHeight,
2329
2329
  headerHeight: 0,
2330
2330
  tabBarHeight: 0,
2331
2331
  languageType: languageNowType,
2332
2332
  };
2333
2333
  if (isJdApp || isH5AndJingGouMini) {
2334
2334
  this.getLbsAddressCachePromise();
2335
2335
  }
2336
2336
  if (isJdApp) {
2337
2337
  this.info.sysInfo['hostVersionName'] = jdAppVersionStr;
2338
2338
  this.info.sysInfo['hostAppVersion'] = jdAppVersion;
2339
2339
  this.getAddressCachePromise();
2340
2340
  this.getElderModePromise();
2341
2341
  this.getJDAppearanceStatePromise();
2342
2342
  this.createJdAndroidRquestEventForTouchStart();
2343
2343
  }
2344
2344
  this.getWifiVideoAutoPlayAsync();
2345
2345
  this.getMPaasConfigAsync();
2346
2346
  this.getNetWorkType();
2347
2347
  }
2348
2348
 
2349
2349
  taskTimeoutPromise(callBack, timeout = 2000) {
2350
2350
  return new Promise((resolve) => {
2351
2351
  setTimeout(() => {
2352
2352
  const getCallBackRes = typeof callBack === 'function' && callBack();
2353
2353
  return resolve(getCallBackRes || false);
2354
2354
  }, timeout);
2355
2355
  });
2356
2356
  }
2357
2357
 
2358
2358
  getElderModePromise() {
2359
2359
  if (this.info.sysInfo.hasOwnProperty('jdAppModeType')) {
2360
2360
  return Promise.resolve(this.info.sysInfo.jdAppModeType);
2361
2361
  } else {
2362
2362
  if (isJdAndAndroidDevice) {
2363
2363
  this.info.sysInfo.jdAppModeType = '0';
2364
2364
  return Promise.resolve(this.info.sysInfo.jdAppModeType);
2365
2365
  } else {
2366
2366
  return Promise.race([
2367
2367
  this.taskTimeoutPromise(() => {
2368
2368
  this.info.sysInfo.jdAppModeType = '0';
2369
2369
  return this.info.sysInfo.jdAppModeType;
2370
2370
  }),
2371
2371
  new Promise((resolve) => {
2372
2372
  const getCallBackName = `getJdCurrentModeType${Date.now()}`;
2373
2373
  if (!window[getCallBackName]) {
2374
2374
  window[getCallBackName] = (res) => {
2375
2375
  try {
2376
2376
  const getResJson = typeof res === 'string' ? JSON.parse(res) : res;
2377
2377
  const { status, data, msg } = getResJson;
2378
2378
  console.log(`获取松果app展示模式成功,返回结果${data}`);
2379
2379
  if (status === '0') {
2380
2380
  this.info.sysInfo.jdAppModeType = data;
2381
2381
  resolve(data);
2382
2382
  } else {
2383
2383
  resolve('0');
2384
2384
  }
2385
2385
  } catch (e) {
2386
2386
  resolve('0');
2387
2387
  }
2388
2388
  window[getCallBackName] = null;
2389
2389
  };
2390
2390
  }
2391
2391
  window?.webkit?.messageHandlers?.JDAppUnite?.postMessage({
2392
2392
  method: 'callSyncRouterModuleWithParams',
2393
2393
  params: JSON.stringify({
2394
2394
  routerURL: 'router://JDBModeModule/getCurrentMode',
2395
2395
  routerParam: {},
2396
2396
  callBackName: `window.${getCallBackName}`,
2397
2397
  callBackId: `${getCallBackName}Ios`,
2398
2398
  }),
2399
2399
  });
2400
2400
  }),
2401
2401
  ]);
2402
2402
  }
2403
2403
  }
2404
2404
  }
2405
2405
  getAPPUseStraightCorner() {
2406
2406
  const routerURL = 'router://JDBaseUtilsModule/isUI14Enable';
2407
2407
  const params = {
2408
2408
  routerURL,
2409
2409
  routerParam: {},
2410
2410
  jdRouter: '1',
2411
2411
  };
2412
2412
  if (this.info.sysInfo.hasOwnProperty('jdStraightCorner')) {
2413
2413
  return Promise.resolve(this.info.sysInfo.jdStraightCorner);
2414
2414
  } else {
2415
2415
  return this.jmfeReayPromise()
2416
2416
  .then(() => {
2417
2417
  if (isJdAndHarmonyDevice || !isJdApp) {
2418
2418
  console.log('not APP or is Harmony');
2419
2419
  return Promise.resolve(false);
2420
2420
  }
2421
2421
  console.log('jmfe setShareInfo', params);
2422
2422
  return Promise.race([
2423
2423
  window.jmfe.callRouter(params),
2424
2424
  this.taskTimeoutPromise(() => {
2425
2425
  return false;
2426
2426
  }),
2427
2427
  ]).then(({ status, data }) => {
2428
2428
  console.log('004 ~ file: index.tsx:133 ~ .then ~ data:', data);
2429
2429
  console.log('004 ~ file: index.tsx:133 ~ .then ~ status:', status);
2430
2430
  this.info.sysInfo.jdStraightCorner = status === '0' && Number(data) === 1;
2431
2431
  return Promise.resolve(status === '0' && Number(data) === 1);
2432
2432
  });
2433
2433
  })
2434
2434
  .catch((e) => {
2435
2435
  console.log('jmfe error', e);
2436
2436
  return Promise.resolve(false);
2437
2437
  });
2438
2438
  }
2439
2439
  }
2440
2440
 
2441
2441
  getJDAppearanceStatePromise() {
2442
2442
  if (this.info.sysInfo.hasOwnProperty('jdAppearanceState')) {
2443
2443
  return Promise.resolve(this.info.sysInfo.jdAppearanceState);
2444
2444
  } else {
2445
2445
  return Promise.race([
2446
2446
  this.taskTimeoutPromise(() => {
2447
2447
  this.info.sysInfo.jdAppearanceState = '0';
2448
2448
  return this.info.sysInfo.jdAppearanceState;
2449
2449
  }),
2450
2450
  new Promise((resolve) => {
2451
2451
  const getCallBackName = `getJdCurrentAppearanceState${Date.now()}`;
2452
2452
  if (!window[getCallBackName]) {
2453
2453
  window[getCallBackName] = (res) => {
2454
2454
  try {
2455
2455
  console.log('getJDAppearanceStatePromise', res);
2456
2456
  const getResJson = typeof res === 'string' ? JSON.parse(res) : res;
2457
2457
  const { status, data, msg } = getResJson;
2458
2458
  console.log(`获取松果app是否开启黑暗模式成功,返回结果${data}`);
2459
2459
  if (status === '0') {
2460
2460
  this.info.sysInfo.jdAppearanceState = data;
2461
2461
  resolve(data);
2462
2462
  } else {
2463
2463
  resolve('0');
2464
2464
  }
2465
2465
  } catch (e) {
2466
2466
  resolve('0');
2467
2467
  }
2468
2468
  window[getCallBackName] = null;
2469
2469
  };
2470
2470
  }
2471
2471
  if (isAndroidDevice) {
2472
2472
  const jsonString = JSON.stringify({
2473
2473
  callBackName: `window.${getCallBackName}`,
2474
2474
  });
2475
2475
  console.log('window.JDAppearance', window?.JDAppearance);
2476
2476
  window?.JDAppearance &&
2477
2477
  window?.JDAppearance?.getUiState &&
2478
2478
  window.JDAppearance.getUiState(jsonString);
2479
2479
  } else {
2480
2480
  window?.webkit?.messageHandlers?.JDAppUnite?.postMessage({
2481
2481
  method: 'callSyncRouterModuleWithParams',
2482
2482
  params: JSON.stringify({
2483
2483
  routerURL: 'router://JDWebViewBusinessModule/getJDAppearanceState',
2484
2484
  routerParam: {},
2485
2485
  callBackName: `window.${getCallBackName}`,
2486
2486
  callBackId: `${getCallBackName}Ios`,
2487
2487
  }),
2488
2488
  });
2489
2489
  }
2490
2490
  }),
2491
2491
  ]);
2492
2492
  }
2493
2493
  }
2494
2494
 
2495
2495
  createJdAndroidRquestEventForTouchStart() {
2496
2496
  if (isJdAndAndroidDevice && window?.JdAndroid) {
2497
2497
  const rootEleNode = document.querySelector('body');
2498
2498
  if (rootEleNode) {
2499
2499
  rootEleNode.addEventListener('touchstart', this.jdAndroidAddEventListenerTouchStart, false);
2500
2500
  }
2501
2501
  }
2502
2502
  }
2503
2503
  jdAndroidAddEventListenerTouchStart(e) {
2504
2504
  const isH5SwiperCustomEle = e?.target?.closest('.J_h5SwiperCustom');
2505
2505
  if (!isH5SwiperCustomEle && window?.JdAndroid) {
2506
2506
  const hasCustomEle = e
2507
2507
  ? e?.target?.closest('.J_customScroll') || e?.target?.closest('.J_customLayout')
2508
2508
  : false;
2509
2509
  if (!hasCustomEle) {
2510
2510
  window?.JdAndroid?.requestEvent && window.JdAndroid.requestEvent(false);
2511
2511
  console.log(
2512
2512
  'createJdAndroidRquestEvent 所有松果安卓APP内的document touch start事件执行检测requestEvent并重置为false',
2513
2513
  );
2514
2514
  }
2515
2515
  }
2516
2516
  }
2517
2517
  removeJdAndroidRquestEventForTouchStart() {
2518
2518
  if (isJdAndAndroidDevice && window.JdAndroid) {
2519
2519
  const rootEleNode = document.querySelector('body');
2520
2520
  if (rootEleNode) {
2521
2521
  rootEleNode.removeEventListener(
2522
2522
  'touchstart',
2523
2523
  this.jdAndroidAddEventListenerTouchStart,
2524
2524
  false,
2525
2525
  );
2526
2526
  }
2527
2527
  }
2528
2528
  }
2529
2529
 
2530
2530
  getNetWorkType() {
2531
2531
  if (isJdApp) {
2532
2532
  this.jmfeReayPromise().then(() => {
2533
2533
  window.jmfe
2534
2534
  .getNetworkStatus()
2535
2535
  .then(({ status, data }) => {
2536
2536
  console.log('在app内初始化通过jmfe对象获取网络状态完成,当前网络状态====', data);
2537
2537
  if (status === '0') {
2538
2538
  this.info.sysInfo['netWorkType'] = data;
2539
2539
  } else {
2540
2540
  this._taroGetNetworkType();
2541
2541
  }
2542
2542
  })
2543
2543
  .catch((err) => {
2544
2544
  console.log('在app内初始化通过jmfe对象获取网络状态异常====', err);
2545
2545
  this._taroGetNetworkType();
2546
2546
  });
2547
2547
  });
2548
2548
  } else {
2549
2549
  this._taroGetNetworkType();
2550
2550
  }
2551
2551
  }
2552
2552
  _taroGetNetworkType() {
2553
2553
  Taro.getNetworkType().then((getRes) => {
2554
2554
  if (getRes && getRes.networkType) {
2555
2555
  this.info.sysInfo['netWorkType'] = getRes.networkType;
2556
2556
  console.log(
2557
2557
  '在app内通过taro对象获取网络状态完成,当前网络状态',
2558
2558
  this.info.sysInfo['netWorkType'],
2559
2559
  );
2560
2560
  }
2561
2561
  });
2562
2562
  }
2563
2563
 
2564
2564
  getCacheAddressRouter() {
2565
2565
  if (isJdApp) {
2566
2566
  if (!isJdAndHarmonyDevice) {
2567
2567
  return Promise.race([
2568
2568
  new Promise((resolve) => {
2569
2569
  const getCallBackName = `getJdCacheAddress${Date.now()}`;
2570
2570
  if (!window[getCallBackName]) {
2571
2571
  window[getCallBackName] = (res) => {
2572
2572
  console.warn(`获取松果appGetJdCacheAddressRes,返回结果`, res);
2573
2573
  try {
2574
2574
  const getResJson = typeof res === 'string' ? JSON.parse(res) : res;
2575
2575
  resolve(getResJson);
2576
2576
  } catch (e) {
2577
2577
  resolve({
2578
2578
  status: '-1002',
2579
2579
  msg: '地址信息解析json异常',
2580
2580
  res,
2581
2581
  });
2582
2582
  }
2583
2583
  window[getCallBackName] = null;
2584
2584
  };
2585
2585
  }
2586
2586
  const getRouterParam = {
2587
2587
  sceneId: 'basicShoppingProcess',
2588
2588
  };
2589
2589
  if (isAndroidDevice) {
2590
2590
  return callRouterAndroid({
2591
2591
  routerURL: 'router://JDAddressModule/getCacheAddress',
2592
2592
  routerParam: getRouterParam,
2593
2593
  callBackName: getCallBackName,
2594
2594
  isSync: true,
2595
2595
  });
2596
2596
  } else {
2597
2597
  return callRouterIOS({
2598
2598
  routerURL: 'router://JDBAddressCacheManagerModule/getCacheAddress',
2599
2599
  routerParam: getRouterParam,
2600
2600
  callBackName: getCallBackName,
2601
2601
  });
2602
2602
  }
2603
2603
  }),
2604
2604
  this.taskTimeoutPromise(() => {
2605
2605
  return {
2606
2606
  status: '-1000',
2607
2607
  msg: '原生router协议获取地址信息超时',
2608
2608
  };
2609
2609
  }, 3000),
2610
2610
  ]);
2611
2611
  } else {
2612
2612
  return Promise.resolve({
2613
2613
  status: '-1001',
2614
2614
  msg: '鸿蒙系统调用jmfe异常,获取失败',
2615
2615
  });
2616
2616
  }
2617
2617
  } else if (isH5AndJingGouMini) {
2618
2618
  return Promise.resolve({
2619
2619
  status: '-1002',
2620
2620
  msg: '普通h5暂无业务需要,未实现,获取失败',
2621
2621
  });
2622
2622
  } else {
2623
2623
  return Promise.resolve({
2624
2624
  status: '-1002',
2625
2625
  msg: '普通h5暂无业务需要,未实现,获取失败',
2626
2626
  });
2627
2627
  }
2628
2628
  }
2629
2629
 
2630
2630
  getAddressCachePromise() {
2631
2631
  return new Promise((resolve) => {
2632
2632
  if (this?.info?.sysInfo?.lat && this?.info?.sysInfo?.lng && this?.info?.sysInfo?.area) {
2633
2633
  resolve({
2634
2634
  lat: this.info.sysInfo.lat,
2635
2635
  lng: this.info.sysInfo.lng,
2636
2636
  area: this?.info?.sysInfo?.area,
2637
2637
  });
2638
2638
  } else {
2639
2639
  this.getCacheAddressRouter()
2640
2640
  .then((res) => {
2641
2641
  const { status, data } = res;
2642
2642
  console.log('原生端获取经纬度及四级地址原始数据结果', status, data, res);
2643
2643
  if (status === '0' && data) {
2644
2644
  const { lat, latitude, lng, longitude, provinceId, cityId, countyId, townId } =
2645
2645
  data || {};
2646
2646
  let area = '';
2647
2647
  this.info.sysInfo['lat'] = `${lat || latitude || ''}`;
2648
2648
  this.info.sysInfo['lng'] = `${lng || longitude || ''}`;
2649
2649
  const getProvinceIdNum = provinceId ? Number(provinceId) : 0;
2650
2650
  if (getProvinceIdNum && getProvinceIdNum > 0) {
2651
2651
  area = `${provinceId}_${cityId || 0}_${countyId || 0}_${townId || 0}`;
2652
2652
  this.info.pageInfo['address'] = area;
2653
2653
  this.info.pageInfo['addressCommaStr'] = area.replace(/_/g, ',');
2654
2654
  this.info.sysInfo['area'] = area;
2655
2655
  Taro.eventCenter.trigger(TaroEventType.USER_AREA_UPDATE, {
2656
2656
  area: this.info.pageInfo.address,
2657
2657
  });
2658
2658
  }
2659
2659
  resolve({
2660
2660
  lat: this.info.sysInfo['lat'],
2661
2661
  lng: this.info.sysInfo['lng'],
2662
2662
  area: area,
2663
2663
  });
2664
2664
  } else {
2665
2665
  if (typeof res === 'object') {
2666
2666
  draBusinessCustomReport({
2667
2667
  type: 'jdapp_getCacheAddress_info_err',
2668
2668
  errMsg: '松果app内通过router协议获取用户地址及经纬度信息异常',
2669
2669
  originReqDataStr: JSON.stringify({
2670
2670
  isJdApp,
2671
2671
  jdAppVersion: jdAppVersionStr,
2672
2672
  ...res,
2673
2673
  }),
2674
2674
  });
2675
2675
  }
2676
2676
  resolve({ lat: '', lng: '', area: '' });
2677
2677
  }
2678
2678
  })
2679
2679
  .catch((e) => {
2680
2680
  console.log('getCacheAddressRouter catch e,获取经纬度信息异常e', e);
2681
2681
  draBusinessCustomReport({
2682
2682
  type: 'jdapp_getCacheAddress_info_catch_err',
2683
2683
  errMsg: '松果app内通过router协议获取用户地址及经纬度信息catch异常',
2684
2684
  originReqDataStr: JSON.stringify({
2685
2685
  isJdApp,
2686
2686
  jdAppVersion: jdAppVersionStr,
2687
2687
  }),
2688
2688
  });
2689
2689
  resolve({ lat: '', lng: '', area: '' });
2690
2690
  });
2691
2691
  }
2692
2692
  });
2693
2693
  }
2694
2694
 
2695
2695
  getLbsCacheAddressRouter() {
2696
2696
  if (isJdApp) {
2697
2697
  if (!isJdAndHarmonyDevice) {
2698
2698
  return Promise.race([
2699
2699
  new Promise((resolve) => {
2700
2700
  const getCallBackName = `getJdLbsCacheAddress${Date.now()}`;
2701
2701
  if (!window[getCallBackName]) {
2702
2702
  window[getCallBackName] = (res) => {
2703
2703
  console.warn(`获取松果appGetJdLbsCacheAddressRes,返回结果`, res);
2704
2704
  try {
2705
2705
  const getResJson = typeof res === 'string' ? JSON.parse(res) : res;
2706
2706
  resolve(getResJson);
2707
2707
  } catch (e) {
2708
2708
  resolve({
2709
2709
  status: '-1002',
2710
2710
  msg: '地址信息解析json异常',
2711
2711
  res,
2712
2712
  });
2713
2713
  }
2714
2714
  window[getCallBackName] = null;
2715
2715
  };
2716
2716
  }
2717
2717
  const getRouterParam = {
2718
2718
  appid: '219f70bbbf7e4ede7968bedaa1beafb4',
2719
2719
  sceneId: 'basicShoppingProcess',
2720
2720
  };
2721
2721
  if (isAndroidDevice) {
2722
2722
  return callRouterAndroid({
2723
2723
  routerURL: 'router://com.jingdong.app.mall.location.JSLocationManager/getLocation',
2724
2724
  routerParam: getRouterParam,
2725
2725
  callBackName: getCallBackName,
2726
2726
  isSync: true,
2727
2727
  hasJdRouter: false,
2728
2728
  });
2729
2729
  } else {
2730
2730
  return callRouterIOS({
2731
2731
  routerURL: 'router://JDBLBSKitModule/getCacheAddressInfo',
2732
2732
  routerParam: getRouterParam,
2733
2733
  callBackName: getCallBackName,
2734
2734
  isSync: true,
2735
2735
  });
2736
2736
  }
2737
2737
  }),
2738
2738
  this.taskTimeoutPromise(() => {
2739
2739
  return {
2740
2740
  status: '-1000',
2741
2741
  msg: '原生router协议获取lbs地址信息3s超时',
2742
2742
  };
2743
2743
  }, 3000),
2744
2744
  ]);
2745
2745
  } else {
2746
2746
  return Promise.resolve({
2747
2747
  status: '-1001',
2748
2748
  msg: '鸿蒙系统调用未实现,获取失败',
2749
2749
  });
2750
2750
  }
2751
2751
  } else if (isH5AndJingGouMini) {
2752
2752
  return this.getLocationForGpsPromise();
2753
2753
  } else {
2754
2754
  return Promise.resolve({
2755
2755
  status: '-1002',
2756
2756
  msg: '普通h5暂无业务需要,未实现,获取失败',
2757
2757
  });
2758
2758
  }
2759
2759
  }
2760
2760
  getLocationForGpsPromise() {
2761
2761
  return new Promise((resolve) => {
2762
2762
  let hasGetLocationForGps = true;
2763
2763
  if (urlCookie && urlCookie['loc']) {
2764
2764
  const [provinceid = 0, cityid = 0, districtid = 0, townid = 0] =
2765
2765
  urlCookie['loc'].split('_');
2766
2766
  const getProvinceIdNum = provinceid ? Number(provinceid) : 0;
2767
2767
  if (getProvinceIdNum && getProvinceIdNum > 0) {
2768
2768
  hasGetLocationForGps = false;
2769
2769
  resolve({
2770
2770
  status: '0',
2771
2771
  data: {
2772
2772
  provinceid,
2773
2773
  cityid,
2774
2774
  districtid,
2775
2775
  townid,
2776
2776
  origin: 'wxapp',
2777
2777
  },
2778
2778
  });
2779
2779
  }
2780
2780
  }
2781
2781
  if (hasGetLocationForGps && window?.navigator?.geolocation) {
2782
2782
  window.navigator.geolocation.getCurrentPosition(
2783
2783
  (position) => {
2784
2784
  console.log('h5 浏览器通过原生geolocation获取经纬度结果', position?.coords);
2785
2785
  if (position?.coords) {
2786
2786
  resolve({
2787
2787
  status: '0',
2788
2788
  data: {
2789
2789
  srclat: position.coords?.latitude,
2790
2790
  srclng: position.coords.longitude,
2791
2791
  origin: 'h5',
2792
2792
  },
2793
2793
  });
2794
2794
  } else {
2795
2795
  resolve({
2796
2796
  status: '-1001',
2797
2797
  msg: 'h5 浏览器通过原生geolocation获取经纬度结果异常,详情见position',
2798
2798
  position,
2799
2799
  });
2800
2800
  }
2801
2801
  },
2802
2802
  (error) => {
2803
2803
  resolve({
2804
2804
  status: '-1001',
2805
2805
  msg: 'h5 浏览器通过原生geolocation获取经纬度结果定位异常,详情见error',
2806
2806
  error,
2807
2807
  });
2808
2808
  },
2809
2809
  {
2810
2810
  enableHighAccuracy: false,
2811
2811
  timeout: 3 * 1000,
2812
2812
  maximumAge: 10 * 60 * 1000,
2813
2813
  },
2814
2814
  );
2815
2815
  } else {
2816
2816
  resolve({
2817
2817
  status: '-1001',
2818
2818
  msg: '您的浏览器不支持地理定位',
2819
2819
  });
2820
2820
  }
2821
2821
  });
2822
2822
  }
2823
2823
 
2824
2824
  createLbsCacheAddress(realTimeArea) {
2825
2825
  const getLbsAddressCacheMinuteTime = Number(
2826
2826
  window?.shopGlobalSwitch?.lbsAddressCacheToCookieMinuteTime || 0,
2827
2827
  );
2828
2828
  console.log(
2829
2829
  '获取lbs缓存到cookie的时间,分钟',
2830
2830
  getLbsAddressCacheMinuteTime,
2831
2831
  'lbsAddressCacheToCookieMinuteTime',
2832
2832
  window?.shopGlobalSwitch?.lbsAddressCacheToCookieMinuteTime,
2833
2833
  );
2834
2834
  if (getLbsAddressCacheMinuteTime > 0) {
2835
2835
  const expires = new Date(Date.now() + getLbsAddressCacheMinuteTime * 60 * 1000);
2836
2836
  realTimeArea &&
2837
2837
  cookie.set(cacheH5LbsAddressKey, realTimeArea, {
2838
2838
  path: '/',
2839
2839
  expires,
2840
2840
  });
2841
2841
  }
2842
2842
  }
2843
2843
 
2844
2844
  getLbsAddressCachePromise() {
2845
2845
  if (!this.lbsAddressCachePromise) {
2846
2846
  this.lbsAddressCachePromise = new Promise((resolve) => {
2847
2847
  const getCookieForLbsAddress = window?.shopGlobalSwitch?.lbsAddressCacheToCookieMinuteTime
2848
2848
  ? cookie.get(cacheH5LbsAddressKey)
2849
2849
  : '';
2850
2850
  const getUserLbsAddress = this?.info?.pageInfo?.userLbsAddress;
2851
2851
  if (getUserLbsAddress && getUserLbsAddress !== '') {
2852
2852
  resolve({
2853
2853
  ok: true,
2854
2854
  realTimeArea: getUserLbsAddress,
2855
2855
  });
2856
2856
  } else if (getCookieForLbsAddress && getCookieForLbsAddress !== '') {
2857
2857
  console.info(
2858
2858
  `通过cookie获取缓存的userLbsAddress,${window?.shopGlobalSwitch?.lbsAddressCacheToCookieMinuteTime}分钟内有效`,
2859
2859
  getCookieForLbsAddress,
2860
2860
  );
2861
2861
  this.info.pageInfo['userLbsAddress'] = getCookieForLbsAddress;
2862
2862
  this.info.sysInfo['realTimeArea'] = getCookieForLbsAddress;
2863
2863
  Taro.eventCenter.trigger(TaroEventType.USER_AREA_UPDATE, {
2864
2864
  realTimeArea: getCookieForLbsAddress,
2865
2865
  });
2866
2866
  resolve({
2867
2867
  ok: true,
2868
2868
  realTimeArea: getCookieForLbsAddress,
2869
2869
  });
2870
2870
  } else {
2871
2871
  this.getLbsCacheAddressRouter()
2872
2872
  .then((res) => {
2873
2873
  const { status, data } = res;
2874
2874
  console.log(
2875
2875
  '原生或者内嵌京购端获取基于lbs的经纬度及四级地址原始数据结果',
2876
2876
  status,
2877
2877
  data,
2878
2878
  res,
2879
2879
  );
2880
2880
  if (status === '0' && data) {
2881
2881
  const { srclat, srclng, provinceid, cityid, districtid, townid, origin } =
2882
2882
  data || {};
2883
2883
  let realTimeArea = '';
2884
2884
  this.info.sysInfo['srclat'] = `${srclat || ''}`;
2885
2885
  this.info.sysInfo['srclng'] = `${srclng || ''}`;
2886
2886
  const getProvinceIdNum = provinceid ? Number(provinceid) : 0;
2887
2887
  if (getProvinceIdNum && getProvinceIdNum > 0) {
2888
2888
  realTimeArea = `${provinceid}_${cityid || 0}_${districtid || 0}_${townid || 0}`;
2889
2889
  this.info.pageInfo['userLbsAddress'] = realTimeArea;
2890
2890
  this.info.sysInfo['realTimeArea'] = realTimeArea;
2891
2891
  Taro.eventCenter.trigger(TaroEventType.USER_AREA_UPDATE, {
2892
2892
  realTimeArea: this.info.pageInfo.userLbsAddress,
2893
2893
  });
2894
2894
  this.createLbsCacheAddress(realTimeArea);
2895
2895
  } else {
2896
2896
  !origin && (this.lbsAddressCachePromise = null);
2897
2897
  }
2898
2898
  const getValidRealTimeArea = realTimeArea !== '';
2899
2899
  resolve({
2900
2900
  lat: this.info.sysInfo['srclat'],
2901
2901
  lng: this.info.sysInfo['srclng'],
2902
2902
  realTimeArea: realTimeArea,
2903
2903
  ok: getValidRealTimeArea,
2904
2904
  msg: getValidRealTimeArea
2905
2905
  ? '成功'
2906
2906
  : origin
2907
2907
  ? origin
2908
2908
  : '根据router底层获取lbs地址信息异常,详情见data',
2909
2909
  data: getValidRealTimeArea ? null : res,
2910
2910
  });
2911
2911
  if (!getValidRealTimeArea && !origin) {
2912
2912
  draBusinessCustomReport({
2913
2913
  type: 'h5_getLbsCacheAddress_info_err',
2914
2914
  errMsg: '松果app内通过router协议获取基于lbs实时用户地址及经纬度信息catch异常',
2915
2915
  originReqDataStr: JSON.stringify({
2916
2916
  isJdApp,
2917
2917
  jdAppVersion: jdAppVersionStr,
2918
2918
  }),
2919
2919
  });
2920
2920
  }
2921
2921
  } else {
2922
2922
  typeof res === 'object' &&
2923
2923
  draBusinessCustomReport({
2924
2924
  type: 'h5_getLbsCacheAddress_info_err',
2925
2925
  errMsg:
2926
2926
  'h5通过router协议或者浏览器gps获取基于lbs实时用户缓存地址及经纬度信息异常',
2927
2927
  originReqDataStr: JSON.stringify({
2928
2928
  isJdApp,
2929
2929
  jdAppVersion: jdAppVersionStr,
2930
2930
  ...res,
2931
2931
  }),
2932
2932
  });
2933
2933
  this.lbsAddressCachePromise = null;
2934
2934
  resolve({ realTimeArea: '', ok: false });
2935
2935
  }
2936
2936
  })
2937
2937
  .catch((e) => {
2938
2938
  console.log('getLbsAddressCachePromise catch e,获取经纬度信息异常e', e);
2939
2939
  this.lbsAddressCachePromise = null;
2940
2940
  draBusinessCustomReport({
2941
2941
  type: 'h5_getLbsCacheAddress_info_err',
2942
2942
  errMsg:
2943
2943
  'h5内通过router协议获取浏览器gps获取基于lbs实时用户地址及经纬度信息catch异常',
2944
2944
  originReqDataStr: JSON.stringify({
2945
2945
  isJdApp,
2946
2946
  jdAppVersion: jdAppVersionStr,
2947
2947
  }),
2948
2948
  });
2949
2949
  resolve({ realTimeArea: '', ok: false });
2950
2950
  });
2951
2951
  }
2952
2952
  });
2953
2953
  }
2954
2954
  return this.lbsAddressCachePromise;
2955
2955
  }
2956
2956
 
2957
2957
  async updateMPaasConfigAsync(isBeforePageReady: boolean) {
2958
2958
  console.log('updateMPaasConfigAsync isBeforePageReady:', isBeforePageReady);
2959
2959
  if (!isJdApp) {
2960
2960
  return;
2961
2961
  }
2962
2962
  const avifSwitch = await getMPaasConfigByBussinessKey('avifSwitch', isBeforePageReady);
2963
2963
  this.info.sysInfo.dynamicConfig['avifSwitch'] = avifSwitch;
2964
2964
  const hybridHttpSwitch = await getMPaasConfigByBussinessKey(
2965
2965
  'hybridHttpSwitch',
2966
2966
  isBeforePageReady,
2967
2967
  );
2968
2968
  const jshopIsVipShopSwitch = await getMPaasConfigByBussinessKey(
2969
2969
  'jshopIsVipShop',
2970
2970
  isBeforePageReady,
2971
2971
  );
2972
2972
  this.info.sysInfo.dynamicConfig['hybridHttpSwitch'] = hybridHttpSwitch;
2973
2973
  this.info.sysInfo.dynamicConfig['jshopIsVipShopSwitch'] = jshopIsVipShopSwitch;
2974
2974
  const isFollowAppVideoPlayStatus = await getMPaasConfigByBussinessKey(
2975
2975
  'isFollowAppVideoPlayStatus',
2976
2976
  isBeforePageReady,
2977
2977
  );
2978
2978
  console.log(
2979
2979
  'isBeforePageReady:',
2980
2980
  isBeforePageReady,
2981
2981
  'isFollowAppVideoPlayStatus:',
2982
2982
  isFollowAppVideoPlayStatus,
2983
2983
  );
2984
2984
  if (isFollowAppVideoPlayStatus === true || isFollowAppVideoPlayStatus === 'true') {
2985
2985
  this.info.sysInfo.dynamicConfig['isFollowAppVideoPlayStatus'] = true;
2986
2986
  }
2987
2987
  }
2988
2988
 
2989
2989
  async getWifiVideoAutoPlayAsync() {
2990
2990
  this.info.sysInfo['wifiVideoAutoPlay'] = false;
2991
2991
  if (!isJdApp) {
2992
2992
  return;
2993
2993
  }
2994
2994
  const videoPlayStatus = await getWifiVideoAutoPlay().catch((e) => {
2995
2995
  return 0;
2996
2996
  });
2997
2997
  if (Number(videoPlayStatus) === 1) {
2998
2998
  this.info.sysInfo['wifiVideoAutoPlay'] = true;
2999
2999
  }
3000
3000
  }
3001
3001
 
3002
3002
  async getMPaasConfigAsync() {
3003
3003
  this.info.sysInfo.dynamicConfig = {};
3004
3004
  this.info.sysInfo.dynamicConfig['avifSwitch'] = {};
3005
3005
  this.info.sysInfo.dynamicConfig['hybridHttpSwitch'] = {};
3006
3006
  this.info.sysInfo.dynamicConfig['jshopIsVipShopSwitch'] = {};
3007
3007
  this.info.sysInfo.dynamicConfig['isFollowAppVideoPlayStatus'] = false;
3008
3008
  return this.updateMPaasConfigAsync(true);
3009
3009
  }
3010
3010
 
3011
3011
  getDynamicConfig(key: string) {
3012
3012
  return this.info.sysInfo?.dynamicConfig?.[key];
3013
3013
  }
3014
3014
  async updateMPaasConfig() {
3015
3015
  console.log('updateMPaasConfig');
3016
3016
  if (
3017
3017
  isIosDevice &&
3018
3018
  versionCompare(jdAppVersionStr, MPAAS_CONFIG_APP_VERSION) < 0 &&
3019
3019
  versionCompare(jdAppVersionStr, MPAAS_CONFIG_APP_LOW_VERSION) >= 0
3020
3020
  ) {
3021
3021
  try {
3022
3022
  await this.updateMPaasConfigAsync(false);
3023
3023
  } catch (e) {
3024
3024
  console.log('updateMPaasConfigAsync:', e);
3025
3025
  }
3026
3026
  }
3027
3027
  }
3028
3028
 
3029
3029
  toLogin(options) {
3030
3030
  return this.info.isJingGouMiniViewState || this.info.isJingxiMiniViewState
3031
3031
  ? this.toWxAppLogin(options)
3032
3032
  : this.toWebLogin(options);
3033
3033
  }
3034
3034
 
3035
3035
  doLogin(options) {
3036
3036
  return this.toLogin(options);
3037
3037
  }
3038
3038
 
3039
3039
  doLoginForJdPin(options = {}) {
3040
3040
  return this.doLogin({
3041
3041
  loginColor: {
3042
3042
  biz: WXAPP_BIZ_SHOP_LIGHT_KEY,
3043
3043
  dpin: 0,
3044
3044
  },
3045
3045
  ...options,
3046
3046
  });
3047
3047
  }
3048
3048
 
3049
3049
  toWebLogin(options) {
3050
3050
  let params: {
3051
3051
  returnurl: string;
3052
3052
  } = {
3053
3053
  returnurl: '',
3054
3054
  };
3055
3055
  const checkToPcLogin = options ? options?.isPc : isPc;
3056
3056
  const loginUrl = checkToPcLogin
3057
3057
  ? `//passport.jd.com/new/login.aspx`
3058
3058
  : `${domain.mobileLogin}/user/login.action`;
3059
3059
  const defaultParams = {
3060
3060
  appid: '100',
3061
3061
  returnurl: window.location.href,
3062
3062
  };
3063
3063
  if (isString(options)) {
3064
3064
  params = Object.assign({}, defaultParams, {
3065
3065
  returnurl: options,
3066
3066
  });
3067
3067
  } else if (isObject(options)) {
3068
3068
  const { loginColor, ...otherOptions } = options;
3069
3069
  params = Object.assign({}, defaultParams, otherOptions);
3070
3070
  } else {
3071
3071
  params = defaultParams;
3072
3072
  }
3073
3073
  params.returnurl = encodeURIComponent(params.returnurl);
3074
3074
  let getFullUrl = loginUrl + '?' + serialize(params);
3075
3075
  if (checkToPcLogin) {
3076
3076
  getFullUrl = getFullUrl.replace(/returnurl/, 'ReturnUrl');
3077
3077
  }
3078
3078
  return Promise.resolve({
3079
3079
  h5ToUrl: true,
3080
3080
  url: getFullUrl,
3081
3081
  }).then(() => {
3082
3082
  window.location.href = getFullUrl;
3083
3083
  });
3084
3084
  }
3085
3085
 
3086
3086
  toWxAppLogin(options = {}) {
3087
3087
  console.log('微信京购小程序中h5登录跳转', options);
3088
3088
  return Promise.resolve(true).then(() => {
3089
3089
  const { loginColor } = Object.assign(
3090
3090
  {},
3091
3091
  {
3092
3092
  loginColor: {
3093
3093
  biz: WXAPP_BIZ_KEY,
3094
3094
  dpin: 1,
3095
3095
  },
3096
3096
  },
3097
3097
  options,
3098
3098
  );
3099
3099
  window.location.href = `${domain.wq}/pinbind/pintokenredirect?biz=${
3100
3100
  loginColor.biz
3101
3101
  }&url=${encodeURIComponent(window.location.href)}`;
3102
3102
  });
3103
3103
  }
3104
3104
 
3105
3105
  getLoginCookie() {
3106
3106
  return Promise.resolve({
3107
3107
  pin: cookie.get('pin') || '',
3108
3108
  });
3109
3109
  }
3110
3110
 
3111
3111
  clearLoginCookie() {
3112
3112
  cookie.remove('pin');
3113
3113
  }
3114
3114
 
3115
3115
  checkStatusAndLogin(options = {}) {
3116
3116
  if (!this.checkStatusAndLoginPromise) {
3117
3117
  this.checkStatusAndLoginPromise = new Promise(async (resolve, reject) => {
3118
3118
  try {
3119
3119
  const getLoginState = await this.doCheckLoginStateAndForApiCheck(options);
3120
3120
  if (getLoginState) {
3121
3121
  resolve(true);
3122
3122
  } else {
3123
3123
  this.toLogin(options);
3124
3124
  reject(false);
3125
3125
  }
3126
3126
  } catch (e) {
3127
3127
  this.toLogin(options);
3128
3128
  reject(false);
3129
3129
  }
3130
3130
  });
3131
3131
  return this.checkStatusAndLoginPromise;
3132
3132
  } else {
3133
3133
  return this.checkStatusAndLoginPromise
3134
3134
  .then(() => {
3135
3135
  return Promise.resolve(true);
3136
3136
  })
3137
3137
  .catch(() => {
3138
3138
  this.toLogin(options);
3139
3139
  return Promise.reject(true);
3140
3140
  });
3141
3141
  }
3142
3142
  }
3143
3143
 
3144
3144
  checkJdStatusAndLogin(
3145
3145
  options = {
3146
3146
  loginColor: {
3147
3147
  biz: WXAPP_BIZ_SHOP_LIGHT_KEY,
3148
3148
  dpin: 0,
3149
3149
  },
3150
3150
  },
3151
3151
  ) {
3152
3152
  return this.checkStatusAndLogin(options);
3153
3153
  }
3154
3154
 
3155
3155
  doCheckLoginStateAndForApiCheck(options) {
3156
3156
  if (this.info.loginState) {
3157
3157
  return Promise.resolve(true);
3158
3158
  } else {
3159
3159
  return new Promise((resolve, reject) => {
3160
3160
  if (this.info.isJingGouMiniViewState || this.info.isJingxiMiniViewState) {
3161
3161
  const getWqAuthToken = cookie.get('wq_auth_token');
3162
3162
  const getWqSkey = cookie.get('wq_skey');
3163
3163
  const getWqUin = cookie.get('wq_uin');
3164
3164
  const isLoginState =
3165
3165
  options?.loginColor?.dpin === 0 ? getWqAuthToken : getWqSkey && getWqUin;
3166
3166
  if (isLoginState) {
3167
3167
  this.info.loginState = true;
3168
3168
  resolve(true);
3169
3169
  } else {
3170
3170
  reject(false);
3171
3171
  }
3172
3172
  } else {
3173
3173
  Taro.request({
3174
3174
  url: api.isLogin,
3175
3175
  jsonp: true,
3176
3176
  timeout: 3000,
3177
3177
  success: (res) => {
3178
3178
  const { statusCode, data } = res;
3179
3179
  if (statusCode === 200 && data?.islogin && Number(data.islogin) === 1) {
3180
3180
  this.info.loginState = true;
3181
3181
  resolve(true);
3182
3182
  } else {
3183
3183
  reject(false);
3184
3184
  }
3185
3185
  },
3186
3186
  fail: (err) => {
3187
3187
  console.log('登录检查异常', err);
3188
3188
  reject(false);
3189
3189
  },
3190
3190
  });
3191
3191
  }
3192
3192
  });
3193
3193
  }
3194
3194
  }
3195
3195
 
3196
3196
  checkLoginStatus(options) {
3197
3197
  return new Promise(async (resolve, reject) => {
3198
3198
  try {
3199
3199
  const getLoginState = await this.doCheckLoginStateAndForApiCheck(options);
3200
3200
  if (getLoginState) {
3201
3201
  const { pin } = await this.getLoginCookie();
3202
3202
  this.info.userInfo = {
3203
3203
  pin,
3204
3204
  encodePin: encodeURIComponent(pin),
3205
3205
  ptkey: '',
3206
3206
  };
3207
3207
  resolve(true);
3208
3208
  } else {
3209
3209
  reject(false);
3210
3210
  }
3211
3211
  } catch (e) {
3212
3212
  reject(false);
3213
3213
  }
3214
3214
  });
3215
3215
  }
3216
3216
 
3217
3217
  updatePageAndLogInfo(updateQuery = {}) {
3218
3218
  const createUpdateQueryInfo: {
3219
3219
  query: {
3220
3220
  shopId?: string | number;
3221
3221
  venderId?: string | number;
3222
3222
  };
3223
3223
  updateShopInfoState: boolean;
3224
3224
  } = Object.assign(
3225
3225
  {},
3226
3226
  {
3227
3227
  query: {},
3228
3228
  updateShopInfoState: false,
3229
3229
  },
3230
3230
  updateQuery,
3231
3231
  );
3232
3232
  console.log(
3233
3233
  '获取当前下发的店铺查询参数',
3234
3234
  updateQuery,
3235
3235
  '获取之前保存的shopInfo店铺查询参数',
3236
3236
  this.info?.shopInfo,
3237
3237
  );
3238
3238
  const { query, updateShopInfoState } = createUpdateQueryInfo;
3239
3239
  const { shopId, venderId, un_area } = query;
3240
3240
  if (updateShopInfoState) {
3241
3241
  this.info.queryInfo = {
3242
3242
  ...this.info.queryInfo,
3243
3243
  ...query,
3244
3244
  };
3245
3245
  if (shopId && venderId) {
3246
3246
  this.info.shopInfo = {
3247
3247
  shopId: `${shopId}`,
3248
3248
  venderId: `${venderId}`,
3249
3249
  };
3250
3250
  }
3251
3251
  } else {
3252
3252
  this.info.queryInfo = {
3253
3253
  ...query,
3254
3254
  };
3255
3255
  if (
3256
3256
  this.info.shopInfo?.shopId &&
3257
3257
  this.info.shopInfo?.venderId &&
3258
3258
  (this.info.shopInfo.shopId == shopId || this.info.shopInfo.venderId == venderId)
3259
3259
  ) {
3260
3260
  this.info.queryInfo.shopId = this.info.shopInfo.shopId;
3261
3261
  this.info.queryInfo.venderId = this.info.shopInfo.venderId;
3262
3262
  console.log(
3263
3263
  '当前存储的店铺shopId和venderId与下发的店铺信息shopId或者venderId为同一个,补充shopId或者venderId查询参数',
3264
3264
  this.info.queryInfo,
3265
3265
  );
3266
3266
  }
3267
3267
  }
3268
3268
  this.info.queryInfo['shopId'] &&
3269
3269
  (this.info.queryInfo['shopId'] = `${this.info.queryInfo['shopId']}`);
3270
3270
  this.info.queryInfo['venderId'] &&
3271
3271
  (this.info.queryInfo['venderId'] = `${this.info.queryInfo['venderId']}`);
3272
3272
  console.log(
3273
3273
  'h5==获取店铺下发查询参数\n',
3274
3274
  query,
3275
3275
  '\n获取店铺最后查询参数\n',
3276
3276
  this.info.queryInfo,
3277
3277
  '\n是否为更新店铺状态\n',
3278
3278
  updateShopInfoState,
3279
3279
  );
3280
3280
  const changeArea = un_area && un_area.length > 0 ? un_area : isPc && ipLoc_djd ? ipLoc_djd : '';
3281
3281
  if (changeArea) {
3282
3282
  const getBottomAreaStr = changeArea.replace(/-/g, '_');
3283
3283
  this.info.pageInfo.address = getBottomAreaStr;
3284
3284
  this.info.pageInfo.un_area = getBottomAreaStr;
3285
3285
  this.info.pageInfo.addressCommaStr = getBottomAreaStr.replace(/_/g, ',');
3286
3286
  }
3287
3287
  }
3288
3288
 
3289
3289
  dealLoadSdkList() {
3290
3290
  const globalLoadJsList = window?.shopGlobalSwitch?.asyncLoadJsList ?? [];
3291
3291
  const businessLoadJsList = window?.PAGE_DATA?.businessData?.asyncLoadJsList ?? [];
3292
3292
  const concatLoadJsList = [].concat(globalLoadJsList, businessLoadJsList);
3293
3293
  let mergeLoadJsList = globalLoadJsList;
3294
3294
  try {
3295
3295
  mergeLoadJsList = concatLoadJsList.reduce((accArr: any[], current: any) => {
3296
3296
  const getFindIndex = accArr.findIndex((item) => item?.fileName === current?.fileName);
3297
3297
  getFindIndex !== -1
3298
3298
  ? (accArr[getFindIndex] = { ...accArr[getFindIndex], ...current })
3299
3299
  : accArr.push(current);
3300
3300
  return accArr;
3301
3301
  }, []);
3302
3302
  } catch (e) {
3303
3303
  console.log('LoadJsList合并错误', e);
3304
3304
  }
3305
3305
  console.log(
3306
3306
  'globalLoadJsList',
3307
3307
  globalLoadJsList,
3308
3308
  'businessLoadJsList',
3309
3309
  businessLoadJsList,
3310
3310
  '两个加载jsList集合合并完成',
3311
3311
  mergeLoadJsList,
3312
3312
  );
3313
3313
  this.loadJsSdkList = mergeLoadJsList;
3314
3314
  return this.loadJsSdkList;
3315
3315
  }
3316
3316
 
3317
3317
  renderNextTickLoadSdk() {
3318
3318
  Taro.nextTick(() => {
3319
3319
  console.log(
3320
3320
  '页面渲染的下一帧执行的js加载方法,当前nextTick存在state的渲染问题,先延迟1s=======',
3321
3321
  );
3322
3322
  setTimeout(() => {
3323
3323
  this.loadOtherSdk(LoadJsInitTriggerType.NRXT_TICK, this.loadJsSdkList);
3324
3324
  }, 1000);
3325
3325
  });
3326
3326
  }
3327
3327
 
3328
3328
  loadOtherSdk(triggerType = LoadJsInitTriggerType.NOW, loadJsList: any[] = []) {
3329
3329
  const getLoadJsList =
3330
3330
  Array.isArray(loadJsList) && loadJsList.length > 0 ? loadJsList : this.dealLoadSdkList();
3331
3331
  const getLoadFilterList = getLoadJsList.filter((item) => {
3332
3332
  const getInitLoadEnvType = item?.initLoadEnvType || LoadJsInitLoadEnvType.ALL;
3333
3333
  let getLoastLoadEventState = true;
3334
3334
  if (getInitLoadEnvType === LoadJsInitLoadEnvType.JD_APP) {
3335
3335
  getLoastLoadEventState = isJdApp;
3336
3336
  }
3337
3337
  else if (getInitLoadEnvType === LoadJsInitLoadEnvType.M) {
3338
3338
  getLoastLoadEventState = !isJdApp || !!isJdAndHarmonyDevice;
3339
3339
  }
3340
3340
  const getInitTriggerType =
3341
3341
  isJdApp && item?.initJdAppTriggerType
3342
3342
  ? item?.initTriggerType
3343
3343
  : item?.initTriggerType || LoadJsInitTriggerType.NOW;
3344
3344
  const getInitLinkTriggerWay = window?.PAGE_DATA[item?.initLinkTriggerWay] || false;
3345
3345
  return getLoastLoadEventState && getInitTriggerType === triggerType && getInitLinkTriggerWay;
3346
3346
  });
3347
3347
  console.log(
3348
3348
  '获取当前触发方式',
3349
3349
  triggerType,
3350
3350
  '获取当前最后加载的js集合',
3351
3351
  getLoadFilterList,
3352
3352
  '过滤前的加载集合',
3353
3353
  getLoadJsList,
3354
3354
  );
3355
3355
  getLoadFilterList.length > 0 &&
3356
3356
  getLoadFilterList.forEach((item) => {
3357
3357
  const isLoadState = /sgm/.test(item?.fileName)
3358
3358
  ? window?.shopGlobalSwitch?.openSgm === 'true'
3359
3359
  : true;
3360
3360
  isLoadState &&
3361
3361
  this.loadItemSdkPromise(item)
3362
3362
  .then((res) => {
3363
3363
  console.info('当前js地址' + item?.src, '加载状态', res);
3364
3364
  const isFileNameNewDraSdkJs = res?.fileName === 'newDraSdkJs';
3365
3365
  if (isFileNameNewDraSdkJs && window?.dra?.run) {
3366
3366
  window.dra.run('init', { aid: res?.aid });
3367
3367
  window.dra.run('start');
3368
3368
  }
3369
3369
  })
3370
3370
  .catch((err) => {
3371
3371
  console.info('当前js地址加载异常', item?.src);
3372
3372
  window?.fetchErrorData &&
3373
3373
  window.fetchErrorData({
3374
3374
  title: '公共js加载异常',
3375
3375
  type: 'jsLoad',
3376
3376
  data: err,
3377
3377
  });
3378
3378
  });
3379
3379
  });
3380
3380
  }
3381
3381
  loadScriptEle(jsInfo, resolve, reject) {
3382
3382
  const getFileName = jsInfo?.fileName;
3383
3383
  if (getFileName) {
3384
3384
  const getEleId = `J_loadJs_${getFileName}`;
3385
3385
  const getEle = document.getElementById(getEleId);
3386
3386
  if (!getEle) {
3387
3387
  const jsLoadErrorSgmCode = `jsLoadError_${jsInfo?.fileName || 'customJs'}`;
3388
3388
  const _sgmEle = document.createElement('script');
3389
3389
  _sgmEle.id = getEleId;
3390
3390
  _sgmEle.onload = function () {
3391
3391
  resolve({
3392
3392
  ...jsInfo,
3393
3393
  jsTip: 'js加载成功',
3394
3394
  });
3395
3395
  };
3396
3396
  _sgmEle.onerror = function () {
3397
3397
  reject({
3398
3398
  ...jsInfo,
3399
3399
  env: getSgmCustomCode(jsLoadErrorSgmCode),
3400
3400
  jsReqError: '当前js创建标签触发onerror异常回调,请排查网络络错误或语法错误或运行时错误',
3401
3401
  });
3402
3402
  };
3403
3403
  const dataAttrList = ['timeout', 'fileName', 'env'];
3404
3404
  const getJsInfoKeyList = Object.keys(jsInfo);
3405
3405
  getJsInfoKeyList.forEach((key) => {
3406
3406
  if (key === 'async') {
3407
3407
  _sgmEle.async = jsInfo[key];
3408
3408
  } else if (key === 'crossOrigin') {
3409
3409
  _sgmEle.crossOrigin = jsInfo[key];
3410
3410
  } else if (key === 'src') {
3411
3411
  _sgmEle.src = `${jsInfo[key]}`;
3412
3412
  } else if (dataAttrList.includes(key) || /init/.test(key)) {
3413
3413
  _sgmEle.setAttribute(`data-${key}`, jsInfo[key]);
3414
3414
  } else {
3415
3415
  _sgmEle.setAttribute(key, jsInfo[key]);
3416
3416
  }
3417
3417
  });
3418
3418
  document.head.appendChild(_sgmEle);
3419
3419
  } else {
3420
3420
  console.log(`当前${jsInfo?.fileName || 'js'}已经存在页面中,可以直接调用相关方法`, jsInfo);
3421
3421
  resolve({
3422
3422
  ...jsInfo,
3423
3423
  jsTip: 'js本身已存在页面中',
3424
3424
  });
3425
3425
  }
3426
3426
  } else {
3427
3427
  console.warn('当前js资源信息缺少必要的参数fileName,请关注', jsInfo);
3428
3428
  }
3429
3429
  }
3430
3430
 
3431
3431
  loadItemSdkPromise(jsInfo = {}) {
3432
3432
  if (jsInfo?.src) {
3433
3433
  const getInitLoadType =
3434
3434
  isJdApp && jsInfo?.initJdAppLoadType
3435
3435
  ? jsInfo?.initJdAppLoadType
3436
3436
  : jsInfo?.initLoadType || LoadJsInitLoadType.ALL;
3437
3437
  if (getInitLoadType !== LoadJsInitLoadType.NONE) {
3438
3438
  const getFileKeyName = jsInfo?.fileName || jsInfo?.src;
3439
3439
  if (!this.loadJsSdkListCachePromise[getFileKeyName]) {
3440
3440
  if (getInitLoadType !== LoadJsInitLoadType.INSERT_ELE) {
3441
3441
  this.loadJsSdkListCachePromise[getFileKeyName] = new Promise((resolve, reject) => {
3442
3442
  const jsLoadErrorSgmCode = `jsLoadError_${jsInfo?.fileName || 'customJs'}`;
3443
3443
  try {
3444
3444
  const jsXhrRequest = new XMLHttpRequest();
3445
3445
  jsXhrRequest.timeout = jsInfo?.timeout ?? 2000;
3446
3446
  const jsUrl = `${jsInfo?.src}`;
3447
3447
  jsXhrRequest.open('GET', jsUrl, true);
3448
3448
  jsXhrRequest.onreadystatechange = () => {
3449
3449
  if (jsXhrRequest.readyState === 4) {
3450
3450
  const getReqStatus = jsXhrRequest.status;
3451
3451
  if ((getReqStatus >= 200 && getReqStatus < 300) || getReqStatus === 304) {
3452
3452
  const getInsetHeadState = getInitLoadType === LoadJsInitLoadType.ALL;
3453
3453
  if (getInsetHeadState) {
3454
3454
  this.loadScriptEle(jsInfo, resolve, reject);
3455
3455
  } else {
3456
3456
  resolve({
3457
3457
  ...jsInfo,
3458
3458
  jsTip: 'js请求成功,暂未插入head节点,业务自行单独插入',
3459
3459
  });
3460
3460
  }
3461
3461
  getReqStatus !== 200 &&
3462
3462
  sgmCustomReport({
3463
3463
  type: 3,
3464
3464
  code: 'js_load_special_code',
3465
3465
  msg: {
3466
3466
  msg: '当前js加载成功,状态非200,特殊上报观察',
3467
3467
  jsReqState: getReqStatus,
3468
3468
  env: getSgmCustomCode('js_load_special_code'),
3469
3469
  data: jsInfo,
3470
3470
  },
3471
3471
  });
3472
3472
  } else {
3473
3473
  const getRes = {
3474
3474
  ...jsInfo,
3475
3475
  env: getSgmCustomCode(jsLoadErrorSgmCode),
3476
3476
  jsReqError: `请求状态异常,状态码为${getReqStatus}`,
3477
3477
  jsReqState: getReqStatus,
3478
3478
  };
3479
3479
  console.log('当前js请求状态异常,具体信息见', getRes);
3480
3480
  reject(getRes);
3481
3481
  }
3482
3482
  }
3483
3483
  };
3484
3484
  jsXhrRequest.onerror = () => {
3485
3485
  const getRes = {
3486
3486
  ...jsInfo,
3487
3487
  env: getSgmCustomCode(jsLoadErrorSgmCode),
3488
3488
  jsReqError: '请求错误',
3489
3489
  };
3490
3490
  console.log('当前js请求错误', getRes);
3491
3491
  jsXhrRequest.abort();
3492
3492
  reject(getRes);
3493
3493
  };
3494
3494
  jsXhrRequest.ontimeout = () => {
3495
3495
  const getRes = {
3496
3496
  ...jsInfo,
3497
3497
  env: getSgmCustomCode(jsLoadErrorSgmCode),
3498
3498
  jsReqError: `请求${jsXhrRequest.timeout}ms超时异常`,
3499
3499
  jsReqState: jsXhrRequest.status,
3500
3500
  };
3501
3501
  console.log('当前js请求超时异常', getRes);
3502
3502
  jsXhrRequest.abort();
3503
3503
  reject(getRes);
3504
3504
  };
3505
3505
  jsXhrRequest.send();
3506
3506
  } catch (e) {
3507
3507
  console.log('执行js请求异常', e);
3508
3508
  reject({
3509
3509
  ...jsInfo,
3510
3510
  env: getSgmCustomCode(jsLoadErrorSgmCode),
3511
3511
  jsReqError: '未知异常',
3512
3512
  error: e,
3513
3513
  });
3514
3514
  }
3515
3515
  });
3516
3516
  } else {
3517
3517
  this.loadJsSdkListCachePromise[getFileKeyName] = new Promise((resolve, reject) => {
3518
3518
  return this.loadScriptEle(jsInfo, resolve, reject);
3519
3519
  });
3520
3520
  }
3521
3521
  }
3522
3522
  return this.loadJsSdkListCachePromise[getFileKeyName];
3523
3523
  } else {
3524
3524
  return Promise.resolve({
3525
3525
  ...jsInfo,
3526
3526
  jsTip: 'js加载方式设置为不加载,当前不做处理',
3527
3527
  });
3528
3528
  }
3529
3529
  } else {
3530
3530
  return Promise.reject(jsInfo);
3531
3531
  }
3532
3532
  }
3533
3533
 
3534
3534
  createLanguagePromise() {
3535
3535
  const getLanguageConfig = window?.shopGlobalSwitch?.language || {};
3536
3536
  if (!this.languageCacheProimse) {
3537
3537
  this.languageCacheProimse = new Promise((resolve, reject) => {
3538
3538
  const { fileName, prefixUrl } = getLanguageConfig;
3539
3539
  console.log('getLanguageConfig', getLanguageConfig, 'languageNowType', languageNowType);
3540
3540
  const dealLanguageFile = () => {
3541
3541
  this.getLanguageFilePromise(getLanguageConfig, languageNowType)
3542
3542
  .then((res) => {
3543
3543
  if (res && res?.data) {
3544
3544
  this.languageJsonData = res.data;
3545
3545
 
3546
3546
  setTimeout(() => {
3547
3547
  const getOtherLanguageList = languageTypeList.filter(
3548
3548
  (item) => item !== languageNowType,
3549
3549
  );
3550
3550
  getOtherLanguageList.length > 0 &&
3551
3551
  getOtherLanguageList.map((languageTypeKey) => {
3552
3552
  this.getLanguageFilePromise(getLanguageConfig, languageTypeKey);
3553
3553
  });
3554
3554
  }, 3000);
3555
3555
  resolve(res);
3556
3556
  } else {
3557
3557
  reject(res);
3558
3558
  }
3559
3559
  })
3560
3560
  .catch((err) => {
3561
3561
  reject(err);
3562
3562
  });
3563
3563
  };
3564
3564
  if (fileName && prefixUrl) {
3565
3565
  const getLangStorageKey = `jshopx_lang_${languageNowType}`;
3566
3566
  const getLocalLangRes = getTaroStorageKeyValue(getLangStorageKey);
3567
3567
  if (getLocalLangRes) {
3568
3568
  try {
3569
3569
  const getLocalLangJsonData =
3570
3570
  typeof getLocalLangRes === 'string' ? JSON.parse(getLocalLangRes) : getLocalLangRes;
3571
3571
  if (getLocalLangJsonData?.fileName && getLocalLangJsonData?.data) {
3572
3572
  if (getLocalLangJsonData?.fileName === fileName) {
3573
3573
  const geThisLangData = getLocalLangJsonData.data;
3574
3574
  this.languageJsonData = geThisLangData;
3575
3575
  return resolve({
3576
3576
  ...getLanguageConfig,
3577
3577
  languageNowType,
3578
3578
  data: geThisLangData,
3579
3579
  });
3580
3580
  } else {
3581
3581
  dealLanguageFile();
3582
3582
  }
3583
3583
  } else {
3584
3584
  dealLanguageFile();
3585
3585
  }
3586
3586
  } catch (e) {
3587
3587
  return reject({
3588
3588
  languageNowType,
3589
3589
  msg: '转换错误',
3590
3590
  ...getLanguageConfig,
3591
3591
  });
3592
3592
  }
3593
3593
  } else {
3594
3594
  dealLanguageFile();
3595
3595
  }
3596
3596
  } else {
3597
3597
  return reject({
3598
3598
  languageNowType,
3599
3599
  msg: '文件对象下发异常',
3600
3600
  ...getLanguageConfig,
3601
3601
  });
3602
3602
  }
3603
3603
  });
3604
3604
  }
3605
3605
  return this.languageCacheProimse;
3606
3606
  }
3607
3607
 
3608
3608
  getLanguageFilePromise(info, languageTypeKey) {
3609
3609
  const { fileName, prefixUrl, timeout } = info || {};
3610
3610
  const getUrl = `${prefixUrl}${fileName}_${languageTypeKey}.json`;
3611
3611
  return new Promise((resolve, reject) => {
3612
3612
  const langLoadErrorSgmCode = `languageLoadError_${fileName || 'lang.json'}`;
3613
3613
  try {
3614
3614
  const langXhrRequest = new XMLHttpRequest();
3615
3615
  langXhrRequest.timeout = timeout || 2000;
3616
3616
  langXhrRequest.open('GET', getUrl, true);
3617
3617
  langXhrRequest.responseType = 'json';
3618
3618
  langXhrRequest.onreadystatechange = () => {
3619
3619
  if (langXhrRequest.readyState === 4) {
3620
3620
  const getReqStatus = langXhrRequest.status;
3621
3621
  const statusText = langXhrRequest.statusText;
3622
3622
  if ((getReqStatus >= 200 && getReqStatus < 300) || getReqStatus === 304) {
3623
3623
  const getData = langXhrRequest?.response || false;
3624
3624
  if (getData) {
3625
3625
  setTaroStorage(`jshopx_lang_${languageTypeKey}`, {
3626
3626
  fileName,
3627
3627
  data: getData,
3628
3628
  });
3629
3629
  resolve({
3630
3630
  ...info,
3631
3631
  languageTypeKey,
3632
3632
  data: getData,
3633
3633
  });
3634
3634
  } else {
3635
3635
  reject({
3636
3636
  ...info,
3637
3637
  languageTypeKey,
3638
3638
  msg: '数据获取异常',
3639
3639
  });
3640
3640
  }
3641
3641
  } else {
3642
3642
  const getRes = {
3643
3643
  ...info,
3644
3644
  languageTypeKey,
3645
3645
  env: getSgmCustomCode(langLoadErrorSgmCode),
3646
3646
  msg: `请求状态异常,状态码为${getReqStatus},statusText:${statusText}`,
3647
3647
  };
3648
3648
  console.log('当前lang请求状态异常,具体信息见', getRes);
3649
3649
  reject(getRes);
3650
3650
  }
3651
3651
  }
3652
3652
  };
3653
3653
  langXhrRequest.onerror = () => {
3654
3654
  const getRes = {
3655
3655
  ...info,
3656
3656
  env: getSgmCustomCode(langLoadErrorSgmCode),
3657
3657
  msg: '请求错误',
3658
3658
  };
3659
3659
  console.log('当前lang请求错误', getRes);
3660
3660
  langXhrRequest.abort();
3661
3661
  reject(getRes);
3662
3662
  };
3663
3663
  langXhrRequest.ontimeout = () => {
3664
3664
  const getRes = {
3665
3665
  ...info,
3666
3666
  msg: `请求${langXhrRequest.timeout}ms超时异常,状态${langXhrRequest.status}`,
3667
3667
  };
3668
3668
  console.log('执行lang多语言请求超时异常', getRes);
3669
3669
  langXhrRequest.abort();
3670
3670
  reject(getRes);
3671
3671
  };
3672
3672
  langXhrRequest.send();
3673
3673
  } catch (e) {
3674
3674
  console.log('执行lang多语言请求异常', e);
3675
3675
  reject({
3676
3676
  ...info,
3677
3677
  env: getSgmCustomCode(langLoadErrorSgmCode),
3678
3678
  msg: '未知异常',
3679
3679
  error: e,
3680
3680
  });
3681
3681
  }
3682
3682
  });
3683
3683
  }