Implemented semantic duplicate detection for doubts using embeddings#581
Conversation
|
CodeAnt AI is reviewing your PR. |
|
@Aditya8369 is attempting to deploy a commit to the Karan Mani Tripathi 's projects Team on Vercel. A member of the Team first needs to authorize it. |
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
WalkthroughAdds pgvector storage and index for 1536-dim embeddings, a Groq-backed embedding library with safe generation and pgvector nearest-neighbor search, persists embeddings on doubt creation, uses vector search as a fast-path in similarity checks with LLM fallback, and minor Ask AI UI/accessibility tweaks. ChangesSemantic duplicate detection with embeddings
Sequence Diagram(s)sequenceDiagram
participant Client
participant CheckAPI as POST /api/doubts/check-similarity
participant EmbeddingLib as findSemanticDuplicates
participant GroqAPI as nomic-embed-text
participant DB as Postgres (pgvector)
Client->>CheckAPI: submit content to check
CheckAPI->>EmbeddingLib: build input & request embedding
EmbeddingLib->>GroqAPI: nomic-embed-text (float)
GroqAPI-->>EmbeddingLib: embedding[1536]
EmbeddingLib->>DB: pgvector cosine query (type/classroomId, LIMIT topK)
DB-->>CheckAPI: candidate rows + similarity%
alt candidates found
CheckAPI-->>Client: return similarDoubts
else none or error
CheckAPI->>Client: fallback to existing Groq LLM comparison
end
Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutes Possibly related issues
Possibly related PRs
Suggested labels
Suggested reviewers
🚥 Pre-merge checks | ✅ 3 | ❌ 2❌ Failed checks (2 warnings)
✅ Passed checks (3 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
|
@coderabbitai review |
|
CodeAnt AI finished reviewing your PR. |
There was a problem hiding this comment.
Actionable comments posted: 3
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
src/configs/schema.ts (1)
2-2:⚠️ Potential issue | 🔴 Critical | ⚡ Quick winFix runtime crash in Drizzle schema:
embedding: any()
src/configs/schema.tsdefinesdoubtsTable.embeddingasany()(around line 191). Sinceanyis not a runtime value/symbol here, schema module initialization will throw (and it blocks the embeddings route).Replace the
embeddingcolumn with a real pgvector/vector(1536)Drizzle column type (the repo already sets the DB column viadrizzle/0009_add_doubt_embeddings_pgvector.sqland uses pgvector operators insrc/lib/ai/embeddings.ts). After that, updatesrc/app/api/doubts/route.tsto stop writingembedding as anyand pass the correct driver value type for that column.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@src/configs/schema.ts` at line 2, doubtsTable.embedding currently uses a non-runtime symbol `any()` which crashes module initialization; replace that column declaration with the pgvector Drizzle column type (a vector(1536) column) by importing and using the appropriate pgvector/vector factory instead of `any()` for doubtsTable.embedding, and then update the code in the doubts route that writes embeddings (the writer that currently does `embedding as any`) to pass the correct pgvector driver value type produced by your embedding code (no `as any` cast). Ensure you update the imports where embedding is declared and the insertion/update call in the route so the column type and the value type match (vector(1536) for doubtsTable.embedding and the driver-specific vector value when inserting).
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@src/app/api/doubts/route.ts`:
- Around line 263-271: The call to safeGenerateEmbedding is unbounded and can
stall the POST; wrap or replace the call to
safeGenerateEmbedding(embeddingInput) with a bounded/abortable request using a
timeout (AbortController or Promise.race with a timeout promise) so the request
path never waits indefinitely; if the embedding call times out or errors,
proceed with a safe fallback (e.g., null or empty array) and still perform
db.update(doubtsTable).set({ embedding: ... }) only when a valid embedding
arrives, and ensure you log the timeout/error context (include embeddingInput
and the error) for debugging.
In `@src/lib/ai/embeddings.ts`:
- Around line 94-96: The code currently treats an embedding generation failure
as "no duplicates" by doing if (!queryEmbedding) return [], which masks provider
outages; instead, when safeGenerateEmbedding(embeddingInput) yields no embedding
(queryEmbedding falsy) raise/propagate an error (or return a distinct sentinel
like null) so callers can detect the failure and trigger LLM fallback; replace
the early return in the block that calls safeGenerateEmbedding with an explicit
throw (or null return) and update any callers to handle that error/sentinel
rather than assuming an empty match.
- Around line 34-39: The current check in embeddings.ts lets non-empty
embeddings with the wrong length slip through; enforce exact dimensionality by
validating that vector is an array and vector.length === EMBEDDING_DIMENSIONS
before returning and throw a descriptive Error if it isn't. Update the existing
conditional around vector/EMBEDDING_DIMENSIONS so any length mismatch (including
zero) triggers an error like "Groq returned embedding with incorrect dimensions"
and include actual lengths in the message to aid debugging.
---
Outside diff comments:
In `@src/configs/schema.ts`:
- Line 2: doubtsTable.embedding currently uses a non-runtime symbol `any()`
which crashes module initialization; replace that column declaration with the
pgvector Drizzle column type (a vector(1536) column) by importing and using the
appropriate pgvector/vector factory instead of `any()` for
doubtsTable.embedding, and then update the code in the doubts route that writes
embeddings (the writer that currently does `embedding as any`) to pass the
correct pgvector driver value type produced by your embedding code (no `as any`
cast). Ensure you update the imports where embedding is declared and the
insertion/update call in the route so the column type and the value type match
(vector(1536) for doubtsTable.embedding and the driver-specific vector value
when inserting).
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 7d91b86b-fc2f-467e-98f8-a715f82faaee
📒 Files selected for processing (6)
drizzle/0009_add_doubt_embeddings_pgvector.sqlsrc/app/api/doubts/check-similarity/route.tssrc/app/api/doubts/route.tssrc/app/ask-ai/page.tsxsrc/configs/schema.tssrc/lib/ai/embeddings.ts
|
Hi @Aditya8369! Thanks for your work on this. Before we can merge, please address the following:
Once these are fixed, the PR will be automatically evaluated again. Let us know if you need any help! |
|
CodeAnt AI Incremental review completed. |
There was a problem hiding this comment.
Actionable comments posted: 1
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@src/app/api/replies/route.ts`:
- Around line 66-67: Remove the unsafe type assertions and add explicit runtime
guards before calling eq(...) with membershipsTable.userEmail and
membershipsTable.classroomId: validate that email is a non-empty string and that
doubt.classroomId is a non-null number (doubt.classroomId) and return a proper
error/abort if they are missing/invalid; then pass the validated values into
eq(...) instead of using as string/number. Update the code paths that branch on
teacher vs student checks so both validate email and classroomId where used
(references: email, doubt.classroomId, eq(), membershipsTable.userEmail,
membershipsTable.classroomId) and keep behavior consistent with the other
membership checks that do not use type assertions.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 4c375515-0838-4ece-a551-aeeda971c26f
📒 Files selected for processing (3)
src/__tests__/api/doubts.test.tssrc/app/api/doubts/check-similarity/route.tssrc/app/api/replies/route.ts
💤 Files with no reviewable changes (1)
- src/tests/api/doubts.test.ts
🚧 Files skipped from review as they are similar to previous changes (1)
- src/app/api/doubts/check-similarity/route.ts
|
@knoxiboy check now |
|
Hi! This PR currently has merge conflicts with the main branch. Please rebase/merge main and resolve conflicts so we can review and merge it. Thank you! |
|
CodeAnt AI is running Incremental review |
|
@knoxiboy solved |
|
CodeAnt AI Incremental review completed. |
User description
Completed the semantic duplicate detection upgrade end-to-end (embeddings + pgvector + vector search + fallback).
What’s now implemented
Added migration: drizzle/0009_add_doubt_embeddings_pgvector.sql
enables vector extension
adds doubts.embedding vector(1536)
creates an HNSW cosine index
Updated: src/configs/schema.ts
added embedding: any() to doubtsTable
Added: src/lib/ai/embeddings.ts
safeGenerateEmbedding(text) uses Groq embeddings (nomic-embed-text)
findSemanticDuplicates(...) runs pgvector cosine similarity search
returns results in the same shape as the existing API, including solvedAnswer by fetching repliesTable for solved doubts
Updated: src/app/api/doubts/route.ts (POST)
after inserting newDoubt, it generates an embedding from:
subject + "\n" + content
persists it into doubts.embedding
fail-open: if embeddings fail, doubt creation still succeeds
Updated: src/app/api/doubts/check-similarity/route.ts (POST)
Primary path: findSemanticDuplicates (vector search across full history for the same scope: community + classroomId or null)
closes #534
Summary by CodeRabbit
New Features
Accessibility
UI/UX
Bug Fixes
Chores
CodeAnt-AI Description
Detect duplicate doubts using meaning, not just exact wording
What Changed
Impact
✅ Fewer duplicate doubt posts✅ Faster duplicate suggestions on submit✅ Clearer image upload for Ask AI💡 Usage Guide
Checking Your Pull Request
Every time you make a pull request, our system automatically looks through it. We check for security issues, mistakes in how you're setting up your infrastructure, and common code problems. We do this to make sure your changes are solid and won't cause any trouble later.
Talking to CodeAnt AI
Got a question or need a hand with something in your pull request? You can easily get in touch with CodeAnt AI right here. Just type the following in a comment on your pull request, and replace "Your question here" with whatever you want to ask:
This lets you have a chat with CodeAnt AI about your pull request, making it easier to understand and improve your code.
Example
Preserve Org Learnings with CodeAnt
You can record team preferences so CodeAnt AI applies them in future reviews. Reply directly to the specific CodeAnt AI suggestion (in the same thread) and replace "Your feedback here" with your input:
This helps CodeAnt AI learn and adapt to your team's coding style and standards.
Example
Retrigger review
Ask CodeAnt AI to review the PR again, by typing:
Check Your Repository Health
To analyze the health of your code repository, visit our dashboard at https://app.codeant.ai. This tool helps you identify potential issues and areas for improvement in your codebase, ensuring your repository maintains high standards of code health.