Align staging/production builds with APP_VARIANT bundle IDs, allow staging HTTP on iOS, add ios-prebuild scripts for TestFlight, and show connected API URL on About for non-production builds.
Co-authored-by: Cursor <cursoragent@cursor.com>
Match playback refs to the correct assistant segment so the interrupt overlay
does not block other bubbles, and preempt local playback when switching segments.
Co-authored-by: Cursor <cursoragent@cursor.com>
After sign-out or data purge, clear session state reliably, remount the
splash overlay above navigation, and navigate to login instead of tabs so
users no longer briefly land on the chat home screen.
Co-authored-by: Cursor <cursoragent@cursor.com>
Explain invite vs. generating state using MemoirState slots, surface remaining
characters to the display gate, refresh memoir-state on pull, and sync i18n.
Co-authored-by: Cursor <cursoragent@cursor.com>
Replace the boolean large-text flag with three global typography tiers,
defaulting new installs to the smallest tier when English is in effect
while preserving legacy storage and Chinese defaults. Add a profile
sub-screen to pick the tier and unit tests for storage resolution.
Co-authored-by: Cursor <cursoragent@cursor.com>
Detect consecutive tts_auto items on the same assistant bubble via listKey (uuid_seg_n / uuid_part_n). When paused, skip the 'clear queue and play latest only' path so later segments enqueue instead of wiping playback. Add regression test.
Co-authored-by: Cursor <cursoragent@cursor.com>
Share font size, font family, and background across all memoir chapters via MemoirReadingSettingsProvider and SecureStore (same app-settings pattern). Add parse/merge helpers and unit tests.
Co-authored-by: Cursor <cursoragent@cursor.com>
Allow staging deployments to expose /api/auth/mock/sms-login by reading APP_ENV from runtime env and setting staging APP_ENV plus MOCK_SMS_LOGIN_ENABLED in staging env config.
Co-authored-by: Cursor <cursoragent@cursor.com>
- Extract maybe_send_topic_chips_ws for WS connect + pipeline reuse
- Default memoir stage to childhood when empty for chip bank lookup
- Resend suggestions after normal assistant reply (English/Chinese)
Co-authored-by: Cursor <cursoragent@cursor.com>
- Pipeline: skip _send_tts_audio only for non-manual when ENABLE_TTS=false;
remove enable_tts early return from handle_tts_request_on_demand.
- Tencent TTS: PrimaryLanguage/chunking follow user language preference only.
- Expo: let manual tts_audio bypass late-segment playback gate after interrupt.
- Docs: clarify ENABLE_TTS vs tts_request in api/.env.example and TTSProvider port.
- Tests: add manual bypass cases; adjust pipeline language tests for en+Chinese text.
Co-authored-by: Cursor <cursoragent@cursor.com>
Two complementary changes to reduce conversation cold-start friction:
A. Returning-user re-greeting (backend)
- When WS reconnects to a non-empty conversation and last_message_at is older
than chat_re_greeting_idle_hours (default 6h), the agent emits a warm
continuation message that references prior history instead of staying silent.
- Self-debouncing: the AI message updates last_message_at, so reconnects
within the window will not re-trigger.
- Skipped while profile collection is still pending.
D. Topic suggestion chips (backend + Expo)
- New WS message type topic_suggestions carries 3-4 quick-start chips derived
from the current memoir stage's empty slots (deterministic, no extra LLM
cost). Sent alongside opening / re-greeting / resume.
- Expo chat screen renders a horizontally-scrollable chip row above the input
bar; tapping a chip sends the chip's text as a user message and clears the
row. Sending any text/voice also clears the chips.
Prefetch opening over WebSocket from the conversations list before navigation, with prepared-session handoff into the chat screen. Add a single-slot background pool so leaving chat (in-app) keeps the last session socket with UI callbacks stripped; dispose on app background and reconnect after resume when the chat screen is mounted. Tear down pooled sockets on logout, purge, and conversation delete. RealtimeSession supports attachUiCallbacks and idempotent dispose, and the chat composer hides the connection notice while connecting if assistant history already exists. Fix pause handler wiring in the conversation screen.
Co-authored-by: Cursor <cursoragent@cursor.com>