Skip to content

make pstack fully droid compatible - #47

Merged
caelaxie merged 1 commit into
mainfrom
droid-compat
Oct 30, 2026
Merged

caelaxie merged 1 commit into
mainfrom
droid-compat

Conversation

@caelaxie

Copy link
Copy Markdown
Contributor

Why

The installed plugin loaded cleanly, but several skills still assumed Cursor behavior that Droid does not have. On Droid a subagent has no Task tool. Every Task call already runs in the background. Droid also ignores skill frontmatter keys outside its schema. Each fix below follows from one of those facts. I checked them against the Droid CLI binary and against live worker and explorer subagents.

This PR also adds COMPATIBILITY.md. It maps every change the Cursor plugin needs to run on Droid and lists the invariants future ports must keep. The validator now enforces the ones a script can check, so CI catches a regression.

What changed

  • No nested spawns. comment-sicko traces claims itself instead of running /how or /why. no-comments and show-me-your-work have an in-subagent path, so Autopilot owners can run them. poteto-mode says every spawn stays in the main chat. The orchestrate sub-coordinator came back in the 0.15.36 port and is removed again, as Drop the orchestrate sub-coordinator #28 did.
  • comment-sicko can edit. It was tools: read-only, so it could not delete the comments it is spawned to delete. Upstream sets no tool restriction.
  • No run_in_background. The field is removed from poteto-mode, arena, swarm, orchestrate, autopilot-full, shipping, and the guide.
  • Script paths. Multi-phase plan ran node skills/poteto-mode/scripts/check-plan.mjs, a path that only exists inside this repository. Script paths are now relative to the skill directory, and poteto-mode states that rule.
  • typescript-best-practices. Droid drops the Cursor paths glob, so the skill never turned on. The description now routes it.
  • Guardrails. scripts/validate-plugin.mjs checks skill and droid frontmatter against Droid's key allowlists. It also rejects Cursor-only tokens: run_in_background, AskQuestion, generalPurpose, .cursor/ paths, .cursor-plugin, is_background, node skills/, and sub-coordinator. AGENTS.md points agents at COMPATIBILITY.md.

Scope

  • icon and color stay on poteto-mode (restore poteto-mode icon and color #38). Droid ignores them, and the validator allows them.
  • Seat droid defaults (grok-4.7 and claude-opus-5-5 at xhigh) are unchanged. Both models and the effort level are valid in the current CLI.

Blast Radius

The changes are prose in skills, two droid frontmatter edits, and validator rules. A delegate that used to try a nested spawn now does the work inline. Inline work is a weaker check than a fresh reviewer, and each fallback says so. typescript-best-practices now appears in the model's skill catalog.

Verification

  • I ran node scripts/validate-plugin.mjs on this branch: OK (61 skills, 5 droids). I also ran it with skills/, droids/, and docs/ restored from main. It fails on every issue this PR fixes.
  • In skills/poteto-mode/scripts, bun run typecheck passes and bun run test reports 61 pass, 0 fail. bash -n passes on both shell scripts.
  • Live probes: a worker subagent and an explorer subagent both report no Task tool. worker has Loop, Edit, and Create.

Fix the places where the port still assumed Cursor behavior, write
COMPATIBILITY.md as the Cursor-to-Droid porting guide, and make the
validator fail on the patterns that broke compatibility before.

Co-authored-by: factory-droid[bot] <138933559+factory-droid[bot]@users.noreply.github.com>

@caelaxie caelaxie left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

verdict: changes requested (comment review, since github won't let the same account request changes on its own pr).

the skill fixes themselves look right: dropping run_in_background, the no-nested-spawn paths, the script-path fix, the typescript-best-practices routing, and comment-sicko losing tools: read-only all trace to real droid facts, and the last one actually restores upstream (upstream sets no tool restriction). ci Validate plugin is green. blockers:

  1. cursor-team-kit mention. COMPATIBILITY.md:63 says "cursor-team-kit deslop, control-cli, control-ui". the port must not name cursor-team-kit anywhere. smallest fix is to drop that row.
  2. minimum changes. COMPATIBILITY.md (110 lines) and AGENTS.md are new port-only docs that droid doesn't need to load pstack, and COMPATIBILITY.md keeps cursor paths and manifests in the tree (.cursor-plugin/plugin.json, ~/.cursor/plugins/, .cursor/rules/pstack-models, CURSOR_AUTOMATION_ID). smallest fix is to drop both files and point the validator's error strings at the rule itself instead of COMPATIBILITY.md. the validator allowlists and the forbidden-token check can stay, since they're minimal ci harness-compat.
  3. harness proof. this touches plugin content (skills, a droid, a playbook), so it needs a real droid run on the exact head c846d49: droid plugin marketplace add on this branch, droid plugin install pstack@droid-pstack, and the plugin list. also show the installed copy has the changed comment-sicko (no tools: read-only) and typescript-best-practices (no paths and no disable-model-invocation), and that deslop, control-cli and control-ui still load. validator, bun tests and the subagent probes don't count as install proof.
  4. linkage. if this fixes a tracked issue, add Closes #N (or Refs #N if it's partial).

nit: droids/comment-sicko.md:26 adds "I cannot spawn subagents, so I never run /how or /why." the replacement clause already covers that, so drop the extra sentence and stay closer to upstream.

Comment thread COMPATIBILITY.md
| `paths: [...]` glob activation | Drop `paths`. Remove `disable-model-invocation` and let the description route the skill (`typescript-best-practices`) |
| `icon`, `color` | Kept for parity with upstream. Droid ignores them |
| A skill loaded by the model by name | Skills with `disable-model-invocation: true` are read by path. `poteto-mode` reads `../<name>/SKILL.md`. Seat droids find `poteto-mode` in `~/.factory/plugins/` |
| cursor-team-kit `deslop`, `control-cli`, `control-ui` | Bundled in `skills/` |

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

names cursor-team-kit. the port must not mention it anywhere, so drop this row (or the whole file, see the review body).

Comment thread COMPATIBILITY.md

| Cursor | Droid |
| :-- | :-- |
| `.cursor-plugin/plugin.json` | `.factory-plugin/plugin.json`, with only `name`, `version`, `description`, `author`, `homepage`, `repository`, `license`, and `keywords` |

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

a port-only doc that keeps cursor manifests and paths (.cursor-plugin/plugin.json, ~/.cursor/..., .cursor/rules/...) in the tree. droid doesn't need it to adopt pstack, so drop the file.

Comment thread AGENTS.md
@@ -0,0 +1,5 @@
# droid-pstack

This repository is the Droid port of pstack. Before you change any skill, playbook, droid, script, or doc, read `COMPATIBILITY.md` and keep its invariants.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

port-only addition that droid doesn't need to load the plugin, and it points at COMPATIBILITY.md. drop it along with that file.

Comment thread droids/comment-sicko.md
`eslint-disable`, `@ts-ignore`, `@ts-expect-error`, and similar suppressions stink. Look up the rule. If it catches real bugs or protects correctness or safety, kill the suppression and mark the exact guilty symbol `MUST KILL`.

`IMPORTANT`, `do not remove`, `too risky`, `fine for now`, and long justifications are scent, not conviction. Before judging, I read nearby code. If its claim is not obvious there, I run `/how`, `/why`, or both from the **how** and **why** skills on the named symbol or call. Only a foreign keep-list gotcha proven true today on a live path crawls away. Our-code surprises die with the reshape flag above. Doubt after the hunt is meat.
`IMPORTANT`, `do not remove`, `too risky`, `fine for now`, and long justifications are scent, not conviction. Before judging, I read nearby code. If its claim is not obvious there, I trace the named symbol or call myself through its callers, its tests, and the line's history. I cannot spawn subagents, so I never run `/how` or `/why`. Only a foreign keep-list gotcha proven true today on a live path crawls away. Our-code surprises die with the reshape flag above. Doubt after the hunt is meat.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"I cannot spawn subagents, so I never run /how or /why." just repeats the clause before it. drop it to stay closer to upstream.

@caelaxie
caelaxie merged commit 2974782 into main Oct 30, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant