Skip to content

Validate name field at parse time to prevent path traversal via repos_dir().join(name) #162

@ooloth

Description

@ooloth

Why

A name value like ../../../tmp/evil in hub.toml is accepted as-is and then joined directly onto repos_dir(), silently writing repo contents outside ~/.hub/repos/.

Current state

config/src/toml.rs deserializes Project.name as a free-form String with no format validation. The value is consumed at workflows/src/fetch.rs:47 (repos_dir.join(name)) and workflows/src/implement.rs:166 (repos_dir().join(name)) without any sanitization. A value containing .. components or an absolute path would cause join to escape the intended repos directory — Path::join in Rust follows the OS rules and a segment like ../.. does traverse upward.

Ideal state

  • name is validated at TOML parse time to match only [a-zA-Z0-9_.-]+ (no /, no .., no absolute paths).
  • A hub.toml entry with an invalid name fails at config load with a clear error naming the offending value, before any filesystem operation runs.
  • repos_dir().join(name) always resolves to a path strictly inside ~/.hub/repos/.

Out of scope

Starting points

  • /config/src/toml.rs lines 11–19 — Project struct and name: String field, where validation should be added.
  • /workflows/src/fetch.rs:47repos_dir.join(name) call site.
  • /workflows/src/implement.rs:166repos_dir().join(name) call site.

QA plan

  1. Add a project entry to hub.toml with name = "../../../tmp/evil".
  2. Run hub fetch — expect a config validation error naming the invalid name, not a directory created outside ~/.hub/repos/.
  3. Confirm ~/.hub/repos/ contains no new directory and /tmp/evil does not exist.
  4. Add a project entry with name = "valid-project_1.0" — expect no error and normal clone behaviour.
  5. Add a project with name = "bad/slash" — expect a validation error at config load.

Done when

Project.name is rejected at TOML parse time for any value that contains /, .., or non-[a-zA-Z0-9_.-] characters, confirmed by the QA steps above producing a validation error rather than a filesystem side-effect.

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions