@frankzhang2026/opencode-android-orchestrator 0.1.0 → 0.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (124) hide show
  1. package/CHANGELOG.md +92 -2
  2. package/LICENSE +21 -0
  3. package/README.md +402 -6
  4. package/THIRD_PARTY_NOTICES.md +119 -0
  5. package/dist/cli.js +360 -1
  6. package/dist/cli.js.map +1 -1
  7. package/dist/compatibility/hooks.d.ts +23 -0
  8. package/dist/compatibility/hooks.d.ts.map +1 -0
  9. package/dist/compatibility/hooks.js +44 -0
  10. package/dist/compatibility/hooks.js.map +1 -0
  11. package/dist/compatibility/versions.d.ts +19 -0
  12. package/dist/compatibility/versions.d.ts.map +1 -1
  13. package/dist/compatibility/versions.js +116 -0
  14. package/dist/compatibility/versions.js.map +1 -1
  15. package/dist/doctor/index.d.ts +36 -0
  16. package/dist/doctor/index.d.ts.map +1 -0
  17. package/dist/doctor/index.js +289 -0
  18. package/dist/doctor/index.js.map +1 -0
  19. package/dist/doctor/installation.d.ts +4 -0
  20. package/dist/doctor/installation.d.ts.map +1 -0
  21. package/dist/doctor/installation.js +497 -0
  22. package/dist/doctor/installation.js.map +1 -0
  23. package/dist/index.d.ts +13 -2
  24. package/dist/index.d.ts.map +1 -1
  25. package/dist/index.js +13 -2
  26. package/dist/index.js.map +1 -1
  27. package/dist/installer/adaptive-templates.d.ts +78 -0
  28. package/dist/installer/adaptive-templates.d.ts.map +1 -0
  29. package/dist/installer/adaptive-templates.js +233 -0
  30. package/dist/installer/adaptive-templates.js.map +1 -0
  31. package/dist/installer/agents-config.d.ts +19 -0
  32. package/dist/installer/agents-config.d.ts.map +1 -0
  33. package/dist/installer/agents-config.js +147 -0
  34. package/dist/installer/agents-config.js.map +1 -0
  35. package/dist/installer/android-project.d.ts +36 -0
  36. package/dist/installer/android-project.d.ts.map +1 -0
  37. package/dist/installer/android-project.js +418 -0
  38. package/dist/installer/android-project.js.map +1 -0
  39. package/dist/installer/index.d.ts +8 -0
  40. package/dist/installer/index.d.ts.map +1 -1
  41. package/dist/installer/index.js +8 -1
  42. package/dist/installer/index.js.map +1 -1
  43. package/dist/installer/init.d.ts +68 -0
  44. package/dist/installer/init.d.ts.map +1 -0
  45. package/dist/installer/init.js +398 -0
  46. package/dist/installer/init.js.map +1 -0
  47. package/dist/installer/install-manifest.d.ts +132 -0
  48. package/dist/installer/install-manifest.d.ts.map +1 -0
  49. package/dist/installer/install-manifest.js +1047 -0
  50. package/dist/installer/install-manifest.js.map +1 -0
  51. package/dist/installer/opencode-config.d.ts +32 -0
  52. package/dist/installer/opencode-config.d.ts.map +1 -0
  53. package/dist/installer/opencode-config.js +302 -0
  54. package/dist/installer/opencode-config.js.map +1 -0
  55. package/dist/installer/uninstall.d.ts +70 -0
  56. package/dist/installer/uninstall.d.ts.map +1 -0
  57. package/dist/installer/uninstall.js +770 -0
  58. package/dist/installer/uninstall.js.map +1 -0
  59. package/dist/installer/upgrade.d.ts +101 -0
  60. package/dist/installer/upgrade.d.ts.map +1 -0
  61. package/dist/installer/upgrade.js +1140 -0
  62. package/dist/installer/upgrade.js.map +1 -0
  63. package/dist/opencode-plugin.d.ts +2 -0
  64. package/dist/opencode-plugin.d.ts.map +1 -0
  65. package/dist/opencode-plugin.js +4 -0
  66. package/dist/opencode-plugin.js.map +1 -0
  67. package/dist/plugin/index.d.ts +7 -2
  68. package/dist/plugin/index.d.ts.map +1 -1
  69. package/dist/plugin/index.js +23 -6
  70. package/dist/plugin/index.js.map +1 -1
  71. package/dist/tools/index.d.ts +35 -1
  72. package/dist/tools/index.d.ts.map +1 -1
  73. package/dist/tools/index.js +197 -1
  74. package/dist/tools/index.js.map +1 -1
  75. package/docs/MIGRATION.md +184 -0
  76. package/docs/SECURITY.md +219 -0
  77. package/docs/TROUBLESHOOTING.md +171 -0
  78. package/package.json +23 -5
  79. package/templates/.opencode/agents/scheduled-coder.md +115 -0
  80. package/templates/.opencode/agents/scheduled-planner.md +166 -0
  81. package/templates/.opencode/agents/scheduled-reviewer.md +88 -0
  82. package/templates/.opencode/commands/abort-task.md +20 -0
  83. package/templates/.opencode/commands/acceptance.md +20 -0
  84. package/templates/.opencode/commands/change.md +23 -0
  85. package/templates/.opencode/commands/resume-review.md +19 -0
  86. package/templates/.opencode/skills/scheduled-quality-coder/SKILL.md +93 -0
  87. package/templates/.opencode/skills/scheduled-quality-orchestrator/SKILL.md +216 -0
  88. package/templates/.opencode/skills/scheduled-quality-reviewer/SKILL.md +68 -0
  89. package/templates/AGENTS.md.fragment +19 -0
  90. package/templates/README.md +55 -9
  91. package/templates/automation/config.json +67 -0
  92. package/templates/automation/config.schema.json +194 -0
  93. package/templates/automation/task-contract.schema.json +92 -0
  94. package/templates/automation/tasks/TASK-TEMPLATE.json.example +56 -0
  95. package/templates/docs/plans/README.md +26 -0
  96. package/templates/installation-manifest.schema.json +201 -0
  97. package/templates/scripts/automation/abort-task.sh +171 -0
  98. package/templates/scripts/automation/accept-and-integrate.sh +263 -0
  99. package/templates/scripts/automation/acceptance-report.sh +132 -0
  100. package/templates/scripts/automation/approve-and-run.sh +175 -0
  101. package/templates/scripts/automation/begin-review.sh +18 -0
  102. package/templates/scripts/automation/block-task.sh +26 -0
  103. package/templates/scripts/automation/claim-task.sh +74 -0
  104. package/templates/scripts/automation/integration-scope-gate.sh +103 -0
  105. package/templates/scripts/automation/lib.sh +815 -0
  106. package/templates/scripts/automation/orchestrate-task.sh +119 -0
  107. package/templates/scripts/automation/preflight.sh +206 -0
  108. package/templates/scripts/automation/prepare-contract-review.sh +101 -0
  109. package/templates/scripts/automation/quality-gate.sh +72 -0
  110. package/templates/scripts/automation/queue-task.sh +35 -0
  111. package/templates/scripts/automation/record-red.sh +55 -0
  112. package/templates/scripts/automation/resume-review-fix.sh +32 -0
  113. package/templates/scripts/automation/resume-review.sh +120 -0
  114. package/templates/scripts/automation/scope-gate.sh +110 -0
  115. package/templates/scripts/automation/select-task.sh +34 -0
  116. package/templates/scripts/automation/shadow-run.sh +24 -0
  117. package/templates/scripts/automation/show-acceptance-review.sh +111 -0
  118. package/templates/scripts/automation/status.sh +125 -0
  119. package/templates/scripts/automation/submit-review.sh +73 -0
  120. package/templates/scripts/automation/tests/run-tests.sh +716 -0
  121. package/templates/scripts/automation/transition-state.sh +21 -0
  122. package/templates/scripts/automation/validate-contract.sh +98 -0
  123. package/templates/scripts/automation/verify-integration.sh +38 -0
  124. package/templates/scripts/automation/verify-task.sh +39 -0
@@ -0,0 +1,219 @@
1
+ # Security model
2
+
3
+ This document describes the security properties of
4
+ `@frankzhang2026/opencode-android-orchestrator@0.3.0`. The lifecycle foundation
5
+ completed the real OpenCode `1.14.22` and `1.15.13` release matrix in `0.2.0`;
6
+ `0.3.0` retains that compatibility boundary.
7
+
8
+ ## Security goals and non-goals
9
+
10
+ The orchestrator is designed to reduce accidental or model-initiated scope
11
+ expansion in a local Android repository. It aims to:
12
+
13
+ - keep human proposal, contract, and final-result approval explicit;
14
+ - constrain Coder edits to contract-approved Android source/test paths;
15
+ - keep Reviewer read-only;
16
+ - authenticate packaged and installed orchestration resources;
17
+ - preserve original files and recover complete installer transactions;
18
+ - block silent overwrites, unsafe symlinks, stale plans, branch drift, pushes,
19
+ unbounded retries, and Scheduler/launchd registration;
20
+ - create one local product-and-planning commit only after sealed verification.
21
+
22
+ It is not a privilege boundary against a malicious local user, a compromised
23
+ OpenCode binary/provider, a compromised npm/Git dependency, or another process
24
+ running as the same operating-system account. It does not sandbox Gradle,
25
+ OpenCode, Java, Git hooks, or project tests. A hostile build script or test can
26
+ perform actions outside the orchestrator's intended scope.
27
+
28
+ ## Trust boundaries
29
+
30
+ | Boundary | Trusted input | Untrusted or separately verified input |
31
+ | --- | --- | --- |
32
+ | Package installation | The exact reviewed npm tarball and its pinned version | Existing project files, paths, modes, symlinks, and concurrent edits |
33
+ | OpenCode interaction | A fresh single-choice result handled by the scheduled planner | Ordinary chat text, command arguments, and model-generated approval phrases |
34
+ | Product implementation | The sealed task contract, baseline HEAD, allowed paths, and deterministic scripts | Coder summaries and any unsealed worktree change |
35
+ | Review | The approved contract and independently recomputed diff/evidence | Coder claims and stale report content |
36
+ | Integration | Task ID, repository lease, sealed diff SHA, approved review, original branch/ref, and fresh acceptance | Branch drift, manual commits, changed worktrees, or a reused acceptance package |
37
+ | Recovery | Manifest, markers, hashes, modes, original backups, snapshots, and Git refs | Guessed cleanup steps or copied state from another repository |
38
+
39
+ ## Human approval boundary
40
+
41
+ The normal workflow has three fresh OpenCode `question` selections: proposal,
42
+ sealed contract, and final result. Direct chat prose, silence, a dismissed
43
+ question, or a copied option label is not a normal-path approval. Exceptional
44
+ abort has its own fresh status display and confirmation flow.
45
+
46
+ Approval phrases stored in `automation/config.json` are validation tokens, not
47
+ secrets or cryptographic proof. Security depends on the scheduled planner
48
+ showing the current review material, the user acting at that boundary, and the
49
+ fixed Shell script independently verifying state, hashes, refs, scope, and
50
+ leases. Anyone with direct shell and repository write access can invoke or
51
+ modify local files; this package does not claim to protect against that actor.
52
+
53
+ OpenCode permission prompts are also not semantic workflow approval. They can
54
+ be accepted for the remainder of a session and may be auto-approved. For that
55
+ reason `0.3.0` exposes only `android_orchestrator_status` and
56
+ `android_orchestrator_doctor` as custom tools. State-changing wrappers remain a
57
+ NO-GO until a one-use, non-model-forgeable receipt can bind the approval kind,
58
+ task, session/message, sealed SHA or branch, time, and nonce.
59
+
60
+ ## Agent and tool permissions
61
+
62
+ All three installed agents start with `"*": deny` and add exact permissions.
63
+ The planner can write only new planning artifacts and invoke the small set of
64
+ orchestration scripts. The Coder can edit detected production/test source sets
65
+ but not Gradle, OpenCode, automation, or control files. Reviewer edit access is
66
+ denied. Subagents, Scheduler/job tools, external directories, web access, push,
67
+ merge/rebase, destructive Git commands, shell composition, and launchd are
68
+ denied where applicable.
69
+
70
+ Permissions are defense in depth, not a substitute for script checks. The
71
+ source preflight resolves each agent and verifies its effective high-risk
72
+ permissions and custom-tool discovery.
73
+
74
+ The read-only status tool additionally:
75
+
76
+ - validates `TASK-[A-Z0-9-]+` at Schema and execution time;
77
+ - binds execution to the worktree that loaded the plugin;
78
+ - authenticates the installation manifest, managed resources, and executable
79
+ modes before running anything;
80
+ - invokes only the fixed `scripts/automation/status.sh` path with separate
81
+ shell expressions;
82
+ - rejects a failed command, malformed/mismatched JSON, or output above 1 MiB.
83
+
84
+ Doctor invokes read-only project, dependency, SDK, and installation checks and
85
+ returns their failures instead of repairing the project.
86
+
87
+ ## Filesystem and configuration safety
88
+
89
+ The installer never follows a symbolic link at a managed file or required
90
+ ancestor. Paths must be relative, normalized, unique, within the detected Git
91
+ root, and regular files where required. Existing content, size, and effective
92
+ mode are captured during planning and rechecked before the first write. A stale
93
+ or tampered plan fails closed.
94
+
95
+ Installation strategies are deliberately distinct:
96
+
97
+ - `copy` and `generate` accept a missing target or an exact content/mode match;
98
+ any differing existing file is a conflict;
99
+ - `merge` accepts only output produced by the structure-aware OpenCode JSON/JSONC
100
+ or bounded AGENTS merge planner;
101
+ - no lifecycle command has a force-overwrite flag.
102
+
103
+ OpenCode JSON/JSONC merging preserves unrelated fields, comments, order, and
104
+ plugin options. It rejects malformed/ambiguous files, duplicate identities,
105
+ different managed-plugin versions, and symlinks. AGENTS merging owns only one
106
+ marked block and rejects partial, duplicate, or modified markers.
107
+
108
+ New installations generate task examples in `all` module scope: every detected
109
+ Android module's `src/main`, `src/test`, and `src/androidTest` path is eligible,
110
+ while Gradle settings/build files and orchestration resources remain protected.
111
+ `primary` scope narrows the generated paths to one module. Upgrade treats a
112
+ legacy configuration with no scope field as `primary`, preventing an implicit
113
+ permission expansion.
114
+
115
+ The installed manifest is `0600`. Installer control, backup, recovery, and
116
+ history directories are created with private `0700` defaults; backup files
117
+ preserve the original file mode where recovery requires it. Shell resources
118
+ must be exact packaged bytes with `0755`; other copied templates are
119
+ non-executable.
120
+
121
+ ## Transaction and recovery safety
122
+
123
+ `init` writes original-file backups before publishing a prepared manifest. It
124
+ then applies validated files, runs the 38-case transaction suite and a shadow
125
+ run, verifies final hashes/modes, and only then marks the manifest installed.
126
+ Failure before completion restores originals and removes safely unchanged new
127
+ files.
128
+
129
+ `upgrade` requires a healthy installed manifest and original backups. It saves
130
+ the exact old manifest and immediate pre-upgrade snapshots, reconstructs merge
131
+ targets from first-install originals, writes the new version, and replaces the
132
+ manifest only after verification. Failure attempts a whole-version rollback.
133
+
134
+ `uninstall` restores an original or removes a plugin-created path only when the
135
+ current path still matches a safe known state. Content, permission, deletion,
136
+ or existence drift is retained and reported. Before changes it saves the
137
+ active manifest and every affected installed file. Failure before commit
138
+ attempts to restore the installed state.
139
+
140
+ An `*_ROLLBACK_FAILED` result is a hard stop. Do not delete markers or recovery
141
+ data and do not guess at partial cleanup. Preserve the repository and inspect
142
+ the recorded before/after hashes and Git refs.
143
+
144
+ ## Git and orchestration invariants
145
+
146
+ - The source repository must have an identifiable original branch and baseline
147
+ HEAD. Original-branch drift blocks integration.
148
+ - The persistent repository lease prevents concurrent orchestrated tasks from
149
+ sharing a mutable repository workspace.
150
+ - Planning artifacts remain uncommitted until the verified product change is
151
+ ready. Successful integration creates exactly one combined local commit.
152
+ - Scope gates inspect tracked and untracked changes, reject protected paths and
153
+ obvious test weakening, and bind the accepted result to a diff SHA.
154
+ - Integration reruns verification before a fast-forward. It never pushes.
155
+ - A successfully integrated task branch is deleted only after the original
156
+ branch reaches the verified commit. Failure preserves the branch for
157
+ recovery.
158
+ - Abort rejects out-of-contract/protected paths, archives the diff, and avoids
159
+ changing the original branch ref.
160
+
161
+ Git hooks and Git configuration remain part of the host repository's trust
162
+ surface. Review them before running a workflow in an untrusted project.
163
+
164
+ ## Dependencies and network behavior
165
+
166
+ Use fixed package references. The installer adds the exact orchestrator
167
+ version and the configured pinned Superpowers Git tag; it does not use
168
+ `latest`. The package is compiled against `@opencode-ai/plugin@1.14.22` and
169
+ declares the bounded peer range `>=1.14.22 <1.16.0`.
170
+
171
+ The orchestrator does not contain a telemetry uploader and the deterministic
172
+ Shell flow forbids Git push. Network activity can still occur outside that
173
+ code when npm/npx downloads a package, OpenCode resolves a pinned plugin,
174
+ OpenCode contacts the configured model provider, or project build/test tooling
175
+ uses the network. Apply the host organization's normal npm, Git, OpenCode,
176
+ provider, proxy, certificate, and dependency-review policy.
177
+
178
+ ## Secrets and retained evidence
179
+
180
+ Installed agents deny reads of `.env`, `.env.*`, `local.properties`, `*.jks`,
181
+ and `*.keystore`. Do not put secrets in task descriptions, plans, source code,
182
+ test output, commit messages, model prompts, or approval summaries.
183
+
184
+ The following may contain sensitive source, paths, branch names, test logs,
185
+ diffs, or review findings:
186
+
187
+ - `.git/automation-runtime/evidence/`;
188
+ - `.git/automation-runtime/workspaces/` and state/transition records;
189
+ - `.automation-plugin/backups/`, `upgrades/`, `uninstalls/`, and `history/`;
190
+ - generated acceptance, abort, integration, and rollback evidence.
191
+
192
+ These paths are excluded from package templates but remain local audit data.
193
+ Keep repository and filesystem access appropriately restricted. Redact user
194
+ names, absolute paths, proprietary source/diffs, provider details, tokens, SDK
195
+ paths, and signing information before sharing a diagnostic bundle. Do not
196
+ commit installer recovery data unless an explicit internal policy requires it.
197
+
198
+ ## Residual risks
199
+
200
+ - Hashes prove byte identity against the running package; they do not prove the
201
+ package itself is trustworthy. Review the tarball and its provenance.
202
+ - A same-user process can race filesystem or Git state around checks. The
203
+ implementation rechecks critical snapshots and locks cooperative workflows,
204
+ but it is not an operating-system sandbox.
205
+ - Gradle tests, Git hooks, OpenCode, model providers, and third-party plugins
206
+ execute outside this package's file planner and may have broader behavior.
207
+ - `inPlaceExclusive` intentionally switches the current worktree to a task
208
+ branch. Use the explicitly configured isolated-worktree strategy only after
209
+ validating its storage and cleanup policy.
210
+ - Recovery evidence improves auditability but increases local sensitive-data
211
+ retention.
212
+ - Real dual-version end-to-end acceptance and a clean install from the final
213
+ tarball remain mandatory release gates.
214
+
215
+ When reporting a suspected security problem, preserve exact versions, error
216
+ codes, hashes, and redacted evidence. Do not publish credentials, proprietary
217
+ diffs, recovery archives, or exploit details that would expose another
218
+ project. See [Troubleshooting](TROUBLESHOOTING.md) for safe first-response
219
+ commands.
@@ -0,0 +1,171 @@
1
+ # Troubleshooting
2
+
3
+ Use this guide for
4
+ `@frankzhang2026/opencode-android-orchestrator@0.3.0`.
5
+
6
+ ## Start with read-only evidence
7
+
8
+ From the repository root, capture:
9
+
10
+ ```sh
11
+ git status --short --branch
12
+ git rev-parse HEAD
13
+ opencode --version
14
+ npx @frankzhang2026/opencode-android-orchestrator@0.3.0 doctor . --json
15
+ ```
16
+
17
+ If installation never completed, doctor will correctly report a missing or
18
+ invalid installed manifest. Preserve the complete error code and details from
19
+ the command that failed. Do not rerun a write command repeatedly while the
20
+ working tree or installer control state is changing.
21
+
22
+ The CLI uses these exit codes:
23
+
24
+ | Exit code | Meaning |
25
+ | ---: | --- |
26
+ | `0` | Command completed, or doctor found no failed check. Doctor warnings are allowed. |
27
+ | `1` | A lifecycle operation failed, or doctor found at least one failed check. |
28
+ | `2` | Unknown command or invalid CLI arguments. |
29
+
30
+ `doctor --json` always emits a structured report. The `--json` option on
31
+ `init`, `upgrade`, and `uninstall` structures successful results; thrown errors
32
+ remain human-readable on stderr with a stable code such as `[FILE_CONFLICT]`.
33
+
34
+ ## Prerequisite and discovery failures
35
+
36
+ | Symptom | Likely cause | Safe response |
37
+ | --- | --- | --- |
38
+ | `DOCTOR_FAILED` before any write | One or more required project/tool checks failed. | Read each failed doctor check; fix only the named prerequisite, then rerun doctor or init. |
39
+ | OpenCode version failure | Installed version is below `1.14.22`, at or above `1.16.0`, or cannot be parsed/executed. | Install a certified version (`1.14.22` or `1.15.13`) for release validation. Do not bypass the version gate. |
40
+ | Git root or Android project not detected | The target is outside a Git repository, settings are missing, or no supported Android module was found. | Run from the intended repository/module and inspect `settings.gradle` or `settings.gradle.kts`. Nested Gradle roots are intentionally unsupported. |
41
+ | Gradle Wrapper failure | `gradlew` or `gradle/wrapper/gradle-wrapper.properties` is missing, or `gradlew` is not executable. | Restore the project's reviewed Wrapper files. Do not let the installer generate or replace build configuration. |
42
+ | `MODULE_SCOPE_INVALID` or an invalid `--module-scope` argument | The value is not `all` or `primary`. | Use `all` for the default all-module contract or `primary` for an intentional single-module restriction. |
43
+ | `PRIMARY_MODULE_AMBIGUOUS` | Restrictive `primary` scope has multiple possible Android modules. | Supply an exact Gradle path, for example `--module-scope primary --primary-module :mobile`, or use the default `all` scope. |
44
+ | `PRIMARY_MODULE_NOT_FOUND` | The selected Gradle path was not detected. | Use a module path reported by doctor/project detection; do not pass a filesystem directory. |
45
+ | Android SDK failure | No valid explicit SDK, `ANDROID_HOME`, `ANDROID_SDK_ROOT`, or `local.properties` `sdk.dir` was found. | Configure one real SDK root containing `platforms/` and `build-tools/`. Do not publish `local.properties`. |
46
+ | Missing `git`, `jq`, `rg`, `shasum`, or Java | Required deterministic command is unavailable on `PATH`. | Install or restore the missing command, record its version, and rerun the read-only checks. |
47
+
48
+ After installation, inspect OpenCode discovery separately:
49
+
50
+ ```sh
51
+ opencode debug config
52
+ opencode debug skill
53
+ opencode debug agent scheduled-planner
54
+ opencode debug agent scheduled-coder
55
+ opencode debug agent scheduled-reviewer
56
+ ```
57
+
58
+ Then run `./scripts/automation/preflight.sh --source`. It validates pinned
59
+ plugins, required skills, agent permissions, and both read-only custom tools.
60
+ If it fails, preserve its exact output. Do not broaden an agent's default-deny
61
+ permissions to make discovery pass.
62
+
63
+ ## Installation conflicts
64
+
65
+ Common fail-closed codes include:
66
+
67
+ | Code | Meaning | Response |
68
+ | --- | --- | --- |
69
+ | `FILE_CONFLICT` | Existing content or mode differs from a `copy`/`generate` target. | Compare the named path with the packaged template. Preserve local policy elsewhere or restore the audited file deliberately; there is no force flag. |
70
+ | `AMBIGUOUS_CONFIG` | Both `opencode.json` and `opencode.jsonc` exist. | Select and consolidate the user-owned configuration in a separate reviewed change. |
71
+ | `PLUGIN_VERSION_CONFLICT` | The same managed package identity has another reference/version. | Review and remove or migrate only the obsolete entry; never let init silently replace it. |
72
+ | `DUPLICATE_PLUGIN` or `DUPLICATE_PROPERTY` | Configuration identity is ambiguous. | Correct the JSON/JSONC structure without discarding unrelated fields or comments. |
73
+ | `INVALID_JSONC` or `ROOT_NOT_OBJECT` | OpenCode configuration cannot be merged safely. | Repair the user-owned file and validate it before retrying. |
74
+ | `AGENTS_BLOCK_CONFLICT` or `AGENTS_MARKERS_INVALID` | The bounded managed block is modified, partial, or duplicated. | Restore one exact managed block; keep project-specific instructions outside its markers. |
75
+ | `FILE_SYMLINK`, `TARGET_SYMLINK`, or `CONFIG_SYMLINK` | A managed target or ancestor is a symbolic link. | Replace it only after understanding ownership and destination. The installer intentionally does not follow it. |
76
+ | `PLAN_STALE` or `TARGET_MODIFIED` | A file changed between planning and application. | Stop concurrent edits, inspect the diff, and rerun from a stable state. |
77
+
78
+ An init verification failure reports `POST_INSTALL_VERIFICATION_FAILED` and
79
+ automatically rolls back the prepared installation. Confirm the original files
80
+ and inspect `.automation-plugin/history/`; do not assume a failed init left a
81
+ usable installation.
82
+
83
+ ## Manifest, upgrade, and uninstall failures
84
+
85
+ Run doctor before deciding on recovery. Its installation section distinguishes
86
+ manifest identity, content drift, permission drift, backups, and semantic
87
+ configuration.
88
+
89
+ | Code or check | Meaning | Response |
90
+ | --- | --- | --- |
91
+ | `MANIFEST_MISSING`, `MANIFEST_INVALID`, or `MANIFEST_STATE` | No trustworthy installed manifest is available. | Do not invent a manifest or copy one from another project. Determine whether this is an uninstalled/manual setup or an interrupted transaction. |
92
+ | `EXISTING_INSTALLATION_DIFFERENT` | `init` found another installed inventory/version. | Use `upgrade` for a healthy older manifest. |
93
+ | `EXISTING_INSTALLATION_INVALID` or `INSTALLATION_INVALID` | Manifest, installed files, or required backups failed validation. | Preserve the project and `.automation-plugin/`; inspect doctor details and recovery history. |
94
+ | `INSTALLED_FILES_MODIFIED` | Upgrade found content, existence, mode, or backup drift. | Move intentional customization out of managed paths or choose manual recovery. Upgrade will not overwrite it. |
95
+ | `VERSION_DOWNGRADE_REFUSED` | Target package is older than the installed manifest. | Use a newer fixed package version; never edit the manifest version. |
96
+ | `UPGRADE_IN_PROGRESS` or `UNINSTALL_IN_PROGRESS` | `.automation-plugin/upgrade.json` or `uninstall.json` records an unfinished transaction. | Inspect the marker and matching recovery directory. Do not delete the marker merely to retry. |
97
+ | `POST_UPGRADE_VERIFICATION_FAILED` | New resources failed verification. | The implementation attempts a complete old-version rollback; verify the old manifest and inspect upgrade evidence. |
98
+ | `UNINSTALL_CONFLICT` | Uninstall planning/application detected unsafe state. | Keep all files and inspect the listed paths. Drift is retained by design. |
99
+ | `POST_UNINSTALL_VERIFICATION_FAILED` | Final restored/removed paths did not verify. | The implementation attempts to restore the installed state; inspect uninstall recovery evidence before another command. |
100
+ | Any `*_ROLLBACK_FAILED` | Automatic recovery could not prove completion. | Stop all automation. Preserve Git refs, the manifest, marker, backups, recovery snapshots, and logs for manual analysis. |
101
+
102
+ Installer control paths are:
103
+
104
+ - active manifest: `.automation-plugin/manifest.json` (`0600`);
105
+ - first-install/original backups: `.automation-plugin/backups/<id>/`;
106
+ - upgrade marker and snapshots: `.automation-plugin/upgrade.json` and
107
+ `.automation-plugin/upgrades/<id>/`;
108
+ - uninstall marker and snapshots: `.automation-plugin/uninstall.json` and
109
+ `.automation-plugin/uninstalls/<id>/`;
110
+ - completed/rolled-back records: `.automation-plugin/history/`.
111
+
112
+ These files are evidence, not cache.
113
+
114
+ ## Read-only custom tool failures
115
+
116
+ `android_orchestrator_status` accepts exactly one `TASK-[A-Z0-9-]+` ID. It
117
+ authenticates the installation before invoking the fixed status script.
118
+
119
+ | Code | Meaning |
120
+ | --- | --- |
121
+ | `INVALID_TASK_ID` | The ID contains invalid characters, extra text, or an unsupported format. |
122
+ | `WORKSPACE_MISMATCH` | The tool context differs from the worktree that loaded the plugin. |
123
+ | `UNTRUSTED_INSTALLATION` | Manifest, packaged resource, or executable-mode checks could not authenticate the installed status script. |
124
+ | `STATUS_RUNNER_UNAVAILABLE` | OpenCode did not supply the compatible shell adapter. |
125
+ | `STATUS_COMMAND_FAILED` | The authenticated status script returned a nonzero exit. Its details usually identify a missing contract or invalid runtime layout. |
126
+ | `INVALID_STATUS_OUTPUT` | Output was not valid JSON or identified another task. |
127
+ | `STATUS_OUTPUT_TOO_LARGE` | Output exceeded the 1 MiB safety bound. |
128
+ | `TOOL_ABORTED` | The OpenCode call was cancelled before execution. |
129
+
130
+ Do not bypass `UNTRUSTED_INSTALLATION` by calling a different script path. Run
131
+ doctor, restore the exact managed installation, or perform a reviewed recovery.
132
+
133
+ ## Automation task recovery
134
+
135
+ Use `./scripts/automation/status.sh <TASK-ID>` or the read-only status tool to
136
+ identify the state, workspace, original branch, sealed diff, and evidence.
137
+
138
+ - `AWAITING_HUMAN`: use `/acceptance <TASK-ID>` to regenerate the verified
139
+ review card and fresh result question.
140
+ - `BLOCKED` after a Reviewer exited without submitting a decision: use
141
+ `/resume-review <TASK-ID>`. The script accepts only the bounded reviewer-only
142
+ recovery and proves the sealed diff has not changed.
143
+ - A supported stopped state that should be abandoned: use
144
+ `/abort-task <TASK-ID>`, inspect the status card, and complete its explicit
145
+ confirmation. It archives contract-scoped work before restoring the original
146
+ branch.
147
+ - `INTEGRATION_BLOCKED`: preserve the task branch, original branch, lease, and
148
+ integration evidence. Do not reset, cherry-pick, merge, or rerun the
149
+ integrator until the recorded refs and failure are understood.
150
+ - `TEST_FAILED` or `NEEDS_HUMAN`: inspect the contract and evidence. Do not
151
+ broaden scope or silently queue the same task again.
152
+
153
+ ## Actions to avoid
154
+
155
+ Never use a troubleshooting shortcut that destroys the evidence needed to
156
+ prove recovery:
157
+
158
+ - do not run `git reset --hard`, `git clean`, an improvised merge/rebase, or a
159
+ manual branch deletion;
160
+ - do not edit manifest hashes, state JSON, approvals, or sealed evidence;
161
+ - do not recursively delete `.automation-plugin/` or
162
+ `.git/automation-runtime/`;
163
+ - do not chmod all managed files to silence permission drift;
164
+ - do not replace a pinned package reference with `latest`;
165
+ - do not expose `.env`, signing keys, keystores, `local.properties`, npm tokens,
166
+ model-provider credentials, or recovery diffs in public reports.
167
+
168
+ For escalation, provide the command, exit code, stable error code, redacted
169
+ details, OpenCode version, package version, current branch/HEAD, and the list of
170
+ affected paths. Share file contents only after applying the guidance in
171
+ [Security](SECURITY.md).
package/package.json CHANGED
@@ -1,13 +1,26 @@
1
1
  {
2
2
  "name": "@frankzhang2026/opencode-android-orchestrator",
3
- "version": "0.1.0",
3
+ "version": "0.3.0",
4
4
  "description": "Reusable OpenCode orchestration for Android projects",
5
5
  "license": "MIT",
6
+ "author": "frankzhang2026",
7
+ "repository": {
8
+ "type": "git",
9
+ "url": "git+https://github.com/frankzhangtx/npm-orchestrator-plugin.git"
10
+ },
11
+ "homepage": "https://github.com/frankzhangtx/npm-orchestrator-plugin#readme",
12
+ "bugs": {
13
+ "url": "https://github.com/frankzhangtx/npm-orchestrator-plugin/issues"
14
+ },
6
15
  "type": "module",
7
- "main": "./dist/index.js",
8
- "types": "./dist/index.d.ts",
16
+ "main": "./dist/opencode-plugin.js",
17
+ "types": "./dist/opencode-plugin.d.ts",
9
18
  "exports": {
10
19
  ".": {
20
+ "types": "./dist/opencode-plugin.d.ts",
21
+ "import": "./dist/opencode-plugin.js"
22
+ },
23
+ "./api": {
11
24
  "types": "./dist/index.d.ts",
12
25
  "import": "./dist/index.js"
13
26
  }
@@ -17,9 +30,12 @@
17
30
  },
18
31
  "files": [
19
32
  "dist/",
33
+ "docs/",
20
34
  "templates/",
21
35
  "README.md",
22
- "CHANGELOG.md"
36
+ "CHANGELOG.md",
37
+ "LICENSE",
38
+ "THIRD_PARTY_NOTICES.md"
23
39
  ],
24
40
  "publishConfig": {
25
41
  "access": "public",
@@ -38,7 +54,6 @@
38
54
  "automation",
39
55
  "orchestration"
40
56
  ],
41
- "author": "",
42
57
  "peerDependencies": {
43
58
  "@opencode-ai/plugin": ">=1.14.22 <1.16.0"
44
59
  },
@@ -46,5 +61,8 @@
46
61
  "@opencode-ai/plugin": "1.14.22",
47
62
  "@types/node": "22.13.9",
48
63
  "typescript": "5.8.2"
64
+ },
65
+ "dependencies": {
66
+ "jsonc-parser": "3.3.1"
49
67
  }
50
68
  }
@@ -0,0 +1,115 @@
1
+ ---
2
+ description: Implements or repairs exactly one orchestrated task with TDD and deterministic quality gates
3
+ mode: primary
4
+ temperature: 0.1
5
+ steps: 32
6
+ permission:
7
+ "*": deny
8
+ android_orchestrator_status: allow
9
+ android_orchestrator_doctor: allow
10
+ read:
11
+ "*": allow
12
+ ".env": deny
13
+ ".env.*": deny
14
+ "local.properties": deny
15
+ "**/*.jks": deny
16
+ "**/*.keystore": deny
17
+ edit:
18
+ "*": deny
19
+ "src/main/**": allow
20
+ "src/test/**": allow
21
+ "src/androidTest/**": allow
22
+ "**/src/main/**": allow
23
+ "**/src/test/**": allow
24
+ "**/src/androidTest/**": allow
25
+ ".opencode/**": deny
26
+ ".opencode/skills/**": deny
27
+ "automation/**": deny
28
+ "scripts/automation/**": deny
29
+ "opencode.json": deny
30
+ "AGENTS.md": deny
31
+ "gradle/**": deny
32
+ "gradlew": deny
33
+ "gradlew.bat": deny
34
+ "settings.gradle": deny
35
+ "settings.gradle.kts": deny
36
+ "build.gradle": deny
37
+ "build.gradle.kts": deny
38
+ "**/build.gradle": deny
39
+ "**/build.gradle.kts": deny
40
+ bash:
41
+ "*": deny
42
+ "git status": allow
43
+ "git status --short": allow
44
+ "git diff": allow
45
+ "git diff --stat": allow
46
+ "git diff --name-only": allow
47
+ "git rev-parse HEAD": allow
48
+ "git rev-parse --show-toplevel": allow
49
+ "git ls-files": allow
50
+ "./gradlew testDebugUnitTest": allow
51
+ "./gradlew assembleDebug": allow
52
+ "./gradlew lint": allow
53
+ "./gradlew connectedDebugAndroidTest": allow
54
+ "./scripts/automation/status.sh *": allow
55
+ "./scripts/automation/select-task.sh PENDING": allow
56
+ "./scripts/automation/claim-task.sh *": allow
57
+ "./scripts/automation/block-task.sh *": allow
58
+ "./scripts/automation/record-red.sh *": allow
59
+ "./scripts/automation/quality-gate.sh *": allow
60
+ "git push*": deny
61
+ "git merge*": deny
62
+ "git rebase*": deny
63
+ "git worktree*": deny
64
+ "git clean*": deny
65
+ "git reset*": deny
66
+ "rm *": deny
67
+ "*>*": deny
68
+ "*<*": deny
69
+ "*|*": deny
70
+ "*;*": deny
71
+ "*&&*": deny
72
+ "*||*": deny
73
+ "*$(*": deny
74
+ "*`*": deny
75
+ glob: allow
76
+ grep: allow
77
+ list: allow
78
+ skill:
79
+ "*": deny
80
+ "using-superpowers": allow
81
+ "scheduled-quality-coder": allow
82
+ "test-driven-development": allow
83
+ "systematic-debugging": allow
84
+ "verification-before-completion": allow
85
+ schedule_job: deny
86
+ list_jobs: deny
87
+ get_version: deny
88
+ get_skill: deny
89
+ install_skill: deny
90
+ get_job: deny
91
+ update_job: deny
92
+ delete_job: deny
93
+ cleanup_global: deny
94
+ run_job: deny
95
+ job_logs: deny
96
+ task: deny
97
+ question: deny
98
+ external_directory: deny
99
+ webfetch: deny
100
+ websearch: deny
101
+ doom_loop: deny
102
+ ---
103
+
104
+ You are the write-capable half of an orchestrated coding quality gate.
105
+
106
+ The orchestrator message must contain exactly one task ID or the compatibility
107
+ selector token `NEXT_PENDING`. Load
108
+ `scheduled-quality-coder` before taking any repository action and follow it
109
+ literally. Do not infer missing requirements and do not ask questions during a
110
+ non-interactive run. If anything is ambiguous or blocked, stop and report the exact
111
+ reason; the deterministic scripts own state transitions.
112
+
113
+ You may edit only paths allowed both by this agent and by the task contract.
114
+ Passing tests never grants permission to push, merge, create worktrees, alter
115
+ automation rules, or declare the task ready for review yourself.