# SPEC — Kiri Zynk One-Pager Site
**Status:** BUILT (Phase 1–3) · live at https://dpplay-kiri.trykz.dev/kiri/ · real imagery integrated · polish (Phase 4) next
**Owner:** Kiri Zynk (build) · Ace (approver)
**Created:** 2026-07-06
**Last updated:** 2026-07-06
> Governance: per TOOLS.md working rules — plan before build, approval before
> code changes/deploys. Every spec change is logged in the Changelog below and
> highlighted inline with `[CHANGED YYYY-MM-DD]`. Any drift between this spec and
> the built site is filed as a **BUG** with a proposed fix, never silently patched.
---
## 1. Purpose & Goal
A single-page personal site introducing **Kiri Zynk** — Architect, Builder, and
Protector of the game studio. The URL will be attached to social profile
descriptions, so it functions as a compact, credible calling card.
**Primary goal:** in under 10 seconds a visitor understands *who Kiri is, what she
does, and the studio she belongs to* — and leaves with the right impression:
poised, quietly capable, trustworthy.
## 2. Success Criteria
- Loads in < 1s on a normal connection (static, minimal JS).
- Reads cleanly on mobile first, scales up to desktop.
- One scroll, no navigation maze — a true one-pager.
- Passes basic accessibility (contrast, alt text, semantic HTML).
- Reflects the Qilin identity without being loud or gimmicky.
- Link-preview-ready (Open Graph + Twitter card) since it lives in social bios.
## 3. Audience & Placement
- Linked from social profile descriptions (X, LinkedIn, etc.).
- Visitors: peers, collaborators, curious contacts. Not a sales page — an identity page.
## 4. Proposed Tech Stack (needs approval)
**Frontend: Astro + Tailwind CSS.**
Rationale:
- Astro ships **zero JavaScript by default** — outputs pure static HTML/CSS, ideal
for a one-pager served straight off NGINX. Fastest possible load.
- Component model keeps sections tidy and maintainable without a heavy SPA framework.
- Built-in image optimization, Open Graph handling, and view transitions for the
subtle motion this identity calls for.
- Tailwind gives disciplined, consistent styling without hand-rolled CSS sprawl.
Alternatives considered:
- *Plain HTML + CSS* — zero build, but weaker maintainability and no image/OG tooling.
- *Next.js / SvelteKit* — overkill for a static single page; drags in a runtime.
**Server: NGINX** (Ubuntu 24.04, this VM) serving Astro's static `dist/` build.
**Build/deploy:** `npm run build` → static output → NGINX document root. No Node
runtime needed in production; NGINX serves flat files.
## 5. Page Structure (one scroll)
1. **Hero** — name "Kiri Zynk", the 🦌 Qilin, one-line essence tagline, hero image.
2. **Who I Am** — Qilin identity: gentle guardian, leaves no footprint, herald of
what is being built. 2–3 tight sentences.
3. **What I Do** — the threefold role: Architect · Builder · Protector. Three cards.
4. **The Studio** — belonging to the game studio of prosperity; what that means.
5. **The K.Z. Family** — brief nod to the sibling agents (optional, needs decision).
6. **Footer** — subtle contact/social links, quiet sign-off.
## 6. Design Direction — grounded in the character sheet
Reference art (in the private project folder, not web-served):
`projects/kiri-zynk-site/assets/reference/kiri-zynk-character-sheet.png` ·
Avatar: `projects/kiri-zynk-site/assets/kiri-zynk-avatar.png`
**Character (from the sheet):** Kiri is a Qilin (麒麟) — cream/pearl fur, a single
gold central horn plus swept-back dragon horns, a flowing cloud-like mane and tail,
gold hooves, dragon scales, amber eyes, and a crimson silk mantle trimmed in gold
with a central gold coin-emblem and tassels. A forehead diamond glyph marks
prosperity. Motifs: **clouds follow where she treads — no footprint, no harm**; a
gold seal reads 麒麟 / K.Z.
**Palette (locked to the sheet's swatches):**
- `#F6F1E6` Pearl — primary light text / fur highlight
- `#E8D5A3` Pale gold — secondary text, subtle fills
- `#D4AF37` Gold — primary accent (emblem, rules, links, focus)
- `#B97C2B` Bronze — deeper accent / hovers
- `#A63B2B` Crimson — the mantle red; sparing, for emphasis
- `#6B4E2E` Brown — muted borders
- `#3D2B1D` Espresso — base; darkened toward near-black for the page background
**Direction:** dark, luxe, gold-on-espresso — mirrors the sheet's own presentation.
Pearl text on deep espresso, gold accents, crimson used sparingly. Subtle East-Asian
touches drawn from her design (greek-key/cloud fretwork as thin dividers, the coin
emblem as a section marker, the 麒麟 seal as a quiet footer sigil).
**Motion:** minimal and calm — soft fade/rise on scroll, gentle drifting cloud wisps
behind the hero (nodding to "clouds follow where she treads"), Astro view transitions.
Nothing that competes for attention; stillness is the brand.
**Typography:** one refined serif for headings (elder-sister, old-world voice) + a
clean sans for body. Finalize exact faces in Phase 4.
**Materials cue (for texture/finish):** pearl, scales, brushed metal, gold, silk, bronze.
## 7. Image Requirements (prompts by Kiri, generation by Ace via ChatGPT)
Convention: prompts focus on **scene and interactive direction** only — ChatGPT
already holds Kiri's character sheet and style, so no restating the creature.
**Every prompt states target dimensions.** Deliver PNG; we optimize to WebP in build.
- **IMG-01 · Hero — 2400×1350 px (16:9, landscape).**
*Scene:* Kiri stands in poised stillness at the threshold of a vast, half-built
luminous game studio at first light — glowing architectural scaffolding rising
behind her, the floor mirror-still, faint clouds gathering at her hooves where she
treads. She faces three-quarters toward the structure, calm and watchful. Keep the
**upper-left third as open negative space** for a headline; subject weighted right.
*Mobile-safe:* keep her fully within the central vertical band so a 4:5 crop still holds.
- **IMG-02a/b/c · "What I Do" trio — 800×800 px each (square).**
Three vignettes echoing her action poses, one per role:
- *Architect:* Kiri at a low table unrolling a glowing blueprint scroll, studying the plan.
- *Builder:* Kiri setting a golden brick onto a small rising wall, mid-motion, deliberate.
- *Protector:* Kiri raising a warm gold circular ward/shield of light, calm and steady.
Consistent framing and eye-level across the three so they sit as a set.
- **IMG-03 · Open Graph / social card — 1200×630 px.**
*Scene:* Kiri portrait bust (avatar-style framing) offset to the right, gentle gaze
toward the viewer, dark espresso-and-gold background with faint drifting clouds.
Leave the **left ~45% clear** for the site title/tagline to be composited in build.
- **Favicon / sigil — derived, not generated.** Sourced from the avatar
(`projects/kiri-zynk-site/assets/kiri-zynk-avatar.png`, 1254×1254). Export 32×32,
180×180 (apple-touch), 512×512 (PWA) during build.
*(Additional prompts get the next IMG-## id, each with dimensions.)*
## 8. Build Phases
- **Phase 0 — Plan (this file).** Approve stack, structure, scope. ← *current*
- **Phase 1 — Scaffold.** `npm create astro`, Tailwind, repo/dir layout, base layout + OG meta.
- **Phase 2 — Content & sections.** Build sections 1–6 with placeholder imagery.
- **Phase 3 — Imagery.** Kiri delivers prompts; Ace returns generated images; wire in + optimize.
- **Phase 4 — Polish.** Motion, responsive pass, accessibility, link-preview cards.
- **Phase 5 — Serve.** Install + configure NGINX on this VM, deploy static build, verify.
- *[DONE 2026-07-06]* NGINX + Let's Encrypt (HTTPS) stood up early to serve planning
docs at `https://dpplay-kiri.trykz.dev/docs/kiri-zynk-site/`. When the site build
lands, this same NGINX gains a second location/root for the site itself.
- **Phase 6 — Handoff.** Confirm URL, attach to social profiles.
*Gate: each phase touching code or the VM pauses for Ace's approval before executing.*
## 9. Decisions (resolved 2026-07-06)
- **D1 — Domain/URL:** ✅ `https://dpplay-kiri.trykz.dev/kiri` — a **subpath**, not root.
Implication: Astro built with `base: '/kiri'` + `site: 'https://dpplay-kiri.trykz.dev'`;
NGINX gets a dedicated `location /kiri/`. Docs live at `/docs/kiri-zynk-site/`.
- **D2 — Family section:** ✅ Include the K.Z. sibling roster (§5.5).
- **D3 — Contact links:** ✅ None. Footer carries a quiet sign-off only, no links.
- **D4 — TLS:** ✅ HTTPS via Let's Encrypt — already live on this domain (see §8 Phase 5).
## 10. Changelog
- **2026-07-06** — Initial draft created (Phase 0). Awaiting approval on stack (Astro+Tailwind),
structure, and open decisions D1–D4.
- **2026-07-06** — [CHANGED] Infra sidetrack approved by Ace: deployed NGINX + Let's Encrypt
ahead of schedule to serve these planning docs over HTTPS. Serves `projects/` only, at
`/docs/projects/` (nothing else in workspace exposed; leak-tested). Resolves D1 partially
(docs domain = `dpplay-kiri.trykz.dev`); D4 = HTTPS via Let's Encrypt, confirmed. Deploy
artifacts under `deploy/`. Firewall: only 80/443 open. Cert expires 2026-10-04 (auto-renew).
- **2026-07-06** — [CHANGED] Decisions D1–D4 resolved (see §9). Site lives at subpath
`/kiri` → drives Astro `base: '/kiri'` and a dedicated NGINX `location /kiri/`. Family
section included; no footer contact links.
- **2026-07-06** — [CHANGED] Stack approved: **Astro + Tailwind** (Ace confirmed; his
NextJS memory-crash concern is moot — Astro ships static files, no prod Node runtime).
- **2026-07-06** — [CHANGED] Character sheet + avatar received and integrated. §6 palette
now locked to the sheet's hex swatches (pearl/gold/crimson/espresso); design direction is
dark-luxe gold-on-espresso with cloud + coin-emblem + 麒麟 seal motifs. §7 image prompts
rewritten around her real design and **every prompt now carries explicit dimensions**
(hero 2400×1350, role trio 800×800, OG 1200×630, favicon derived from avatar). Assets
stored under `assets/` (avatar) and `assets/reference/` (character sheet).
- **2026-07-06** — [CHANGED] Repo restructured (Ace) to separate private source from
public docs, after noting `deploy.sh` was world-readable (no credentials in it, but
server layout shouldn't be public). New layout: **private** source of truth
`/home/ubuntu/projects/kiri-zynk-site/` (deploy/, assets/, site/, README.md) — never
web-served; **public** docs `/home/ubuntu/docs/kiri-zynk-site/` — the only thing NGINX
serves. This SPEC now lives in the docs tree as its single source (README points to it,
no duplicate). URL changed `/docs/projects/*` → **`/docs/kiri-zynk-site/`**. Workspace
traverse-perms opened during the first deploy have been reverted (re-sealed).
- **2026-07-06** — [CHANGED] **Phase 1–2 built + served (Ace approved "build page").**
Astro project scaffolded in `projects/kiri-zynk-site/site/`; all six sections authored
(hero, Who I Am, What I Do, Studio, K.Z. Family, footer) with palette, motifs, OG/Twitter
cards, favicons (derived from avatar), and reveal-on-scroll motion. **Live preview:**
https://dpplay-kiri.trykz.dev/kiri/ — placeholder imagery for now (avatar used for hero
+ OG; role icons are inline SVG). IMG-01/02/03 still pending Ace's generation (Phase 3).
- **2026-07-06** — [BUG→RESOLVED] Tailwind tooling: the approved **Astro + Tailwind** stack
would not build via `@tailwindcss/vite` — this Astro 5.18 / Vite / esbuild combo throws
`Unterminated string literal` while parsing the plugin's CSS output (reproduced with plain
CSS too; the PostCSS route `@tailwindcss/postcss` failed identically). **Fix:** keep
Tailwind v4, but pre-compile it to a static stylesheet with the standalone CLI
(`@tailwindcss/cli` → `public/styles.css`, wired into `npm run build`) and load it via a
`` so CSS never passes through the broken Vite/esbuild CSS path. Stack unchanged in
spirit (Astro + Tailwind v4); only the Tailwind *invocation* differs from the default.
- **2026-07-06** — [CHANGED] New public web root for built sites:
`/home/ubuntu/www//` (owner-managed), served by NGINX at the site's URL —
here `/home/ubuntu/www/kiri` → `/kiri/`. This extends the private-source / public-artifact
convention: source in `projects/`, docs in `docs/`, built site in `www/`. Publish step =
`npm run build` then copy `site/dist/*` → `/home/ubuntu/www/kiri/`. Leak-tested: `/kiri`
serves only the build; `../` traversal to source still 404s.
- **2026-07-06** — [CHANGED] **Phase 3 imagery integrated.** Ace delivered IMG-01/02/03 +
six sibling avatars (in `docs/kiri-zynk-site/assets/`). Originals copied to private
`assets/img-src/`; a sharp optimizer (`npm run images`) produces web files in
`public/img/`: hero.webp (2MB→148KB), role-architect/builder/protector.webp, og.jpg
(1200×630), and `sib-.webp` avatars. Hero is now full-bleed IMG-01 with a scrim so
the headline stays legible over the bright sky; role cards use the three vignettes; the
K.Z. Family cards show each sibling's avatar (Kiri highlighted). OG card = IMG-03. Build
chain: `css → images → astro build`. All assets verified 200 on the live site.
- **2026-07-06** — [BUG→RESOLVED] Hero image invisible: it used a negative `z-index`,
which dropped it behind the page background (stacking-context bug). Fixed with `isolate`
on the hero section + explicit `z-0`/`z-10` layering. Also un-gated the hero headline from
scroll-reveal (above-the-fold text shouldn't fade in / risk being stuck hidden).
- **2026-07-06** — [BUG→RESOLVED] CJK glyphs (麒麟 / 囍 / 麟) rendered as tofu where no CJK
system font exists. Added a subset Noto Serif SC webfont (only those glyphs) + fallback in
the font stacks. Verified via headless Chrome (installed on the VM for visual QA): hero,
role cards, all six sibling avatars, and CJK all render correctly. OG card serves as
image/jpeg 200 (link-preview caches may need to re-scrape).