apphx 1.1.0 → 2.0.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 (120) hide show
  1. package/README.md +50 -182
  2. package/benchmarks/peer-context-worker.mjs +186 -0
  3. package/benchmarks/peer-context.mjs +150 -0
  4. package/dist/apple-types.js.map +1 -1
  5. package/dist/cli.js +370 -118
  6. package/dist/cli.js.map +1 -1
  7. package/dist/config.js +42 -4
  8. package/dist/config.js.map +1 -1
  9. package/dist/dependencies.js +455 -16
  10. package/dist/dependencies.js.map +1 -1
  11. package/dist/export-options.js +44 -2
  12. package/dist/export-options.js.map +1 -1
  13. package/dist/flutter.js +13 -25
  14. package/dist/flutter.js.map +1 -1
  15. package/dist/go-dependencies.js +389 -0
  16. package/dist/go-dependencies.js.map +1 -0
  17. package/dist/inbox.js +7 -8
  18. package/dist/inbox.js.map +1 -1
  19. package/dist/integrations.js +3 -3
  20. package/dist/isolation.js +190 -0
  21. package/dist/isolation.js.map +1 -0
  22. package/dist/macos.js +57 -0
  23. package/dist/macos.js.map +1 -0
  24. package/dist/mygo-build.js +55 -0
  25. package/dist/mygo-build.js.map +1 -0
  26. package/dist/policy.js +35 -0
  27. package/dist/policy.js.map +1 -0
  28. package/dist/preflight.js +1 -1
  29. package/dist/process.js +3 -3
  30. package/dist/project-profiles.js +163 -0
  31. package/dist/project-profiles.js.map +1 -0
  32. package/dist/proof.js +33 -0
  33. package/dist/proof.js.map +1 -0
  34. package/dist/remote.js +1 -1
  35. package/dist/runner.js +269 -287
  36. package/dist/runner.js.map +1 -1
  37. package/dist/scheduler.js +0 -3
  38. package/dist/scheduler.js.map +1 -1
  39. package/dist/schemas.js +156 -44
  40. package/dist/schemas.js.map +1 -1
  41. package/dist/store.js +166 -44
  42. package/dist/store.js.map +1 -1
  43. package/dist/vendor/obfuscator/dist/cli.js +72 -0
  44. package/dist/vendor/obfuscator/dist/cli.js.map +1 -0
  45. package/dist/vendor/obfuscator/dist/code.js +585 -0
  46. package/dist/vendor/obfuscator/dist/code.js.map +1 -0
  47. package/dist/vendor/obfuscator/dist/common.js +262 -0
  48. package/dist/vendor/obfuscator/dist/common.js.map +1 -0
  49. package/dist/vendor/obfuscator/dist/config.js +123 -0
  50. package/dist/vendor/obfuscator/dist/config.js.map +1 -0
  51. package/dist/vendor/obfuscator/dist/content.js +89 -0
  52. package/dist/vendor/obfuscator/dist/content.js.map +1 -0
  53. package/dist/vendor/obfuscator/dist/obfuscate.js +93 -0
  54. package/dist/vendor/obfuscator/dist/obfuscate.js.map +1 -0
  55. package/dist/vendor/obfuscator/dist/png.js +283 -0
  56. package/dist/vendor/obfuscator/dist/png.js.map +1 -0
  57. package/dist/vendor/obfuscator/dist/project.js +159 -0
  58. package/dist/vendor/obfuscator/dist/project.js.map +1 -0
  59. package/dist/vendor/obfuscator/dist/resources.js +335 -0
  60. package/dist/vendor/obfuscator/dist/resources.js.map +1 -0
  61. package/dist/vendor/obfuscator/package.json +22 -0
  62. package/dist/workspace.js +113 -0
  63. package/dist/workspace.js.map +1 -0
  64. package/evals/control.mjs +73 -0
  65. package/evals/expectations.mjs +37 -0
  66. package/evals/host.mjs +51 -0
  67. package/evals/oracle.mjs +80 -0
  68. package/evals/policy.mjs +268 -0
  69. package/examples/android-java.factory.json +18 -0
  70. package/examples/android-java.json +16 -0
  71. package/examples/existing-project.factory.json +18 -0
  72. package/examples/existing-project.json +17 -0
  73. package/examples/expo.eas.json +17 -0
  74. package/examples/expo.factory.json +18 -0
  75. package/examples/expo.json +16 -0
  76. package/examples/factory.json +0 -2
  77. package/examples/flutter.factory.json +13 -0
  78. package/examples/flutter.json +16 -0
  79. package/examples/luggage.json +5 -3
  80. package/examples/mygo-web.factory.json +18 -0
  81. package/examples/mygo-web.json +16 -0
  82. package/examples/mygo.factory.json +18 -0
  83. package/examples/mygo.json +16 -0
  84. package/examples/react-native.factory.json +18 -0
  85. package/examples/react-native.json +16 -0
  86. package/examples/runtime/android-java/app/build.gradle +7 -0
  87. package/examples/runtime/android-java/app/src/main/AndroidManifest.xml +8 -0
  88. package/examples/runtime/android-java/app/src/main/java/dev/apphx/runtime/MainActivity.java +44 -0
  89. package/examples/runtime/android-java/sdk-build.mjs +29 -0
  90. package/examples/runtime/android-java/settings.gradle +2 -0
  91. package/examples/runtime/android-ui.mjs +70 -0
  92. package/examples/runtime/mygo-native/go.mod +13 -0
  93. package/examples/runtime/mygo-native/go.sum +10 -0
  94. package/examples/runtime/mygo-native/main.go +173 -0
  95. package/examples/runtime/mygo-native/main_test.go +14 -0
  96. package/examples/runtime/mygo-native/mygo.json +1 -0
  97. package/examples/runtime/mygo-web/bun.lock +15 -0
  98. package/examples/runtime/mygo-web/go.mod +9 -0
  99. package/examples/runtime/mygo-web/go.sum +8 -0
  100. package/examples/runtime/mygo-web/index.html +1 -0
  101. package/examples/runtime/mygo-web/main.go +60 -0
  102. package/examples/runtime/mygo-web/mygo.config.ts +10 -0
  103. package/examples/runtime/mygo-web/package.json +1 -0
  104. package/examples/runtime/mygo-web/src/main.ts +23 -0
  105. package/examples/runtime/mygo-web/src/mygo.ts +14 -0
  106. package/examples/swift.factory.json +18 -0
  107. package/examples/swift.json +16 -0
  108. package/examples/uni-app.factory.json +18 -0
  109. package/examples/uni-app.json +16 -0
  110. package/package.json +12 -5
  111. package/scripts/bundle-obfuscator.mjs +19 -0
  112. package/scripts/runtime-smoke.mjs +209 -0
  113. package/skills/apphx/SKILL.md +94 -17
  114. package/skills/apphx/resources/google-play-research-result.json +6 -0
  115. package/skills/apphx/resources/local-research-result.json +6 -0
  116. package/skills/apphx/resources/requirement.json +5 -8
  117. package/skills/apphx/resources/research-result.json +5 -14
  118. package/skills/apphx/resources/review-result.json +1 -1
  119. package/dist/apple.js +0 -900
  120. package/dist/apple.js.map +0 -1
@@ -1,30 +1,38 @@
1
1
  ---
2
2
  name: apphx
3
- description: Build and locally package a Flutter iOS app from explicit product requirements using the embedded apphx harness. Use for apphx init, enqueue, native research/build/independent review, external verification, packaging, or resuming a persisted job. Not a coding-agent launcher or an automatic App Store publisher.
3
+ description: Build, verify and locally package Flutter, Java Android, Swift, React Native, Expo, uni-app or MyGo macOS projects from explicit requirements using apphx. Supports new apps and safe existing-project snapshots. Use for init, enqueue, research, native implementation, independent review or resuming a persisted job. Not a coding-agent launcher or automatic store publisher.
4
4
  ---
5
5
 
6
6
  # apphx
7
7
 
8
8
  Use your current host's model, context, authentication, filesystem, browser and native delegation tools. The installed `apphx` CLI owns requirements, durable turns, verification, fingerprints and local packaging. Never start another coding-agent CLI, including Hermes, as a subprocess to perform a phase. There is no apphx chat UI, model credential setup, daemon, or background agent loop.
9
9
 
10
- This skill is advisory to the host. apphx code gates apphx-owned transitions, not arbitrary host edits or shell commands. It does not sandbox your host, enforce reviewer identity, guarantee Apple approval, or verify that a policy citation's contents are true. Preserve host permissions and the user's scope.
10
+ This skill is advisory to the host. apphx code gates apphx-owned transitions, not arbitrary host edits or shell commands. It does not sandbox your host, enforce reviewer identity or guarantee store approval. Store submission and review are manual human work outside this tool. Preserve host permissions and the user's scope.
11
11
 
12
12
  ## 1. Establish the control project
13
13
 
14
14
  1. Use the project where the user installed/invoked this skill as the control project. Keep `factory.json`, its SQLite state, requirement files and result JSON outside generated app workspaces. Keep the absolute config path for every command below, including commands issued while your working directory is an app workspace.
15
- 2. The npm package, executable and skill are all `apphx`. Run `apphx --version` and `apphx --help`. If `apphx` is an already-installed local dependency of the control project rather than on PATH, use that project's package manager for **every** apphx command: `pnpm exec apphx`, `yarn exec apphx`, or `npm exec --offline --package=apphx -- apphx`. Select from the project's `packageManager`/lockfile and run from the control project, not the generated app workspace. Confirm `apphx` is already installed; do not fetch a similarly named package or silently change the user's environment. If neither route is available, stop and report the missing installation. Installing a skill alone does not install Node, Flutter or Xcode.
16
- 3. If there is no configuration, run `apphx init --config /absolute/control/factory.json`. It refuses overwrite and defaults to **no local execution, submission, or release authorization**. Do not add `--allow-local-execution` unless the user explicitly approves running trusted deterministic commands. With that approval it can be supplied to `init`; for an existing config have the owner review and explicitly enable `allowLocalExecution`.
17
- 4. Read the actual config. Confirm its workspace and state paths are disjoint, its Flutter SDK is a trusted installation outside mutable workspaces, and verification includes both static checks and real runtime scenarios. Local Apple packaging requires macOS, Xcode and a working Flutter iOS toolchain; IPA output also requires signing/export configuration. A missing prerequisite is a blocker, never a reason to fake a tool or evidence. Do not replace checks with no-op commands to make a job pass.
15
+ 2. The npm package, executable and skill are all `apphx`. Run `apphx --version` and `apphx --help`. If `apphx` is an already-installed local dependency of the control project rather than on PATH, use that project's package manager for **every** apphx command: `pnpm exec apphx`, `yarn exec apphx`, or `npm exec --offline --package=apphx -- apphx`. Select from the project's `packageManager`/lockfile and run from the control project, not the app workspace. Confirm `apphx` is already installed; do not fetch a similarly named package or silently change the user's environment. If neither route is available, stop and report the missing installation. Installing a skill does not install platform SDKs.
16
+ 3. If there is no configuration, select the actual stack and platform: `apphx init --framework react-native --platform android --package-target aab --config /absolute/control/factory.json`, for example. Choices are `flutter`, `android-java`, `swift`, `react-native`, `expo`, `uni-app`, `mygo`; iOS targets `simulator`/`ipa`, Android targets `apk`/`aab`, MyGo macOS targets `app`/`dmg`. Defaults remain Flutter/iOS/simulator; android-java defaults Android/APK, Expo defaults iOS/IPA with EAS local, MyGo defaults macOS/app. `init` creates an owner-editable config, not source code. It refuses overwrite and defaults to **no local execution or cloud build authorization**. Do not add `--allow-local-execution` unless the user explicitly approves trusted deterministic commands; existing configurations require owner review before enabling it.
17
+ 4. Read the actual config and paired framework examples in the installed package's `examples/` directory. Confirm workspace/state paths are disjoint, SDKs are trusted installations outside mutable workspaces, and verification includes static checks and **real native runtime scenarios**. Adapt module names, Xcode project/workspace/scheme, package-manager scripts, device IDs, signing and exact artifact output to the owner's existing project. Non-Flutter stacks require `packaging.commands` (argv arrays) and an exact project-relative `artifactPath`; Flutter may use built-in packaging. Do not replace an existing Expo/uni-app/RN project with a Flutter app, prebuild or eject it. Commands run in the selected app directory, not necessarily the snapshot root. Run `apphx doctor /absolute/control/requirement.json --config /absolute/control/factory.json --build-only`; without the requirement, doctor only checks configured prerequisites and assumes no stack. Missing SDK/device/signing/script is a blocker, never a reason to fake evidence or use no-op checks.
18
18
 
19
19
  In examples below, replace `/absolute/control/factory.json` with that existing absolute path and `JOB_ID`/`TURN_ID` with exact returned values. Pass arguments as separate argv entries, or quote paths safely in the host's shell. Do not execute prompt or JSON fields as shell code.
20
20
 
21
+ ### Optional Harness subprocess confinement
22
+
23
+ The owner may select `isolation: { "mode": "macos-sandbox", "readOnlyPaths": [], "network": "deny" }` in the frozen configuration. It applies to Harness-launched verification/prerequisite/package commands and doctor probes, not native host-agent tools. It requires the actual macOS `sandbox-exec` backend; unsupported/unavailable execution stops rather than silently downgrading. This deprecated Apple backend is not a VM/container, resource quota, malicious-host boundary or guarantee of GUI/device IPC compatibility. For arbitrary hostile projects use a separately provisioned disposable OS/VM as well; this mode alone is not universal untrusted-code containment.
24
+
25
+ Default child capabilities cover its own workspace, isolated temporary HOME/cache, scoped system/runtime files and the executable itself. Add only reviewed existing toolchain/input files or directories to `readOnlyPaths`; paths exposing configuration/state or the shared workspace root are rejected, and their canonical identities are rechecked. Avoid broad private directories or secrets within approved trees. Use the actual runtime binary rather than a home-directory PATH shim where needed. `network: "allow"` is a separate explicit owner choice, not implied by build permission. No shell, loader or SDK override is an isolation bypass permission.
26
+
27
+ Doctor uses a disposable writable area and grants imported source only read access. Real commands may fail because the tool needs undeclared files, network or GUI services; report that prerequisite instead of broadening permissions automatically. Changing isolation invalidates previous execution proof. Artifact deletion and sandbox temporary-directory cleanup remain confined to their original trusted roots even while inherited detached children are still present. Normal process-group cleanup is preserved, but the mode does not promise to reclaim deliberately detached descendants or prevent resource exhaustion. Existing secrets/hardlinks already inside permitted readable trees remain exposed. Prepared IPA export plists receive narrow read capabilities, not access to the state directory.
28
+
21
29
  ## 2. Freeze and enqueue the actual requirement
22
30
 
23
31
  Read the bundled [requirement example](resources/requirement.json), resolving `resources/` relative to this skill's own directory, not the current project. Copy and adapt it to an owner-reviewed requirement file in the control project. Do not modify installed skill assets.
24
32
 
25
33
  If the user supplied an existing task id or asked to resume it, including a scheduled wake, **skip enqueue**. Read `status` and continue that exact id/config with `next`; never reconstruct its requirement or create a second task for the same work.
26
34
 
27
- The requirement must describe a real audience, purpose, differentiators, Flutter framework, concrete acceptance scenarios and constraints. Preserve the user's product; do not substitute a simpler app. Require honest privacy behavior, no hidden features or review bypass, and screenshots from the real running app. Clarify material unknown product choices before enqueue. Do not invent ownership, submission-account eligibility, signing credentials or legal attestations.
35
+ The requirement must describe a real audience, purpose, differentiators, framework, explicit `platform` (`ios`, `android` or `macos`), neutral top-level `version`, `channel` (`local`, `app-store`, `google-play`) and concrete acceptance scenarios/constraints. `version` defaults to `1.0.0` and `channel` to `local`; neither belongs in `apple`. `screenshotsDir` is also top-level. Java Android is Android-only; Swift is iOS-only; MyGo is macOS/local-only; App Store requires iOS and Google Play requires Android/AAB. Preserve the user's product; do not substitute a simpler app. Require honest privacy behavior, no hidden features/review bypass and real screenshots. The optional top-level `apple` metadata block is owner documentation for a manual store submission, never a requirement or a claim of approval. Shared purpose/audience is not a duplicate-admission error; assess meaningful distinction in the selected channel's research. Do not invent ownership, account eligibility, signing credentials or legal attestations.
28
36
 
29
37
  ```sh
30
38
  apphx enqueue /absolute/control/requirement.json --config /absolute/control/factory.json --build-only
@@ -32,14 +40,20 @@ apphx status JOB_ID --config /absolute/control/factory.json
32
40
  apphx next JOB_ID --config /absolute/control/factory.json --build-only
33
41
  ```
34
42
 
35
- Keep the returned immutable job id and workspace. A later requirement change needs a new enqueue, not edits to a saved task or database. For a local revision, the requirement may include `baseJobId` of a verified predecessor; apphx validates and prepares the base. Do not copy arbitrary stale build artifacts yourself.
43
+ Keep the returned immutable job id and workspace. New projects have no `project` field; the native host build turn creates the selected stack. Existing projects use `project: { "sourceDir": "/absolute/owned/repository", "directory": "apps/mobile" }` (or directory `"."` for its root). apphx pins a source snapshot; work only in the returned workspace, never the original. `directory` must stay inside the snapshot. Do not follow escaping source/local dependency symlinks or import from mutable external dependencies. A changed source after enqueue must be resubmitted honestly rather than forced through stale proof. A later requirement change needs a new enqueue, not saved-task/database edits. `baseJobId` may reference a verified/finished same-product predecessor with the same framework/platform/channel; do not copy stale artifacts yourself.
44
+
45
+ For **iOS App Store releases only**, omitting both `baseJobId` and `project.sourceDir` automatically pins the most recently enqueued finished same-product/platform/channel predecessor (`built`, `ready`, `approved` or `released`), recording `baseJobId`, `baseDigest` and `automaticBase: true`. Explicit source/base selection keeps its existing precedence and validation. The latest matching predecessor must have the same framework and valid unchanged source/dependency proof; a stale or incompatible latest version stops rather than falling back to an older version or starting fresh. Prior same-product history without a finished predecessor also stops; only a first-ever release without history may start new. Do not ask the owner to classify each release as new/update or manually copy code. A previous release is a source reuse baseline when available, not a differentiation unit; prior versions are release context, not competing portfolio products requiring artificial differentiation. Preserve application identity and data compatibility. Reuse and minimal changes are preferences, not a ban on theme, display-name, content, function or architecture changes needed for the product and its actual quality gaps.
46
+
47
+ For a batch, enqueue the entire requested set before starting research so pending peers are visible to every review. With a configured inbox, submit its individual requirements and run `apphx scan --config /absolute/control/factory.json --build-only`; otherwise enqueue each requirement once and retain its returned job id. Drive each id through `next` and its returned action. A repair verdict is a continuation of that same job, not a request for manual classification, owner-written code or a replacement task. Continue eligible jobs while another is blocked or deferred, respect each due time and existing host scheduling/attempt limits, and never reuse one package's review for the batch.
48
+
49
+ Research and review compare the same-channel portfolio including pending batch peers, using their supplied versions and available read-only source. If `next` or `complete` rejects changed peer context, abandon that exact stale token and request a fresh turn within existing budgets; do not reuse its verdict or create a replacement task. Packaging rechecks the accepted comparison before and after commands. A peer-only change returns unchanged own source to review rather than discarding its runtime proof. Scheduling notes and unrelated-channel/same-product history are not peer-comparison changes.
36
50
 
37
51
  ## 3. Dispatch exactly the persisted action
38
52
 
39
- Read the JSON from `next`; do not guess stages from memory. Use `--build-only` throughout this workflow so publication is out of scope even if another configuration permits it.
53
+ Read the JSON from `next`; do not guess stages from memory. Use `--build-only` throughout this workflow; it is accepted for CLI compatibility. Local packaging never grants submission, upload or release authority.
40
54
 
41
- - **`action: "host"`**: preserve `turn.id`; read the full `turn.prompt`, `turn.stage`, `turn.cwd` and `turn.environment`. Perform that one native host phase as below. Work inside the returned cwd and merge the returned task/toolchain overrides into your host's existing command environment; do not replace it. Configured environment values are intentionally not printed in the response. This is not a host-wide security boundary; never copy publisher secrets into task commands. Only the CLI completion call advances the task. Repeated `next` resumes the same active turn without spending a second turn, unless its task deadline has expired.
42
- - **`action: "step"`**: run `apphx step JOB_ID --config /absolute/control/factory.json --build-only` once, inspect its exit status and returned job, then ask `next` again if successful. Only deterministic verify/package stages should be needed here. `step` cannot perform research, build or review for you. Never label a host verdict as external verification.
55
+ - **`action: "host"`**: preserve `turn.id`; read the full `turn.prompt`, `turn.stage`, `turn.cwd` and `turn.environment`. Perform that one native host phase as below. Work inside the returned cwd and merge the returned task/toolchain overrides into your host's existing command environment; do not replace it. Configured environment values are intentionally not printed in the response. This is not a host-wide security boundary; never copy store credentials into task commands. Only the CLI completion call advances the task. Repeated `next` resumes the same active turn without spending a second turn, unless its task deadline has expired.
56
+ - **`action: "step"`**: run `apphx step JOB_ID --config /absolute/control/factory.json --build-only` once, inspect its exit status and returned job, then follow `next`. A returned build/research repair is actionable host work under the existing authorization, not a reason to ask the owner to fix code manually; respect its due time. Blocked/failed states remain stopped. Only deterministic verify/package stages should be needed here. `step` cannot perform research, build or review for you. Never label a host verdict as external verification.
43
57
  - **`action: "wait"`**: inspect the job's status, reason, error and due time. Report the exact blocker or scheduled time; do not busy-loop, automatically grant permission, or retry a failed command until it happens to pass. Resume with `next` after the prerequisite/due time is satisfied and the user intends to continue.
44
58
  - **`action: "done"`**: inspect the persisted outcome. `built` plus a recorded local artifact is successful local packaging. Blocked/failed/rejected outcomes are not success merely because no action remains. Report the artifact kind/path/digest and evidence, or the exact unmet requirement.
45
59
 
@@ -55,9 +69,24 @@ This explicitly abandons the current token; it does not refund the consumed turn
55
69
 
56
70
  ## 4. Native research
57
71
 
58
- Read the immutable requirement and all context in the research prompt. Use your host's web/browsing tools to read the current official [Apple App Review Guidelines](https://developer.apple.com/app-store/review/guidelines/). Evaluate **2.1, 2.3.1, 2.5.19, 4.2, 4.2.6, 4.3 and 5.1.1**, meaningful distinctness against the supplied portfolio, offline persistence/backup, privacy and accessibility. Account/content ownership for 4.2.6 cannot be attested by the model; surface unknowns.
72
+ Read the immutable requirement and the research prompt. Research produces a local package; store submission and review are manual human work outside this tool, so no channel-specific policy citation or approval claim is required:
73
+
74
+ - **local**: evaluate implementability, real device acceptance, privacy, accessibility and the supplied portfolio. Use [local-research-result.json](resources/local-research-result.json) for shape only.
75
+ - **app-store** (iOS): evaluate honest differentiation and quality for a package the owner may later submit manually. Use [research-result.json](resources/research-result.json) for shape only.
76
+ - **google-play** (Android): evaluate honest differentiation and quality for a local AAB the owner may later submit manually. Use [google-play-research-result.json](resources/google-play-research-result.json) for shape only.
77
+
78
+ For every channel, return `viable` boolean, nonempty `distinctness` and nonempty `plan`; `risks` is optional. Replace all unassessed example content with actual findings against the channel-scoped portfolio. If not viable, return false with reasons; do not invent ownership attestations or an approval promise.
59
79
 
60
- Use [research-result.json](resources/research-result.json) for the exact JSON shape, not a pre-approved verdict. Replace its unassessed content with sourced findings. Required fields: `viable` boolean, `policySources` entries with exact `rule` and official HTTPS `url` for every listed rule, `distinctness` text, and nonempty `plan`; `risks` is optional. If not viable, return false and explain the reasons rather than concealing them.
80
+ Research and independent review apply an honest differentiation and quality checklist, comparing the same-channel portfolio including pending batch peers:
81
+
82
+ - **Real value**: each package has its own genuine purpose, audience and functional behavior; identical functionality with only renamed labels is not meaningful differentiation.
83
+ - **Visual identity**: themes, layouts, colors and interaction flows are real product choices for this app, not templated reskins produced to look different.
84
+ - **Developer and identity metadata**: app name, title, icon, bundle/package id, keywords and description truthfully describe this app and its actual developer. Never forge identities, accounts, locations or submission sources.
85
+ - **Functionality**: every advertised feature works and is exercised by the frozen runtime acceptance; no hidden functionality for any audience and no fabricated screenshots or evidence.
86
+ - **Code identity**: project, folder, class, function and resource names follow this project's real conventions. Do not mutate hashes, names or resource bytes solely to defeat similarity checks.
87
+ - **Quality gate**: source, dependency and runtime proofs must be current, and independent review must cover every frozen acceptance requirement with observed evidence.
88
+
89
+ Missing owner facts (account, ownership, legal) are a blocker for that job, not permission to fabricate content. Store submission remains manual human work; nothing here bypasses, influences or pre-approves a store reviewer, and no Apple or Google Play approval is promised.
61
90
 
62
91
  Save result JSON **outside the app workspace**, for example `/absolute/control/results/JOB_ID-research.json`, then:
63
92
 
@@ -68,7 +97,27 @@ apphx next JOB_ID --config /absolute/control/factory.json --build-only
68
97
 
69
98
  ## 5. Native implementation
70
99
 
71
- Perform the returned build prompt with your own native edit, terminal and design tools in `turn.cwd`. Implement the full requirement as a real Flutter iOS project with `pubspec.yaml`, complete workflows, persistence, privacy UI and appropriate tests. For unfamiliar APIs, use real official references. Never use mock runtime evidence, placeholder features, screenshots of nonexistent UI, or a replacement product. Do not weaken configured verification or change frozen requirements/state.
100
+ Perform the returned build prompt with native edit, terminal and design tools in `turn.cwd`. Implement the full requirement in its selected stack: Flutter (`pubspec.yaml`), Java Android (Gradle/Android manifest), Swift (Xcode project/workspace), React Native/Expo (existing package scripts and native host/build profile), or uni-app (its manifests/scripts and owner-maintained native packaging). For new projects create the real matching host; for imports preserve native integrations, project structure and scripts, with no forced ejection or migration. Run resource generation that changes owned source during this turn, before external verification. For unfamiliar APIs use official references. Never fake features, runtime evidence or screenshots. Do not weaken verification or alter frozen requirements/state.
101
+
102
+ For each pending package, inspect its fresh research/review findings and any pinned source baseline. Implement the identified repairs and requested product changes. Prefer reuse and small effective changes, but allow theme, display-name, content, functional or architecture changes where appropriate; preserve application identity and data compatibility. Cosmetic changes alone do not establish meaningful differentiation. A review repair returns here automatically; do not ask the owner to write routine feedback or enqueue a replacement job. Complete the returned build turn, then let `next`/`step` obtain renewed runtime and source/dependency proof before independent review. Missing owner facts remain a blocker for this job, not permission to fabricate content or dodge review.
103
+
104
+ The bundled uni-app command pair specifically illustrates a CLI/npm project with an owner-maintained offline native host; it is not a requirement to convert other uni-app projects. Classic HBuilderX projects may have `App.vue`, `main.js`/`main.ts`, `manifest.json` and `pages.json` without `package.json`; do not require or add Node/npm, invent npm scripts or convert that project. Preserve its existing HBuilderX layout and owner-provided prerequisite, native build and real device acceptance commands. `doctor` must not infer npm requirements for this variant; only the configured owner prerequisites identify its actual build tooling.
105
+
106
+ Expo initialization uses **EAS local** for either platform, without assuming `ios/` or `android/` exists or requesting prebuild/eject. Preserve the owner's existing `eas.json`: the generated commands require a `production` profile for IPA/AAB, an `apk` profile with `android.buildType: "apk"`, or a `simulator` profile with `ios.simulator: true`. The explicit simulator profile emits `build/simulator.tar.gz`, then extracts the expected `build/App.app`; adapt the product name/archive layout to the actual project. The owner supplies EAS CLI/authentication, SDK/signing and real native acceptance scripts; local compilation does not imply the EAS CLI is network-free. Never silently switch to cloud compilation. uni-app iOS's `native/ios` path is likewise an owner-configured offline-host convention, not a promise that init generates a native project.
107
+
108
+ ### MyGo macOS: native UI and web frontend
109
+
110
+ `apphx init --framework mygo` defaults to macOS/app; `--package-target dmg` selects DMG. MyGo is macOS/local-only; other frameworks do not gain macOS support. Unsupported platform/target combinations fail before writing configuration. Keep `allowCloudBuild` false and packaging provider local. Init creates configuration, not app source or an acceptance harness. Requirements explicitly use `framework: "mygo"`, `platform: "macos"`, `channel: "local"`.
111
+
112
+ Use paired `examples/mygo.json` / `mygo.factory.json` for Go-only native UI, or `mygo-web.json` / `mygo-web.factory.json` for web. MyGo requires `go.mod` and exactly one `mygo.json` (native UI) or `mygo.config.ts` (web); web also retains its actual frontend `package.json` and dependency lock. Native UI does **not** require Bun, npm or package.json. Preserve existing layout, `project.directory` and package manager; the web pair illustrates an existing Bun `build` script, not mandatory migration. Do not auto-install tools: pinned MyGo v0.3.0 requires Go 1.27.1, `require github.com/egoist/mygo v0.3.0` and `tool github.com/egoist/mygo/cmd/mygo` in the owner's go.mod. Probe with `go tool mygo version`; never use `@latest`. The optional npm CLI distribution is `mygo-cli`, not the unrelated `mygo` package.
113
+
114
+ With a MyGo requirement, doctor runs configured prerequisites in the existing imported `project.sourceDir` / `project.directory`, using its closest owned Go workspace (or `GOWORK=off`), `GOENV=off`, `GOTOOLCHAIN=local` and `GOFLAGS=-mod=readonly`. Missing/new source is reported as not yet checkable; doctor never substitutes the control module or creates source. Generic Go availability probes are not proof that the project-pinned MyGo tool is available.
115
+
116
+ The owner must implement `go run ./cmd/acceptance` as a **real app-specific desktop harness**: launch the actual macOS app, wait for its window, drive visible controls, assert frozen scenarios, save actual screenshots and fail on errors. `go vet`, `go test`, browser-only tests and headless view tests do not replace it. A safe app build may precede runtime checks to provide the executable. No iOS simulator is involved; unavailable macOS runtime is a blocker. Prepare frontend bindings, dependency locks and other source generation during the host build turn before proof. MyGo v0.3.0 generates its client even with `-skip-build-command`; repeated generation during verify/package must leave owned source byte-identical or require renewed verification/review.
117
+
118
+ Packaging contains one direct `go tool mygo build` invocation pinned by go.mod, not a shell/npm wrapper: `-platform darwin/arm64 -sign - -skip-notarize -o build`, plus `-skip-dmg` for app only (omit for dmg). No upload, notarization or Developer ID workflow is authorized. Match name/version/architecture to actual project config: examples assume **MyGo App**, **0.1.0**, **arm64**, producing exactly `build/darwin-arm64/MyGo App.app` or, for pinned v0.3.0, `build/darwin-arm64/MyGo App 0.1.0.dmg`. Both are supported local deliverables. A `.app` must be a real executable signed bundle and a DMG must pass integrity validation; filenames alone are not proof. MyGo TypeScript configuration and owner commands are trusted executable code, not a sandbox: inspect them, keep store credentials out, and do not claim the direct-command guard constrains arbitrary project code. Included profiles are not evidence of successful builds or runtime acceptance.
119
+
120
+ Keep runtime screenshots outside the platform directory MyGo replaces, for example `build/screenshots`, not `build/darwin-arm64/screenshots`. Static `mygo.json` file inputs must remain owned and fingerprinted; duplicate fields, external resources and cache references are rejected. Declared JSON `frontendDist` under the app's `dist` or a separate `build/frontend` directory carries its actual file bytes in dependency proof, even though snapshots omit generated output; rebuild it during the host turn before verification. Do not embed the platform output directory itself. TypeScript configuration remains trusted executable code whose computed inputs require owner review; no static sandbox guarantee is implied.
72
121
 
73
122
  Native delegation may handle independent file boundaries. The implementation owner integrates before any external verification. Complete only after the source exists and the requested implementation is ready:
74
123
 
@@ -77,11 +126,25 @@ apphx complete JOB_ID TURN_ID --config /absolute/control/factory.json --build-on
77
126
  apphx next JOB_ID --config /absolute/control/factory.json --build-only
78
127
  ```
79
128
 
80
- No result JSON is required for build. Build completion only advances to deterministic verification; it is not approval or a package.
129
+ No result JSON is normally required for build. The optional `apple` metadata block in the requirement is owner documentation for a manual store submission; it is never required for local packaging and never a claim of approval. Build completion is not approval or a package.
81
130
 
82
131
  ## 6. External verification, then independent review
83
132
 
84
- The next deterministic `step` executes the configured prerequisite/static/runtime checks and records real results and source/dependency fingerprints. Read logs and evidence from the returned job or `apphx events JOB_ID --config /absolute/control/factory.json`. A compilation-only success is not runtime acceptance. Never synthesize receipts or report unavailable iOS execution as passed. Fix the concrete failure through apphx's stopped-task/retry path; do not directly move its stage.
133
+ The deterministic `step` executes configured prerequisite/static/runtime checks and records real results and source/dependency fingerprints for the selected profile. Read logs/evidence from the returned job or `apphx events JOB_ID --config /absolute/control/factory.json`. Compilation-only success is not runtime acceptance; web-only tests are not native acceptance for Expo/uni-app. Never synthesize receipts or claim unavailable iOS/Android execution passed. Fix actual failures through stopped-task/retry, not direct stage edits. Changing commands, execution environment, toolchain, packaging provider/commands/output, package target or obfuscation config invalidates prior proof and requires renewed verification/review; retry preserves budgets. Uncertain cloud packaging runs require reconciliation, not replay.
134
+
135
+ ### Optional deterministic obfuscation (runs between build and verify)
136
+
137
+ When the factory config sets `obfuscation`, completing the build turn advances to an `obfuscate` step before verification: the runner executes `obfuscation.command` (default `obfuscator`) with `--project <workspace project> --config <obfuscation.configPath> --framework <stack>` and the optional `--seed`, so the verified and packaged code is the obfuscated code. `configPath` is resolved against the factory config directory and must exist as a regular file. The obfuscated source is exactly what verify checks, review approves and package ships; obfuscation never runs after verification.
138
+
139
+ The bundled `obfuscator` package is deterministic: identical project + config + seed produce byte-identical output, in place, never writing outside the walked owned project. Installing `apphx` also installs the `obfuscator` executable (the package ships the private obfuscator), and `apphx obfuscator <project> --config <file> [--framework <stack>] [--seed <text>]` runs it directly; the harness default `obfuscation.command` resolves to that bundled executable. Point `obfuscation.command` at a different binary only to override it. Its JSON config supports:
140
+ - `project`: `name: { from, to }` (whole-word display-name scrub in framework config files), `directories: [...]` (seeded directory renames with reference rewrites), `uuids: true` (Xcode-UUID remapping that preserves the internal reference graph)
141
+ - `resources`: `rename: { mappings, generated }` (asset stem renames with reference rewrites; `generated` deterministically renames that many discovered stems to seed-derived tokens), `hashPerturb: { bytes }` (decode-safe hash perturbation for PNG/JPEG/GIF), `images: { recolor, recolorAll }` (PNG color remap / hue-shift / invert / channel order)
142
+ - `content`: `sensitiveWords`, `controlColors`, `fontColors` (whole-word scrub and hex-color remap across text and code, never binary payloads)
143
+ - `code`: `removeComments`, `encryptStrings`, `renameIdentifiers`, `junkCode`, `keywords`. `renameIdentifiers: { generated }` additionally renames that many discovered top-level declarations (classes, top-level functions) to seed-derived tokens, consistently across files; generated renames never touch entrypoints (`main`, `init`) or build-generated files (`*.g.dart`, `*.freezed.dart`, …).
144
+
145
+ Seed semantics: identical project + config + seed always produce byte-identical output, while directory tokens, UUID mappings, hash-perturb payloads, junk names and every `generated` rename differ per seed. Mappings, recolor rules, sensitive words and name scrubbing are config-driven: vary them per app when those surfaces must also differ.
146
+
147
+ Obfuscation must keep the app buildable: the ordinary verify/checks/review/package stages run unchanged afterward, and any breakage is a task failure repaired through the stopped-task/retry loop. Never weaken acceptance or verification to accommodate a failing obfuscation config.
85
148
 
86
149
  When `next` returns a **review** turn, use a **fresh native reviewer context** that did not implement the change. Give it the exact review prompt, requirement, workspace and external evidence. Have it independently inspect every acceptance scenario, code and real evidence, with **no source/dependency/screenshot edits**. Evidence-producing commands that mutate the verified source invalidate approval. An implementation agent's second self-review is not independent.
87
150
 
@@ -98,6 +161,20 @@ apphx rejects incomplete evidence, rejected verdicts and changed fingerprints. I
98
161
 
99
162
  ## 7. Package locally and hand off
100
163
 
101
- Run the returned package `step` once with `--build-only`, then inspect `status` and `next`. Packaging produces a local simulator build or, when explicitly configured with signing prerequisites, an IPA. Report only recorded artifact paths/digests and exercised checks, including any remaining environmental limitation. Local packaging is not App Store submission, approval, TestFlight availability or release.
164
+ Recognizable direct native IPA exports (`xcodebuild -exportArchive` or direct `xcrun xcodebuild`) are prevalidated across the complete packaging sequence before any packaging command. Export options must select local `export` (or omit `destination`); the runner substitutes an immutable checked plist snapshot and cleans it afterward. Shell/npm wrappers remain trusted owner code, not a sandbox. Missing or ambiguous export-options arguments are blockers.
165
+
166
+ Run the returned package `step` once with `--build-only`, then inspect `status`/`next`. Output is the selected local simulator `.app`, signed `.ipa`, `.apk` or `.aab`. The configured packager must produce a fresh nonempty artifact at its exact generated-output path without changing verified source/dependencies. No arbitrary artifact glob or stale file is evidence. Report only recorded paths/digests, exercised checks and remaining environment limitations. These bundled command profiles have not been built or runtime-tested merely by being included here; owner adaptation and actual task evidence are required.
167
+
168
+ `packaging.provider: "cloud"` additionally requires explicit owner-approved `allowCloudBuild: true`; defaults remain local. Cloud commands can create remote work, so never enable them implicitly or blindly replay an uncertain run. Preserve the owner's existing build service/profile.
169
+
170
+ For an explicitly permitted cloud packaging provider, doctor validates the requirement/config and imported project profile but relies on owner-configured prerequisites rather than adding local SDK probes. This does not waive the task's required real runtime acceptance commands.
171
+
172
+ Store submission, upload and review are manual human work outside this tool; this skill never authorizes or performs them. Local packaging is not store submission, approval, TestFlight availability or release. This workflow ends at the recorded artifact or an accurately reported blocker.
173
+
174
+ ## 8. Maintainer behavior, runtime and performance checks
175
+
176
+ The distributed package contains `evals/`, `scripts/` and `examples/runtime/`; these tools launch neither models nor another coding agent. `node evals/policy.mjs prepare /absolute/fresh-run` prepares seven separate controlled workflows. Retain its manifest SHA-256 outside actor access, give each fresh native actor only the neutral case instructions, and hand review turns to another fresh context. After actors stop, run `node evals/policy.mjs score /absolute/fresh-run --manifest-sha256 HASH`. Scoring checks actual persisted CLI transitions, frozen inputs/checks, source and metadata changes, genuine local runtime/persistence oracles and rejected-command receipts. Unrun or incomplete cases remain unfinished; supplied grades are ignored. Do not let actors inspect controller expectations. This is a controlled JavaScript workflow—not iOS UI, legal-account evidence, store approval, authenticated reviewer identity or a sandbox against arbitrary hostile fixture code. Reprepare after any distribution/evaluator change; never update frozen baselines to conceal a failure.
177
+
178
+ `node scripts/runtime-smoke.mjs --help` describes installed-tool prerequisites and fresh-output arguments for actual Android Java APK/native UI and MyGo native/WKWebView `.app` workflows. Android owns a fresh AVD/private ADB server and ephemeral signing key; never target a user device. Its direct installed-SDK compilation path is explicit, not evidence of Gradle compatibility. MyGo uses existing pinned module/frontend caches without installing packages. Workflows retain original task ids across abandoned/reclaimed turns, assert UI/backend state and relaunch persistence, save screenshots, check signed native artifacts and clean only owned runtime processes. Do not treat a source fixture or help output as successful execution; iOS needs its own actual device/simulator surface.
102
179
 
103
- Do not call `authorize`, upload with other tools, enable `allowSubmit`/`allowRelease`, or run publication/monitoring on the strength of this skill. Publication requires a separate explicit owner request, the existing apphx permission/receipt gates, truthful account ownership, signing and Apple prerequisites. This workflow ends at the local artifact or an accurately reported blocker.
180
+ `node benchmarks/peer-context.mjs prepare FRESH_ROOT` freezes the production ten-project workload, then `baseline ROOT` and `compare ROOT CANDIDATE_DIST` collect paired measurements, exact output/stale-input correctness and separate profiles. Worker errors, signals, malformed reports or incomplete work fail the run; old sample output is never reused. Request-scoped comparison reuse does not cache across requests or weaken fresh completion/package validation. Timings cover the named Harness workload, not mobile compilation or store submission.
@@ -0,0 +1,6 @@
1
+ {
2
+ "viable": false,
3
+ "distinctness": "Unassessed Google Play example: compare this package's actual utility and identity with the supplied channel-scoped portfolio.",
4
+ "risks": ["This example has not assessed the product, built an AAB or verified its behavior.", "The harness hands off a local AAB and does not automate store submission; store review remains manual human work outside this tool."],
5
+ "plan": ["Assess real user value, honest identity metadata, privacy behavior and meaningful differentiation against same-channel peers.", "Assess the real Android runtime acceptance and signed AAB packaging profile; return a product-specific plan or preserve viable=false with blockers."]
6
+ }
@@ -0,0 +1,6 @@
1
+ {
2
+ "viable": false,
3
+ "distinctness": "Unassessed local example: inspect the actual requirement and supplied channel-scoped portfolio before returning a real verdict.",
4
+ "risks": ["No implementation or runtime acceptance has been assessed by this example."],
5
+ "plan": ["Assess the selected stack, imported project constraints, owner-approved commands, privacy, accessibility and real device scenarios.", "Return a concrete implementation and verification plan for the actual product, or preserve viable=false with exact blockers. No store approval claim is needed for local delivery."]
6
+ }
@@ -2,6 +2,10 @@
2
2
  "id": "pack-balance",
3
3
  "name": "行李配重与打包助手",
4
4
  "framework": "flutter",
5
+ "platform": "ios",
6
+ "channel": "local",
7
+ "version": "1.0.0",
8
+ "screenshotsDir": "build/screenshots",
5
9
  "purpose": "离线规划多个行李包的重量,完成出发打包与返程核对,减少遗漏和超重",
6
10
  "audience": "需要管理随身包与托运行李的个人旅客",
7
11
  "differentiators": [
@@ -28,12 +32,5 @@
28
32
  "导入损坏、未知版本或字段非法的备份时给出可操作错误,原数据不被部分覆盖",
29
33
  "在无网络、空清单、大字体与 VoiceOver 标签场景下完成创建、分配、勾选和恢复流程",
30
34
  "截图来自真实运行页面,隐私说明和应用行为一致,不宣称保证航空公司接受或苹果过审"
31
- ],
32
- "apple": {
33
- "bundleId": "com.example.packbalance",
34
- "version": "1.0.0",
35
- "buildNumber": "1",
36
- "locale": "zh-Hans",
37
- "screenshotsDir": "build/screenshots"
38
- }
35
+ ]
39
36
  }
@@ -1,21 +1,12 @@
1
1
  {
2
2
  "viable": false,
3
- "policySources": [
4
- { "rule": "2.1", "url": "https://developer.apple.com/app-store/review/guidelines/#app-completeness" },
5
- { "rule": "2.3.1", "url": "https://developer.apple.com/app-store/review/guidelines/#accurate-metadata" },
6
- { "rule": "2.5.19", "url": "https://developer.apple.com/app-store/review/guidelines/#software-requirements" },
7
- { "rule": "4.2", "url": "https://developer.apple.com/app-store/review/guidelines/#minimum-functionality" },
8
- { "rule": "4.2.6", "url": "https://developer.apple.com/app-store/review/guidelines/#minimum-functionality" },
9
- { "rule": "4.3", "url": "https://developer.apple.com/app-store/review/guidelines/#spam" },
10
- { "rule": "5.1.1", "url": "https://developer.apple.com/app-store/review/guidelines/#data-collection-and-storage" }
11
- ],
12
- "distinctness": "Unassessed example: evaluate the owner's actual requirements against the supplied portfolio and current official policies before returning a real verdict.",
3
+ "distinctness": "Unassessed example: evaluate this pending package's real purpose, audience, function, visual identity, developer/app metadata and code identity against the same-channel portfolio. Identical functionality with renamed labels is not meaningful differentiation.",
13
4
  "risks": [
14
- "The current policy contents have not been researched by this example.",
15
- "The content owner and submitting account's eligibility under 4.2.6 are unknown; a model must not invent an attestation."
5
+ "No implementation or runtime acceptance has been assessed by this example.",
6
+ "Store submission, account setup and platform review are manual human work outside this tool; nothing here pre-approves a store reviewer."
16
7
  ],
17
8
  "plan": [
18
- "Read the current official policy sections and assess viability, ownership, distinct utility, privacy and runtime acceptance for the actual product.",
19
- "If viable, return a concrete product-specific implementation and verification plan; otherwise preserve viable=false and report the specific blockers."
9
+ "Assess real value, honest visual identity, truthful developer and app metadata, exercised functionality and genuine code identity for this package, comparing same-channel peers and treating earlier versions of this same app as its source baseline.",
10
+ "Plan concrete agent work followed by real runtime verification and a fresh independent review; preserve viable=false with exact blockers when owner facts are missing. Do not promise store approval or add unrequested features."
20
11
  ]
21
12
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "approved": false,
3
3
  "findings": [
4
- "This is a result-shape example, not a completed review. A fresh independent reviewer must inspect the real implementation and external evidence."
4
+ "This is an unassessed result-shape example, not a completed review. A fresh independent reviewer must inspect this package's actual source, effective metadata, runtime evidence and same-channel peers; another package's pass does not approve this job."
5
5
  ],
6
6
  "acceptanceEvidence": []
7
7
  }