fix(slack): handle Bolt ESM/CJS import for Node 25.x

The slackBoltModule.default points to App class directly on Node 25.x,
not the module object. Check for App property first before using default.
main
SocialNerd42069 2026-01-20 19:44:12 -06:00 committed by Peter Steinberger
parent 0d6e78b718
commit 5b8007784b
1 changed files with 9 additions and 26 deletions

View File

@ -1,6 +1,6 @@
import type { IncomingMessage, ServerResponse } from "node:http"; import type { IncomingMessage, ServerResponse } from "node:http";
import SlackBoltDefault, * as SlackBoltModule from "@slack/bolt"; import SlackBolt from "@slack/bolt";
import { resolveTextChunkLimit } from "../../auto-reply/chunk.js"; import { resolveTextChunkLimit } from "../../auto-reply/chunk.js";
import { DEFAULT_GROUP_HISTORY_LIMIT } from "../../auto-reply/reply/history.js"; import { DEFAULT_GROUP_HISTORY_LIMIT } from "../../auto-reply/reply/history.js";
@ -26,24 +26,14 @@ import { normalizeAllowList } from "./allow-list.js";
import type { MonitorSlackOpts } from "./types.js"; import type { MonitorSlackOpts } from "./types.js";
type SlackBoltNamespace = typeof import("@slack/bolt"); const slackBoltModule = SlackBolt as typeof import("@slack/bolt") & {
type SlackBoltDefault = SlackBoltNamespace | SlackBoltNamespace["App"]; default?: typeof import("@slack/bolt");
};
const slackBoltDefaultImport = SlackBoltDefault as SlackBoltDefault | undefined; // Bun allows named imports from CJS; Node ESM doesn't. Use default+fallback for compatibility.
const slackBoltModuleDefault = (SlackBoltModule as { default?: SlackBoltDefault }).default; // Fix: Check if module has App property directly (Node 25.x ESM/CJS compat issue)
const slackBoltDefault = slackBoltDefaultImport ?? slackBoltModuleDefault; const slackBolt =
const slackBoltNamespace = (slackBoltModule.App ? slackBoltModule : slackBoltModule.default) ?? slackBoltModule;
typeof slackBoltDefault === "object" && slackBoltDefault const { App, HTTPReceiver } = slackBolt;
? (slackBoltDefault as SlackBoltNamespace)
: typeof slackBoltModuleDefault === "object" && slackBoltModuleDefault
? (slackBoltModuleDefault as SlackBoltNamespace)
: undefined;
// Bun allows named imports from CJS; Node ESM doesn't. Resolve default/module shapes for compatibility.
const App = ((typeof slackBoltDefault === "function" ? slackBoltDefault : undefined) ??
slackBoltNamespace?.App ??
SlackBoltModule.App) as SlackBoltNamespace["App"];
const HTTPReceiver = (slackBoltNamespace?.HTTPReceiver ??
SlackBoltModule.HTTPReceiver) as SlackBoltNamespace["HTTPReceiver"];
function parseApiAppIdFromAppToken(raw?: string) { function parseApiAppIdFromAppToken(raw?: string) {
const token = raw?.trim(); const token = raw?.trim();
if (!token) return undefined; if (!token) return undefined;
@ -133,13 +123,6 @@ export async function monitorSlackProvider(opts: MonitorSlackOpts = {}) {
const mediaMaxBytes = (opts.mediaMaxMb ?? slackCfg.mediaMaxMb ?? 20) * 1024 * 1024; const mediaMaxBytes = (opts.mediaMaxMb ?? slackCfg.mediaMaxMb ?? 20) * 1024 * 1024;
const removeAckAfterReply = cfg.messages?.removeAckAfterReply ?? false; const removeAckAfterReply = cfg.messages?.removeAckAfterReply ?? false;
if (!App) {
throw new Error("Slack Bolt App export missing; check @slack/bolt installation.");
}
if (slackMode === "http" && !HTTPReceiver) {
throw new Error("Slack Bolt HTTPReceiver export missing; check @slack/bolt installation.");
}
const receiver = const receiver =
slackMode === "http" slackMode === "http"
? new HTTPReceiver({ ? new HTTPReceiver({