@myop/cli 0.1.46 → 0.1.48
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/dist/myop-cli.js +844 -812
- package/dist/skills/myop-angular-host/SKILL.md +118 -1
- package/dist/skills/myop-cli/SKILL.md +147 -0
- package/dist/skills/myop-component/SKILL.md +105 -73
- package/dist/skills/myop-component/references/component-api.md +0 -28
- package/dist/skills/myop-component/references/dev-workflow.md +3 -2
- package/dist/skills/myop-component/references/sizing-and-layout.md +41 -71
- package/dist/skills/myop-component/references/type-definitions.md +2 -19
- package/dist/skills/myop-react-host/SKILL.md +143 -1
- package/dist/skills/myop-react-native-host/SKILL.md +119 -1
- package/dist/skills/myop-vue-host/SKILL.md +112 -1
- package/package.json +1 -1
|
@@ -1,12 +1,129 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: myop-angular-host
|
|
3
|
-
description: "Integrate Myop components into Angular applications using @myop/angular.
|
|
3
|
+
description: "Integrate Myop components into Angular applications using @myop/angular. ALWAYS use the myop-component Angular component or auto-generated packages — NEVER create iframes manually. Covers the MyopComponent standalone component, inputs, outputs, content projection, data binding, preloading, auto-generated packages, and local dev setup. Activate when the user is building an Angular app that hosts Myop components, or when you see @myop/angular in package.json."
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
# Myop Angular Host Integration
|
|
7
7
|
|
|
8
8
|
Embed Myop components in Angular applications using `@myop/angular`.
|
|
9
9
|
|
|
10
|
+
## CRITICAL: Always Use the SDK
|
|
11
|
+
|
|
12
|
+
**NEVER create `<iframe>` elements manually. NEVER call `myop_init_interface()` or wire `myop_cta_handler()` directly.**
|
|
13
|
+
|
|
14
|
+
The `@myop/angular` SDK handles all iframe management, communication, loading, error handling, and caching. Always use `<myop-component>` or an auto-generated package.
|
|
15
|
+
|
|
16
|
+
```typescript
|
|
17
|
+
// WRONG — never do this
|
|
18
|
+
this.iframe.nativeElement.contentWindow.myop_init_interface(data)
|
|
19
|
+
|
|
20
|
+
// CORRECT — always use the SDK
|
|
21
|
+
<myop-component [componentId]="'abc-123'" [data]="data" (cta)="onCta($event)" />
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
## End-to-End Workflow: Angular App with Myop Components
|
|
25
|
+
|
|
26
|
+
Each Myop component is a **separate project** in its own directory. You create them, develop them, push them to get a `componentId`, then reference that ID in your Angular host app.
|
|
27
|
+
|
|
28
|
+
### Step 1: Create component projects
|
|
29
|
+
|
|
30
|
+
```bash
|
|
31
|
+
# Each component gets its own directory
|
|
32
|
+
mkdir components/sidebar && cd components/sidebar
|
|
33
|
+
npx myop create # Scaffolds index.html + myop.config.json
|
|
34
|
+
# Build the component UI (see myop-component skill), then Ctrl+C
|
|
35
|
+
|
|
36
|
+
cd ../ && mkdir chart && cd chart
|
|
37
|
+
npx myop create
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
### Step 2: Push components to get IDs
|
|
41
|
+
|
|
42
|
+
```bash
|
|
43
|
+
cd components/sidebar
|
|
44
|
+
npx myop push # Uploads → componentId written to myop.config.json
|
|
45
|
+
|
|
46
|
+
cd ../chart
|
|
47
|
+
npx myop push
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
### Step 3: Use in your Angular app
|
|
51
|
+
|
|
52
|
+
```bash
|
|
53
|
+
cd my-angular-app
|
|
54
|
+
npm install @myop/angular @myop/sdk
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
```typescript
|
|
58
|
+
import { MyopComponent } from "@myop/angular";
|
|
59
|
+
|
|
60
|
+
@Component({
|
|
61
|
+
selector: 'app-root',
|
|
62
|
+
standalone: true,
|
|
63
|
+
imports: [MyopComponent],
|
|
64
|
+
template: `
|
|
65
|
+
<myop-component
|
|
66
|
+
[componentId]="'<sidebar-componentId-from-step-2>'"
|
|
67
|
+
[data]="{ items: ['Home', 'Settings'] }"
|
|
68
|
+
(cta)="onCta($event)"
|
|
69
|
+
style="width: 300px"
|
|
70
|
+
/>
|
|
71
|
+
<myop-component
|
|
72
|
+
[componentId]="'<chart-componentId-from-step-2>'"
|
|
73
|
+
[data]="{ values: [10, 20, 30] }"
|
|
74
|
+
style="flex: 1"
|
|
75
|
+
/>
|
|
76
|
+
`
|
|
77
|
+
})
|
|
78
|
+
export class AppComponent {
|
|
79
|
+
onCta(event: any) { console.log(event.action, event.payload); }
|
|
80
|
+
}
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
### Working locally on existing components (componentId already in code)
|
|
84
|
+
|
|
85
|
+
When you find `componentId` values already used in the codebase and the developer wants to modify those components locally:
|
|
86
|
+
|
|
87
|
+
**Step A: Pull the component source**
|
|
88
|
+
|
|
89
|
+
```bash
|
|
90
|
+
mkdir components/sidebar && cd components/sidebar
|
|
91
|
+
npx myop pull <componentId>
|
|
92
|
+
# Downloads index.html + creates myop.config.json with the componentId
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
**Step B: Start the local dev server**
|
|
96
|
+
|
|
97
|
+
```bash
|
|
98
|
+
npx myop dev # Serves component on port 9292 with HMR
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
**Step C: Point the Angular app to local dev server**
|
|
102
|
+
|
|
103
|
+
```typescript
|
|
104
|
+
import { enableLocalDev } from "@myop/angular";
|
|
105
|
+
enableLocalDev(); // All <myop-component> instances load from localhost:9292
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
Now edits to `index.html` are reflected instantly in the Angular app.
|
|
109
|
+
|
|
110
|
+
**Step D: Push changes when done**
|
|
111
|
+
|
|
112
|
+
```bash
|
|
113
|
+
npx myop push # Uploads updated component to the same componentId
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
Remove or comment out `enableLocalDev()` to go back to loading from the Myop cloud.
|
|
117
|
+
|
|
118
|
+
**Multiple components:**
|
|
119
|
+
|
|
120
|
+
```bash
|
|
121
|
+
mkdir -p components && cd components
|
|
122
|
+
npx myop pull <sidebar-id> -o sidebar/index.html
|
|
123
|
+
npx myop pull <chart-id> -o chart/index.html
|
|
124
|
+
npx myop dev -m # Monorepo mode — select which components to serve
|
|
125
|
+
```
|
|
126
|
+
|
|
10
127
|
## When This Skill Activates
|
|
11
128
|
|
|
12
129
|
- `@myop/angular` is in `package.json` dependencies
|
|
@@ -0,0 +1,147 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: myop-cli
|
|
3
|
+
description: "Myop CLI tool for creating, developing, and deploying Myop components. Myop is a platform for building isolated, independently deployable UI components that integrate into any host application. Components can be built with any framework or architecture. Covers all CLI commands: create, dev, push, pull, list, train, mcp, login. Activates when the user needs CLI operations or when myop.config.json exists."
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Myop CLI
|
|
7
|
+
|
|
8
|
+
Command-line tool for creating, developing, and deploying Myop components.
|
|
9
|
+
|
|
10
|
+
## CRITICAL: Package Name
|
|
11
|
+
|
|
12
|
+
The npm package is **`myop`**. Always use `npx myop <command>`.
|
|
13
|
+
|
|
14
|
+
```bash
|
|
15
|
+
npx myop create # Correct
|
|
16
|
+
npx myop dev # Correct
|
|
17
|
+
npx myop push # Correct
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
**NEVER use** `npx @anthropic/myop`, `npx @myop/cli`, or any other package name — the package is simply **`myop`**.
|
|
21
|
+
|
|
22
|
+
## Immediate Action Required
|
|
23
|
+
|
|
24
|
+
**Check `myop.config.json` in the current directory:**
|
|
25
|
+
- **EXISTS** → This is an existing Myop component project. You can use `myop dev`, `myop push`, `myop pull`.
|
|
26
|
+
- **DOESN'T EXIST** → Either create a new component with `myop create`, or pull one with `myop pull <id>`.
|
|
27
|
+
|
|
28
|
+
**When to use this skill vs `myop-component`:**
|
|
29
|
+
- **This skill (myop-cli):** Operations — deploying, downloading, serving, listing, authenticating
|
|
30
|
+
- **myop-component:** Building — implementing `myop_init_interface`/`myop_cta_handler`, component architecture, styling
|
|
31
|
+
|
|
32
|
+
## Commands
|
|
33
|
+
|
|
34
|
+
### Create a new component
|
|
35
|
+
```bash
|
|
36
|
+
npx myop create
|
|
37
|
+
```
|
|
38
|
+
Interactive: prompts for name, creates `index.html` + `myop.config.json`, starts dev server.
|
|
39
|
+
|
|
40
|
+
### Start dev server
|
|
41
|
+
```bash
|
|
42
|
+
npx myop dev
|
|
43
|
+
```
|
|
44
|
+
- Port **9292** — serves the component
|
|
45
|
+
- Port **9293** — management dashboard
|
|
46
|
+
- Watches `.js`, `.css`, `.html` files for changes
|
|
47
|
+
- HMR: changes reflect instantly in the browser
|
|
48
|
+
- Single-file mode: serves `index.html` directly (no build step)
|
|
49
|
+
- Multi-file mode: runs `npm run build` or `node build.js` on change
|
|
50
|
+
|
|
51
|
+
### Push (deploy) to Myop
|
|
52
|
+
```bash
|
|
53
|
+
# Push using componentId from myop.config.json
|
|
54
|
+
npx myop push
|
|
55
|
+
|
|
56
|
+
# Push to a specific component ID
|
|
57
|
+
npx myop push <componentId>
|
|
58
|
+
```
|
|
59
|
+
Uploads the component to Myop platform. First push assigns a `componentId` and updates `myop.config.json`.
|
|
60
|
+
|
|
61
|
+
### Pull (download) from Myop
|
|
62
|
+
```bash
|
|
63
|
+
# Pull using componentId from myop.config.json
|
|
64
|
+
npx myop pull
|
|
65
|
+
|
|
66
|
+
# Pull by ID
|
|
67
|
+
npx myop pull <componentId>
|
|
68
|
+
|
|
69
|
+
# Pull to a specific output path
|
|
70
|
+
npx myop pull <componentId> -o ./output/index.html
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
### Browse & batch operations
|
|
74
|
+
```bash
|
|
75
|
+
# Interactive search, multi-select, batch pull or push
|
|
76
|
+
npx myop list
|
|
77
|
+
|
|
78
|
+
# Specify organization
|
|
79
|
+
npx myop list --org <orgId>
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
### Install AI skills for coding assistants
|
|
83
|
+
```bash
|
|
84
|
+
npx myop train
|
|
85
|
+
```
|
|
86
|
+
Installs SKILL.md files into all AI agent directories (Claude Code, Cursor, Windsurf, VS Code Copilot, Kiro, Goose, Augment, and more) so they understand Myop conventions.
|
|
87
|
+
|
|
88
|
+
### Configure MCP server
|
|
89
|
+
```bash
|
|
90
|
+
npx myop mcp
|
|
91
|
+
```
|
|
92
|
+
Interactive setup for connecting Myop MCP to Claude Code, Cursor, Windsurf, or VS Code Copilot.
|
|
93
|
+
|
|
94
|
+
### Authentication
|
|
95
|
+
```bash
|
|
96
|
+
npx myop login # Opens browser for OAuth
|
|
97
|
+
npx myop logout # Clears stored credentials
|
|
98
|
+
npx myop whoami # Show current user
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
## Common Workflows
|
|
102
|
+
|
|
103
|
+
### Deploy a component
|
|
104
|
+
```bash
|
|
105
|
+
npx myop push
|
|
106
|
+
# Dashboard: https://dashboard.myop.dev/dashboard/2.0/component/<componentId>
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
### Download all components from an org
|
|
110
|
+
```bash
|
|
111
|
+
mkdir components && cd components
|
|
112
|
+
npx myop list
|
|
113
|
+
# Select components → Pull
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
### Set up AI tooling
|
|
117
|
+
```bash
|
|
118
|
+
npx myop train # Install skills for all AI agents
|
|
119
|
+
npx myop mcp # Configure MCP server for your IDE
|
|
120
|
+
```
|
|
121
|
+
|
|
122
|
+
### Local development
|
|
123
|
+
```bash
|
|
124
|
+
npx myop dev # Start dev server at localhost:9292
|
|
125
|
+
# Edit index.html → changes reflect instantly
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
## Configuration
|
|
129
|
+
|
|
130
|
+
### myop.config.json
|
|
131
|
+
```json
|
|
132
|
+
{
|
|
133
|
+
"name": "My Component",
|
|
134
|
+
"componentId": "DEV",
|
|
135
|
+
"type": "html",
|
|
136
|
+
"author": "@myop-cli",
|
|
137
|
+
"HMR": true
|
|
138
|
+
}
|
|
139
|
+
```
|
|
140
|
+
- `componentId` is `"DEV"` until first push, then becomes a UUID
|
|
141
|
+
- After push, `organization` field is added
|
|
142
|
+
|
|
143
|
+
### Dev Server
|
|
144
|
+
- Component: `http://localhost:9292`
|
|
145
|
+
- Management: `http://localhost:9293`
|
|
146
|
+
- Single-file mode: serves `index.html` directly (no build)
|
|
147
|
+
- Multi-file mode: watches files, runs `npm run build` or `node build.js` on change
|
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: myop-component
|
|
3
|
-
description: "Myop is a platform for
|
|
3
|
+
description: "Myop is a platform for building isolated, independently deployable UI components that integrate into any host application. Components can be built with any framework or architecture — vanilla JS, React, Vue, Svelte, or any toolchain — and are deployed as a single entry point. This skill covers the component public API (myop_init_interface, myop_cta_handler), type definitions, sizing, layout, development workflow, and CLI commands. When building or modifying a Myop component, you must learn this skill."
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
# Myop Component Developer
|
|
7
7
|
|
|
8
|
-
Build
|
|
8
|
+
Build isolated, independently deployable UI components for the Myop platform.
|
|
9
9
|
|
|
10
10
|
## Immediate Action Required - Read This First
|
|
11
11
|
|
|
12
|
-
This skill activates when a `myop.config.json` file exists in the project, or when the user mentions "myop", "myop component", or asks to create/edit
|
|
12
|
+
This skill activates when a `myop.config.json` file exists in the project, or when the user mentions "myop", "myop component", or asks to create/edit a component for Myop.
|
|
13
13
|
|
|
14
14
|
**Your first action MUST be:**
|
|
15
15
|
1. Check if `myop.config.json` exists in the current directory
|
|
@@ -18,24 +18,30 @@ This skill activates when a `myop.config.json` file exists in the project, or wh
|
|
|
18
18
|
- Read `index.html` to understand the current component implementation
|
|
19
19
|
- Implement the requested changes following the patterns in this skill
|
|
20
20
|
3. If **NO** (new component):
|
|
21
|
-
- Guide the user to run `myop create` to scaffold a new component
|
|
21
|
+
- Guide the user to run `npx myop create` to scaffold a new component
|
|
22
22
|
- Or create the files manually following the structure below
|
|
23
23
|
|
|
24
24
|
## Component Architecture
|
|
25
25
|
|
|
26
|
-
|
|
26
|
+
A Myop component is an **isolated, independently deployable UI module** that runs within any host application (React, Vue, Angular, React Native, or any web framework). Components can be as complex as needed — built with any internal architecture, framework, or toolchain (vanilla JS, React, Vue, Svelte, Web Components, etc.).
|
|
27
|
+
|
|
28
|
+
The platform communicates with every component through exactly **2 global functions**:
|
|
27
29
|
|
|
28
30
|
| Function | Direction | Purpose | Reference |
|
|
29
31
|
|----------|-----------|---------|-----------|
|
|
30
32
|
| `myop_init_interface(data)` | Host -> Component | Receive data, render UI | [component-api.md](references/component-api.md) |
|
|
31
33
|
| `myop_cta_handler(action, payload)` | Component -> Host | Send user actions back | [component-api.md](references/component-api.md) |
|
|
32
34
|
|
|
35
|
+
### Deployment Format
|
|
36
|
+
|
|
37
|
+
The deployed artifact is a **single entry point** — currently an HTML file (`index.html` or `dist/index.html`) with all code, styles, and markup bundled. For multi-file projects, a build step (`npm run build`) compiles your source into this entry point. The internal complexity is unlimited: use modules, state management, third-party libraries, or any architecture you need.
|
|
38
|
+
|
|
33
39
|
## CRITICAL: Rules You Must Follow
|
|
34
40
|
|
|
35
41
|
1. **Both functions MUST be defined at top-level script execution** - never inside `setTimeout`, `Promise.then`, `async`, `DOMContentLoaded`, or any deferred code
|
|
36
42
|
2. **Rendering MUST be synchronous** - no `fetch`, no `await`, no `setTimeout` inside `myop_init_interface`
|
|
37
43
|
3. **All state is private** - use an IIFE to encapsulate; only expose the 2 global functions
|
|
38
|
-
4. **Single
|
|
44
|
+
4. **Single entry point** - the deployed artifact is one HTML file with all CSS/JS inlined (a build step compiles multi-file projects into this)
|
|
39
45
|
5. **No external network requests** - components cannot fetch external resources at runtime
|
|
40
46
|
|
|
41
47
|
## Quick Start - Minimal Component
|
|
@@ -46,25 +52,17 @@ Every Myop component is a **single HTML file** (`index.html` or `dist/index.html
|
|
|
46
52
|
<head>
|
|
47
53
|
<meta charset="UTF-8">
|
|
48
54
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
49
|
-
<meta name="myop:size" content='{"width":"100%","height":
|
|
55
|
+
<meta name="myop:size" content='{"width":"100%","height":300}'>
|
|
50
56
|
<title>My Component</title>
|
|
51
57
|
<script type="myop/types">
|
|
58
|
+
// Only dynamic data goes here — static labels stay hardcoded in the component
|
|
52
59
|
interface MyopInitData {
|
|
53
|
-
|
|
54
|
-
|
|
60
|
+
items: Array<{ id: string; label: string; status?: 'active' | 'done' }>;
|
|
61
|
+
selectedId?: string;
|
|
55
62
|
}
|
|
56
63
|
|
|
57
64
|
interface MyopCtaPayloads {
|
|
58
65
|
'item-selected': { itemId: string };
|
|
59
|
-
'size-requested': {
|
|
60
|
-
width?: number | null;
|
|
61
|
-
height?: number | null;
|
|
62
|
-
minWidth?: number | null;
|
|
63
|
-
maxWidth?: number | null;
|
|
64
|
-
minHeight?: number | null;
|
|
65
|
-
maxHeight?: number | null;
|
|
66
|
-
required?: boolean;
|
|
67
|
-
};
|
|
68
66
|
}
|
|
69
67
|
|
|
70
68
|
declare function myop_init_interface(): MyopInitData;
|
|
@@ -75,10 +73,10 @@ Every Myop component is a **single HTML file** (`index.html` or `dist/index.html
|
|
|
75
73
|
</script>
|
|
76
74
|
<style>
|
|
77
75
|
* { box-sizing: border-box; margin: 0; padding: 0; }
|
|
78
|
-
html, body { width: 100%;
|
|
76
|
+
html, body { width: 100%; margin: 0; padding: 0;
|
|
79
77
|
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
|
|
80
78
|
}
|
|
81
|
-
#app-root { width: 100%;
|
|
79
|
+
#app-root { width: 100%; padding: 16px; }
|
|
82
80
|
</style>
|
|
83
81
|
</head>
|
|
84
82
|
<body>
|
|
@@ -91,8 +89,9 @@ Every Myop component is a **single HTML file** (`index.html` or `dist/index.html
|
|
|
91
89
|
function render(data) {
|
|
92
90
|
state = data;
|
|
93
91
|
var root = document.getElementById('app-root');
|
|
92
|
+
// "My Tasks" heading is hardcoded — it's part of the component, not dynamic data
|
|
94
93
|
root.innerHTML =
|
|
95
|
-
'<h2>
|
|
94
|
+
'<h2>My Tasks</h2>' +
|
|
96
95
|
'<ul>' + (data.items || []).map(function(item) {
|
|
97
96
|
return '<li data-id="' + item.id + '">' + item.label + '</li>';
|
|
98
97
|
}).join('') + '</ul>';
|
|
@@ -117,12 +116,12 @@ Every Myop component is a **single HTML file** (`index.html` or `dist/index.html
|
|
|
117
116
|
})();
|
|
118
117
|
</script>
|
|
119
118
|
|
|
119
|
+
<!-- Preview: only dynamic data, not UI labels -->
|
|
120
120
|
<script id="myop_preview">
|
|
121
121
|
window.myop_init_interface({
|
|
122
|
-
title: 'My Component',
|
|
123
122
|
items: [
|
|
124
|
-
{ id: '1', label: '
|
|
125
|
-
{ id: '2', label: '
|
|
123
|
+
{ id: '1', label: 'Review PR #42' },
|
|
124
|
+
{ id: '2', label: 'Update dependencies', status: 'done' }
|
|
126
125
|
]
|
|
127
126
|
});
|
|
128
127
|
</script>
|
|
@@ -130,31 +129,67 @@ Every Myop component is a **single HTML file** (`index.html` or `dist/index.html
|
|
|
130
129
|
</html>
|
|
131
130
|
```
|
|
132
131
|
|
|
132
|
+
## What Goes in myop_init_interface vs Component Code
|
|
133
|
+
|
|
134
|
+
Think of `myop_init_interface(data)` exactly like **React component props**. The component is a reusable UI module — its structure, labels, buttons, and layout are built-in. The host only passes dynamic data.
|
|
135
|
+
|
|
136
|
+
### Component code (hardcoded — like JSX):
|
|
137
|
+
- Button labels ("Submit", "Cancel", "Sign Up")
|
|
138
|
+
- Headings and static copy ("Welcome", "Sign up to continue")
|
|
139
|
+
- Icons, decorative elements, illustrations
|
|
140
|
+
- Form labels ("Email", "Password")
|
|
141
|
+
- Placeholder text
|
|
142
|
+
- Navigation items, tabs, section titles
|
|
143
|
+
- Any text that is part of the component's identity
|
|
144
|
+
|
|
145
|
+
### myop_init_interface data (dynamic — like React props):
|
|
146
|
+
- Lists of items (users, products, tasks, notifications)
|
|
147
|
+
- User-specific data (name, email, avatar, role)
|
|
148
|
+
- Configuration flags (theme, locale, permissions, feature flags)
|
|
149
|
+
- Counts and metrics (unread: 5, total: 42)
|
|
150
|
+
- State (selectedId, isExpanded, activeTab)
|
|
151
|
+
- URLs and dynamic assets (profile image URL, API endpoints)
|
|
152
|
+
|
|
153
|
+
### Example — Login Component:
|
|
154
|
+
|
|
155
|
+
| WRONG (everything as data) | CORRECT (only dynamic data as props) |
|
|
156
|
+
|---|---|
|
|
157
|
+
| `heading: "Welcome back"` | `user: { email: "prefilled@example.com" }` |
|
|
158
|
+
| `emailLabel: "Email"` | `error: null` |
|
|
159
|
+
| `passwordLabel: "Password"` | `redirectUrl: "/dashboard"` |
|
|
160
|
+
| `submitText: "Sign In"` | |
|
|
161
|
+
| `forgotText: "Forgot password?"` | |
|
|
162
|
+
|
|
163
|
+
The labels "Welcome back", "Email", "Password", "Sign In" are part of the component — hardcoded in the HTML/JS, just like you'd write them in React JSX.
|
|
164
|
+
|
|
165
|
+
### Rule of thumb:
|
|
166
|
+
If the host app would NOT need to change this value across different instances, it belongs in the component code, not in myop_init_interface.
|
|
167
|
+
|
|
133
168
|
## Component File Structure
|
|
134
169
|
|
|
135
|
-
### Single-file mode (simplest)
|
|
170
|
+
### Single-file mode (simplest — good for small components)
|
|
136
171
|
```
|
|
137
172
|
project/
|
|
138
|
-
├── index.html #
|
|
173
|
+
├── index.html # Complete component in one file
|
|
139
174
|
├── myop.config.json # Component metadata
|
|
140
175
|
└── .gitignore
|
|
141
176
|
```
|
|
142
177
|
|
|
143
|
-
### Multi-file mode (with build step)
|
|
178
|
+
### Multi-file mode (with build step — for complex components)
|
|
144
179
|
```
|
|
145
180
|
project/
|
|
146
181
|
├── index.html # HTML template with <link> and <script src>
|
|
147
|
-
├── src/
|
|
182
|
+
├── src/ # Any internal architecture you need
|
|
148
183
|
│ ├── index.js # Entry point
|
|
149
|
-
│ ├── modules/
|
|
150
|
-
│ │ ├── app.js
|
|
184
|
+
│ ├── modules/ # Business logic, state management, etc.
|
|
185
|
+
│ │ ├── app.js
|
|
151
186
|
│ │ └── myop.js # Myop interface setup
|
|
152
187
|
│ └── styles/
|
|
153
|
-
│ ├── index.css
|
|
154
|
-
│ └── main.css
|
|
155
|
-
├── build.js #
|
|
188
|
+
│ ├── index.css
|
|
189
|
+
│ └── main.css
|
|
190
|
+
├── build.js # Bundler (compiles everything into dist/index.html)
|
|
156
191
|
├── dist/
|
|
157
|
-
│ └── index.html # Built
|
|
192
|
+
│ └── index.html # Built entry point (deployed artifact)
|
|
158
193
|
├── myop.config.json
|
|
159
194
|
├── package.json
|
|
160
195
|
└── .gitignore
|
|
@@ -212,31 +247,35 @@ project/
|
|
|
212
247
|
| Mutating data passed to `myop_init_interface` | Storing a copy of the data |
|
|
213
248
|
| Not returning state when called without args | `if (!data) return state;` pattern |
|
|
214
249
|
|
|
250
|
+
## CLI — Package Name is `myop`
|
|
251
|
+
|
|
252
|
+
The npm package is **`myop`**. Always use `npx myop <command>`. **NEVER** `npx @anthropic/myop`, `npx @myop/cli`, or any other scope — the package is simply **`myop`**.
|
|
253
|
+
|
|
215
254
|
## CLI Commands Quick Reference
|
|
216
255
|
|
|
217
256
|
| Command | Description |
|
|
218
257
|
|---------|-------------|
|
|
219
|
-
| `myop create` | Create a new component (scaffolds files + starts dev server) |
|
|
220
|
-
| `myop dev` | Start development server with HMR on port 9292 |
|
|
221
|
-
| `myop push [componentId]` | Upload component to Myop platform (optional ID overrides config) |
|
|
222
|
-
| `myop pull [componentId]` | Download component HTML from Myop platform |
|
|
223
|
-
| `myop list [--org <orgId>]` | Browse, search, and batch pull/push remote components |
|
|
224
|
-
| `myop sync` | Build and upload component to Myop platform |
|
|
225
|
-
| `myop login` | Authenticate with Myop (opens browser) |
|
|
226
|
-
| `myop logout` | Clear stored credentials |
|
|
227
|
-
| `myop whoami` | Show current authenticated user |
|
|
258
|
+
| `npx myop create` | Create a new component (scaffolds files + starts dev server) |
|
|
259
|
+
| `npx myop dev` | Start development server with HMR on port 9292 |
|
|
260
|
+
| `npx myop push [componentId]` | Upload component to Myop platform (optional ID overrides config) |
|
|
261
|
+
| `npx myop pull [componentId]` | Download component HTML from Myop platform |
|
|
262
|
+
| `npx myop list [--org <orgId>]` | Browse, search, and batch pull/push remote components |
|
|
263
|
+
| `npx myop sync` | Build and upload component to Myop platform |
|
|
264
|
+
| `npx myop login` | Authenticate with Myop (opens browser) |
|
|
265
|
+
| `npx myop logout` | Clear stored credentials |
|
|
266
|
+
| `npx myop whoami` | Show current authenticated user |
|
|
228
267
|
|
|
229
268
|
## Deploying with `myop push`
|
|
230
269
|
|
|
231
|
-
`myop push` uploads the
|
|
270
|
+
`myop push` uploads the component to the Myop platform. After a successful push, the component is live — including all CTA wiring (e.g., `myop_cta_handler('button-clicked', …)`). No rebuild or redeploy of the host application is needed.
|
|
232
271
|
|
|
233
272
|
### What push does
|
|
234
273
|
|
|
235
274
|
1. Reads `myop.config.json` to identify the component
|
|
236
275
|
2. If a `componentId` argument is passed, it overrides the one in config
|
|
237
|
-
3. Locates the
|
|
276
|
+
3. Locates the entry point (`index.html` for single-file mode, `dist/index.html` for multi-file)
|
|
238
277
|
4. Authenticates with Myop (prompts login if needed)
|
|
239
|
-
5. Uploads the
|
|
278
|
+
5. Uploads the component via a presigned URL
|
|
240
279
|
6. On first push: assigns a real `componentId` (UUID) and `organization` to `myop.config.json`
|
|
241
280
|
7. On subsequent pushes: adds a new version to the existing component
|
|
242
281
|
|
|
@@ -246,17 +285,10 @@ From the component's project directory:
|
|
|
246
285
|
|
|
247
286
|
```bash
|
|
248
287
|
# Push using componentId from myop.config.json
|
|
249
|
-
myop push
|
|
288
|
+
npx myop push
|
|
250
289
|
|
|
251
290
|
# Push to a specific remote component (overrides config)
|
|
252
|
-
myop push <componentId>
|
|
253
|
-
```
|
|
254
|
-
|
|
255
|
-
Or using npx (no global install needed):
|
|
256
|
-
|
|
257
|
-
```bash
|
|
258
|
-
npx @myop/cli push
|
|
259
|
-
npx @myop/cli push <componentId>
|
|
291
|
+
npx myop push <componentId>
|
|
260
292
|
```
|
|
261
293
|
|
|
262
294
|
### When the user asks to push
|
|
@@ -264,7 +296,7 @@ npx @myop/cli push <componentId>
|
|
|
264
296
|
When the user says **"push to myop"**, **"deploy"**, **"upload"**, or **"run the push"**, you should:
|
|
265
297
|
|
|
266
298
|
1. `cd` into the component's project directory (where `myop.config.json` lives)
|
|
267
|
-
2. Run `npx
|
|
299
|
+
2. Run `npx myop push`
|
|
268
300
|
3. If push succeeds, report the dashboard URL: `https://dashboard.myop.dev/dashboard/2.0/component/<componentId>`
|
|
269
301
|
4. If push fails, show the error output and suggest the user run the command manually
|
|
270
302
|
|
|
@@ -272,24 +304,24 @@ When the user says **"push to myop"**, **"deploy"**, **"upload"**, or **"run the
|
|
|
272
304
|
|
|
273
305
|
- **First push** — `componentId` in `myop.config.json` changes from `"DEV"` to a real UUID. The `organization` field is also added. The component now exists on the Myop platform.
|
|
274
306
|
- **Subsequent pushes** — A new version is added to the existing component. The previous version remains accessible. The latest version becomes the live version immediately.
|
|
275
|
-
- **What goes live** — The
|
|
276
|
-
- **Multi-file projects** — For projects with a build step, run `myop sync` instead (which runs `npm run build` first, then uploads
|
|
307
|
+
- **What goes live** — The complete component entry point is uploaded with all CTA handlers, type definitions, styles, and logic bundled. The host application picks up changes automatically on next load (no host redeploy).
|
|
308
|
+
- **Multi-file projects** — For projects with a build step, run `myop sync` instead (which runs `npm run build` first, then uploads the built entry point).
|
|
277
309
|
|
|
278
310
|
## Downloading with `myop pull`
|
|
279
311
|
|
|
280
|
-
`myop pull` downloads a component's latest
|
|
312
|
+
`myop pull` downloads a component's latest version from the Myop platform into your local directory.
|
|
281
313
|
|
|
282
314
|
### Running pull
|
|
283
315
|
|
|
284
316
|
```bash
|
|
285
317
|
# Pull using componentId from myop.config.json
|
|
286
|
-
myop pull
|
|
318
|
+
npx myop pull
|
|
287
319
|
|
|
288
320
|
# Pull a specific component by ID (works in empty directories)
|
|
289
|
-
myop pull <componentId>
|
|
321
|
+
npx myop pull <componentId>
|
|
290
322
|
|
|
291
323
|
# Pull to a custom output path
|
|
292
|
-
myop pull <componentId> -o ./components/sidebar/index.html
|
|
324
|
+
npx myop pull <componentId> -o ./components/sidebar/index.html
|
|
293
325
|
```
|
|
294
326
|
|
|
295
327
|
### When the user asks to pull
|
|
@@ -297,34 +329,34 @@ myop pull <componentId> -o ./components/sidebar/index.html
|
|
|
297
329
|
When the user says **"pull from myop"**, **"download component"**, or **"get the latest version"**, you should:
|
|
298
330
|
|
|
299
331
|
1. `cd` into the component's project directory (or an empty directory for a new clone)
|
|
300
|
-
2. Run `npx
|
|
332
|
+
2. Run `npx myop pull` (or `npx myop pull <componentId>` if pulling a specific component)
|
|
301
333
|
3. Report the saved file path and size
|
|
302
334
|
|
|
303
335
|
### Pull behavior
|
|
304
336
|
|
|
305
|
-
- **Existing directory** — overwrites `index.html`
|
|
337
|
+
- **Existing directory** — overwrites the entry point (`index.html` or `dist/index.html`) with the latest remote version
|
|
306
338
|
- **Empty directory** — creates `index.html` + `myop.config.json` with component metadata
|
|
307
|
-
- **Custom output** — use `-o <path>` to write
|
|
339
|
+
- **Custom output** — use `-o <path>` to write to a specific file; parent directories are created automatically
|
|
308
340
|
|
|
309
341
|
## Browsing with `myop list`
|
|
310
342
|
|
|
311
|
-
`myop list` lets you browse all components in your organization
|
|
343
|
+
`myop list` lets you browse all components in your organization — search, filter, select multiple, and batch pull or push them.
|
|
312
344
|
|
|
313
345
|
### Running list
|
|
314
346
|
|
|
315
347
|
```bash
|
|
316
348
|
# Interactive browse (prompts for org if multiple)
|
|
317
|
-
myop list
|
|
349
|
+
npx myop list
|
|
318
350
|
|
|
319
351
|
# Specify an organization
|
|
320
|
-
myop list --org <orgId>
|
|
352
|
+
npx myop list --org <orgId>
|
|
321
353
|
```
|
|
322
354
|
|
|
323
355
|
### When the user asks to list or browse
|
|
324
356
|
|
|
325
357
|
When the user says **"show my components"**, **"list components"**, **"browse"**, or **"clone all components"**, you should:
|
|
326
358
|
|
|
327
|
-
1. Run `npx
|
|
359
|
+
1. Run `npx myop list`
|
|
328
360
|
2. The interactive UI handles org selection, search, and batch operations
|
|
329
361
|
|
|
330
362
|
### List behavior
|
|
@@ -336,8 +368,8 @@ When the user says **"show my components"**, **"list components"**, **"browse"**
|
|
|
336
368
|
|
|
337
369
|
## Workflow Summary
|
|
338
370
|
|
|
339
|
-
1. `myop create`
|
|
340
|
-
2.
|
|
341
|
-
3. `myop dev`
|
|
342
|
-
4. `myop push`
|
|
371
|
+
1. `npx myop create` — Scaffold a new component
|
|
372
|
+
2. Build your component — edit source files (single-file or multi-file with any framework)
|
|
373
|
+
3. `npx myop dev` — Preview with hot reload at http://localhost:9292
|
|
374
|
+
4. `npx myop push` — Deploy to Myop platform (live immediately)
|
|
343
375
|
5. View on dashboard: `https://dashboard.myop.dev/dashboard/2.0/component/<componentId>`
|