Skip to content

Commit 30c0b87

Browse files
committed
chore: 更新 eventRouter 和 messageReply 函數以使用更嚴格的類型定義,並改善事件處理邏輯
1 parent fae0819 commit 30c0b87

4 files changed

Lines changed: 31 additions & 14 deletions

File tree

src/eventRouter.ts

Lines changed: 22 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,16 @@
11
import { sendMessage, markAsRead, loadStart } from "./utils/eventRoutes";
22
import { env } from "cloudflare:workers";
33
import { version } from "../package.json";
4+
import type { webhook } from "@line/bot-sdk";
5+
import type { Message } from "./types";
46

5-
export async function eventRouter(event: any, channelAccessToken: string, ctx: ExecutionContext): Promise<any[]> {
7+
export async function eventRouter(event: webhook.Event, channelAccessToken: string, ctx: ExecutionContext): Promise<Message[]> {
68
// Log
79
let eventType: string = event.type;
810
try {
9-
if (["message"].includes(event.type)) {
10-
eventType = `${event.type}(${event.message?.type})`;
11+
if (event.type === "message") {
12+
const msgEvent = event as webhook.MessageEvent;
13+
eventType = `${event.type}(${msgEvent.message?.type})`;
1114
}
1215
} catch (e) {
1316
console.error("Failed to determine message event type", { error: e });
@@ -17,16 +20,25 @@ export async function eventRouter(event: any, channelAccessToken: string, ctx: E
1720

1821
switch (event.type) {
1922
case "message": {
20-
ctx.waitUntil(markAsRead(channelAccessToken, event.message.markAsReadToken));
23+
const msgEvent = event as webhook.MessageEvent;
24+
if (msgEvent.message.markAsReadToken) {
25+
ctx.waitUntil(markAsRead(channelAccessToken, msgEvent.message.markAsReadToken));
26+
}
27+
28+
const userId = msgEvent.source && typeof (msgEvent.source as any).userId === "string" ? (msgEvent.source as any).userId : undefined;
2129

22-
await Promise.race([
23-
loadStart(channelAccessToken, event.source.userId, 5),
24-
new Promise((resolve) => setTimeout(resolve, 50)), // 最多等 50ms
25-
]);
30+
if (userId) {
31+
await Promise.race([
32+
loadStart(channelAccessToken, userId, 5),
33+
new Promise((resolve) => setTimeout(resolve, 50)), // 最多等 50ms
34+
]);
35+
} else {
36+
await new Promise((resolve) => setTimeout(resolve, 50));
37+
}
2638

27-
switch (event.message.type) {
39+
switch (msgEvent.message.type) {
2840
case "text":
29-
switch (event.message.text) {
41+
switch (msgEvent.message.text) {
3042
case "/version":
3143
const { id: versionId, tag: versionTag, timestamp: versionTimestamp } = env.CF_VERSION_METADATA;
3244

src/router.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -42,10 +42,10 @@ export async function router(request: Request, env: Env, ctx: ExecutionContext)
4242
}
4343
// 解析 JSON body
4444
const events = body.events || [];
45-
for (const event of events as any[]) {
45+
for (const event of events) {
4646
const responses = (await eventRouter(event, channelAccessToken, ctx)) ?? [];
47-
if (responses.length > 0) {
48-
await sendMessage(channelAccessToken, event.replyToken, responses as any[]);
47+
if (responses.length > 0 && "replyToken" in event && typeof event.replyToken === "string") {
48+
await sendMessage(channelAccessToken, event.replyToken, responses);
4949
}
5050
}
5151
// 回應 LINE 伺服器

src/types.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
export type TextMessage = { type: "text"; text: string };
2+
export type ImageMessage = { type: "image"; originalContentUrl: string; previewImageUrl: string };
3+
export type Message = TextMessage | ImageMessage | { type: string; [key: string]: unknown };

src/utils/eventRoutes/messageReply.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
1-
export async function sendMessage(ChannelAccessToken: string, replyToken: string, messages: any[]) {
1+
import type { Message } from "../../types";
2+
3+
export async function sendMessage(ChannelAccessToken: string, replyToken: string, messages: Message[]): Promise<unknown> {
24
const res = await fetch("https://api.line.me/v2/bot/message/reply", {
35
headers: {
46
"Content-Type": "application/json",

0 commit comments

Comments
 (0)