Cowork scheduled-tasks MCP: 3 issues with UNC/junction paths after storage migration
Preflight Checklist
- [x] I have searched existing issues and this hasn't been reported yet
- [x] This is a single bug report (please file separate reports for different bugs)
- [x] I am using the latest version of Claude Code
What's Wrong?
Summary
After migrating Cowork scheduled-tasks storage from OneDrive to a network share (Pi5 SMB) via an NTFS junction on 2026-05-04, three behaviors became visible in the scheduled-tasks MCP. Filing as one issue because they share root cause (path-handling around UNC and junctions); split if preferred.
Environment
- Cowork (Claude desktop app), latest stable as of 2026-05-22
- Windows 11, Cowork scheduled-tasks storage migrated to UNC path via NTFS junction
- Junction:
C:\Users\<user>\OneDrive\Documenten\Claude\Scheduled\→\\<host>\<share>\cowork-scheduled\ - Two task-population states coexist in
list_scheduled_tasks: - Pre-migration tasks (created before 2026-05-04): path-string still contains the junction parent (
C:\Users\...\OneDrive\...) but physical files live on the share - Post-migration tasks (created after 2026-05-04): path-string is the resolved UNC (
\\<host>\<share>\cowork-scheduled\<task>), because the cowork service runs as LocalSystem and cannot resolve a user-owned junction; it resolves to UNC on write
Bug 1 — No delete_scheduled_task tool
The MCP exposes create_scheduled_task, list_scheduled_tasks, and update_scheduled_task but no delete. The only way to remove a task is to delete the underlying SKILL.md from the filesystem, which then triggers Bug 3.
Expected: A delete_scheduled_task tool that removes both the file and the register entry atomically.
Actual: No delete tool; filesystem delete leaves a ghost in list_scheduled_tasks.
Bug 2 — update_scheduled_task fails with "path traversal detected" on UNC paths
Any task whose stored path begins with \\ (i.e. all post-migration tasks) cannot be updated via the MCP.
Repro:
- Create a task via
create_scheduled_taskwhile Cowork scheduled-storage is configured as a UNC path (directly, or via a junction whose target is UNC). - Inspect
list_scheduled_tasksand confirm the path string starts with\\. - Call
update_scheduled_taskon that task with any field change (e.g. cron expression). - Observe error: "path traversal detected".
Expected: UNC paths should be allowed; the leading \\ is part of standard Windows UNC syntax, not a traversal sequence.
Actual: The path validator appears to treat \\ as suspicious and rejects, making all post-migration tasks read-only via the MCP. Tasks with the junction-style path (pre-migration) remain updateable because the string starts with C:\.
Workaround used: Recreate the task (which overwrites the register entry). Inefficient for small changes such as a single cron-expression tweak.
Bug 3 — Filesystem delete of SKILL.md leaves a ghost in list_scheduled_tasks
After a manual filesystem delete of SKILL.md, the task continues to appear in list_scheduled_tasks with an empty description. For post-migration tasks (UNC path), the ghost is permanent because Bug 2 prevents setting enabled: false.
Expected: list_scheduled_tasks should reconcile against the filesystem and either omit orphaned register entries or surface them with an explicit orphaned: true flag so they can be ignored or cleaned up.
Actual: Ghost entries persist with no remediation path for UNC tasks.
Why these matter (use-case context)
We're building a local "expired one-time task cleanup" handler that detects ghosts based on fire-date < now and absence of corresponding SKILL.md. Because of Bug 2 and Bug 3, our handler can only clean the filesystem side; the register-side ghost is by-design unreachable from the MCP. Our handler therefore restricts itself to filesystem cleanup and surfaces register-ghosts as a digest warning. We'd prefer the MCP itself reconciled.
Suggested fix priorities (subjective)
- Bug 2 (path validator) — single behavioral change, unblocks Bug 3 workaround
- Bug 3 (orphan reconciliation) — improves correctness even when Bug 2 stands
- Bug 1 (delete tool) — nice-to-have once Bug 2 is fixed (delete via
update enabled:falsebecomes viable)
Happy to provide additional traces or path-string examples on request.
What Should Happen?
Each of the three issues described above has its own Expected/Actual section in the body. Compact summary:
delete_scheduled_tasktool should exist as a sibling of create/list/update.update_scheduled_taskshould accept paths starting with\\(valid Windows UNC syntax), not flag them as path traversal.list_scheduled_tasksshould reconcile against the filesystem — either omit orphaned register entries or surface them with an explicitorphaned: trueflag.
Error Messages/Logs
update_scheduled_task — error string returned by MCP:
"path traversal detected"
(User-facing error from the MCP response; no stack trace available at this layer. The leading `\\` of standard Windows UNC paths is being misclassified as a traversal sequence.)
Steps to Reproduce
Steps below reproduce Bug 2 (most concrete, deterministic). Bugs 1 and 3 are behavioral observations against the same MCP, fully described in the main body above.
Bug 2 reproduction:
- On Windows 11, configure Cowork scheduled-tasks storage as a path that resolves to UNC. This can be a direct UNC path, or an NTFS junction whose target is UNC. In our environment:
C:\Users\<user>\OneDrive\Documenten\Claude\Scheduled\is a junction with target\\<host>\<share>\cowork-scheduled\.
- Call
create_scheduled_taskvia the MCP with any valid task definition. Confirm it creates successfully.
- Call
list_scheduled_tasksand inspect the new task. Confirm itspathfield starts with\\(UNC). This happens because the cowork service runs as LocalSystem and cannot resolve a user-owned junction, so it stores the resolved UNC.
- Call
update_scheduled_taskon that task with any field change (e.g. change the cron expression).
- Observe: MCP returns error
"path traversal detected". Task remains unchanged.
Expected: update succeeds, just as it does for pre-migration tasks whose path string still begins with C:\.
Bugs 1 and 3 are observational (no error to capture) — see main body.
Claude Model
None
Is this a regression?
No, this never worked
Last Working Version
_No response_
Claude Code Version
2.1.146 (Claude Code)
Platform
Anthropic API
Operating System
Windows
Terminal/Shell
PowerShell
Additional Information
Context note for triager: this report is about the Cowork (Claude desktop app) scheduled-tasks MCP, not Claude Code CLI itself. Some template fields (Claude Code Version, Terminal/Shell, Regression status) are filled because the form requires them, but they aren't diagnostic for this bug — the issue lives in the MCP server's path-validation and register-reconciliation layers. If a more appropriate template or repo exists for Cowork MCP bugs, please redirect.
"Filing as one issue" (vs three separate) is deliberate: all three behaviors share a single root cause (path-handling around UNC paths and NTFS junctions on Windows after storage-relocation). Bug 3 (orphan reconciliation) is meaningfully harder to triage without Bug 2 (UNC validator) context, because Bug 2 is the reason workarounds for Bug 3 are unreachable. Happy to split into separate issues if you prefer — please let me know.
This issue has 3 comments on GitHub. Read the full discussion on GitHub ↗