Skip to content

Provider permissions: source-path tagging on tool results #166

Description

@jeonghun-jj-lee

Important

Decision Surface

Problem: Tool results that return file content carry no metadata about where that content came from. Without source-path annotations, history redaction on model switch cannot know what to filter.

Approach: Annotate every file-content tool result with sourcePaths: string[] in its message metadata. Extend the message schema to carry this field. Tools that read files (Read, Glob content, Grep matches) tag their results.

Scope: Message schema extension + tagging in file-touching tools. No filtering logic (that is slices #5 and #6).


Acceptance Criteria

  • Message metadata schema includes an optional sourcePaths: string[] field
  • The Read tool annotates its result messages with the absolute path(s) read
  • The Grep tool annotates results with the file paths that contained matches
  • The Glob tool annotates results with matched file paths (when content is returned)
  • sourcePaths is persisted in the session message store (survives session reload)
  • Tools that do NOT return file content (bash output, webfetch) do NOT add spurious sourcePaths
  • Zero runtime cost when sourcePaths is not consumed (lazy — no extra work beyond the annotation)

Key Decisions

# Decision Rationale
1 Absolute paths in sourcePaths Glob matching in the resolution engine uses absolute paths; avoids ambiguity
2 Optional field (undefined when absent) Backward compatible — existing messages without it are treated as "unknown source"

Testing Decisions

  • Test Read tool result carries the correct sourcePath
  • Test Grep result carries all matched file paths
  • Test Glob result carries matched paths
  • Test bash tool result does NOT carry sourcePaths
  • Test sourcePaths persists across session save/load cycle

Constraints & Invariants

  • sourcePaths must be the canonical absolute path (resolved symlinks) to match permission globs correctly
  • Messages from before this feature (no sourcePaths) are treated as "source unknown" — they are NOT redacted on model switch (conservative: don't break existing sessions)

Source

Part of #163
Blocked by #164

Metadata

Metadata

Assignees

Labels

afkImplement + merge unattended

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions