fix(security): fix SQL injection in the sample-listing sort parameter#286
Merged
Conversation
## [1.0.7-alpha.6](v1.0.7-alpha.5...v1.0.7-alpha.6) (2024-10-28) ### Bug Fixes * update notification action ([e9152c9](e9152c9))
## [1.0.7-alpha.7](v1.0.7-alpha.6...v1.0.7-alpha.7) (2024-10-28) ### Bug Fixes * update notification action ([046f47a](046f47a))
## [1.0.7-alpha.8](v1.0.7-alpha.7...v1.0.7-alpha.8) (2024-10-28) ### Bug Fixes * test notification action ([8fed078](8fed078))
## [1.0.7-alpha.9](v1.0.7-alpha.8...v1.0.7-alpha.9) (2024-10-28) ### Bug Fixes * test notification action ([851818e](851818e))
## [1.0.7-alpha.10](v1.0.7-alpha.9...v1.0.7-alpha.10) (2024-10-28) ### Bug Fixes * test notification action ([bc63ee5](bc63ee5))
## [1.0.7-alpha.11](v1.0.7-alpha.10...v1.0.7-alpha.11) (2024-10-28) ### Bug Fixes * test notification action ([83f43eb](83f43eb))
## [1.0.7-alpha.12](v1.0.7-alpha.11...v1.0.7-alpha.12) (2024-10-28) ### Bug Fixes * update notification action ([63286cb](63286cb))
## [1.0.9-alpha.1](v1.0.8...v1.0.9-alpha.1) (2024-10-28) ### Bug Fixes * test notification action ([83f43eb](83f43eb)) * test notification action ([bc63ee5](bc63ee5)) * test notification action ([851818e](851818e)) * test notification action ([8fed078](8fed078)) * update notification action ([63286cb](63286cb)) * update notification action ([046f47a](046f47a)) * update notification action ([e9152c9](e9152c9)) * update notification action ([04e0388](04e0388)) * update notification action ([b6abe17](b6abe17)) * Upgrade frontend to v5.3.0-alpha.4. See the details in [release notes](https://github.com/opendatalab/labelU-Kit/releases/tag/v5.3.0-alpha.4) ([01fc3b5](01fc3b5)) * Upgrade frontend to v5.3.0-alpha.5. See the details in [release notes](https://github.com/opendatalab/labelU-Kit/releases/tag/v5.3.0-alpha.5) ([f97601d](f97601d))
## [1.0.9-alpha.2](v1.0.9-alpha.1...v1.0.9-alpha.2) (2024-10-28) ### Bug Fixes * Upgrade frontend to v5.3.0-alpha.6. See the details in [release notes](https://github.com/opendatalab/labelU-Kit/releases/tag/v5.3.0-alpha.6) ([9f5e698](9f5e698))
## [1.0.9-alpha.3](v1.0.9-alpha.2...v1.0.9-alpha.3) (2024-10-28) ### Bug Fixes * Upgrade frontend to v5.3.0-alpha.7. See the details in [release notes](https://github.com/opendatalab/labelU-Kit/releases/tag/v5.3.0-alpha.7) ([7cb455e](7cb455e))
## [1.0.9-alpha.4](v1.0.9-alpha.3...v1.0.9-alpha.4) (2024-10-29) ### Bug Fixes * Upgrade frontend to v5.5.0-alpha.1. See the details in [release notes](https://github.com/opendatalab/labelU-Kit/releases/tag/v5.5.0-alpha.1) ([7b04670](7b04670)) * Upgrade frontend to v5.5.0-alpha.2. See the details in [release notes](https://github.com/opendatalab/labelU-Kit/releases/tag/v5.5.0-alpha.2) ([491cf33](491cf33))
## [1.0.9-alpha.5](v1.0.9-alpha.4...v1.0.9-alpha.5) (2024-10-30) ### Bug Fixes * Upgrade frontend to v5.5.0-alpha.3. See the details in [release notes](https://github.com/opendatalab/labelU-Kit/releases/tag/v5.5.0-alpha.3) ([dc022fd](dc022fd))
add pascal voc, yolo, tfrecord exporting format files
# [1.1.0-alpha.1](v1.0.9-alpha.5...v1.1.0-alpha.1) (2024-11-05) ### Bug Fixes * Upgrade frontend to v5.5.0-alpha.4. See the details in [release notes](https://github.com/opendatalab/labelU-Kit/releases/tag/v5.5.0-alpha.4) ([7622524](7622524)) ### Features * supports exporting "csv" format files ([d35a93a](d35a93a)) * supports exporting "labelme" format files ([8d4ea8e](8d4ea8e)) * supports exporting "pascal voc" format files ([4344f99](4344f99)) * supports exporting "tfrecord" format files ([f728fd6](f728fd6)) * supports exporting "xml" format files ([b165cce](b165cce)) * supports exporting "yolo" format files ([b3d07b4](b3d07b4))
fix: fix category name in pascal_voc and tfrecord format files
# [1.1.0-alpha.2](v1.1.0-alpha.1...v1.1.0-alpha.2) (2024-11-05) ### Bug Fixes * fix category name in pascal_voc and tfrecord format files ([b089074](b089074))
# [1.3.0-alpha.18](v1.3.0-alpha.17...v1.3.0-alpha.18) (2025-10-01) ### Bug Fixes * cli options ([2c42b7e](2c42b7e))
…nticated arbitrary file read)
_resolve only stripped leading slashes from the key; it neither handled
".." nor verified the resolved path stayed within MEDIA_ROOT. Because the
/api/v1/tasks/attachment/{path} and /partial/{path} download endpoints are
unauthenticated, an attacker could traverse with "../" to read any
process-readable file (e.g. labelu.sqlite, /etc/passwd).
_resolve now resolve()s both MEDIA_ROOT and the target and enforces
containment, raising 404 on escape. This covers read/write/delete/exists.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
…itrary file write) Attachment upload only sanitized the last path segment; the directory part "/".join(path_filename[:-1]) was kept verbatim and could contain "..", letting save_file -> _resolve -> shutil.move create files anywhere the process can write (potential RCE). Each directory segment is now sanitized the same way and "", "." and ".." segments are dropped. Legitimate subdirectories still work while traversal is neutralized; uploads always land under upload/<task_id>/. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
… (CWE-89) crud_sample.list_by interpolated the sort column/direction into an ORDER BY clause via a raw text() f-string, and the route pattern used an unanchored re.search that could be bypassed with "valid_col:dir,<injection>", letting an authenticated user blind-extract arbitrary data. Primary fix: the crud layer now maps allowed column names to real ORM columns, accepts only asc/desc, and skips anything else, removing the text() interpolation entirely. Defense in depth: the route pattern is anchored to ^(col:dir)(,col:dir)*$, rejecting injection at validation and closing the substring bypass while still allowing comma-separated multi-column sorts. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
CreateDataSourceCommand/UpdateDataSourceCommand only bounded the length of endpoint, and _build_s3_client passed it straight to boto3 as endpoint_url, so an authenticated user could point it at http://169.254.169.254 and other internal/metadata addresses, triggering outbound requests via list_objects/import_from_s3 (cloud IAM credential theft, internal scanning). The endpoint is now validated: only http(s) is allowed, and the host is resolved and rejected if it maps to a loopback/private/link-local/reserved/ multicast/unspecified address. Note: connection-time DNS-rebinding re-check (TOCTOU) is left as a follow-up defense-in-depth item. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Sample create/import/list/get/patch/delete and export create/status/download did not verify the caller could access the corresponding task, so any authenticated user could enumerate auto-increment IDs to read, modify or delete other users' annotation data, or download their export results. Adds access.assert_task_access(task, current_user) (owner or collaborator) and enforces it across the sample service and export endpoints; get/patch additionally verify sample.task_id matches the URL task to prevent referencing another user's sample through a task you own. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
task.update neither received current_user nor checked ownership (inconsistent with get/delete/collaborator management in the same file), so any authenticated user could PATCH and overwrite another user's task config/name/description/media_type. update now receives current_user and calls assert_task_access (owner or collaborator). Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Data source get/update/delete/list_objects and S3 import did not check ownership, so any authenticated user could read others' S3 configuration, tamper with/delete data sources, or use the victim's decrypted S3 credentials to list their private bucket or import objects. Adds access.assert_owner(resource, current_user) (owner-only; data sources have no collaborator concept) and enforces it on the four data source endpoints and in sample.import_from_s3 before the credentials are used; list_objects checks access before building the S3 client, preventing credential abuse. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Pre-annotation create/list/get/delete/delete_file already received current_user but never used it for authorization, so any authenticated user could read/inject/delete another task's pre-annotations (delete_file also physically removed the underlying files). All endpoints now call assert_task_access; get additionally verifies pre_annotation.task_id matches the URL task, and delete checks access for each pre-annotation's task. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The test suite persisted state across runs in two places: test.db was pinned to the cwd (so sqlite_sequence accumulated and task_ids kept growing) and MEDIA_ROOT pointed at the real appdirs data directory (~/Library/Application Support/labelu/media). Fresh task_ids collided with leftover upload/<task_id>/... files, intermittently failing uploads with a 400 "file already exists" (e.g. test_upload_file_with_hash_symbol). - Redirect both the sqlite test DB and MEDIA_ROOT into a per-run temp directory created at import time (the engine is built at module import, before any tmp_path/monkeypatch fixture could run); remove it at session end via the _hermetic_storage fixture. - Force STORAGE_BACKEND=local and clear the get_storage_backend lru_cache so it resolves against the new MEDIA_ROOT. - Seed the test user at session scope so it exists before the module-scoped login fixture (previously it survived only because test.db persisted across runs). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…bilities Make the test suite hermetic by isolating the sqlite test DB and media storage into a per-run temp directory, so tests no longer pollute the real appdirs data directory or the cwd and can be run repeatedly.
…loyments The SSRF guard rejected any endpoint resolving to a non-public address, which broke the common on-prem deployment backed by an internal MinIO/ S3-compatible store on a LAN or the same host. Adds ALLOW_PRIVATE_S3_ENDPOINT (default true): private (RFC1918/ULA) and loopback endpoints are permitted by default so internal deployments work out of the box, and can be locked down to public-only with a strict mode (set false). The cloud metadata endpoint (link-local 169.254.0.0/16, fe80::/10), multicast, reserved and unspecified addresses are ALWAYS rejected regardless of the flag, so the highest-impact SSRF (IAM credential theft) stays closed even in the permissive default. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
No description provided.