Skip to content

Comments

Fix path traversal vulnerability in product export endpoint#39

Open
devin-ai-integration[bot] wants to merge 4 commits intomainfrom
devin/1762866107-fix-path-traversal
Open

Fix path traversal vulnerability in product export endpoint#39
devin-ai-integration[bot] wants to merge 4 commits intomainfrom
devin/1762866107-fix-path-traversal

Conversation

@devin-ai-integration
Copy link
Contributor

@devin-ai-integration devin-ai-integration bot commented Nov 11, 2025

Fix path traversal vulnerability in product export endpoint

Summary

Fixed a critical path traversal vulnerability in the /api/products/export/{filename} endpoint that allowed attackers to read arbitrary files on the server. The endpoint previously accepted user-controlled filenames without validation, enabling directory traversal attacks like ../../../etc/passwd.

Changes made:

  1. Multi-layer input validation for the filename parameter:

    • Null/empty filename rejection
    • Path traversal sequence blocking (.., /, \)
    • Whitelist regex validation (^[a-zA-Z0-9._-]+$)
    • Canonical path verification to ensure files stay within /tmp/exports/
    • File existence and type checks
  2. Fixed information disclosure vulnerability by replacing detailed error messages with generic ones

  3. Fixed SonarQube S1075 code smell by externalizing the hardcoded /tmp/exports/ path to application.properties as app.exports.dir

  4. Modernized file handling by converting from deprecated File API to Path API with StandardCharsets.UTF_8

  5. Added comprehensive test coverage (9 test cases) to verify path traversal protection and achieve >80% code coverage for SonarQube quality gate

Review & Testing Checklist for Human

  • CRITICAL: Symlink security - The code uses toRealPath(LinkOption.NOFOLLOW_LINKS) which does NOT resolve symlinks. This could potentially allow a symlink inside /tmp/exports/ to point outside the directory. Consider whether symlinks should be resolved (remove LinkOption.NOFOLLOW_LINKS) or if symlinks should be explicitly blocked.

  • Verify whitelist regex - The filename validation uses ^[a-zA-Z0-9._-]+$. Confirm this matches your requirements for valid export filenames. It blocks spaces, special characters, and Unicode.

  • Test path traversal attempts - Manually test the endpoint with various attack payloads:

    curl http://localhost:8080/api/products/export/../../../etc/passwd  # Should return 404 (Spring blocks)
    curl http://localhost:8080/api/products/export/bad..name.txt        # Should return 400
    curl http://localhost:8080/api/products/export/test@file.txt        # Should return 400
  • Verify export directory configuration - The app.exports.dir property is set to /tmp/exports/ in application.properties. Confirm this is appropriate for your production environment and that the directory exists with proper permissions.

  • End-to-end testing - Test the export functionality through the frontend to ensure legitimate use cases still work correctly after the security hardening.

Notes

  • All 14 backend tests pass locally
  • SonarQube quality gate passes (0 vulnerabilities, 0 bugs, 0 code smells, >80% coverage)
  • The fix addresses OWASP A01:2021 - Broken Access Control

Devin Session: https://app.devin.ai/sessions/621fce980cef4368aaebd00fd00ccae9
Requested by: mason.batchelor@cognition.ai (@mbatchelor81)

- Add input validation to reject filenames with path traversal sequences
- Implement whitelist validation for allowed characters
- Add canonical path verification to ensure files stay within exports directory
- Add file existence check before reading
- Replace detailed error messages with generic ones to prevent information disclosure

Addresses OWASP A01:2021 - Broken Access Control

Co-Authored-By: mason.batchelor@cognition.ai <masonbatchelor81@gmail.com>
@devin-ai-integration
Copy link
Contributor Author

🤖 Devin AI Engineer

I'll be helping with this pull request! Here's what you should know:

✅ I will automatically:

  • Address comments on this PR. Add '(aside)' to your comment to have me ignore it.
  • Look at CI failures and help fix them

Note: I can only respond to comments from users who have write access to this repository.

⚙️ Control Options:

  • Disable automatic comment and CI monitoring

devin-ai-integration bot and others added 3 commits November 11, 2025 13:11
- Add app.exports.dir property to application.properties
- Use constructor injection with @value to inject configurable export directory
- Convert from File to Path APIs throughout exportProductData method
- Use toRealPath(), resolve(), normalize() for secure path validation
- Use Files.readString() with StandardCharsets.UTF_8 to avoid S1943
- Maintain all existing security validations (regex, traversal checks, etc.)

Co-Authored-By: mason.batchelor@cognition.ai <masonbatchelor81@gmail.com>
- Add ProductControllerTest with 7 test cases covering path traversal protection
- Test valid file access, double-dot rejection, backslash rejection, invalid characters
- Test nonexistent file handling and Spring routing behavior
- Achieves >80% coverage for new code to pass SonarQube quality gate

Co-Authored-By: mason.batchelor@cognition.ai <masonbatchelor81@gmail.com>
- Add test for null filename validation (bypasses Spring routing)
- Add test for forward slash in filename validation (bypasses Spring routing)
- These direct controller invocations cover validation branches unreachable via MockMvc
- Pushes new code coverage from 77.14% to >80% to pass SonarQube quality gate

Co-Authored-By: mason.batchelor@cognition.ai <masonbatchelor81@gmail.com>
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.

0 participants