Skip to content

Commit dcd162f

Browse files
committed
Merge remote-tracking branch 'origin/staging' into feat/func-cli-resolver
# Conflicts: # apps/sim/lib/copilot/vfs/workspace-vfs.ts # apps/sim/lib/core/config/env-flags.ts # apps/sim/lib/execution/remote-sandbox/pi-lifetime.test.ts # apps/sim/lib/execution/remote-sandbox/pi-lifetime.ts # apps/sim/lib/execution/remote-sandbox/provider.ts # scripts/setup/checks.ts
2 parents d192e21 + 8ca3b27 commit dcd162f

183 files changed

Lines changed: 11460 additions & 2046 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.agents/skills/add-block/SKILL.md

Lines changed: 46 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,32 @@ export const {ServiceName}Block: BlockConfig = {
163163

164164
Optional companions: `credentialLabels` (override the picker's section/connect-row copy) and `allowServiceAccounts: true` (trigger-mode only — list service accounts, which triggers otherwise exclude; set only when the trigger's polling path can resolve a service-account token). The connect modal, provider families (Google JSON key, Atlassian token, token-paste, client-credential, Slack bot), and the preview gate are all resolved from `serviceAccountProviderId` — you don't wire them per block.
165165

166+
### OAuth deployment availability (required for integration blocks)
167+
168+
A visible tools-category block with OAuth is deployment-gated. Its `oauth-input.serviceId` is
169+
projected into `apps/sim/lib/integrations/integrations.json`, then resolved through
170+
`resolveOAuthClientCapabilityId()` in `apps/sim/lib/core/config/env-capabilities.ts`.
171+
172+
When adding or changing an OAuth integration block:
173+
174+
1. Keep exactly one distinct OAuth `serviceId` across the block's `oauth-input` subBlocks.
175+
2. Confirm that service ID resolves to an entry in `OAUTH_CLIENT_CAPABILITIES`. Google and
176+
Microsoft service IDs intentionally share their provider-level capability; do not add duplicate
177+
entries for those aliases.
178+
3. For a new capability, add its required client fields to `OAUTH_CLIENT_CAPABILITIES` and ensure
179+
every referenced field exists in the env schema in `apps/sim/lib/core/config/env.ts`. Then add
180+
the matching `text` or `secret` input modes to `OAUTH_CLIENT_SETUP_FIELDS` in
181+
`scripts/setup/capability-config.ts`. The CLI catalog is exhaustively typed and checked against
182+
the runtime field list; do not infer secrecy from the field name.
183+
4. If the canonical OAuth service declares `serviceAccountProviderId`, keep
184+
`SERVICE_ACCOUNT_METADATA_BY_OAUTH_SERVICE_ID` in
185+
`apps/sim/lib/integrations/service-account-metadata.ts` aligned. Set
186+
`deploymentRequirement` only when the service-account path is preview-gated or depends on the
187+
OAuth client fields; otherwise omit it.
188+
189+
Missing capability metadata is a runtime configuration error, not a reason to make the integration
190+
silently available.
191+
166192
### Selectors (with dynamic options)
167193
```typescript
168194
// Channel selector (Slack, Discord, etc.)
@@ -919,12 +945,25 @@ Derive templates from the service's real use cases. Each prompt should name a co
919945
- **Ground every skill in operations the block actually exposes** — cross-check each skill's steps against `tools.access`. Never describe an action the integration cannot perform.
920946
- **Derive skills from real, popular use cases found online — never invent them.** Web-search the service's documented use cases (vendor use-case/solutions pages, official docs describing the workflow, reputable "top automations for X" articles) and only add a skill you can source as something people genuinely do with the service. Do not hallucinate skills.
921947

922-
## Generated tool metadata
948+
## Generated artifacts
923949

924-
Adding a block on its own needs **no** regeneration — a block references existing tool IDs through `tools.access` and does not change any tool's shape.
950+
Adding a block on its own needs no **tool metadata** regeneration — a block references existing
951+
tool IDs through `tools.access` and does not change any tool's shape.
925952

926953
But if the same change also adds, edits **or removes** a tool, run `bun run tool-metadata:generate` and commit the result, or CI fails on stale artifacts. That matters here because a block's `outputs` are authored to match its tools' outputs, and the UI now reads those from the generated metadata rather than the executable registry — an unregenerated tool change makes the block's outputs disagree with what the panel renders. See `.agents/skills/tool-registry-boundary/SKILL.md`.
927954

955+
A visible integration block does require the generated integration catalog and docs to be refreshed.
956+
After adding or changing one, run:
957+
958+
```bash
959+
bun run scripts/generate-docs.ts
960+
bun run integration-catalog:check
961+
```
962+
963+
The catalog check independently derives deployment metadata from the executable block registry and
964+
compares it with the committed `apps/sim/lib/integrations/integrations.json`. Review the generated
965+
diff and keep only intentional changes.
966+
928967
## Checklist Before Finishing
929968

930969
- [ ] `integrationType` is set to the correct `IntegrationType` enum value
@@ -934,12 +973,17 @@ But if the same change also adds, edits **or removes** a tool, run `bun run tool
934973
- [ ] DependsOn set for fields that need other values
935974
- [ ] Required fields marked correctly (boolean or condition)
936975
- [ ] OAuth inputs have correct `serviceId` and `requiredScopes: getScopesForService(serviceId)`
976+
- [ ] Every OAuth `serviceId` resolves through `resolveOAuthClientCapabilityId()` to the correct `OAUTH_CLIENT_CAPABILITIES` entry
977+
- [ ] Any new OAuth capability fields exist in `apps/sim/lib/core/config/env.ts`
978+
- [ ] If the OAuth service supports service accounts, `SERVICE_ACCOUNT_METADATA_BY_OAUTH_SERVICE_ID` matches its canonical `serviceAccountProviderId` and deployment requirement
937979
- [ ] Scope descriptions added to `SCOPE_DESCRIPTIONS` in `lib/oauth/utils.ts` for any new scopes
938980
- [ ] Tools.access lists all tool IDs (snake_case)
939981
- [ ] Tools.config.tool returns correct tool ID (snake_case)
940982
- [ ] Outputs match tool outputs
941983
- [ ] Block + meta registered in registry-maps.ts (`BLOCK_REGISTRY` / `BLOCK_META_REGISTRY`)
942984
- [ ] If any tool was added, changed or removed alongside the block: ran `bun run tool-metadata:generate` and committed the artifacts
985+
- [ ] Ran `bun run scripts/generate-docs.ts`, reviewed the generated diff, and committed the integration catalog changes
986+
- [ ] `bun run integration-catalog:check` passes
943987
- [ ] If icon missing: asked user to provide SVG
944988
- [ ] If triggers exist: `triggers` config set, trigger subBlocks spread
945989
- [ ] Optional/rarely-used fields set to `mode: 'advanced'`

.agents/skills/add-integration/SKILL.md

Lines changed: 47 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,8 @@ Adding an integration involves these steps in order:
1717
4. **Add Icon** - Add the service's brand icon
1818
5. **Create Triggers** (optional) - If the service supports webhooks
1919
6. **Register** - Register tools, block, and triggers in their registries
20-
7. **Generate Docs** - Run the docs generation script
20+
7. **Configure Deployment Availability** - Wire OAuth client and service-account metadata
21+
8. **Generate and Validate the Catalog** - Regenerate docs/catalog artifacts and run drift checks
2122

2223
## Step 1: Research the API
2324

@@ -465,15 +466,48 @@ export const TRIGGER_REGISTRY: TriggerRegistry = {
465466
}
466467
```
467468

468-
## Step 7: Generate Docs
469+
## Step 7: Configure Deployment Availability
470+
471+
Do this for every visible OAuth integration. API-key and unauthenticated integrations do not need
472+
an OAuth client capability.
473+
474+
The block's `oauth-input.serviceId` is the canonical link between the generated integration catalog,
475+
the OAuth service configuration, deployment availability, and the setup CLI.
476+
477+
1. Ensure the block has exactly one distinct OAuth `serviceId` and that it matches the canonical
478+
service entry in `apps/sim/lib/oauth/oauth.ts`.
479+
2. Confirm `resolveOAuthClientCapabilityId(serviceId)` resolves to the intended provider entry in
480+
`OAUTH_CLIENT_CAPABILITIES` in `apps/sim/lib/core/config/env-capabilities.ts`. Google and
481+
Microsoft service IDs deliberately share provider-level capabilities.
482+
3. For a new OAuth provider, add the required client fields to `OAUTH_CLIENT_CAPABILITIES`, add
483+
every referenced field to the env schema in `apps/sim/lib/core/config/env.ts`, and add the
484+
matching `text` or `secret` entries to `OAUTH_CLIENT_SETUP_FIELDS` in
485+
`scripts/setup/capability-config.ts`. Do not create integration-specific setup logic or infer
486+
secret fields from naming; the CLI mapping is exhaustively checked against the runtime fields.
487+
4. If the canonical OAuth service has `serviceAccountProviderId`, add the matching projection to
488+
`SERVICE_ACCOUNT_METADATA_BY_OAUTH_SERVICE_ID` in
489+
`apps/sim/lib/integrations/service-account-metadata.ts`. Use:
490+
- no `deploymentRequirement` when the service-account path works independently of OAuth client fields;
491+
- `'oauth-client'` when it requires the same deployment OAuth client fields;
492+
- `'preview-gated'` when availability is controlled by the service-account preview block.
493+
494+
Never add a permissive fallback for missing capability metadata. A visible OAuth integration without
495+
a resolvable capability must fail validation.
496+
497+
## Step 8: Generate and Validate the Catalog
469498

470499
Run the documentation generator:
471500
```bash
472501
bun run scripts/generate-docs.ts
502+
bun run integration-catalog:check
473503
```
474504

475505
This creates `apps/docs/content/docs/en/integrations/{service}.mdx` — one page per service carrying the block's Actions and, if it has one, its Triggers section. Never hand-edit generated pages; the only editable region is the `{/* MANUAL-CONTENT */}` block (see `scripts/README.md`).
476506

507+
The same generator refreshes `apps/sim/lib/integrations/integrations.json`. The catalog check then
508+
derives the deployment-relevant fields from the executable block registry and compares them with the
509+
committed projection. Review the generated diff and keep only intentional changes.
510+
477511
## V2 Integration Pattern
478512

479513
If creating V2 versions (API-aligned outputs):
@@ -524,6 +558,13 @@ If creating V2 versions (API-aligned outputs):
524558
- [ ] Used `getCanonicalScopesForProvider()` in `auth.ts` (never hardcode)
525559
- [ ] Used `getScopesForService()` in block `requiredScopes` (never hardcode)
526560

561+
### Deployment Availability (if OAuth service)
562+
- [ ] Block declares exactly one distinct `oauth-input.serviceId`
563+
- [ ] `resolveOAuthClientCapabilityId(serviceId)` resolves to the intended `OAUTH_CLIENT_CAPABILITIES` entry
564+
- [ ] Every new OAuth capability field exists in `apps/sim/lib/core/config/env.ts`
565+
- [ ] Runtime OAuth fields live in `OAUTH_CLIENT_CAPABILITIES`; matching CLI input modes live in the exhaustively checked `OAUTH_CLIENT_SETUP_FIELDS`
566+
- [ ] If `serviceAccountProviderId` is configured, `SERVICE_ACCOUNT_METADATA_BY_OAUTH_SERVICE_ID` has the matching projection and deployment requirement
567+
527568
### Icon
528569
- [ ] Asked user to provide SVG
529570
- [ ] Added icon to `components/icons.tsx`
@@ -542,6 +583,8 @@ If creating V2 versions (API-aligned outputs):
542583
### Docs
543584
- [ ] Ran `bun run scripts/generate-docs.ts`
544585
- [ ] Verified docs file created
586+
- [ ] Reviewed and committed the generated `apps/sim/lib/integrations/integrations.json` change
587+
- [ ] `bun run integration-catalog:check` passes
545588

546589
### Final Validation (Required)
547590
- [ ] Read every tool file and cross-referenced inputs/outputs against the API docs
@@ -886,3 +929,5 @@ requiredScopes: getScopesForService('{service}'),
886929
10. **Complex inputs need wandConfig** - Timestamps, JSON arrays, and other hard-to-type values should have `wandConfig` enabled
887930
11. **Never hardcode scopes** - Use `getScopesForService()` in blocks and `getCanonicalScopesForProvider()` in auth.ts
888931
12. **Always add scope descriptions** - New scopes must have entries in `SCOPE_DESCRIPTIONS` within `lib/oauth/utils.ts`
932+
13. **OAuth service IDs need deployment capabilities** - Every visible OAuth integration must resolve through `OAUTH_CLIENT_CAPABILITIES`; shared Google/Microsoft aliases map to their provider capability
933+
14. **Keep runtime and presentation separate** - Runtime OAuth fields live in `env-capabilities.ts`; CLI input modes live in the exhaustively checked `scripts/setup/capability-config.ts` mapping

.agents/skills/ship/SKILL.md

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -54,17 +54,23 @@ When the user runs `/ship`:
5454
```
5555
Then `git status --short` to see what regenerated — those files must be staged in step 7 alongside your own changes.
5656

57-
**Do NOT blanket-run the domain generators here.** `mship:generate` (`generate-mship-contracts.ts`) is an **umbrella** that drives all nine mothership contract generators (`mship-contracts`, `billing-protocol-contract`, `mship-tools`, the four `trace-*`, `metrics-contract`, `vfs-snapshot-contract`) and biome-formats `apps/sim/lib/copilot/generated/` — never run it *and* its constituents (they write the same files and corrupt each other in parallel), and never run it on an ordinary ship: it reads an **external** copilot-contract source that isn't checked out in most worktrees, so it hard-fails with `ENOENT` and would abort ship for an unrelated reason. `generate:pi-model-catalog` (under `apps/sim`) likewise regenerates from the installed Pi package, not repo source. Only when **this PR's diff actually touches** a domain generator's input do you regenerate it deliberately and run its matching `:check` (`bun run mship:check` / the individual `*:check`) — with the external source present.
57+
**Do NOT blanket-run the domain generators here.** `mship:generate` (`generate-mship-contracts.ts`) is an **umbrella** that drives all nine mothership contract generators (`mship-contracts`, `billing-protocol-contract`, `mship-tools`, the four `trace-*`, `metrics-contract`, `vfs-snapshot-contract`) and biome-formats `apps/sim/lib/copilot/generated/` — never run it *and* its constituents (they write the same files and corrupt each other in parallel), and never run it on an ordinary ship: it reads an **external** copilot-contract source that isn't checked out in most worktrees, so it hard-fails with `ENOENT` and would abort ship for an unrelated reason. `generate:pi-model-catalog` (under `apps/sim`) likewise regenerates from the installed Pi package, not repo source. `scripts/generate-docs.ts` rewrites the integration docs and client-safe catalog; run it when this PR changes their block/icon/landing-content inputs or when `integration-catalog:check` reports drift, then review its broad generated diff. Only when **this PR's diff actually touches** a domain generator's input do you regenerate it deliberately and run its matching `:check` (`bun run mship:check` / the individual `*:check`) — with the external source present.
5858

59-
**Phase B — run lint + every audit CI enforces, in parallel, and abort ship if any fails.** `bun run lint` first (it autofixes formatting and mutates files, so don't parallelize it with the read-only audits), then fan the rest out and collect exit codes. This is exactly the read-only audit set from CI's `Lint and Test` job (all in-repo, runnable in any worktree):
59+
**Phase B — run lint + every audit CI enforces, in parallel, and abort ship if any fails.** Before running the commands, compare this list with `.github/workflows/test-build.yml`; when CI adds an audit, run it and update this skill instead of trusting a stale snapshot. The env-flag audit is currently an inline workflow block rather than a package script: when `apps/sim/lib/core/config/env-flags.ts` changed, run that current workflow block verbatim instead of copying a second version into this skill. Run `bun run lint` first (it autofixes formatting and mutates files, so don't parallelize it with the read-only audits), then run the base-sensitive block-registry check, then fan the independent audits out and collect exit codes:
6060
```bash
6161
# autofix formatting first (mutating; not parallel-safe with the audits). Gate its exit too —
6262
# a non-zero lint (unfixable errors) must abort before the audits run, not be ignored.
6363
bun run lint || { echo "❌ lint failed — do not ship"; exit 1; }
64+
bun run apps/sim/scripts/check-block-registry.ts origin/staging || {
65+
echo "❌ block registry audit failed — do not ship"
66+
exit 1
67+
}
6468
rm -f /tmp/ship-audit-results
65-
for s in check:boundaries check:api-validation:strict check:utils check:zustand-v5 \
69+
for s in check:boundaries check:api-validation:strict check:desktop-bridge check:desktop-ipc \
70+
check:utils check:zustand-v5 \
6671
check:react-query check:client-boundary check:bare-icons check:icon-paths \
67-
check:realtime-prune skills:check agent-stream-docs:check; do
72+
check:realtime-prune check:tool-registry-boundary tool-metadata:check \
73+
integration-catalog:check skills:check agent-stream-docs:check; do
6874
( bun run "$s" >"/tmp/ship-audit-${s//:/-}.log" 2>&1; echo "$? $s" >>/tmp/ship-audit-results ) &
6975
done
7076
wait
@@ -150,4 +156,3 @@ gh pr create --base staging --title "COMMIT_MESSAGE" --body "PR_BODY"
150156
- "Tested manually" is acceptable for testing section; include lint, boundary validation, and (when migrations changed) `check:migrations` results when run
151157
- Checkboxes filled in appropriately
152158
- No screenshots section unless UI changes
153-

0 commit comments

Comments
 (0)