@synap-core/workspace-templates 0.12.0 → 0.24.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.
- package/README.md +509 -0
- package/automations/bookmark-enrichment.automation.json +321 -0
- package/automations/github-pr-events.automation.json +505 -0
- package/automations/mail-feed.automation.json +86 -0
- package/automations/ship-a-change-checks-green.automation.json +106 -0
- package/automations/ship-a-change-checks-red.automation.json +106 -0
- package/automations/ship-a-change-deployed.automation.json +56 -0
- package/automations/ship-a-change-pr-merged.automation.json +110 -0
- package/automations/ship-a-change-pr-opened.automation.json +104 -0
- package/automations/url-bookmark-capture.automation.json +132 -0
- package/capabilities/agency-skills.capability.json +157 -0
- package/capabilities/apify.capability.json +265 -0
- package/capabilities/apollo.capability.json +120 -0
- package/capabilities/arch-backend.capability.json +97 -0
- package/capabilities/arch-client-intelligence.capability.json +401 -0
- package/capabilities/backblaze-b2.capability.json +205 -0
- package/capabilities/cal-com.capability.json +266 -0
- package/capabilities/canva.capability.json +274 -0
- package/capabilities/claude-code-routines.capability.json +172 -0
- package/capabilities/claude-managed-agents.capability.json +215 -0
- package/capabilities/client-comms-report.capability.json +246 -0
- package/capabilities/content-idea-to-production.capability.json +29 -0
- package/capabilities/datagouv.capability.json +315 -0
- package/capabilities/discord-bot.capability.json +157 -0
- package/capabilities/dropbox.capability.json +281 -0
- package/capabilities/exa.capability.json +109 -0
- package/capabilities/fal-ai.capability.json +83 -0
- package/capabilities/fal-media-lab.capability.json +158 -0
- package/capabilities/fireflies.capability.json +191 -0
- package/capabilities/freellmapi.capability.json +114 -0
- package/capabilities/generic-apikey.capability.json +92 -0
- package/capabilities/github-merge.capability.json +99 -0
- package/capabilities/github-read.capability.json +325 -0
- package/capabilities/governance-tighten-recommender.capability.json +81 -0
- package/capabilities/jev.capability.json +226 -0
- package/capabilities/lead-conversion-enrollment.capability.json +246 -0
- package/capabilities/mail-feed.capability.json +277 -0
- package/capabilities/mailgun.capability.json +52 -0
- package/capabilities/nango-google.capability.json +639 -0
- package/capabilities/notion.capability.json +417 -0
- package/capabilities/omniroute.capability.json +137 -0
- package/capabilities/posthog-analytics.capability.json +258 -0
- package/capabilities/postiz.capability.json +467 -0
- package/capabilities/proactive-digest.capability.json +190 -0
- package/capabilities/proton.capability.json +288 -0
- package/capabilities/replicate-rvm.capability.json +97 -0
- package/capabilities/research-methods.capability.json +57 -0
- package/capabilities/shopify.capability.json +395 -0
- package/capabilities/slack.capability.json +369 -0
- package/capabilities/stripe.capability.json +1496 -0
- package/capabilities/telegram-bridge.capability.json +56 -0
- package/capabilities/treg.capability.json +102 -0
- package/capabilities/unipile-linkedin.capability.json +494 -0
- package/capabilities/vercel.capability.json +424 -0
- package/dist/define-DqoItRiR.d.ts +1370 -0
- package/dist/index.d.ts +174 -900
- package/dist/index.js +26447 -24075
- package/dist/index.js.map +1 -1
- package/dist/wire.d.ts +222 -0
- package/dist/wire.js +77 -0
- package/dist/wire.js.map +1 -0
- package/package.json +27 -4
- package/retired.yaml +136 -0
- package/skills/app-factory-build-slice/SKILL.md +70 -0
- package/skills/app-factory-build-slice.catalog.json +17 -0
- package/skills/app-factory-design-canvas/SKILL.md +96 -0
- package/skills/app-factory-design-canvas.catalog.json +17 -0
- package/skills/app-factory-design-review/SKILL.md +105 -0
- package/skills/app-factory-design-review.catalog.json +18 -0
- package/skills/app-factory-research/SKILL.md +123 -0
- package/skills/app-factory-research.catalog.json +17 -0
- package/skills/bookmark-enrichment/SKILL.md +40 -0
- package/skills/carousel-format/carousel-format.skill.json +18 -0
- package/skills/collage-broll/collage-broll.skill.json +20 -0
- package/skills/content-taste/content-taste.skill.json +18 -0
- package/skills/creative-director/creative-director.skill.json +18 -0
- package/skills/design-critique/SKILL.md +138 -0
- package/skills/design-critique.catalog.json +12 -0
- package/skills/designing-with-real-components/SKILL.md +140 -0
- package/skills/designing-with-real-components.catalog.json +12 -0
- package/skills/edit-loop/edit-loop.skill.json +25 -0
- package/skills/facecam-edit/facecam-edit.skill.json +24 -0
- package/skills/mapping-the-server/SKILL.md +54 -0
- package/skills/math-explainer-manimgx/math-explainer-manimgx.skill.json +20 -0
- package/skills/motion-quality-gates/motion-quality-gates.skill.json +20 -0
- package/skills/open-design-edit/open-design-edit.skill.json +24 -0
- package/skills/reading-client-progress/SKILL.md +65 -0
- package/skills/routing-to-channels/SKILL.md +54 -0
- package/skills/stellar-scf-grants-advisor/ASSOCIATE-CHEATSHEET.md +133 -0
- package/skills/stellar-scf-grants-advisor/ASSOCIATE-ONBOARDING-GUIDE.md +761 -0
- package/skills/stellar-scf-grants-advisor/CLIENT-FAQ.md +181 -0
- package/skills/stellar-scf-grants-advisor/PARTNER-HANDOVER.md +130 -0
- package/skills/stellar-scf-grants-advisor/SKILL.md +102 -0
- package/skills/stellar-scf-grants-advisor/examples/README.md +43 -0
- package/skills/stellar-scf-grants-advisor/examples/chat-summary-templates.md +158 -0
- package/skills/stellar-scf-grants-advisor/examples/corpus-comparable-rows.md +136 -0
- package/skills/stellar-scf-grants-advisor/examples/q10-team-rewrites.md +109 -0
- package/skills/stellar-scf-grants-advisor/examples/q2-description-rewrites.md +88 -0
- package/skills/stellar-scf-grants-advisor/examples/q6-integration-rewrites.md +107 -0
- package/skills/stellar-scf-grants-advisor/examples/tranche-structures.md +176 -0
- package/skills/stellar-scf-grants-advisor/reference/01-methodology.md +96 -0
- package/skills/stellar-scf-grants-advisor/reference/02-scoring-framework.md +199 -0
- package/skills/stellar-scf-grants-advisor/reference/03-rejection-patterns.md +241 -0
- package/skills/stellar-scf-grants-advisor/reference/04-winner-patterns.md +120 -0
- package/skills/stellar-scf-grants-advisor/reference/05-comeback-patterns.md +92 -0
- package/skills/stellar-scf-grants-advisor/reference/06-budget-benchmarks.md +125 -0
- package/skills/stellar-scf-grants-advisor/reference/07-integration-list.md +147 -0
- package/skills/stellar-scf-grants-advisor/reference/08-abstract-fields.md +258 -0
- package/skills/stellar-scf-grants-advisor/reference/09-build-fields.md +259 -0
- package/skills/stellar-scf-grants-advisor/reference/10-corpus-winners.md +135 -0
- package/skills/stellar-scf-grants-advisor/reference/11-corpus-rejects.md +267 -0
- package/skills/stellar-scf-grants-advisor/reference/12-client-communication.md +131 -0
- package/skills/stellar-scf-grants-advisor/reference/13-excel-output-spec.md +199 -0
- package/skills/stellar-scf-grants-advisor/reference/14-worked-examples.md +160 -0
- package/skills/stellar-scf-grants-advisor/templates/abstract-review-builder.py +253 -0
- package/skills/stellar-scf-grants-advisor/templates/build-review-builder.py +213 -0
- package/skills/video-direction/video-direction.skill.json +20 -0
- package/skills/video-style-vocabulary/video-style-vocabulary.skill.json +20 -0
- package/skills/video-toolbox/video-toolbox.skill.json +20 -0
- package/src/__fixtures__/lifecycle-presets.flat-before.json +205 -0
- package/src/agency-os.yaml +122 -0
- package/src/agent-os-skill-slugs.test.ts +65 -0
- package/src/apify-social-reader.test.ts +317 -0
- package/src/base.yaml +85 -39
- package/src/blockchain-ecosystem.yaml +1 -0
- package/src/brand-library.yaml +525 -14
- package/src/builder-dev-fold.template.test.ts +113 -0
- package/src/builder.yaml +779 -91
- package/src/business-model-catalog-description.test.ts +47 -0
- package/src/business-model-grp.template.test.ts +214 -0
- package/src/business-model.yaml +296 -49
- package/src/catalog-safety.test.ts +198 -0
- package/src/catalog.template-items.test.ts +75 -0
- package/src/catalog.ts +66 -2
- package/src/concept-guard.test.ts +28 -8
- package/src/concept-guard.ts +2 -2
- package/src/content-creation.template.test.ts +52 -0
- package/src/content-creation.yaml +192 -0
- package/src/content-os.edit-loop.template.test.ts +210 -0
- package/src/content-os.publish-due-posts.template.test.ts +261 -0
- package/src/content-os.template.test.ts +349 -0
- package/src/content-os.video-takes.template.test.ts +338 -0
- package/src/content-os.work-a-take.template.test.ts +125 -0
- package/src/content-os.yaml +1873 -39
- package/src/content-studio-retired.template.test.ts +82 -0
- package/src/corpus-flow-validity.test.ts +4 -5
- package/src/crm-absorbs-outreach.template.test.ts +117 -0
- package/src/crm-build-plan.template.test.ts +128 -0
- package/src/crm-lists.template.test.ts +96 -0
- package/src/crm-messages-cadence.template.test.ts +246 -0
- package/src/crm-one-send-door.template.test.ts +65 -0
- package/src/crm.yaml +1563 -181
- package/src/decisions-wave.template.test.ts +186 -0
- package/src/define.ts +146 -17
- package/src/design-to-implementation.template.test.ts +94 -0
- package/src/domain-template-type.test.ts +75 -0
- package/src/ecosystem.yaml +27 -66
- package/src/enterprise-os.yaml +10 -134
- package/src/facecam-edit.audio-studio.test.ts +188 -0
- package/src/fal-generate-image.test.ts +200 -0
- package/src/fal-media-lab-pod-files.test.ts +180 -0
- package/src/finance.yaml +254 -1
- package/src/foundation.yaml +78 -38
- package/src/frame-host-modules.d.mts +6 -0
- package/src/frame-host-modules.mjs +58 -0
- package/src/generate.mjs +9 -3
- package/src/github-merge.test.ts +210 -0
- package/src/grants.yaml +46 -17
- package/src/hr.yaml +39 -6
- package/src/index.ts +36 -1
- package/src/intent.test.ts +161 -0
- package/src/internal-runbook.yaml +19 -1
- package/src/jev.test.ts +356 -0
- package/src/legal.yaml +33 -1
- package/src/life-os.yaml +51 -240
- package/src/lifecycle-coverage.test.ts +124 -0
- package/src/lifecycle-declarations.test.ts +252 -0
- package/src/lifecycle-presets.test.ts +468 -0
- package/src/lifecycle-presets.ts +494 -0
- package/src/lifecycle-stuck.test.ts +46 -0
- package/src/lifecycle-waits.parity.test.ts +319 -0
- package/src/marketing.yaml +108 -4
- package/src/meetings-knowledge.yaml +18 -0
- package/src/networking.yaml +23 -2
- package/src/operations.yaml +304 -4
- package/src/pipeline-views.template.test.ts +88 -0
- package/src/playbook-goal-placeholders.test.ts +57 -0
- package/src/postiz-contract.test.ts +134 -0
- package/src/presentation-declarations.test.ts +174 -0
- package/src/process-contract.validate.test.ts +352 -0
- package/src/project-management.yaml +39 -740
- package/src/publish-body.d.mts +29 -0
- package/src/publish-body.mjs +74 -0
- package/src/publish-body.test.ts +74 -0
- package/src/publish-official-lib.test.ts +176 -0
- package/src/replicate-rvm.test.ts +504 -0
- package/src/research-base.yaml +119 -20
- package/src/research-decision.yaml +60 -3
- package/src/reserved-profile-slugs.test.ts +81 -0
- package/src/retired-goal-kinds.test.ts +52 -0
- package/src/role-reference-and-step-domain.test.ts +192 -0
- package/src/seed-obligation.test.ts +1 -6
- package/src/send-message-maps.test.ts +227 -0
- package/src/shared-role-ssot.test.ts +40 -2
- package/src/ship-a-change.template.test.ts +177 -0
- package/src/skills.test.ts +170 -0
- package/src/social.yaml +85 -27
- package/src/space-packages.freshness.test.ts +97 -0
- package/src/space-packages.generated.ts +40 -0
- package/src/space-packages.test.ts +125 -0
- package/src/space-packages.ts +73 -0
- package/src/start.test.ts +188 -0
- package/src/stripe-capability.test.ts +192 -0
- package/src/task-intents.test.ts +293 -0
- package/src/template-documents.test.ts +158 -0
- package/src/templates.ts +20907 -21464
- package/src/types.ts +475 -61
- package/src/unipile-linkedin-find-profile.test.ts +183 -0
- package/src/unipile-publish-post.test.ts +162 -0
- package/src/validate-flow.drift.test.ts +2 -3
- package/src/validate-flow.ts +22 -2
- package/src/validate-onboarding.test.ts +59 -0
- package/src/validate.test.ts +71 -4
- package/src/validate.ts +1416 -7
- package/src/wire-core.ts +231 -0
- package/src/wire.test.ts +159 -0
- package/src/wire.ts +107 -0
- package/views/bookmark-views-pack.view.json +39 -0
- package/views/event-views-pack.view.json +45 -0
- package/views/task-views-pack.view.json +53 -0
- package/src/agent-fleet.yaml +0 -1645
- package/src/business-developer.template.test.ts +0 -351
- package/src/business-developer.yaml +0 -860
- package/src/content-studio.yaml +0 -361
- package/src/dev-dashboard.yaml +0 -990
- package/src/outreach-comms.yaml +0 -486
- package/src/the-arch.yaml +0 -201
package/dist/wire.d.ts
ADDED
|
@@ -0,0 +1,222 @@
|
|
|
1
|
+
import { g as PackageDefinitionOutput, X as WorkspaceDefinitionInput } from './define-DqoItRiR.js';
|
|
2
|
+
import '@synap-core/types/presentation';
|
|
3
|
+
import '@synap-core/types/space-brief';
|
|
4
|
+
import '@synap-core/types/capability-intents';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* The per-kind wire envelopes and the ONE unwrap — import-free on purpose.
|
|
8
|
+
*
|
|
9
|
+
* Re-exported (with the workspace types) by `./wire`, the public subpath
|
|
10
|
+
* `@synap-core/workspace-templates/wire`. It has no imports so a consumer that
|
|
11
|
+
* still resolves an older npm copy of this package (the CLI, the CP, the pod)
|
|
12
|
+
* can carry it as a BYTE-IDENTICAL mirror pinned by a tripwire until it can
|
|
13
|
+
* import the subpath. Edit it here; the mirror copies it.
|
|
14
|
+
*
|
|
15
|
+
* What `GET {CP}/api/packages/:slug` serves as `package.definition`, per kind:
|
|
16
|
+
* the outputs of this package's producers (`scripts/catalog-lib.mjs`
|
|
17
|
+
* `toPublishBody`; `toOfficialPublishBody` for workspaces) plus what the CP
|
|
18
|
+
* adds on store/serve (`_meta.slug` via `withTemplateSlug`,
|
|
19
|
+
* `capability.contentHash`).
|
|
20
|
+
*
|
|
21
|
+
* WHY: a skill package is served as `{ _meta, skill: {…} }`. Read flat, every
|
|
22
|
+
* field is `undefined`: install refused a "bodiless" skill and the update door
|
|
23
|
+
* reported "no drift" forever (founder pod 2026-10-13, creative-director). Each
|
|
24
|
+
* consumer had its own cast; this is the one place the envelope is known.
|
|
25
|
+
*
|
|
26
|
+
* Element fields are pinned to the catalog schema (`SKILL_FIELDS`,
|
|
27
|
+
* `CapabilitySpec`) and `AutomationElement` to `PackageAutomationWire` by
|
|
28
|
+
* `schema/wire.parity.test.ts` (compile time).
|
|
29
|
+
*/
|
|
30
|
+
/** The kinds whose served definition this module describes. */
|
|
31
|
+
declare const WIRE_KINDS: readonly ["workspace", "capability", "skill", "automation", "view"];
|
|
32
|
+
type WireKind = (typeof WIRE_KINDS)[number];
|
|
33
|
+
/**
|
|
34
|
+
* Other names the same kinds go by: the pod's `market.install` says
|
|
35
|
+
* `template`, the CP category for an automation is `workflow`, and a pack is
|
|
36
|
+
* a workspace-shaped definition.
|
|
37
|
+
*/
|
|
38
|
+
declare const WIRE_KIND_ALIASES: {
|
|
39
|
+
readonly template: "workspace";
|
|
40
|
+
readonly pack: "workspace";
|
|
41
|
+
readonly workflow: "automation";
|
|
42
|
+
};
|
|
43
|
+
type WireKindName = WireKind | keyof typeof WIRE_KIND_ALIASES;
|
|
44
|
+
/** `template` → `workspace`, `workflow` → `automation`; `null` for a kind with no wire contract here (e.g. `cell`). */
|
|
45
|
+
declare function toWireKind(kind: string): WireKind | null;
|
|
46
|
+
/**
|
|
47
|
+
* `definition._meta` as served: the CP stamps `slug` on every row (the pod
|
|
48
|
+
* keys "which space is this template's?" on it); the CLI adds the `version`
|
|
49
|
+
* label it installs.
|
|
50
|
+
*/
|
|
51
|
+
interface WireMeta {
|
|
52
|
+
slug?: string;
|
|
53
|
+
version?: string;
|
|
54
|
+
[key: string]: unknown;
|
|
55
|
+
}
|
|
56
|
+
/** `meta.icon` / `color` / `domain`, mirrored onto the definition by every publish builder. */
|
|
57
|
+
interface WireIdentity {
|
|
58
|
+
icon?: string;
|
|
59
|
+
color?: string;
|
|
60
|
+
domain?: string;
|
|
61
|
+
}
|
|
62
|
+
/** A composition dependency. */
|
|
63
|
+
interface WireDependency {
|
|
64
|
+
slug: string;
|
|
65
|
+
kind?: "workspace" | "capability" | "skill" | "workflow" | "view" | "cell" | "automation";
|
|
66
|
+
relation?: "compose" | "require";
|
|
67
|
+
reason?: string;
|
|
68
|
+
}
|
|
69
|
+
interface WireEnvelope extends WireIdentity {
|
|
70
|
+
_meta?: WireMeta;
|
|
71
|
+
dependencies?: WireDependency[];
|
|
72
|
+
}
|
|
73
|
+
/** The capability itself (`CapabilityDefinition`). */
|
|
74
|
+
interface CapabilityElement {
|
|
75
|
+
key: string;
|
|
76
|
+
name: string;
|
|
77
|
+
description?: string;
|
|
78
|
+
params?: Array<Record<string, unknown>>;
|
|
79
|
+
vault?: Array<Record<string, unknown>>;
|
|
80
|
+
tools?: Array<Record<string, unknown>>;
|
|
81
|
+
skills?: Array<Record<string, unknown>>;
|
|
82
|
+
provides?: string[];
|
|
83
|
+
playbooks?: Array<Record<string, unknown>>;
|
|
84
|
+
/** Stamped by the CP on publish; the pod's drift marker. */
|
|
85
|
+
contentHash?: string;
|
|
86
|
+
automations?: Array<Record<string, unknown>>;
|
|
87
|
+
mcpServers?: unknown;
|
|
88
|
+
metadata?: Record<string, unknown>;
|
|
89
|
+
_generated?: unknown;
|
|
90
|
+
}
|
|
91
|
+
/** capability: `{ profiles: [], description, capability }`. */
|
|
92
|
+
interface CapabilityWire extends WireEnvelope {
|
|
93
|
+
profiles: unknown[];
|
|
94
|
+
description?: string;
|
|
95
|
+
capability: CapabilityElement;
|
|
96
|
+
}
|
|
97
|
+
/** ONE standalone skill. Not a workspace's `skills[]` link list. */
|
|
98
|
+
interface SkillElement {
|
|
99
|
+
/** The pod-side `load_skill` ref — its own identity, not the package slug. */
|
|
100
|
+
slug?: string;
|
|
101
|
+
name?: string;
|
|
102
|
+
displayName?: string;
|
|
103
|
+
description?: string;
|
|
104
|
+
kind?: "instruction" | "code" | "declarative" | "builtin";
|
|
105
|
+
scope?: "pod" | "user" | "workspace";
|
|
106
|
+
agentTypes?: string[];
|
|
107
|
+
body?: string;
|
|
108
|
+
code?: string;
|
|
109
|
+
providerSpec?: Record<string, unknown>;
|
|
110
|
+
parameters?: Record<string, unknown>;
|
|
111
|
+
category?: string;
|
|
112
|
+
executionMode?: "sync" | "async";
|
|
113
|
+
timeoutSeconds?: number;
|
|
114
|
+
intent?: string;
|
|
115
|
+
[key: string]: unknown;
|
|
116
|
+
}
|
|
117
|
+
/** skill: `{ skill, icon?, color?, domain?, dependencies? }`. */
|
|
118
|
+
interface SkillWire extends WireEnvelope {
|
|
119
|
+
skill: SkillElement;
|
|
120
|
+
}
|
|
121
|
+
/** One graph automation (= `PackageAutomationWire`): `flowDefinition`, not the authored `flow`. */
|
|
122
|
+
interface AutomationElement {
|
|
123
|
+
key?: string;
|
|
124
|
+
name: string;
|
|
125
|
+
description?: string;
|
|
126
|
+
triggerType: "event" | "cron" | "webhook" | "manual";
|
|
127
|
+
triggerConfig?: Record<string, unknown>;
|
|
128
|
+
flowDefinition?: {
|
|
129
|
+
nodes: unknown[];
|
|
130
|
+
edges: unknown[];
|
|
131
|
+
precondition?: string;
|
|
132
|
+
};
|
|
133
|
+
status?: "draft" | "active" | "paused";
|
|
134
|
+
}
|
|
135
|
+
/** automation (CP category `workflow`): `{ profiles: [], automations: [one] }`. */
|
|
136
|
+
interface AutomationWire extends WireEnvelope {
|
|
137
|
+
profiles: unknown[];
|
|
138
|
+
automations: AutomationElement[];
|
|
139
|
+
}
|
|
140
|
+
/** One view, as the pod's view install and update doors read it. */
|
|
141
|
+
interface ViewElement {
|
|
142
|
+
slug?: string;
|
|
143
|
+
name?: string;
|
|
144
|
+
displayName?: string;
|
|
145
|
+
description?: string;
|
|
146
|
+
type?: string;
|
|
147
|
+
config?: Record<string, unknown>;
|
|
148
|
+
query?: Record<string, unknown>;
|
|
149
|
+
metadata?: Record<string, unknown>;
|
|
150
|
+
scopeProfileSlugs?: string[];
|
|
151
|
+
scopeProfileIds?: string[];
|
|
152
|
+
[key: string]: unknown;
|
|
153
|
+
}
|
|
154
|
+
/** view: `{ views: [...] }`, or a legacy single view with its fields on top (has its own `type`). No catalog producer today. */
|
|
155
|
+
type ViewWire = (WireEnvelope & {
|
|
156
|
+
views: ViewElement[];
|
|
157
|
+
}) | ViewElement;
|
|
158
|
+
/**
|
|
159
|
+
* What {@link unwrapPackage} returns per kind. `workspace` is the definition
|
|
160
|
+
* itself; `./wire` narrows it to `WorkspaceWire`.
|
|
161
|
+
*/
|
|
162
|
+
interface PackageElementByKind<W = Record<string, unknown>> {
|
|
163
|
+
workspace: W;
|
|
164
|
+
capability: CapabilityElement;
|
|
165
|
+
skill: SkillElement;
|
|
166
|
+
automation: AutomationElement[];
|
|
167
|
+
view: ViewElement[];
|
|
168
|
+
}
|
|
169
|
+
type ElementOf<K extends WireKindName, W = Record<string, unknown>> = PackageElementByKind<W>[K extends WireKind ? K : K extends keyof typeof WIRE_KIND_ALIASES ? (typeof WIRE_KIND_ALIASES)[K] : never];
|
|
170
|
+
|
|
171
|
+
/**
|
|
172
|
+
* @synap-core/workspace-templates/wire — ONE wire contract per package kind.
|
|
173
|
+
*
|
|
174
|
+
* The per-kind envelopes and `unwrapPackage` live in `./wire-core` (import-free,
|
|
175
|
+
* so it can be mirrored byte-for-byte by consumers still pinned to an older npm
|
|
176
|
+
* copy). This adds what needs the rest of the package: the workspace envelope,
|
|
177
|
+
* derived from `PackageDefinitionOutput` instead of re-declared, and the one
|
|
178
|
+
* workspace wire → create-input translation.
|
|
179
|
+
*/
|
|
180
|
+
|
|
181
|
+
/**
|
|
182
|
+
* workspace / pack: `toPackageDefinition()` output — re-used, not re-declared.
|
|
183
|
+
* As served it is `toOfficialPublishBody().definition` (identity mirrored on
|
|
184
|
+
* top, `sourcePackage`) with `_meta` cut down to what the CP stamps; a bundled
|
|
185
|
+
* `PackageDefinitionOutput` is assignable to it as is.
|
|
186
|
+
*/
|
|
187
|
+
type WorkspaceWire = Omit<PackageDefinitionOutput, "_meta"> & WireIdentity & {
|
|
188
|
+
_meta?: Partial<PackageDefinitionOutput["_meta"]> & WireMeta;
|
|
189
|
+
/** Which build of this package generated the row (official rows only). */
|
|
190
|
+
sourcePackage?: {
|
|
191
|
+
name: string;
|
|
192
|
+
version: string;
|
|
193
|
+
};
|
|
194
|
+
};
|
|
195
|
+
/** The served definition, keyed by kind. */
|
|
196
|
+
interface PackageWireByKind {
|
|
197
|
+
workspace: WorkspaceWire;
|
|
198
|
+
capability: CapabilityWire;
|
|
199
|
+
skill: SkillWire;
|
|
200
|
+
automation: AutomationWire;
|
|
201
|
+
view: ViewWire;
|
|
202
|
+
}
|
|
203
|
+
type PackageWire = PackageWireByKind[WireKind];
|
|
204
|
+
/** `./wire-core`'s `unwrapPackage`, with the workspace element typed as {@link WorkspaceWire}. */
|
|
205
|
+
declare function unwrapPackage<K extends WireKindName>(kind: K, definition: unknown): ElementOf<K, WorkspaceWire>;
|
|
206
|
+
/**
|
|
207
|
+
* The served workspace definition → the input the pod's create/reconcile door
|
|
208
|
+
* takes (`WorkspaceDefinitionInput`). The two renames live here and only here:
|
|
209
|
+
* `suggestedEntities` → `seedEntities` and `automations` (graph flows) →
|
|
210
|
+
* `flowAutomations`.
|
|
211
|
+
*
|
|
212
|
+
* A 1:1 copy of the pod's `toWorkspaceDefinitionInput`
|
|
213
|
+
* (synap-backend `services/capabilities/resolve-workspace-template.ts`), so the
|
|
214
|
+
* pod can import this instead. Like it, it does NOT carry `taskIntents`,
|
|
215
|
+
* `capabilities`, `playbooks`, `actionPlacements`, `rules` or `skills`: the
|
|
216
|
+
* post-workspace layer reads the last five off the package definition itself;
|
|
217
|
+
* `taskIntents` is a gap on that path today. `wire.test.ts` pins every
|
|
218
|
+
* difference from `toWorkspaceDefinition`.
|
|
219
|
+
*/
|
|
220
|
+
declare function toWorkspaceInput(pkg: WorkspaceWire): WorkspaceDefinitionInput;
|
|
221
|
+
|
|
222
|
+
export { type AutomationElement, type AutomationWire, type CapabilityElement, type CapabilityWire, type PackageElementByKind, type PackageWire, type PackageWireByKind, type SkillElement, type SkillWire, type ViewElement, type ViewWire, WIRE_KINDS, WIRE_KIND_ALIASES, type WireDependency, type WireEnvelope, type WireIdentity, type WireKind, type WireKindName, type WireMeta, type WorkspaceWire, toWireKind, toWorkspaceInput, unwrapPackage };
|
package/dist/wire.js
ADDED
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
// src/wire-core.ts
|
|
2
|
+
var WIRE_KINDS = ["workspace", "capability", "skill", "automation", "view"];
|
|
3
|
+
var WIRE_KIND_ALIASES = {
|
|
4
|
+
template: "workspace",
|
|
5
|
+
pack: "workspace",
|
|
6
|
+
workflow: "automation"
|
|
7
|
+
};
|
|
8
|
+
function toWireKind(kind) {
|
|
9
|
+
if (WIRE_KINDS.includes(kind)) return kind;
|
|
10
|
+
return WIRE_KIND_ALIASES[kind] ?? null;
|
|
11
|
+
}
|
|
12
|
+
var isRecord = (v) => typeof v === "object" && v !== null && !Array.isArray(v);
|
|
13
|
+
function unwrapPackage(kind, definition) {
|
|
14
|
+
const wireKind = toWireKind(kind);
|
|
15
|
+
if (!wireKind) throw new Error(`unwrapPackage: "${kind}" has no wire contract`);
|
|
16
|
+
if (!isRecord(definition)) {
|
|
17
|
+
throw new TypeError(
|
|
18
|
+
`unwrapPackage(${kind}): the definition is not an object (${definition === null ? "null" : Array.isArray(definition) ? "array" : typeof definition})`
|
|
19
|
+
);
|
|
20
|
+
}
|
|
21
|
+
switch (wireKind) {
|
|
22
|
+
case "skill":
|
|
23
|
+
return isRecord(definition.skill) ? definition.skill : definition;
|
|
24
|
+
case "capability":
|
|
25
|
+
return isRecord(definition.capability) ? definition.capability : definition;
|
|
26
|
+
case "automation":
|
|
27
|
+
return Array.isArray(definition.automations) ? definition.automations : [];
|
|
28
|
+
case "view":
|
|
29
|
+
if (Array.isArray(definition.views) && definition.views.length > 0) return definition.views;
|
|
30
|
+
return definition.type ? [definition] : [];
|
|
31
|
+
case "workspace":
|
|
32
|
+
return definition;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
// src/wire.ts
|
|
37
|
+
function unwrapPackage2(kind, definition) {
|
|
38
|
+
return unwrapPackage(kind, definition);
|
|
39
|
+
}
|
|
40
|
+
function toWorkspaceInput(pkg) {
|
|
41
|
+
return {
|
|
42
|
+
workspaceName: pkg.workspaceName,
|
|
43
|
+
description: pkg.description,
|
|
44
|
+
proposalId: pkg._meta?.slug,
|
|
45
|
+
profiles: pkg.profiles,
|
|
46
|
+
views: pkg.views ?? [],
|
|
47
|
+
entityLinks: pkg.entityLinks ?? [],
|
|
48
|
+
seedEntities: pkg.suggestedEntities ?? [],
|
|
49
|
+
suggestedRelations: pkg.suggestedRelations,
|
|
50
|
+
displayTemplates: pkg.displayTemplates,
|
|
51
|
+
layoutConfig: pkg.layoutConfig,
|
|
52
|
+
bentoViewName: pkg.bentoViewName,
|
|
53
|
+
bentoLayout: pkg.bentoLayout,
|
|
54
|
+
bentoViewBlocks: pkg.bentoViewBlocks,
|
|
55
|
+
profileEntityBentoTemplates: pkg.profileEntityBentoTemplates,
|
|
56
|
+
workspaceSubtype: pkg.workspaceSubtype,
|
|
57
|
+
workspaceType: pkg.workspaceType,
|
|
58
|
+
workspaceVisibility: pkg.workspaceVisibility,
|
|
59
|
+
workspaceCapabilities: pkg.workspaceCapabilities,
|
|
60
|
+
intent: pkg.intent,
|
|
61
|
+
sourceRoles: pkg.sourceRoles,
|
|
62
|
+
defaultSources: pkg.defaultSources,
|
|
63
|
+
onboarding: pkg.onboarding,
|
|
64
|
+
dependencies: pkg.dependencies,
|
|
65
|
+
flowAutomations: pkg.automations ?? [],
|
|
66
|
+
commands: pkg.commands ?? [],
|
|
67
|
+
relationDefs: pkg.relationDefs ?? []
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
export {
|
|
71
|
+
WIRE_KINDS,
|
|
72
|
+
WIRE_KIND_ALIASES,
|
|
73
|
+
toWireKind,
|
|
74
|
+
toWorkspaceInput,
|
|
75
|
+
unwrapPackage2 as unwrapPackage
|
|
76
|
+
};
|
|
77
|
+
//# sourceMappingURL=wire.js.map
|
package/dist/wire.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/wire-core.ts","../src/wire.ts"],"sourcesContent":["/**\n * The per-kind wire envelopes and the ONE unwrap — import-free on purpose.\n *\n * Re-exported (with the workspace types) by `./wire`, the public subpath\n * `@synap-core/workspace-templates/wire`. It has no imports so a consumer that\n * still resolves an older npm copy of this package (the CLI, the CP, the pod)\n * can carry it as a BYTE-IDENTICAL mirror pinned by a tripwire until it can\n * import the subpath. Edit it here; the mirror copies it.\n *\n * What `GET {CP}/api/packages/:slug` serves as `package.definition`, per kind:\n * the outputs of this package's producers (`scripts/catalog-lib.mjs`\n * `toPublishBody`; `toOfficialPublishBody` for workspaces) plus what the CP\n * adds on store/serve (`_meta.slug` via `withTemplateSlug`,\n * `capability.contentHash`).\n *\n * WHY: a skill package is served as `{ _meta, skill: {…} }`. Read flat, every\n * field is `undefined`: install refused a \"bodiless\" skill and the update door\n * reported \"no drift\" forever (founder pod 2026-10-13, creative-director). Each\n * consumer had its own cast; this is the one place the envelope is known.\n *\n * Element fields are pinned to the catalog schema (`SKILL_FIELDS`,\n * `CapabilitySpec`) and `AutomationElement` to `PackageAutomationWire` by\n * `schema/wire.parity.test.ts` (compile time).\n */\n\n// ─── Kinds ──────────────────────────────────────────────────────────────────\n\n/** The kinds whose served definition this module describes. */\nexport const WIRE_KINDS = [\"workspace\", \"capability\", \"skill\", \"automation\", \"view\"] as const;\nexport type WireKind = (typeof WIRE_KINDS)[number];\n\n/**\n * Other names the same kinds go by: the pod's `market.install` says\n * `template`, the CP category for an automation is `workflow`, and a pack is\n * a workspace-shaped definition.\n */\nexport const WIRE_KIND_ALIASES = {\n template: \"workspace\",\n pack: \"workspace\",\n workflow: \"automation\",\n} as const satisfies Record<string, WireKind>;\nexport type WireKindName = WireKind | keyof typeof WIRE_KIND_ALIASES;\n\n/** `template` → `workspace`, `workflow` → `automation`; `null` for a kind with no wire contract here (e.g. `cell`). */\nexport function toWireKind(kind: string): WireKind | null {\n if ((WIRE_KINDS as readonly string[]).includes(kind)) return kind as WireKind;\n return (WIRE_KIND_ALIASES as Record<string, WireKind>)[kind] ?? null;\n}\n\n// ─── Envelope pieces every kind shares ──────────────────────────────────────\n\n/**\n * `definition._meta` as served: the CP stamps `slug` on every row (the pod\n * keys \"which space is this template's?\" on it); the CLI adds the `version`\n * label it installs.\n */\nexport interface WireMeta {\n slug?: string;\n version?: string;\n [key: string]: unknown;\n}\n\n/** `meta.icon` / `color` / `domain`, mirrored onto the definition by every publish builder. */\nexport interface WireIdentity {\n icon?: string;\n color?: string;\n domain?: string;\n}\n\n/** A composition dependency. */\nexport interface WireDependency {\n slug: string;\n kind?: \"workspace\" | \"capability\" | \"skill\" | \"workflow\" | \"view\" | \"cell\" | \"automation\";\n relation?: \"compose\" | \"require\";\n reason?: string;\n}\n\nexport interface WireEnvelope extends WireIdentity {\n _meta?: WireMeta;\n dependencies?: WireDependency[];\n}\n\n// ─── Elements and envelopes, per kind ───────────────────────────────────────\n\n/** The capability itself (`CapabilityDefinition`). */\nexport interface CapabilityElement {\n key: string;\n name: string;\n description?: string;\n params?: Array<Record<string, unknown>>;\n vault?: Array<Record<string, unknown>>;\n tools?: Array<Record<string, unknown>>;\n skills?: Array<Record<string, unknown>>;\n provides?: string[];\n playbooks?: Array<Record<string, unknown>>;\n /** Stamped by the CP on publish; the pod's drift marker. */\n contentHash?: string;\n automations?: Array<Record<string, unknown>>;\n mcpServers?: unknown;\n metadata?: Record<string, unknown>;\n _generated?: unknown;\n}\n\n/** capability: `{ profiles: [], description, capability }`. */\nexport interface CapabilityWire extends WireEnvelope {\n profiles: unknown[];\n description?: string;\n capability: CapabilityElement;\n}\n\n/** ONE standalone skill. Not a workspace's `skills[]` link list. */\nexport interface SkillElement {\n /** The pod-side `load_skill` ref — its own identity, not the package slug. */\n slug?: string;\n name?: string;\n displayName?: string;\n description?: string;\n kind?: \"instruction\" | \"code\" | \"declarative\" | \"builtin\";\n scope?: \"pod\" | \"user\" | \"workspace\";\n agentTypes?: string[];\n body?: string;\n code?: string;\n providerSpec?: Record<string, unknown>;\n parameters?: Record<string, unknown>;\n category?: string;\n executionMode?: \"sync\" | \"async\";\n timeoutSeconds?: number;\n intent?: string;\n [key: string]: unknown;\n}\n\n/** skill: `{ skill, icon?, color?, domain?, dependencies? }`. */\nexport interface SkillWire extends WireEnvelope {\n skill: SkillElement;\n}\n\n/** One graph automation (= `PackageAutomationWire`): `flowDefinition`, not the authored `flow`. */\nexport interface AutomationElement {\n key?: string;\n name: string;\n description?: string;\n triggerType: \"event\" | \"cron\" | \"webhook\" | \"manual\";\n triggerConfig?: Record<string, unknown>;\n flowDefinition?: { nodes: unknown[]; edges: unknown[]; precondition?: string };\n status?: \"draft\" | \"active\" | \"paused\";\n}\n\n/** automation (CP category `workflow`): `{ profiles: [], automations: [one] }`. */\nexport interface AutomationWire extends WireEnvelope {\n profiles: unknown[];\n automations: AutomationElement[];\n}\n\n/** One view, as the pod's view install and update doors read it. */\nexport interface ViewElement {\n slug?: string;\n name?: string;\n displayName?: string;\n description?: string;\n type?: string;\n config?: Record<string, unknown>;\n query?: Record<string, unknown>;\n metadata?: Record<string, unknown>;\n scopeProfileSlugs?: string[];\n scopeProfileIds?: string[];\n [key: string]: unknown;\n}\n\n/** view: `{ views: [...] }`, or a legacy single view with its fields on top (has its own `type`). No catalog producer today. */\nexport type ViewWire = (WireEnvelope & { views: ViewElement[] }) | ViewElement;\n\n/**\n * What {@link unwrapPackage} returns per kind. `workspace` is the definition\n * itself; `./wire` narrows it to `WorkspaceWire`.\n */\nexport interface PackageElementByKind<W = Record<string, unknown>> {\n workspace: W;\n capability: CapabilityElement;\n skill: SkillElement;\n automation: AutomationElement[];\n view: ViewElement[];\n}\n\nexport type ElementOf<K extends WireKindName, W = Record<string, unknown>> = PackageElementByKind<W>[K extends WireKind\n ? K\n : K extends keyof typeof WIRE_KIND_ALIASES\n ? (typeof WIRE_KIND_ALIASES)[K]\n : never];\n\n// ─── The ONE unwrap ─────────────────────────────────────────────────────────\n\nconst isRecord = (v: unknown): v is Record<string, unknown> =>\n typeof v === \"object\" && v !== null && !Array.isArray(v);\n\n/**\n * The installable element(s) inside a served definition:\n *\n * skill → the `skill` object (a legacy flat definition is the skill itself)\n * capability → the `capability` object (a flat `CapabilityDefinition` — the\n * pod cache / CP by-key shape — passes through)\n * automation → `automations[]` (`[]` when the definition declares none)\n * view → `views[]`, or a legacy flat view (top-level `type`) as `[def]`, else `[]`\n * workspace → the definition itself\n *\n * An empty array means the definition declares none; the install doors refuse\n * that themselves. A definition that is not an object is a failed read, never\n * an empty one: it throws.\n */\nexport function unwrapPackage<K extends WireKindName>(kind: K, definition: unknown): ElementOf<K>;\nexport function unwrapPackage(kind: string, definition: unknown): unknown {\n const wireKind = toWireKind(kind);\n if (!wireKind) throw new Error(`unwrapPackage: \"${kind}\" has no wire contract`);\n if (!isRecord(definition)) {\n throw new TypeError(\n `unwrapPackage(${kind}): the definition is not an object (${definition === null ? \"null\" : Array.isArray(definition) ? \"array\" : typeof definition})`,\n );\n }\n switch (wireKind) {\n case \"skill\":\n return isRecord(definition.skill) ? definition.skill : definition;\n case \"capability\":\n return isRecord(definition.capability) ? definition.capability : definition;\n case \"automation\":\n return Array.isArray(definition.automations) ? definition.automations : [];\n case \"view\":\n if (Array.isArray(definition.views) && definition.views.length > 0) return definition.views;\n return definition.type ? [definition] : [];\n case \"workspace\":\n return definition;\n }\n}\n","/**\n * @synap-core/workspace-templates/wire — ONE wire contract per package kind.\n *\n * The per-kind envelopes and `unwrapPackage` live in `./wire-core` (import-free,\n * so it can be mirrored byte-for-byte by consumers still pinned to an older npm\n * copy). This adds what needs the rest of the package: the workspace envelope,\n * derived from `PackageDefinitionOutput` instead of re-declared, and the one\n * workspace wire → create-input translation.\n */\n\nimport type { PackageDefinitionOutput, WorkspaceDefinitionInput } from \"./define\";\nimport { unwrapPackage as unwrapCore, type ElementOf, type WireIdentity, type WireKindName, type WireMeta } from \"./wire-core\";\n\nexport {\n WIRE_KINDS,\n WIRE_KIND_ALIASES,\n toWireKind,\n type WireKind,\n type WireKindName,\n type WireMeta,\n type WireIdentity,\n type WireDependency,\n type WireEnvelope,\n type CapabilityElement,\n type CapabilityWire,\n type SkillElement,\n type SkillWire,\n type AutomationElement,\n type AutomationWire,\n type ViewElement,\n type ViewWire,\n type PackageElementByKind,\n} from \"./wire-core\";\nimport type { AutomationWire, CapabilityWire, SkillWire, ViewWire, WireKind } from \"./wire-core\";\n\n/**\n * workspace / pack: `toPackageDefinition()` output — re-used, not re-declared.\n * As served it is `toOfficialPublishBody().definition` (identity mirrored on\n * top, `sourcePackage`) with `_meta` cut down to what the CP stamps; a bundled\n * `PackageDefinitionOutput` is assignable to it as is.\n */\nexport type WorkspaceWire = Omit<PackageDefinitionOutput, \"_meta\"> &\n WireIdentity & {\n _meta?: Partial<PackageDefinitionOutput[\"_meta\"]> & WireMeta;\n /** Which build of this package generated the row (official rows only). */\n sourcePackage?: { name: string; version: string };\n };\n\n/** The served definition, keyed by kind. */\nexport interface PackageWireByKind {\n workspace: WorkspaceWire;\n capability: CapabilityWire;\n skill: SkillWire;\n automation: AutomationWire;\n view: ViewWire;\n}\nexport type PackageWire = PackageWireByKind[WireKind];\n\n/** `./wire-core`'s `unwrapPackage`, with the workspace element typed as {@link WorkspaceWire}. */\nexport function unwrapPackage<K extends WireKindName>(kind: K, definition: unknown): ElementOf<K, WorkspaceWire> {\n return unwrapCore(kind, definition) as ElementOf<K, WorkspaceWire>;\n}\n\n/**\n * The served workspace definition → the input the pod's create/reconcile door\n * takes (`WorkspaceDefinitionInput`). The two renames live here and only here:\n * `suggestedEntities` → `seedEntities` and `automations` (graph flows) →\n * `flowAutomations`.\n *\n * A 1:1 copy of the pod's `toWorkspaceDefinitionInput`\n * (synap-backend `services/capabilities/resolve-workspace-template.ts`), so the\n * pod can import this instead. Like it, it does NOT carry `taskIntents`,\n * `capabilities`, `playbooks`, `actionPlacements`, `rules` or `skills`: the\n * post-workspace layer reads the last five off the package definition itself;\n * `taskIntents` is a gap on that path today. `wire.test.ts` pins every\n * difference from `toWorkspaceDefinition`.\n */\nexport function toWorkspaceInput(pkg: WorkspaceWire): WorkspaceDefinitionInput {\n return {\n workspaceName: pkg.workspaceName,\n description: pkg.description,\n proposalId: pkg._meta?.slug,\n profiles: pkg.profiles,\n views: pkg.views ?? [],\n entityLinks: pkg.entityLinks ?? [],\n seedEntities: pkg.suggestedEntities ?? [],\n suggestedRelations: pkg.suggestedRelations,\n displayTemplates: pkg.displayTemplates,\n layoutConfig: pkg.layoutConfig,\n bentoViewName: pkg.bentoViewName,\n bentoLayout: pkg.bentoLayout,\n bentoViewBlocks: pkg.bentoViewBlocks,\n profileEntityBentoTemplates: pkg.profileEntityBentoTemplates,\n workspaceSubtype: pkg.workspaceSubtype,\n workspaceType: pkg.workspaceType,\n workspaceVisibility: pkg.workspaceVisibility,\n workspaceCapabilities: pkg.workspaceCapabilities,\n intent: pkg.intent,\n sourceRoles: pkg.sourceRoles,\n defaultSources: pkg.defaultSources,\n onboarding: pkg.onboarding,\n dependencies: pkg.dependencies,\n flowAutomations: pkg.automations ?? [],\n commands: pkg.commands ?? [],\n relationDefs: pkg.relationDefs ?? [],\n };\n}\n"],"mappings":";AA4BO,IAAM,aAAa,CAAC,aAAa,cAAc,SAAS,cAAc,MAAM;AAQ5E,IAAM,oBAAoB;AAAA,EAC/B,UAAU;AAAA,EACV,MAAM;AAAA,EACN,UAAU;AACZ;AAIO,SAAS,WAAW,MAA+B;AACxD,MAAK,WAAiC,SAAS,IAAI,EAAG,QAAO;AAC7D,SAAQ,kBAA+C,IAAI,KAAK;AAClE;AAgJA,IAAM,WAAW,CAAC,MAChB,OAAO,MAAM,YAAY,MAAM,QAAQ,CAAC,MAAM,QAAQ,CAAC;AAiBlD,SAAS,cAAc,MAAc,YAA8B;AACxE,QAAM,WAAW,WAAW,IAAI;AAChC,MAAI,CAAC,SAAU,OAAM,IAAI,MAAM,mBAAmB,IAAI,wBAAwB;AAC9E,MAAI,CAAC,SAAS,UAAU,GAAG;AACzB,UAAM,IAAI;AAAA,MACR,iBAAiB,IAAI,uCAAuC,eAAe,OAAO,SAAS,MAAM,QAAQ,UAAU,IAAI,UAAU,OAAO,UAAU;AAAA,IACpJ;AAAA,EACF;AACA,UAAQ,UAAU;AAAA,IAChB,KAAK;AACH,aAAO,SAAS,WAAW,KAAK,IAAI,WAAW,QAAQ;AAAA,IACzD,KAAK;AACH,aAAO,SAAS,WAAW,UAAU,IAAI,WAAW,aAAa;AAAA,IACnE,KAAK;AACH,aAAO,MAAM,QAAQ,WAAW,WAAW,IAAI,WAAW,cAAc,CAAC;AAAA,IAC3E,KAAK;AACH,UAAI,MAAM,QAAQ,WAAW,KAAK,KAAK,WAAW,MAAM,SAAS,EAAG,QAAO,WAAW;AACtF,aAAO,WAAW,OAAO,CAAC,UAAU,IAAI,CAAC;AAAA,IAC3C,KAAK;AACH,aAAO;AAAA,EACX;AACF;;;AC3KO,SAASA,eAAsC,MAAS,YAAkD;AAC/G,SAAO,cAAW,MAAM,UAAU;AACpC;AAgBO,SAAS,iBAAiB,KAA8C;AAC7E,SAAO;AAAA,IACL,eAAe,IAAI;AAAA,IACnB,aAAa,IAAI;AAAA,IACjB,YAAY,IAAI,OAAO;AAAA,IACvB,UAAU,IAAI;AAAA,IACd,OAAO,IAAI,SAAS,CAAC;AAAA,IACrB,aAAa,IAAI,eAAe,CAAC;AAAA,IACjC,cAAc,IAAI,qBAAqB,CAAC;AAAA,IACxC,oBAAoB,IAAI;AAAA,IACxB,kBAAkB,IAAI;AAAA,IACtB,cAAc,IAAI;AAAA,IAClB,eAAe,IAAI;AAAA,IACnB,aAAa,IAAI;AAAA,IACjB,iBAAiB,IAAI;AAAA,IACrB,6BAA6B,IAAI;AAAA,IACjC,kBAAkB,IAAI;AAAA,IACtB,eAAe,IAAI;AAAA,IACnB,qBAAqB,IAAI;AAAA,IACzB,uBAAuB,IAAI;AAAA,IAC3B,QAAQ,IAAI;AAAA,IACZ,aAAa,IAAI;AAAA,IACjB,gBAAgB,IAAI;AAAA,IACpB,YAAY,IAAI;AAAA,IAChB,cAAc,IAAI;AAAA,IAClB,iBAAiB,IAAI,eAAe,CAAC;AAAA,IACrC,UAAU,IAAI,YAAY,CAAC;AAAA,IAC3B,cAAc,IAAI,gBAAgB,CAAC;AAAA,EACrC;AACF;","names":["unwrapPackage"]}
|
package/package.json
CHANGED
|
@@ -1,25 +1,46 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@synap-core/workspace-templates",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.24.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Canonical workspace definitions — YAML source + typed exports for browser, backend, CLI, and marketplace",
|
|
6
|
+
"repository": {
|
|
7
|
+
"type": "git",
|
|
8
|
+
"url": "git+https://github.com/Synap-core/app-bases.git",
|
|
9
|
+
"directory": "packages/workspace-templates"
|
|
10
|
+
},
|
|
6
11
|
"exports": {
|
|
7
12
|
".": {
|
|
8
13
|
"types": "./dist/index.d.ts",
|
|
9
14
|
"default": "./dist/index.js"
|
|
10
|
-
}
|
|
15
|
+
},
|
|
16
|
+
"./wire": {
|
|
17
|
+
"types": "./dist/wire.d.ts",
|
|
18
|
+
"default": "./dist/wire.js"
|
|
19
|
+
},
|
|
20
|
+
"./capabilities/*": "./capabilities/*",
|
|
21
|
+
"./skills/*": "./skills/*",
|
|
22
|
+
"./automations/*": "./automations/*",
|
|
23
|
+
"./views/*": "./views/*",
|
|
24
|
+
"./package.json": "./package.json"
|
|
11
25
|
},
|
|
12
26
|
"files": [
|
|
13
27
|
"dist",
|
|
14
|
-
"src"
|
|
28
|
+
"src",
|
|
29
|
+
"capabilities",
|
|
30
|
+
"skills",
|
|
31
|
+
"automations",
|
|
32
|
+
"views",
|
|
33
|
+
"retired.yaml"
|
|
15
34
|
],
|
|
16
35
|
"dependencies": {
|
|
36
|
+
"@synap-core/types": "^1.12.0",
|
|
17
37
|
"zod": "^3.0.0",
|
|
18
38
|
"js-yaml": "^4.1.0"
|
|
19
39
|
},
|
|
20
40
|
"devDependencies": {
|
|
21
41
|
"@types/js-yaml": "^4.0.9",
|
|
22
42
|
"@types/node": "^22.0.0",
|
|
43
|
+
"esbuild": "^0.27.3",
|
|
23
44
|
"tsup": "^8.0.0",
|
|
24
45
|
"typescript": "^5.5.0"
|
|
25
46
|
},
|
|
@@ -28,8 +49,10 @@
|
|
|
28
49
|
"access": "public"
|
|
29
50
|
},
|
|
30
51
|
"scripts": {
|
|
31
|
-
"type-check": "tsc --noEmit",
|
|
52
|
+
"type-check": "tsc -p tsconfig.catalog.json && tsc --noEmit",
|
|
53
|
+
"type-check:catalog": "tsc -p tsconfig.catalog.json",
|
|
32
54
|
"build:yaml": "node --experimental-strip-types build.mjs",
|
|
55
|
+
"build:space-packages": "node scripts/build-space-packages.mjs",
|
|
33
56
|
"check:converters": "node scripts/check-converters.mjs",
|
|
34
57
|
"check:concepts": "node scripts/check-concepts.mjs",
|
|
35
58
|
"build": "node --experimental-strip-types build.mjs && tsup && node scripts/check-converters.mjs && node scripts/check-concepts.mjs",
|
package/retired.yaml
ADDED
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
# Retired templates: the tombstone registry (schema: schema/retired.ts).
|
|
2
|
+
#
|
|
3
|
+
# A template that leaves the catalog stays KNOWN here. `synap catalog publish`
|
|
4
|
+
# sends each entry to the control plane (POST /api/packages/retire) after the
|
|
5
|
+
# live publishes, so a pod can tell "retired, replaced by X" from "never heard
|
|
6
|
+
# of it" and offer the person a safe move to X. Removing an entry does NOT
|
|
7
|
+
# un-retire the row on the CP.
|
|
8
|
+
#
|
|
9
|
+
# slug the retired slug
|
|
10
|
+
# kind workspace (default) · capability · skill · pack · automation
|
|
11
|
+
# replacedBy a LIVE catalog slug of the same kind, or absent when nothing replaces it
|
|
12
|
+
# reason one plain sentence a person reads
|
|
13
|
+
# since the date it left the catalog (YYYY-MM-DD)
|
|
14
|
+
#
|
|
15
|
+
# Validation (`synap catalog validate`): replacedBy is live and not retired; no
|
|
16
|
+
# slug is both live and retired in the same category; reasons are not empty.
|
|
17
|
+
# The evidence behind each entry is in pod file 00c1b2fe-ef98-41fa-86cf-801dfab12cd1 ("Template lifecycle: decisions wave + lane catalog").
|
|
18
|
+
|
|
19
|
+
apiVersion: synap/v1
|
|
20
|
+
retired:
|
|
21
|
+
# c64ec2fe: "ecosystem (absorbs radar+content-os per ratified merge)". Every
|
|
22
|
+
# radar kind (competitor, market-segment, trend, inspiration) is declared by ecosystem.
|
|
23
|
+
- slug: radar
|
|
24
|
+
kind: workspace
|
|
25
|
+
replacedBy: ecosystem
|
|
26
|
+
reason: Radar was merged into Ecosystem, which tracks competitors, market segments, trends and inspiration in one place.
|
|
27
|
+
since: "2026-07-16"
|
|
28
|
+
|
|
29
|
+
# 2026-07-22 (b12efb1b). Second Brain (life-os) declares every kind Personal
|
|
30
|
+
# held (note, bookmark, article; projects are the pod's own).
|
|
31
|
+
- slug: personal
|
|
32
|
+
kind: workspace
|
|
33
|
+
replacedBy: life-os
|
|
34
|
+
reason: Personal was replaced by Second Brain, which keeps your notes, bookmarks and articles together.
|
|
35
|
+
since: "2026-07-22"
|
|
36
|
+
|
|
37
|
+
# R7 2026-09-27 (src/builder-dev-fold.template.test.ts): the four views worth
|
|
38
|
+
# keeping were rebuilt over Builder's own kinds (slug builder-workspace, shown as "Dev"). credential, vendor, repository,
|
|
39
|
+
# service and environment were NOT ported.
|
|
40
|
+
- slug: dev-dashboard
|
|
41
|
+
kind: workspace
|
|
42
|
+
replacedBy: builder-workspace
|
|
43
|
+
reason: Dev Dashboard was folded into the Dev space, where its service health, deploy and cost views now live.
|
|
44
|
+
since: "2026-09-27"
|
|
45
|
+
|
|
46
|
+
# R7 2026-09-27: retired as a template, its `agent` kind deliberately not
|
|
47
|
+
# ported anywhere. Not a system space (only pod-admin carries a system_slug).
|
|
48
|
+
- slug: agent-fleet
|
|
49
|
+
kind: workspace
|
|
50
|
+
reason: Agent Fleet is no longer offered; your agents belong to the pod itself, not to a space.
|
|
51
|
+
since: "2026-09-27"
|
|
52
|
+
|
|
53
|
+
# eaf49166: it declared no profiles, only tools, skills and vault. It lives on
|
|
54
|
+
# as the capability `posthog-analytics` (capabilities/), a different category.
|
|
55
|
+
- slug: posthog-analytics
|
|
56
|
+
kind: workspace
|
|
57
|
+
reason: PostHog Analytics is now a capability you connect, not a space.
|
|
58
|
+
since: "2026-10-06"
|
|
59
|
+
|
|
60
|
+
# relay-app's private template (relay-app/src/lib/workspace-templates/relay.ts).
|
|
61
|
+
# Never in the catalog, but pods hold it. person and company move to CRM;
|
|
62
|
+
# event and task are pod-wide; campaign and contact have no home in CRM.
|
|
63
|
+
- slug: relay
|
|
64
|
+
kind: workspace
|
|
65
|
+
replacedBy: crm
|
|
66
|
+
reason: Relay was replaced by CRM, which keeps the people and companies you track.
|
|
67
|
+
since: "2026-10-11"
|
|
68
|
+
|
|
69
|
+
# relay-app's private template (relay-app/src/lib/workspace-templates/pkm.ts).
|
|
70
|
+
# life-os.yaml says it was consolidated from the CP pkm-template; it declares
|
|
71
|
+
# note, bookmark and highlight.
|
|
72
|
+
- slug: pkm
|
|
73
|
+
kind: workspace
|
|
74
|
+
replacedBy: life-os
|
|
75
|
+
reason: Knowledge was replaced by Second Brain, which keeps your notes, bookmarks and highlights.
|
|
76
|
+
since: "2026-10-11"
|
|
77
|
+
|
|
78
|
+
# Founder decision 2026-10-12 (pod file 00c1b2fe-ef98-41fa-86cf-801dfab12cd1, decisions wave item 1).
|
|
79
|
+
# Its lead/client fields, the campaign kind and "Qualify a lead" folded into
|
|
80
|
+
# crm.yaml; "Advance a commercial proposal" was dropped for CRM's "Win a
|
|
81
|
+
# deal"; the Synap-fee + commission model moved to the private arch-sales.yaml,
|
|
82
|
+
# itself retired the same day (below).
|
|
83
|
+
- slug: business-developer
|
|
84
|
+
kind: workspace
|
|
85
|
+
replacedBy: crm
|
|
86
|
+
reason: Business Developer was folded into CRM, which now qualifies your leads and runs your campaigns.
|
|
87
|
+
since: "2026-10-12"
|
|
88
|
+
|
|
89
|
+
# Founder decision 2026-10-12: The Arch (project + pod) is no longer in use.
|
|
90
|
+
# Both were private. Their sources are kept, never loaded, in retired-sources/.
|
|
91
|
+
# Existing pods keep their spaces and data; nothing offers them again.
|
|
92
|
+
- slug: arch-sales
|
|
93
|
+
kind: workspace
|
|
94
|
+
reason: Arch Sales was The Arch's own business-developer commission model, and that project is no longer in use.
|
|
95
|
+
since: "2026-10-12"
|
|
96
|
+
|
|
97
|
+
- slug: the-arch
|
|
98
|
+
kind: workspace
|
|
99
|
+
reason: The Arch was a private suite for a project that is no longer in use.
|
|
100
|
+
since: "2026-10-12"
|
|
101
|
+
|
|
102
|
+
# 2026-10-15, "Any link → data": every pod reads a
|
|
103
|
+
# public link itself (the builtin web read verb in Synap Core), so this pack
|
|
104
|
+
# and its capture_public_url twin are no longer offered. Nothing replaces it:
|
|
105
|
+
# nothing needs installing.
|
|
106
|
+
- slug: web.read
|
|
107
|
+
kind: capability
|
|
108
|
+
reason: Reading a public link is built into every pod.
|
|
109
|
+
since: "2026-10-15"
|
|
110
|
+
|
|
111
|
+
# Founder decision 2026-10-23: one space per domain. For a founder-led company
|
|
112
|
+
# outreach is part of the commercial job, so the CRM absorbs it: the
|
|
113
|
+
# `outreach-touch` kind (same slug and lifecycle keys), `sent_to` / `part_of`,
|
|
114
|
+
# the two views, "Personalized Outreach" and the LinkedIn ingest live in
|
|
115
|
+
# crm.yaml. `outreach-campaign` folded into CRM's `campaign` (campaign-type
|
|
116
|
+
# outreach); "Send an outreach message" became "Read the reply to an outreach
|
|
117
|
+
# message" (the agent drafts, a person sends). No pod had it installed.
|
|
118
|
+
- slug: outreach-comms
|
|
119
|
+
kind: workspace
|
|
120
|
+
replacedBy: crm
|
|
121
|
+
reason: Outreach & Comms was folded into CRM, which now keeps your outreach campaigns and the messages drafted for you to send.
|
|
122
|
+
since: "2026-10-23"
|
|
123
|
+
|
|
124
|
+
# Static edit loop W5 (build plan ab3e0a5a §4, founder D0-D1, 2 Nov 2026).
|
|
125
|
+
# Superseded since 2026-10-06: Content OS re-declared its three video kinds
|
|
126
|
+
# (content-composition, content-asset, render-job) verbatim, their views and
|
|
127
|
+
# pipeline links; brand-library folded its production-recipe into
|
|
128
|
+
# brand-template. The edit loop (edit-loop skill, video-toolbox routing)
|
|
129
|
+
# replaced its render pipeline. The founder's pod holds no Content Studio
|
|
130
|
+
# space (2026-11-03); a pod that does keeps it as it is (the resolver
|
|
131
|
+
# refuses a new install and leaves an installed space alone).
|
|
132
|
+
- slug: content-studio
|
|
133
|
+
kind: workspace
|
|
134
|
+
replacedBy: content-os
|
|
135
|
+
reason: Content Studio was folded into Content OS, which now keeps your videos, carousels and other visual posts with the rest of your content.
|
|
136
|
+
since: "2026-11-03"
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: app-factory-build-slice
|
|
3
|
+
description: Build one slice of a new app from its approved design boards — scope by board files, data read server-side only through the person's sign-in, governed writes, the Website Factory gates, an independent re-run of every gate by the orchestrator, and a stop for the person's first look after slice 1. Use in the Build stage of "Build an app (App Factory)", or when handing an approved design to a coding agent.
|
|
4
|
+
metadata:
|
|
5
|
+
synap_native: true
|
|
6
|
+
auto_load: false
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# App Factory: build a slice
|
|
10
|
+
|
|
11
|
+
A slice is a set of approved boards built pixel for pixel, gate-green, in a pull request. It never starts before the
|
|
12
|
+
person approved the design, and never starts while a gap it depends on is open without a labelled bridge. Content
|
|
13
|
+
Studio's slice S1 (Home + idea bank, read-only, real data) is the reference.
|
|
14
|
+
|
|
15
|
+
## 1. Write the slice brief (in the app repo, e.g. `BUILD-S1.md`)
|
|
16
|
+
|
|
17
|
+
The builder reads it fully, then `AGENTS.md`, `.claude/skills/build-site/SKILL.md`, the plan document (sections it
|
|
18
|
+
names) and the boards. The brief says:
|
|
19
|
+
|
|
20
|
+
- **Scope, by boards.** Each route with the board files it must match (desktop 1280, phone 390, every state board).
|
|
21
|
+
Shell items outside the slice link to ONE "coming next" page drawn with the kit's `StatePanel`, never a dead link.
|
|
22
|
+
- **Rules computed on the server**, written once (e.g. Home's one line: open interview with unanswered questions →
|
|
23
|
+
owed asks → pending proposals → the most overdue item). The counts that must agree across pages come from one
|
|
24
|
+
function.
|
|
25
|
+
- **Not in this slice**, explicitly (writes, sign-in, the pages of later slices).
|
|
26
|
+
- **Data.** The read set per page (route, `workspaceId` always passed, what it returns), the request budget per page
|
|
27
|
+
against the key's rate limit, cache per request only (no shared cache across people). A failed read renders the
|
|
28
|
+
error state with retry, never an empty list.
|
|
29
|
+
- **Sign-in, never a key.** The app is a pod-app site (`create-site --path pod-app`): the person signs in to their pod
|
|
30
|
+
and the server reads through `@synap-core/sdk/connect` (`createPodAppAuth`); follow the kit's AGENTS.md. Never an app
|
|
31
|
+
key; the session secret stays server-only, never in client code, never `NEXT_PUBLIC_*`, never logged or committed.
|
|
32
|
+
Not connected → the kit's "not connected" state. What a pod app can see and do (spaces, roles, pod-wide records,
|
|
33
|
+
writes): `node_modules/@synap-core/sdk/AGENTS.md`, section "What a pod app can see and do". It wins over anything
|
|
34
|
+
here. If something the app needs is not supported yet, that is a recorded gap with an owner — never edit
|
|
35
|
+
`synap-check.mjs` to pass.
|
|
36
|
+
- **Writes are governed.** A write from a pod app is a proposal in a granted space (`proposed` is success: link the
|
|
37
|
+
review, label it in the UI "Proposed · in your pod", never retry it); a person connection applies directly.
|
|
38
|
+
- **Look.** `design-kit/tokens.css` decisions copied into `app/brand.css` (shadcn token names), fonts self-hosted
|
|
39
|
+
(`next/font/local` or `@fontsource*`, never Google at build time), sizes = shadcn base-nova plus only the sizes the
|
|
40
|
+
design decisions added (as cva variants). Private app: `app/robots.ts` disallows all, pages carry `noindex`, and any
|
|
41
|
+
cookie (e.g. the sidebar's `sidebar_state`) is named on the privacy page.
|
|
42
|
+
|
|
43
|
+
## 2. Gates (the builder runs them, quotes them, fixes until green)
|
|
44
|
+
|
|
45
|
+
- `pnpm verify` green (typecheck, lint, arc / extensions / synap / registry checks, build, smoke).
|
|
46
|
+
- `pnpm shots` and READ the PNGs and `.shots/REPORT.md` at 375 / 768 / 1280 (and dark, if designed): zero serious or
|
|
47
|
+
critical axe issues; compare each page with its board and list every remaining difference.
|
|
48
|
+
- Credential grep: the key's variable name appears only in server files
|
|
49
|
+
(`grep -rn "<KEY_VAR>" app components lib`).
|
|
50
|
+
- Mutation grep (read-only slices): no write call anywhere
|
|
51
|
+
(`grep -rnE 'method: ?"(POST|PATCH|PUT|DELETE)"|\.create\(|\.update\(|\.transition\(' app components lib` is empty).
|
|
52
|
+
- Small commits on a branch `s<N>-<slug>`, pushed, a pull request to main. Never push to main, never deploy
|
|
53
|
+
production; a preview deploy only when `VERCEL_TOKEN` is set (if not, say so and skip).
|
|
54
|
+
|
|
55
|
+
## 3. Independent verification (the orchestrator, not the builder)
|
|
56
|
+
|
|
57
|
+
Never accept "done" from the builder's report. On the devbox (heavy gates never on the Mac; take the gate lock):
|
|
58
|
+
check out the PR head, run `pnpm verify` and the two greps yourself, read the screenshots, and quote the outputs.
|
|
59
|
+
Look for green-by-accident: a verify that passed only through a temporary proxy or a cached font, a flag that does not
|
|
60
|
+
exist or is not the pod-app path (`create-site --path pod-app`), ids in the brief that drifted from the pod. Record each trap you find as a lesson.
|
|
61
|
+
|
|
62
|
+
## 4. Report and stop
|
|
63
|
+
|
|
64
|
+
Post in the slice's session room: what was built (routes, boards matched), the quoted gates, screenshot findings by
|
|
65
|
+
severity (VERIFIED), what only the person can judge (NEEDS-DOGFOOD), and the gaps still open with owners. After
|
|
66
|
+
**slice 1, STOP**: the person's first look on the preview (or the screenshots) decides the next slice. Later slices
|
|
67
|
+
continue in order unless the person stops them; each ends with the same report.
|
|
68
|
+
|
|
69
|
+
Done when: the PR is open, every gate is quoted by the orchestrator's own run, the differences from the boards are
|
|
70
|
+
listed, and (after slice 1) the person has been asked for their first look.
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
{
|
|
2
|
+
"apiVersion": "synap/v1",
|
|
3
|
+
"kind": "skill",
|
|
4
|
+
"meta": {
|
|
5
|
+
"slug": "app-factory-build-slice",
|
|
6
|
+
"name": "App Factory: build a slice",
|
|
7
|
+
"description": "Build one slice of an app from its approved boards: server-side reads through the person's sign-in, governed writes, the Website Factory gates, an independent re-run of every gate, and a stop for the person's first look after slice 1.",
|
|
8
|
+
"tags": [
|
|
9
|
+
"skill",
|
|
10
|
+
"app-factory",
|
|
11
|
+
"build",
|
|
12
|
+
"builder"
|
|
13
|
+
],
|
|
14
|
+
"isPublic": true
|
|
15
|
+
},
|
|
16
|
+
"dependencies": []
|
|
17
|
+
}
|