@rovela-ai/sdk 0.19.4 → 0.19.5

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.
Files changed (202) hide show
  1. package/docs/changelog/README.md +53 -0
  2. package/docs/changelog/epoch-01-chrome-consent.md +63 -0
  3. package/docs/changelog/epoch-02-platform-commerce.md +108 -0
  4. package/docs/changelog/epoch-03-i18n-files.md +72 -0
  5. package/docs/changelog/epoch-04-emails.md +65 -0
  6. package/docs/changelog/epoch-05-admin-experience.md +98 -0
  7. package/docs/changelog/epoch-06-mobile-integrity.md +72 -0
  8. package/docs/design/admin-ledger-visual-universe.html +1961 -0
  9. package/docs/design/admin-sidebar-and-band.html +542 -0
  10. package/package.json +3 -1
  11. package/templates/store-template/.claude/skills/add-section/SKILL.md +438 -0
  12. package/templates/store-template/.claude/skills/build-feature/SKILL.md +201 -0
  13. package/templates/store-template/.claude/skills/customize-theme/SKILL.md +167 -0
  14. package/templates/store-template/.claude/skills/debug-errors/SKILL.md +68 -0
  15. package/templates/store-template/.claude/skills/frontend-design/SKILL.md +176 -0
  16. package/templates/store-template/.claude/skills/generate-images/SKILL.md +115 -0
  17. package/templates/store-template/.claude/skills/manage-products/SKILL.md +187 -0
  18. package/templates/store-template/.claude/skills/override-sdk-component/SKILL.md +154 -0
  19. package/templates/store-template/.env.example +50 -0
  20. package/templates/store-template/.mcp.json +8 -0
  21. package/templates/store-template/.rovela/blueprint.example.json +190 -0
  22. package/templates/store-template/CLAUDE.md +14 -0
  23. package/templates/store-template/app/LayoutContent.tsx +106 -0
  24. package/templates/store-template/app/[...path]/page.tsx +79 -0
  25. package/templates/store-template/app/account/addresses/page.tsx +45 -0
  26. package/templates/store-template/app/account/layout.tsx +17 -0
  27. package/templates/store-template/app/account/orders/[id]/invoice/page.tsx +277 -0
  28. package/templates/store-template/app/account/orders/[id]/page.tsx +725 -0
  29. package/templates/store-template/app/account/orders/page.tsx +153 -0
  30. package/templates/store-template/app/account/page.tsx +184 -0
  31. package/templates/store-template/app/account/profile/page.tsx +434 -0
  32. package/templates/store-template/app/admin/(dashboard)/account/page.tsx +16 -0
  33. package/templates/store-template/app/admin/(dashboard)/analytics/events/page.tsx +14 -0
  34. package/templates/store-template/app/admin/(dashboard)/analytics/layout.tsx +48 -0
  35. package/templates/store-template/app/admin/(dashboard)/analytics/page.tsx +15 -0
  36. package/templates/store-template/app/admin/(dashboard)/analytics/visitors/page.tsx +14 -0
  37. package/templates/store-template/app/admin/(dashboard)/categories/[id]/page.tsx +38 -0
  38. package/templates/store-template/app/admin/(dashboard)/categories/new/page.tsx +35 -0
  39. package/templates/store-template/app/admin/(dashboard)/categories/page.tsx +223 -0
  40. package/templates/store-template/app/admin/(dashboard)/customers/[id]/page.tsx +26 -0
  41. package/templates/store-template/app/admin/(dashboard)/customers/page.tsx +33 -0
  42. package/templates/store-template/app/admin/(dashboard)/discounts/page.tsx +16 -0
  43. package/templates/store-template/app/admin/(dashboard)/emails/page.tsx +16 -0
  44. package/templates/store-template/app/admin/(dashboard)/files/page.tsx +16 -0
  45. package/templates/store-template/app/admin/(dashboard)/layout.tsx +44 -0
  46. package/templates/store-template/app/admin/(dashboard)/loading.tsx +88 -0
  47. package/templates/store-template/app/admin/(dashboard)/locations/page.tsx +16 -0
  48. package/templates/store-template/app/admin/(dashboard)/orders/[id]/page.tsx +66 -0
  49. package/templates/store-template/app/admin/(dashboard)/orders/page.tsx +26 -0
  50. package/templates/store-template/app/admin/(dashboard)/page.tsx +146 -0
  51. package/templates/store-template/app/admin/(dashboard)/payments/page.tsx +15 -0
  52. package/templates/store-template/app/admin/(dashboard)/products/[id]/page.tsx +38 -0
  53. package/templates/store-template/app/admin/(dashboard)/products/new/page.tsx +35 -0
  54. package/templates/store-template/app/admin/(dashboard)/products/page.tsx +31 -0
  55. package/templates/store-template/app/admin/(dashboard)/settings/page.tsx +46 -0
  56. package/templates/store-template/app/admin/(dashboard)/shipping/page.tsx +15 -0
  57. package/templates/store-template/app/admin/(dashboard)/tax/page.tsx +15 -0
  58. package/templates/store-template/app/admin/(dashboard)/users/[id]/page.tsx +114 -0
  59. package/templates/store-template/app/admin/(dashboard)/users/page.tsx +16 -0
  60. package/templates/store-template/app/admin/accept-invite/page.tsx +36 -0
  61. package/templates/store-template/app/admin/forgot-password/page.tsx +13 -0
  62. package/templates/store-template/app/admin/layout.tsx +47 -0
  63. package/templates/store-template/app/admin/login/page.tsx +528 -0
  64. package/templates/store-template/app/admin/reset-password/page.tsx +36 -0
  65. package/templates/store-template/app/api/account/addresses/[id]/route.ts +10 -0
  66. package/templates/store-template/app/api/account/addresses/route.ts +10 -0
  67. package/templates/store-template/app/api/account/change-password/route.ts +107 -0
  68. package/templates/store-template/app/api/account/orders/[id]/refund/route.ts +11 -0
  69. package/templates/store-template/app/api/account/orders/[id]/return/route.ts +14 -0
  70. package/templates/store-template/app/api/account/orders/[id]/route.ts +42 -0
  71. package/templates/store-template/app/api/account/orders/route.ts +29 -0
  72. package/templates/store-template/app/api/account/profile/route.ts +165 -0
  73. package/templates/store-template/app/api/admin/accept-invite/route.ts +11 -0
  74. package/templates/store-template/app/api/admin/analytics/events/route.ts +9 -0
  75. package/templates/store-template/app/api/admin/analytics/route.ts +10 -0
  76. package/templates/store-template/app/api/admin/analytics/visitors/route.ts +9 -0
  77. package/templates/store-template/app/api/admin/branding/favicon/route.ts +9 -0
  78. package/templates/store-template/app/api/admin/branding/logo/route.ts +9 -0
  79. package/templates/store-template/app/api/admin/categories/[id]/route.ts +9 -0
  80. package/templates/store-template/app/api/admin/categories/route.ts +9 -0
  81. package/templates/store-template/app/api/admin/check/route.ts +10 -0
  82. package/templates/store-template/app/api/admin/customer-groups/[id]/route.ts +10 -0
  83. package/templates/store-template/app/api/admin/customer-groups/route.ts +10 -0
  84. package/templates/store-template/app/api/admin/customers/[id]/addresses/[addressId]/route.ts +15 -0
  85. package/templates/store-template/app/api/admin/customers/[id]/addresses/route.ts +15 -0
  86. package/templates/store-template/app/api/admin/customers/[id]/route.ts +11 -0
  87. package/templates/store-template/app/api/admin/customers/bulk/route.ts +8 -0
  88. package/templates/store-template/app/api/admin/customers/route.ts +9 -0
  89. package/templates/store-template/app/api/admin/discounts/[id]/route.ts +11 -0
  90. package/templates/store-template/app/api/admin/discounts/route.ts +10 -0
  91. package/templates/store-template/app/api/admin/emails/preview/route.ts +4 -0
  92. package/templates/store-template/app/api/admin/emails/route.ts +5 -0
  93. package/templates/store-template/app/api/admin/emails/test/route.ts +4 -0
  94. package/templates/store-template/app/api/admin/files/route.ts +8 -0
  95. package/templates/store-template/app/api/admin/forgot-password/route.ts +7 -0
  96. package/templates/store-template/app/api/admin/linked-customer/route.ts +11 -0
  97. package/templates/store-template/app/api/admin/locations/[id]/route.ts +10 -0
  98. package/templates/store-template/app/api/admin/locations/route.ts +10 -0
  99. package/templates/store-template/app/api/admin/me/password/route.ts +13 -0
  100. package/templates/store-template/app/api/admin/me/route.ts +11 -0
  101. package/templates/store-template/app/api/admin/orders/[id]/refund/route.ts +7 -0
  102. package/templates/store-template/app/api/admin/orders/[id]/return/approve/route.ts +7 -0
  103. package/templates/store-template/app/api/admin/orders/[id]/return/reject/route.ts +7 -0
  104. package/templates/store-template/app/api/admin/orders/[id]/route.ts +9 -0
  105. package/templates/store-template/app/api/admin/orders/[id]/ship-with-shippo/route.ts +6 -0
  106. package/templates/store-template/app/api/admin/orders/[id]/shippo-rates/route.ts +6 -0
  107. package/templates/store-template/app/api/admin/orders/bulk/route.ts +8 -0
  108. package/templates/store-template/app/api/admin/orders/route.ts +9 -0
  109. package/templates/store-template/app/api/admin/payment-methods/[id]/route.ts +10 -0
  110. package/templates/store-template/app/api/admin/payment-methods/route.ts +10 -0
  111. package/templates/store-template/app/api/admin/products/[id]/route.ts +9 -0
  112. package/templates/store-template/app/api/admin/products/bulk/route.ts +9 -0
  113. package/templates/store-template/app/api/admin/products/route.ts +9 -0
  114. package/templates/store-template/app/api/admin/products/stats/route.ts +10 -0
  115. package/templates/store-template/app/api/admin/reset-password/route.ts +10 -0
  116. package/templates/store-template/app/api/admin/settings/route.ts +11 -0
  117. package/templates/store-template/app/api/admin/setup/route.ts +10 -0
  118. package/templates/store-template/app/api/admin/setup-guide/manual-mark/route.ts +13 -0
  119. package/templates/store-template/app/api/admin/setup-guide/route.ts +10 -0
  120. package/templates/store-template/app/api/admin/shipping/carriers/[id]/route.ts +9 -0
  121. package/templates/store-template/app/api/admin/shipping/carriers/route.ts +9 -0
  122. package/templates/store-template/app/api/admin/shipping/rates/[id]/route.ts +9 -0
  123. package/templates/store-template/app/api/admin/shipping/rates/route.ts +9 -0
  124. package/templates/store-template/app/api/admin/shipping/shippo/api-key/route.ts +1 -0
  125. package/templates/store-template/app/api/admin/shipping/shippo/validate/route.ts +1 -0
  126. package/templates/store-template/app/api/admin/shipping/zones/[id]/route.ts +9 -0
  127. package/templates/store-template/app/api/admin/shipping/zones/route.ts +9 -0
  128. package/templates/store-template/app/api/admin/stats/route.ts +9 -0
  129. package/templates/store-template/app/api/admin/stripe-status/route.ts +1 -0
  130. package/templates/store-template/app/api/admin/tax-zones/[id]/route.ts +7 -0
  131. package/templates/store-template/app/api/admin/tax-zones/route.ts +7 -0
  132. package/templates/store-template/app/api/admin/users/[id]/route.ts +14 -0
  133. package/templates/store-template/app/api/admin/users/route.ts +12 -0
  134. package/templates/store-template/app/api/admin-auth/[...nextauth]/route.ts +17 -0
  135. package/templates/store-template/app/api/analytics/track/route.ts +12 -0
  136. package/templates/store-template/app/api/auth/[...nextauth]/route.ts +19 -0
  137. package/templates/store-template/app/api/auth/forgot-password/route.ts +9 -0
  138. package/templates/store-template/app/api/auth/register/route.ts +9 -0
  139. package/templates/store-template/app/api/auth/resend-verification/route.ts +9 -0
  140. package/templates/store-template/app/api/auth/reset-password/route.ts +10 -0
  141. package/templates/store-template/app/api/auth/verify-email/route.ts +10 -0
  142. package/templates/store-template/app/api/categories/route.ts +10 -0
  143. package/templates/store-template/app/api/checkout/countries/route.ts +7 -0
  144. package/templates/store-template/app/api/checkout/discount/route.ts +9 -0
  145. package/templates/store-template/app/api/checkout/manual/route.ts +10 -0
  146. package/templates/store-template/app/api/checkout/payment-methods/route.ts +8 -0
  147. package/templates/store-template/app/api/checkout/pickup-locations/route.ts +8 -0
  148. package/templates/store-template/app/api/checkout/route.ts +10 -0
  149. package/templates/store-template/app/api/checkout/shipping/route.ts +21 -0
  150. package/templates/store-template/app/api/checkout/status/route.ts +10 -0
  151. package/templates/store-template/app/api/contact/route.ts +164 -0
  152. package/templates/store-template/app/api/media/presign/route.ts +7 -0
  153. package/templates/store-template/app/api/media/route.ts +7 -0
  154. package/templates/store-template/app/api/products/[slug]/route.ts +10 -0
  155. package/templates/store-template/app/api/products/route.ts +10 -0
  156. package/templates/store-template/app/api/store/settings/route.ts +12 -0
  157. package/templates/store-template/app/api/webhooks/stripe/route.ts +63 -0
  158. package/templates/store-template/app/auth/forgot-password/page.tsx +38 -0
  159. package/templates/store-template/app/auth/layout.tsx +17 -0
  160. package/templates/store-template/app/auth/reset-password/page.tsx +81 -0
  161. package/templates/store-template/app/auth/signin/page.tsx +62 -0
  162. package/templates/store-template/app/auth/signup/page.tsx +38 -0
  163. package/templates/store-template/app/auth/verify-email/page.tsx +185 -0
  164. package/templates/store-template/app/cart/page.tsx +137 -0
  165. package/templates/store-template/app/checkout/page.tsx +88 -0
  166. package/templates/store-template/app/checkout/success/page.tsx +50 -0
  167. package/templates/store-template/app/contact/layout.tsx +24 -0
  168. package/templates/store-template/app/contact/page.tsx +321 -0
  169. package/templates/store-template/app/faq/page.tsx +153 -0
  170. package/templates/store-template/app/globals.css +99 -0
  171. package/templates/store-template/app/layout.tsx +269 -0
  172. package/templates/store-template/app/not-found.tsx +35 -0
  173. package/templates/store-template/app/page.tsx +23 -0
  174. package/templates/store-template/app/privacy/page.tsx +281 -0
  175. package/templates/store-template/app/products/[slug]/ProductDetailClient.tsx +179 -0
  176. package/templates/store-template/app/products/[slug]/page.tsx +149 -0
  177. package/templates/store-template/app/products/layout.tsx +26 -0
  178. package/templates/store-template/app/products/page.tsx +102 -0
  179. package/templates/store-template/app/robots.ts +25 -0
  180. package/templates/store-template/app/sitemap.ts +76 -0
  181. package/templates/store-template/app/terms/page.tsx +313 -0
  182. package/templates/store-template/components/PathSyncBridge.tsx +61 -0
  183. package/templates/store-template/components/Providers.tsx +37 -0
  184. package/templates/store-template/components/layout/Footer.tsx +150 -0
  185. package/templates/store-template/components/layout/Header.tsx +162 -0
  186. package/templates/store-template/components/sections/.gitkeep +7 -0
  187. package/templates/store-template/components/sections/CTA.tsx +51 -0
  188. package/templates/store-template/components/sections/Features.tsx +91 -0
  189. package/templates/store-template/components/sections/Hero.tsx +85 -0
  190. package/templates/store-template/eslint.config.mjs +18 -0
  191. package/templates/store-template/lib/store-config.ts +77 -0
  192. package/templates/store-template/lib/store-policy.ts +68 -0
  193. package/templates/store-template/lib/utils.ts +21 -0
  194. package/templates/store-template/next-env.d.ts +6 -0
  195. package/templates/store-template/next.config.js +105 -0
  196. package/templates/store-template/package.json +32 -0
  197. package/templates/store-template/postcss.config.js +6 -0
  198. package/templates/store-template/proxy.ts +150 -0
  199. package/templates/store-template/public/rovela-logo.png +0 -0
  200. package/templates/store-template/tailwind.config.ts +74 -0
  201. package/templates/store-template/tsconfig.json +41 -0
  202. package/templates/store-template/types/next-auth.d.ts +32 -0
@@ -0,0 +1,167 @@
1
+ ---
2
+ name: customize-theme
3
+ description: Use when the user asks to change colors, fonts, spacing, layout, shadows, borders, or any visual styling. Covers CSS variables, globals.css, tailwind.config.ts, and theme tokens.
4
+ ---
5
+
6
+ # Theme Customization
7
+
8
+ > **Scope: STOREFRONT only.** Everything in this skill (these tokens, `globals.css` variables, Tailwind classes like `text-muted-foreground`/`bg-card`) styles the customer-facing store. The `/admin` dashboard has its OWN design system — `hsl(var(--admin-*))` tokens + `admin-*` classes, governed by CLAUDE.md §7.6 — and storefront tokens must never be used there.
9
+
10
+ ## Key Files
11
+
12
+ - `/app/app/globals.css` — CSS variables (`:root` and `.dark` blocks)
13
+ - `/app/tailwind.config.ts` — Maps CSS variables to Tailwind classes
14
+ - `/app/.rovela/blueprint.json` — Original theme specification
15
+
16
+ ## CSS Variable System
17
+
18
+ The theme uses HSL CSS variables. All colors are defined as `H S% L%` values (no `hsl()` wrapper — Tailwind adds it).
19
+
20
+ ### Color Variables in globals.css
21
+
22
+ ```css
23
+ :root {
24
+ --background: 0 0% 100%;
25
+ --foreground: 0 0% 3.9%;
26
+ --primary: 0 0% 9%;
27
+ --primary-foreground: 0 0% 98%;
28
+ --secondary: 0 0% 96.1%;
29
+ --secondary-foreground: 0 0% 9%;
30
+ --muted: 0 0% 96.1%;
31
+ --muted-foreground: 0 0% 45.1%;
32
+ --accent: 0 0% 96.1%;
33
+ --accent-foreground: 0 0% 9%;
34
+ --destructive: 0 84.2% 60.2%;
35
+ --destructive-foreground: 0 0% 98%;
36
+ --border: 0 0% 89.8%;
37
+ --input: 0 0% 89.8%;
38
+ --ring: 0 0% 3.9%;
39
+ --card: 0 0% 100%;
40
+ --card-foreground: 0 0% 3.9%;
41
+ --popover: 0 0% 100%;
42
+ --popover-foreground: 0 0% 3.9%;
43
+ --radius: 0.5rem;
44
+ }
45
+ ```
46
+
47
+ ### Usage in Components
48
+
49
+ ```tsx
50
+ // Correct — use semantic tokens
51
+ <div className="bg-background text-foreground">
52
+ <button className="bg-primary text-primary-foreground">
53
+ <p className="text-muted-foreground">
54
+ <div className="border border-border rounded-lg">
55
+
56
+ // Wrong — hardcoded colors bypass theming
57
+ <div className="bg-white text-black">
58
+ ```
59
+
60
+ ## How to Change Colors
61
+
62
+ 1. Read `/app/app/globals.css` to see current values
63
+ 2. Modify the HSL values in `:root` (and `.dark` if dark mode exists)
64
+ 3. Run error check after saving
65
+
66
+ ### Example: Change primary to blue
67
+
68
+ ```css
69
+ /* Before */
70
+ --primary: 0 0% 9%;
71
+ /* After */
72
+ --primary: 221 83% 53%;
73
+ ```
74
+
75
+ ## How to Change Fonts
76
+
77
+ 1. Fonts are loaded in `/app/app/layout.tsx` via `next/font/google`
78
+ 2. CSS variables `--font-heading` and `--font-body` are set in globals.css
79
+ 3. Update both the import AND the CSS variable
80
+
81
+ ### Example: Change heading font
82
+
83
+ ```tsx
84
+ // In layout.tsx
85
+ import { Playfair_Display } from 'next/font/google';
86
+ const heading = Playfair_Display({ subsets: ['latin'], variable: '--font-heading' });
87
+ ```
88
+
89
+ ## How to Change Spacing/Radius
90
+
91
+ Modify `--radius` in globals.css:
92
+ - `0.25rem` — sharp/minimal
93
+ - `0.5rem` — balanced (default)
94
+ - `0.75rem` — rounded
95
+ - `1rem` — very rounded
96
+
97
+ ## Responsive Design Rules
98
+
99
+ - Mobile-first: base styles for 320px, then `sm:`, `md:`, `lg:` breakpoints
100
+ - Touch targets: minimum 44x44px for buttons and links
101
+ - Body text: minimum 16px (prevents iOS zoom)
102
+ - Use `flex-wrap` and responsive grids, never horizontal scroll
103
+
104
+ ## Brand-Expression Tokens — the polished feel layer
105
+
106
+ Beyond the shadcn color variables, every store should ship a fixed scaffold of brand-expression CSS variables in `globals.css` `:root`. These are the named primitives that separate a generic shadcn theme from a brand-expressive one. Same names every store, values per-brand.
107
+
108
+ ```css
109
+ :root {
110
+ /* shadcn color base (--primary, --background, etc.) above */
111
+
112
+ --primary-glow: [lighter HSL of primary, typically primary-300 from the derived scale];
113
+ --gradient-primary: linear-gradient(135deg, hsl(var(--primary)), hsl(var(--primary-glow)));
114
+ --gradient-subtle: linear-gradient(180deg, hsl(var(--background)), hsl(var(--muted)));
115
+ --shadow-elegant: 0 10px 30px -10px hsl(var(--primary) / 0.3);
116
+ --shadow-glow: 0 0 40px hsl(var(--primary-glow) / 0.4);
117
+ --transition-smooth: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
118
+ }
119
+ ```
120
+
121
+ ### When the merchant asks for a polished feel
122
+
123
+ If the merchant asks to "make the hero feel more premium" / "add a glow to the CTAs" / "make this feel more designed" — reach for these tokens FIRST before inventing new ones.
124
+
125
+ Usage examples:
126
+
127
+ ```tsx
128
+ // Hero CTA — brand-tinted shadow, smooth transition
129
+ <Button
130
+ style={{ background: 'var(--gradient-primary)', boxShadow: 'var(--shadow-elegant)', transition: 'var(--transition-smooth)' }}
131
+ className="hover:[box-shadow:var(--shadow-glow)]"
132
+ >
133
+ Shop now
134
+ </Button>
135
+
136
+ // Section with layered subtle gradient background
137
+ <section style={{ background: 'var(--gradient-subtle)' }}>
138
+ ...
139
+ </section>
140
+
141
+ // Card with brand-glow halo
142
+ <Card className="shadow-[var(--shadow-glow)] transition-[var(--transition-smooth)]">
143
+ ...
144
+ </Card>
145
+ ```
146
+
147
+ ### Iteration rule
148
+
149
+ If a section feels generic mid-build, revisit `globals.css` + `tailwind.config.ts` to deepen these tokens (e.g. add `--gradient-radial-hero` for a specific section). NEVER change the merchant-frozen primary / secondary / heading / body — those are pinned by the platform per the Design Source of Truth routing in `/app/CLAUDE.md` §4. "Deepening" means adding expression tokens, not swapping brand identity.
150
+
151
+ ## Editorial Accent — off-palette color, one specific section
152
+
153
+ If `theme_essentials.editorialAccent` is set in the brief, that hex is used at ONE specific location named in `editorialAccent.usage`. It is NOT bled across the page — it's an editorial moment, not a brand color. Examples:
154
+ - Warm coffee brand (brown + cream primaries) + sage editorial accent on the pull-quote ribbon
155
+ - Minimalist tech (black + white primaries) + warm amber editorial accent on the newsletter strip
156
+
157
+ When the merchant asks to "add a pop color" or "make the pull-quote section feel different," check if `editorialAccent` is set first — use it. If not set, propose a new one consistent with the chromatic story and update `globals.css` with a comment noting the single-use intent.
158
+
159
+ ## Photography Style Lock — keep imagery cohesive
160
+
161
+ If `theme_essentials.photographyStyleLock` is set (5 axes: camera, lighting, composition, tone, subject), ALL image generation prompts MUST reuse those 5 axes verbatim. Only the subject-specific details vary per image; the rest stays constant.
162
+
163
+ When merchant asks "regenerate the hero photo" — keep the same STYLE LOCK, change only the subject specifics.
164
+
165
+ When merchant asks "make the photos feel more Aesop" — apply the `aesop-coded` PHOTOGRAPHY_STYLE_TEMPLATE (Hasselblad-coded medium format 80mm prime, north-window natural light 4500K, three-quarter view with generous negative space, warm cream/sepia tone, raw materials no people) and store the 5 axes in the brief's style lock for future iterations.
166
+
167
+ Other named templates: `glossier-coded`, `brutalist-raw`, `editorial-fashion`, `minimalist-product`, `studio-soft`, `documentary-natural`, `bright-saturated-pop`.
@@ -0,0 +1,68 @@
1
+ ---
2
+ name: debug-errors
3
+ description: Use when something is broken, not working, showing errors, or the user reports a bug. Covers the get_errors, read, fix, verify debugging loop.
4
+ ---
5
+
6
+ # Debug & Fix Errors
7
+
8
+ ## Primary Tool
9
+
10
+ Use `get_errors` via next-devtools MCP for instant error checking (under 1 second).
11
+
12
+ **Never** run `npm run build` for error checking — it takes 30-60 seconds. Use `get_errors` instead.
13
+
14
+ ## Debugging Workflow
15
+
16
+ 1. **Check errors**: Run `get_errors` to see current TypeScript/compilation errors
17
+ 2. **Read the file**: Read the relevant file(s) to understand the current implementation
18
+ 3. **Identify root cause**: Look for the actual source of the issue, not just symptoms
19
+ 4. **Make minimal fix**: Targeted changes only — avoid modifying unrelated code
20
+ 5. **Verify fix**: Run `get_errors` again to confirm zero errors
21
+ 6. **Check regressions**: Ensure related functionality still works
22
+
23
+ ## Common Error Patterns
24
+
25
+ ### Missing 'use client' Directive
26
+ **Symptom**: "useState is not defined" or "onClick handler in server component"
27
+ **Fix**: Add `'use client'` at the top of components using hooks or event handlers
28
+
29
+ ### Import Resolution Errors
30
+ **Symptom**: "Module not found" or "Cannot find module"
31
+ **Fix**: Check SDK import paths against CLAUDE.md. Common mistake: wrong subpath.
32
+ ```tsx
33
+ // Wrong
34
+ import { ProductCard } from '@rovela-ai/sdk'
35
+ // Correct
36
+ import { ProductCard } from '@rovela-ai/sdk/products'
37
+ ```
38
+
39
+ ### Type Errors
40
+ **Symptom**: "Type X is not assignable to type Y"
41
+ **Fix**: Define proper interfaces for props. Check component prop types.
42
+ ```tsx
43
+ interface Props {
44
+ title: string;
45
+ onClick: () => void;
46
+ }
47
+ ```
48
+
49
+ ### Tailwind Class Errors
50
+ **Symptom**: Styles not applying or build warnings
51
+ **Fix**: Common mistake — `border-border` is invalid. Use `border` for border color with `border-border` for the utility.
52
+
53
+ ### SDK Hook Errors
54
+ **Symptom**: Hook errors mentioning SDK files
55
+ **Fix**: The issue is likely in YOUR code, not the SDK. SDK internals are pre-validated. Focus debugging on files in `/app`.
56
+
57
+ ## Stale Cache Issues
58
+
59
+ If errors persist after fixing, clear the build cache:
60
+ ```
61
+ nextjs_call with port="3000", toolName="clear_cache"
62
+ ```
63
+
64
+ Then run `get_errors` again.
65
+
66
+ ## When to Use npm run build
67
+
68
+ Only as **final verification** after all `get_errors` checks pass. Never use it as the primary debugging tool.
@@ -0,0 +1,176 @@
1
+ ---
2
+ name: frontend-design
3
+ description: Create distinctive, production-grade frontend interfaces with high design quality. Use this skill when the user asks to build web components, pages, or applications. Generates creative, polished code that avoids generic AI aesthetics.
4
+ ---
5
+
6
+ > **Languages**: on multilingual stores (`store_settings.enabled_locales` has
7
+ > more than one entry), every user-visible string must be authored in ALL
8
+ > enabled languages via the store dictionary (CLAUDE.md §5.5). Internal links
9
+ > always use `LocaleLink` from `@rovela-ai/sdk/core`.
10
+
11
+ This skill guides creation of distinctive, production-grade frontend interfaces that avoid generic "AI slop" aesthetics. Implement real working code with exceptional attention to aesthetic details and creative choices.
12
+
13
+ The user provides frontend requirements: a component, page, application, or interface to build. They may include context about the purpose, audience, or technical constraints.
14
+
15
+ ## Design Thinking
16
+
17
+ Before coding, understand the context and commit to a BOLD aesthetic direction:
18
+ - **Purpose**: What problem does this interface solve? Who uses it?
19
+ - **Tone**: Pick an extreme: brutally minimal, maximalist chaos, retro-futuristic, organic/natural, luxury/refined, playful/toy-like, editorial/magazine, brutalist/raw, art deco/geometric, soft/pastel, industrial/utilitarian, etc. There are so many flavors to choose from. Use these for inspiration but design one that is true to the aesthetic direction.
20
+ - **Constraints**: Technical requirements (framework, performance, accessibility).
21
+ - **Differentiation**: What makes this UNFORGETTABLE? What's the one thing someone will remember?
22
+
23
+ **CRITICAL**: Choose a clear conceptual direction and execute it with precision. Bold maximalism and refined minimalism both work - the key is intentionality, not intensity.
24
+
25
+ Then implement working code (HTML/CSS/JS, React, Vue, etc.) that is:
26
+ - Production-grade and functional
27
+ - Visually striking and memorable
28
+ - Cohesive with a clear aesthetic point-of-view
29
+ - Meticulously refined in every detail
30
+
31
+ ## Frontend Aesthetics Guidelines
32
+
33
+ Focus on:
34
+ - **Typography**: Choose fonts that are beautiful, unique, and interesting. Avoid generic fonts like Arial and Inter; opt instead for distinctive choices that elevate the frontend's aesthetics; unexpected, characterful font choices. Pair a distinctive display font with a refined body font.
35
+ - **Color & Theme**: Commit to a cohesive aesthetic. Use CSS variables for consistency. Dominant colors with sharp accents outperform timid, evenly-distributed palettes.
36
+ - **Motion**: Use animations for effects and micro-interactions. Prioritize CSS-only solutions for HTML. Use Motion library for React when available. Focus on high-impact moments: one well-orchestrated page load with staggered reveals (animation-delay) creates more delight than scattered micro-interactions. Use scroll-triggering and hover states that surprise.
37
+ - **Spatial Composition**: Unexpected layouts. Asymmetry. Overlap. Diagonal flow. Grid-breaking elements. Generous negative space OR controlled density.
38
+ - **Backgrounds & Visual Details**: Create atmosphere and depth rather than defaulting to solid colors. Add contextual effects and textures that match the overall aesthetic. Apply creative forms like gradient meshes, noise textures, geometric patterns, layered transparencies, dramatic shadows, decorative borders, custom cursors, and grain overlays.
39
+
40
+ NEVER use generic AI-generated aesthetics like overused font families (Inter, Roboto, Arial, system fonts), cliched color schemes (particularly purple gradients on white backgrounds), predictable layouts and component patterns, and cookie-cutter design that lacks context-specific character.
41
+
42
+ Interpret creatively and make unexpected choices that feel genuinely designed for the context. No design should be the same. Vary between light and dark themes, different fonts, different aesthetics. NEVER converge on common choices (Space Grotesk, for example) across generations.
43
+
44
+ **IMPORTANT**: Match implementation complexity to the aesthetic vision. Maximalist designs need elaborate code with extensive animations and effects. Minimalist or refined designs need restraint, precision, and careful attention to spacing, typography, and subtle details. Elegance comes from executing the vision well.
45
+
46
+ Remember: Claude is capable of extraordinary creative work. Don't hold back, show what can truly be created when thinking outside the box and committing fully to a distinctive vision.
47
+
48
+ ## Content Voice — short, specific, sounds-human
49
+
50
+ The merchant will replace most copy with their own product details. Your job is short, specific placeholder content that demonstrates voice and structure — not paragraphs the merchant has to delete before they can think. This applies to BOTH initial generation AND chat-edit rewrites.
51
+
52
+ **Length caps (hard, per section):**
53
+ - Hero: headline ≤ 8 words. Subhead ≤ 14 words. NO additional paragraph below the subhead.
54
+ - Features: 3–4 cards. Each card: title ≤ 4 words + description ≤ 16 words. Total feature prose ≤ 80 words.
55
+ - Trust / About: 2–3 sentences, ≤ 80 words total. No three-paragraph "Our story" essay. No "Founded in..." preamble unless the merchant actually said so.
56
+ - CTA: headline ≤ 8 words. Subhead ≤ 12 words. Button label ≤ 3 words.
57
+ - FAQ (when included): question ≤ 12 words, answer ≤ 30 words, max 5 entries.
58
+
59
+ **Banned vocabulary (AI tells — do NOT use in storefront copy):**
60
+ elevate, enhance, delve, embrace, embark, leverage, unlock, navigate, harness, streamline, optimize, seamless, robust, transform, empower, discover, unveil, journey, treasure trove, game-changer, world-class, cutting-edge, next-generation, premium, modern, clean, sophisticated, elevated.
61
+
62
+ **Banned structures:**
63
+ - "Not just X — it's Y" / "It's not about X, it's about Y" (AI negation cliché).
64
+ - "In today's world..." / "In the digital age..." (throat-clearing preambles).
65
+ - Em-dash overuse: max 1 em-dash per section.
66
+ - Generic adjective stacks ("premium, modern, clean") — guaranteed AI tell.
67
+
68
+ **Write like a human who knows the product:**
69
+ - Specifics over abstractions: "hand-stitched Italian calfskin" beats "premium leather."
70
+ - Real numbers, names, places: "ships in 4 days from Brooklyn" beats "fast shipping."
71
+ - Verbs over adjectives: "roasted in small batches" beats "high-quality coffee."
72
+ - Sensory details for taste/feel/touch: "tastes of charred sugar and tobacco" beats "rich flavor."
73
+ - Plain English: "for people who" beats "designed for the discerning individual who."
74
+
75
+ Source the specifics from the merchant's business_description in CLAUDE.md §2 first. If the merchant wrote one good concrete sentence, lift that language verbatim or close. The brief's `brand_essentials.voice.vocabulary.preferred` list is the safe phrase pool; `vocabulary.avoid` is the additional per-merchant banned list on top of the universal one above.
76
+
77
+ **Chat-edit application**: when the merchant asks you to rewrite a section ("make the hero punchier", "shorten this", "less AI-sounding"), the same caps apply. Going OVER cap is a regression — never lengthen unless the merchant explicitly asked for more copy.
78
+
79
+ ## Aesthetic Ritual — commit before you code
80
+
81
+ Before writing any major redesign or new section, pause and write a 4-bullet commitment in your narration. This forces concrete decisions and prevents drift to safe defaults. This applies to BOTH initial generation AND chat-edit redesigns ("make the hero more premium", "redesign this section to feel editorial").
82
+
83
+ 1. **What this brand evokes** — one sentence. Concrete, sensory, specific. NOT "premium / modern / clean."
84
+ 2. **Design inspirations** — one sentence. If the merchant referenced specific designs or supplied screenshots, those ARE your inspirations; name them. Otherwise name 1–2 specific influences (an aesthetic era, a specific brand category, a material world).
85
+ 3. **Palette commitment** — list the primary + secondary + accent hex codes you're committing to. If editing, confirm the existing palette OR propose specific replacements with reasoning.
86
+ 4. **Motion commitment** — list the 2–3 specific motion moments you'll implement (entrance, hover, signature). Cite ms timings.
87
+
88
+ ## Component Customization Pattern — variants, not inline overrides
89
+
90
+ When customizing buttons / cards / pills / badges from shadcn or the SDK, CREATE NEW cva variants using semantic tokens. Variant definitions live in the component file's cva() block.
91
+
92
+ ```tsx
93
+ // ✅ CORRECT — new variant lives in the component
94
+ const buttonVariants = cva("...", {
95
+ variants: {
96
+ variant: {
97
+ default: "bg-primary text-primary-foreground hover:bg-primary/90",
98
+ hero: "bg-gradient-primary text-primary-foreground shadow-elegant hover:shadow-glow transition-smooth",
99
+ editorial: "bg-transparent border border-foreground/20 text-foreground hover:bg-foreground hover:text-background",
100
+ },
101
+ },
102
+ });
103
+
104
+ // At the call site:
105
+ <Button variant="hero">Shop now</Button>
106
+ ```
107
+
108
+ ```tsx
109
+ // ❌ WRONG — inline overrides bypass the design system
110
+ <Button className="bg-primary/90 hover:bg-primary text-white px-6 shadow-xl">
111
+ Shop now
112
+ </Button>
113
+ ```
114
+
115
+ Inline raw-class overrides at call sites rot. Variants compose, stay coherent across chat-edits, and let the design system evolve as a single unit.
116
+
117
+ ## Contrast Trap — real bug-class warning
118
+
119
+ When alternating section backgrounds (background → muted → card → background), verify text contrast in BOTH light AND dark modes. White text on bg-muted in light-mode often disappears; dark text on bg-card in dark-mode often does too. Sanity-check every section-pair you ship — this is the single most common visual bug class.
120
+
121
+ ## Layout Vocabulary — pattern catalog for chat-edits
122
+
123
+ When the merchant asks to change a section's layout (e.g. "make the hero more editorial" / "switch the products to a bento grid" / "this footer feels generic, can it be more like Aesop's"), look up the named pattern from one of these catalogs and apply the matching skeleton.
124
+
125
+ **HERO PATTERNS** (9):
126
+ - `split` — text + image side-by-side, equal weight
127
+ - `center` — text-only, vertically stacked, max-w-3xl
128
+ - `bg-image` — full-bleed photographic bg + text overlay
129
+ - `immersive` — viewport-height with full-bleed bg; cinematic
130
+ - `editorial` — asymmetric magazine, oversized type on non-center column, image floats
131
+ - `bento` — compartmentalized grid hero (4-6 tiles, one large + smaller + text card)
132
+ - `type-first` — kinetic huge typography dominates; size jump 5×+
133
+ - `parallax-bg` — full-bleed with CSS 3D parallax (translateZ + perspective)
134
+ - `video-bg` — variant of immersive with autoPlay/muted/loop/playsInline video
135
+
136
+ **SECTION SEPARATION** (6):
137
+ - `soft` — subtle bg-color shifts, no borders
138
+ - `clean` — distinct stripes with whitespace/thin borders
139
+ - `cards` — every section wrapped in card chrome
140
+ - `editorial-interleave` — non-commerce section every 2 commerce (pull-quote / craft vignette / founder photo)
141
+ - `scroll-snap` — full-page snap sections (scroll-snap-type: y mandatory)
142
+ - `asymmetric-alt` — alternate left → right → full-bleed → center
143
+
144
+ **PRODUCT SHOWCASE** (6):
145
+ - `grid` — uniform 3-col responsive grid
146
+ - `list` — vertical full-width rows
147
+ - `lookbook` — asymmetric, one hero + smaller tiles
148
+ - `editorial-2col` — magazine spread, product + prose alternating
149
+ - `horizontal-snap` — horizontal scroll-snap carousel
150
+ - `bento-grid` — hero product + smaller tiles + ONE text/copy card peer
151
+
152
+ **HEADER PATTERNS** (5):
153
+ - `transparent-to-solid` — transparent on load, solidifies on scroll
154
+ - `sticky-condensed` — shrinks + condenses after 80px scroll
155
+ - `mega-menu` — compact top + rich hover mega-menus (Stripe-style)
156
+ - `editorial-minimal` — centered logo, sparse nav, no utility row (Aesop)
157
+ - `utility-first` — cart + search prominent, nav secondary
158
+
159
+ **FOOTER PATTERNS** (4):
160
+ - `editorial-massive` — multi-column newsletter + values + craft-story + sitemap
161
+ - `minimal-utility` — logo + 5 links + copyright, one row
162
+ - `newsletter-first` — newsletter dominates, sitemap secondary
163
+ - `brand-narrative` — long-form brand-story prose body (Aesop)
164
+
165
+ **TYPOGRAPHY MODES** (5):
166
+ - `decorative` — standard hierarchy, conservative
167
+ - `kinetic` — aggressive jumps 5×+, weight extremes (300/900), animated stagger
168
+ - `editorial-display` — refined oversized display (200 or 700), generous tracking, slow fade
169
+ - `marquee` — scrolling type bands as brand statement
170
+ - `variable-axis` — variable fonts with weight/width transitions tied to scroll
171
+
172
+ **SIGNATURE MOVES** (12 named): slow-page-fade, cursor-halo, scroll-progress-bar, parallax-vertical-mark, letter-stagger-reveal, color-shift-on-scroll, sticky-cta-reveal, marquee-headline, ambient-grain, intersection-reveal, custom-cursor, page-load-stagger. Pick ONE per store; CSS-only when possible; respect `prefers-reduced-motion`.
173
+
174
+ **SIGNATURE COMPONENT CATEGORIES** (7): decorative-divider, custom-product-card, themed-indicator, narrative-interlude, signature-button, decorative-frame, parallax-mark.
175
+
176
+ When CLAUDE.md §4's Design Source of Truth routing table names a pattern, that pattern is FROZEN — do not propose alternatives unless the merchant explicitly asks to change it.
@@ -0,0 +1,115 @@
1
+ ---
2
+ name: generate-images
3
+ description: Use when generating visual assets (hero, product photos, feature graphics, section backgrounds, testimonial headshots) for a store. Covers the mcp__r2__generate_image tool, aspect ratios per section, prompt writing, filename conventions, and the gradient fallback. Triggers on any mention of image generation, hero image, product photos, or missing visuals.
4
+ ---
5
+
6
+ # Generate Images
7
+
8
+ ## Rule zero
9
+
10
+ **Call `mcp__r2__generate_image` directly from this skill's execution context, in sequence.** Directly-spawned `Agent`/`Task` subagents outside of skill context do not reliably inherit MCP tool access (github anthropics/claude-code #7296, #38920) — delegation outside this skill means silent failure and missing images. Inside this skill, calls you make execute in a context that has MCP access, so just call the tool directly.
11
+
12
+ ## When to generate
13
+
14
+ | Surface | Count (typical full homepage) |
15
+ |---|---|
16
+ | **Hero** — background or foreground image | 1 |
17
+ | **Features** — one image per feature card | 1–3 of the most visual cards |
18
+ | **Products** — photo per seed product if no image provided | 1 per product |
19
+ | **Testimonials** — headshots (optional, brand-dependent) | 0–1 |
20
+ | **Trust / other sections** | Only if the blueprint requests imagery |
21
+
22
+ Total: around 5–6 `mcp__r2__generate_image` calls for a typical full homepage generation. Sequential. ~30–45 seconds total.
23
+
24
+ ## Prompt format
25
+
26
+ 40–75 words. Anchor on the Visual Creative Brief in CLAUDE.md §4 (personality, color philosophy, imagery direction). Include photography terminology: lighting, angle, subject, mood, color palette, lens, texture.
27
+
28
+ Example (Cofme — editorial Parisian atelier):
29
+
30
+ > Editorial Parisian atelier, unmade silk pillows in dusty rose and cream, morning light streaming through tall windows, warm bronze accents, shallow depth of field, soft grainy texture, 85mm portrait lens, 4:3 aspect ratio.
31
+
32
+ Example (Tech / SaaS store):
33
+
34
+ > Minimal product flat-lay on matte charcoal surface, single cyan accent light from upper-left, subtle blue gradient background, precise geometric composition, studio lighting with soft shadows, 50mm macro lens, 1:1 square aspect ratio.
35
+
36
+ ## Aspect ratios by context
37
+
38
+ | Context | Aspect | Notes |
39
+ |---|---|---|
40
+ | Hero — full-screen layout | 16:9 | Landscape, widescreen |
41
+ | Hero — split layout | 3:4 | Portrait side panel |
42
+ | Feature card | 4:3 | Balanced landscape |
43
+ | Product photo | 1:1 | Square grid |
44
+ | Testimonial portrait | 1:1 | Square headshot |
45
+ | Section background | 16:9 | Wide background |
46
+
47
+ Pass the aspect ratio both in the prompt text AND as the `aspect_ratio` parameter to `mcp__r2__generate_image`.
48
+
49
+ ## Filename convention
50
+
51
+ `{section}-{index}-{slug}.webp` — for example `hero-1-atelier.webp`, `feature-2-bespoke-pillows.webp`, `product-3-silk-cream.webp`. Human-readable and visible in R2 storage when debugging.
52
+
53
+ ## Fallback on error
54
+
55
+ If `mcp__r2__generate_image` returns an error (Gemini rate limit, safety block, timeout), use a CSS gradient with the brand primary colors from the Visual Creative Brief. **Never** hardcode external URLs (Unsplash, placeholder.com, picsum.photos). **Never** leave a broken `<img>` tag.
56
+
57
+ ```tsx
58
+ // Fallback pattern — no broken images, no external URLs
59
+ <div className="bg-gradient-to-br from-primary/20 via-primary/10 to-transparent h-full w-full" />
60
+ ```
61
+
62
+ ## Canonical call sequence for a full homepage
63
+
64
+ **Preferred — single batched call** (`mcp__r2__generate_images`, plural):
65
+
66
+ ```
67
+ mcp__r2__generate_images({
68
+ images: [
69
+ { prompt: "...", filename: "hero-1-{slug}", aspect_ratio: "16:9" },
70
+ { prompt: "...", filename: "feature-1-{slug}", aspect_ratio: "4:3" },
71
+ { prompt: "...", filename: "feature-2-{slug}", aspect_ratio: "4:3" },
72
+ { prompt: "...", filename: "feature-3-{slug}", aspect_ratio: "4:3" },
73
+ { prompt: "...", filename: "about-1-{slug}", aspect_ratio: "4:3" },
74
+ { prompt: "...", filename: "product-1-{slug}", aspect_ratio: "1:1" },
75
+ { prompt: "...", filename: "product-2-{slug}", aspect_ratio: "1:1" },
76
+ { prompt: "...", filename: "product-3-{slug}", aspect_ratio: "1:1" },
77
+ ]
78
+ })
79
+ ```
80
+
81
+ Returns `{ images: [{ success, url?, key?, size?, error? }, ...] }` preserving input order. The server fans out at concurrency 4 → typical 8-image batch lands in ~12s wall-clock vs ~48s sequential. **Use this for the initial homepage build whenever you have 3+ images planned up front.** Max 12 entries per call.
82
+
83
+ **Per-entry fallback contract is unchanged** — if `images[i].success === false`, use a CSS gradient for that one image only and continue with the rest. Don't abort the page over one Gemini error.
84
+
85
+ **Singular `mcp__r2__generate_image` is still preferred for:**
86
+
87
+ - Edit-mode iteration (merchant asks "regenerate just the hero" — one image at a time)
88
+ - Workflows where the prompt for image N depends on what image N-1 produced
89
+ - <3 images total
90
+
91
+ **Sequential singular fallback** (if `generate_images` ever returns an error for the whole call):
92
+
93
+ ```
94
+ 1. mcp__r2__generate_image — hero (16:9 or 3:4 depending on layout)
95
+ 2. mcp__r2__generate_image — feature 1 (4:3)
96
+ 3. mcp__r2__generate_image — feature 2 (4:3)
97
+ ...
98
+ ```
99
+
100
+ Call them one after the other in THIS session. Not via Agent/Task. ~6s each, ~30-45s total for a homepage — slower than the plural batch but guaranteed-compatible with older sandbox images.
101
+
102
+ ## Common anti-patterns
103
+
104
+ - ❌ `Agent(prompt="Generate 5 images via mcp__r2__generate_image")` outside this skill → subagent won't have MCP access, silent failure
105
+ - ❌ "I'll use Task in parallel to generate all images outside the skill" → don't; stay inside this skill's execution
106
+ - ❌ Using singular `generate_image` 8 times in a row for a homepage build → use the plural tool instead, saves ~30s of wall-clock
107
+ - ❌ Using plural `generate_images` for a single-image edit-mode iteration → wasteful, use singular
108
+ - ❌ Treating `generate_images` whole-call failure differently from per-image failure → check `images[i].success` per entry, not the call's outer success
109
+ - ❌ Using `imageUrl` from blueprint without checking if it's null/empty
110
+ - ❌ `src="https://images.unsplash.com/..."` or any other external URL
111
+ - ❌ Leaving `<img>` without src — always either a generated URL or replace with a gradient `<div>`
112
+ - ✅ One plural `mcp__r2__generate_images` call for the initial homepage build
113
+ - ✅ One-by-one singular `mcp__r2__generate_image` calls for edit-mode iteration
114
+ - ✅ Brand-specific scene descriptions drawn from the Visual Creative Brief
115
+ - ✅ Gradient `<div>` fallback if a single image's `success` is `false`