@olonjs/cli 3.0.109 → 3.0.110

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.
@@ -1607,11 +1607,9 @@ cat << 'END_OF_FILE_CONTENT' > "index.html"
1607
1607
  <meta charset="UTF-8" />
1608
1608
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
1609
1609
  <meta name="description" content="Olon — Agentic Content Infrastructure" />
1610
- <link rel="icon" type="image/svg+xml" href="/favicon.svg" />
1611
- <link href="https://cdn.jsdelivr.net/npm/geist@1.3.0/dist/fonts/geist-sans/style.css" rel="stylesheet" />
1612
- <link href="https://cdn.jsdelivr.net/npm/geist@1.3.0/dist/fonts/geist-mono/style.css" rel="stylesheet" />
1613
- <link href="https://fonts.googleapis.com/css2?family=Fraunces:ital,wght@0,300;0,500;0,700;1,300;1,500;1,700&display=swap" rel="stylesheet" />
1614
- <link href="https://cdn.jsdelivr.net/npm/@fontsource-variable/merriweather@5.2.6/wdth.css" rel="stylesheet" />
1610
+ <link rel="preconnect" href="https://fonts.googleapis.com">
1611
+ <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
1612
+ <link href="https://fonts.googleapis.com/css2?family=Geist+Mono:wght@100..900&family=Instrument+Sans:ital,wght@0,400..700;1,400..700&family=Merriweather:ital,opsz,wght@0,18..144,300..900;1,18..144,300..900&display=swap" rel="stylesheet">
1615
1613
  <title>Olon</title>
1616
1614
  </head>
1617
1615
  <body>
@@ -1646,7 +1644,7 @@ cat << 'END_OF_FILE_CONTENT' > "package.json"
1646
1644
  "@tiptap/extension-link": "^2.11.5",
1647
1645
  "@tiptap/react": "^2.11.5",
1648
1646
  "@tiptap/starter-kit": "^2.11.5",
1649
- "@olonjs/core": "^1.0.96",
1647
+ "@olonjs/core": "^1.0.97",
1650
1648
  "class-variance-authority": "^0.7.1",
1651
1649
  "clsx": "^2.1.1",
1652
1650
  "lucide-react": "^0.474.0",
@@ -4141,7 +4139,7 @@ export function OlonMark({ size = 32, className }: OlonMarkProps) {
4141
4139
 
4142
4140
  // Dark: nucleus = Parchment #E2D5B0 (warm, human)
4143
4141
  // Light: nucleus = Primary #1E1814 (brand, on white bg)
4144
- const nucleusFill = theme === 'dark' ? '#E2D5B0' : '#1E1814'
4142
+ const nucleusFill = theme === 'dark' ? '#F4F3EF' : '#080808'
4145
4143
 
4146
4144
  return (
4147
4145
  <svg
@@ -4153,8 +4151,8 @@ export function OlonMark({ size = 32, className }: OlonMarkProps) {
4153
4151
  >
4154
4152
  <defs>
4155
4153
  <linearGradient id="olon-ring" x1="0" y1="0" x2="0" y2="1">
4156
- <stop offset="0%" stopColor="#B8A4E0" />
4157
- <stop offset="100%" stopColor="#5B3F9A" />
4154
+ <stop offset="0%" stopColor="#84ABFF" />
4155
+ <stop offset="100%" stopColor="#0F52E0" />
4158
4156
  </linearGradient>
4159
4157
  </defs>
4160
4158
  <circle cx="50" cy="50" r="38" stroke="url(#olon-ring)" strokeWidth="20" />
@@ -6055,8 +6053,8 @@ export function Header({ data, settings, menu }: HeaderViewProps) {
6055
6053
  {/* Logo */}
6056
6054
  <a href="/" className="flex items-center gap-2 shrink-0" aria-label="OlonJS home">
6057
6055
  <OlonMark size={26} className="mb-0.5" />
6058
- <span
6059
- className="text-2xl text-accent leading-none"
6056
+ <div className="flex items-center gap-1"><span
6057
+ className="text-2xl text-foreground leading-none"
6060
6058
  style={{
6061
6059
  fontFamily: 'var(--wordmark-font)',
6062
6060
  letterSpacing: 'var(--wordmark-tracking)',
@@ -6065,12 +6063,9 @@ export function Header({ data, settings, menu }: HeaderViewProps) {
6065
6063
  }}
6066
6064
  >
6067
6065
  {data.logoText}
6068
- </span>
6069
- {data.badge && (
6070
- <span className="hidden sm:inline-flex items-center px-1.5 py-0.5 text-[10px] font-medium font-mono-olon bg-primary-900 text-primary-light border border-primary-800 rounded-sm">
6071
- {data.badge}
6072
- </span>
6073
- )}
6066
+ </span>
6067
+ <span className="text-primary-light font-mono">{data.badge}</span>
6068
+ </div>
6074
6069
  </a>
6075
6070
 
6076
6071
  {/* Desktop nav */}
@@ -6341,6 +6336,7 @@ export type HeaderSettings = z.infer<typeof HeaderSettingsSchema>;
6341
6336
 
6342
6337
  END_OF_FILE_CONTENT
6343
6338
  mkdir -p "src/components/hero"
6339
+ # SKIP: src/components/hero/RadialBackground - Copy.tsx:Zone.Identifier is binary and cannot be embedded as text.
6344
6340
  echo "Creating src/components/hero/RadialBackground.tsx..."
6345
6341
  cat << 'END_OF_FILE_CONTENT' > "src/components/hero/RadialBackground.tsx"
6346
6342
  import { useEffect, useRef, useState } from 'react';
@@ -6427,6 +6423,93 @@ export function RadialBackground({
6427
6423
  );
6428
6424
  }
6429
6425
 
6426
+ END_OF_FILE_CONTENT
6427
+ echo "Creating src/components/hero/RadialBackground.txt..."
6428
+ cat << 'END_OF_FILE_CONTENT' > "src/components/hero/RadialBackground.txt"
6429
+ import { useEffect, useRef, useState } from 'react';
6430
+ import { motion } from 'motion/react';
6431
+
6432
+ // CSS var names — order matches STOPS
6433
+ const TOKEN_VARS = [
6434
+ '--background', // #0B0907 center
6435
+ '--background', // #130F0D
6436
+ '--background', // #1E1814
6437
+ '--background', // #2E271F
6438
+ '--background', // #241D17
6439
+ '--elevated', // #1E1814
6440
+ '--background', // #0B0907 outer
6441
+ ] as const;
6442
+
6443
+ const STOPS = [0, 30, 55, 72, 84, 93, 100] as const;
6444
+
6445
+ function readTokenColors(): string[] {
6446
+ if (typeof document === 'undefined') return TOKEN_VARS.map(() => '#000');
6447
+ const s = getComputedStyle(document.documentElement);
6448
+ return TOKEN_VARS.map((v) => s.getPropertyValue(v).trim() || '#000');
6449
+ }
6450
+
6451
+ export function RadialBackground({
6452
+ startingGap =80,
6453
+ breathing = true,
6454
+ animationSpeed = 0.01,
6455
+ breathingRange = 180,
6456
+ topOffset = 0,
6457
+ }: {
6458
+ startingGap?: number;
6459
+ breathing?: boolean;
6460
+ animationSpeed?: number;
6461
+ breathingRange?: number;
6462
+ topOffset?: number;
6463
+ }) {
6464
+ const containerRef = useRef<HTMLDivElement | null>(null);
6465
+ const [colors, setColors] = useState<string[]>(() => readTokenColors());
6466
+
6467
+ // Re-read tokens when data-theme changes (dark ↔ light)
6468
+ useEffect(() => {
6469
+ setColors(readTokenColors());
6470
+ const observer = new MutationObserver(() => setColors(readTokenColors()));
6471
+ observer.observe(document.documentElement, {
6472
+ attributes: true,
6473
+ attributeFilter: ['data-theme'],
6474
+ });
6475
+ return () => observer.disconnect();
6476
+ }, []);
6477
+
6478
+ useEffect(() => {
6479
+ let animationFrame: number;
6480
+ let width = startingGap;
6481
+ let direction = 1;
6482
+
6483
+ const animate = () => {
6484
+ if (width >= startingGap + breathingRange) direction = -1;
6485
+ if (width <= startingGap - breathingRange) direction = 1;
6486
+ if (!breathing) direction = 0;
6487
+ width += direction * animationSpeed;
6488
+
6489
+ const stops = STOPS.map((s, i) => `${colors[i]} ${s}%`).join(', ');
6490
+ const gradient = `radial-gradient(${width}% ${width + topOffset}% at 50% 20%, ${stops})`;
6491
+
6492
+ if (containerRef.current) {
6493
+ containerRef.current.style.background = gradient;
6494
+ }
6495
+ animationFrame = requestAnimationFrame(animate);
6496
+ };
6497
+
6498
+ animationFrame = requestAnimationFrame(animate);
6499
+ return () => cancelAnimationFrame(animationFrame);
6500
+ }, [startingGap, breathing, animationSpeed, breathingRange, topOffset, colors]);
6501
+
6502
+ return (
6503
+ <motion.div
6504
+ animate={{ opacity: 1, scale: 1, transition: { duration: 2, ease: [0.25, 0.1, 0.25, 1] } }}
6505
+ className="absolute inset-0 overflow-hidden"
6506
+ initial={{ opacity: 0, scale: 1.5 }}
6507
+ >
6508
+ <div className="absolute inset-0" ref={containerRef} />
6509
+ </motion.div>
6510
+ );
6511
+ }
6512
+
6430
6513
  END_OF_FILE_CONTENT
6431
6514
  echo "Creating src/components/hero/View.tsx..."
6432
6515
  cat << 'END_OF_FILE_CONTENT' > "src/components/hero/View.tsx"
@@ -6470,11 +6553,11 @@ export function Hero({ data, settings }: HeroViewProps) {
6470
6553
  )}
6471
6554
 
6472
6555
  {/* Headline */}
6473
- <h1 className="font-display font-normal text-7xl text-foreground leading-tight tracking-display mb-1" data-jp-field="title">
6556
+ <h1 className="font-display font-bold text-7xl text-foreground leading-tight tracking-tight mb-1" data-jp-field="title">
6474
6557
  {data.title}
6475
6558
  </h1>
6476
6559
  {data.titleHighlight && (
6477
- <h2 className="font-display font-normal italic text-5xl md:text-6xl text-primary-light leading-tight tracking-display mb-7" data-jp-field="titleHighlight">
6560
+ <h2 className="font-display font-normal italic text-5xl md:text-6xl text-primary-light leading-tight tracking-tight mb-7" data-jp-field="titleHighlight">
6478
6561
  {data.titleHighlight}
6479
6562
  </h2>
6480
6563
  )}
@@ -6807,6 +6890,969 @@ import { LoginSchema, LoginSettingsSchema } from './schema';
6807
6890
  export type LoginData = z.infer<typeof LoginSchema>;
6808
6891
  export type LoginSettings = z.infer<typeof LoginSettingsSchema>;
6809
6892
 
6893
+ END_OF_FILE_CONTENT
6894
+ mkdir -p "src/components/olon-architecture"
6895
+ echo "Creating src/components/olon-architecture/View.tsx..."
6896
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-architecture/View.tsx"
6897
+ import type { OlonArchitectureData } from './types';
6898
+
6899
+ const ICONS: Record<string, React.ReactNode> = {
6900
+ mtrp: (
6901
+ <svg width="32" height="32" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
6902
+ <defs><linearGradient id="am" x1="0" y1="0" x2="1" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient><linearGradient id="amc" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#EEF3FF"/><stop offset="1" stopColor="#84ABFF"/></linearGradient></defs>
6903
+ <rect x="25" y="30" width="130" height="140" rx="10" fill="none" stroke="url(#am)" strokeWidth="7"/>
6904
+ <line x1="25" y1="60" x2="155" y2="60" stroke="url(#am)" strokeWidth="5"/>
6905
+ <path fill="none" stroke="url(#am)" strokeLinecap="round" strokeLinejoin="round" strokeWidth="4.5" d="M72,42 c-5,0 -8,2 -8,6v2c0,4 -3,5 -6,5 3,0 6,1 6,5v2c0,4 3,6 8,6"/>
6906
+ <path fill="none" stroke="url(#am)" strokeLinecap="round" strokeLinejoin="round" strokeWidth="4.5" d="M108,42 c5,0 8,2 8,6v2c0,4 3,5 6,5 -3,0 -6,1 -6,5v2c0,4 -3,6 -8,6"/>
6907
+ <circle fill="url(#am)" opacity="0.35" cx="46" cy="90" r="4.5"/>
6908
+ <rect fill="url(#am)" opacity="0.35" x="59" y="86.5" width="68" height="7" rx="3.5"/>
6909
+ <circle fill="url(#amc)" cx="46" cy="117" r="6.5"/>
6910
+ <rect fill="url(#amc)" x="59" y="113" width="82" height="8" rx="4"/>
6911
+ <circle fill="url(#am)" opacity="0.55" cx="46" cy="145" r="4.5"/>
6912
+ <rect fill="url(#am)" opacity="0.55" x="59" y="141.5" width="50" height="7" rx="3.5"/>
6913
+ <path fill="none" stroke="url(#amc)" strokeLinecap="round" strokeWidth="5" d="M192,117 h-35"/>
6914
+ <path fill="none" stroke="url(#amc)" strokeLinecap="round" strokeLinejoin="round" strokeWidth="5" d="M170,108 l17,9 -17,9"/>
6915
+ </svg>
6916
+ ),
6917
+ tbp: (
6918
+ <svg width="32" height="32" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
6919
+ <defs><linearGradient id="at" x1="0" y1="0" x2="1" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient><linearGradient id="atc" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#EEF3FF"/><stop offset="1" stopColor="#84ABFF"/></linearGradient></defs>
6920
+ <rect fill="none" stroke="url(#at)" strokeWidth="5.5" strokeLinejoin="round" opacity="0.3" x="65" y="22" width="108" height="74" rx="9"/>
6921
+ <rect fill="none" stroke="url(#at)" strokeWidth="5.5" strokeLinejoin="round" opacity="0.6" x="46" y="50" width="108" height="74" rx="9"/>
6922
+ <rect fill="none" stroke="url(#at)" strokeWidth="6.5" strokeLinejoin="round" x="27" y="78" width="108" height="74" rx="9"/>
6923
+ <rect fill="url(#at)" opacity="0.6" x="42" y="101" width="52" height="6" rx="3"/>
6924
+ <rect fill="url(#atc)" x="42" y="116" width="36" height="6" rx="3"/>
6925
+ <circle fill="url(#at)" opacity="0.3" cx="162" cy="33" r="4"/>
6926
+ <circle fill="url(#at)" opacity="0.6" cx="143" cy="61" r="4"/>
6927
+ <circle fill="url(#atc)" cx="124" cy="89" r="5"/>
6928
+ </svg>
6929
+ ),
6930
+ jsp: (
6931
+ <svg width="32" height="32" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
6932
+ <defs><linearGradient id="aj" x1="0" y1="0" x2="1" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient><linearGradient id="ajc" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#EEF3FF"/><stop offset="1" stopColor="#84ABFF"/></linearGradient></defs>
6933
+ <rect fill="none" stroke="url(#aj)" strokeWidth="7" strokeLinejoin="round" x="14" y="22" width="172" height="128" rx="12"/>
6934
+ <line x1="14" y1="52" x2="186" y2="52" stroke="url(#aj)" strokeWidth="5"/>
6935
+ <circle fill="url(#aj)" opacity="0.4" cx="34" cy="37" r="5"/>
6936
+ <circle fill="url(#aj)" opacity="0.6" cx="52" cy="37" r="5"/>
6937
+ <circle fill="url(#ajc)" cx="70" cy="37" r="5"/>
6938
+ <path fill="none" stroke="url(#ajc)" strokeLinecap="round" strokeLinejoin="round" strokeWidth="6" d="M28,75 l12,11 -12,11"/>
6939
+ <rect fill="url(#ajc)" x="48" y="80" width="22" height="7" rx="3.5"/>
6940
+ <rect fill="url(#aj)" opacity="0.7" x="28" y="106" width="88" height="6" rx="3"/>
6941
+ <rect fill="url(#aj)" opacity="0.5" x="28" y="121" width="62" height="6" rx="3"/>
6942
+ <rect fill="url(#aj)" opacity="0.35" x="28" y="136" width="76" height="6" rx="3"/>
6943
+ </svg>
6944
+ ),
6945
+ idac: (
6946
+ <svg width="32" height="32" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
6947
+ <defs><linearGradient id="ai" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient><linearGradient id="aic" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#EEF3FF"/><stop offset="1" stopColor="#84ABFF"/></linearGradient></defs>
6948
+ <rect fill="none" stroke="url(#ai)" strokeWidth="6.5" strokeLinejoin="round" x="8" y="36" width="72" height="128" rx="9"/>
6949
+ <rect fill="url(#ai)" opacity="0.5" x="20" y="56" width="48" height="5.5" rx="2.75"/>
6950
+ <rect fill="url(#aic)" x="20" y="75" width="48" height="8" rx="4"/>
6951
+ <rect fill="url(#ai)" opacity="0.4" x="20" y="98" width="48" height="5.5" rx="2.75"/>
6952
+ <path fill="none" stroke="url(#aic)" strokeLinecap="round" strokeWidth="5.5" d="M80,100 h40"/>
6953
+ <circle fill="url(#aic)" cx="100" cy="100" r="5.5"/>
6954
+ <path fill="none" stroke="url(#ai)" strokeLinecap="round" strokeWidth="4" opacity="0.4" d="M80,75 h40"/>
6955
+ <path fill="none" stroke="url(#ai)" strokeLinecap="round" strokeWidth="4" opacity="0.4" d="M80,125 h40"/>
6956
+ <rect fill="none" stroke="url(#ai)" strokeWidth="6.5" strokeLinejoin="round" x="120" y="36" width="72" height="128" rx="9"/>
6957
+ <rect fill="url(#ai)" opacity="0.5" x="132" y="56" width="48" height="5.5" rx="2.75"/>
6958
+ <rect fill="url(#aic)" x="132" y="75" width="48" height="8" rx="4"/>
6959
+ <rect fill="url(#ai)" opacity="0.4" x="132" y="98" width="48" height="5.5" rx="2.75"/>
6960
+ </svg>
6961
+ ),
6962
+ bsds: (
6963
+ <svg width="32" height="32" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
6964
+ <defs><linearGradient id="ab" x1="0" y1="0" x2="1" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient><linearGradient id="abc" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#EEF3FF"/><stop offset="1" stopColor="#84ABFF"/></linearGradient></defs>
6965
+ <rect fill="none" stroke="url(#ab)" strokeWidth="8" strokeLinejoin="round" x="16" y="152" width="168" height="32" rx="8"/>
6966
+ <circle fill="url(#abc)" cx="100" cy="168" r="7"/>
6967
+ <path fill="none" stroke="url(#ab)" strokeLinecap="round" strokeWidth="5" opacity="0.5" d="M54,138 v14"/>
6968
+ <path fill="none" stroke="url(#ab)" strokeLinecap="round" strokeWidth="5" opacity="0.5" d="M146,138 v14"/>
6969
+ <rect fill="none" stroke="url(#ab)" strokeWidth="6" strokeLinejoin="round" x="16" y="68" width="76" height="70" rx="9"/>
6970
+ <rect fill="url(#ab)" opacity="0.55" x="28" y="84" width="42" height="6" rx="3"/>
6971
+ <rect fill="url(#abc)" x="28" y="112" width="32" height="6" rx="3"/>
6972
+ <rect fill="none" stroke="url(#ab)" strokeWidth="6" strokeLinejoin="round" x="108" y="44" width="76" height="94" rx="9"/>
6973
+ <rect fill="url(#ab)" opacity="0.55" x="120" y="60" width="42" height="6" rx="3"/>
6974
+ <rect fill="url(#abc)" x="120" y="88" width="32" height="6" rx="3"/>
6975
+ </svg>
6976
+ ),
6977
+ pss: (
6978
+ <svg width="32" height="32" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
6979
+ <defs><linearGradient id="ap" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient><linearGradient id="apc" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#EEF3FF"/><stop offset="1" stopColor="#84ABFF"/></linearGradient></defs>
6980
+ <path fill="none" stroke="url(#apc)" strokeLinecap="round" strokeWidth="5.5" d="M100,32 L52,90"/>
6981
+ <path fill="none" stroke="url(#ap)" strokeLinecap="round" strokeWidth="5" opacity="0.3" d="M100,32 L148,90"/>
6982
+ <path fill="none" stroke="url(#ap)" strokeLinecap="round" strokeWidth="4.5" opacity="0.3" d="M52,90 L22,158"/>
6983
+ <path fill="none" stroke="url(#apc)" strokeLinecap="round" strokeWidth="5.5" d="M52,90 L90,158"/>
6984
+ <path fill="none" stroke="url(#ap)" strokeLinecap="round" strokeWidth="4" opacity="0.25" d="M148,90 L170,158"/>
6985
+ <circle fill="url(#apc)" cx="100" cy="22" r="11"/>
6986
+ <circle fill="url(#apc)" cx="52" cy="90" r="10"/>
6987
+ <circle fill="url(#ap)" opacity="0.3" cx="148" cy="90" r="8"/>
6988
+ <circle fill="url(#ap)" opacity="0.3" cx="22" cy="165" r="7"/>
6989
+ <circle fill="url(#apc)" cx="90" cy="165" r="11"/>
6990
+ <rect fill="none" stroke="url(#apc)" strokeWidth="4" strokeLinejoin="round" opacity="0.5" x="76" y="151" width="28" height="28" rx="5"/>
6991
+ </svg>
6992
+ ),
6993
+ };
6994
+
6995
+ interface Props { data: OlonArchitectureData; }
6996
+
6997
+ export function OlonArchitectureView({ data }: Props) {
6998
+ return (
6999
+ <section
7000
+ style={{
7001
+ '--local-bg': 'var(--background)',
7002
+ '--local-fg': 'var(--foreground)',
7003
+ '--local-muted': 'var(--muted-foreground)',
7004
+ '--local-p400': 'var(--primary)',
7005
+ '--local-card': 'var(--card)',
7006
+ '--local-border':'var(--border)',
7007
+ } as React.CSSProperties}
7008
+ className="bg-[var(--local-bg)] text-[var(--local-fg)] py-24 border-t border-[var(--local-border)]"
7009
+ data-jp-section-id={data.id}
7010
+ data-jp-section-type="olon-architecture"
7011
+ >
7012
+ <div className="max-w-6xl mx-auto px-8">
7013
+ <p className="text-xs font-semibold tracking-[0.12em] uppercase text-[var(--local-muted)] mb-3"
7014
+ data-jp-field="label">{data.label}</p>
7015
+ <h2 className="text-4xl font-bold tracking-[-0.03em] text-white mb-3"
7016
+ data-jp-field="headline">{data.headline}</h2>
7017
+ <p className="text-base text-[var(--local-muted)] leading-relaxed max-w-2xl mb-3"
7018
+ data-jp-field="body">{data.body}</p>
7019
+ {data.specHref && (
7020
+ <p className="text-sm text-[var(--local-muted)] mb-12">
7021
+ Full specification:{' '}
7022
+ <a href={data.specHref} target="_blank" rel="noopener noreferrer"
7023
+ className="text-[var(--local-p400)] hover:underline">
7024
+ olonjsSpecs_V_1_5.md ↗
7025
+ </a>
7026
+ </p>
7027
+ )}
7028
+
7029
+ <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 border border-[var(--local-border)] rounded-2xl overflow-hidden"
7030
+ data-jp-array="protocols">
7031
+ {data.protocols.map((p) => (
7032
+ <div key={p.id}
7033
+ className="bg-[var(--local-card)] p-7 flex flex-col gap-3 border-r border-b border-[var(--local-border)] hover:bg-[var(--elevated)] transition-colors"
7034
+ data-jp-item-id={p.id}>
7035
+ <div>{ICONS[p.icon]}</div>
7036
+ <p className="text-[11px] font-semibold tracking-[0.1em] uppercase text-[var(--local-p400)] font-mono"
7037
+ data-jp-field="version">{p.acronym} · {p.version}</p>
7038
+ <p className="font-bold text-white text-base" data-jp-field="name">{p.name}</p>
7039
+ <p className="text-sm text-[var(--local-muted)] leading-relaxed flex-1"
7040
+ data-jp-field="desc">{p.desc}</p>
7041
+ <a href={p.specHref} target="_blank" rel="noopener noreferrer"
7042
+ className="text-xs text-[var(--local-p400)] hover:text-white transition-colors mt-auto"
7043
+ data-jp-field="specHref">Read spec ↗</a>
7044
+ </div>
7045
+ ))}
7046
+ </div>
7047
+ </div>
7048
+ </section>
7049
+ );
7050
+ }
7051
+
7052
+ END_OF_FILE_CONTENT
7053
+ echo "Creating src/components/olon-architecture/index.ts..."
7054
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-architecture/index.ts"
7055
+ export { OlonArchitectureView as View } from './View';
7056
+ export { OlonArchitectureSchema } from './schema';
7057
+ export type { OlonArchitectureData } from './types';
7058
+
7059
+ END_OF_FILE_CONTENT
7060
+ echo "Creating src/components/olon-architecture/schema.ts..."
7061
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-architecture/schema.ts"
7062
+ import { z } from 'zod';
7063
+ import { BaseSectionData, BaseArrayItem } from '@/lib/base-schemas';
7064
+
7065
+ export const ProtocolSchema = BaseArrayItem.extend({
7066
+ version: z.string(),
7067
+ acronym: z.string(),
7068
+ name: z.string(),
7069
+ desc: z.string(),
7070
+ specHref: z.string(),
7071
+ icon: z.enum(['mtrp', 'tbp', 'jsp', 'idac', 'bsds', 'pss']),
7072
+ });
7073
+
7074
+ export const OlonArchitectureSchema = BaseSectionData.extend({
7075
+ label: z.string().default('Architecture'),
7076
+ headline: z.string().default('Six governing protocols.'),
7077
+ body: z.string().default(''),
7078
+ specHref: z.string().default(''),
7079
+ protocols: z.array(ProtocolSchema).min(1).max(6),
7080
+ });
7081
+
7082
+ export type OlonArchitectureData = z.infer<typeof OlonArchitectureSchema>;
7083
+
7084
+ END_OF_FILE_CONTENT
7085
+ echo "Creating src/components/olon-architecture/types.ts..."
7086
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-architecture/types.ts"
7087
+ export type { OlonArchitectureData } from './schema';
7088
+
7089
+ END_OF_FILE_CONTENT
7090
+ mkdir -p "src/components/olon-example"
7091
+ echo "Creating src/components/olon-example/View.tsx..."
7092
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-example/View.tsx"
7093
+ import type { OlonExampleData } from './types';
7094
+
7095
+ interface Props { data: OlonExampleData; }
7096
+
7097
+ export function OlonExampleView({ data }: Props) {
7098
+ return (
7099
+ <section
7100
+ style={{
7101
+ '--local-bg': 'var(--background)',
7102
+ '--local-fg': 'var(--foreground)',
7103
+ '--local-muted': 'var(--muted-foreground)',
7104
+ '--local-p400': 'var(--primary)',
7105
+ '--local-p300': 'var(--primary-light)',
7106
+ '--local-card': 'var(--card)',
7107
+ '--local-border':'var(--border)',
7108
+ } as React.CSSProperties}
7109
+ className="bg-[var(--local-bg)] text-[var(--local-fg)] py-24 border-t border-[var(--local-border)]"
7110
+ data-jp-section-id={data.id}
7111
+ data-jp-section-type="olon-example"
7112
+ >
7113
+ <div className="max-w-6xl mx-auto px-8">
7114
+ <p className="text-xs font-semibold tracking-[0.12em] uppercase text-[var(--local-muted)] mb-3"
7115
+ data-jp-field="label">{data.label}</p>
7116
+ <h2 className="text-4xl font-bold tracking-[-0.03em] text-white mb-3"
7117
+ data-jp-field="headline">{data.headline}</h2>
7118
+ <p className="text-base text-[var(--local-muted)] leading-relaxed max-w-2xl mb-12"
7119
+ data-jp-field="body">{data.body}</p>
7120
+
7121
+ <div className="grid grid-cols-1 md:grid-cols-2 gap-6">
7122
+ {data.steps.map((step) => (
7123
+ <div key={step.number}
7124
+ className="bg-[var(--local-card)] border border-[var(--local-border)] rounded-2xl overflow-hidden">
7125
+ {/* Step header */}
7126
+ <div className="px-6 py-4 border-b border-[var(--local-border)] flex items-center gap-3">
7127
+ <span className="w-6 h-6 rounded-full bg-[var(--local-p400)] text-white text-xs font-bold flex items-center justify-center flex-shrink-0">
7128
+ {step.number}
7129
+ </span>
7130
+ <span className="font-semibold text-white text-sm">{step.title}</span>
7131
+ <span className="ml-auto text-xs text-[var(--local-muted)]">{step.meta}</span>
7132
+ </div>
7133
+ {/* Code block */}
7134
+ <pre className="p-6 font-mono text-xs leading-relaxed bg-[#080E14] text-[var(--local-fg)] overflow-x-auto whitespace-pre-wrap min-h-[200px]">
7135
+ {step.code}
7136
+ </pre>
7137
+ </div>
7138
+ ))}
7139
+ </div>
7140
+
7141
+ {/* MCP manifest note */}
7142
+ {data.note && (
7143
+ <div className="mt-6 px-6 py-4 bg-[var(--local-card)] border border-[var(--local-border)] rounded-xl flex items-start gap-3">
7144
+ <svg width="18" height="18" viewBox="0 0 24 24" fill="none"
7145
+ stroke="currentColor" strokeWidth="2" strokeLinecap="round"
7146
+ className="text-[var(--local-p400)] mt-0.5 flex-shrink-0">
7147
+ <circle cx="12" cy="12" r="10"/>
7148
+ <line x1="12" y1="8" x2="12" y2="12"/>
7149
+ <line x1="12" y1="16" x2="12.01" y2="16"/>
7150
+ </svg>
7151
+ <p className="text-sm text-[var(--local-muted)]" data-jp-field="note">
7152
+ {data.note}{' '}
7153
+ {data.noteHref && (
7154
+ <code className="font-mono text-[var(--local-p300)] text-xs">{data.noteHref}</code>
7155
+ )}
7156
+ </p>
7157
+ </div>
7158
+ )}
7159
+ </div>
7160
+ </section>
7161
+ );
7162
+ }
7163
+
7164
+ END_OF_FILE_CONTENT
7165
+ echo "Creating src/components/olon-example/index.ts..."
7166
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-example/index.ts"
7167
+ export { OlonExampleView as View } from './View';
7168
+ export { OlonExampleSchema } from './schema';
7169
+ export type { OlonExampleData } from './types';
7170
+
7171
+ END_OF_FILE_CONTENT
7172
+ echo "Creating src/components/olon-example/schema.ts..."
7173
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-example/schema.ts"
7174
+ import { z } from 'zod';
7175
+ import { BaseSectionData } from '@/lib/base-schemas';
7176
+
7177
+ const StepSchema = z.object({
7178
+ number: z.number(),
7179
+ title: z.string(),
7180
+ meta: z.string(),
7181
+ code: z.string(),
7182
+ });
7183
+
7184
+ export const OlonExampleSchema = BaseSectionData.extend({
7185
+ label: z.string().default('Quick Example'),
7186
+ headline: z.string().default('Two steps. One contract.'),
7187
+ body: z.string().default(''),
7188
+ note: z.string().default(''),
7189
+ noteHref: z.string().default(''),
7190
+ steps: z.tuple([StepSchema, StepSchema]),
7191
+ });
7192
+
7193
+ export type OlonExampleData = z.infer<typeof OlonExampleSchema>;
7194
+
7195
+ END_OF_FILE_CONTENT
7196
+ echo "Creating src/components/olon-example/types.ts..."
7197
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-example/types.ts"
7198
+ export type { OlonExampleData } from './schema';
7199
+
7200
+ END_OF_FILE_CONTENT
7201
+ mkdir -p "src/components/olon-getstarted"
7202
+ echo "Creating src/components/olon-getstarted/View.tsx..."
7203
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-getstarted/View.tsx"
7204
+ import type { OlonGetStartedData } from './types';
7205
+ import { Button } from '@/components/ui/button';
7206
+
7207
+ const BADGE_STYLES: Record<string, string> = {
7208
+ oss: 'bg-blue-500/15 text-blue-400 border border-blue-500/30',
7209
+ cli: 'bg-primary/10 text-primary border border-primary/20',
7210
+ deploy: 'bg-muted text-muted-foreground border border-border',
7211
+ };
7212
+
7213
+ interface Props { data: OlonGetStartedData; }
7214
+
7215
+ export function OlonGetStartedView({ data }: Props) {
7216
+ return (
7217
+ <section
7218
+ style={{
7219
+ '--local-bg': 'var(--background)',
7220
+ '--local-fg': 'var(--foreground)',
7221
+ '--local-muted': 'var(--muted-foreground)',
7222
+ '--local-p400': 'var(--primary)',
7223
+ '--local-p300': 'var(--primary-light)',
7224
+ '--local-card': 'var(--card)',
7225
+ '--local-border':'var(--border)',
7226
+ } as React.CSSProperties}
7227
+ className="bg-[var(--local-bg)] text-[var(--local-fg)] py-24 border-t border-[var(--local-border)]"
7228
+ data-jp-section-id={data.id}
7229
+ data-jp-section-type="olon-getstarted"
7230
+ >
7231
+ <div className="max-w-6xl mx-auto px-8">
7232
+ <p className="text-xs font-semibold tracking-[0.12em] uppercase text-[var(--local-muted)] mb-3"
7233
+ data-jp-field="label">{data.label}</p>
7234
+ <h2 className="text-4xl font-bold tracking-[-0.03em] text-white mb-3"
7235
+ data-jp-field="headline">{data.headline}</h2>
7236
+ <p className="text-base text-[var(--local-muted)] leading-relaxed max-w-2xl mb-12"
7237
+ data-jp-field="body">{data.body}</p>
7238
+
7239
+ <div className="grid grid-cols-1 md:grid-cols-3 border border-[var(--local-border)] rounded-2xl overflow-hidden"
7240
+ data-jp-array="cards">
7241
+ {data.cards.map((card) => (
7242
+ <div key={card.id}
7243
+ className="bg-[var(--local-card)] p-8 flex flex-col gap-4 border-r last:border-r-0 border-[var(--local-border)] hover:bg-[var(--elevated)] transition-colors"
7244
+ data-jp-item-id={card.id}>
7245
+ <span className={`text-[11px] font-bold tracking-[0.08em] uppercase px-2.5 py-0.5 rounded-full w-fit ${BADGE_STYLES[card.badgeStyle]}`}
7246
+ data-jp-field="badge">
7247
+ {card.badge}
7248
+ </span>
7249
+ <p className="font-bold text-white text-base" data-jp-field="title">{card.title}</p>
7250
+ <p className="text-sm text-[var(--local-muted)] leading-relaxed flex-1"
7251
+ data-jp-field="body">{card.body}</p>
7252
+ {card.code && (
7253
+ <code className="font-mono text-xs bg-[#080E14] border border-[var(--local-border)] rounded-lg px-4 py-3 text-[var(--local-p300)] block"
7254
+ data-jp-field="code">
7255
+ {card.code}
7256
+ </code>
7257
+ )}
7258
+ {card.deployHref && card.deployLabel && (
7259
+ <Button asChild variant="outline" size="sm" className="w-fit">
7260
+ <a href={card.deployHref} target="_blank" rel="noopener noreferrer">
7261
+ {card.deployLabel}
7262
+ </a>
7263
+ </Button>
7264
+ )}
7265
+ <a href={card.linkHref} target="_blank" rel="noopener noreferrer"
7266
+ className="text-sm text-[var(--local-p400)] hover:text-[var(--local-p300)] transition-colors flex items-center gap-1 mt-auto"
7267
+ data-jp-field="linkLabel">
7268
+ {card.linkLabel} ↗
7269
+ </a>
7270
+ </div>
7271
+ ))}
7272
+ </div>
7273
+ </div>
7274
+ </section>
7275
+ );
7276
+ }
7277
+
7278
+ END_OF_FILE_CONTENT
7279
+ echo "Creating src/components/olon-getstarted/index.ts..."
7280
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-getstarted/index.ts"
7281
+ export { OlonGetStartedView as View } from './View';
7282
+ export { OlonGetStartedSchema } from './schema';
7283
+ export type { OlonGetStartedData } from './types';
7284
+
7285
+ END_OF_FILE_CONTENT
7286
+ echo "Creating src/components/olon-getstarted/schema.ts..."
7287
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-getstarted/schema.ts"
7288
+ import { z } from 'zod';
7289
+ import { BaseSectionData, BaseArrayItem } from '@/lib/base-schemas';
7290
+
7291
+ export const StartCardSchema = BaseArrayItem.extend({
7292
+ badge: z.string(),
7293
+ badgeStyle: z.enum(['oss', 'cli', 'deploy']),
7294
+ title: z.string(),
7295
+ body: z.string(),
7296
+ code: z.string().optional(),
7297
+ linkLabel: z.string(),
7298
+ linkHref: z.string(),
7299
+ deployLabel:z.string().optional(),
7300
+ deployHref: z.string().optional(),
7301
+ });
7302
+
7303
+ export const OlonGetStartedSchema = BaseSectionData.extend({
7304
+ label: z.string().default('Get Started'),
7305
+ headline: z.string().default('Three paths in.'),
7306
+ body: z.string().default(''),
7307
+ cards: z.array(StartCardSchema).min(1).max(3),
7308
+ });
7309
+
7310
+ export type OlonGetStartedData = z.infer<typeof OlonGetStartedSchema>;
7311
+
7312
+ END_OF_FILE_CONTENT
7313
+ echo "Creating src/components/olon-getstarted/types.ts..."
7314
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-getstarted/types.ts"
7315
+ export type { OlonGetStartedData } from './schema';
7316
+
7317
+ END_OF_FILE_CONTENT
7318
+ mkdir -p "src/components/olon-hero"
7319
+ echo "Creating src/components/olon-hero/DawnBackground.tsx..."
7320
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-hero/DawnBackground.tsx"
7321
+ import { useEffect, useRef } from 'react';
7322
+ import { motion } from 'motion/react';
7323
+
7324
+ export function DawnBackground({
7325
+ dawnDuration = 3.5,
7326
+ breathingSpeed = 0.5,
7327
+ breathingRange = 0.03,
7328
+ intensity = 0.55,
7329
+ }: {
7330
+ dawnDuration?: number;
7331
+ breathingSpeed?: number;
7332
+ breathingRange?: number;
7333
+ intensity?: number;
7334
+ }) {
7335
+ const containerRef = useRef<HTMLDivElement | null>(null);
7336
+ const canvasRef = useRef<HTMLCanvasElement | null>(null);
7337
+ const rafRef = useRef<number>(0);
7338
+ const startRef = useRef<number | null>(null);
7339
+
7340
+ useEffect(() => {
7341
+ const canvas = canvasRef.current;
7342
+ const container = containerRef.current;
7343
+ if (!canvas || !container) return;
7344
+
7345
+ const ctx = canvas.getContext('2d');
7346
+ if (!ctx) return;
7347
+
7348
+ function resize() {
7349
+ if (!canvas || !container) return;
7350
+ const dpr = window.devicePixelRatio || 1;
7351
+ canvas.width = container.offsetWidth * dpr;
7352
+ canvas.height = container.offsetHeight * dpr;
7353
+ }
7354
+ resize();
7355
+
7356
+ const ro = new ResizeObserver(resize);
7357
+ ro.observe(container);
7358
+
7359
+ function easeOut(t: number) {
7360
+ return 1 - Math.pow(1 - t, 3);
7361
+ }
7362
+
7363
+ function draw(ts: number) {
7364
+ if (!canvas || !ctx) return;
7365
+ if (!startRef.current) startRef.current = ts;
7366
+
7367
+ const elapsed = (ts - startRef.current) / 1000;
7368
+ const dawnP = Math.min(elapsed / dawnDuration, 1);
7369
+ const dawnE = easeOut(dawnP);
7370
+ const breathT = Math.max(0, elapsed - dawnDuration);
7371
+ const breathe = dawnP >= 1
7372
+ ? 1 + Math.sin(breathT * breathingSpeed) * breathingRange
7373
+ : 1;
7374
+
7375
+ const W = canvas.width;
7376
+ const H = canvas.height;
7377
+ const masterIntensity = dawnE * intensity * breathe;
7378
+
7379
+ ctx.clearRect(0, 0, W, H);
7380
+
7381
+ // Left source — bottom left, primary blue
7382
+ const lx = W * 0.18;
7383
+ const ly = H * 0.92;
7384
+ const lr = W * 0.75 * breathe;
7385
+ const gL = ctx.createRadialGradient(lx, ly, 0, lx, ly, lr);
7386
+ gL.addColorStop(0.00, `rgba(15,52,224,${0.70 * masterIntensity})`);
7387
+ gL.addColorStop(0.20, `rgba(23,99,255,${0.60 * masterIntensity})`);
7388
+ gL.addColorStop(0.45, `rgba(91,142,255,${0.35 * masterIntensity})`);
7389
+ gL.addColorStop(0.70, `rgba(84,171,255,${0.15 * masterIntensity})`);
7390
+ gL.addColorStop(1.00, 'rgba(12,17,22,0)');
7391
+ ctx.fillStyle = gL;
7392
+ ctx.fillRect(0, 0, W, H);
7393
+
7394
+ // Right source — mirror
7395
+ const gR = ctx.createRadialGradient(W - lx, ly, 0, W - lx, ly, lr);
7396
+ gR.addColorStop(0.00, `rgba(15,52,224,${0.70 * masterIntensity})`);
7397
+ gR.addColorStop(0.20, `rgba(23,99,255,${0.60 * masterIntensity})`);
7398
+ gR.addColorStop(0.45, `rgba(91,142,255,${0.35 * masterIntensity})`);
7399
+ gR.addColorStop(0.70, `rgba(84,171,255,${0.15 * masterIntensity})`);
7400
+ gR.addColorStop(1.00, 'rgba(12,17,22,0)');
7401
+ ctx.fillStyle = gR;
7402
+ ctx.fillRect(0, 0, W, H);
7403
+
7404
+ // Center V tip — deep navy, very subtle
7405
+ const vr = W * 0.32 * breathe;
7406
+ const gV = ctx.createRadialGradient(W * 0.5, H * 0.72, 0, W * 0.5, H * 0.72, vr);
7407
+ gV.addColorStop(0.00, `rgba(9,64,184,${0.50 * masterIntensity})`);
7408
+ gV.addColorStop(0.40, `rgba(15,52,224,${0.25 * masterIntensity})`);
7409
+ gV.addColorStop(1.00, 'rgba(12,17,22,0)');
7410
+ ctx.fillStyle = gV;
7411
+ ctx.fillRect(0, 0, W, H);
7412
+
7413
+ // Top dark veil — keeps header very dark
7414
+ const gTop = ctx.createLinearGradient(0, 0, 0, H * 0.6);
7415
+ gTop.addColorStop(0, 'rgba(12,17,22,1)');
7416
+ gTop.addColorStop(0.55, 'rgba(12,17,22,0.85)');
7417
+ gTop.addColorStop(1, 'rgba(12,17,22,0)');
7418
+ ctx.fillStyle = gTop;
7419
+ ctx.fillRect(0, 0, W, H);
7420
+
7421
+ rafRef.current = requestAnimationFrame(draw);
7422
+ }
7423
+
7424
+ rafRef.current = requestAnimationFrame(draw);
7425
+
7426
+ return () => {
7427
+ cancelAnimationFrame(rafRef.current);
7428
+ ro.disconnect();
7429
+ };
7430
+ }, [dawnDuration, breathingSpeed, breathingRange, intensity]);
7431
+
7432
+ return (
7433
+ <motion.div
7434
+ ref={containerRef}
7435
+ className="absolute inset-0 overflow-hidden"
7436
+ animate={{ opacity: 1, transition: { duration: 0.1 } }}
7437
+ initial={{ opacity: 0 }}
7438
+ >
7439
+ <canvas
7440
+ ref={canvasRef}
7441
+ className="absolute inset-0 w-full h-full"
7442
+ />
7443
+ </motion.div>
7444
+ );
7445
+ }
7446
+
7447
+ END_OF_FILE_CONTENT
7448
+ echo "Creating src/components/olon-hero/View.tsx..."
7449
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-hero/View.tsx"
7450
+ import type { OlonHeroData } from './types';
7451
+ import { Button } from '@/components/ui/button';
7452
+ import { DawnBackground } from './DawnBackground';
7453
+
7454
+ interface Props {
7455
+ data: OlonHeroData;
7456
+ }
7457
+
7458
+ export function OlonHeroView({ data }: Props) {
7459
+ return (
7460
+ <section
7461
+ style={{
7462
+ '--local-bg': 'var(--background)',
7463
+ '--local-fg': 'var(--foreground)',
7464
+ '--local-muted': 'var(--muted-foreground)',
7465
+ '--local-primary': 'var(--primary)',
7466
+ '--local-p300': 'var(--primary-light)',
7467
+ } as React.CSSProperties}
7468
+ className="relative min-h-screen bg-[var(--local-bg)] text-[var(--local-fg)] pt-36 pb-24 overflow-hidden"
7469
+ data-jp-section-id={data.id}
7470
+ data-jp-section-type="olon-hero"
7471
+ >
7472
+ {/* Dawn background — absolute, behind content */}
7473
+ <DawnBackground />
7474
+
7475
+ {/* Content — relative, above background */}
7476
+ <div className="relative z-10 max-w-6xl mx-auto px-8 grid grid-cols-1 md:grid-cols-2 gap-16 items-center">
7477
+ {/* Left: copy */}
7478
+ <div className="flex flex-col gap-6">
7479
+ <p
7480
+ className="text-xs font-semibold tracking-[0.12em] uppercase text-[var(--local-muted)]"
7481
+ data-jp-field="eyebrow"
7482
+ >
7483
+ {data.eyebrow}
7484
+ </p>
7485
+
7486
+ <div>
7487
+ <h1
7488
+ className="text-5xl md:text-6xl font-bold tracking-[-0.03em] leading-[1.05] text-white"
7489
+ data-jp-field="headline"
7490
+ >
7491
+ {data.headline}
7492
+ </h1>
7493
+ <p
7494
+ className="text-4xl md:text-5xl font-semibold tracking-[-0.03em] leading-[1.1] text-[var(--local-p300)] italic mt-1"
7495
+ data-jp-field="subline"
7496
+ >
7497
+ {data.subline}
7498
+ </p>
7499
+ </div>
7500
+
7501
+ <p
7502
+ className="text-base text-[var(--local-muted)] leading-relaxed max-w-lg"
7503
+ data-jp-field="body"
7504
+ >
7505
+ {data.body}
7506
+ </p>
7507
+
7508
+ <div className="flex flex-wrap gap-3 items-center">
7509
+ <Button asChild size="lg" className="font-semibold">
7510
+ <a href={data.cta.primary.href}>{data.cta.primary.label} →</a>
7511
+ </Button>
7512
+ <Button asChild variant="outline" size="lg" className="font-semibold">
7513
+ <a href={data.cta.secondary.href}>{data.cta.secondary.label}</a>
7514
+ </Button>
7515
+ <a
7516
+ href={data.cta.ghost.href}
7517
+ className="text-sm text-[var(--local-muted)] hover:text-[var(--local-fg)] transition-colors flex items-center gap-1.5"
7518
+ >
7519
+ {data.cta.ghost.label}
7520
+ </a>
7521
+ </div>
7522
+ </div>
7523
+
7524
+ {/* Right: SVG illustration */}
7525
+ <div className="hidden md:flex items-center justify-center">
7526
+ <svg
7527
+ viewBox="0 0 400 400"
7528
+ fill="none"
7529
+ xmlns="http://www.w3.org/2000/svg"
7530
+ className="w-full max-w-md"
7531
+ >
7532
+ <defs>
7533
+ <linearGradient id="hero-main" x1="0" y1="0" x2="1" y2="1">
7534
+ <stop offset="0%" stopColor="#84ABFF"/>
7535
+ <stop offset="60%" stopColor="#1763FF"/>
7536
+ <stop offset="100%" stopColor="#0F52E0"/>
7537
+ </linearGradient>
7538
+ <linearGradient id="hero-accent" x1="0" y1="0" x2="0" y2="1">
7539
+ <stop offset="0%" stopColor="#EEF3FF"/>
7540
+ <stop offset="100%" stopColor="#84ABFF"/>
7541
+ </linearGradient>
7542
+ <linearGradient id="hero-glow" x1="0" y1="0" x2="0" y2="1">
7543
+ <stop offset="0%" stopColor="#1763FF" stopOpacity="0.3"/>
7544
+ <stop offset="100%" stopColor="#1763FF" stopOpacity="0"/>
7545
+ </linearGradient>
7546
+ <filter id="glow">
7547
+ <feGaussianBlur stdDeviation="8" result="blur"/>
7548
+ <feComposite in="SourceGraphic" in2="blur" operator="over"/>
7549
+ </filter>
7550
+ </defs>
7551
+ <circle cx="200" cy="200" r="160" fill="url(#hero-glow)" opacity="0.4"/>
7552
+ <rect x="90" y="90" width="220" height="220" rx="28" fill="none" stroke="url(#hero-main)" strokeWidth="14"/>
7553
+ {/* Left pins */}
7554
+ <line x1="16" y1="148" x2="90" y2="148" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7555
+ <line x1="16" y1="200" x2="90" y2="200" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7556
+ <line x1="16" y1="252" x2="90" y2="252" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7557
+ {/* Right pins */}
7558
+ <line x1="310" y1="148" x2="384" y2="148" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7559
+ <line x1="310" y1="200" x2="384" y2="200" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7560
+ <line x1="310" y1="252" x2="384" y2="252" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7561
+ {/* Top pins */}
7562
+ <line x1="148" y1="16" x2="148" y2="90" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7563
+ <line x1="200" y1="16" x2="200" y2="90" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7564
+ <line x1="252" y1="16" x2="252" y2="90" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7565
+ {/* Bottom pins */}
7566
+ <line x1="148" y1="310" x2="148" y2="384" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7567
+ <line x1="200" y1="310" x2="200" y2="384" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7568
+ <line x1="252" y1="310" x2="252" y2="384" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7569
+ {/* Corner nodes */}
7570
+ <circle cx="148" cy="148" r="13" fill="url(#hero-main)"/>
7571
+ <circle cx="252" cy="148" r="13" fill="url(#hero-main)"/>
7572
+ <circle cx="148" cy="252" r="13" fill="url(#hero-main)"/>
7573
+ <circle cx="252" cy="252" r="13" fill="url(#hero-main)"/>
7574
+ {/* Connection lines */}
7575
+ <line x1="148" y1="148" x2="200" y2="200" stroke="#84ABFF" strokeWidth="2.5" opacity="0.35"/>
7576
+ <line x1="252" y1="148" x2="200" y2="200" stroke="#84ABFF" strokeWidth="2.5" opacity="0.35"/>
7577
+ <line x1="148" y1="252" x2="200" y2="200" stroke="#84ABFF" strokeWidth="2.5" opacity="0.35"/>
7578
+ <line x1="252" y1="252" x2="200" y2="200" stroke="#84ABFF" strokeWidth="2.5" opacity="0.35"/>
7579
+ {/* Center node */}
7580
+ <circle cx="200" cy="200" r="18" fill="url(#hero-accent)" filter="url(#glow)"/>
7581
+ </svg>
7582
+ </div>
7583
+ </div>
7584
+ </section>
7585
+ );
7586
+ }
7587
+
7588
+ END_OF_FILE_CONTENT
7589
+ echo "Creating src/components/olon-hero/View_.tsx..."
7590
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-hero/View_.tsx"
7591
+ import type { OlonHeroData } from './types';
7592
+ import { Button } from '@/components/ui/button';
7593
+
7594
+ interface Props {
7595
+ data: OlonHeroData;
7596
+ }
7597
+
7598
+ export function OlonHeroView({ data }: Props) {
7599
+ return (
7600
+ <section
7601
+ style={{
7602
+ '--local-bg': 'var(--background)',
7603
+ '--local-fg': 'var(--foreground)',
7604
+ '--local-muted': 'var(--muted-foreground)',
7605
+ '--local-primary': 'var(--primary)',
7606
+ '--local-p300': 'var(--primary-light)',
7607
+ } as React.CSSProperties}
7608
+ className="min-h-screen bg-[var(--local-bg)] text-[var(--local-fg)] pt-36 pb-24"
7609
+ data-jp-section-id={data.id}
7610
+ data-jp-section-type="olon-hero"
7611
+ >
7612
+ <div className="max-w-6xl mx-auto px-8 grid grid-cols-1 md:grid-cols-2 gap-16 items-center">
7613
+ {/* Left: copy */}
7614
+ <div className="flex flex-col gap-6">
7615
+ <p className="text-xs font-semibold tracking-[0.12em] uppercase text-[var(--local-muted)]"
7616
+ data-jp-field="eyebrow">
7617
+ {data.eyebrow}
7618
+ </p>
7619
+
7620
+ <div>
7621
+ <h1 className="text-5xl md:text-6xl font-bold tracking-[-0.03em] leading-[1.05] text-white"
7622
+ data-jp-field="headline">
7623
+ {data.headline}
7624
+ </h1>
7625
+ <p className="text-4xl md:text-5xl font-semibold tracking-[-0.03em] leading-[1.1] text-[var(--local-p300)] italic mt-1"
7626
+ data-jp-field="subline">
7627
+ {data.subline}
7628
+ </p>
7629
+ </div>
7630
+
7631
+ <p className="text-base text-[var(--local-muted)] leading-relaxed max-w-lg"
7632
+ data-jp-field="body">
7633
+ {data.body}
7634
+ </p>
7635
+
7636
+ <div className="flex flex-wrap gap-3 items-center">
7637
+ <Button asChild size="lg" className="font-semibold">
7638
+ <a href={data.cta.primary.href}>{data.cta.primary.label} →</a>
7639
+ </Button>
7640
+ <Button asChild variant="outline" size="lg" className="font-semibold">
7641
+ <a href={data.cta.secondary.href}>{data.cta.secondary.label}</a>
7642
+ </Button>
7643
+ <a href={data.cta.ghost.href}
7644
+ className="text-sm text-[var(--local-muted)] hover:text-[var(--local-fg)] transition-colors flex items-center gap-1.5">
7645
+ {data.cta.ghost.label}
7646
+ </a>
7647
+ </div>
7648
+ </div>
7649
+
7650
+ {/* Right: SVG illustration */}
7651
+ <div className="hidden md:flex items-center justify-center">
7652
+ <svg viewBox="0 0 400 400" fill="none" xmlns="http://www.w3.org/2000/svg" className="w-full max-w-md">
7653
+ <defs>
7654
+ <linearGradient id="hero-main" x1="0" y1="0" x2="1" y2="1">
7655
+ <stop offset="0%" stopColor="#84ABFF"/>
7656
+ <stop offset="60%" stopColor="#1763FF"/>
7657
+ <stop offset="100%" stopColor="#0F52E0"/>
7658
+ </linearGradient>
7659
+ <linearGradient id="hero-accent" x1="0" y1="0" x2="0" y2="1">
7660
+ <stop offset="0%" stopColor="#EEF3FF"/>
7661
+ <stop offset="100%" stopColor="#84ABFF"/>
7662
+ </linearGradient>
7663
+ <linearGradient id="hero-glow" x1="0" y1="0" x2="0" y2="1">
7664
+ <stop offset="0%" stopColor="#1763FF" stopOpacity="0.3"/>
7665
+ <stop offset="100%" stopColor="#1763FF" stopOpacity="0"/>
7666
+ </linearGradient>
7667
+ <filter id="glow"><feGaussianBlur stdDeviation="8" result="blur"/><feComposite in="SourceGraphic" in2="blur" operator="over"/></filter>
7668
+ </defs>
7669
+ <circle cx="200" cy="200" r="160" fill="url(#hero-glow)" opacity="0.4"/>
7670
+ <rect x="90" y="90" width="220" height="220" rx="28" fill="none" stroke="url(#hero-main)" strokeWidth="14"/>
7671
+ <line x1="16" y1="148" x2="90" y2="148" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7672
+ <line x1="16" y1="200" x2="90" y2="200" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7673
+ <line x1="16" y1="252" x2="90" y2="252" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7674
+ <line x1="310" y1="148" x2="384" y2="148" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7675
+ <line x1="310" y1="200" x2="384" y2="200" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7676
+ <line x1="310" y1="252" x2="384" y2="252" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7677
+ <line x1="148" y1="16" x2="148" y2="90" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7678
+ <line x1="200" y1="16" x2="200" y2="90" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7679
+ <line x1="252" y1="16" x2="252" y2="90" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7680
+ <line x1="148" y1="310" x2="148" y2="384" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7681
+ <line x1="200" y1="310" x2="200" y2="384" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7682
+ <line x1="252" y1="310" x2="252" y2="384" stroke="url(#hero-main)" strokeWidth="10" strokeLinecap="round"/>
7683
+ <circle cx="148" cy="148" r="13" fill="url(#hero-main)"/>
7684
+ <circle cx="252" cy="148" r="13" fill="url(#hero-main)"/>
7685
+ <circle cx="148" cy="252" r="13" fill="url(#hero-main)"/>
7686
+ <circle cx="252" cy="252" r="13" fill="url(#hero-main)"/>
7687
+ <line x1="148" y1="148" x2="200" y2="200" stroke="#84ABFF" strokeWidth="2.5" opacity="0.35"/>
7688
+ <line x1="252" y1="148" x2="200" y2="200" stroke="#84ABFF" strokeWidth="2.5" opacity="0.35"/>
7689
+ <line x1="148" y1="252" x2="200" y2="200" stroke="#84ABFF" strokeWidth="2.5" opacity="0.35"/>
7690
+ <line x1="252" y1="252" x2="200" y2="200" stroke="#84ABFF" strokeWidth="2.5" opacity="0.35"/>
7691
+ <circle cx="200" cy="200" r="18" fill="url(#hero-accent)" filter="url(#glow)"/>
7692
+ </svg>
7693
+ </div>
7694
+ </div>
7695
+ </section>
7696
+ );
7697
+ }
7698
+
7699
+ END_OF_FILE_CONTENT
7700
+ echo "Creating src/components/olon-hero/index.ts..."
7701
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-hero/index.ts"
7702
+ export { OlonHeroView as View } from './View';
7703
+ export { OlonHeroSchema } from './schema';
7704
+ export type { OlonHeroData } from './types';
7705
+
7706
+ END_OF_FILE_CONTENT
7707
+ echo "Creating src/components/olon-hero/schema.ts..."
7708
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-hero/schema.ts"
7709
+ import { z } from 'zod';
7710
+ import { BaseSectionData } from '@/lib/base-schemas';
7711
+
7712
+ export const OlonHeroSchema = BaseSectionData.extend({
7713
+ eyebrow: z.string().default('CONTRACT LAYER · V1.5 · OPEN CORE'),
7714
+ headline: z.string().default('Contract Layer'),
7715
+ subline: z.string().default('for the agentic web.'),
7716
+ body: z.string().default(''),
7717
+ cta: z.object({
7718
+ primary: z.object({ label: z.string(), href: z.string() }),
7719
+ secondary: z.object({ label: z.string(), href: z.string() }),
7720
+ ghost: z.object({ label: z.string(), href: z.string() }),
7721
+ }),
7722
+ });
7723
+
7724
+ export type OlonHeroData = z.infer<typeof OlonHeroSchema>;
7725
+
7726
+ END_OF_FILE_CONTENT
7727
+ echo "Creating src/components/olon-hero/types.ts..."
7728
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-hero/types.ts"
7729
+ export type { OlonHeroData } from './schema';
7730
+
7731
+ END_OF_FILE_CONTENT
7732
+ mkdir -p "src/components/olon-why"
7733
+ echo "Creating src/components/olon-why/View.tsx..."
7734
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-why/View.tsx"
7735
+ import type { OlonWhyData } from './types';
7736
+
7737
+ const ICONS = {
7738
+ contract: (
7739
+ <svg width="36" height="36" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
7740
+ <defs>
7741
+ <linearGradient id="w1" x1="0" y1="0" x2="1" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient>
7742
+ </defs>
7743
+ <rect x="20" y="20" width="160" height="160" rx="16" fill="none" stroke="url(#w1)" strokeWidth="10"/>
7744
+ <line x1="20" y1="70" x2="180" y2="70" stroke="url(#w1)" strokeWidth="7"/>
7745
+ <rect x="40" y="100" width="60" height="8" rx="4" fill="url(#w1)" opacity="0.4"/>
7746
+ <rect x="40" y="118" width="90" height="8" rx="4" fill="url(#w1)" opacity="0.7"/>
7747
+ <rect x="40" y="136" width="72" height="8" rx="4" fill="url(#w1)" opacity="0.5"/>
7748
+ </svg>
7749
+ ),
7750
+ holon: (
7751
+ <svg width="36" height="36" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
7752
+ <defs>
7753
+ <linearGradient id="w2" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient>
7754
+ <linearGradient id="w2a" x1="0" y1="0" x2="0" y2="1"><stop offset="0" stopColor="#EEF3FF"/><stop offset="1" stopColor="#84ABFF"/></linearGradient>
7755
+ </defs>
7756
+ <circle cx="100" cy="100" r="75" fill="none" stroke="url(#w2)" strokeWidth="10"/>
7757
+ <circle cx="100" cy="100" r="28" fill="url(#w2a)"/>
7758
+ </svg>
7759
+ ),
7760
+ generated: (
7761
+ <svg width="36" height="36" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
7762
+ <defs>
7763
+ <linearGradient id="w3" x1="0" y1="0" x2="1" y2="1"><stop offset="0" stopColor="#84ABFF"/><stop offset="1" stopColor="#0F52E0"/></linearGradient>
7764
+ </defs>
7765
+ <circle cx="100" cy="40" r="14" fill="url(#w3)"/>
7766
+ <circle cx="50" cy="110" r="12" fill="url(#w3)" opacity="0.6"/>
7767
+ <circle cx="150" cy="110" r="12" fill="url(#w3)" opacity="0.6"/>
7768
+ <circle cx="80" cy="175" r="10" fill="url(#w3)" opacity="0.35"/>
7769
+ <circle cx="130" cy="175" r="14" fill="url(#w3)"/>
7770
+ <line x1="100" y1="54" x2="54" y2="98" stroke="url(#w3)" strokeWidth="5" strokeLinecap="round"/>
7771
+ <line x1="100" y1="54" x2="146" y2="98" stroke="url(#w3)" strokeWidth="5" strokeLinecap="round" opacity="0.4"/>
7772
+ <line x1="54" y1="122" x2="82" y2="165" stroke="url(#w3)" strokeWidth="4" strokeLinecap="round" opacity="0.35"/>
7773
+ <line x1="146" y1="122" x2="128" y2="165" stroke="url(#w3)" strokeWidth="5" strokeLinecap="round"/>
7774
+ </svg>
7775
+ ),
7776
+ };
7777
+
7778
+ interface Props { data: OlonWhyData; }
7779
+
7780
+ export function OlonWhyView({ data }: Props) {
7781
+ return (
7782
+ <section
7783
+ style={{
7784
+ '--local-bg': 'var(--background)',
7785
+ '--local-fg': 'var(--foreground)',
7786
+ '--local-muted': 'var(--muted-foreground)',
7787
+ '--local-p300': 'var(--primary-light)',
7788
+ '--local-card': 'var(--card)',
7789
+ '--local-border':'var(--border)',
7790
+ } as React.CSSProperties}
7791
+ className="bg-[var(--local-bg)] text-[var(--local-fg)] py-24 border-t border-[var(--local-border)]"
7792
+ data-jp-section-id={data.id}
7793
+ data-jp-section-type="olon-why"
7794
+ >
7795
+ <div className="max-w-6xl mx-auto px-8">
7796
+ <p className="text-xs font-semibold tracking-[0.12em] uppercase text-[var(--local-muted)] mb-3"
7797
+ data-jp-field="label">{data.label}</p>
7798
+ <h2 className="text-4xl font-bold tracking-[-0.03em] text-white leading-tight"
7799
+ data-jp-field="headline">{data.headline}</h2>
7800
+ <p className="text-3xl font-semibold tracking-[-0.03em] text-[var(--local-p300)] leading-tight mb-4"
7801
+ data-jp-field="subline">{data.subline}</p>
7802
+ <p className="text-base text-[var(--local-muted)] leading-relaxed max-w-2xl mb-12"
7803
+ data-jp-field="body">{data.body}</p>
7804
+
7805
+ <div className="grid grid-cols-1 md:grid-cols-3 border border-[var(--local-border)] rounded-2xl overflow-hidden"
7806
+ data-jp-array="pillars">
7807
+ {data.pillars.map((pillar) => (
7808
+ <div key={pillar.id}
7809
+ className="bg-[var(--local-card)] p-8 flex flex-col gap-4 border-r last:border-r-0 border-[var(--local-border)]"
7810
+ data-jp-item-id={pillar.id}>
7811
+ <div>{ICONS[pillar.icon]}</div>
7812
+ <div className="font-bold text-white" data-jp-field="title">{pillar.title}</div>
7813
+ <div className="text-sm text-[var(--local-muted)] leading-relaxed" data-jp-field="body">{pillar.body}</div>
7814
+ </div>
7815
+ ))}
7816
+ </div>
7817
+ </div>
7818
+ </section>
7819
+ );
7820
+ }
7821
+
7822
+ END_OF_FILE_CONTENT
7823
+ echo "Creating src/components/olon-why/index.ts..."
7824
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-why/index.ts"
7825
+ export { OlonWhyView as View } from './View';
7826
+ export { OlonWhySchema } from './schema';
7827
+ export type { OlonWhyData } from './types';
7828
+
7829
+ END_OF_FILE_CONTENT
7830
+ echo "Creating src/components/olon-why/schema.ts..."
7831
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-why/schema.ts"
7832
+ import { z } from 'zod';
7833
+ import { BaseSectionData, BaseArrayItem } from '@/lib/base-schemas';
7834
+
7835
+ export const PillarSchema = BaseArrayItem.extend({
7836
+ title: z.string(),
7837
+ body: z.string(),
7838
+ icon: z.enum(['contract', 'holon', 'generated']),
7839
+ });
7840
+
7841
+ export const OlonWhySchema = BaseSectionData.extend({
7842
+ label: z.string().default('Why OlonJS'),
7843
+ headline: z.string().default('A Meaningful Web'),
7844
+ subline: z.string().default('Whole in itself, part of something greater.'),
7845
+ body: z.string().default(''),
7846
+ pillars: z.array(PillarSchema).min(1).max(3),
7847
+ });
7848
+
7849
+ export type OlonWhyData = z.infer<typeof OlonWhySchema>;
7850
+
7851
+ END_OF_FILE_CONTENT
7852
+ echo "Creating src/components/olon-why/types.ts..."
7853
+ cat << 'END_OF_FILE_CONTENT' > "src/components/olon-why/types.ts"
7854
+ export type { OlonWhyData } from './schema';
7855
+
6810
7856
  END_OF_FILE_CONTENT
6811
7857
  mkdir -p "src/components/page-hero"
6812
7858
  echo "Creating src/components/page-hero/View.tsx..."
@@ -10053,8 +11099,37 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/config/menu.json"
10053
11099
  {
10054
11100
  "main": [
10055
11101
  {
10056
- "label": "Platform",
10057
- "href": "/platform",
11102
+ "label": "Why",
11103
+ "href": "#Why"
11104
+
11105
+ },
11106
+ {
11107
+ "label": "Architecture",
11108
+ "href": "#Architecture"
11109
+ },
11110
+ {
11111
+ "label": "Example",
11112
+ "href": "#Example"
11113
+ },
11114
+ {
11115
+ "label": "Get started",
11116
+ "href": "#Getstarted"
11117
+ },
11118
+ {
11119
+ "label": "GitHub",
11120
+ "href": "https://github.com/olonjs/core"
11121
+ }
11122
+ ]
11123
+ }
11124
+ END_OF_FILE_CONTENT
11125
+ # SKIP: src/data/config/menu.json:Zone.Identifier is binary and cannot be embedded as text.
11126
+ echo "Creating src/data/config/menu_example_for_schema.json..."
11127
+ cat << 'END_OF_FILE_CONTENT' > "src/data/config/menu_example_for_schema.json"
11128
+ {
11129
+ "main": [
11130
+ {
11131
+ "label": "Why",
11132
+ "href": "/why",
10058
11133
  "children": [
10059
11134
  {
10060
11135
  "label": "Overview",
@@ -10093,7 +11168,6 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/config/menu.json"
10093
11168
  ]
10094
11169
  }
10095
11170
  END_OF_FILE_CONTENT
10096
- # SKIP: src/data/config/menu.json:Zone.Identifier is binary and cannot be embedded as text.
10097
11171
  echo "Creating src/data/config/site.json..."
10098
11172
  cat << 'END_OF_FILE_CONTENT' > "src/data/config/site.json"
10099
11173
  {
@@ -10116,36 +11190,47 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/config/site.json"
10116
11190
  "type": "header",
10117
11191
  "data": {
10118
11192
  "logoText": "Olon",
10119
- "badge": "",
10120
- "links": {
10121
- "$ref": "../config/menu.json#/main"
10122
- },
10123
- "ctaLabel": "Get started →",
10124
- "ctaHref": "#contact",
10125
- "signinHref": "#login"
11193
+ "badge": "JS",
11194
+ "links": [
11195
+ {
11196
+ "label": "Why",
11197
+ "href": "#Why"
11198
+ },
11199
+ {
11200
+ "label": "Architecture",
11201
+ "href": "#Architecture"
11202
+ },
11203
+ {
11204
+ "label": "Example",
11205
+ "href": "#Example"
11206
+ },
11207
+ {
11208
+ "label": "Get started",
11209
+ "href": "#Getstarted"
11210
+ },
11211
+ {
11212
+ "label": "GitHub",
11213
+ "href": "https://github.com/olonjs/core"
11214
+ }
11215
+ ],
11216
+ "ctaLabel": "",
11217
+ "ctaHref": "",
11218
+ "signinHref": ""
10126
11219
  }
10127
11220
  },
10128
11221
  "footer": {
10129
11222
  "id": "global-footer",
10130
11223
  "type": "footer",
10131
11224
  "data": {
10132
- "brandText": "Olon",
10133
- "copyright": "© 2025 OlonJS · v1.4 · Holon",
11225
+ "brandText": "OlonJS",
11226
+ "copyright": "© 2026 OlonJS · v1.5 · Guido Serio",
10134
11227
  "links": [
10135
11228
  {
10136
11229
  "label": "GitHub",
10137
- "href": "#"
10138
- },
10139
- {
10140
- "label": "Privacy",
10141
- "href": "#"
10142
- },
10143
- {
10144
- "label": "Terms",
10145
- "href": "#"
11230
+ "href": "https://github.com/olonjs/core"
10146
11231
  }
10147
11232
  ],
10148
- "designSystemHref": "/design-system"
11233
+ "designSystemHref": ""
10149
11234
  },
10150
11235
  "settings": {
10151
11236
  "showLogo": true
@@ -10160,168 +11245,162 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/config/theme.json"
10160
11245
  "name": "Olon",
10161
11246
  "tokens": {
10162
11247
  "colors": {
10163
- "background": "#0B0907",
10164
- "card": "#130F0D",
10165
- "elevated": "#1E1814",
10166
- "overlay": "#241D17",
10167
- "popover": "#1A1410",
10168
- "popover-foreground": "#F2EDE6",
10169
- "foreground": "#F2EDE6",
10170
- "card-foreground": "#F2EDE6",
10171
- "muted-foreground": "#9A8D80",
10172
- "placeholder": "#5C5248",
10173
- "primary": "#5B3F9A",
10174
- "primary-foreground": "#EDE8F8",
10175
- "primary-light": "#B8A4E0",
10176
- "primary-dark": "#3D2770",
10177
- "primary-50": "#EDE8F8",
10178
- "primary-100": "#CEC1F0",
10179
- "primary-200": "#B8A4E0",
10180
- "primary-300": "#A48ED5",
10181
- "primary-400": "#8B6FC6",
10182
- "primary-500": "#7254B0",
10183
- "primary-600": "#5B3F9A",
10184
- "primary-700": "#4C3482",
10185
- "primary-800": "#3D2770",
10186
- "primary-900": "#271852",
10187
- "accent": "#E2D5B0",
10188
- "accent-foreground": "#0B0907",
10189
- "secondary": "#1E1814",
10190
- "secondary-foreground": "#F2EDE6",
10191
- "muted": "#1E1814",
10192
- "border": "#2E271F",
10193
- "border-strong": "#4A3D30",
10194
- "input": "#2E271F",
10195
- "ring": "#5B3F9A",
10196
- "destructive": "#7F1D1D",
10197
- "destructive-foreground": "#FCA5A5",
10198
- "destructive-border": "#991B1B",
10199
- "destructive-ring": "#EF4444",
10200
- "success": "#14532D",
10201
- "success-foreground": "#86EFAC",
10202
- "success-border": "#166534",
10203
- "success-indicator": "#22C55E",
10204
- "warning": "#78350F",
10205
- "warning-foreground": "#FCD34D",
10206
- "warning-border": "#92400E",
10207
- "info": "#1E3A5F",
10208
- "info-foreground": "#93C5FD",
10209
- "info-border": "#1E40AF"
11248
+ "background": "hsl(215 28% 7%)",
11249
+ "card": "hsl(218 44% 9%)",
11250
+ "elevated": "#141B24",
11251
+ "overlay": "#1C2433",
11252
+ "popover": "hsl(218 44% 9%)",
11253
+ "popover-foreground": "hsl(214 33% 84%)",
11254
+ "foreground": "hsl(214 33% 84%)",
11255
+ "card-foreground": "hsl(214 33% 84%)",
11256
+ "muted-foreground": "hsl(215 23% 57%)",
11257
+ "placeholder": "#4A5C78",
11258
+ "primary": "hsl(222 100% 54%)",
11259
+ "primary-foreground": "hsl(0 0% 100%)",
11260
+ "primary-light": "#84ABFF",
11261
+ "primary-dark": "#0F52E0",
11262
+ "primary-50": "#EEF3FF",
11263
+ "primary-100": "#D6E4FF",
11264
+ "primary-200": "#ADC8FF",
11265
+ "primary-300": "#84ABFF",
11266
+ "primary-400": "#5B8EFF",
11267
+ "primary-500": "#1763FF",
11268
+ "primary-600": "#0F52E0",
11269
+ "primary-700": "#0940B8",
11270
+ "primary-800": "#063090",
11271
+ "primary-900": "#031E68",
11272
+ "accent": "hsl(216 28% 15%)",
11273
+ "accent-foreground": "hsl(214 33% 84%)",
11274
+ "secondary": "hsl(217 30% 11%)",
11275
+ "secondary-foreground": "hsl(214 33% 84%)",
11276
+ "muted": "hsl(217 30% 11%)",
11277
+ "border": "hsl(216 27% 21%)",
11278
+ "border-strong": "#2F3D55",
11279
+ "input": "hsl(216 27% 21%)",
11280
+ "ring": "hsl(222 100% 54%)",
11281
+ "destructive": "hsl(0 40% 46%)",
11282
+ "destructive-foreground": "hsl(210 58% 93%)",
11283
+ "destructive-border": "#7F2626",
11284
+ "destructive-ring": "#E06060",
11285
+ "success": "hsl(152 83% 26%)",
11286
+ "success-foreground": "hsl(210 58% 93%)",
11287
+ "success-border": "#1DB87A",
11288
+ "success-indicator": "#1DB87A",
11289
+ "warning": "hsl(46 100% 21%)",
11290
+ "warning-foreground": "hsl(210 58% 93%)",
11291
+ "warning-border": "#C49A00",
11292
+ "info": "hsl(214 100% 40%)",
11293
+ "info-foreground": "hsl(210 58% 93%)",
11294
+ "info-border": "#4D9FE0"
10210
11295
  },
10211
11296
  "modes": {
10212
11297
  "light": {
10213
11298
  "colors": {
10214
- "background": "#F2EDE6",
10215
- "card": "#FFFFFF",
10216
- "elevated": "#F5F2EE",
10217
- "overlay": "#EDE9E3",
10218
- "popover": "#FFFFFF",
10219
- "popover-foreground": "#1A1410",
10220
- "foreground": "#1A1410",
10221
- "card-foreground": "#1A1410",
10222
- "muted-foreground": "#6B6058",
10223
- "placeholder": "#A89E96",
10224
- "primary": "#5B3F9A",
10225
- "primary-foreground": "#FAFAF8",
10226
- "primary-light": "#7254B0",
10227
- "primary-dark": "#3D2770",
10228
- "primary-50": "#EDE8F8",
10229
- "primary-100": "#CEC1F0",
10230
- "primary-200": "#B8A4E0",
10231
- "primary-300": "#A48ED5",
10232
- "primary-400": "#8B6FC6",
10233
- "primary-500": "#7254B0",
10234
- "primary-600": "#5B3F9A",
10235
- "primary-700": "#4C3482",
10236
- "primary-800": "#3D2770",
10237
- "primary-900": "#271852",
10238
- "accent": "#2E271F",
10239
- "accent-foreground": "#FFFFFF",
10240
- "secondary": "#F5F2EE",
10241
- "secondary-foreground": "#1A1410",
10242
- "muted": "#F5F2EE",
10243
- "border": "#DDD8D2",
10244
- "border-strong": "#C4BEB8",
10245
- "input": "#DDD8D2",
10246
- "ring": "#5B3F9A",
10247
- "destructive": "#FEF2F2",
10248
- "destructive-foreground": "#991B1B",
11299
+ "background": "hsl(0 0% 96%)",
11300
+ "card": "hsl(0 0% 100%)",
11301
+ "elevated": "#F4F3EF",
11302
+ "overlay": "#E5E3DC",
11303
+ "popover": "hsl(0 0% 100%)",
11304
+ "popover-foreground": "hsl(0 0% 3%)",
11305
+ "foreground": "hsl(0 0% 3%)",
11306
+ "card-foreground": "hsl(0 0% 3%)",
11307
+ "muted-foreground": "hsl(0 0% 42%)",
11308
+ "placeholder": "#B4B2AD",
11309
+ "primary": "hsl(222 100% 54%)",
11310
+ "primary-foreground": "hsl(0 0% 100%)",
11311
+ "primary-light": "#5B8EFF",
11312
+ "primary-dark": "#0F52E0",
11313
+ "primary-50": "#EEF3FF",
11314
+ "primary-100": "#D6E4FF",
11315
+ "primary-200": "#ADC8FF",
11316
+ "primary-300": "#84ABFF",
11317
+ "primary-400": "#5B8EFF",
11318
+ "primary-500": "#1763FF",
11319
+ "primary-600": "#0F52E0",
11320
+ "primary-700": "#0940B8",
11321
+ "primary-800": "#063090",
11322
+ "primary-900": "#031E68",
11323
+ "accent": "hsl(222 100% 92%)",
11324
+ "accent-foreground": "hsl(222 100% 54%)",
11325
+ "secondary": "hsl(0 0% 92%)",
11326
+ "secondary-foreground": "hsl(0 0% 3%)",
11327
+ "muted": "hsl(0 0% 92%)",
11328
+ "border": "hsl(0 0% 84%)",
11329
+ "border-strong": "#B4B2AD",
11330
+ "input": "hsl(0 0% 84%)",
11331
+ "ring": "hsl(222 100% 54%)",
11332
+ "destructive": "hsl(0 72% 51%)",
11333
+ "destructive-foreground": "hsl(0 0% 100%)",
10249
11334
  "destructive-border": "#FECACA",
10250
11335
  "destructive-ring": "#EF4444",
10251
- "success": "#F0FDF4",
10252
- "success-foreground": "#166534",
10253
- "success-border": "#BBF7D0",
10254
- "success-indicator": "#16A34A",
10255
- "warning": "#FFFBEB",
10256
- "warning-foreground": "#92400E",
10257
- "warning-border": "#FDE68A",
10258
- "info": "#EFF6FF",
10259
- "info-foreground": "#1E40AF",
10260
- "info-border": "#BFDBFE"
11336
+ "success": "hsl(160 84% 39%)",
11337
+ "success-foreground": "hsl(0 0% 100%)",
11338
+ "success-border": "#D4F0E2",
11339
+ "success-indicator": "#0A7C4E",
11340
+ "warning": "hsl(38 92% 50%)",
11341
+ "warning-foreground": "hsl(0 0% 3%)",
11342
+ "warning-border": "#F5EAD4",
11343
+ "info": "hsl(222 100% 54%)",
11344
+ "info-foreground": "hsl(0 0% 100%)",
11345
+ "info-border": "#D4E5F5"
10261
11346
  }
10262
11347
  }
10263
11348
  },
10264
11349
  "typography": {
10265
11350
  "fontFamily": {
10266
- "primary": "'Geist', 'Geist Fallback', system-ui, sans-serif",
10267
- "mono": "'Geist Mono', 'Geist Mono Fallback', monospace",
10268
- "display": "'Merriweather Variable', Georgia, serif"
11351
+ "primary": "\"Instrument Sans\", Helvetica, Arial, sans-serif",
11352
+ "mono": "\"JetBrains Mono\", \"Fira Code\", monospace",
11353
+ "display": "\"Instrument Sans\", Helvetica, Arial, sans-serif"
10269
11354
  },
10270
11355
  "wordmark": {
10271
- "fontFamily": "'Merriweather Variable', sans-serif",
10272
- "weight": "500",
10273
- "width": "112"
11356
+ "fontFamily": "\"Instrument Sans\", Helvetica, Arial, sans-serif",
11357
+ "weight": "700"
10274
11358
  },
10275
11359
  "scale": {
10276
- "xs": "11px",
10277
- "sm": "13px",
11360
+ "xs": "0.75rem",
11361
+ "sm": "0.875rem",
10278
11362
  "base": "1rem",
10279
- "md": "1.125rem",
10280
- "lg": "1.25rem",
10281
- "xl": "1.5rem",
10282
- "2xl": "1.625rem",
10283
- "3xl": "1.75rem",
10284
- "4xl": "2rem",
10285
- "5xl": "2.5rem",
11363
+ "lg": "1.125rem",
11364
+ "xl": "1.25rem",
11365
+ "2xl": "1.5rem",
11366
+ "3xl": "1.875rem",
11367
+ "4xl": "2.25rem",
11368
+ "5xl": "3rem",
10286
11369
  "6xl": "3rem",
10287
11370
  "7xl": "4.5rem"
10288
11371
  },
10289
11372
  "tracking": {
10290
- "tight": "-0.03em",
10291
- "display": "-0.035em",
11373
+ "tight": "-0.04em",
10292
11374
  "normal": "0em",
10293
11375
  "wide": "0.04em",
10294
- "label": "0.12em"
11376
+ "widest": "0.14em"
10295
11377
  },
10296
11378
  "leading": {
10297
- "none": "1",
10298
11379
  "tight": "1.2",
10299
- "snug": "1.35",
10300
- "normal": "1.65",
10301
- "relaxed": "1.75"
11380
+ "normal": "1.5",
11381
+ "relaxed": "1.7"
10302
11382
  }
10303
11383
  },
10304
11384
  "borderRadius": {
10305
- "xl": "16px",
10306
- "lg": "12px",
10307
- "md": "8px",
10308
- "sm": "4px",
11385
+ "xl": "1rem",
11386
+ "lg": "0.75rem",
11387
+ "md": "0.5rem",
11388
+ "sm": "0.25rem",
10309
11389
  "full": "9999px"
10310
11390
  },
10311
11391
  "spacing": {
10312
- "container-max": "1152px",
10313
- "section-y": "96px",
10314
- "header-h": "56px",
10315
- "sidebar-w": "240px"
11392
+ "container-max": "72rem",
11393
+ "section-y": "4rem",
11394
+ "header-h": "4rem"
10316
11395
  },
10317
11396
  "zIndex": {
10318
11397
  "base": "0",
10319
11398
  "elevated": "10",
10320
- "dropdown": "100",
10321
- "sticky": "200",
10322
- "overlay": "300",
10323
- "modal": "400",
10324
- "toast": "500"
11399
+ "dropdown": "20",
11400
+ "sticky": "40",
11401
+ "overlay": "50",
11402
+ "modal": "60",
11403
+ "toast": "100"
10325
11404
  }
10326
11405
  }
10327
11406
  }
@@ -10350,7 +11429,6 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/design-system.json"
10350
11429
  "global-header": false
10351
11430
  }
10352
11431
  END_OF_FILE_CONTENT
10353
- # SKIP: src/data/pages/design-system.json:Zone.Identifier is binary and cannot be embedded as text.
10354
11432
  echo "Creating src/data/pages/docs.json..."
10355
11433
  cat << 'END_OF_FILE_CONTENT' > "src/data/pages/docs.json"
10356
11434
  {
@@ -10375,6 +11453,215 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/docs.json"
10375
11453
  END_OF_FILE_CONTENT
10376
11454
  echo "Creating src/data/pages/home.json..."
10377
11455
  cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
11456
+ {
11457
+ "id": "home-page",
11458
+ "slug": "home",
11459
+ "meta": {
11460
+ "title": "OlonJS — Contract Layer for the Agentic Web",
11461
+ "description": "OlonJS is a TypeScript framework for building JSON-driven websites with a deterministic data contract. Every section is typed, validated, and structurally addressable."
11462
+ },
11463
+ "sections": [
11464
+ {
11465
+ "id": "hero-main",
11466
+ "type": "olon-hero",
11467
+ "data": {
11468
+ "id": "hero-main",
11469
+ "eyebrow": "CONTRACT LAYER · V1.5 · OPEN CORE",
11470
+ "headline": "Contract Layer",
11471
+ "subline": "for the agentic web.",
11472
+ "body": "AI agents are becoming operational actors in commerce, marketing, and support. They need more than content — they need a contract. OlonJS is the deterministic machine contract for websites: every site typed, structured, and addressable by design. No custom glue. No fragile integrations. Just a contract any agent can read and operate.",
11473
+ "cta": {
11474
+ "primary": {
11475
+ "label": "Get started",
11476
+ "href": "#Getstarted"
11477
+ },
11478
+ "secondary": {
11479
+ "label": "GitHub",
11480
+ "href": "https://github.com/olonjs/core"
11481
+ },
11482
+ "ghost": {
11483
+ "label": "Explore platform",
11484
+ "href": "#architecture"
11485
+ }
11486
+ }
11487
+ }
11488
+ },
11489
+ {
11490
+ "id": "why-olon",
11491
+ "type": "olon-why",
11492
+ "data": {
11493
+ "id": "why-olon",
11494
+ "label": "Why OlonJS",
11495
+ "headline": "A Meaningful Web",
11496
+ "subline": "Whole in itself, part of something greater.",
11497
+ "body": "Most web frameworks separate concerns across layers — data, UI, validation, metadata — with no shared contract between them. OlonJS inverts this: the JSON data structure is the contract. Every layer — rendering, editing, validation, machine access — is a deterministic projection of the same typed source. The result is a site that is structurally coherent by construction, not by convention. Every site built with OlonJS is a holon: complete in itself, intelligible to the network around it. The meaningful web doesn't happen all at once. It grows one site at a time.",
11498
+ "pillars": [
11499
+ {
11500
+ "id": "pillar-contract",
11501
+ "icon": "contract",
11502
+ "title": "The data is the contract",
11503
+ "body": "One typed JSON source. Every layer — UI, editor, agent, SEO — is a projection. No translation, no drift."
11504
+ },
11505
+ {
11506
+ "id": "pillar-holon",
11507
+ "icon": "holon",
11508
+ "title": "Every site is a holon",
11509
+ "body": "Autonomous, complete, structurally intelligible. Each site is whole in itself and part of a network that understands it."
11510
+ },
11511
+ {
11512
+ "id": "pillar-generated",
11513
+ "icon": "generated",
11514
+ "title": "Built to be generated",
11515
+ "body": "Every constraint is also an instruction. The spec is precise enough for AI agents to scaffold a fully compliant tenant from scratch."
11516
+ }
11517
+ ],
11518
+ "anchorId": "Why"
11519
+ }
11520
+ },
11521
+ {
11522
+ "id": "architecture-protocols",
11523
+ "type": "olon-architecture",
11524
+ "data": {
11525
+ "id": "architecture-protocols",
11526
+ "label": "Architecture",
11527
+ "headline": "Six governing protocols.",
11528
+ "body": "OlonJS is specified as a versioned set of architectural protocols. Each protocol is independently versioned and mandatory for compliant tenants.",
11529
+ "specHref": "https://github.com/olonjs/core/blob/main/specs/olonjsSpecs_V_1_5.md",
11530
+ "protocols": [
11531
+ {
11532
+ "id": "proto-mtrp",
11533
+ "icon": "mtrp",
11534
+ "acronym": "MTRP",
11535
+ "version": "v1.2",
11536
+ "name": "Modular Type Registry",
11537
+ "desc": "Core exports an empty SectionDataRegistry. Tenants extend it via module augmentation. Full TypeScript inference across all section types at compile-time, zero Core changes.",
11538
+ "specHref": "https://github.com/olonjs/core/blob/main/specs/olonjsSpecs_V_1_5.md#1--modular-type-registry-pattern-mtrp-v12"
11539
+ },
11540
+ {
11541
+ "id": "proto-tbp",
11542
+ "icon": "tbp",
11543
+ "acronym": "TBP",
11544
+ "version": "v1.0",
11545
+ "name": "Tenant Block Protocol",
11546
+ "desc": "Each section type is a self-contained capsule: View.tsx, schema.ts, types.ts, index.ts. Renderable, validatable, and ingestible by the engine without additional configuration.",
11547
+ "specHref": "https://github.com/olonjs/core/blob/main/specs/olonjsSpecs_V_1_5.md#3--tenant-block-protocol-tbp-v10"
11548
+ },
11549
+ {
11550
+ "id": "proto-jsp",
11551
+ "icon": "jsp",
11552
+ "acronym": "JSP",
11553
+ "version": "v1.8",
11554
+ "name": "JsonPages Site Protocol",
11555
+ "desc": "Deterministic file system ontology and CLI projection engine. config/ separates global governance from per-page content. Reproducible across every environment.",
11556
+ "specHref": "https://github.com/olonjs/core/blob/main/specs/olonjsSpecs_V_1_5.md#2--jsonpages-site-protocol-jsp-v18"
11557
+ },
11558
+ {
11559
+ "id": "proto-idac",
11560
+ "icon": "idac",
11561
+ "acronym": "IDAC",
11562
+ "version": "v1.0",
11563
+ "name": "ICE Data Contract",
11564
+ "desc": "Mandatory data-jp-* DOM attributes bind every section to its data. Any consumer that can traverse the DOM can identify and operate any content node — human or agent.",
11565
+ "specHref": "https://github.com/olonjs/core/blob/main/specs/olonjsSpecs_V_1_5.md"
11566
+ },
11567
+ {
11568
+ "id": "proto-bsds",
11569
+ "icon": "bsds",
11570
+ "acronym": "BSDS",
11571
+ "version": "v1.0",
11572
+ "name": "Base Schema Fragments",
11573
+ "desc": "BaseSectionData and BaseArrayItem enforce anchor IDs and stable React keys across all capsules. The foundation that doesn't move so your content never drifts.",
11574
+ "specHref": "https://github.com/olonjs/core/blob/main/specs/olonjsSpecs_V_1_5.md"
11575
+ },
11576
+ {
11577
+ "id": "proto-pss",
11578
+ "icon": "pss",
11579
+ "acronym": "PSS",
11580
+ "version": "v1.4",
11581
+ "name": "Path-Based Selection",
11582
+ "desc": "Every node has an address. Content selection uses strict root-to-leaf path semantics — unambiguous, stable, operable by any consumer that knows the contract.",
11583
+ "specHref": "https://github.com/olonjs/core/blob/main/specs/olonjsSpecs_V_1_5.md"
11584
+ }
11585
+ ],
11586
+ "anchorId": "Architecture"
11587
+ }
11588
+ },
11589
+ {
11590
+ "id": "example-steps",
11591
+ "type": "olon-example",
11592
+ "data": {
11593
+ "id": "example-steps",
11594
+ "label": "Quick Example",
11595
+ "headline": "Two steps. One contract.",
11596
+ "body": "Scaffold a fully compliant tenant in under three minutes. Then read any page via the OlonJS protocol — from a browser, a script, or an AI agent.",
11597
+ "note": "Every OlonJS tenant exposes a machine-readable manifest at",
11598
+ "noteHref": "http://localhost:5173/mcp-manifest.json",
11599
+ "steps": [
11600
+ {
11601
+ "number": 1,
11602
+ "title": "Scaffold a tenant",
11603
+ "meta": "~3 min",
11604
+ "code": "# Install the CLI\nnpm install -g @olonjs/cli\n\n# Scaffold a new tenant\nnpx @olonjs/cli new tenant\n\n✓ Projecting infrastructure...\n✓ Projecting source (src_tenant_alpha.sh)\n✓ Resolving dependencies\n✓ Tenant scaffolded\n\nsrc/\n components/hero/\n View.tsx\n schema.ts\n types.ts\n index.ts\n data/config/\n site.json\n theme.json\n menu.json\n lib/\n schemas.ts\n base-schemas.ts"
11605
+ },
11606
+ {
11607
+ "number": 2,
11608
+ "title": "Read via OlonJS protocol",
11609
+ "meta": "Any consumer",
11610
+ "code": "// Read any page via the contract\n// Works from browser, script, or AI agent\n\nconst page = await\n navigator.modelContextProtocol\n .readResource(\n 'olon://pages/home'\n );\n\n// Returns the full typed contract\n// { slug, meta, sections: Section[] }\n// No DOM scraping. No layout knowledge.\n// Just the contract.\n\n// {\n// \"slug\": \"home\",\n// \"sections\": [\n// { \"type\": \"hero\", \"data\": {...} },\n// { \"type\": \"features\", \"data\": {...} }\n// ]\n// }"
11611
+ }
11612
+ ],
11613
+ "anchorId": "Example"
11614
+ }
11615
+ },
11616
+ {
11617
+ "id": "getstarted-cards",
11618
+ "type": "olon-getstarted",
11619
+ "data": {
11620
+ "id": "getstarted-cards",
11621
+ "label": "Get Started",
11622
+ "headline": "Three paths in.",
11623
+ "body": "Start with the Core package, scaffold a full tenant with the CLI, or deploy a working example in one click.",
11624
+ "cards": [
11625
+ {
11626
+ "id": "card-core",
11627
+ "badge": "Open Core",
11628
+ "badgeStyle": "oss",
11629
+ "title": "Install Core",
11630
+ "body": "The Core package is free and open — forever. The contract, the protocols, the CLI. No lock-in on the foundation.",
11631
+ "code": "npm install @olonjs/core",
11632
+ "linkLabel": "View on GitHub",
11633
+ "linkHref": "https://github.com/olonjs/core"
11634
+ },
11635
+ {
11636
+ "id": "card-cli",
11637
+ "badge": "CLI",
11638
+ "badgeStyle": "cli",
11639
+ "title": "Scaffold a tenant",
11640
+ "body": "The CLI scaffolds a fully compliant tenant from a canonical script. Same result on every machine, every run.",
11641
+ "code": "npx @olonjs/cli new tenant",
11642
+ "linkLabel": "View on npm",
11643
+ "linkHref": "https://www.npmjs.com/package/@olonjs/cli"
11644
+ },
11645
+ {
11646
+ "id": "card-deploy",
11647
+ "badge": "Deploy",
11648
+ "badgeStyle": "deploy",
11649
+ "title": "Deploy a template",
11650
+ "body": "Clone a working OlonJS tenant and deploy it with one click. Explore the full capsule structure in a real project.",
11651
+ "deployLabel": "Deploy template →",
11652
+ "deployHref": "https://github.com/olonjs/core",
11653
+ "linkLabel": "View on npm",
11654
+ "linkHref": "https://www.npmjs.com/package/@olonjs/core"
11655
+ }
11656
+ ],
11657
+ "anchorId": "Getstarted"
11658
+ }
11659
+ }
11660
+ ]
11661
+ }
11662
+ END_OF_FILE_CONTENT
11663
+ echo "Creating src/data/pages/home_.json..."
11664
+ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home_.json"
10378
11665
  {
10379
11666
  "id": "home-page",
10380
11667
  "slug": "home",
@@ -10388,9 +11675,9 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10388
11675
  "type": "hero",
10389
11676
  "data": {
10390
11677
  "eyebrow": "Contract layer · v1.4 · Open Core",
10391
- "title": "Start Building",
11678
+ "title": "Contract Layer",
10392
11679
  "titleHighlight": "for the agentic web.",
10393
- "description": "AI agents are becoming operational actors in commerce, marketing, and support. But websites are still built for humans first: HTML-heavy, CMS-fragmented, and inconsistent across properties. That makes agent integration slow, brittle, and expensive. Olon introduces a deterministic machine contract for websites OlonJS. This makes content reliably readable and operable by agents while preserving normal human UI.",
11680
+ "description": "OlonJS is a TypeScript framework for building JSON-driven websites with a deterministic data contract. Every section is typed, validated, and structurally addressable. Designed for reproducible tenant generation and machine-readable output.",
10394
11681
  "ctas": [
10395
11682
  {
10396
11683
  "id": "cta-started",
@@ -10408,8 +11695,8 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10408
11695
  "docsLabel": "Explore platform",
10409
11696
  "docsHref": "/platform/overview",
10410
11697
  "heroImage": {
10411
- "url": "https://bat5elmxofxdroan.public.blob.vercel-storage.com/tenant-assets/511f18d7-d8ac-4292-ad8a-b0efa99401a3/1774286598548-adac7c36-9001-451d-9b16-c3787ac27f57-signup-hero-olon-graded_1_.png",
10412
- "alt": ""
11698
+ "url": "data:image/svg+xml;base64,PHN2ZyB2ZXJzaW9uPSIxLjIiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgdmlld0JveD0iMCAwIDIwMCAyMDAiIHdpZHRoPSI1MTIiIGhlaWdodD0iNTEyIj4KICA8ZGVmcz4KICAgIDxsaW5lYXJHcmFkaWVudCBpZD0iZy1tYWluIiB4Mj0iMSIgZ3JhZGllbnRVbml0cz0idXNlclNwYWNlT25Vc2UiIGdyYWRpZW50VHJhbnNmb3JtPSJtYXRyaXgoMTEwLjc5NSwxMTAuNzk1LC0xMTAuNzk1LDExMC43OTUsNDQuNjAzLDQ0LjYwMykiPgogICAgICA8c3RvcCBvZmZzZXQ9IjAiIHN0b3AtY29sb3I9IiM1QjhFRkYiLz4KICAgICAgPHN0b3Agb2Zmc2V0PSIwLjUiIHN0b3AtY29sb3I9IiMwRjUyRTAiLz4KICAgICAgPHN0b3Agb2Zmc2V0PSIxIiBzdG9wLWNvbG9yPSIjMDYzMDkwIi8+CiAgICA8L2xpbmVhckdyYWRpZW50PgogICAgPGxpbmVhckdyYWRpZW50IGlkPSJnLWFjY2VudCIgeDE9IjAiIHkxPSIwIiB4Mj0iMCIgeTI9IjEiPgogICAgICA8c3RvcCBvZmZzZXQ9IjAiIHN0b3AtY29sb3I9IiNBREM4RkYiLz4KICAgICAgPHN0b3Agb2Zmc2V0PSIxIiBzdG9wLWNvbG9yPSIjNUI4RUZGIi8+CiAgICA8L2xpbmVhckdyYWRpZW50PgogIDwvZGVmcz4KICA8IS0tIENoaXAgYm9yZGVyIC0tPgogIDxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0idXJsKCNnLW1haW4pIiBzdHJva2Utd2lkdGg9IjgiCiAgICBkPSJtNTkuMzggNDQuNmg4MS4yNGM4LjE2IDAgMTQuNzggNi42MiAxNC43OCAxNC43OHY4MS4yNGMwIDguMTYtNi42MiAxNC43OC0xNC43OCAxNC43OGgtODEuMjRjLTguMTYgMC0xNC43OC02LjYyLTE0Ljc4LTE0Ljc4di04MS4yNGMwLTguMTYgNi42Mi0xNC43OCAxNC43OC0xNC43OHoiLz4KICA8IS0tIExlZnQgcGlucyAtLT4KICA8cGF0aCBmaWxsPSJub25lIiBzdHJva2U9InVybCgjZy1tYWluKSIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2Utd2lkdGg9IjYiIGQ9Im03LjY3IDcyLjNoMzYuOTMiLz4KICA8cGF0aCBmaWxsPSJub25lIiBzdHJva2U9InVybCgjZy1tYWluKSIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2Utd2lkdGg9IjYiIGQ9Im03LjY3IDEwMGgzNi45MyIvPgogIDxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0idXJsKCNnLW1haW4pIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS13aWR0aD0iNiIgZD0ibTcuNjcgMTI3LjdoMzYuOTMiLz4KICA8IS0tIFJpZ2h0IHBpbnMgLS0+CiAgPHBhdGggZmlsbD0ibm9uZSIgc3Ryb2tlPSJ1cmwoI2ctbWFpbikiIHN0cm9rZS1saW5lY2FwPSJyb3VuZCIgc3Ryb2tlLXdpZHRoPSI2IiBkPSJtMTU1LjQgNzIuM2gzNi45MyIvPgogIDxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0idXJsKCNnLW1haW4pIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS13aWR0aD0iNiIgZD0ibTE1NS40IDEwMGgzNi45MyIvPgogIDxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0idXJsKCNnLW1haW4pIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS13aWR0aD0iNiIgZD0ibTE1NS40IDEyNy43aDM2LjkzIi8+CiAgPCEtLSBUb3AgcGlucyAtLT4KICA8cGF0aCBmaWxsPSJub25lIiBzdHJva2U9InVybCgjZy1tYWluKSIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2Utd2lkdGg9IjYiIGQ9Im03Mi4zIDcuNjd2MzYuOTMiLz4KICA8cGF0aCBmaWxsPSJub25lIiBzdHJva2U9InVybCgjZy1tYWluKSIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2Utd2lkdGg9IjYiIGQ9Im0xMDAgNy42N3YzNi45MyIvPgogIDxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0idXJsKCNnLW1haW4pIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS13aWR0aD0iNiIgZD0ibTEyNy43IDcuNjd2MzYuOTMiLz4KICA8IS0tIEJvdHRvbSBwaW5zIC0tPgogIDxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0idXJsKCNnLW1haW4pIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS13aWR0aD0iNiIgZD0ibTcyLjMgMTU1LjR2MzYuOTMiLz4KICA8cGF0aCBmaWxsPSJub25lIiBzdHJva2U9InVybCgjZy1tYWluKSIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2Utd2lkdGg9IjYiIGQ9Im0xMDAgMTU1LjR2MzYuOTMiLz4KICA8cGF0aCBmaWxsPSJub25lIiBzdHJva2U9InVybCgjZy1tYWluKSIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2Utd2lkdGg9IjYiIGQ9Im0xMjcuNyAxNTUuNHYzNi45MyIvPgogIDwhLS0gQ29ybmVyIG5vZGVzIC0tPgogIDxjaXJjbGUgZmlsbD0idXJsKCNnLW1haW4pIiBjeD0iNzIuMyIgY3k9IjcyLjMiIHI9IjcuMzkiLz4KICA8Y2lyY2xlIGZpbGw9InVybCgjZy1tYWluKSIgY3g9IjEyNy43IiBjeT0iNzIuMyIgcj0iNy4zOSIvPgogIDxjaXJjbGUgZmlsbD0idXJsKCNnLW1haW4pIiBjeD0iNzIuMyIgY3k9IjEyNy43IiByPSI3LjM5Ii8+CiAgPGNpcmNsZSBmaWxsPSJ1cmwoI2ctbWFpbikiIGN4PSIxMjcuNyIgY3k9IjEyNy43IiByPSI3LjM5Ii8+CiAgPCEtLSBDZW50ZXIgbm9kZSDigJQgYWNjZW50IC0tPgogIDxjaXJjbGUgZmlsbD0idXJsKCNnLWFjY2VudCkiIGN4PSIxMDAiIGN5PSIxMDAiIHI9IjkuMjMiLz4KICA8IS0tIENvbm5lY3Rpb24gbGluZXMgLS0+CiAgPHBhdGggb3BhY2l0eT0iMC4zIiBmaWxsPSJub25lIiBzdHJva2U9IiM1QjhFRkYiIHN0cm9rZS13aWR0aD0iMiIgZD0ibTcyLjMgNzIuM2wyNy43IDI3LjciLz4KICA8cGF0aCBvcGFjaXR5PSIwLjMiIGZpbGw9Im5vbmUiIHN0cm9rZT0iIzVCOEVGRiIgc3Ryb2tlLXdpZHRoPSIyIiBkPSJtMTI3LjcgNzIuM2wtMjcuNyAyNy43Ii8+CiAgPHBhdGggb3BhY2l0eT0iMC4zIiBmaWxsPSJub25lIiBzdHJva2U9IiM1QjhFRkYiIHN0cm9rZS13aWR0aD0iMiIgZD0ibTcyLjMgMTI3LjdsMjcuNy0yNy43Ii8+CiAgPHBhdGggb3BhY2l0eT0iMC4zIiBmaWxsPSJub25lIiBzdHJva2U9IiM1QjhFRkYiIHN0cm9rZS13aWR0aD0iMiIgZD0ibTEyNy43IDEyNy43bC0yNy43LTI3LjciLz4KPC9zdmc+Cg==",
11699
+ "alt": "icon-ai-specs.svg"
10413
11700
  }
10414
11701
  },
10415
11702
  "settings": {
@@ -10421,9 +11708,9 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10421
11708
  "type": "feature-grid",
10422
11709
  "data": {
10423
11710
  "label": "Why OlonJS",
10424
- "sectionTitle": "A whole in itself,",
10425
- "sectionTitleItalic": "part of something greater.",
10426
- "sectionLead": "Built on the concept of the holonevery component autonomous yet part of the larger contract. Governance and developer experience, unified.",
11711
+ "sectionTitle": "A Meaningful Web",
11712
+ "sectionTitleItalic": "Whole in itself, part of something greater.",
11713
+ "sectionLead": "Most web frameworks separate concerns across layers — data, UI, validation, metadata — with no shared contract between them. OlonJS inverts this: the JSON data structure is the contract. Every layer rendering, editing, validation, machine access — is a deterministic projection of the same typed source. The result is a site that is structurally coherent by construction, not by convention.",
10427
11714
  "cards": [
10428
11715
  {
10429
11716
  "id": "card-endpoints",
@@ -10431,8 +11718,8 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10431
11718
  "url": "/icons/features/icon-json-files.svg",
10432
11719
  "alt": "JSON files icon"
10433
11720
  },
10434
- "title": "Canonical JSON endpoints",
10435
- "description": "Every page available at /{slug}.jsondeterministic, typed, agent-readable. No custom integration per tenant."
11721
+ "title": "Modular Type Registry",
11722
+ "description": "Core exports an empty SectionDataRegistry. Tenants extend it via module augmentation no Core changes required. Full TypeScript inference across all section types at compile-time."
10436
11723
  },
10437
11724
  {
10438
11725
  "id": "card-schema",
@@ -10440,8 +11727,8 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10440
11727
  "url": "/icons/features/icon-zod-schemas.svg",
10441
11728
  "alt": "Zod schemas icon"
10442
11729
  },
10443
- "title": "Schema-driven contracts",
10444
- "description": "Typed components validated against your schema. Shared conventions eliminate prompt ambiguity across teams."
11730
+ "title": "Tenant Block Protocol",
11731
+ "description": "Each section type lives in a self-contained capsule: View.tsx, schema.ts, types.ts, index.ts. The capsule is the unit of extension — renderable, validatable, and ingestible by the engine without additional configuration."
10445
11732
  },
10446
11733
  {
10447
11734
  "id": "card-ai",
@@ -10449,8 +11736,8 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10449
11736
  "url": "/icons/features/icon-ai-specs.svg",
10450
11737
  "alt": "AI specs icon"
10451
11738
  },
10452
- "title": "AI-native velocity",
10453
- "description": "Structure is deterministic, so AI can scaffold and evolve tenants faster. Ship new experiences in hours, not weeks."
11739
+ "title": "Deterministic CLI",
11740
+ "description": "@olonjs/cli scaffolds new tenants from a canonical script. Infrastructure, source structure, and dependencies are projected deterministically. Output is reproducible across environments"
10454
11741
  },
10455
11742
  {
10456
11743
  "id": "card-multitenant",
@@ -10458,8 +11745,8 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10458
11745
  "url": "/icons/features/icon-own-data.svg",
10459
11746
  "alt": "Own data icon"
10460
11747
  },
10461
- "title": "Multi-tenant at scale",
10462
- "description": "One convention across many tenants enables reusable automations. No per-tenant custom integration work."
11748
+ "title": "ICE Data Contract",
11749
+ "description": "Mandatory data-jp-* DOM attributes bind rendered sections to their data contract. The binding is structural, not UI-dependent any consumer that can traverse the DOM can identify and address any content node."
10463
11750
  },
10464
11751
  {
10465
11752
  "id": "card-governance",
@@ -10467,8 +11754,8 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10467
11754
  "url": "/icons/features/icon-governance.svg",
10468
11755
  "alt": "Governance icon"
10469
11756
  },
10470
- "title": "Enterprise governance",
10471
- "description": "Audit trails, compliance controls, and private cloud deployment via NX monorepo. SOC2-ready by design."
11757
+ "title": "Base Schema Fragments",
11758
+ "description": "BaseSectionData and BaseArrayItem are the required base types for all section data schemas and array items. They enforce anchor IDs and stable React keys across all capsules."
10472
11759
  },
10473
11760
  {
10474
11761
  "id": "card-deploy",
@@ -10476,8 +11763,8 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10476
11763
  "url": "/icons/features/icon-clean-commits.svg",
10477
11764
  "alt": "Clean commits icon"
10478
11765
  },
10479
- "title": "Deployment flexibility",
10480
- "description": "OSS core you can trust. Vercel-native cloud for speed. Private cloud for governance-heavy orgs."
11766
+ "title": "Path-Based Selection",
11767
+ "description": "Content selection uses strict root-to-leaf path semantics. Each segment identifies a node unambiguously. The flat itemField/itemId protocol is removed in v1.3+."
10481
11768
  }
10482
11769
  ],
10483
11770
  "proofStatement": "Working end-to-end with production routing parity.",
@@ -10557,7 +11844,6 @@ cat << 'END_OF_FILE_CONTENT' > "src/data/pages/home.json"
10557
11844
  }
10558
11845
  END_OF_FILE_CONTENT
10559
11846
  mkdir -p "src/data/pages/platform"
10560
- # SKIP: src/data/pages/platform.json:Zone.Identifier is binary and cannot be embedded as text.
10561
11847
  echo "Creating src/data/pages/platform/overview.json..."
10562
11848
  cat << 'END_OF_FILE_CONTENT' > "src/data/pages/platform/overview.json"
10563
11849
  {
@@ -12049,6 +13335,13 @@ import { CloudAiNativeGridView } from '@/components/cloud-ai-native-grid';
12049
13335
  import { PageHero } from '@/components/page-hero';
12050
13336
  import { Tiptap } from '@/components/tiptap';
12051
13337
 
13338
+
13339
+ import { View as OlonHeroView } from '@/components/olon-hero';
13340
+ import { View as OlonWhyView } from '@/components/olon-why';
13341
+ import { View as OlonArchitectureView } from '@/components/olon-architecture';
13342
+ import { View as OlonExampleView } from '@/components/olon-example';
13343
+ import { View as OlonGetStartedView } from '@/components/olon-getstarted';
13344
+
12052
13345
  export const ComponentRegistry: {
12053
13346
  [K in SectionType]: React.FC<SectionComponentPropsMap[K]>;
12054
13347
  } = {
@@ -12062,6 +13355,13 @@ export const ComponentRegistry: {
12062
13355
  'cloud-ai-native-grid': CloudAiNativeGridView as React.FC<SectionComponentPropsMap['cloud-ai-native-grid']>,
12063
13356
  'page-hero': PageHero as React.FC<SectionComponentPropsMap['page-hero']>,
12064
13357
  'tiptap': Tiptap as React.FC<SectionComponentPropsMap['tiptap']>,
13358
+
13359
+
13360
+ 'olon-hero': OlonHeroView,
13361
+ 'olon-why': OlonWhyView,
13362
+ 'olon-architecture': OlonArchitectureView,
13363
+ 'olon-example': OlonExampleView,
13364
+ 'olon-getstarted': OlonGetStartedView,
12065
13365
  };
12066
13366
 
12067
13367
  END_OF_FILE_CONTENT
@@ -12182,6 +13482,7 @@ export const ImageSelectionSchema = z
12182
13482
  * Capsules extend these for consistent anchorId, array items, and settings.
12183
13483
  */
12184
13484
  export const BaseSectionData = z.object({
13485
+ id: z.string().optional(),
12185
13486
  anchorId: z.string().optional().describe('ui:text'),
12186
13487
  });
12187
13488
 
@@ -12463,6 +13764,12 @@ import { CloudAiNativeGridSchema } from '@/components/cloud-ai-native-grid';
12463
13764
  import { PageHeroSchema } from '@/components/page-hero';
12464
13765
  import { TiptapSchema } from '@/components/tiptap';
12465
13766
 
13767
+ import { OlonHeroSchema } from '@/components/olon-hero';
13768
+ import { OlonWhySchema } from '@/components/olon-why';
13769
+ import { OlonArchitectureSchema } from '@/components/olon-architecture';
13770
+ import { OlonExampleSchema } from '@/components/olon-example';
13771
+ import { OlonGetStartedSchema } from '@/components/olon-getstarted';
13772
+
12466
13773
  export const SECTION_SCHEMAS = {
12467
13774
  'header': HeaderSchema,
12468
13775
  'footer': FooterSchema,
@@ -12473,7 +13780,13 @@ export const SECTION_SCHEMAS = {
12473
13780
  'design-system': DesignSystemSchema,
12474
13781
  'cloud-ai-native-grid': CloudAiNativeGridSchema,
12475
13782
  'page-hero': PageHeroSchema,
12476
- 'tiptap': TiptapSchema,
13783
+ 'tiptap': TiptapSchema,
13784
+
13785
+ 'olon-hero': OlonHeroSchema,
13786
+ 'olon-why': OlonWhySchema,
13787
+ 'olon-architecture': OlonArchitectureSchema,
13788
+ 'olon-example': OlonExampleSchema,
13789
+ 'olon-getstarted': OlonGetStartedSchema,
12477
13790
  } as const;
12478
13791
 
12479
13792
  export type SectionType = keyof typeof SECTION_SCHEMAS;
@@ -12620,6 +13933,13 @@ import type { CloudAiNativeGridData, CloudAiNativeGridSettings } from '@/com
12620
13933
  import type { PageHeroData, PageHeroSettings } from '@/components/page-hero';
12621
13934
  import type { TiptapData, TiptapSettings } from '@/components/tiptap';
12622
13935
 
13936
+
13937
+ import type { OlonHeroData } from '@/components/olon-hero';
13938
+ import type { OlonWhyData } from '@/components/olon-why';
13939
+ import type { OlonArchitectureData } from '@/components/olon-architecture';
13940
+ import type { OlonExampleData } from '@/components/olon-example';
13941
+ import type { OlonGetStartedData } from '@/components/olon-getstarted';
13942
+
12623
13943
  export type SectionComponentPropsMap = {
12624
13944
  'header': { data: HeaderData; settings?: HeaderSettings; menu: MenuItem[] };
12625
13945
  'footer': { data: FooterData; settings?: FooterSettings };
@@ -12631,6 +13951,13 @@ export type SectionComponentPropsMap = {
12631
13951
  'cloud-ai-native-grid': { data: CloudAiNativeGridData; settings?: CloudAiNativeGridSettings };
12632
13952
  'page-hero': { data: PageHeroData; settings?: PageHeroSettings };
12633
13953
  'tiptap': { data: TiptapData; settings?: TiptapSettings };
13954
+
13955
+
13956
+ 'olon-hero': { data: OlonHeroData };
13957
+ 'olon-why': { data: OlonWhyData };
13958
+ 'olon-architecture': { data: OlonArchitectureData };
13959
+ 'olon-example': { data: OlonExampleData };
13960
+ 'olon-getstarted': { data: OlonGetStartedData };
12634
13961
  };
12635
13962
 
12636
13963
  declare module '@olonjs/core' {
@@ -12645,6 +13972,11 @@ declare module '@olonjs/core' {
12645
13972
  'cloud-ai-native-grid': CloudAiNativeGridData;
12646
13973
  'page-hero': PageHeroData;
12647
13974
  'tiptap': TiptapData;
13975
+ 'olon-hero': OlonHeroData;
13976
+ 'olon-why': OlonWhyData;
13977
+ 'olon-architecture': OlonArchitectureData;
13978
+ 'olon-example': OlonExampleData;
13979
+ 'olon-getstarted': OlonGetStartedData;
12648
13980
  }
12649
13981
  export interface SectionSettingsRegistry {
12650
13982
  'header': HeaderSettings;