尚未检测到更新。GitHub 发布版本后会显示在这里。
个人 GitHub 账号下公开仓库的所有者可以登录并验证所有权,自行管理介绍,无需管理员批准。
登录并生成验证文件,在 30 分钟内将其提交到此仓库的默认分支。其他分支或分叉仓库中的文件无效。然后在下方检查文件,即可无需管理员批准直接管理项目。请保留文件以维持管理权限。
如需登录,将前往登录页面。登录后请回到此处,再次点击所选的验证按钮。
在项目文件夹中运行 /nomorevibe verify,即可验证所有权并自行管理介绍。
一分钟完成验证my beloved app
翻译准备中
取自仓库 README
正在加载完整 README。 以下为已保存的摘录。
A private space for two, built around the 777 Relationship Rule:
Every 7 days a date · every 7 weeks a mini adventure · every 7 months something bigger.
Not another calendar. A rhythm two people keep together, and a record of what
they made while keeping it.
build:static routes on the hash and emits pure-ASCII output, so the bundle can
be inlined into one self-contained HTML file and served from anywhere — a host
that can't rewrite deep links to index.html, or a page whose charset it does
not control. The default build keeps clean paths and is what a real deployment
should use.查看完整 README ↗A private space for two, built around the 777 Relationship Rule:
Every 7 days a date · every 7 weeks a mini adventure · every 7 months something bigger.
Not another calendar. A rhythm two people keep together, and a record of what they made while keeping it.
npm install
npm run dev # http://localhost:5173
npm run build # typecheck + production build
npm run build:static # single-file build for static hosting
build:static routes on the hash and emits pure-ASCII output, so the bundle can
be inlined into one self-contained HTML file and served from anywhere — a host
that can't rewrite deep links to index.html, or a page whose charset it does
not control. The default build keeps clean paths and is what a real deployment
should use.
Mobile-first: open it on a phone, or narrow the browser. On a wide screen it renders inside a centred device frame.
All nine of the first-pass screens, wired into one loop:
| Onboarding | 5 steps — the rule, the two of you, the invite code, what stays private |
| Home | The three 777 countdowns, today's prompt, inspiration, recent memories |
| Explore | Date generator (6 filters + Surprise Me), mini adventures, big-trip wishlist |
| Plan a date | One editor for all three tiers, with a surprise toggle |
| Plan detail | Countdown, details, "We did this", and a planning space for big trips |
| Memories | Month-grouped timeline with a date gutter and connecting thread |
| Memory detail | Gallery, a shared line, each partner's own words, a private note |
| Memory capture | Offered automatically the moment a plan is completed |
| Relationship Room | 12 guided conversations: answer privately → reveal → agree one thing |
| Daily question | Sealed until you have both answered |
| Notes | Send now, send later, or keep private |
| Us | The relationship profile, presented emotionally rather than as a scoreboard |
prompt → connect → plan → experience → capture → look forward
Every screen has an exit into the next stage. Finishing a Room conversation offers to put something in the diary; revealing a daily answer offers to turn it into a plan; completing a plan opens memory capture; capturing resets the countdown. See docs/PRODUCT.md for the full architecture, data model, and design system.
The split is enforced in the data model, not just hidden in the UI.
A partner's surprise renders as "A surprise, from them" and nothing more. A mutual wishlist save is never named anywhere until the reveal has been shown.
Writing a memory is one box and then a short conversation: what was written is read for when, where, how it felt and what kind of moment it is, and only what the note left out is asked about — two or three questions, one at a time, all skippable.
The reading happens in api/memory-read.ts, a serverless function, so the API
key stays on the server. It returns one structured object (tone, type, title,
date, place, feelings, the next question and its quick replies, a default
visibility, and which follow-on offers fit). src/lib/memoryAi.ts calls it and
builds the same object on the phone when there is no key, no endpoint, or no
signal — the screens never learn which they got.
Two rules do not depend on the model, and are enforced in the prompt, in the endpoint and in the client:
supabase/migrations/0002_memory_visibility.sql), not a flag the client
respects;The sentence said back to you is written by whatever did the reading, for that note. The fallback does not write one: it says "Got it." to everybody, because pattern matching can be confidently wrong about a sentence it has never seen, and a wrong guess dressed as an emotional response is worse than none.
MEMORY_AI_API_KEY and MEMORY_AI_MODEL (default claude-opus-5) configure
it. npm run test:ai checks the rules against a model that ignores its brief.
Which reader is running. Us → Settings says so in words. For the detail,
open any screen with ?debug=1 — the capture flow then shows a small badge
reading Reading with Claude or Using local fallback, with the tone that
came back and, on a fallback, why. ?debug=0 turns it off again.
React 19 · TypeScript · Vite · react-router · CSS Modules over a design-token
layer. State is a reducer in context, persisted to localStorage — no backend,
by design. Sample data is generated relative to today, so the prototype never
goes stale.
Type is San Francisco on Apple platforms and Inter everywhere else. The palette is soft blush and warm neutrals with a single rose accent, and every primary action carries the pink → peach gradient. Light only, by design.
src/
components/ui/ design-system primitives
components/layout/ AppShell, TabBar, Screen
features/ RitualCard, DailyCard, MemoryCard, IdeaCard, …
screens/ one file per screen + its CSS module
data/ ideas, adventures, destinations, prompts, topics, seed
lib/ types, dates & the 777 rhythm, selectors, generator
styles/ tokens.css, global.css
Two things stand in for infrastructure a real build would have:
picsum.photos, and memory capture
offers a mock camera roll rather than a file picker. Every image falls back to
a warm gradient if it fails to load.