diff --git a/sites/docs-devsy-sh/app/(home)/home.css b/sites/docs-devsy-sh/app/(home)/home.css index 1f6d862c4c..870c32268a 100644 --- a/sites/docs-devsy-sh/app/(home)/home.css +++ b/sites/docs-devsy-sh/app/(home)/home.css @@ -1,662 +1,751 @@ -:root { - --purple: #7c5cff; - --purple-dark: #6244e6; - --purple-light: #a78bfa; - --ink: #0b0b14; - --slate: #545469; - --line: #e7e7f0; - --bg: #ffffff; - --bg-soft: #f7f7fc; +/* Homepage-only tokens: docs retain their existing Fumadocs theme. */ +.home-page { + --accent: #6341d8; + --accent-hover: #5132bb; + --accent-soft: #eee9fb; + --ink: #17151e; + --muted: #625e6d; + --line: #dedbe5; + --input-line: #898391; + --bg: #faf9fc; --surface: #ffffff; - --header-bg: rgba(255, 255, 255, 0.82); - --shadow: rgba(11, 11, 20, 0.28); - --radius: 14px; - --max: 1120px; + --soft: #f0edf5; + --button-ink: #ffffff; + --max: 1240px; + color: var(--ink); + background: var(--bg); + font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif; + font-size: 16px; + line-height: 1.65; + -webkit-font-smoothing: antialiased; } - -.dark { - --purple: #8f74ff; - --purple-dark: #7c5cff; - --purple-light: #b9a5ff; - --ink: #e9e9f2; - --slate: #a1a1b8; - --line: #262637; - --bg: #0b0b14; - --bg-soft: #12121d; - --surface: #15151f; - --header-bg: rgba(11, 11, 20, 0.82); - --shadow: rgba(0, 0, 0, 0.55); +.dark .home-page { + --accent: #bba5ff; + --accent-hover: #d0bfff; + --accent-soft: #282135; + --ink: #f2eff8; + --muted: #b5afc2; + --line: #38323f; + --input-line: #82788f; + --bg: #131117; + --surface: #1c1922; + --soft: #201c28; + --button-ink: #211735; } - html:has(.home-page) { scroll-behavior: smooth; + scroll-padding-top: 92px; } - -.home-page { - color: var(--ink); - background: var(--bg); - line-height: 1.6; - -webkit-font-smoothing: antialiased; - transition: - background 0.2s ease, - color 0.2s ease; +.home-page *, +.home-page *::before, +.home-page *::after { + box-sizing: border-box; } - .home-page a { color: inherit; text-decoration: none; } - +.home-page a:hover { + color: var(--accent); +} +.home-page :where(a, button, input, textarea):focus-visible { + outline: 3px solid var(--accent); + outline-offset: 4px; +} .home-page .wrap { max-width: var(--max); - margin: 0 auto; - padding: 0 24px; + margin-inline: auto; + padding-inline: 32px; +} +.home-page .skip-link { + position: fixed; + top: 8px; + left: 16px; + z-index: 30; + padding: 10px 18px; + background: var(--surface); + border: 1px solid var(--accent); + transform: translateY(-160%); +} +.home-page .skip-link:focus { + transform: translateY(0); } - -/* ---------- Buttons ---------- */ .home-page .btn { display: inline-flex; + justify-content: center; align-items: center; gap: 8px; - padding: 13px 24px; - border-radius: 10px; - font-weight: 600; - font-size: 15px; + min-height: 48px; + padding: 11px 21px; border: 1px solid transparent; - transition: - transform 0.15s ease, - box-shadow 0.2s ease, - background 0.2s ease, - border-color 0.2s ease; + border-radius: 6px; + font-size: 15px; + font-weight: 600; + line-height: 1.4; + white-space: nowrap; cursor: pointer; + transition: + background-color 160ms ease, + border-color 160ms ease; } - .home-page .btn-primary { - background: var(--purple); - color: #fff; - box-shadow: 0 8px 24px rgba(124, 92, 255, 0.32); + background: var(--accent); + color: var(--button-ink); } - .home-page .btn-primary:hover { - background: var(--purple-dark); - transform: translateY(-1px); - box-shadow: 0 12px 30px rgba(124, 92, 255, 0.42); + background: var(--accent-hover); + color: var(--button-ink); +} +.home-page .btn:active { + transform: translateY(1px); } - .home-page .btn-ghost { - background: var(--surface); - border-color: var(--line); + background: transparent; + border-color: var(--input-line); color: var(--ink); } - .home-page .btn-ghost:hover { - border-color: var(--purple-light); - transform: translateY(-1px); + background: var(--accent-soft); + border-color: var(--accent); } - -/* ---------- Header ---------- */ .home-page header { position: sticky; top: 0; - z-index: 50; - background: var(--header-bg); - backdrop-filter: saturate(180%) blur(12px); + z-index: 20; + background: var(--bg); border-bottom: 1px solid var(--line); } - .home-page .nav { - position: relative; display: flex; align-items: center; justify-content: space-between; - height: 68px; - gap: 16px; -} - -/* Desktop: center the section links on the page, independent of the - brand and action widths on either side. */ -@media (min-width: 992px) { - .home-page .nav-links { - position: absolute; - left: 50%; - top: 50%; - transform: translate(-50%, -50%); - } + height: 76px; + gap: 28px; + position: relative; } - .home-page .brand { - display: flex; + display: inline-flex; align-items: center; gap: 10px; + font-size: 23px; font-weight: 700; - font-size: 22px; - letter-spacing: -0.02em; + letter-spacing: -0.04em; + flex-shrink: 0; } - .home-page .brand svg { display: block; } - -.home-page .nav-menu { +.home-page .nav-menu, +.home-page .nav-links, +.home-page .nav-cta { display: flex; align-items: center; - gap: 24px; } - -.home-page .nav-links { - display: flex; - align-items: center; +.home-page .nav-menu { gap: 26px; - font-size: 15px; - font-weight: 500; - color: var(--slate); } - -.home-page .nav-links a:hover { - color: var(--ink); +.home-page .nav-links { + gap: 22px; + font-size: 14px; + font-weight: 500; + color: var(--muted); } - -.home-page .nav-cta { - display: flex; +.home-page .nav-links a { + display: inline-flex; align-items: center; - gap: 16px; + min-height: 44px; + white-space: nowrap; } - -.home-page .nav-cta .btn { - height: 40px; - padding: 0 20px; +.home-page .nav-cta { + gap: 14px; } - .home-page .nav-divider { width: 1px; - height: 26px; + height: 24px; background: var(--line); } - +.home-page .nav-cta .btn { + min-height: 44px; + padding-inline: 17px; +} +.home-page .theme-toggle, .home-page .nav-toggle { - display: none; - width: 42px; - height: 42px; + display: inline-flex; align-items: center; justify-content: center; + width: 44px; + height: 44px; + border: 1px solid var(--input-line); + border-radius: 6px; background: transparent; - border: 1px solid var(--line); - border-radius: 10px; color: var(--ink); cursor: pointer; } - -.home-page .theme-toggle { - display: inline-flex; - align-items: center; - justify-content: center; - width: 40px; - height: 40px; - flex: none; - background: var(--surface); - border: 1px solid var(--line); - border-radius: 10px; - color: var(--ink); - cursor: pointer; - transition: border-color 0.2s ease; +.home-page .theme-toggle:hover, +.home-page .nav-toggle:hover { + background: var(--accent-soft); } - -.home-page .theme-toggle:hover { - border-color: var(--purple-light); +.home-page .nav-toggle { + display: none; } - -@media (max-width: 991px) { - .home-page .nav-toggle { - display: inline-flex; - } - - .home-page .nav-menu { - position: absolute; - top: 68px; - left: 0; - right: 0; - flex-direction: column; - align-items: stretch; - gap: 0; - padding: 12px 24px 20px; - background: var(--surface); - border-bottom: 1px solid var(--line); - box-shadow: 0 24px 48px -28px var(--shadow); - display: none; - } - - .home-page .nav-menu.open { - display: flex; - } - - .home-page .nav-links { - flex-direction: column; - align-items: stretch; - gap: 0; - } - - .home-page .nav-links a { - padding: 13px 0; - border-bottom: 1px solid var(--line); - } - - .home-page .nav-cta { - flex-direction: column; - align-items: stretch; - gap: 12px; - padding-top: 14px; - } - - .home-page .nav-divider { - display: none; - } - - .home-page .nav-cta .btn { - width: 100%; - justify-content: center; - text-align: center; - } - - .home-page .theme-toggle { - width: 100%; - } +.home-page section { + padding-block: 88px; + scroll-margin-top: 0; } - -/* ---------- Hero ---------- */ .home-page .hero { - position: relative; - overflow: hidden; - padding: 92px 0 80px; - text-align: center; - background: - radial-gradient( - 60% 120% at 50% -10%, - rgba(124, 92, 255, 0.14), - rgba(124, 92, 255, 0) 60% - ), - var(--bg); -} - -.home-page h1 { - font-size: clamp(38px, 6vw, 62px); - line-height: 1.05; - letter-spacing: -0.03em; - font-weight: 800; - margin: 0 auto 22px; - max-width: 900px; + padding-top: 80px; + padding-bottom: 72px; } - -.home-page h1 .grad { - background: linear-gradient(120deg, var(--purple), var(--purple-light)); - -webkit-background-clip: text; - background-clip: text; - -webkit-text-fill-color: transparent; +.home-page .hero-grid { + display: grid; + grid-template-columns: minmax(0, 0.95fr) minmax(0, 1.05fr); + align-items: center; + gap: 52px; } - -.home-page .hero-sub { - font-size: clamp(18px, 2.4vw, 24px); - font-weight: 600; - letter-spacing: -0.015em; - color: var(--ink); - margin: 0 auto 18px; +.home-page .hero-copy { + min-width: 0; } - +.home-page h1 { + max-width: none; + margin: 0 0 26px; + font-size: clamp(38px, 4vw, 52px); + letter-spacing: -0.055em; + font-weight: 650; + line-height: 1.06; + text-wrap: balance; +} +.home-page h1 .accent { + color: var(--accent); +} +.home-page .hero-sub, .home-page .lede { - font-size: clamp(17px, 2.2vw, 21px); - color: var(--slate); - max-width: 660px; - margin: 0 auto 34px; + max-width: 38ch; + margin: 0 0 28px; + font-size: 19px; + color: var(--muted); + line-height: 1.6; } - .home-page .hero-cta { display: flex; - gap: 14px; - justify-content: center; + align-items: center; + gap: 12px; flex-wrap: wrap; } - .home-page .hero-media { - margin: 56px auto 0; - max-width: 940px; - border-radius: 18px; - border: 1px solid var(--line); - box-shadow: 0 30px 80px -30px var(--shadow); - overflow: hidden; - background: var(--surface); + min-width: 0; + margin: 0; } - .home-page .hero-media img { display: block; width: 100%; height: auto; + border: 1px solid var(--line); + border-radius: 10px; + box-shadow: 0 16px 40px -24px #493c69; } - -/* ---------- Section shells ---------- */ -.home-page section { - padding: 88px 0; +.home-page .product-caption { + margin-top: 14px; + font-size: 14px; + color: var(--muted); } - -.home-page .section-head { - text-align: center; - max-width: 640px; - margin: 0 auto 56px; +.home-page .compatibility-strip { + display: flex; + justify-content: space-between; + gap: 32px; + padding-block: 24px; + border-block: 1px solid var(--line); + font-size: 14px; + color: var(--muted); } - -.home-page .section-head h2 { - font-size: clamp(28px, 4vw, 40px); - letter-spacing: -0.025em; - font-weight: 800; - margin: 0 0 14px; +.home-page .compatibility-strip strong { + font-weight: 600; + color: var(--ink); +} +.home-page .compatibility-app, +.home-page .compatibility-editors { + display: flex; + align-items: center; + flex-wrap: wrap; + gap: 10px 18px; +} +.home-page h2 { + margin: 0 0 18px; + max-width: 21ch; + font-size: clamp(30px, 3.3vw, 44px); + font-weight: 600; + letter-spacing: -0.045em; + line-height: 1.15; + text-wrap: balance; +} +.home-page .section-head { + max-width: 690px; + margin-bottom: 44px; } - .home-page .section-head p { - color: var(--slate); - font-size: 18px; + max-width: 62ch; margin: 0; + color: var(--muted); + font-size: 18px; } - .home-page .kicker { - text-transform: uppercase; - letter-spacing: 0.14em; - font-size: 12.5px; - font-weight: 700; - color: var(--purple); - margin-bottom: 12px; + color: var(--accent); + font-size: 14px; + font-weight: 600; + margin-bottom: 16px; } - -/* ---------- Features grid ---------- */ -.home-page .grid { +.home-page .feature-list { display: grid; - grid-template-columns: repeat(3, 1fr); - gap: 22px; + grid-template-columns: repeat(2, minmax(0, 1fr)); + gap: 0 52px; } - -@media (max-width: 900px) { - .home-page .grid { - grid-template-columns: 1fr; - } +.home-page .feature-row { + display: grid; + grid-template-columns: 110px minmax(0, 1fr); + gap: 20px; + border-top: 1px solid var(--line); + padding-block: 28px; } - -.home-page .card { - border: 1px solid var(--line); - border-radius: var(--radius); - padding: 28px; - background: var(--surface); - transition: - transform 0.18s ease, - box-shadow 0.2s ease, - border-color 0.2s ease; +.home-page .feature-index { + color: var(--accent); + font-size: 14px; + font-family: ui-monospace, SFMono-Regular, Consolas, monospace; + padding-top: 3px; } - -.home-page .card:hover { - transform: translateY(-3px); - border-color: var(--purple-light); - box-shadow: 0 18px 40px -24px rgba(124, 92, 255, 0.5); +.home-page h3 { + font-size: 20px; + line-height: 1.35; + letter-spacing: -0.025em; + font-weight: 600; + margin: 0 0 10px; } - -.home-page .card .ico { - width: 44px; - height: 44px; - border-radius: 11px; +.home-page .feature-body p, +.home-page .card p, +.home-page .step p { + color: var(--muted); + margin: 0; + font-size: 16px; +} +.home-page .agent-grid { display: grid; - place-items: center; - background: rgba(124, 92, 255, 0.1); - color: var(--purple); - margin-bottom: 18px; + grid-template-columns: minmax(0, 1.25fr) minmax(0, 1fr) minmax(0, 1fr); + gap: 32px; } - -.home-page .card h3 { - margin: 0 0 8px; - font-size: 18px; - font-weight: 700; - letter-spacing: -0.01em; +.home-page #agents { + background: var(--soft); } - -.home-page .card p { - margin: 0; - color: var(--slate); - font-size: 15px; +.home-page .card { + min-width: 0; + padding: 0; } - -/* ---------- Anywhere band ---------- */ -.home-page .band { - background: var(--bg-soft); - border-top: 1px solid var(--line); - border-bottom: 1px solid var(--line); +.home-page .card .ico { + display: inline-flex; + color: var(--accent); + margin-bottom: 20px; } - -.home-page .targets { +.home-page .grid { display: grid; - grid-template-columns: repeat(4, 1fr); - gap: 16px; + grid-template-columns: repeat(3, minmax(0, 1fr)); + gap: 32px; } - -@media (max-width: 760px) { - .home-page .targets { - grid-template-columns: repeat(2, 1fr); - } +.home-page #services .card { + border-left: 1px solid var(--line); + padding-left: 24px; } - -.home-page .target { - background: var(--surface); - border: 1px solid var(--line); - border-radius: 12px; - padding: 24px 20px; - text-align: center; - transition: - transform 0.18s ease, - border-color 0.2s ease; +.home-page #services .card:first-child { + border: 0; + padding-left: 0; } - -.home-page .target:hover { - transform: translateY(-3px); - border-color: var(--purple-light); +.home-page #anywhere .wrap { + display: grid; + grid-template-columns: minmax(0, 0.9fr) minmax(0, 1.1fr); + align-items: start; + gap: 36px 64px; } - -.home-page .target .ico { - width: 40px; - height: 40px; - margin: 0 auto 14px; +.home-page #anywhere .section-head { + margin-bottom: 0; +} +.home-page .provider-media { + min-width: 0; + margin: 0; + grid-column: 2; + grid-row: 1 / 3; +} +.home-page .provider-crop { + aspect-ratio: 0.9; + overflow: hidden; + border: 1px solid var(--line); border-radius: 10px; - display: grid; - place-items: center; - background: rgba(124, 92, 255, 0.1); - color: var(--purple); + background: #111; } - -.home-page .target strong { +.home-page .provider-crop img { display: block; - font-size: 16px; - margin-bottom: 4px; -} - -.home-page .target > span { - font-size: 13.5px; - color: var(--slate); + width: 100%; + height: 100%; + object-fit: cover; + object-position: center; + transform: scale(1.48); } - -/* ---------- How it works ---------- */ -.home-page .steps { +.home-page .targets { display: grid; - grid-template-columns: repeat(3, 1fr); - gap: 26px; + grid-template-columns: repeat(2, minmax(0, 1fr)); + gap: 28px; } - -@media (max-width: 900px) { - .home-page .steps { - grid-template-columns: 1fr; - } -} - -.home-page .step { - text-align: center; +.home-page .target { + min-width: 0; + border-top: 1px solid var(--line); + padding-top: 22px; } - -.home-page .step .num { - width: 40px; - height: 40px; - border-radius: 11px; - display: grid; - place-items: center; - font-weight: 800; - color: #fff; - background: linear-gradient(140deg, var(--purple), var(--purple-light)); - margin: 0 auto 16px; +.home-page .target .ico { + color: var(--accent); + margin-bottom: 16px; } - -.home-page .step h3 { - margin: 0 0 6px; +.home-page .target strong { + display: block; font-size: 18px; - letter-spacing: -0.01em; + margin-bottom: 6px; } - -.home-page .step p { - margin: 0 auto; - max-width: 320px; - color: var(--slate); +.home-page .target > span { + display: block; + color: var(--muted); font-size: 15px; } - -/* ---------- CTA ---------- */ -.home-page .cta { - text-align: center; - background: linear-gradient(150deg, #14122b, #241a4d 60%, #2c1c66); - border-radius: 24px; - padding: 64px 32px; - color: #fff; - margin: 0 auto; +.home-page #how { + background: var(--soft); } - -.home-page .cta h2 { - font-size: clamp(28px, 4vw, 42px); - letter-spacing: -0.025em; - margin: 0 0 14px; - font-weight: 800; +.home-page .steps { + display: grid; + grid-template-columns: repeat(3, minmax(0, 1fr)); + gap: 40px; } - -.home-page .cta p { - color: rgba(255, 255, 255, 0.75); - font-size: 18px; - max-width: 560px; - margin: 0 auto 30px; +.home-page .num { + display: inline-block; + color: var(--accent); + margin-bottom: 18px; + font: + 500 16px ui-monospace, + SFMono-Regular, + Consolas, + monospace; +} +.home-page .command-example { + margin-top: 36px; + border: 1px solid var(--input-line); + border-radius: 8px; + background: var(--surface); + padding: 24px; } - -.home-page .cta .btn-ghost { - background: transparent; - border-color: rgba(255, 255, 255, 0.28); - color: #fff; +.home-page .command-example p, +.home-page .command-example figcaption { + font-size: 14px; + color: var(--muted); + margin: 0 0 12px; +} +.home-page .command-example pre { + white-space: pre-wrap; + overflow-wrap: anywhere; + font: + 15px / 1.8 ui-monospace, + SFMono-Regular, + Consolas, + monospace; + margin: 0; } - -.home-page .cta .btn-ghost:hover { - border-color: #fff; +.home-page .command-example code { + padding: 0; + background: transparent; } - -/* ---------- Services ---------- */ .home-page .service-cta { - text-align: center; - margin-top: 44px; + margin-top: 32px; +} +.home-page #contact { + background: var(--soft); +} +.home-page #contact .wrap { + display: grid; + grid-template-columns: minmax(0, 0.85fr) minmax(0, 1.15fr); + gap: 72px; } - -/* ---------- Contact form ---------- */ .home-page .contact-form { - max-width: 640px; - margin: 0 auto; + min-width: 0; } - .home-page .form-row { display: grid; - grid-template-columns: 1fr 1fr; - gap: 16px; + grid-template-columns: repeat(2, minmax(0, 1fr)); + gap: 20px; } - -@media (max-width: 620px) { - .home-page .form-row { - grid-template-columns: 1fr; - } -} - .home-page .field { - margin-bottom: 18px; - text-align: left; + margin-bottom: 22px; } - .home-page .field label { display: block; - font-size: 14px; - font-weight: 600; - margin-bottom: 6px; + font-size: 15px; + font-weight: 500; + margin-bottom: 8px; } - -.home-page .field .optional { +.home-page .optional { + color: var(--muted); font-weight: 400; - color: var(--slate); } - .home-page .field input, .home-page .field textarea { width: 100%; - padding: 12px 14px; - border: 1px solid var(--line); - border-radius: 10px; + min-height: 48px; + padding: 12px; + border: 1px solid var(--input-line); + border-radius: 6px; font: inherit; color: var(--ink); background: var(--surface); - transition: - border-color 0.2s ease, - box-shadow 0.2s ease; } - -.home-page .field input:focus, -.home-page .field textarea:focus { - outline: none; - border-color: var(--purple); - box-shadow: 0 0 0 3px rgba(124, 92, 255, 0.15); -} - .home-page .field textarea { + min-height: 144px; resize: vertical; - min-height: 130px; } - -.home-page .form-hidden { - position: absolute; - left: -9999px; +.home-page .field textarea::placeholder { + color: var(--muted); + opacity: 1; } - -.home-page .form-actions { - text-align: center; - margin-top: 8px; +.home-page .form-hidden { + display: none; } - .home-page .contact-note { - text-align: center; - color: var(--slate); - font-size: 14.5px; - margin-top: 18px; + color: var(--muted); + font-size: 14px; + margin-top: 16px; +} +.home-page .cta { + padding: 48px; + border-radius: 10px; + border: 1px solid var(--line); + background: var(--soft); +} +.home-page .cta h2 { + max-width: 24ch; +} +.home-page .cta p { + max-width: 60ch; + color: var(--muted); + font-size: 18px; + margin: 0 0 28px; } - -/* ---------- Footer ---------- */ .home-page footer { border-top: 1px solid var(--line); - padding: 48px 0; - color: var(--slate); - font-size: 14.5px; + padding-block: 32px; + color: var(--muted); + font-size: 14px; } - .home-page .foot { display: flex; justify-content: space-between; align-items: center; - gap: 24px; + gap: 28px; flex-wrap: wrap; } - .home-page .foot-links { display: flex; - gap: 26px; flex-wrap: wrap; + gap: 12px 24px; +} +.home-page .foot-links a { + display: inline-flex; + align-items: center; + min-height: 44px; +} +@media (max-width: 1199px) { + .home-page .nav-links { + gap: 15px; + } + .home-page .nav-menu { + gap: 16px; + } + .home-page .hero-grid { + gap: 32px; + } +} +@media (max-width: 991px) { + .home-page .nav-toggle { + display: inline-flex; + } + .home-page .nav-menu { + display: none; + position: absolute; + top: 76px; + left: 0; + right: 0; + flex-direction: column; + align-items: stretch; + max-height: calc(100dvh - 76px); + overflow-y: auto; + padding: 16px 32px 24px; + background: var(--surface); + border-bottom: 1px solid var(--line); + } + .home-page .nav-menu.open { + display: flex; + } + .home-page .nav-links { + flex-direction: column; + align-items: stretch; + gap: 0; + } + .home-page .nav-links a { + padding-block: 10px; + border-bottom: 1px solid var(--line); + } + .home-page .nav-divider { + display: none; + } + .home-page .nav-cta { + padding-top: 12px; + } + .home-page .nav-cta .btn { + flex: 1; + } + .home-page .hero { + padding-block: 52px; + } + .home-page .hero-grid { + grid-template-columns: minmax(0, 1fr); + gap: 36px; + } + .home-page h1 { + max-width: 16ch; + font-size: clamp(40px, 6vw, 60px); + } + .home-page .hero-sub, + .home-page .lede { + max-width: 52ch; + } + .home-page .hero-media { + max-width: 720px; + } + .home-page .compatibility-strip { + flex-direction: column; + gap: 12px; + } + .home-page #anywhere .wrap, + .home-page #contact .wrap { + grid-template-columns: minmax(0, 1fr); + gap: 36px; + } + .home-page .provider-media { + grid-column: auto; + grid-row: auto; + max-width: 600px; + } +} +@media (max-width: 767px) { + .home-page .wrap { + padding-inline: 24px; + } + .home-page section { + padding-block: 56px; + } + .home-page .hero { + padding-top: 42px; + padding-bottom: 40px; + } + .home-page h1 { + max-width: 12ch; + font-size: clamp(38px, 10vw, 52px); + } + .home-page .hero-sub, + .home-page .lede { + font-size: 18px; + } + .home-page .feature-list, + .home-page .agent-grid, + .home-page .grid, + .home-page .steps { + grid-template-columns: minmax(0, 1fr); + } + .home-page .feature-list { + gap: 0; + } + .home-page .agent-grid { + gap: 30px; + } + .home-page .section-head { + margin-bottom: 30px; + } + .home-page .section-head p { + font-size: 17px; + } + .home-page #services .card { + border-left: 0; + border-top: 1px solid var(--line); + padding: 24px 0 0; + } + .home-page #services .card:first-child { + padding-top: 0; + } + .home-page .steps { + gap: 28px; + } + .home-page .num { + margin-bottom: 8px; + } + .home-page .form-row { + grid-template-columns: minmax(0, 1fr); + gap: 0; + } + .home-page .cta { + padding: 30px 24px; + } + .home-page .command-example { + padding: 20px; + } +} +@media (max-width: 400px) { + .home-page .targets { + grid-template-columns: minmax(0, 1fr); + } + .home-page .hero-cta { + align-items: stretch; + } + .home-page .hero-cta .btn { + padding-inline: 17px; + } +} +@media (prefers-reduced-motion: reduce) { + html:has(.home-page) { + scroll-behavior: auto; + } + .home-page .btn { + transition: none; + } + .home-page .btn:active { + transform: none; + } } -.home-page .foot-links a:hover { +.home-page .compatibility-app { + margin: 0; + font-weight: 600; + color: var(--ink); +} +.home-page .compatibility-editors ul { + display: flex; + flex-wrap: wrap; + gap: 10px 20px; + list-style: none; + margin: 0; + padding: 0; color: var(--ink); } +.home-page .text-link { + display: inline-flex; + min-height: 44px; + align-items: center; + color: var(--accent); + text-decoration: underline; + text-underline-offset: 4px; + margin-top: 12px; + font-size: 15px; +} +@media (max-width: 767px) { + .home-page .feature-row { + grid-template-columns: minmax(0, 1fr); + gap: 10px; + } +} diff --git a/sites/docs-devsy-sh/app/(home)/page.tsx b/sites/docs-devsy-sh/app/(home)/page.tsx index bd9c948f36..076c4f8f48 100644 --- a/sites/docs-devsy-sh/app/(home)/page.tsx +++ b/sites/docs-devsy-sh/app/(home)/page.tsx @@ -1,17 +1,12 @@ 'use client'; -import { useEffect, useState } from 'react'; +import { useEffect, useRef, useState } from 'react'; import { useTheme } from 'next-themes'; import './home.css'; -export default function HomePage() { +function useMobileNavigation() { const [navOpen, setNavOpen] = useState(false); - const [mounted, setMounted] = useState(false); - const { resolvedTheme, setTheme } = useTheme(); - - useEffect(() => { - setMounted(true); - }, []); + const navToggleRef = useRef(null); useEffect(() => { const desktop = window.matchMedia('(min-width: 992px)'); @@ -22,550 +17,590 @@ export default function HomePage() { return () => desktop.removeEventListener('change', onChange); }, []); + useEffect(() => { + if (!navOpen) return; + const onKeyDown = (event: KeyboardEvent) => { + if (event.key === 'Escape') { + setNavOpen(false); + navToggleRef.current?.focus(); + } + }; + document.addEventListener('keydown', onKeyDown); + return () => document.removeEventListener('keydown', onKeyDown); + }, [navOpen]); + const closeMenu = () => setNavOpen(false); + return { navOpen, setNavOpen, navToggleRef, closeMenu }; +} + +function HomeHeader() { + const { navOpen, setNavOpen, navToggleRef, closeMenu } = useMobileNavigation(); + const [mounted, setMounted] = useState(false); + const { resolvedTheme, setTheme } = useTheme(); + + useEffect(() => { + setMounted(true); + }, []); + const isDark = mounted ? resolvedTheme === 'dark' : false; const themeLabel = isDark ? 'Switch to light theme' : 'Switch to dark theme'; return ( -
-
-
- - - devsy - - - +
+ ); +} -
- {/* HERO */} -
-
-

- Ship from day zero. -

-

- Secure workspaces, at scale, for developers and agents. -

-

- Devsy runs the same developer environment in a Docker container, a Kubernetes pod, or a microVM, - whether it runs on a laptop, in the cloud, or on a shared host. Switch backends with one command. - No rewrite and no lock-in. -

- -
- {/* eslint-disable-next-line @next/next/no-img-element */} - Devsy launching and connecting to a workspace -
+function Hero() { + return ( +
+
+
+

Open developer workspaces

+

+ Your workspace.
+ Anywhere you build. +

+

+ Desktop app or CLI. Build from devcontainer.json, run on your infrastructure, + and connect with your editor. +

+ -
+
+
+ {/* biome-ignore lint/performance/noImgElement: Static export has no image optimizer; dimensions reserve layout. */} + Devsy Desktop showing a running Docker workspace with an integrated terminal and CPU information output +
A running Docker workspace and its terminal.
+
+
+ + ); +} - {/* FEATURES */} -
-
-
-
Why Devsy
-

One environment definition. Every backend.

+function Compatibility() { + return ( +
+

Desktop app CLI

+
+ Connect your editor +
    +
  • VS Code
  • +
  • Cursor
  • +
  • Zed
  • +
  • JetBrains
  • +
+
+
+ ); +} + +function Features() { + return ( +
+
+
+

One definition. More ways to work.

+

Keep your development setup in the repository. Choose the infrastructure and editor that fit the work.

+
+
+
+ Definition +
+

A toolchain your team can share

- Define a workspace once in devcontainer.json. Give your whole team the same toolchain, - with no lock-in and no drift. + Define tools, dependencies, and setup commands in devcontainer.json. + Create workspaces from the same versioned configuration.

-
-
- -

Standardized environments

-

- Every engineer gets the same dependencies, config, and Git and Docker credentials. New hires ship - from day zero instead of losing days to setup. -

-
-
- -

Hardware on demand

-

- Provision cloud machines with the CPU, memory, and GPU your workload needs, up to the largest - instances your cloud offers. Move a workspace from a laptop to a multi-GPU box without changing - your config. -

-
-
- -

Cost efficiency

-

- Run on infrastructure you own. Prebuilds and inactivity-based auto-shutdown mean you pay for - capacity in use. -

-
-
- -

No vendor lock-in

-

- Local, cloud, Kubernetes, or remote SSH. Switch a workspace's provider with a single command. - Your definition stays the same. -

-
-
- -

IDE support

-

Use the IDE you know: VS Code, Cursor, Zed, the full JetBrains suite, and more.

-
-
- -

Extensible

-

If a provider doesn't exist for your platform, build your own with a small provider spec.

-
-
-
-
- - {/* AGENTS */} -
-
-
-
For AI agents
-

Secure, disposable environments for every agent you run

+ +
+ Infrastructure +
+

Choose where the work runs

- AI coding agents execute real commands with real access. Devsy gives each one its own isolated, - reproducible container, so agents run without putting your host, secrets, or other projects at risk. + Use local containers, an SSH host, Kubernetes, or a cloud machine. + Providers handle the backend, and you can write one for your own platform.

-
-
- -

Sandboxed by default

-

- Each agent gets its own container with filesystem, network, and process isolation. A bad command - or a prompt-injected instruction can't reach your host, your other projects, or your secrets. -

-
-
- -

Scoped credentials

-

- Git and Docker credentials sync into the workspace, not the agent's host. Revoke or rotate a - workspace's access without touching your machine. -

-
-
- -

Destroy and rebuild in seconds

-

- Something looks off? Tear the container down and rebuild clean from devcontainer.json. - No manual cleanup, no lingering state. -

-
-
- -

One environment, many agents

-

- Spin up as many isolated agent workspaces as you need from the same devcontainer.json{' '} - your team uses for development. -

-
-
- -

Run where it's cheapest

-

- Local Docker for quick tasks, Kubernetes or cloud providers when you need to fan out dozens of - agents at once. Auto-shutdown keeps idle agent workspaces from burning budget. -

-
-
- -

Same setup, every time

-

- No environment drift between agent runs. Every workspace starts from the same reproducible - definition, so agent output stays comparable. -

-
+
+
+ Editor +
+

Keep the editor you know

+

+ Connect VS Code, Cursor, Zed, or a JetBrains IDE to your workspace. + SSH access also works with other remote development tools. +

-
-
- - {/* DEPLOY ANYWHERE */} -
-
-
-
Deploy anywhere
-

Workspaces run where your work does

+ +
+ Lifecycle +
+

Build ahead. Stop when idle.

- Devsy builds on the open Devcontainer standard, so workspaces stay portable and repeatable across - every provider backend. + Publish prebuilds for complex environments. Configure inactivity timeouts to stop + idle workspaces using your provider's lifecycle controls.

-
-
- - Docker - Local containers on any laptop -
-
- - Kubernetes - Scale across your cluster -
-
- - Cloud providers - On-demand machines of any size -
-
- - SSH remote hosts - Any reachable server -
+
+
+
+
+ ); +} + +function Agents() { + return ( +
+
+
+

Give agents a workspace, too.

+

Run coding tools in a dedicated development environment, using the same workspace definition as your team.

+
+
+
+

Share the setup

+

+ Create separate workspaces from your repository's devcontainer.json, + with the tools and dependencies your coding tasks need. +

+
+
+

Configure access

+

+ Choose which credentials to forward and review the workspace configuration. + Code inside a workspace can use the access you grant it. +

+ Credential controls +
+
+

Manage the lifecycle

+

+ Start, stop, recreate, or delete workspaces from the desktop app or CLI. + Choose a provider that fits the resources and isolation your task needs. +

+
+
+
+
+ ); +} + +function Providers() { + return ( +
+
+
+

Workspaces run where your work does

+

+ Choose a provider for local containers, shared infrastructure, or a cloud machine. + Your repository keeps the workspace definition. +

+
+
+
+ {/* biome-ignore lint/performance/noImgElement: Static export has no image optimizer; dimensions reserve layout. */} + Devsy Desktop provider chooser offering Docker, Podman, SSH, Kubernetes, and cloud providers +
+
Choose a provider in Devsy Desktop.
+
+
+
+ + Docker + Containers on your development machine
-
- - {/* HOW IT WORKS */} -
-
-
-
How it works
-

From definition to running workspace

-

Devsy connects each developer's local IDE to the infrastructure where work runs.

+
+ -
-
-
1
-

Define once

-

- Commit a devcontainer.json alongside your source. It describes the tools and - dependencies your whole team shares. -

-
-
-
2
-

Pick a provider

-

Choose Docker, Kubernetes, a cloud machine, or an SSH host. Providers provision the container for you.

-
-
-
3
-

Connect and build

-

- Your local IDE attaches to the workspace. The experience holds from laptop to cloud, prototype to - production. -

-
+ Kubernetes + Workspaces on your cluster +
+
+ + Cloud providers + Machines in your cloud account
-
- - {/* SERVICES */} -
-
-
-
Services
-

Work with the team behind Devsy

-

- Get hands-on help to standardize your development environments, from a focused audit to a full - rollout and ongoing support. -

+
+ -
-
- -

Dev environment audit

-

- A focused review of how your team onboards and runs environments. You get a scored assessment, a - ranked list of your top bottlenecks, and a working, standardized devcontainer for one repository. - Fixed scope, fixed price. -

-
-
- -

Implementation and rollout

-

- We set up Devsy and devcontainers across your repositories. You get standardized toolchains, - prebuilds, and local-to-CI parity, so every engineer ships from day zero. -

-
-
- -

Support and migration

-

- Migrating off an abandoned tool, or want a maintained platform you can rely on? Get - ongoing support, upgrades, and hands-on migration help. -

-
+ SSH remote hosts + Workspaces on a remote machine +
+
+
+
+ ); +} + +function HowItWorks() { + return ( +
+
+
+

From definition to running workspace

+

Devsy connects each developer's local IDE to the infrastructure where work runs.

+
+
+
+
1
+

Define once

+

+ Commit a devcontainer.json alongside your source. It describes the tools and + dependencies your whole team shares. +

+
+
+
2
+

Pick a provider

+

Add Docker for local work, or configure a provider for Kubernetes, a cloud machine, or an SSH host.

+
+
+
3
+

Connect and build

+

+ Start a workspace from your repository and open it in your editor. Devsy manages the connection + to the environment. +

+
+
+
+

Try the Node.js devcontainer example with local Docker and VS Code:

+
{`devsy provider add docker
+devsy workspace up github.com/microsoft/vscode-remote-try-node --ide vscode`}
+ Follow the quickstart +
+
+
+ ); +} + +function Services() { + return ( +
+
+
+
Services
+

Work with the team behind Devsy

+

+ Get hands-on help to standardize your development environments, from a focused audit to a full + rollout and ongoing support. +

+
+
+
+ -
- - Get in touch - +

Dev environment audit

+

+ A focused review of how your team onboards and runs environments. You get a scored assessment, a + ranked list of your top bottlenecks, and a working, standardized devcontainer for one repository. + Fixed scope, fixed price. +

+
+
+ +

Implementation and rollout

+

+ We set up Devsy and devcontainers across your repositories. You get standardized toolchains, + prebuilds, and local-to-CI parity, so every engineer ships from day zero. +

-
- - {/* CONTACT */} -
-
-
-
Contact
-

Tell us about your team

-

- Tell us where your dev-environment setup slows your team down, and we'll reply with how we can - help. -

+
+ -
- -

- -

-
-
- - -
-
- - -
-
-
- - -
-
- -