Conversation
|
Note Other AI code review bot(s) detectedCodeRabbit has detected other AI code review bot(s) in this pull request and will avoid duplicating their findings in the review comments. This may lead to a less comprehensive review. 📝 WalkthroughWalkthroughAdds a new project "labels" attribute (VAR_STRING, size 128, array, default []) to the projects collection and initializes it on project creation. Introduces an HTTP action class to update project labels via PUT /v1/projects/:projectId/labels with validation and persistence. Registers the new action in the Projects HTTP service. Updates query validation to allow filtering by "labels". Extends the Project response model to include the "labels" field. Adds end-to-end tests covering label creation, updates, and label-based querying across projects. Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutes Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✨ Finishing touches
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 |
Security Scan Results for PRDocker Image Scan Results
Source Code Scan Results🎉 No vulnerabilities found! |
There was a problem hiding this comment.
Pull request overview
This PR adds a labels feature to projects, enabling easier filtering and organization of projects within the Appwrite platform. The implementation includes database schema updates, API endpoints for managing labels, and comprehensive test coverage.
Key Changes:
- Added a
labelsarray field to the projects collection schema - Implemented a new API endpoint (
PUT /v1/projects/:projectId/labels) to update project labels - Extended the project query validator to support filtering by labels
Reviewed changes
Copilot reviewed 7 out of 7 changed files in this pull request and generated 10 comments.
Show a summary per file
| File | Description |
|---|---|
app/config/collections/platform.php |
Adds labels field to the projects collection schema as a string array |
app/controllers/api/projects.php |
Initializes the labels field as an empty array during project creation |
src/Appwrite/Utopia/Response/Model/Project.php |
Adds labels to the Project response model definition |
src/Appwrite/Utopia/Database/Validator/Queries/Projects.php |
Adds labels to the allowed queryable attributes for projects |
src/Appwrite/Platform/Modules/Projects/Services/Http.php |
Registers the new UpdateProjectLabels action in the HTTP service |
src/Appwrite/Platform/Modules/Projects/Http/Projects/Labels/Update.php |
Implements the update labels endpoint with validation and business logic |
tests/e2e/Services/Projects/ProjectsConsoleClientTest.php |
Adds comprehensive end-to-end tests for the labels functionality including filtering scenarios |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
There was a problem hiding this comment.
Actionable comments posted: 2
🧹 Nitpick comments (4)
app/config/collections/platform.php (1)
334-344: Consider default value and index for the labels field.Two observations:
Default value inconsistency: The default is set to
null, but the controller initializes it as[](line 207 inapp/controllers/api/projects.php). Consider changing the default to[]for consistency.Missing index: The labels field is included in
ALLOWED_ATTRIBUTESfor queries (seesrc/Appwrite/Utopia/Database/Validator/Queries/Projects.php), but there's no index defined. If filtering/querying by labels is expected to be common, consider adding an index to improve performance.🔎 Proposed fix for default value
[ '$id' => ID::custom('labels'), 'type' => Database::VAR_STRING, 'format' => '', 'size' => 128, 'signed' => true, 'required' => false, - 'default' => null, + 'default' => [], 'array' => true, 'filters' => [], ],Note: For the index consideration, verify whether array field indexes are supported and beneficial in your database configuration before adding one.
tests/e2e/Services/Projects/ProjectsConsoleClientTest.php (1)
5492-5589: Minor test hygiene: second project cleanup and misleading comment
- The comment
// Setup: Second project with only imagine labeldoesn’t match the data; project 2 gets['vip', 'imagine'].- The test deletes only
$projectIdand the team, but leaves$projectId2around. In this suite, extra projects may affect tests that rely on global counts / ordering.Consider:
- Updating the comment to reflect actual labels, and
- Deleting
$projectId2as part of the cleanup to keep the test self-contained.src/Appwrite/Platform/Modules/Projects/Http/Projects/Labels/Update.php (2)
24-32: Add return type togetName()for consistency with other actions
getName()currently has no return type hint. To keep this aligned with typical Action implementations and avoid potential signature mismatches with the base class/interface, it’s safer to declare: string.Also, since
getQueriesValidator()returns aProjectsvalidator but the action doesn’t acceptqueries, this override is effectively unused today. That’s fine, but if the base Action doesn’t expect queries here, you could drop it to reduce noise.If the base
Action(or an interface it implements) already definespublic static function getName(): string, please update this method signature accordingly:public static function getName(): string { return 'updateProjectLabels'; }Please verify against the current
Actiondefinition in your codebase.
59-82: Label validation and normalization considerationsThe labels param is well-constrained (max count via
APP_LIMIT_ARRAY_LABELS_SIZE, per-label length 36, alphanumeric only). The action also de-duplicates labels viaarray_unique.If you want stricter consistency over time, you might also consider:
- Trimming whitespace from each label before validation.
- Normalizing case (e.g., lowercasing) so
VIPandviparen’t treated as distinct.Not strictly required for correctness, but improves long-term data hygiene and query predictability.
If you decide to normalize, confirm with product/API docs that label matching is intended to be case-insensitive before changing behavior.
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (7)
app/config/collections/platform.phpapp/controllers/api/projects.phpsrc/Appwrite/Platform/Modules/Projects/Http/Projects/Labels/Update.phpsrc/Appwrite/Platform/Modules/Projects/Services/Http.phpsrc/Appwrite/Utopia/Database/Validator/Queries/Projects.phpsrc/Appwrite/Utopia/Response/Model/Project.phptests/e2e/Services/Projects/ProjectsConsoleClientTest.php
🧰 Additional context used
🧬 Code graph analysis (4)
src/Appwrite/Utopia/Response/Model/Project.php (1)
src/Appwrite/Utopia/Response/Model.php (1)
addRule(90-102)
src/Appwrite/Platform/Modules/Projects/Http/Projects/Labels/Update.php (2)
src/Appwrite/Utopia/Database/Validator/Queries/Projects.php (2)
Projects(5-26)__construct(17-20)src/Appwrite/Utopia/Response/Model/Project.php (1)
__construct(17-322)
src/Appwrite/Platform/Modules/Projects/Services/Http.php (1)
src/Appwrite/Platform/Modules/Projects/Http/Projects/Labels/Update.php (2)
Update(20-86)getName(24-27)
tests/e2e/Services/Projects/ProjectsConsoleClientTest.php (4)
tests/e2e/Client.php (1)
Client(8-342)src/Appwrite/Event/Event.php (1)
getProject(153-156)tests/e2e/Scopes/ProjectCustom.php (1)
getProject(21-184)tests/e2e/Scopes/Scope.php (2)
getProject(150-150)getHeaders(145-145)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (4)
- GitHub Check: Agent
- GitHub Check: Setup & Build Appwrite Image
- GitHub Check: Setup & Build Appwrite Image
- GitHub Check: scan
🔇 Additional comments (3)
src/Appwrite/Platform/Modules/Projects/Services/Http.php (1)
10-10: LGTM!The import and registration of the
UpdateProjectLabelsaction follow the established patterns in this service.Also applies to: 26-26
src/Appwrite/Utopia/Database/Validator/Queries/Projects.php (1)
9-10: LGTM!Adding 'labels' to the allowed query attributes is correct and enables filtering projects by labels.
src/Appwrite/Utopia/Response/Model/Project.php (1)
279-285: Project model labels field looks consistentThe new
labelsrule (string, array, default[]) matches the intended usage in the API and tests and integrates cleanly with the existing model.
✨ Benchmark results
⚡ Benchmark Comparison
|
There was a problem hiding this comment.
Actionable comments posted: 0
🧹 Nitpick comments (1)
tests/e2e/Services/Projects/ProjectsConsoleClientTest.php (1)
5416-5442: Good coverage of label operations.The test validates both applying initial labels and updating them. The assertions properly check array structure, count, and individual values. Note that the test assumes label order is preserved (lines 5427-5429, 5440-5441), which is appropriate if order preservation is part of the API contract.
Consider adding test cases for edge cases and failure scenarios, such as:
- Empty labels array (might already be covered by default state)
- Invalid label values (if any constraints exist)
- Duplicate labels in input
- Maximum label array size (if any limit exists)
These could help ensure robustness, though they may be covered in other test files.
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (2)
app/config/collections/platform.phptests/e2e/Services/Projects/ProjectsConsoleClientTest.php
🚧 Files skipped from review as they are similar to previous changes (1)
- app/config/collections/platform.php
🧰 Additional context used
🧬 Code graph analysis (1)
tests/e2e/Services/Projects/ProjectsConsoleClientTest.php (4)
tests/e2e/Client.php (1)
Client(8-342)src/Appwrite/Event/Event.php (1)
getProject(153-156)tests/e2e/Scopes/ProjectCustom.php (1)
getProject(21-184)tests/e2e/Scopes/Scope.php (1)
getProject(150-150)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (20)
- GitHub Check: E2E Service Test (Teams)
- GitHub Check: E2E Service Test (Users)
- GitHub Check: E2E Service Test (Proxy)
- GitHub Check: E2E Service Test (Avatars)
- GitHub Check: E2E Service Test (Storage)
- GitHub Check: E2E Service Test (Health)
- GitHub Check: E2E Service Test (Locale)
- GitHub Check: E2E Service Test (Tokens)
- GitHub Check: E2E Service Test (Functions)
- GitHub Check: E2E Service Test (Sites)
- GitHub Check: E2E Service Test (Projects)
- GitHub Check: E2E Service Test (Databases/Legacy)
- GitHub Check: E2E Service Test (Console)
- GitHub Check: E2E Service Test (Databases/TablesDB)
- GitHub Check: E2E Service Test (Site Screenshots)
- GitHub Check: E2E General Test
- GitHub Check: Unit Test
- GitHub Check: E2E Service Test (Dev Keys)
- GitHub Check: Benchmark
- GitHub Check: scan
🔇 Additional comments (4)
tests/e2e/Services/Projects/ProjectsConsoleClientTest.php (4)
5388-5414: LGTM! Well-structured test setup.The setup properly creates a team and project, and validates that the
labelsfield is initialized as an empty array. This provides a clean starting point for the label operations testing.
5444-5490: Excellent! Status-code assertions now reference the correct variable.All filtering queries correctly use
$projects['headers']['status-code']instead of the previous incorrect$project['headers']['status-code']. This resolves the issue flagged in past reviews where assertions were validating the wrong response.The filtering tests properly cover:
- Single label queries (lines 5450, 5462, 5473)
- OR operation using
Query::contains('labels', ['nonvip', 'imagine'])(line 5485)
5492-5573: Comprehensive cross-project filtering tests.The test properly validates filtering behavior across multiple projects and distinguishes between AND and OR operations:
- Lines 5553-5554: Multiple
Query::contains()calls implement AND logic (must match all)- Line 5567: Single
Query::contains()with array implements OR logic (match any)The assertions correctly use
$projectsvariable throughout, and the expected results properly validate the filtering logic.
5575-5595: Proper cleanup now includes both projects!The cleanup correctly deletes both
projectIdandprojectId2before removing the team. This resolves the past review concern about the second project not being cleaned up.The cleanup order (projects → team) is appropriate since projects belong to the team.
What does this PR do?
Adds labels to projects for ease filtering
Test Plan
(Write your test plan here. If you changed any code, please provide us with clear instructions on how you verified your changes work. Screenshots may also be helpful.)
Related PRs and Issues
x
Checklist