Changelog
What's new.
Every improvement to the platform, as it ships.
· kamo-internal
LabelManager software identity UI + internal tab title
- Company Info: software name/short-name + login/register name + tab-title selectors - Branding: software full/simple logo uploads, override toggles, and per-surface identity selectors (watermark, navpri, login/register logos) - forced-legal surfaces communicated as always-company (documents/email/invoices/etc.) - layout: internal browser tab title resolves via internalTabBrandSource
· kamo-internal
3-stage org onboarding guidance (create → finish DNS → enter)
Generalize the first-org hero into a single stage-aware guidance panel keyed on the member's owned-org count + DNS status (from /api/security/org/my-networks): create — owns no child org → launch first white-label org (/network/create) dns — owns 1, DNS not verified → finish domain setup (/setup/dns?orgId=..) enter — owns 1, DNS complete → enter it (enter-as OTK → internal.<domain>) Once they own a second org, no panel shows — they know the ropes. DNS-pending mirrors the network page rule exactly (custom domain && domainSetupComplete===false; a *.kamocrm.com org needs no DNS). Each stage gets its own accent family (people/work/crm), icon and copy; CTA is a link for create/dns and an async enter action for the ready stage. Fails safe (no panel) on any fetch error.
· kamo-internal
Dual company/software resolver + delivery + consumption
- Organization.ts: deliver software identity + per-surface selectors via OrgContext - brand.ts: **************** (+ vitest, 8 cases) - ThemeLogo: logoSoftware/logoFullSoftware variants - NavPri: navpri logo + text follow the Internal Software Logo selector - BackgroundWatermark + Backdrop: watermark honors software identity (both paths)
· SecurityService
Software logo upload types + config.json bake
- uploadLogo: explicit object-key switch **************** with rejecting default so a software upload can never clobber the company logo.svg - copyFolder: preserve uploaded software logos on template re-copy - config.json: bake software identity + auth-surface selectors for login/register - tests: UploadLogoObjectKeyTest, buildConfigJson software cases
· kamo-shared-library
Add software white-label branding columns to Organization
· kamo-shared-library
Persist software branding fields via patchOrganization whitelist
· kamo-internal
First-org CTA hero for members on the platform org
Show an onboarding hero at the top of the home launchpad inviting a KamoCRM-platform member (not a team member) who hasn't yet created a child org to spin up their first white-label organization. A prominent CTA button and an inline 'click here' link both route to /network/create, and the copy points to the 'My {branches}' nav above. Gated on userInfo.memberType === MEMBER + organization.isTopLevel; stays hidden unless /api/security/org/my-networks confirms they own no child org, and fails safe (hidden) on any fetch error. Follows the Instrument Panel design language (people accent, kglass, operator-label, house easing, reduced-motion-gated). Strings under home.firstOrg.
· VOIPService
TURN-REST credentials endpoint for the mobile softphone
GET /api/voip/turn/credentials mints ephemeral coturn creds (HMAC-SHA1 over "<expiry>:<memberId>" with the shared static-auth-secret) so native/cellular WebRTC can relay through 47.181.8.84:3478. Auth via the same X-***-Token the SIP endpoint uses; returns configured:false (STUN-only) when the secret is absent. Wires KAMO_TURN_SECRET from the existing *** (optional).
· SecurityService
Expose per-org primaryColor + logo URLs on /my-networks
Each org row now carries primaryColor (Organization.colors.colorPri, '#'-prefixed to match config.json) and derived logoUrl/logoSimpleUrl (theme.<domain>/public/ logos and per-org hex-head border colors.
· MediaService
Snapshot web-chat integration id on support visitor + ticket
Resolves the WebChatIntegration by creatingKeyHash (enabled-filtered, consistent with bootstrap()/AI-prompt resolution) once in createSupportSession and stamps its id onto both PublicChatVisitor and SupportTicket for per-website attribution. Null/blank keyHash or no matching enabled integration leaves the columns null.
· AIService
Per-integration public AI prompt + session attribution
Upgrade the public-chat system-prompt waterfall from per-org to per-integration: PublicAiChatController now reads the X-Public-Chat-Key-Hash header (nullable) forwarded by APIService and passes it to **************** which resolves the WebChatIntegration by hash and prefers its aiSystemPrompt over the AiOrgSettings default, falling back to the generic prompt. The resolved AiChatSession is also stamped with webChatIntegrationId for stable attribution that survives key rotation. Extracted the waterfall into a static, unit-tested resolvePrompt helper (integration-wins / org-fallback / generic-fallback / blank handling).
· APIService
GET /api/public-chat/bootstrap gateway route
Add bootstrap endpoint that reuses the existing proxyWithAuth pipeline (key validation + opt-in origin + PUBLIC_CHAT scope + rate-limit + X-Public-Chat-Key-Hash) and proxies to the MediaService bootstrap endpoint.
· MediaService
Public-chat bootstrap config resolver
Adds an internal GET **************** that resolves a WebChatIntegration by X-Public-Chat-Key-Hash and returns its resolved design/behavior config (default-filled via WebChatDefaultConfig.merge so a key with no integration row still renders like today's widget). Falls back to the active PublicChatApiKey's org when no integration exists; 404s when the key hash doesn't resolve at all.
· MediaService
WebChatIntegration CRUD (mints key + integration, org-scoped)
Org-facing management API for the Phase-2 web-chat settings tab. On create, mints the underlying PublicChatApiKey (same key-gen approach as PublicChatKeyController) alongside the WebChatIntegration row and returns the raw key once. list/get/update/delete are org-ownership checked; update busts the (Task-5) bootstrap cache when designConfig or enabled changes.
· kamo-shared-library
Add WEB_CHAT_INTEGRATION_ID attribution columns to visitor/ticket/ai-session
· kamo-shared-library
WebChatIntegration entity + repo + DTO + default design config
· kamo-internal
Add "Access Copilot Mobile App" entry points on home + NavPri
Both surfaces dispatch an `open-interaction-center` event that NavTop listens for to open the Interaction Center on the Setup Mobile App tab. Home shows a labeled pill under the wallpaper controls; NavPri shows a logo icon below the trial pill (label when expanded, tooltip when collapsed). Both gated by the ALLOW_MOBILE_ACCESS right.
· kamo-internal
Password-gate the QR, single-line tab, logo-left header, 10-min code
- Member must re-enter their password (server-verified via /api/mobile-access-otk, which mints the OTK only on success) before the QR is revealed — prevents someone at an already-signed-in computer from grabbing it. - QR/OTK now lives 10 minutes (600s); countdown then re-locks. - Tab label forced to one line; logo moved left of the title to save vertical space; removed the 'Configuring for' pill.
· SecurityService
POST **************** — gate Mobile Copilot QR
Verifies the caller's own password (passwordEncoder.matches against their session's user) without changing anything. Used by the mobile-access-otk BFF route so the setup QR is only minted after re-confirming the password.
· kamo-internal
Setup Mobile Access tab — QR to install + auto-configure Mobile Copilot
New 3rd tab in NavTopPanel (gated by ALLOW_MOBILE_ACCESS right): shows a branded QR encoding a short-lived OTK deep link (kamocopilot://configure) that signs the member in on their phone and defaults the app to the current org. Auto-refreshes the OTK before expiry; polished MUI layout with the org's primary color. Adds
· kamo-shared-library
Add ALLOW_MOBILE_ACCESS (167) general right for Mobile Copilot
New RoleRightType (serviceType=null → General group) gating the 'Setup Mobile Access' interaction-center tab. RoleRightsSyncService backfills it to all roles on SecurityService restart; appears under General Permissions in the role editor.
· AIService
Per-org public prompt, human-handoff on no provider, anon daily message cap
· kamo-shared-library
Add anon usage count query for public web-chat quota
· APIService
Verify *** PoW at the edge on public session create (enforced when payload present)
· MediaService
Bust APIService key cache immediately on public-chat key toggle/delete
· MediaService
Persist creating key hash on public-chat visitor + ticket for attribution
· kamo-shared-library
Add publicDailyMessageCap to AiOrgSettings for anon web-chat quota
· kamo-shared-library
Add creating-key-hash attribution columns to PublicChatVisitor + SupportTicket
· kamo-shared-library
Add findOrganizationOwners for per-org public-chat system member
· MediaService
Mobile push dispatch (FCM data + direct APNs) with presence gate
chat incoming (MediaController), support ticket (SupportNotificationService), SMS/voicemail (VoipStompRelayController), social **************** Presence-gated like the missed-message email consumer (skip when a live socket is up). Android = data-only high-priority FCM; iOS = direct APNs HTTP/2 via Pushy (no Firebase on iOS); APNS_VOIP reserved for the future CallKit path. Per-conversation rate limit. POST /api/internal/push/dispatch (X-Internal-Auth) for cross-service flows. Senders no-op until FCM service-account + APNs .p8 are provisioned.

Your universe is waiting.
Start free in minutes. Add products whenever you are ready — no migration, no new logins.
Free forever — no credit card required