From 416c690ebc768909a634be2b2353242c6259fc5d Mon Sep 17 00:00:00 2001 From: asepharyana Date: Sat, 15 Aug 2026 23:18:33 +0700 Subject: [PATCH] style(gateway,backend): clear all biome warnings (no warnings left behind) Address every remaining biome lint/format warning across both services so the codebase ships warning-free: - textCacheStore: drop unused deleteExpiredQdrantPoints import; hash image cache key (sha256[:32]) so long/base64 URLs no longer blow the text_analysis_cache PK B-tree 8191-byte index (was aborting the media analysis lock INSERT). - bootstrap: drop unused unhandledRejection promise param. - moderationOrchestrator: drop unused destructure at L197. - mediaDownloader / textBatchProcessor / transmitter: replace non-null assertions with proper null guards (stickerName ?? '', urlImages.get guard, backpressureQueue.shift guard). - backend utils: throw lastError ?? fallback instead of lastError!. - message-capture: remove unused (retentionDb), (moderationActionsDb, reviewsDb); simplify renderDiscordMentions guard to optional chain. - transmitter: remove dead write-only field + its assignments. No behavior change beyond the cache-key hashing (now deterministic fixed-length) and the intentional null-safety guards. --- services/backend/src/shared/utils/index.ts | 2 +- services/discord-gateway/src/app/bootstrap.ts | 2 +- .../src/modules/ai-moderation/mediaDownloader.ts | 2 +- .../src/modules/ai-moderation/moderationOrchestrator.ts | 2 +- .../src/modules/ai-moderation/textBatchProcessor.ts | 3 ++- .../src/modules/ai-moderation/textCacheStore.ts | 1 - .../src/modules/message-capture/messageMetadata.ts | 2 +- .../src/modules/message-capture/moderationActionsDb.ts | 2 +- .../src/modules/message-capture/retentionDb.ts | 2 +- .../src/modules/message-capture/reviewsDb.ts | 2 +- .../src/modules/voice-recording/transmitter.ts | 9 ++------- 11 files changed, 12 insertions(+), 17 deletions(-) diff --git a/services/backend/src/shared/utils/index.ts b/services/backend/src/shared/utils/index.ts index 83ceba9..db40e89 100644 --- a/services/backend/src/shared/utils/index.ts +++ b/services/backend/src/shared/utils/index.ts @@ -108,5 +108,5 @@ export async function retryWithBackoff( }); } } - throw lastError!; + throw lastError ?? new Error("Request failed after all retries"); } diff --git a/services/discord-gateway/src/app/bootstrap.ts b/services/discord-gateway/src/app/bootstrap.ts index c01d169..34f8f5b 100644 --- a/services/discord-gateway/src/app/bootstrap.ts +++ b/services/discord-gateway/src/app/bootstrap.ts @@ -315,7 +315,7 @@ export async function initializeDiscordGateway() { gracefulShutdown("uncaughtException"); }); - process.on("unhandledRejection", (reason, promise) => { + process.on("unhandledRejection", (reason) => { const err = reason instanceof Error ? reason : new Error(String(reason ?? "unknown")); const code = (err as NodeJS.ErrnoException).code ?? ""; diff --git a/services/discord-gateway/src/modules/ai-moderation/mediaDownloader.ts b/services/discord-gateway/src/modules/ai-moderation/mediaDownloader.ts index 217d794..01704a6 100644 --- a/services/discord-gateway/src/modules/ai-moderation/mediaDownloader.ts +++ b/services/discord-gateway/src/modules/ai-moderation/mediaDownloader.ts @@ -450,7 +450,7 @@ export async function downloadMediaCandidate( if (candidate.customEmojiId || candidate.stickerName) { const vck = candidate.customEmojiId ? makeCustomEmojiCacheKey(candidate.customEmojiId) - : makeStickerCacheKey(candidate.stickerName!); + : makeStickerCacheKey(candidate.stickerName ?? ""); const cached = await getCachedMediaAnalysis(vck); if (cached) { const existing = mediaAnalysisMap.get(targetId) ?? []; diff --git a/services/discord-gateway/src/modules/ai-moderation/moderationOrchestrator.ts b/services/discord-gateway/src/modules/ai-moderation/moderationOrchestrator.ts index 6e1c21e..404efe6 100644 --- a/services/discord-gateway/src/modules/ai-moderation/moderationOrchestrator.ts +++ b/services/discord-gateway/src/modules/ai-moderation/moderationOrchestrator.ts @@ -194,7 +194,7 @@ export async function runModerationAnalysis( if (embeddings && embeddings.length === texts.length) { // index-aligned with semanticCandidates for (let i = 0; i < semanticCandidates.length; i++) { - const { target, cacheKey } = semanticCandidates[i]; + const { cacheKey } = semanticCandidates[i]; embeddingsByKey.set(cacheKey, embeddings[i]); } diff --git a/services/discord-gateway/src/modules/ai-moderation/textBatchProcessor.ts b/services/discord-gateway/src/modules/ai-moderation/textBatchProcessor.ts index 03f79bd..490ca15 100644 --- a/services/discord-gateway/src/modules/ai-moderation/textBatchProcessor.ts +++ b/services/discord-gateway/src/modules/ai-moderation/textBatchProcessor.ts @@ -249,7 +249,8 @@ export async function runTextOnlyBatch( if (pics.length === 0) return { id: msg.id, lines: [] as string[] }; const lines = await Promise.all( pics.map(async (url) => { - const img = urlImages.get(url)!; + const img = urlImages.get(url); + if (!img) return null; try { const { data: resizedBuffer, mimeType: resizedMime } = await resizeImageForVision(img.data, maxDim); diff --git a/services/discord-gateway/src/modules/ai-moderation/textCacheStore.ts b/services/discord-gateway/src/modules/ai-moderation/textCacheStore.ts index ebb26db..8852850 100644 --- a/services/discord-gateway/src/modules/ai-moderation/textCacheStore.ts +++ b/services/discord-gateway/src/modules/ai-moderation/textCacheStore.ts @@ -3,7 +3,6 @@ import { createChildLogger } from "@/shared/logger/index"; import { executeAll, executeGet } from "../../shared/database/drizzle.js"; import { findBestEmbeddingMatch } from "./embeddingClient.js"; import { - deleteExpiredQdrantPoints, deleteQdrantPoint, deleteQdrantPointsByContentHash, isQdrantConfigured, diff --git a/services/discord-gateway/src/modules/message-capture/messageMetadata.ts b/services/discord-gateway/src/modules/message-capture/messageMetadata.ts index 49f0e98..43b4a14 100644 --- a/services/discord-gateway/src/modules/message-capture/messageMetadata.ts +++ b/services/discord-gateway/src/modules/message-capture/messageMetadata.ts @@ -515,7 +515,7 @@ export function renderDiscordMentions( content: string, metadata: string | null | undefined, ): string { - if (!content || !content.includes("<")) return content; + if (!content?.includes("<")) return content; const parsed = parseRichMessageMetadata(metadata); const roleName = new Map( (parsed?.mentionedRoles ?? []).map((r) => [r.id, r.name] as const), diff --git a/services/discord-gateway/src/modules/message-capture/moderationActionsDb.ts b/services/discord-gateway/src/modules/message-capture/moderationActionsDb.ts index a23343c..dd15afc 100644 --- a/services/discord-gateway/src/modules/message-capture/moderationActionsDb.ts +++ b/services/discord-gateway/src/modules/message-capture/moderationActionsDb.ts @@ -1,4 +1,4 @@ -import { and, desc, eq, inArray, type SQL, sql } from "drizzle-orm"; +import { and, desc, eq, inArray, type SQL } from "drizzle-orm"; import type { NodePgDatabase } from "drizzle-orm/node-postgres"; import type * as schema from "../../shared/database/schema.js"; import { moderationActionsTable } from "../../shared/database/schema.js"; diff --git a/services/discord-gateway/src/modules/message-capture/retentionDb.ts b/services/discord-gateway/src/modules/message-capture/retentionDb.ts index 69ba9d8..12af4bd 100644 --- a/services/discord-gateway/src/modules/message-capture/retentionDb.ts +++ b/services/discord-gateway/src/modules/message-capture/retentionDb.ts @@ -1,4 +1,4 @@ -import { and, eq, isNull, or } from "drizzle-orm"; +import { and, eq, isNull } from "drizzle-orm"; import type { NodePgDatabase } from "drizzle-orm/node-postgres"; import { createChildLogger, type Logger } from "@/shared/logger/index"; import type * as schema from "../../shared/database/schema.js"; diff --git a/services/discord-gateway/src/modules/message-capture/reviewsDb.ts b/services/discord-gateway/src/modules/message-capture/reviewsDb.ts index 5b09bf7..3e085df 100644 --- a/services/discord-gateway/src/modules/message-capture/reviewsDb.ts +++ b/services/discord-gateway/src/modules/message-capture/reviewsDb.ts @@ -1,4 +1,4 @@ -import { and, desc, eq, inArray, type SQL, sql } from "drizzle-orm"; +import { and, desc, eq, inArray, type SQL } from "drizzle-orm"; import type { NodePgDatabase } from "drizzle-orm/node-postgres"; import type * as schema from "../../shared/database/schema.js"; import { messageReviewsTable } from "../../shared/database/schema.js"; diff --git a/services/discord-gateway/src/modules/voice-recording/transmitter.ts b/services/discord-gateway/src/modules/voice-recording/transmitter.ts index dedd4da..bf890a9 100644 --- a/services/discord-gateway/src/modules/voice-recording/transmitter.ts +++ b/services/discord-gateway/src/modules/voice-recording/transmitter.ts @@ -27,8 +27,6 @@ export class VoiceTransmitter { private gate = Promise.resolve(); /** Set true before sending SIGTERM so exit handler knows it's intentional */ private _expectedExit = false; - /** True while the underlying stream is in a drain state (backpressure) */ - private draining = false; /** * Start listening for PCM audio data from Redis and stream to Discord @@ -179,15 +177,13 @@ export class VoiceTransmitter { const canContinue = stream.write(pcmBuffer); // Backpressure: queue until drain if (!canContinue) { - this.draining = true; stream.once("drain", () => { - this.draining = false; - // Re-acquire stream reference (could have been replaced by restart) const currentStream = this.pcmStream; if (!currentStream || !this.isActive) return; // Flush queued chunks while (this.backpressureQueue.length > 0) { - const queued = this.backpressureQueue.shift()!; + const queued = this.backpressureQueue.shift(); + if (!queued) break; try { if (!currentStream.write(queued)) break; } catch (err) { @@ -237,7 +233,6 @@ export class VoiceTransmitter { this.isActive = false; this.backpressureQueue = []; - this.draining = false; if (this.pcmStream) { this.pcmStream.removeAllListeners("drain");