cclawd 1.0.0 → 1.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (111) hide show
  1. package/dist/{active-listener-DYmI7imH.js → active-listener-BLd27Pxd.js} +2 -2
  2. package/dist/{api-key-rotation-DLU4jvSu.js → api-key-rotation-Dg3JlNDQ.js} +1 -1
  3. package/dist/{audio-preflight-C9TMbRb4.js → audio-preflight-eV5m9mMp.js} +15 -15
  4. package/dist/{audio-transcription-runner-Q5zG_hYd.js → audio-transcription-runner-CQU4Eg1M.js} +10 -10
  5. package/dist/{audit-membership-runtime-DhxSwFnF.js → audit-membership-runtime-hXUuer4x.js} +6 -6
  6. package/dist/build-info.json +3 -3
  7. package/dist/bundled/boot-md/handler.js +35 -35
  8. package/dist/bundled/bootstrap-extra-files/handler.js +5 -5
  9. package/dist/bundled/command-logger/handler.js +2 -2
  10. package/dist/bundled/session-memory/handler.js +35 -35
  11. package/dist/{channel-activity-Bx08UTAg.js → channel-activity-dT3cYb0e.js} +2 -2
  12. package/dist/{commands-registry-llLVCTH9.js → commands-registry-CyLMCPuP.js} +2 -2
  13. package/dist/compact.runtime-DGRl4st4.js +39 -0
  14. package/dist/{deliver-DJf2ZBpe.js → deliver-B6eTtXSk.js} +19 -19
  15. package/dist/deliver-runtime-CLDpY6AW.js +19 -0
  16. package/dist/deps-send-discord.runtime-CxADlame.js +19 -0
  17. package/dist/deps-send-imessage.runtime-Wi79xm6H.js +18 -0
  18. package/dist/deps-send-signal.runtime-BDtzvsnR.js +17 -0
  19. package/dist/deps-send-slack.runtime-CgX24hgT.js +17 -0
  20. package/dist/deps-send-telegram.runtime-CEWc7ePn.js +20 -0
  21. package/dist/deps-send-whatsapp.runtime-B1KJ7YOp.js +43 -0
  22. package/dist/{diagnostic-BCCMF3O_.js → diagnostic-BZmAxdu9.js} +2 -2
  23. package/dist/{env-aYXLHjfZ.js → env-lw2hsIUY.js} +1 -1
  24. package/dist/{fetch-bvgIiupu.js → fetch-C0iyt-Iz.js} +3 -3
  25. package/dist/{fetch-DCTUdr1U.js → fetch-CMLoICyN.js} +5 -5
  26. package/dist/{fetch-guard-CqpEmMQ2.js → fetch-guard-DCj3k042.js} +2 -2
  27. package/dist/{frontmatter-DjZuS525.js → frontmatter-C_obXuTp.js} +3 -3
  28. package/dist/{github-copilot-token-CQmATy5E.js → github-copilot-token-8N63GdbE.js} +7 -7
  29. package/dist/{image-Q8E1-lZn.js → image-Bt49ybRv.js} +4 -4
  30. package/dist/image-runtime-Cilhq73U.js +12 -0
  31. package/dist/{ir-CzM3SxId.js → ir-CVtBjUiL.js} +6 -6
  32. package/dist/llm-slug-generator.js +35 -35
  33. package/dist/{logger-ChbX1G7s.js → logger-CbUVl62f.js} +7 -7
  34. package/dist/{login-B0mtU11X.js → login-D0fUoX-p.js} +4 -4
  35. package/dist/{login-qr-DY_i60f5.js → login-qr-ClBxstxZ.js} +10 -10
  36. package/dist/{manager-FAQPC0uO.js → manager-DSfEj66R.js} +12 -12
  37. package/dist/manager-runtime-BrZlGJsj.js +15 -0
  38. package/dist/{model-selection-wf3OY5DX.js → model-selection-CMEj8bpy.js} +130 -130
  39. package/dist/{outbound-Bw0dOVS7.js → outbound-BxIJyMzV.js} +6 -6
  40. package/dist/{outbound-attachment-1R6r9Pg_.js → outbound-attachment-CVJwpypG.js} +2 -2
  41. package/dist/{paths-C0HLtPu0.js → paths-CehYKFsO.js} +7 -7
  42. package/dist/{paths-hfkBoC7i.js → paths-DkxwiA8g.js} +5 -5
  43. package/dist/{pi-embedded-BAHaY-Oh.js → pi-embedded-CHNPEUAv.js} +159 -159
  44. package/dist/{pi-model-discovery-ItS07aJB.js → pi-model-discovery-D-r5y7kV.js} +7 -7
  45. package/dist/pi-model-discovery-runtime-DZQXYmdu.js +12 -0
  46. package/dist/{pi-tools.before-tool-call.runtime-D_mthvtC.js → pi-tools.before-tool-call.runtime-DagGpfw0.js} +10 -10
  47. package/dist/{proxy-fetch-c1ZUFFcO.js → proxy-fetch-BOh1PLOW.js} +1 -1
  48. package/dist/{pw-ai-Ok6KGelf.js → pw-ai-CoIUdns_.js} +9 -9
  49. package/dist/{qmd-manager-DhfEz4Ar.js → qmd-manager-DEscZz5_.js} +6 -6
  50. package/dist/{query-expansion-GqNV2iIE.js → query-expansion-BErUY8P2.js} +4 -4
  51. package/dist/runtime-whatsapp-login.runtime-ChqE9BkX.js +13 -0
  52. package/dist/runtime-whatsapp-outbound.runtime-yiy6jzKk.js +17 -0
  53. package/dist/{send-DPflcjM5.js → send-4rRrSKp9.js} +6 -6
  54. package/dist/{send-CEg4P96c.js → send-BKO1-P1t.js} +5 -5
  55. package/dist/{send-CS0ocZHl.js → send-EDBPXjTT.js} +3 -3
  56. package/dist/{send-6R8b9zsj.js → send-K2mAG7KC.js} +5 -5
  57. package/dist/{send-DwAoiT2p.js → send-V1MRV7QF.js} +25 -25
  58. package/dist/{session-BoIID5UR.js → session-CuVCho2m.js} +7 -7
  59. package/dist/{skill-commands-DhdiziMs.js → skill-commands-B55LOaMB.js} +9 -9
  60. package/dist/slash-commands.runtime-BchS0VkW.js +12 -0
  61. package/dist/slash-dispatch.runtime-BIKRY3fr.js +39 -0
  62. package/dist/slash-skill-commands.runtime-BP4jBHU9.js +13 -0
  63. package/dist/subagent-registry-runtime-DjEYzSyM.js +39 -0
  64. package/dist/{subsystem-C8z6w6xC.js → subsystem-DfXy5gUB.js} +14 -14
  65. package/dist/{tables-DQusRhkD.js → tables-BAGqh2XD.js} +1 -1
  66. package/dist/{target-errors-CfavnC9U.js → target-errors-CeBF8Pws.js} +1 -1
  67. package/dist/{tokens-BWDIKewp.js → tokens-6ul2IrzG.js} +1 -1
  68. package/dist/{web-CrcrTQ2c.js → web-BRSmQdtm.js} +39 -39
  69. package/dist/{whatsapp-actions-B0u0ZAme.js → whatsapp-actions-Dxb2K2Xh.js} +15 -15
  70. package/dist/{workspace-CWDYHR27.js → workspace-DGIcKCCW.js} +20 -20
  71. package/extensions/mfa-auth/README.md +33 -38
  72. package/extensions/mfa-auth/index.ts +97 -92
  73. package/extensions/mfa-auth/node_modules/.bin/qrcode-terminal +1 -6
  74. package/extensions/mfa-auth/node_modules/.bin/qrcode-terminal.cmd +17 -0
  75. package/extensions/mfa-auth/node_modules/.bin/qrcode-terminal.ps1 +0 -13
  76. package/extensions/mfa-auth/node_modules/.bin/tsx +1 -6
  77. package/extensions/mfa-auth/node_modules/.bin/tsx.cmd +17 -0
  78. package/extensions/mfa-auth/node_modules/.bin/tsx.ps1 +0 -13
  79. package/extensions/mfa-auth/node_modules/.package-lock.json +103 -0
  80. package/extensions/mfa-auth/package-lock.json +115 -0
  81. package/extensions/mfa-auth/package.json +1 -1
  82. package/extensions/mfa-auth/src/auth-manager.ts +4 -2
  83. package/extensions/mfa-auth/src/config.ts +1 -4
  84. package/extensions/mfa-auth/src/dabby-client.test.ts +68 -147
  85. package/extensions/mfa-auth/src/dabby-client.ts +70 -89
  86. package/extensions/mfa-auth/src/feishu-support/index.ts +2 -2
  87. package/extensions/mfa-auth/src/notification-service.ts +19 -14
  88. package/extensions/mfa-auth/src/providers/base.ts +0 -1
  89. package/extensions/mfa-auth/src/providers/qr-code.ts +3 -506
  90. package/extensions/mfa-auth/src/server.ts +3 -223
  91. package/extensions/mfa-auth/src/types.ts +13 -36
  92. package/package.json +458 -460
  93. package/dist/compact.runtime-BEn3giMt.js +0 -39
  94. package/dist/deliver-runtime-DkQ3XzGv.js +0 -19
  95. package/dist/deps-send-discord.runtime-BLpqSj6s.js +0 -19
  96. package/dist/deps-send-imessage.runtime-BFzyYqvR.js +0 -18
  97. package/dist/deps-send-signal.runtime-DT0TYCy1.js +0 -17
  98. package/dist/deps-send-slack.runtime-BhaGFfMX.js +0 -17
  99. package/dist/deps-send-telegram.runtime-B6Cic9NX.js +0 -20
  100. package/dist/deps-send-whatsapp.runtime-WtEhIq2S.js +0 -43
  101. package/dist/image-runtime-B1LFYfQ2.js +0 -12
  102. package/dist/manager-runtime-Da7ME9vS.js +0 -15
  103. package/dist/pi-model-discovery-runtime-DjM7Z1fx.js +0 -12
  104. package/dist/runtime-whatsapp-login.runtime-D4BRhQkK.js +0 -13
  105. package/dist/runtime-whatsapp-outbound.runtime-DJPpS6g-.js +0 -17
  106. package/dist/slash-commands.runtime-Cu1lTjV9.js +0 -12
  107. package/dist/slash-dispatch.runtime-DRVJEF4l.js +0 -39
  108. package/dist/slash-skill-commands.runtime-C373PJjv.js +0 -13
  109. package/dist/subagent-registry-runtime-D7hWBo1G.js +0 -39
  110. package/extensions/mfa-auth/node_modules/.bin/qrcode-terminal.CMD +0 -12
  111. package/extensions/mfa-auth/node_modules/.bin/tsx.CMD +0 -12
@@ -1,9 +1,8 @@
1
1
  import { dabbyConfig } from "./config.js";
2
2
  import type {
3
3
  DabbyConfig,
4
- DabbyAccessTokenResponse,
5
- DabbyQrCodeResponse,
6
- DabbyAuthResultResponse,
4
+ DabbyVerifyCodeResponse,
5
+ DabbyCheckAuthStatusResponse,
7
6
  } from "./types.js";
8
7
 
9
8
  const resolveFetch = (): typeof fetch => {
@@ -15,110 +14,89 @@ const resolveFetch = (): typeof fetch => {
15
14
  };
16
15
 
17
16
  export class DabbyClient {
18
- private cachedAccessToken: string | null = null;
19
- private tokenExpiryTime: number = 0;
20
-
21
17
  constructor(private config: DabbyConfig = dabbyConfig) {}
22
18
 
23
- async getAccessToken(forceRefresh = false): Promise<string> {
24
- if (!this.config.clientId || !this.config.clientSecret) {
25
- throw new Error("Dabby clientId and clientSecret are not configured");
26
- }
27
-
28
- if (!forceRefresh && this.cachedAccessToken && Date.now() < this.tokenExpiryTime) {
29
- return this.cachedAccessToken;
19
+ async getVerifyCode(): Promise<DabbyVerifyCodeResponse["data"]> {
20
+ if (!this.config.apiKey) {
21
+ throw new Error("MFA_AUTH_API_KEY is not configured");
30
22
  }
31
23
 
32
- const url = `${this.config.apiBaseUrl}/getaccesstoken`;
33
- const params = new URLSearchParams({
34
- clientId: this.config.clientId,
35
- clientSecret: this.config.clientSecret,
36
- });
37
24
  const fetch = resolveFetch();
38
- const fullUrl = `${url}?${params.toString()}`;
39
- console.log(`[mfa-auth] Fetching accessToken from: ${fullUrl}`);
25
+ const url = `${this.config.apiBaseUrl}/api/v1/getVerifyCode`;
26
+
27
+ const requestBody = {
28
+ apiKey: this.config.apiKey,
29
+ authType: "ScanAuth",
30
+ mode: "66",
31
+ };
32
+
33
+ console.log(`[mfa-auth] Fetching verify code from: ${url}`);
34
+ console.log(`[mfa-auth] Request body:`, JSON.stringify(requestBody, null, 2));
40
35
 
41
36
  let lastError: any;
42
37
  for (let i = 0; i < 3; i++) {
43
38
  try {
44
- const response = await fetch(fullUrl, {
45
- method: "GET",
39
+ const response = await fetch(url, {
40
+ method: "POST",
46
41
  headers: {
47
42
  "Content-Type": "application/json",
48
43
  "User-Agent": "OpenClaw/1.0 (mfa-auth)",
49
44
  },
45
+ body: JSON.stringify(requestBody),
50
46
  });
51
47
 
52
48
  if (!response.ok) {
53
49
  throw new Error(`HTTP ${response.status}: ${response.statusText}`);
54
50
  }
55
51
 
56
- const data = (await response.json()) as DabbyAccessTokenResponse;
52
+ const data = (await response.json()) as DabbyVerifyCodeResponse;
53
+
54
+ console.log(`[mfa-auth] API response:`, JSON.stringify(data, null, 2));
57
55
 
58
56
  if (data.retCode !== 0) {
59
- throw new Error(`Dabby API error: ${data.retMessage}`);
57
+ throw new Error(`Dabby API error: ${data.message} (code: ${data.retCode})`);
58
+ }
59
+
60
+ if (!data.data) {
61
+ throw new Error("Dabby API returned empty data");
60
62
  }
61
63
 
62
- this.cachedAccessToken = data.accessToken;
63
- this.tokenExpiryTime = Date.now() + data.expireSeconds * 1000;
64
+ console.log(
65
+ `[mfa-auth] Verify code generated, certToken: ${data.data.certToken}, qrCodeUrl: ${data.data.qrCodeUrl}`,
66
+ );
64
67
 
65
- console.log(`[mfa-auth] Dabby accessToken refreshed, expires in ${data.expireSeconds}s`);
68
+ // Append fromSource parameter to qrCodeUrl
69
+ const qrCodeUrlWithSource = data.data.qrCodeUrl.includes("?")
70
+ ? `${data.data.qrCodeUrl}&fromSource=Cclawd`
71
+ : `${data.data.qrCodeUrl}?fromSource=Cclawd`;
66
72
 
67
- return this.cachedAccessToken;
73
+ console.log(`[mfa-auth] QR code URL with fromSource: ${qrCodeUrlWithSource}`);
74
+
75
+ return {
76
+ ...data.data,
77
+ qrCodeUrl: qrCodeUrlWithSource,
78
+ };
68
79
  } catch (error: any) {
69
- console.error(`[mfa-auth] Attempt ${i + 1} failed to get accessToken: ${error.message}`);
80
+ console.error(`[mfa-auth] Attempt ${i + 1} failed to get verify code: ${error.message}`);
70
81
  if (error.cause) {
71
82
  console.error(`[mfa-auth] Failure cause:`, error.cause);
72
83
  }
73
84
  lastError = error;
74
- await new Promise((resolve) => setTimeout(resolve, 1000)); // Wait 1s before retry
85
+ await new Promise((resolve) => setTimeout(resolve, 1000));
75
86
  }
76
87
  }
77
88
 
78
- console.error(`[mfa-auth] Failed to get accessToken after 3 attempts`);
89
+ console.error(`[mfa-auth] Failed to get verify code after 3 attempts`);
79
90
  throw lastError;
80
91
  }
81
92
 
82
- async refreshAccessToken(): Promise<string> {
83
- return this.getAccessToken(true);
84
- }
85
-
86
- async getQrCode(): Promise<DabbyQrCodeResponse["tokenInfo"]> {
87
- try {
88
- const accessToken = await this.getAccessToken();
89
- const fetch = resolveFetch();
90
-
91
- const url = `${this.config.apiBaseUrl}/authreq`;
92
- const response = await fetch(url, {
93
- method: "POST",
94
- headers: {
95
- "Content-Type": "application/json",
96
- "User-Agent": "OpenClaw/1.0 (mfa-auth)",
97
- },
98
- body: JSON.stringify({
99
- accessToken,
100
- authType: "ScanAuth",
101
- mode: 66,
102
- }),
103
- });
104
-
105
- if (!response.ok) {
106
- throw new Error(`HTTP ${response.status}: ${response.statusText}`);
107
- }
108
-
109
- const data = (await response.json()) as DabbyQrCodeResponse;
110
-
111
- if (data.retCode !== 0) {
112
- throw new Error(`Dabby API error: ${data.retMessage}`);
113
- }
114
-
115
- console.log(`[mfa-auth] QR code generated, certToken: ${data.tokenInfo.certToken}`);
116
-
117
- return data.tokenInfo;
118
- } catch (error: any) {
119
- console.error(`[mfa-auth] Failed to generate QR code: ${error.message}`);
120
- throw error;
121
- }
93
+ // Alias for backward compatibility if needed by other files, or just refactor them too.
94
+ // The plan said "Rename or keep original name". I'll keep this alias to minimize changes in other files for now,
95
+ // but I'll also update the other files to use getVerifyCode if I can.
96
+ // Actually, I'll update other files to use getVerifyCode as per plan step 4.
97
+ // But keeping it as alias is safer during transition.
98
+ async getQrCode(): Promise<DabbyVerifyCodeResponse["data"]> {
99
+ return this.getVerifyCode();
122
100
  }
123
101
 
124
102
  async getAuthResult(certToken: string): Promise<{
@@ -126,50 +104,53 @@ export class DabbyClient {
126
104
  error?: string;
127
105
  authObject?: { idNum: string; fullName: string };
128
106
  }> {
107
+ if (!this.config.apiKey) {
108
+ return { status: "failed", error: "MFA_AUTH_API_KEY is not configured" };
109
+ }
110
+
129
111
  try {
130
- const accessToken = await this.getAccessToken();
131
112
  const fetch = resolveFetch();
113
+ const url = `${this.config.apiBaseUrl}/api/v1/checkAuthStatus`;
114
+
115
+ const requestBody = {
116
+ apiKey: this.config.apiKey,
117
+ certToken,
118
+ };
119
+
120
+ console.log(`[mfa-auth] Checking auth status for certToken: ${certToken}`);
121
+ console.log(`[mfa-auth] CheckAuthStatus request body:`, JSON.stringify(requestBody, null, 2));
132
122
 
133
- const url = `${this.config.apiBaseUrl}/authhist`;
134
123
  const response = await fetch(url, {
135
124
  method: "POST",
136
125
  headers: {
137
126
  "Content-Type": "application/json",
138
127
  "User-Agent": "OpenClaw/1.0 (mfa-auth)",
139
128
  },
140
- body: JSON.stringify({
141
- accessToken,
142
- authHistQry: { certToken },
143
- }),
129
+ body: JSON.stringify(requestBody),
144
130
  });
145
131
 
146
132
  if (!response.ok) {
147
133
  throw new Error(`HTTP ${response.status}: ${response.statusText}`);
148
134
  }
149
135
 
150
- const data: DabbyAuthResultResponse = await response.json();
136
+ const data = (await response.json()) as DabbyCheckAuthStatusResponse;
137
+
138
+ console.log(`[mfa-auth] CheckAuthStatus response:`, JSON.stringify(data, null, 2));
151
139
 
152
- // 处理特定的“等待中”状态码
153
- // 4401: 该 certToken 未进行认证 -> 视为 Pending 状态,继续轮询
154
140
  if (data.retCode !== 0) {
155
141
  if (data.retCode === 4401) {
156
142
  return { status: "pending" };
157
143
  }
158
- // 其他错误才抛出异常
159
- throw new Error(`Dabby API error: ${data.retMessage} (code: ${data.retCode})`);
144
+ throw new Error(`Dabby API error: ${data.message} (code: ${data.retCode})`);
160
145
  }
161
146
 
162
- const resCode = data.authData.resCode;
163
- const authObject = data.authData.authObject;
164
-
165
- if (resCode === 0) {
166
- return { status: "verified", authObject };
147
+ if (data.data.authSuccess) {
148
+ return { status: "verified", authObject: data.data.authResult };
167
149
  }
168
150
 
169
- return { status: "failed", error: `认证失败 (resCode: ${resCode})` };
151
+ return { status: "failed", error: data.data.message || "认证失败" };
170
152
  } catch (error: any) {
171
153
  console.error(`[mfa-auth] Failed to get auth result: ${error.message}`);
172
- // Don't throw here, return error status so polling can continue or fail gracefully
173
154
  return { status: "failed", error: error.message };
174
155
  }
175
156
  }
@@ -12,14 +12,14 @@ export type FeishuConfig = {
12
12
  domain?: FeishuDomain;
13
13
  accounts?: Record<string, FeishuAccountConfig>;
14
14
  defaultAccount?: string;
15
- // 鍏朵粬瀛楁蹇界暐
15
+ // 其他字段忽略
16
16
  };
17
17
 
18
18
  export type FeishuAccountConfig = {
19
19
  appId?: string;
20
20
  appSecret?: string | { source: string; id: string };
21
21
  domain?: FeishuDomain;
22
- // 鍏朵粬瀛楁蹇界暐
22
+ // 其他字段忽略
23
23
  };
24
24
 
25
25
  export type ResolvedFeishuAccount = {
@@ -29,8 +29,8 @@ class NotificationService {
29
29
  return;
30
30
  }
31
31
 
32
- if (channel === "webchat" || channel === "web") {
33
- console.log(`[mfa-auth] Web/webchat channel: sending notification via WebSocket`);
32
+ if (channel === "webchat" || channel === "web" || channel === "main" || channel === "desktop") {
33
+ console.log(`[mfa-auth] ${channel} channel: sending notification via WebSocket`);
34
34
  await this.sendToWebChat(session, message);
35
35
  return;
36
36
  }
@@ -172,8 +172,7 @@ class NotificationService {
172
172
  ),
173
173
  );
174
174
  }
175
- } catch (e) {
176
- }
175
+ } catch (e) {}
177
176
  });
178
177
 
179
178
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
@@ -205,29 +204,35 @@ class NotificationService {
205
204
  : undefined;
206
205
  const sessionsRaw = Array.isArray(resultObject?.sessions) ? resultObject.sessions : [];
207
206
  const webchatRows = sessionsRaw
208
- .map((row) =>
209
- row && typeof row === "object" ? (row as Record<string, unknown>) : undefined,
210
- )
207
+ .map((row) => (row && typeof row === "object" ? (row as Record<string, unknown>) : undefined))
211
208
  .filter((row): row is Record<string, unknown> => Boolean(row))
212
209
  .filter((row) => {
213
- const ch = String(row.channel ?? "").trim().toLowerCase();
210
+ const ch = String(row.channel ?? "")
211
+ .trim()
212
+ .toLowerCase();
214
213
  const dc = row.deliveryContext as Record<string, unknown> | undefined;
215
- const dcChannel = String(dc?.channel ?? "").trim().toLowerCase();
214
+ const dcChannel = String(dc?.channel ?? "")
215
+ .trim()
216
+ .toLowerCase();
216
217
  return ch === "webchat" || ch === "web" || dcChannel === "webchat" || dcChannel === "web";
217
218
  });
218
219
 
219
220
  const exactRows = webchatRows.filter((row) => {
220
221
  const dc = row.deliveryContext as Record<string, unknown> | undefined;
221
- const peer = String(dc?.to ?? row.lastTo ?? "").trim().toLowerCase();
222
+ const peer = String(dc?.to ?? row.lastTo ?? "")
223
+ .trim()
224
+ .toLowerCase();
222
225
  return peer.length > 0 && peer === normalizedTarget;
223
226
  });
224
227
  const fallbackRows = webchatRows.filter((row) => !exactRows.includes(row));
225
-
228
+
226
229
  // Fuzzy match: include any webchat session that contains the userId in its key
227
230
  const fuzzyRows = webchatRows.filter((row) => {
228
231
  const key = String(row.key ?? "").toLowerCase();
229
232
  // Ensure we don't duplicate rows already found
230
- return key.includes(normalizedTarget) && !exactRows.includes(row) && !fallbackRows.includes(row);
233
+ return (
234
+ key.includes(normalizedTarget) && !exactRows.includes(row) && !fallbackRows.includes(row)
235
+ );
231
236
  });
232
237
 
233
238
  const sortByUpdatedAtDesc = (a: Record<string, unknown>, b: Record<string, unknown>) => {
@@ -302,9 +307,9 @@ class NotificationService {
302
307
 
303
308
  // Simplified assertion
304
309
  if (response.code !== 0) {
305
- throw new Error(`Feishu API error ${response.code}: ${response.msg}`);
310
+ throw new Error(`Feishu API error ${response.code}: ${response.msg}`);
306
311
  }
307
-
312
+
308
313
  const messageId = response.data?.message_id || "unknown";
309
314
  console.log(`[mfa-auth] Feishu message sent: ${messageId} to ${to}`);
310
315
  } catch (error) {
@@ -7,7 +7,6 @@ export abstract class BaseAuthProvider implements AuthMethodProvider {
7
7
 
8
8
  abstract initialize(session: AuthSession): Promise<void>;
9
9
  abstract verify(sessionId: string, userInput?: string): Promise<AuthResult>;
10
- abstract generateAuthPage(session: AuthSession, authUrl: string): Promise<string>;
11
10
 
12
11
  cleanup(sessionId: string): void {}
13
12
  }