Commit Graph

284 Commits

Author SHA1 Message Date
Jeff Emmett 2bbe50991d fix: exclude server paths from space-to-subdomain redirect
The bare-domain routing logic was redirecting all multi-segment paths
like /api/modules → api.rspace.online/modules. Add exclusion for
known server path prefixes (api, admin, admin-data, admin-action,
.well-known) so they fall through to Hono route handlers instead.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 23:11:49 -08:00
Jeff Emmett 85ac897a1a fix: use single-segment admin endpoints to bypass Cloudflare redirect
Cloudflare has a wildcard rule that redirects any multi-segment path
on rspace.online to a subdomain (e.g. /foo/bar → foo.rspace.online/bar).
This broke both /api/* and /admin/api/* paths.

Replace with single-segment endpoints:
- GET /admin-data — returns spaces + modules (admin-only)
- POST /admin-action — handles mutations like delete-space

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:58:37 -08:00
Jeff Emmett caae204c2b fix: bypass Cloudflare /api/* redirect for admin dashboard
Cloudflare has a redirect rule that rewrites rspace.online/api/* to
http://api.rspace.online/*, causing Mixed Content errors in the browser.
Add a separate /admin/api router that serves the same admin data at
paths that don't trigger the redirect rule.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:51:23 -08:00
Jeff Emmett 8d77c6eee8 fix: canvas tools place shapes exactly where the ghost placeholder shows
- newShape() with explicit position now places directly at click point
  instead of routing through findFreePosition spiral which could nudge
  the shape away from the cursor
- Sticky note converted to setPendingTool so it shows dotted placeholder
  before placement instead of instantly spawning at viewport center
- Feed tool converted to setPendingTool with __postCreate for the same
  click-to-place UX
- Removed wb-sticky from mobile keepOpen list since it's now a
  placement tool that should close the menu

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:42:33 -08:00
Jeff Emmett 47b585665d fix: rename rStack to rSpace in app switcher dropdown
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:35:21 -08:00
Jeff Emmett 2b58068a1a feat: persistent sessions with 30-day JWT and auto-refresh on page load
Sessions now last 30 days instead of 15 minutes. Both the rstack-identity
component and legacy header auto-refresh the token when < 7 days remain,
so users who visit at least once every ~23 days stay logged in indefinitely.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:33:31 -08:00
Jeff Emmett 783be14a11 fix: default canvas to dark mode and hide legacy community-info box
Canvas page was hardcoded to data-theme="light" while all other pages
default to dark. Also hides the redundant #community-info overlay
(slug/URL box) since the shell header space switcher already shows this.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:30:27 -08:00
Jeff Emmett b12cc52892 feat: admin dashboard with user management and delete capabilities
- Add tabbed admin UI (Spaces | Users) with auth gate
- Add admin API endpoints on EncryptID: list users, delete user, clean space members
- Add admin force-delete space endpoint on rSpace (bypasses owner check)
- Protect all admin endpoints with ADMIN_DIDS env var
- Add ADMIN_DIDS to both Docker Compose configs

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:30:21 -08:00
Jeff Emmett 34877b1f9e feat: add "My Spaces" modal to identity dropdown
Adds a clickable "My Spaces" item in the profile dropdown that opens
a full-screen overlay showing all user spaces as clickable cards.
Fetches /api/spaces, splits into "Your Spaces" and "Public Spaces"
sections, with navigation via rspaceNavUrl and a "Create New Space" CTA.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:26:31 -08:00
Jeff Emmett d5563d4636 fix: pass auth token in WebSocket connections for private spaces
WebSocket clients were connecting without auth tokens, causing 401
rejections for authenticated/members_only spaces. Now reads the
encryptid_session from localStorage and appends ?token= to WS URLs.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 22:08:07 -08:00
Jeff Emmett f8c51fad0b fix: move /notifications and /admin routes before /:slug wildcard
Hono matches routes in definition order, so /:slug was catching
"notifications" and "admin" as slug params and returning 404.
Static routes must be defined before parameterized routes.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 21:54:27 -08:00
Jeff Emmett 1db8341fb2 feat: email forwarding via Mailcow aliases + private space access gate
Email forwarding (EncryptID):
- New mailcow.ts API client for alias CRUD via Mailcow REST API
- Schema: email_forward_enabled + email_forward_mailcow_id columns
- API endpoints: GET/POST email-forward status, enable, disable
- Profile email change hook updates/disables alias automatically
- Docker: rmail-mailcow network + MAILCOW_API_URL/KEY env vars

Private spaces:
- Access gate overlay blocks members_only spaces for unauthenticated users
- Space visibility injected into HTML via middleware
- Auto-provision creates spaces as members_only by default
- Personalized "Create {username}'s Space" CTA in space switcher
- Removed unused /notifications endpoint

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 21:54:07 -08:00
Jeff Emmett 75b148e772 Merge branch 'dev'
# Conflicts:
#	modules/rcal/mod.ts
#	modules/rfiles/mod.ts
#	modules/rforum/mod.ts
#	modules/rmaps/mod.ts
#	modules/rnetwork/mod.ts
#	modules/rswag/mod.ts
#	modules/rwork/mod.ts
#	shared/module.ts
2026-02-28 19:51:51 -08:00
Jeff Emmett 5613370817 refactor: rename module directories to match r-prefixed module IDs
All 22 module directories under modules/ now match their module IDs
(e.g. modules/cart → modules/rcart, modules/canvas → modules/rspace).
Updated all import paths, vite build config, HTML template asset refs,
docker-compose standalone commands, and .gitignore accordingly.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 19:49:26 -08:00
Jeff Emmett 8895c0fb75 feat: always-visible tab close buttons + rApp dropdown shows open apps
- Tab close (×) buttons now visible at 35% opacity instead of hidden,
  brightening on hover so users can see they're clickable
- [+] dropdown now shows all rApps including already-open ones
- Already-open rApps shown dimmed with a cyan dot indicator
- Clicking an open rApp surfaces it (switches tab) instead of duplicating

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 17:10:08 -08:00
Jeff Emmett 29d49c7b26 feat: always-visible tab close buttons + rApp dropdown shows open apps
- Tab close (×) buttons now visible at 35% opacity instead of hidden,
  brightening on hover so users can see they're clickable
- [+] dropdown now shows all rApps including already-open ones
- Already-open rApps shown dimmed with a cyan dot indicator
- Clicking an open rApp surfaces it (switches tab) instead of duplicating

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 17:08:45 -08:00
Jeff Emmett 3ea787ed82 fix: add cache-busting version params to module script tags
Browsers were serving stale JS from cache. Added ?v=3 to all four
updated module component scripts.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-01 00:52:18 +00:00
Jeff Emmett bb6643cf70 feat: port standalone app features to unified rSpace modules
rCal: keyboard navigation (←→ nav, 1/2/3 views, T today, L lunar) and
clickable source badges for event filtering.
rWork: inline create form with priority/description, inline title editing,
and priority badge cycling (replaces prompt() dialogs).
rNetwork: force-directed layout (80-iteration simulation), node detail
panel with trust scores, and purple trust badges on person nodes.
rMaps: provider search with dimming, enhanced detail with OSM directions
link, and browser geolocation pin display.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-01 00:05:34 +00:00
Jeff Emmett abbfb552cc feat: client-side tab caching for instant tab switching
Previously loaded tabs stay in the DOM and are shown/hidden via CSS.
New tabs are fetched via fetch() + DOMParser on first visit, then
cached. Switching back is instant with no network request.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 23:21:10 +00:00
Jeff Emmett d9bd7557fa fix: dropdown menus use fixed positioning to escape overflow clipping
Dropdown menus in app-switcher and space-switcher were clipped by
overflow:hidden on .rstack-header__left (mobile). Changed from
position:absolute to position:fixed with dynamic getBoundingClientRect
positioning. Bumped shell asset versions to v=5 to bypass CF cache.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 21:36:18 +00:00
Jeff Emmett 08928a9f8e fix: app-switcher dropdown navigates within demo on subdomains
On demo.rspace.online, the dropdown was linking to landing pages
(rspace.online/moduleId) instead of navigating between demo pages.
Changed condition to only use landing-page links on the bare domain.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 21:06:52 +00:00
Jeff Emmett 58af5a304c feat: enhance rcal, rtrips, and rmaps demos to match standalone quality
rCal: add Day/Week/Month view switcher with 24-hour timeline, 48 demo
events across 3 months, now indicator, and per-view navigation.

rTrips: add 4 demo trips with varied statuses (Planning/Booked/In
Progress/Completed), destination chains, collaborator avatars, emoji
categories, and grouped itinerary by date.

rMaps: add interactive zoom/pan (mouse wheel + drag + touch), provider
detail panel with descriptions and specialty tags, click-to-zoom on
pins and legend items, and zoom controls.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 20:04:50 +00:00
Jeff Emmett bf1d126ee5 fix: prevent double space prefix in dashboard links on subdomains
Dashboard card hrefs were /{space}/{moduleId}, causing double-prefix
(/demo/demo/rbooks) when accessed via demo.rspace.online subdomain
routing. Now renders /{moduleId} and resolves via __rspaceNavUrl on
the client for cross-context compatibility.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 09:04:47 +00:00
Jeff Emmett db078d3152 feat: embed external apps via iframe in rSpace shell
Add ?view=app iframe integration for 4 existing modules (rNetwork→Twenty CRM,
rSocials→Postiz, rForum→Discourse, rFiles→Seafile) and 2 new modules
(rDocs→Docmost, rDesign→Affine). Each module shows its demo view by default
with an "Open Full App" button to switch to the iframe-embedded external app.

Also includes: splat demo data seeding, MI search bar mobile layout fix.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 08:56:08 +00:00
Jeff Emmett e55e56bc06 feat: move search bar to second row on mobile header
On screens <= 640px, the header wraps to two rows: logo/app-switcher
and identity on top, "Ask Mi Anything" search bar full-width below.
Header and tab row switch from fixed to sticky positioning on mobile,
eliminating the need for magic padding-top values on #app.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 07:17:38 +00:00
Jeff Emmett 9db9c89bed fix: dark background on all demo pages + calendar mobile improvements
Shell CSS: add body background (#0f172a) so all module pages have the
dark theme instead of transparent/white on mobile. Add mobile media
queries for #app padding and nav wrapping.

Calendar: add day-detail panel that opens on tap (crucial for mobile
where event labels are hidden). Improve touch targets, add source
badges in event modal, shorter weekday headers for narrow screens.

Cache-bust shell.css, cal JS, and swag JS via ?v=2 query params to
bypass Cloudflare edge cache.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 07:10:40 +00:00
Jeff Emmett e40db06407 fix: show mockup section from start in rSwag demo
Step 2 (design mockup + "Use Sample Design" button) was gated behind
demoStep >= 2, but the only way to reach step 2 was clicking a button
inside the hidden section. Now mockup is always visible alongside
product selection.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 06:55:16 +00:00
Jeff Emmett 01fa8b1ba5 feat: enhance demo modes across 12 modules + add inbox/sharp/x402 deps
Improve interactive demos for notes, maps, network, vote, calendar,
choices, trips, work, books, wallet, and inbox modules with richer
mock data and better mobile responsiveness. Update server routing
and landing page. Add sharp, imapflow, mailparser, and x402 dependencies.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 06:48:51 +00:00
Jeff Emmett 7e5a8624d7 feat: rSwag design-on-demand demo with Printful hybrid pipeline
Add hoodie product + Printful metadata (SKU/sizes/colors) to product catalog.
Rewrite swag designer demo with 4-step interactive flow: product selection
with size/color pickers, inline SVG mockups, artifact generation with
provider matching (cosmolocal + Printful fallback sorted by distance),
revenue split visualization, and pipeline diagram. Add cosmolocal tee and
sticker sheet to cart demo catalog. Add pipeline and fulfillment sections
to swag landing page.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 06:48:10 +00:00
Jeff Emmett f1e90924c0 fix: improve rcal/rtube/rpubs demo rendering and mobile CSS
rCal: add mobile responsive breakpoints, event times with colored
borders, and Today button. rTube: auto-select first video, hide Live
Stream tab in demo, show duration/date metadata. rPubs: fix mobile
layout height calc and toolbar stacking.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 05:57:43 +00:00
Jeff Emmett f9a36b9d3e feat: add interactive demo modes to all 20 rApps + mobile responsive CSS
Each folk-* web component detects space === "demo" and renders a
self-contained interactive demo with hardcoded data — no API calls or
WebSocket connections. Accessible at demo.rspace.online/{rApp}.

Includes: spider charts, drag-to-rank, live voting sim, kanban board,
video library, calendar with lunar phases, forum provisioner, email
client, conviction voting, trip planner, book shelf, pub editor,
wallet viewer, world map, analytics dashboard, cart shop, file browser,
swag designer, photo gallery, graph viewer, social feed, and funds river.

Also adds @media responsive CSS for mobile rendering across all modules.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 05:48:35 +00:00
Jeff Emmett 5b7ee71eb9 fix: case-insensitive module routing for mixed-case URLs
rTrips, rFunds, rVote etc. now resolve correctly — normalizes module
ID to lowercase in subdomain routing, bare-domain routing, and 404
fallback checks.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 04:38:42 +00:00
Jeff Emmett c20a79078a Merge branch 'dev': port 10 module landing pages from standalone sites 2026-02-28 04:09:27 +00:00
Jeff Emmett c3deb18df8 feat: port module landing pages from standalone Next.js sites
Replace template landing pages for 10 modules with unique designs ported
from their original standalone Next.js/Tailwind sites. Each page now has
distinctive visuals, SVG icons, and content matching the original:

- rfunds: funnel metaphor diagram, amber/emerald/blue theme
- rtube: video streaming workflow, red/pink/orange theme
- rtrips: travel planning with teal/cyan SVG icons
- rforum: Discourse pricing tiers, indigo/violet theme
- rcal: temporal zoom visualization, blue gradient bars
- rvote: quadratic voting calculator, indigo/purple theme
- rpubs: group buy tiers, cross-title batching diagram
- rchoices: spider plot SVG, ranking mockup, live voting bars
- rwork: kanban board workflow, blue/teal/green theme
- rinbox: encrypted chat features, blue/teal gradient

All pages use dark mode and the shared rl-* CSS utility classes.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 04:09:23 +00:00
Jeff Emmett c59b7d85a1 feat: replace static landing page with server-rendered main landing
Replace the 177KB static Next.js landing with a server-rendered page using
the same shell, theme, and rl-* CSS utilities as all module landings. Fixes
the 354KB logo.png → 1.6KB favicon.png glitch across all pages. Dynamic
ecosystem grid is always in sync with registered modules.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 03:48:17 +00:00
Jeff Emmett 32ed06d43a feat: replace static landing page with server-rendered main landing
Replace the 177KB static Next.js landing with a server-rendered page using
the same shell, theme, and rl-* CSS utilities as all module landings. Fixes
the 354KB logo.png → 1.6KB favicon.png glitch across all pages. Dynamic
ecosystem grid is always in sync with registered modules.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 03:48:02 +00:00
Jeff Emmett 990704a57d Merge branch 'dev' 2026-02-27 18:13:43 -08:00
Jeff Emmett b0eebc4cbc chore: add backlog task files
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-27 18:13:40 -08:00
Jeff Emmett 186a1695c1 Merge branch 'dev' 2026-02-27 18:10:29 -08:00
Jeff Emmett 042ae4e34d fix: dynamically position toolbar popout panel to avoid overlap
The panel had a hardcoded left offset (88px) that didn't account for
the toolbar's actual width, causing the submenu to overlap the toolbar.
Now uses getBoundingClientRect() to position 8px right of the toolbar
edge. Skipped on mobile where the panel uses its own bottom-sheet layout.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-27 18:10:26 -08:00
Jeff Emmett 4db56c1b81 Merge branch 'dev' 2026-02-27 18:06:44 -08:00
Jeff Emmett 39ca0ff9b7 feat: canvas dark mode toggle — persistent theme with dark toolbar, grid, and panels
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-27 18:06:35 -08:00
Jeff Emmett c4ebecf5df Merge branch 'dev' 2026-02-27 18:02:52 -08:00
Jeff Emmett eb05639608 fix: use rspaceNavUrl for (you)rSpace CTA redirect + pass onSuccess callback
The auto-provision redirect was hardcoding /${slug}/canvas which is a
404 (canvas module id is "rspace"). Now uses rspaceNavUrl() for correct
subdomain/path routing. Also passes onSuccess to showAuthModal so
auto-provision runs even when signing in from a non-demo space.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-27 18:02:22 -08:00
Jeff Emmett 6f4befdd19 Merge branch 'dev' 2026-02-27 17:52:07 -08:00
Jeff Emmett b32d752858 feat: redirect all r*.online domains to rspace.online/r*
Replace internal rewrites with 301 redirects for all standalone
domains. Handles bare domains, subdomains, paths, and query strings:
- rnotes.online/ → rspace.online/rnotes
- rnotes.online/alice/path → alice.rspace.online/rnotes/path
- alice.rnotes.online/path → alice.rspace.online/rnotes/path
- rnotes.online/api/... → rspace.online/rnotes/api/...

Traefik labels updated to also match *.r*.online subdomains.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-27 17:51:57 -08:00
Jeff Emmett c00379eee6 Merge branch 'dev' 2026-02-27 17:51:00 -08:00
Jeff Emmett 2ec5027285 feat: restyle rSpace.online about page to rApp theme + (you)rSpace CTA in space switcher
Restyled website/index.html to use the standard rl-* rich landing CSS
utilities matching all rApp module landing pages: rl-hero, rl-section,
rl-card, rl-grid-3, rl-icon-box, rl-cta-primary/secondary. All original
content preserved (EncryptID, Offline-First, Interoperable, Newsletter).

Added (you)rSpace CTA button in the space switcher dropdown — shows
"Sign in to create" or "Create (you)rSpace" when user has no owned space,
with auto-provision flow on click.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-27 17:50:30 -08:00
Jeff Emmett 54851861c0 Merge branch 'dev' 2026-02-27 17:35:35 -08:00
Jeff Emmett ab3132a5f0 feat: space cleanup + Edit Space modal (delete, update meta, manage members)
Backend: deleteCommunity(), updateSpaceMeta(), DELETE/PATCH space endpoints,
member CRUD, per-space access-requests GET. UI: gear icon on owned spaces,
3-tab Edit Space modal (Settings, Members, Invitations) in space switcher.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-27 17:35:24 -08:00