T05 · Unauthorized Access and Privilege Escalation
- Location
scripts/profile_extractor.py:87- Finding
Workspace Memory Is Scanned Without Programmatic Consent Enforcement
- Content
View full analysis
Vulnerability Details
File Location:
scripts/profile_extractor.py:87-100, 110-145;scripts/build_application_plan.py:49-55
Vulnerability Type: Missing authorization enforcement for sensitive workspace data
Risk Level: MediumVulnerable Code
python def collect_text_sources(workspace: Path) -> List[tuple[str, str]]: files: List[tuple[str, str]] = [] for rel in ('USER.md', 'MEMORY.md'): p = workspace / rel if p.exists(): files.append((rel, scan_text_file(p))) mem_dir = workspace / 'memory' if mem_dir.exists(): for p in sorted(mem_dir.glob('*.md')): files.append((str(p.relative_to(workspace)), scan_text_file(p))) return filespython def build_candidates(workspace: Path) -> List[Candidate]: candidates: List[Candidate] = [] json_profile = load_json_profile(workspace) # Structured JSON is preferred and can include high-sensitivity fields explicitly provided by the user. for field, value in json_profile.items(): if value in ('', None, [], {}): continue if field.startswith('consent_') or field == 'notes': continue if isinstance(value, (list, dict, bool, int, float)): value_str = json.dumps(value, ensure_ascii=False) else: value_str = str(value) candidates.append(Candidate( field=field, value=value_str, source='profiles/applicant_profile.json or template', confidence='high', masked_preview=mask_value(field, value_str), )) existing_fields = {c.field for c in candidates} for source_name, text in collect_text_sources(workspace): for field in FIELD_PATTERNS: if field in existing_fields: continue extracted = extract_from_text(field, text) if extract ...[truncated 3171 chars]- Remediation
View remediation
Remediation Suggestions
- Make memory access disabled by default and require an explicit option such as
--include-memory. - Require a separate, auditable consent value rather than inferring consent from invocation alone.
- Pass authorization into
build_candidates(), for example:python def build_candidates( workspace: Path, include_memory: bool = False, approved_sources: Optional[List[Path]] = None, ) -> List[Candidate]: - Do not call
collect_text_sources()unlessinclude_memoryis explicitly true. - Require the caller to identify individually approved files instead of scanning all
memory/*.md. - Make
build_application_plan.pyfail closed unless the required consent option is supplied. - Keep browser-prefill consent separate from permission to read memory; authorization for one action must not imply authorization for the other.
- Record which sources were authorized and display that list before extraction begins.
- Add tests proving that the default invocation never opens
USER.md,MEMORY.md, ormemory/*.md.
- Make memory access disabled by default and require an explicit option such as
