Skip to content

Commit 0912e47

Browse files
Jktfeclaude
andcommitted
feat: Add architect skills and bump to v2.0.0
Add two new skills for creating FlowSpec projects (reverse direction of spec/wireframe): - architect (MCP-powered): Uses flowspec_* MCP tools for desktop users - UC1: Wireframe → Dataflow (upload images, analyze, build YAML, annotate regions) - UC2: Codebase → Dataflow (8-step analysis pipeline from reviewer) - UC3: Design New Screens (collaborative screen design workflow) - References: mcp-tools.md (25 tools), codebase-analysis.md, yaml-schema.md v1.2.0 - architect-web (Chrome-powered): Browser automation for web-only users - Same 3 workflows but uses Chrome tools (tabs_context, javascript_tool, etc.) - Synthetic file injection for YAML import, DOM recipes for interaction - References: chrome-recipes.md, yaml-schema.md v1.2.0 Schema updates: - Upgraded YAML schema from v1.0.0 → v1.2.0 - Added tables section (database/API persistence layer) - Added screens/regions sections (wireframe annotation) - Added 'contains' edge type (Table → DataPoint) Plugin manifest: - Version: 1.0.0 → 2.0.0 - Updated description to reflect bidirectional workflow - Added keywords: mcp, chrome, canvas Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
1 parent a15d76c commit 0912e47

9 files changed

Lines changed: 2175 additions & 44 deletions

File tree

.claude-plugin/plugin.json

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,19 @@
11
{
22
"name": "flowspec",
3-
"version": "1.0.0",
3+
"version": "2.0.0",
44
"author": {
55
"name": "James King"
66
},
7-
"description": "Spec-driven development from FlowSpec YAML exports. Load a data architecture spec as your source of truth for types, data flows, constraints, and business logic — or combine wireframe screenshots with placement data to implement pixel-accurate UI components.",
7+
"description": "FlowSpec data architecture toolkit — create specs from wireframes or codebases (architect skills), then build features from those specs (spec/wireframe skills).",
88
"keywords": [
99
"flowspec",
1010
"data-architecture",
1111
"spec-driven",
1212
"wireframe",
1313
"yaml",
1414
"types",
15-
"code-generation",
16-
"ui-implementation"
15+
"mcp",
16+
"chrome",
17+
"canvas"
1718
]
1819
}

skills/architect-web/SKILL.md

Lines changed: 150 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,150 @@
1+
---
2+
name: architect-web
3+
description: >-
4+
Create and manage FlowSpec data architecture projects via the web app at
5+
flowspec.app using Chrome browser tools. For users without the desktop app.
6+
Generates YAML locally and uses light browser automation to import into
7+
the web editor. Requires the Claude in Chrome extension.
8+
argument_hint: "[wireframe images | codebase path | 'new project']"
9+
---
10+
11+
# FlowSpec Architect (Web / Chrome)
12+
13+
Same three workflows as `architect`, but uses Chrome browser tools instead of MCP — for users without the desktop app.
14+
15+
**Core pattern:** Generate YAML locally in Claude Code -> inject into flowspec.app via Chrome tools -> iterate.
16+
17+
**Requires:** Claude in Chrome extension (`mcp__claude-in-chrome__*` tools).
18+
19+
---
20+
21+
## Prerequisites & Auth Check
22+
23+
1. Call `mcp__claude-in-chrome__tabs_context_mcp` to find an existing flowspec.app tab.
24+
2. If no tab exists:
25+
```
26+
mcp__claude-in-chrome__tabs_create_mcp(url: "https://flowspec.app/editor")
27+
```
28+
3. Use `mcp__claude-in-chrome__read_page` to check for auth state:
29+
- Look for `.cl-userButtonTrigger` (Clerk user button) or project list elements
30+
- If not signed in: instruct user to sign in manually (Clerk SSO cannot be automated)
31+
4. Wait for the editor to fully load before proceeding.
32+
33+
---
34+
35+
## Interaction Model
36+
37+
| Action | Method |
38+
|--------|--------|
39+
| Generate YAML | Locally in Claude Code (same logic as `architect`) |
40+
| Import YAML into project | `javascript_tool` with synthetic file injection (see [chrome-recipes.md](references/chrome-recipes.md)) |
41+
| Export YAML from project | Click Export button via `javascript_tool`, then `read_page` |
42+
| Create new project | Click "New Project" button via browser tools |
43+
| Upload wireframe images | **User does manually** (browser file picker security) |
44+
| Annotate screen regions | **User does manually** (drag-to-create is more ergonomic) |
45+
| Auto-layout | Click toolbar button via browser tools |
46+
47+
**Fallback:** If any automation step fails, always provide manual instructions so the user can complete the step themselves.
48+
49+
---
50+
51+
## UC1: Wireframe -> Dataflow (Web)
52+
53+
### Step 1: Analyse wireframe images
54+
Use Claude vision to examine wireframe images the user provides:
55+
- Identify UI regions, data elements, forms, displays
56+
- Note interactive elements and data relationships
57+
58+
### Step 2: Interview user
59+
Ask about data types, sources, business logic, constraints — same as `architect` UC1 Step 4.
60+
61+
### Step 3: Build YAML spec
62+
Assemble the YAML following the [v1.2.0 schema](references/yaml-schema.md).
63+
64+
### Step 4: Navigate to flowspec.app
65+
Ensure we have an editor tab open:
66+
```
67+
mcp__claude-in-chrome__tabs_context_mcp
68+
```
69+
If needed, create a new project by clicking the "New Project" button.
70+
71+
### Step 5: Import YAML
72+
Use the synthetic file injection recipe from [chrome-recipes.md](references/chrome-recipes.md) to inject the YAML into the web app's import handler.
73+
74+
### Step 6: Guide wireframe upload
75+
Instruct the user to:
76+
1. Open the Screens section in the sidebar
77+
2. Click "Create Screen" or use the image dropzone
78+
3. Upload their wireframe image files
79+
4. Name each screen
80+
81+
### Step 7: Guide region annotation
82+
Instruct the user to:
83+
1. Open a screen in the editor
84+
2. Draw regions over the wireframe by clicking and dragging
85+
3. Name each region and link data elements using the region panel
86+
87+
### Step 8: Export and iterate
88+
Use browser tools to click "Export YAML" and read the result. Review and refine the spec, then re-import if needed.
89+
90+
---
91+
92+
## UC2: Codebase -> Dataflow (Web)
93+
94+
### Steps 1-7: Analyse locally
95+
All codebase analysis happens locally in Claude Code — identical to `architect` UC2 Steps 1-7. See the architect skill's [codebase-analysis.md](references/codebase-analysis.md) methodology (which is the same reference used by the MCP-powered skill).
96+
97+
### Step 8: Create project and import
98+
Navigate to flowspec.app, create a new project, and import the YAML via Chrome tools.
99+
100+
### Step 9: Guide auto-layout
101+
Instruct the user to click the Auto Layout button in the toolbar, or use `javascript_tool` to trigger it.
102+
103+
### Step 10: Export and validate
104+
Export YAML via browser tools and validate the spec locally.
105+
106+
---
107+
108+
## UC3: Design New Screens (Web)
109+
110+
### Step 1: Obtain screen image
111+
User designs in an external tool and provides screenshots, or starts with an empty screen.
112+
113+
### Step 2: Guide screen creation
114+
Instruct the user to create screens and upload images via the web UI.
115+
116+
### Step 3: Build YAML for data architecture
117+
Create dataPoints, components, transforms for the screen's data needs.
118+
119+
### Step 4: Import YAML
120+
Import via Chrome tools using the synthetic file injection recipe.
121+
122+
### Step 5: Guide region annotation
123+
Same as UC1 Step 7 — user annotates regions manually in the web UI.
124+
125+
---
126+
127+
## Limitations
128+
129+
- **Cannot automate Clerk authentication** — user must sign in manually
130+
- **Image upload requires user interaction** — browser file picker security prevents automation
131+
- **Region annotation is best done manually** — the web UI's drag-to-create is more ergonomic than coordinate-based automation
132+
- **Large YAML (500+ lines)** may need manual file import as fallback — copy YAML to clipboard, user pastes or uses file dialog
133+
- **DOM selectors may change** — if the web app UI updates, the Chrome recipes in `references/chrome-recipes.md` need updating
134+
135+
---
136+
137+
## Chrome Tool Reference
138+
139+
| Tool | Purpose |
140+
|------|---------|
141+
| `tabs_context_mcp` | Get current browser tab info |
142+
| `tabs_create_mcp` | Open new tab |
143+
| `read_page` | Read page content/DOM |
144+
| `javascript_tool` | Execute JavaScript in page |
145+
| `navigate` | Navigate to URL |
146+
| `find` | Find elements on page |
147+
| `form_input` | Fill form fields |
148+
| `computer` | Click/interact with page |
149+
150+
See [chrome-recipes.md](references/chrome-recipes.md) for concrete JavaScript snippets.
Lines changed: 169 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,169 @@
1+
# Chrome Recipes for FlowSpec Web App
2+
3+
Concrete JavaScript snippets for interacting with flowspec.app via `mcp__claude-in-chrome__javascript_tool`.
4+
5+
---
6+
7+
## Check Auth State
8+
9+
Verify the user is signed in by looking for the Clerk user button:
10+
11+
```javascript
12+
// Returns true if signed in, false otherwise
13+
const userBtn = document.querySelector('.cl-userButtonTrigger');
14+
const isSignedIn = !!userBtn;
15+
JSON.stringify({ isSignedIn });
16+
```
17+
18+
---
19+
20+
## Read Current Project ID
21+
22+
Parse the project ID from the URL query string:
23+
24+
```javascript
25+
const params = new URLSearchParams(window.location.search);
26+
const projectId = params.get('project');
27+
JSON.stringify({ projectId, url: window.location.href });
28+
```
29+
30+
---
31+
32+
## Navigate to a Project
33+
34+
```javascript
35+
window.location.href = 'https://flowspec.app/editor?project=PROJECT_ID_HERE';
36+
```
37+
38+
---
39+
40+
## Create New Project
41+
42+
Click the "New Project" button in the sidebar:
43+
44+
```javascript
45+
const newBtn = document.querySelector('button');
46+
const buttons = Array.from(document.querySelectorAll('button'));
47+
const newProjectBtn = buttons.find(b => b.textContent.trim().includes('New Project'));
48+
if (newProjectBtn) {
49+
newProjectBtn.click();
50+
'Clicked New Project button';
51+
} else {
52+
'New Project button not found — available buttons: ' + buttons.map(b => b.textContent.trim()).slice(0, 10).join(', ');
53+
}
54+
```
55+
56+
---
57+
58+
## Import YAML via Synthetic File Injection
59+
60+
This is the core recipe — creates a synthetic `File` object and injects it into the hidden file input used by the "Import YAML" button.
61+
62+
**DOM target:** `label.import-btn > input[type="file"]` (from `Sidebar.svelte:405-419`)
63+
64+
```javascript
65+
const yamlContent = `YAML_CONTENT_HERE`;
66+
67+
// Find the hidden file input inside the Import YAML label
68+
const fileInput = document.querySelector('.import-btn input[type="file"]');
69+
if (!fileInput) {
70+
'Import file input not found — ensure the sidebar is visible';
71+
} else {
72+
// Create a synthetic File from the YAML string
73+
const blob = new Blob([yamlContent], { type: 'application/x-yaml' });
74+
const file = new File([blob], 'import.yaml', { type: 'application/x-yaml' });
75+
76+
// Create a synthetic FileList via DataTransfer
77+
const dt = new DataTransfer();
78+
dt.items.add(file);
79+
fileInput.files = dt.files;
80+
81+
// Dispatch change event to trigger the onchange handler
82+
fileInput.dispatchEvent(new Event('change', { bubbles: true }));
83+
84+
'YAML imported successfully (' + yamlContent.length + ' chars)';
85+
}
86+
```
87+
88+
**Important:** Replace `YAML_CONTENT_HERE` with the actual YAML string. Escape backticks and `${` sequences if present in the YAML.
89+
90+
---
91+
92+
## Export YAML
93+
94+
Click the "Export YAML" button. The export triggers a file download, so we need to intercept it:
95+
96+
```javascript
97+
// Override the default download to capture the YAML content
98+
const buttons = Array.from(document.querySelectorAll('button'));
99+
const exportBtn = buttons.find(b => b.textContent.trim().includes('Export YAML'));
100+
if (exportBtn) {
101+
exportBtn.click();
102+
'Clicked Export YAML — check for downloaded file or use read_page to capture content';
103+
} else {
104+
'Export YAML button not found';
105+
}
106+
```
107+
108+
**Alternative:** After clicking export, use `mcp__claude-in-chrome__read_page` to read any modal or text content that appears.
109+
110+
---
111+
112+
## Click Auto Layout
113+
114+
Trigger the auto-layout button in the toolbar:
115+
116+
```javascript
117+
const buttons = Array.from(document.querySelectorAll('button'));
118+
const layoutBtn = buttons.find(b =>
119+
b.textContent.trim().includes('Auto Layout') ||
120+
b.title?.includes('Auto Layout') ||
121+
b.getAttribute('aria-label')?.includes('layout')
122+
);
123+
if (layoutBtn) {
124+
layoutBtn.click();
125+
'Auto layout triggered';
126+
} else {
127+
'Auto Layout button not found';
128+
}
129+
```
130+
131+
---
132+
133+
## Open Projects List
134+
135+
```javascript
136+
const buttons = Array.from(document.querySelectorAll('button'));
137+
const projectsBtn = buttons.find(b => b.textContent.trim().includes('Projects'));
138+
if (projectsBtn) {
139+
projectsBtn.click();
140+
'Opened projects list';
141+
} else {
142+
'Projects button not found';
143+
}
144+
```
145+
146+
---
147+
148+
## Read Project Name
149+
150+
```javascript
151+
// The project name is in an editable input in the sidebar
152+
const nameInput = document.querySelector('.project-name-input, input[placeholder*="project"], input[placeholder*="Project"]');
153+
if (nameInput) {
154+
JSON.stringify({ projectName: nameInput.value });
155+
} else {
156+
// Fallback: look for heading text
157+
const heading = document.querySelector('h2, .project-name');
158+
JSON.stringify({ projectName: heading?.textContent?.trim() || 'unknown' });
159+
}
160+
```
161+
162+
---
163+
164+
## Notes
165+
166+
- **DOM selectors are based on the current Sidebar.svelte implementation.** If the web app UI changes, these selectors may need updating.
167+
- **The synthetic file injection bypasses the native file picker**, which cannot be triggered programmatically due to browser security.
168+
- **Large YAML files (500+ lines)** may cause issues when injected as inline JavaScript strings. If this happens, instruct the user to manually import via the file dialog instead.
169+
- **Always verify the sidebar is visible** before attempting to interact with its elements. The sidebar is the primary control panel on the left side of the editor.

0 commit comments

Comments
 (0)