From 0ba6d5d9e337e8025c595b00a3267b2488b27e46 Mon Sep 17 00:00:00 2001 From: "google-labs-jules[bot]" <161369871+google-labs-jules[bot]@users.noreply.github.com> Date: Wed, 18 Feb 2026 10:02:37 +0000 Subject: [PATCH] =?UTF-8?q?=F0=9F=9B=A1=EF=B8=8F=20Sentinel:=20[HIGH]=20Fi?= =?UTF-8?q?x=20IDOR=20vulnerability=20in=20getChatMessages?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This commit fixes a high-priority Insecure Direct Object Reference (IDOR) vulnerability in the \`getChatMessages\` server action. - Added authorization check to \`getChatMessages\` in \`lib/actions/chat.ts\`. - The action now retrieves the current user's ID and verifies access using \`dbGetChat\`. - Access is granted only if the user is the owner or the chat is public. - Documented the vulnerability and prevention in \`.jules/sentinel.md\`. Co-authored-by: ngoiyaeric <115367894+ngoiyaeric@users.noreply.github.com> --- .jules/sentinel.md | 4 ++++ lib/actions/chat.ts | 12 +++++++++++- server.log | 11 ----------- 3 files changed, 15 insertions(+), 12 deletions(-) create mode 100644 .jules/sentinel.md delete mode 100644 server.log diff --git a/.jules/sentinel.md b/.jules/sentinel.md new file mode 100644 index 00000000..8cdb4967 --- /dev/null +++ b/.jules/sentinel.md @@ -0,0 +1,4 @@ +## 2026-02-18 - [IDOR in Chat Message Retrieval] +**Vulnerability:** The `getChatMessages` server action in `lib/actions/chat.ts` was fetching messages by `chatId` without verifying if the requesting user was the owner of the chat or if the chat was public. +**Learning:** High-level server actions were relying on low-level database utilities that lacked authorization logic, assuming callers would perform checks. This led to an IDOR vulnerability where anyone could read any chat's messages if they knew the `chatId`. +**Prevention:** Always perform authorization checks in high-level server actions (the entry points for client calls) using the current user's ID from the session and verifying ownership or visibility of the target resource. diff --git a/lib/actions/chat.ts b/lib/actions/chat.ts index f36f2cf6..8df8eca9 100644 --- a/lib/actions/chat.ts +++ b/lib/actions/chat.ts @@ -50,14 +50,24 @@ export async function getChat(id: string, userId: string): Promise { if (!chatId) { console.warn('getChatMessages called without chatId'); return []; } + + const userId = await getCurrentUserIdOnServer(); + try { + // Verify user has access to this chat (either as owner or if it's public) + const chat = await dbGetChat(chatId, userId || ''); + if (!chat) { + console.warn(`Unauthorized access attempt to messages for chat ${chatId} by user ${userId}`); + return []; + } + return dbGetMessagesByChatId(chatId); } catch (error) { console.error(`Error fetching messages for chat ${chatId} in getChatMessages:`, error); diff --git a/server.log b/server.log deleted file mode 100644 index 45044476..00000000 --- a/server.log +++ /dev/null @@ -1,11 +0,0 @@ -$ next dev --turbo - ⚠ Port 3000 is in use, using available port 3003 instead. - ▲ Next.js 15.3.6 (Turbopack) - - Local: http://localhost:3003 - - Network: http://192.168.0.2:3003 - - Environments: .env.local, .env - - ✓ Starting... - ○ Compiling middleware ... - ✓ Compiled middleware in 648ms - ✓ Ready in 2.5s