🛡️ Sentinel: [CRITICAL] Fix Path Traversal Vulnerability in TypeScript Extractor#274
🛡️ Sentinel: [CRITICAL] Fix Path Traversal Vulnerability in TypeScript Extractor#274bashandbone wants to merge 1 commit into
Conversation
…t Extractor Co-authored-by: bashandbone <89049923+bashandbone@users.noreply.github.com>
|
👋 Jules, reporting for duty! I'm here to lend a hand with this pull request. When you start a review, I'll add a 👀 emoji to each comment to let you know I've read it. I'll focus on feedback directed at me and will do my best to stay out of conversations between you and other bots or reviewers to keep the noise down. I'll push a commit with your requested changes shortly after. Please note there might be a delay between these steps, but rest assured I'm on the job! For more direct control, you can switch me to Reactive Mode. When this mode is on, I will only act on comments where you specifically mention me with New to Jules? Learn more at jules.google/docs. For security, I will only act on instructions from the user who triggered this task. |
Reviewer's guide (collapsed on small PRs)Reviewer's GuideFixes a critical path traversal vulnerability in the TypeScript dependency extractor by hardening manual path normalization behavior and adds a Sentinel journal entry documenting the issue and its prevention. Flow diagram for updated ParentDir handling in manual path normalizationflowchart TD
A[Iterate resolved.components] --> B{component is ParentDir?}
B -- no --> C[components.push component]
C --> A
B -- yes --> D{components.is_empty or components.last is ParentDir?}
D -- yes --> E[components.push ParentDir]
E --> A
D -- no --> F{components.last is RootDir or Prefix?}
F -- yes --> G[[Ignore ParentDir]]
G --> A
F -- no --> H[components.pop]
H --> A
File-Level Changes
Tips and commandsInteracting with Sourcery
Customizing Your ExperienceAccess your dashboard to:
Getting Help
|
There was a problem hiding this comment.
Hey - I've left some high level feedback:
- The new
ParentDirhandling logic is subtle; consider extracting it into a small helper function (e.g.,normalize_parent_dir_component) or adding a short inline comment describing the intended invariants (when to push vs. ignore vs. pop) to make future maintenance and security review easier.
Prompt for AI Agents
Please address the comments from this code review:
## Overall Comments
- The new `ParentDir` handling logic is subtle; consider extracting it into a small helper function (e.g., `normalize_parent_dir_component`) or adding a short inline comment describing the intended invariants (when to push vs. ignore vs. pop) to make future maintenance and security review easier.Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.
There was a problem hiding this comment.
Pull request overview
Hardens the TypeScript/JavaScript dependency extractor’s fallback path normalization (when canonicalize() fails) to prevent .. segments from popping past RootDir/Prefix, avoiding incorrect normalization that could enable path traversal behaviors. Also adds a Sentinel journal entry documenting the vulnerability and mitigation.
Changes:
- Update manual
.components()normalization to avoid poppingRootDir/Prefixand to preserve leading..for inherently-relative paths. - Add a Sentinel journal entry describing the path traversal issue and safe normalization rules.
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
crates/flow/src/incremental/extractors/typescript.rs |
Hardens manual ParentDir handling during fallback normalization to prevent popping above root/prefix. |
.jules/sentinel.md |
Documents the vulnerability, root cause, and prevention guidance in Sentinel notes. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| @@ -0,0 +1,4 @@ | |||
| ## 2024-05-30 - Path Traversal in Manual Path Normalization | |||
| std::path::Component::ParentDir => { | ||
| components.pop(); | ||
| if components.is_empty() || components.last() == Some(&std::path::Component::ParentDir) { | ||
| components.push(std::path::Component::ParentDir); | ||
| } else if let Some(last) = components.last() { | ||
| match last { |
🚨 Severity: CRITICAL
💡 Vulnerability: A path traversal vulnerability existed in the manual path normalization logic (
.components()) of the TypeScript module extractor (crates/flow/src/incremental/extractors/typescript.rs). When thecanonicalizefallback was triggered, the manual implementation simply calledpop()on encountering a..(ParentDir) component. This allowed malicious import paths with excessive../components to strip root (/) or prefix boundaries and inadvertently turn into relative paths or bypass intended base path confinement.🎯 Impact: If an attacker controls or injects module specifiers, they could theoretically escape the intended analysis directory, causing the engine to resolve, read, and process arbitrary files on the host filesystem that the process has access to, leading to information disclosure.
🔧 Fix: Implemented robust and secure manual path normalization. The fix prevents popping when at the root or prefix (
RootDir,Prefix) and ensures thatParentDiris correctly accumulated (push) if the resolved path is inherently relative and already walking up the tree, strictly imitating the safe behavior ofcanonicalize.✅ Verification:
cargo test -p thread-flow --test extractor_typescript_testspasses seamlessly without regressions.PR created automatically by Jules for task 12719017417937973642 started by @bashandbone
Summary by Sourcery
Harden TypeScript dependency extractor path normalization to prevent path traversal beyond the intended root and document the vulnerability and its mitigation in Sentinel notes.
Bug Fixes:
Documentation: