@lark-apaas/client-toolkit 1.2.15 → 1.2.17-alpha.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (59) hide show
  1. package/lib/components/AppContainer/IframeBridge.d.ts +1 -0
  2. package/lib/components/AppContainer/IframeBridge.js +20 -1
  3. package/lib/components/AppContainer/api-proxy/core.js +1 -2
  4. package/lib/components/AppContainer/index.d.ts +2 -5
  5. package/lib/components/AppContainer/index.js +46 -9
  6. package/lib/components/AppContainer/utils/childApi.js +0 -1
  7. package/lib/components/AppContainer/utils/listenHot.d.ts +1 -0
  8. package/lib/components/AppContainer/utils/listenHot.js +57 -0
  9. package/lib/components/AppContainer/utils/tea.js +1 -1
  10. package/lib/components/ErrorRender/index.js +11 -5
  11. package/lib/components/User/UserSelect.js +13 -1
  12. package/lib/hooks/index.d.ts +0 -1
  13. package/lib/hooks/index.js +0 -1
  14. package/lib/index.js +1 -5
  15. package/lib/integrations/dataloom.js +2 -4
  16. package/lib/logger/batch-logger.js +2 -3
  17. package/lib/logger/intercept-global-error.js +14 -16
  18. package/lib/logger/log-types.d.ts +4 -4
  19. package/lib/logger/log-types.js +1 -1
  20. package/lib/logger/selected-logs.js +2 -1
  21. package/lib/theme-layer.css +1 -2
  22. package/lib/utils/axiosConfig.js +3 -25
  23. package/lib/utils/getParentOrigin.js +2 -12
  24. package/lib/utils/module-hot.d.ts +5 -9
  25. package/lib/utils/module-hot.js +10 -9
  26. package/lib/utils/requestManager.js +3 -1
  27. package/package.json +11 -5
  28. package/lib/apis/components/ActiveLink.d.ts +0 -26
  29. package/lib/apis/components/ActiveLink.js +0 -66
  30. package/lib/apis/hooks/useScrollReveal.d.ts +0 -1
  31. package/lib/apis/hooks/useScrollReveal.js +0 -1
  32. package/lib/apis/utils/getEnv.d.ts +0 -1
  33. package/lib/apis/utils/getEnv.js +0 -2
  34. package/lib/apis/utils/scopedStorage.d.ts +0 -1
  35. package/lib/apis/utils/scopedStorage.js +0 -2
  36. package/lib/auth.d.ts +0 -1
  37. package/lib/auth.js +0 -2
  38. package/lib/components/ui/toast.d.ts +0 -2
  39. package/lib/components/ui/toast.js +0 -53
  40. package/lib/hooks/useScrollReveal.d.ts +0 -61
  41. package/lib/hooks/useScrollReveal.js +0 -37
  42. package/lib/runtime/axios.d.ts +0 -5
  43. package/lib/runtime/axios.js +0 -2
  44. package/lib/runtime/dayjs.d.ts +0 -5
  45. package/lib/runtime/dayjs.js +0 -2
  46. package/lib/runtime/iframe-bridge.d.ts +0 -11
  47. package/lib/runtime/iframe-bridge.js +0 -29
  48. package/lib/runtime/index.d.ts +0 -23
  49. package/lib/runtime/index.js +0 -16
  50. package/lib/runtime/observable.d.ts +0 -5
  51. package/lib/runtime/observable.js +0 -2
  52. package/lib/runtime/server-log.d.ts +0 -5
  53. package/lib/runtime/server-log.js +0 -41
  54. package/lib/runtime/styles.d.ts +0 -5
  55. package/lib/runtime/styles.js +0 -1
  56. package/lib/utils/hmr-api.d.ts +0 -39
  57. package/lib/utils/hmr-api.js +0 -36
  58. package/lib/utils/scopedStorage.d.ts +0 -5
  59. package/lib/utils/scopedStorage.js +0 -46
@@ -1,2 +1,3 @@
1
1
  import React from 'react';
2
+ import './utils/listenHot';
2
3
  export default function IframeBridge(): React.JSX.Element;
@@ -1,8 +1,11 @@
1
1
  import { jsx } from "react/jsx-runtime";
2
2
  import { useCallback, useEffect, useMemo, useRef } from "react";
3
3
  import { useLocation, useNavigate } from "react-router-dom";
4
+ import { connectToParent } from "penpal";
4
5
  import { useUpdatingRef } from "../../hooks/useUpdatingRef.js";
5
- import { submitPostMessage } from "../../utils/postMessage.js";
6
+ import { resolveParentOrigin, submitPostMessage } from "../../utils/postMessage.js";
7
+ import { childApi } from "./utils/childApi.js";
8
+ import "./utils/listenHot.js";
6
9
  var IframeBridge_RouteMessageType = /*#__PURE__*/ function(RouteMessageType) {
7
10
  RouteMessageType["RouteChange"] = "RouteChange";
8
11
  RouteMessageType["RouteBack"] = "RouteBack";
@@ -12,6 +15,22 @@ var IframeBridge_RouteMessageType = /*#__PURE__*/ function(RouteMessageType) {
12
15
  function isRouteMessageType(type) {
13
16
  return Object.values(IframeBridge_RouteMessageType).includes(type);
14
17
  }
18
+ async function connectParent() {
19
+ submitPostMessage({
20
+ type: 'PreviewReady',
21
+ data: {}
22
+ });
23
+ const parentOrigin = resolveParentOrigin();
24
+ if (!parentOrigin) return;
25
+ const connection = connectToParent({
26
+ parentOrigin,
27
+ methods: {
28
+ ...childApi
29
+ }
30
+ });
31
+ await connection.promise;
32
+ }
33
+ 'production' !== process.env.NODE_ENV && connectParent();
15
34
  function IframeBridge() {
16
35
  const location = useLocation();
17
36
  const navigate = useNavigate();
@@ -139,8 +139,7 @@ class ApiProxy {
139
139
  ...config,
140
140
  headers: {
141
141
  ...this.defaultConfig.headers,
142
- ...config.headers,
143
- 'X-Page-Route': 'undefined' != typeof window ? window.location?.pathname || '/' : '/'
142
+ ...config.headers
144
143
  }
145
144
  };
146
145
  const requestKey = this.generateRequestKey(mergedConfig);
@@ -1,10 +1,7 @@
1
1
  import React from 'react';
2
2
  import { IBaseThemeProviderProps } from '../theme';
3
- import '../../runtime';
4
- interface IBaseAuthProviderProps {
5
- enableAuth?: boolean;
6
- }
3
+ import '../../index.css';
7
4
  declare const AppContainer: React.FC<{
8
5
  children: React.ReactNode;
9
- } & IBaseThemeProviderProps & IBaseAuthProviderProps>;
6
+ } & IBaseThemeProviderProps>;
10
7
  export default AppContainer;
@@ -1,5 +1,5 @@
1
1
  import { Fragment, jsx, jsxs } from "react/jsx-runtime";
2
- import { useEffect, useState } from "react";
2
+ import { useEffect, useRef, useState } from "react";
3
3
  import { ConfigProvider } from "antd";
4
4
  import { MiaodaInspector } from "@lark-apaas/miaoda-inspector";
5
5
  import zh_CN from "antd/locale/zh_CN";
@@ -8,14 +8,20 @@ import { defaultUIConfig } from "../theme/ui-config.js";
8
8
  import { Toaster } from "./sonner.js";
9
9
  import { PageHoc } from "./PageHoc.js";
10
10
  import { findValueByPixel, generateTailwindRadiusToken, themeColorTokenMap, themeMetaOptions } from "../theme/index.js";
11
+ import { registerDayjsPlugins } from "./dayjsPlugins.js";
12
+ import "../../index.css";
13
+ import { initAxiosConfig } from "../../utils/axiosConfig.js";
11
14
  import { reportTeaEvent } from "./utils/tea.js";
12
15
  import { useAppInfo } from "../../hooks/index.js";
13
16
  import { TrackKey } from "../../types/tea.js";
14
17
  import safety from "./safety.js";
15
18
  import { getAppId } from "../../utils/getAppId.js";
19
+ import { ServerLogSSEClient } from "../../server-log/index.js";
16
20
  import QueryProvider from "../QueryProvider/index.js";
17
- import { AuthProvider } from "@lark-apaas/auth-sdk";
18
- import "../../runtime/index.js";
21
+ import { initObservable } from "./utils/observable.js";
22
+ registerDayjsPlugins();
23
+ initAxiosConfig();
24
+ initObservable();
19
25
  const isMiaodaPreview = window.IS_MIAODA_PREVIEW;
20
26
  const readCssVarColor = (varName, fallback)=>{
21
27
  try {
@@ -27,8 +33,9 @@ const readCssVarColor = (varName, fallback)=>{
27
33
  }
28
34
  };
29
35
  const App = (props)=>{
30
- const { themeMeta = {}, enableAuth } = props;
36
+ const { themeMeta = {} } = props;
31
37
  useAppInfo();
38
+ const serverLogClientRef = useRef(null);
32
39
  const { rem } = findValueByPixel(themeMetaOptions.themeRadius, themeMeta.borderRadius) || {
33
40
  rem: '0.625'
34
41
  };
@@ -40,6 +47,40 @@ const App = (props)=>{
40
47
  borderRadius: radiusToken
41
48
  }
42
49
  };
50
+ useEffect(()=>{
51
+ if ('production' !== process.env.NODE_ENV && window.parent !== window) {
52
+ try {
53
+ const backendUrl = window.location.origin;
54
+ serverLogClientRef.current = new ServerLogSSEClient({
55
+ serverUrl: backendUrl,
56
+ sseEndpoint: '/dev/logs/server-logs/stream',
57
+ debug: true
58
+ });
59
+ serverLogClientRef.current.start();
60
+ console.log('[AppContainer] Server log SSE client started');
61
+ } catch (error) {
62
+ console.error('[AppContainer] Failed to start server log SSE client:', error);
63
+ }
64
+ const handleVisibilityChange = ()=>{
65
+ if (!serverLogClientRef.current) return;
66
+ if (document.hidden) {
67
+ serverLogClientRef.current.pause();
68
+ console.log('[AppContainer] Tab hidden, SSE paused');
69
+ } else {
70
+ serverLogClientRef.current.resume();
71
+ console.log('[AppContainer] Tab visible, SSE resumed');
72
+ }
73
+ };
74
+ document.addEventListener('visibilitychange', handleVisibilityChange);
75
+ return ()=>{
76
+ document.removeEventListener('visibilitychange', handleVisibilityChange);
77
+ if (serverLogClientRef.current) {
78
+ serverLogClientRef.current.stop();
79
+ console.log('[AppContainer] Server log SSE client stopped');
80
+ }
81
+ };
82
+ }
83
+ }, []);
43
84
  useEffect(()=>{
44
85
  if (isMiaodaPreview) fetch(`${location.origin}/ai/api/feida_preview/csrf`).then(()=>{
45
86
  setTimeout(()=>{
@@ -58,10 +99,7 @@ const App = (props)=>{
58
99
  }
59
100
  });
60
101
  }, []);
61
- return /*#__PURE__*/ jsxs(AuthProvider, {
62
- config: {
63
- enable: enableAuth
64
- },
102
+ return /*#__PURE__*/ jsxs(Fragment, {
65
103
  children: [
66
104
  /*#__PURE__*/ jsx(Toaster, {}),
67
105
  'production' !== process.env.NODE_ENV && /*#__PURE__*/ jsx(MiaodaInspector, {
@@ -209,7 +247,6 @@ const AppContainer_AppContainer = (props)=>{
209
247
  },
210
248
  children: /*#__PURE__*/ jsx(App, {
211
249
  themeMeta: props.themeMeta,
212
- enableAuth: props.enableAuth,
213
250
  children: children
214
251
  })
215
252
  })
@@ -16,7 +16,6 @@ async function getRoutes() {
16
16
  return routes;
17
17
  }
18
18
  async function getSourceMap() {
19
- if ('vite' === process.env.BUILD_TOOL) return '';
20
19
  let sourceMapContent = '';
21
20
  try {
22
21
  const basePath = normalizeBasePath(process.env.CLIENT_BASE_PATH);
@@ -0,0 +1 @@
1
+ export declare function connectDevServer(): WebSocket;
@@ -0,0 +1,57 @@
1
+ import sockjs_client from "sockjs-client";
2
+ import { submitPostMessage, submitSlardarEvent } from "../../../utils/postMessage.js";
3
+ import { getWsPath } from "../../../utils/utils.js";
4
+ let hotInited = false;
5
+ function handleDevServerMessage(msg) {
6
+ if ('hash' === msg.type) {
7
+ if (!hotInited) {
8
+ hotInited = true;
9
+ return;
10
+ }
11
+ submitPostMessage({
12
+ type: 'HmrMessage',
13
+ msg: {
14
+ type: 'hot'
15
+ },
16
+ data: null
17
+ });
18
+ } else if ('errors' === msg.type) submitPostMessage({
19
+ type: 'HmrMessage',
20
+ msg: {
21
+ type: 'errors',
22
+ data: JSON.stringify(msg.data)
23
+ },
24
+ data: null
25
+ });
26
+ else if ('hmr-timing' === msg.type) {
27
+ const { duration, fileCount, fileTotalSize } = msg.data;
28
+ submitSlardarEvent({
29
+ name: 'runTiming',
30
+ metrics: {
31
+ duration
32
+ },
33
+ categories: {
34
+ type: 'sandbox-hmr-timing',
35
+ fileCount,
36
+ fileTotalSize
37
+ }
38
+ });
39
+ }
40
+ }
41
+ function connectDevServer() {
42
+ const sockUrl = getWsPath();
43
+ const sock = new sockjs_client(sockUrl);
44
+ sock.onopen = ()=>console.log('✅ connect DevServer SockJS');
45
+ sock.onmessage = (event)=>{
46
+ try {
47
+ const msg = JSON.parse(event.data);
48
+ console.log('hmr 消息:', msg);
49
+ handleDevServerMessage(msg);
50
+ } catch (err) {
51
+ console.error('解析 hmr 消息失败:', event.data);
52
+ }
53
+ };
54
+ return sock;
55
+ }
56
+ 'production' !== process.env.NODE_ENV && connectDevServer();
57
+ export { connectDevServer };
@@ -16,7 +16,7 @@ async function createTracker() {
16
16
  const userIDEncrypt = userID && '0' !== userID ? encryptTea(userID) : void 0;
17
17
  const tenantIDEncrypt = tenantID && '0' !== tenantID ? encryptTea(tenantID) : void 0;
18
18
  window.collectEvent('init', {
19
- app_id: 788827,
19
+ app_id: 672575,
20
20
  channel: 'cn',
21
21
  disable_auto_pv: false,
22
22
  enable_ab_test: false,
@@ -1,7 +1,7 @@
1
1
  import { jsx, jsxs } from "react/jsx-runtime";
2
2
  import { useEffect } from "react";
3
3
  import { logger } from "../../logger/index.js";
4
- import { getHmrApi } from "../../utils/hmr-api.js";
4
+ import { createApplyHandle, getModuleHot } from "../../utils/module-hot.js";
5
5
  import { submitPostMessage } from "../../utils/postMessage.js";
6
6
  const RenderError = (props)=>{
7
7
  const { error, resetErrorBoundary } = props;
@@ -27,10 +27,16 @@ const RenderError = (props)=>{
27
27
  ]);
28
28
  useEffect(()=>{
29
29
  if (!resetErrorBoundary) return;
30
- const hmr = getHmrApi();
31
- if (hmr) return hmr.onSuccess(()=>{
32
- resetErrorBoundary();
33
- });
30
+ const hot = getModuleHot();
31
+ if (hot) {
32
+ const handler = createApplyHandle((success)=>{
33
+ if (success) resetErrorBoundary();
34
+ });
35
+ hot.addStatusHandler(handler);
36
+ return ()=>{
37
+ hot.removeStatusHandler(handler);
38
+ };
39
+ }
34
40
  }, [
35
41
  resetErrorBoundary
36
42
  ]);
@@ -67,8 +67,20 @@ const UserSelect = ({ mode = 'single', defaultValue, value, onChange, placeholde
67
67
  if (!normalizedIds.length) return void setUiValue(void 0);
68
68
  const fetchProfiles = async ()=>{
69
69
  try {
70
+ const ids = normalizedIds.map((id)=>Number(id)).filter((id)=>Number.isFinite(id));
71
+ if (!ids.length) {
72
+ const profiles = normalizedIds.map((id)=>inputProfilesMap.get(id) ?? {
73
+ user_id: id,
74
+ name: '',
75
+ avatar: '',
76
+ email: '',
77
+ status: 1
78
+ });
79
+ setUiValue('single' === mode ? profiles[0] : profiles);
80
+ return;
81
+ }
70
82
  const dataloom = await getDataloom();
71
- const response = await dataloom.service.user.getByIds(normalizedIds);
83
+ const response = await dataloom.service.user.getByIds(ids);
72
84
  const fetchedList = Array.isArray(response?.data) ? response?.data : Array.isArray(response?.data?.user_list) ? response?.data?.user_list : [];
73
85
  const fetchedMap = new Map();
74
86
  fetchedList.forEach((profile)=>{
@@ -2,4 +2,3 @@ export * from './useAppInfo';
2
2
  export * from './useCurrentUserProfile';
3
3
  export * from './useIsMobile';
4
4
  export * from './useLogout';
5
- export * from './useScrollReveal';
@@ -2,4 +2,3 @@ export * from "./useAppInfo.js";
2
2
  export * from "./useCurrentUserProfile.js";
3
3
  export * from "./useIsMobile.js";
4
4
  export * from "./useLogout.js";
5
- export * from "./useScrollReveal.js";
package/lib/index.js CHANGED
@@ -1,7 +1,6 @@
1
1
  import { createClient } from "@lark-apaas/client-capability";
2
2
  import { normalizeBasePath } from "./utils/utils.js";
3
3
  import { logger } from "./logger/index.js";
4
- import { showToast } from "./components/ui/toast.js";
5
4
  import { version } from "../package.json";
6
5
  const capabilityClient = createClient({
7
6
  baseURL: normalizeBasePath(process.env.CLIENT_BASE_PATH),
@@ -10,10 +9,7 @@ const capabilityClient = createClient({
10
9
  'X-Suda-Csrf-Token': window.csrfToken ?? ''
11
10
  }
12
11
  },
13
- logger: logger,
14
- onRateLimitError: ()=>{
15
- showToast('应用额度已耗尽,请联系应用开发者');
16
- }
12
+ logger: logger
17
13
  });
18
14
  const src = {
19
15
  version: version
@@ -3,10 +3,8 @@ import { createClient } from "@data-loom/js";
3
3
  import { getAppId } from "../utils/getAppId.js";
4
4
  import { getInitialInfo } from "../utils/getInitialInfo.js";
5
5
  const createDataLoomClient = (url, pat)=>{
6
- const { baseUrl, workspace } = url ? splitWorkspaceUrl(url) : {
7
- baseUrl: '',
8
- workspace: ''
9
- };
6
+ if (!url) return null;
7
+ const { baseUrl, workspace } = splitWorkspaceUrl(url);
10
8
  const appId = getAppId(window.location.pathname);
11
9
  return createClient(baseUrl, pat, workspace, {
12
10
  global: {
@@ -4,9 +4,9 @@ class BatchLogger {
4
4
  flushTimer = null;
5
5
  isProcessing = false;
6
6
  originConsole;
7
- constructor(console1, config){
7
+ constructor(console, config){
8
8
  this.originConsole = {
9
- ...console1
9
+ ...console
10
10
  };
11
11
  const { userId = '', tenantId = '', appId = '' } = window || {};
12
12
  this.config = {
@@ -131,5 +131,4 @@ function destroyBatchLogger() {
131
131
  defaultBatchLogger = null;
132
132
  }
133
133
  }
134
- if ('production' !== process.env.NODE_ENV && 'undefined' != typeof window) defaultBatchLogger = new BatchLogger(console);
135
134
  export { BatchLogger, batchLogInfo, destroyBatchLogger, getBatchLogger, initBatchLogger };
@@ -1,4 +1,4 @@
1
- import { getHmrApi } from "../utils/hmr-api.js";
1
+ import { createApplyHandle, getModuleHot } from "../utils/module-hot.js";
2
2
  import { submitPostMessage, submitSlardarEvent } from "../utils/postMessage.js";
3
3
  import { levelSchema } from "./log-types.js";
4
4
  import { logger } from "./logger.js";
@@ -63,28 +63,26 @@ function processDevServerLog(log) {
63
63
  }
64
64
  }
65
65
  function listenModuleHmr() {
66
- const hmr = getHmrApi();
67
- if (hmr) {
68
- hmr.onSuccess(()=>{
69
- submitPostMessage({
70
- type: 'DevServerMessage',
71
- data: {
72
- type: 'devServer-status',
73
- status: 'hmr-apply-success'
74
- }
75
- });
66
+ const hot = getModuleHot();
67
+ if (hot) hot.addStatusHandler(createApplyHandle((success, status)=>{
68
+ if (success) submitPostMessage({
69
+ type: 'DevServerMessage',
70
+ data: {
71
+ type: 'devServer-status',
72
+ status: 'hmr-apply-success'
73
+ }
76
74
  });
77
- hmr.onError((error)=>{
78
- console.warn('hmr apply failed', error);
75
+ else {
76
+ console.warn('hmr apply failed', status);
79
77
  submitSlardarEvent({
80
78
  name: 'sandbox-devServer',
81
79
  categories: {
82
80
  type: 'hmr-apply-failed',
83
- error: String(error)
81
+ status
84
82
  }
85
83
  });
86
- });
87
- }
84
+ }
85
+ }));
88
86
  }
89
87
  function interceptErrors() {
90
88
  window.addEventListener('error', (event)=>{
@@ -1,7 +1,7 @@
1
1
  import z from 'zod';
2
2
  export declare const networkRequestLogSchema: z.ZodObject<{
3
3
  method: z.ZodString;
4
- status: z.ZodNumber;
4
+ status: z.ZodInt;
5
5
  statusText: z.ZodString;
6
6
  path: z.ZodString;
7
7
  requestData: z.ZodOptional<z.ZodUnknown>;
@@ -27,11 +27,11 @@ export declare const logStackFrameSchema: z.ZodObject<{
27
27
  columnNumber: z.ZodNumber;
28
28
  }, z.core.$strip>;
29
29
  export declare const levelSchema: z.ZodEnum<{
30
- error: "error";
31
30
  success: "success";
32
31
  debug: "debug";
33
32
  info: "info";
34
33
  warn: "warn";
34
+ error: "error";
35
35
  }>;
36
36
  export declare const logMeta: z.ZodObject<{
37
37
  stacktrace: z.ZodOptional<z.ZodArray<z.ZodObject<{
@@ -52,11 +52,11 @@ export declare const logMeta: z.ZodObject<{
52
52
  export declare const selectedLogSchema: z.ZodObject<{
53
53
  type: z.ZodLiteral<"typedLogV2">;
54
54
  level: z.ZodEnum<{
55
- error: "error";
56
55
  success: "success";
57
56
  debug: "debug";
58
57
  info: "info";
59
58
  warn: "warn";
59
+ error: "error";
60
60
  }>;
61
61
  id: z.ZodString;
62
62
  args: z.ZodArray<z.ZodUnknown>;
@@ -80,11 +80,11 @@ export declare const selectedLogSchema: z.ZodObject<{
80
80
  export type LogLevel = z.infer<typeof levelSchema>;
81
81
  export declare const logWithMetaSchema: z.ZodObject<{
82
82
  level: z.ZodEnum<{
83
- error: "error";
84
83
  success: "success";
85
84
  debug: "debug";
86
85
  info: "info";
87
86
  warn: "warn";
87
+ error: "error";
88
88
  }>;
89
89
  args: z.ZodArray<z.ZodUnknown>;
90
90
  meta: z.ZodOptional<z.ZodObject<{
@@ -1,7 +1,7 @@
1
1
  import zod from "zod";
2
2
  const networkRequestLogSchema = zod.object({
3
3
  method: zod.string(),
4
- status: zod.number().int(),
4
+ status: zod.int(),
5
5
  statusText: zod.string(),
6
6
  path: zod.string(),
7
7
  requestData: zod.optional(zod.unknown()),
@@ -2,7 +2,7 @@ import { SourceMapConsumer as external_source_map_SourceMapConsumer } from "sour
2
2
  import "../utils/utils.js";
3
3
  import { mappingText } from "./source-map-mappings-wasm.js";
4
4
  import stacktrace_js from "stacktrace-js";
5
- import { batchLogInfo } from "./batch-logger.js";
5
+ import { batchLogInfo, initBatchLogger } from "./batch-logger.js";
6
6
  function hexToBuffer(hexString) {
7
7
  const hex = hexString.replace(/\s/g, '').toUpperCase();
8
8
  if (!/^[0-9A-F]+$/.test(hex)) throw new Error('Invalid hex string');
@@ -213,6 +213,7 @@ const typedLogInterceptor = (logger)=>({
213
213
  });
214
214
  }
215
215
  });
216
+ 'production' !== process.env.NODE_ENV && initBatchLogger(console);
216
217
  const interceptors = 'production' !== process.env.NODE_ENV ? [
217
218
  typedLogInterceptor
218
219
  ] : [];
@@ -1,4 +1,3 @@
1
1
  @layer theme, base, antd, components, utilities;
2
- @import 'tailwindcss' source(none);
3
- @source "../**/*.{js,jsx,ts,tsx}";
2
+ @import "tailwindcss";
4
3
 
@@ -54,7 +54,7 @@ async function logResponse(ok, responseOrError) {
54
54
  logTraceID
55
55
  };
56
56
  if (stacktrace) logMeta.stacktrace = stacktrace;
57
- logger.log({
57
+ logger.debug({
58
58
  level: ok,
59
59
  args: [
60
60
  parts.join(''),
@@ -110,7 +110,7 @@ async function logResponse(ok, responseOrError) {
110
110
  const stacktrace = await requestStacktraceMap.get(requestUUID);
111
111
  const logMeta = {};
112
112
  if (stacktrace) logMeta.stacktrace = stacktrace;
113
- logger.log({
113
+ logger.debug({
114
114
  level: 'error',
115
115
  args: [
116
116
  parts.join(''),
@@ -120,7 +120,7 @@ async function logResponse(ok, responseOrError) {
120
120
  });
121
121
  return;
122
122
  }
123
- logger.log({
123
+ logger.debug({
124
124
  level: 'error',
125
125
  args: [
126
126
  '请求失败:无响应对象或配置信息'
@@ -234,30 +234,8 @@ function initAxiosConfig(axiosInstance) {
234
234
  config._startTime = config._startTime || Date.now();
235
235
  const csrfToken = window.csrfToken;
236
236
  if (csrfToken) config.headers['X-Suda-Csrf-Token'] = csrfToken;
237
- if ('undefined' != typeof window && window.location?.pathname) config.headers['X-Page-Route'] = window.location.pathname;
238
237
  return config;
239
238
  }, (error)=>Promise.reject(error));
240
- instance.interceptors.response.use((response)=>response, (error)=>{
241
- try {
242
- if (error.response?.status === 403) {
243
- const method = (error.config?.method || 'GET').toUpperCase();
244
- const url = (error.config?.url || '').split('?')[0];
245
- logger.log({
246
- level: 'warn',
247
- args: [
248
- `请求被拒绝(403):${method} ${url}`,
249
- {
250
- 状态码: 403,
251
- 返回数据: error.response.data
252
- }
253
- ],
254
- meta: {}
255
- });
256
- return error.response;
257
- }
258
- } catch (e) {}
259
- return Promise.reject(error);
260
- });
261
239
  'production' !== process.env.NODE_ENV && instance.interceptors.response.use((response)=>{
262
240
  logResponse('success', response);
263
241
  return response;
@@ -1,17 +1,7 @@
1
1
  function getEnv() {
2
- switch(globalThis.ENVIRONMENT){
3
- case 'staging':
4
- return 'BOE';
5
- case 'gray':
6
- return 'PRE';
7
- case 'online':
8
- return 'ONLINE';
9
- default:
10
- break;
11
- }
12
2
  const { origin } = window.location;
13
- if (origin.includes('feishuapp.cn') || origin.includes('miaoda.feishuapp.net') || origin.includes('aiforce.cloud') || origin.includes('aiforce.run')) return 'ONLINE';
14
- if (origin.includes('fsapp.kundou.cn') || origin.includes('miaoda-pre.feishuapp.net') || origin.includes('aiforce-pre.bytedance.net') || origin.includes('aiforce-pre-preview.bytedance.net') || origin.includes('aiforce-pre.cloud') || origin.includes('aiforce-pre.run')) return 'PRE';
3
+ if (origin.includes('feishuapp.cn') || origin.includes('miaoda.feishuapp.net')) return 'ONLINE';
4
+ if (origin.includes('fsapp.kundou.cn') || origin.includes('miaoda-pre.feishuapp.net')) return 'PRE';
15
5
  return 'BOE';
16
6
  }
17
7
  export { getEnv };
@@ -10,20 +10,16 @@
10
10
  * - abort: An update was aborted, but the system is still in its previous state
11
11
  * - fail: An update has thrown an exception and the system's state has been compromised
12
12
  */
13
- export type ModuleHotType = 'idle' | 'check' | 'prepare' | 'ready' | 'dispose' | 'apply' | 'abort' | 'fail';
14
- export interface ModuleHotInstance {
13
+ type ModuleHotType = 'idle' | 'check' | 'prepare' | 'ready' | 'dispose' | 'apply' | 'abort' | 'fail';
14
+ interface ModuleHotInstance {
15
15
  addStatusHandler: (handler: (status: ModuleHotType) => void) => void;
16
16
  removeStatusHandler: (handler: (status: ModuleHotType) => void) => void;
17
17
  }
18
- /**
19
- * 获取 Webpack HMR 实例
20
- * 仅支持 Webpack/Rspack 的 HMR API
21
- */
22
18
  export declare function getModuleHot(): ModuleHotInstance | null;
23
19
  /**
24
20
  * 创建模块热更成功处理函数
25
- * 监听模块热更状态,检测 apply -> idle 转换表示热更成功
26
- *
27
- * @param callback 热更回调函数,参数为是否成功和当前状态
21
+ * 监听模块热更状态,当状态为apply时,调用回调函数并传入true
22
+ * @param callback 热更成功回调函数,参数为是否成功
28
23
  */
29
24
  export declare function createApplyHandle(callback: (success: boolean, status: ModuleHotType) => void): (status: ModuleHotType) => void;
25
+ export {};
@@ -1,21 +1,22 @@
1
1
  function getModuleHot() {
2
2
  if ('production' === process.env.NODE_ENV) return null;
3
- if (import.meta.webpackHot) return import.meta.webpackHot;
4
- 'undefined' != typeof module && module.hot;
5
- return null;
3
+ return import.meta.webpackHot || module.hot;
6
4
  }
7
5
  function createApplyHandle(callback) {
8
- let lastStatus = null;
6
+ let hasApply = false;
9
7
  return (status)=>{
10
8
  if ('fail' === status || 'abort' === status) {
11
- lastStatus = status;
9
+ hasApply = false;
12
10
  return callback(false, status);
13
11
  }
14
- if ('idle' === status && 'apply' === lastStatus) {
15
- lastStatus = status;
16
- return callback(true, status);
12
+ if (hasApply) {
13
+ if ('idle' === status) {
14
+ hasApply = false;
15
+ callback(true, status);
16
+ }
17
+ return;
17
18
  }
18
- lastStatus = status;
19
+ hasApply = 'apply' === status;
19
20
  };
20
21
  }
21
22
  export { createApplyHandle, getModuleHot };
@@ -4,7 +4,9 @@ async function fetchUserProfilesByIds(ids) {
4
4
  try {
5
5
  const dataloom = await getDataloom();
6
6
  if (!dataloom) throw new Error('Dataloom client is unavailable');
7
- const response = await dataloom.service.user.getByIds(ids);
7
+ const numericIds = ids.map(Number).filter(Number.isFinite);
8
+ if (0 === numericIds.length) return [];
9
+ const response = await dataloom.service.user.getByIds(numericIds);
8
10
  return Array.isArray(response?.data) ? response.data : response?.data?.user_list || [];
9
11
  } catch (error) {
10
12
  console.error(`Failed to fetch profiles for user IDs ${ids.join(', ')}:`, error);