vibespot 1.2.0 → 1.3.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 +44 -5
- package/assets/blog-rules.md +251 -0
- package/assets/email-rules.md +390 -0
- package/assets/humanify-guide.md +300 -101
- package/assets/plan-templates/blog-content-hub.md +18 -9
- package/assets/plan-templates/email-announcement.md +41 -0
- package/assets/plan-templates/email-event-invite.md +43 -0
- package/assets/plan-templates/email-newsletter.md +41 -0
- package/assets/plan-templates/email-re-engagement.md +42 -0
- package/assets/plan-templates/email-welcome.md +41 -0
- package/dist/index.js +1460 -387
- package/dist/index.js.map +1 -1
- package/package.json +5 -5
- package/starters/06-blog-content-hub.json +75 -0
- package/starters/06-email-welcome.json +60 -0
- package/starters/07-email-announcement.json +60 -0
- package/starters/08-email-newsletter.json +52 -0
- package/ui/chat.js +777 -63
- package/ui/code-editor.js +49 -7
- package/ui/dashboard.js +379 -93
- package/ui/docs/docs.css +29 -0
- package/ui/docs/index.html +186 -108
- package/ui/docs/screenshots/brand-kit-preview.png +0 -0
- package/ui/docs/screenshots/content-type-dropdown.png +0 -0
- package/ui/docs/screenshots/editor-full-layout.png +0 -0
- package/ui/docs/screenshots/inline-wysiwyg-editing.png +0 -0
- package/ui/docs/screenshots/multi-page-tree.png +0 -0
- package/ui/docs/screenshots/onboarding-walkthrough.png +0 -0
- package/ui/docs/screenshots/split-pane-view.png +0 -0
- package/ui/docs/screenshots/visual-controls-toolbar.png +0 -0
- package/ui/docs/screenshots/workspace-tabs.png +0 -0
- package/ui/email-preview.js +109 -0
- package/ui/field-editor.js +72 -1
- package/ui/icons.js +120 -0
- package/ui/index.html +877 -629
- package/ui/inline-edit.js +710 -0
- package/ui/plan.js +0 -0
- package/ui/preview.js +101 -198
- package/ui/section-controls.js +628 -0
- package/ui/settings.js +58 -16
- package/ui/setup.js +750 -140
- package/ui/styles.css +3430 -952
- package/ui/upload-panel.js +47 -20
package/README.md
CHANGED
|
@@ -25,20 +25,33 @@ npx vibespot
|
|
|
25
25
|
|
|
26
26
|
Opens a browser with:
|
|
27
27
|
- **Chat on the left** — describe your landing page in natural language
|
|
28
|
-
- **Live preview on the right** — see your page render in real-time,
|
|
28
|
+
- **Live preview on the right** — see your page render in real-time, with Split, Plan, and Code views
|
|
29
29
|
- **Agentic pipeline** — multi-stage AI generation with real-time progress
|
|
30
|
-
- **
|
|
31
|
-
- **
|
|
30
|
+
- **Multi-page sites** — create full HubSpot sites from a single prompt with shared header/footer, per-page layouts, and cross-page navigation validation
|
|
31
|
+
- **Inline WYSIWYG editing** — click text, images, and links directly in the live preview to edit them inline
|
|
32
|
+
- **Per-section visual controls** — hover any module for a floating toolbar with color pickers, spacing sliders, image swap, and font size controls
|
|
33
|
+
- **Plan mode** — toggle on to deliberate before generating: the AI asks elicitation questions, builds a markdown plan in a resizable sidebar, and only generates after you approve. Pre-canned plan templates for common page types skip the cold-start phase.
|
|
34
|
+
- **Onboarding walkthrough** — 3-step intro for first-time users covering what vibeSpot is, how it maps to HubSpot, and a guided first prompt
|
|
35
|
+
- **Workspace tabs** — Pages, Brand, Library, Marketplace, Settings tabs organize the dashboard. Brand tab includes a live visual preview of your brand kit.
|
|
36
|
+
- **Project sidebar** — create, open, resume, or delete projects; page tree shows all templates with type badges and module counts
|
|
32
37
|
- **Module management** — reorder via drag-and-drop, edit fields, delete modules from module list or module library
|
|
33
|
-
- **Starter templates** — SaaS, Portfolio, Restaurant, Event
|
|
38
|
+
- **Starter templates** — SaaS, Portfolio, Restaurant, Event, Coming Soon, Blog — pre-built page bundles for instant preview with no AI wait
|
|
39
|
+
- **Content types** — landing pages, email templates, and blog templates all supported from the UI page type dropdown
|
|
40
|
+
- **Split-pane view** — preview + code editor side by side in a 50/50 layout
|
|
41
|
+
- **Brand kit enforcement** — colors, fonts, and logo are injected as constraints into AI generation; validator warns on off-brand values
|
|
42
|
+
- **Interact mode** — unified mode that auto-detects whether you're editing content inline or referencing modules in chat
|
|
43
|
+
- **Undo/redo** — Ctrl+Z / Ctrl+Y step through version history; a compact timeline strip shows every generation step
|
|
44
|
+
- **Smart suggestions** — contextual suggestion chips appear after pipeline completion, filtered by existing modules
|
|
34
45
|
- **From Figma** *(Beta)* — paste a Figma URL to extract design tokens, text, and assets, then generate a full page that translates the design verbatim
|
|
35
46
|
- **From React** *(Beta)* — convert existing React/Lovable projects from a Git URL
|
|
47
|
+
- **From HubSpot** — fetch an existing theme, then run inverse analysis to extract design tokens, module graph, and round-trip risks
|
|
36
48
|
- **Field editor** — tweak text, colors, images directly
|
|
37
49
|
- **File uploads** — attach images and documents via drag-and-drop or paperclip button
|
|
38
50
|
- **Upload to HubSpot** — per-file progress, auto-fix, celebration popup with direct portal link
|
|
39
|
-
- **Version history** — per-template git commits with rollback
|
|
51
|
+
- **Version history** — per-template git commits with rollback in a collapsible bottom panel
|
|
40
52
|
- **Light/dark mode** — toggle or auto-detect system preference
|
|
41
53
|
- **Tabbed settings** — AI engines (with extended-thinking toggle), HubSpot accounts, Figma, GitHub, vibeSpot config
|
|
54
|
+
- **Mobile responsive** — tablet breakpoint collapses the rail; sub-768px shows a gate dialog
|
|
42
55
|
- **ZIP download** — export your theme as a ZIP file
|
|
43
56
|
|
|
44
57
|
### Agentic Pipeline
|
|
@@ -161,6 +174,7 @@ vibespot wizard # Classic CLI wizard
|
|
|
161
174
|
vibespot init # Check and install required tools
|
|
162
175
|
vibespot convert # Convert a React project (no upload)
|
|
163
176
|
vibespot upload # Upload theme to HubSpot
|
|
177
|
+
vibespot inverse [--path] [--json] [--apply-tokens] # Analyze an imported theme (design tokens, module graph, risks)
|
|
164
178
|
vibespot marketplace check [--fix] [--json] # Audit theme for HubSpot Marketplace submission
|
|
165
179
|
vibespot marketplace edit # Edit Marketplace listing metadata (marketplace.json)
|
|
166
180
|
vibespot doctor # Diagnose environment issues
|
|
@@ -182,6 +196,31 @@ Settings are managed in the **Settings** panel (tabbed: AI, HubSpot, Figma, GitH
|
|
|
182
196
|
|
|
183
197
|
## What's New
|
|
184
198
|
|
|
199
|
+
### Unreleased
|
|
200
|
+
- **Multi-page sites** — create full HubSpot sites from a single prompt with shared modules, page tree sidebar, and cross-page navigation validation
|
|
201
|
+
- **Inline WYSIWYG editing** — click text, images, and links directly in the live preview to edit inline
|
|
202
|
+
- **Per-section visual controls** — hover toolbar with color pickers, spacing sliders, image swap, and font size controls
|
|
203
|
+
- **Blog template generation** — blog as a content type with HubSpot blog variable support and a Blog Content Hub starter template
|
|
204
|
+
- **Split-pane view** — preview + code editor side by side
|
|
205
|
+
- **Brand kit enforcement** — colors, fonts, and logo injected as AI constraints with off-brand warnings
|
|
206
|
+
- **Workspace tab navigation** — Pages, Brand, Library, Marketplace, Settings tabs replace the flat dashboard
|
|
207
|
+
- **First-visit onboarding** — 3-step walkthrough for new users
|
|
208
|
+
- **CSS token system** — comprehensive design tokens for spacing, typography, z-index, transitions, and component library
|
|
209
|
+
- **HubSpot terminology alignment** — UI copy uses HubSpot's canonical terms (Module, Module Library, Brand Kit)
|
|
210
|
+
|
|
211
|
+
### v1.3.0
|
|
212
|
+
- **Email template generation** — full pipeline support for HubSpot email templates: email-specific prompts, table-based layout, MSO/VML compatibility, 3 email starters, 5 email plan templates, and email validator auto-fix
|
|
213
|
+
|
|
214
|
+
### v1.2.0
|
|
215
|
+
- **Inverse pipeline (HubSpot → vibeSpot)** — reverse-engineer imported HubSpot themes: design token extraction, module graph, field schema flags, and round-trip risk detection
|
|
216
|
+
- **Simplified setup** — returning users land on a recent projects rail; new users see a chat-style prompt as the primary path
|
|
217
|
+
- **Select mode** — click elements in the live preview to reference them in chat
|
|
218
|
+
- **Undo/redo with visual timeline** — Ctrl+Z / Ctrl+Y step through version history with hover tooltips
|
|
219
|
+
- **Smart chat suggestions** — contextual suggestion chips filtered by existing modules
|
|
220
|
+
- **Plan-mode templates** — 7 pre-canned plan structures that skip cold-start elicitation
|
|
221
|
+
- **Starter templates** — 5 bundled page templates for instant preview with no AI wait
|
|
222
|
+
- **HubSpot Marketplace publication path** — rule-based audit, auto-fix, and listing metadata editor
|
|
223
|
+
|
|
185
224
|
### v1.1.3
|
|
186
225
|
- **Model selection persists for Codex CLI, Gemini CLI, and Gemini API** — picking a non-default model used to revert because the `/api/settings/engine` route had no cases for those engines, no config fields existed, and `getCurrentModel` returned `null` (so the dropdown reset to the first option). Added the config fields, route persistence, UI lookup, and runtime `--model`/`-m` flag plumbing into the CLI subprocess invocation.
|
|
187
226
|
|
|
@@ -0,0 +1,251 @@
|
|
|
1
|
+
# BLOG_RULES.md — HubSpot Blog Template Rules & Variables
|
|
2
|
+
|
|
3
|
+
> Rules for generating HubSpot blog listing and blog post templates. Every variable and pattern here comes from the HubSpot CMS blog documentation and real template validation.
|
|
4
|
+
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
## 1. Template Types
|
|
8
|
+
|
|
9
|
+
HubSpot blogs require TWO templates:
|
|
10
|
+
|
|
11
|
+
### Blog Post Template
|
|
12
|
+
- `templateType: blog_post` in the template annotation
|
|
13
|
+
- Renders a single blog post
|
|
14
|
+
- `host_template_types: ["BLOG_POST"]` in module meta.json
|
|
15
|
+
|
|
16
|
+
### Blog Listing Template
|
|
17
|
+
- `templateType: blog_listing` in the template annotation
|
|
18
|
+
- Renders the blog index / archive page with post cards
|
|
19
|
+
- `host_template_types: ["BLOG_LISTING"]` in module meta.json
|
|
20
|
+
|
|
21
|
+
Modules can support both: `host_template_types: ["BLOG_POST", "BLOG_LISTING"]`
|
|
22
|
+
|
|
23
|
+
---
|
|
24
|
+
|
|
25
|
+
## 2. Blog Post Variables (Required)
|
|
26
|
+
|
|
27
|
+
These HubL variables are available in blog post templates:
|
|
28
|
+
|
|
29
|
+
```
|
|
30
|
+
{{ content.name }} — Post title
|
|
31
|
+
{{ content.post_body }} — Full post body HTML (the article content)
|
|
32
|
+
{{ content.featured_image }} — Featured image URL
|
|
33
|
+
{{ content.featured_image_alt_text }} — Featured image alt text
|
|
34
|
+
{{ content.publish_date }} — Publish date (use |datetimeformat)
|
|
35
|
+
{{ content.updated }} — Last updated date
|
|
36
|
+
{{ content.meta_description }} — SEO meta description / excerpt
|
|
37
|
+
{{ content.absolute_url }} — Canonical URL
|
|
38
|
+
{{ content.comment_count }} — Number of comments
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
### Author Variables
|
|
42
|
+
```
|
|
43
|
+
{{ content.blog_post_author }} — Author display name
|
|
44
|
+
{{ content.author.display_name }} — Author display name (alternative)
|
|
45
|
+
{{ content.author.avatar }} — Author avatar image URL
|
|
46
|
+
{{ content.author.bio }} — Author bio text
|
|
47
|
+
{{ content.author.slug }} — Author URL slug
|
|
48
|
+
{{ content.author.email }} — Author email
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
### Tag & Topic Variables
|
|
52
|
+
```
|
|
53
|
+
{{ content.tag_list }} — List of tags (iterable)
|
|
54
|
+
{{ content.topic_list }} — List of topics/categories (iterable)
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
Tag iteration:
|
|
58
|
+
```html
|
|
59
|
+
{% for tag in content.tag_list %}
|
|
60
|
+
<a href="{{ blog_tag_url(group.id, tag.slug) }}">{{ tag.name }}</a>
|
|
61
|
+
{% endfor %}
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
### Date Formatting
|
|
65
|
+
```html
|
|
66
|
+
{{ content.publish_date|datetimeformat('%B %d, %Y') }}
|
|
67
|
+
<!-- Output: April 30, 2026 -->
|
|
68
|
+
|
|
69
|
+
{{ content.publish_date|datetimeformat('%b %d') }}
|
|
70
|
+
<!-- Output: Apr 30 -->
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
---
|
|
74
|
+
|
|
75
|
+
## 3. Blog Listing Variables (Required)
|
|
76
|
+
|
|
77
|
+
These HubL variables are available in blog listing templates:
|
|
78
|
+
|
|
79
|
+
### Post Loop
|
|
80
|
+
```html
|
|
81
|
+
{% for content in contents %}
|
|
82
|
+
<h2><a href="{{ content.absolute_url }}">{{ content.name }}</a></h2>
|
|
83
|
+
<p>{{ content.meta_description|truncate(160) }}</p>
|
|
84
|
+
{% if content.featured_image %}
|
|
85
|
+
<img src="{{ content.featured_image }}" alt="{{ content.featured_image_alt_text }}" />
|
|
86
|
+
{% endif %}
|
|
87
|
+
<span>{{ content.publish_date|datetimeformat('%B %d, %Y') }}</span>
|
|
88
|
+
<span>{{ content.blog_post_author }}</span>
|
|
89
|
+
{% endfor %}
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
### Blog Metadata
|
|
93
|
+
```
|
|
94
|
+
{{ group.public_title }} — Blog name/title
|
|
95
|
+
{{ group.description }} — Blog description
|
|
96
|
+
{{ group.absolute_url }} — Blog listing URL
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
### Pagination
|
|
100
|
+
```html
|
|
101
|
+
{% if last_page_num > 1 %}
|
|
102
|
+
<nav class="blog-pagination">
|
|
103
|
+
{% if current_page_num > 1 %}
|
|
104
|
+
<a href="{{ blog_page_link(current_page_num - 1) }}">Previous</a>
|
|
105
|
+
{% endif %}
|
|
106
|
+
|
|
107
|
+
{% for page_num in range(1, last_page_num + 1) %}
|
|
108
|
+
{% if page_num == current_page_num %}
|
|
109
|
+
<span class="current">{{ page_num }}</span>
|
|
110
|
+
{% else %}
|
|
111
|
+
<a href="{{ blog_page_link(page_num) }}">{{ page_num }}</a>
|
|
112
|
+
{% endif %}
|
|
113
|
+
{% endfor %}
|
|
114
|
+
|
|
115
|
+
{% if current_page_num < last_page_num %}
|
|
116
|
+
<a href="{{ blog_page_link(current_page_num + 1) }}">Next</a>
|
|
117
|
+
{% endif %}
|
|
118
|
+
</nav>
|
|
119
|
+
{% endif %}
|
|
120
|
+
```
|
|
121
|
+
|
|
122
|
+
### Filtering by Topic/Tag
|
|
123
|
+
```html
|
|
124
|
+
{% set topics = blog_topics(group.id, 250) %}
|
|
125
|
+
{% for topic in topics %}
|
|
126
|
+
<a href="{{ blog_tag_url(group.id, topic.slug) }}"
|
|
127
|
+
class="{% if topic.slug == tag %}active{% endif %}">
|
|
128
|
+
{{ topic.name }}
|
|
129
|
+
</a>
|
|
130
|
+
{% endfor %}
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
---
|
|
134
|
+
|
|
135
|
+
## 4. Related Posts & Widgets
|
|
136
|
+
|
|
137
|
+
### Related Posts
|
|
138
|
+
```html
|
|
139
|
+
{% related_blog_posts limit=3 %}
|
|
140
|
+
```
|
|
141
|
+
|
|
142
|
+
Or manual implementation:
|
|
143
|
+
```html
|
|
144
|
+
{% set recent = blog_recent_posts(group.id, 3) %}
|
|
145
|
+
{% for post in recent %}
|
|
146
|
+
{% if post.absolute_url != content.absolute_url %}
|
|
147
|
+
<a href="{{ post.absolute_url }}">{{ post.name }}</a>
|
|
148
|
+
{% endif %}
|
|
149
|
+
{% endfor %}
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
### Blog Social Sharing
|
|
153
|
+
```html
|
|
154
|
+
{% blog_social_sharing %}
|
|
155
|
+
```
|
|
156
|
+
|
|
157
|
+
### Blog Comments
|
|
158
|
+
```html
|
|
159
|
+
{% blog_comments %}
|
|
160
|
+
```
|
|
161
|
+
|
|
162
|
+
### Blog Subscribe (CTA)
|
|
163
|
+
```html
|
|
164
|
+
{% blog_subscribe "blog_subscribe" overrideable=True, label="Blog Subscribe" %}
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
---
|
|
168
|
+
|
|
169
|
+
## 5. Reading-Optimized Design Rules
|
|
170
|
+
|
|
171
|
+
### Typography
|
|
172
|
+
- Body text: 18-20px for long-form readability
|
|
173
|
+
- Line height: 1.6-1.8 for body copy
|
|
174
|
+
- Content width: 680-720px max for article body (optimal reading measure)
|
|
175
|
+
- Heading scale: use a clear hierarchy (h1 > h2 > h3)
|
|
176
|
+
|
|
177
|
+
### Spacing
|
|
178
|
+
- Generous paragraph spacing: 1.5em between paragraphs
|
|
179
|
+
- Section breaks: 3-4rem between major sections
|
|
180
|
+
- Whitespace is critical for readability
|
|
181
|
+
|
|
182
|
+
### Images
|
|
183
|
+
- Featured image: full-width within content area, 16:9 or 3:2 aspect ratio
|
|
184
|
+
- In-article images: max-width: 100% within the content column
|
|
185
|
+
- Always include alt text fields
|
|
186
|
+
- Use lazy loading: `loading="lazy"` on images below the fold
|
|
187
|
+
|
|
188
|
+
### Colors
|
|
189
|
+
- High contrast for body text (WCAG AA minimum)
|
|
190
|
+
- Subtle accent for links (distinguishable but not distracting)
|
|
191
|
+
- Light background for reading (dark text on light bg for articles)
|
|
192
|
+
|
|
193
|
+
---
|
|
194
|
+
|
|
195
|
+
## 6. Module Patterns for Blog
|
|
196
|
+
|
|
197
|
+
### Blog Post Modules (typical set)
|
|
198
|
+
1. **blog-post-header** — Title, featured image, author, date, tags
|
|
199
|
+
2. **blog-post-body** — The `{{ content.post_body }}` wrapper with reading-optimized styles
|
|
200
|
+
3. **author-bio** — Author card with avatar, name, bio, social links
|
|
201
|
+
4. **related-posts** — 3 related post cards
|
|
202
|
+
5. **blog-comments** — Comment section
|
|
203
|
+
6. **share-bar** — Social sharing buttons
|
|
204
|
+
|
|
205
|
+
### Blog Listing Modules (typical set)
|
|
206
|
+
1. **blog-hero** — Blog name, description, featured/pinned post
|
|
207
|
+
2. **topic-filter** — Category/tag navigation pills
|
|
208
|
+
3. **post-grid** — Card grid of posts with pagination
|
|
209
|
+
4. **newsletter-signup** — Email subscription form
|
|
210
|
+
5. **popular-posts** — Sidebar or section with most-read posts
|
|
211
|
+
|
|
212
|
+
### Module meta.json for Blog Post
|
|
213
|
+
```json
|
|
214
|
+
{
|
|
215
|
+
"host_template_types": ["BLOG_POST"],
|
|
216
|
+
"is_available_for_new_content": true
|
|
217
|
+
}
|
|
218
|
+
```
|
|
219
|
+
|
|
220
|
+
### Module meta.json for Blog Listing
|
|
221
|
+
```json
|
|
222
|
+
{
|
|
223
|
+
"host_template_types": ["BLOG_LISTING"],
|
|
224
|
+
"is_available_for_new_content": true
|
|
225
|
+
}
|
|
226
|
+
```
|
|
227
|
+
|
|
228
|
+
---
|
|
229
|
+
|
|
230
|
+
## 7. Common Mistakes
|
|
231
|
+
|
|
232
|
+
- Using `{{ content.body }}` instead of `{{ content.post_body }}` — post_body is the correct variable
|
|
233
|
+
- Forgetting pagination on listing templates — always include when more than 1 page
|
|
234
|
+
- Not using `|datetimeformat` on dates — raw dates are ugly
|
|
235
|
+
- Using `now()` — not valid HubL, use `local_dt` instead
|
|
236
|
+
- Hardcoding blog URLs — use `{{ content.absolute_url }}` and `{{ blog_page_link() }}`
|
|
237
|
+
- Missing `{% for content in contents %}` loop on listing pages — this is required
|
|
238
|
+
- Using page-style `{% dnd_area %}` in blog templates — blog templates use fixed module positions
|
|
239
|
+
- Not setting correct `host_template_types` — blog modules need `BLOG_POST` or `BLOG_LISTING`
|
|
240
|
+
|
|
241
|
+
---
|
|
242
|
+
|
|
243
|
+
## 8. SEO Essentials
|
|
244
|
+
|
|
245
|
+
Blog post templates should include:
|
|
246
|
+
- `<title>{{ content.name }} | {{ group.public_title }}</title>` (or via HubSpot settings)
|
|
247
|
+
- `<meta name="description" content="{{ content.meta_description }}" />`
|
|
248
|
+
- `<link rel="canonical" href="{{ content.absolute_url }}" />`
|
|
249
|
+
- Open Graph tags for social sharing
|
|
250
|
+
- Structured data (Article schema) where possible
|
|
251
|
+
- Proper heading hierarchy (single h1 for post title)
|