Skip to content

Refactor request validation and parsing using utility functions#168

Open
Shweta-281 wants to merge 1 commit intoAOSSIE-Org:mainfrom
Shweta-281:fix/request-validation
Open

Refactor request validation and parsing using utility functions#168
Shweta-281 wants to merge 1 commit intoAOSSIE-Org:mainfrom
Shweta-281:fix/request-validation

Conversation

@Shweta-281
Copy link
Copy Markdown

@Shweta-281 Shweta-281 commented Mar 27, 2026

Addressed Issues:

Fixes #167

✨ Changes

  • Improved throwIfMissing utility to correctly handle falsy values
  • Added parseBody utility for safe JSON parsing
  • Refactored create-room function to:
    • Use centralized parsing and validation
    • Improve error handling
    • Standardize API response format

🧩 Problem Solved

  • Prevents crashes due to invalid JSON
  • Removes redundant parsing logic
  • Ensures consistent validation across functions

🚀 Impact

  • Improves backend reliability
  • Makes request handling more maintainable
  • Establishes a reusable validation pattern for future functions

AI Usage Disclosure:

We encourage contributors to use AI tools responsibly when creating Pull Requests. While AI can be a valuable aid, it is essential to ensure that your contributions meet the task requirements, build successfully, include relevant tests, and pass all linters. Submissions that do not meet these standards may be closed without warning to maintain the quality and integrity of the project. Please take the time to understand the changes you are proposing and their impact. AI slop is strongly discouraged and may lead to banning and blocking. Do not spam our repos with AI slop.

Check one of the checkboxes below:

  • This PR does not contain AI-generated code at all.
  • This PR contains AI-generated code. I have read the AI Usage Policy and this PR complies with this policy. I have tested the code locally and I am responsible for it.

I have used the following AI models and tools: TODO

Checklist

  • My PR addresses a single issue, fixes a single bug or makes a single improvement.
  • My code follows the project's code style and conventions
  • If applicable, I have made corresponding changes or additions to the documentation
  • If applicable, I have made corresponding changes or additions to tests
  • My changes generate no new warnings or errors
  • I have joined the Discord server and I will share a link to this PR with the project maintainers there
  • I have read the Contribution Guidelines
  • Once I submit my PR, CodeRabbit AI will automatically review it and I will address CodeRabbit's comments.
  • I have filled this PR template completely and carefully, and I understand that my PR may be closed without review otherwise.

Summary by CodeRabbit

  • Bug Fixes

    • Fixed non-awaited asynchronous operations in participant deletion, ensuring proper completion.
  • Improvements

    • Standardized error response format across all room management endpoints with structured JSON responses (success/message fields).
    • Enhanced request validation with clearer, categorized error messages.
    • Improved environment variable validation with explicit error handling.

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Mar 27, 2026

📝 Walkthrough

Walkthrough

This PR improves request validation and JSON parsing across backend functions by introducing a new parseBody utility and updating the throwIfMissing validator to correctly handle falsy values. The changes are applied to create-room, delete-room, join-room, and database-cleaner functions, standardizing error responses and adding centralized error handling.

Changes

Cohort / File(s) Summary
Utility Functions
functions/create-room/src/utils.js, functions/delete-room/src/utils.js, functions/join-room/src/utils.js, functions/database-cleaner/src/utils.js
Updated throwIfMissing to treat only undefined and null as missing (rather than all falsy values). Added new parseBody utility that validates request body is non-empty and performs JSON parsing with specific error messages for each failure case.
Create Room
functions/create-room/src/main.js
Integrated parseBody for request parsing, wrapped environment validation in try-catch with HTTP 500 error responses, standardized success/error response structure (success, message, data), and added tagged logging ([CREATE_ROOM_REQUEST], [ENV_ERROR], etc.).
Delete Room
functions/delete-room/src/main.js
Implemented parseBody for body validation, wrapped env var validation in try-catch, fixed participants deletion to use Promise.all instead of non-awaited forEach, standardized response shapes with success flag, and added error prefixing with [DELETE_ROOM_ERROR].
Database Cleaner
functions/database-cleaner/src/main.js
Destructured response/log utilities, wrapped environment validation in try-catch with JSON error responses (HTTP 500), added step-specific logging for cleanup operations ([CLEANUP_ERROR]), and changed final response to JSON format with success flag.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~23 minutes

Possibly related PRs

Suggested labels

enhancement

Poem

🐰 A rabbit hops through JSON streams,
Where undefined no longer dreams,
Of falsy tricks or parsing woes—
Now structured responses in neat prose!
Error handling blooms so bright,
Making backend requests just right! ✨

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The PR title accurately summarizes the main change: refactoring request validation and parsing using utility functions, which is the core objective.
Linked Issues check ✅ Passed The PR successfully addresses all primary requirements from #167: improved throwIfMissing to handle falsy values, added parseBody utility, refactored multiple functions (create-room, delete-room, join-room, database-cleaner), and standardized API response formats.
Out of Scope Changes check ✅ Passed All changes are directly aligned with #167 objectives. Updates to throwIfMissing, addition of parseBody, and refactoring of functions with standardized responses all address stated requirements with no unrelated modifications.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

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.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🧹 Nitpick comments (2)
functions/create-room/src/utils.js (1)

25-25: Minor: missing semicolon for consistency.

Other utils.js files end parseBody with a semicolon. Add one here for consistency.

-}
+};
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@functions/create-room/src/utils.js` at line 25, The file ends the parseBody
function without a trailing semicolon; update the closing brace of the parseBody
function in functions/create-room/src/utils.js (the parseBody function) to
include a semicolon for consistency with other utils.js files.
functions/delete-room/src/utils.js (1)

1-25: Code duplication: identical utilities copied across 4 files.

The throwIfMissing and parseBody functions are duplicated verbatim in:

  • functions/delete-room/src/utils.js
  • functions/join-room/src/utils.js
  • functions/database-cleaner/src/utils.js
  • functions/create-room/src/utils.js

Consider extracting these to a shared module (e.g., functions/shared/utils.js or a workspace package) to avoid maintaining identical code in multiple places.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@functions/delete-room/src/utils.js` around lines 1 - 25, The utilities
throwIfMissing and parseBody are duplicated across four function packages;
extract them into a single shared module (e.g., functions/shared/utils.js or a
workspace package) and replace the local copies with imports from that shared
module in delete-room, join-room, database-cleaner, and create-room; ensure the
shared file exports throwIfMissing and parseBody with identical behavior and
update all imports/usages (functions named throwIfMissing and parseBody) so
tests/build use the single source of truth and remove the duplicate files.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@functions/database-cleaner/src/main.js`:
- Around line 29-34: cleanParticipantsCollection currently uses
participantDocs.documents.forEach with async callbacks so individual deletion
errors don't propagate and the try/catch around its caller won't catch failures;
refactor the async forEach into a Promise array (map participantDocs.documents
to deletion promises) and await Promise.all on that array inside
cleanParticipantsCollection (similar to the other cleanup methods), and only
resolve/return after all deletions complete so the caller's try/catch and the
success log in the caller reflect actual outcome.
- Around line 52-55: Change the unconditional success response to return an
aggregated result: during each cleanup phase push any caught error messages into
an errors array (instead of only logging), compute success = errors.length ===
0, and then call res.json with success, a message that reflects full/partial
success (e.g., "Database cleanup completed" vs "Completed with errors"), and
include the errors array (or error count) alongside the existing "expired OTPs
cleared" info; update the code path that currently calls res.json({ success:
true, message: "Database cleanup completed and expired OTPs cleared" }) to use
these aggregated values.

In `@functions/database-cleaner/src/utils.js`:
- Around line 15-25: Remove the unused parseBody export from utils.js: locate
the parseBody function declaration and export (function name parseBody) and
delete the entire function block and its export so it's no longer part of the
module's public API; ensure no other code references parseBody (remove any
leftover imports/usages if present) and run tests/lint to confirm no missing
symbols remain.

---

Nitpick comments:
In `@functions/create-room/src/utils.js`:
- Line 25: The file ends the parseBody function without a trailing semicolon;
update the closing brace of the parseBody function in
functions/create-room/src/utils.js (the parseBody function) to include a
semicolon for consistency with other utils.js files.

In `@functions/delete-room/src/utils.js`:
- Around line 1-25: The utilities throwIfMissing and parseBody are duplicated
across four function packages; extract them into a single shared module (e.g.,
functions/shared/utils.js or a workspace package) and replace the local copies
with imports from that shared module in delete-room, join-room,
database-cleaner, and create-room; ensure the shared file exports throwIfMissing
and parseBody with identical behavior and update all imports/usages (functions
named throwIfMissing and parseBody) so tests/build use the single source of
truth and remove the duplicate files.
🪄 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: defaults

Review profile: CHILL

Plan: Pro

Run ID: ad19a469-ad8e-4ad3-8e74-c6e76df1124d

📥 Commits

Reviewing files that changed from the base of the PR and between 795f29b and 7ea25a9.

📒 Files selected for processing (7)
  • functions/create-room/src/main.js
  • functions/create-room/src/utils.js
  • functions/database-cleaner/src/main.js
  • functions/database-cleaner/src/utils.js
  • functions/delete-room/src/main.js
  • functions/delete-room/src/utils.js
  • functions/join-room/src/utils.js

Comment on lines 29 to 34
try {
await appwrite.cleanParticipantsCollection();
log("[CLEANUP] Participants collection cleaned");
} catch (e) {
context.error(String(e));
error("[CLEANUP_ERROR] Participants: " + String(e));
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Try/catch ineffective for cleanParticipantsCollection errors.

Per the relevant code snippet at functions/database-cleaner/src/appwrite.js:31-46, cleanParticipantsCollection uses forEach with async callbacks:

participantDocs.documents.forEach(async (participantDoc) => {
    // errors here won't propagate to the caller
});

Errors from individual document deletions won't propagate to this try/catch, and the success log on line 31 will print even if deletions fail silently. Consider refactoring cleanParticipantsCollection to use Promise.all like the other cleanup methods.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@functions/database-cleaner/src/main.js` around lines 29 - 34,
cleanParticipantsCollection currently uses participantDocs.documents.forEach
with async callbacks so individual deletion errors don't propagate and the
try/catch around its caller won't catch failures; refactor the async forEach
into a Promise array (map participantDocs.documents to deletion promises) and
await Promise.all on that array inside cleanParticipantsCollection (similar to
the other cleanup methods), and only resolve/return after all deletions complete
so the caller's try/catch and the success log in the caller reflect actual
outcome.

Comment on lines +52 to +55
return res.json({
success: true,
message: "Database cleanup completed and expired OTPs cleared",
});
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Success response returned even when individual cleanup steps fail.

The function returns success: true unconditionally, even if one or more cleanup phases encountered errors (logged but swallowed). Consider tracking failures and returning a partial success indicator or including error details in the response.

💡 Suggested approach
+    const errors = [];
+
     // Cleanup Participants
     try {
         await appwrite.cleanParticipantsCollection();
         log("[CLEANUP] Participants collection cleaned");
     } catch (e) {
         error("[CLEANUP_ERROR] Participants: " + String(e));
+        errors.push("Participants");
     }
     // ... similar for other phases
 
     return res.json({
-        success: true,
+        success: errors.length === 0,
         message: "Database cleanup completed and expired OTPs cleared",
+        ...(errors.length > 0 && { failedPhases: errors }),
     });
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@functions/database-cleaner/src/main.js` around lines 52 - 55, Change the
unconditional success response to return an aggregated result: during each
cleanup phase push any caught error messages into an errors array (instead of
only logging), compute success = errors.length === 0, and then call res.json
with success, a message that reflects full/partial success (e.g., "Database
cleanup completed" vs "Completed with errors"), and include the errors array (or
error count) alongside the existing "expired OTPs cleared" info; update the code
path that currently calls res.json({ success: true, message: "Database cleanup
completed and expired OTPs cleared" }) to use these aggregated values.

Comment on lines +15 to +25
export const parseBody = (body) => {
if (!body) {
throw new Error("Request body is empty");
}

try {
return JSON.parse(body);
} catch (err) {
throw new Error("Invalid JSON body");
}
};
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Check if parseBody is imported/used in database-cleaner/main.js
rg -n "parseBody" functions/database-cleaner/src/

Repository: AOSSIE-Org/Resonate-Backend

Length of output: 150


🏁 Script executed:

# Check imports and usage of parseBody in database-cleaner main.js
rg -n "parseBody\|import.*parseBody" functions/database-cleaner/src/main.js

Repository: AOSSIE-Org/Resonate-Backend

Length of output: 53


🏁 Script executed:

# Check the main.js file to understand what the database-cleaner function does
cat -n functions/database-cleaner/src/main.js

Repository: AOSSIE-Org/Resonate-Backend

Length of output: 1991


🏁 Script executed:

# Verify if parseBody is called anywhere within utils.js itself
rg -n "parseBody(" functions/database-cleaner/src/utils.js

Repository: AOSSIE-Org/Resonate-Backend

Length of output: 141


🏁 Script executed:

# Check if parseBody is called within utils.js (fixing regex)
rg -n "parseBody\s*\(" functions/database-cleaner/src/utils.js

Repository: AOSSIE-Org/Resonate-Backend

Length of output: 53


🏁 Script executed:

# Also check the full utils.js to see what functions are defined and exported
cat -n functions/database-cleaner/src/utils.js

Repository: AOSSIE-Org/Resonate-Backend

Length of output: 1110


Remove unused parseBody function.

The parseBody export at lines 15-25 is never imported or used in this module. Since database-cleaner is a scheduled cleanup function that doesn't parse HTTP request bodies, this function is dead code and should be removed.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@functions/database-cleaner/src/utils.js` around lines 15 - 25, Remove the
unused parseBody export from utils.js: locate the parseBody function declaration
and export (function name parseBody) and delete the entire function block and
its export so it's no longer part of the module's public API; ensure no other
code references parseBody (remove any leftover imports/usages if present) and
run tests/lint to confirm no missing symbols remain.

@Shweta-281
Copy link
Copy Markdown
Author

Hi 👋 @M4dhav

I’ve worked on improving request validation and JSON parsing across backend functions.

Key Improvements:

  • Fixed validation logic in throwIfMissing to correctly handle falsy values like 0 and false
  • Added a reusable parseBody utility for safe JSON parsing
  • Refactored the following functions:
    • create-room
    • join-room
    • delete-room
  • Standardized API responses (success, message, data)
  • Improved structured logging for better debugging
  • Fixed async issue in participant deletion using Promise.all

These changes aim to improve backend reliability and prevent runtime errors due to invalid input.

Would love your feedback and suggestions 🙌

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[BUG]: Improve request validation and JSON parsing across backend functions

1 participant