Platform Configuration ๐ ๏ธ
By Jessica
By Jessica
Configure Benchmarks (Matrix)
The Benchmarks page lets you set target benchmarks per business stage and industry for each FORTIS metric. Benchmarks drive scoring and the Executive-tier benchmark comparison. This guide covers configuring them. ๐ก Tip โ Who can use this For platform admins, under Benchmarks. Quick reference | Step | Action | |------|--------| | 1 | Edit benchmark values per stage/industry with a reason | Step 1 โ Configure benchmarks Go to Benchmarks. Use the stage buttons (startup, growth, mature, transformation) and industry dropdown to scope the view. ("All industries" sets the stage default; a specific industry creates an override.) The matrix table shows each metric with its label, pillar, unit, direction, and an editable Benchmark input (with the effective value and a source badge โ Override vs Default). Edit values, then Save Changes (N) opens a reason modal (at least 10 chars) before the PATCH. You can also Reset scope (rewrites overrides back to defaults) or use CSV export/import. ๐ Note โ Benchmarks are service-role data The benchmark matrix is service-role-only. Reads and writes go through the admin endpoints, not the client-facing API. ๐ก Tip โ Use industry overrides sparingly Start with solid stage defaults, then add industry overrides only where a metric genuinely differs by industry (e.g. churn norms in SaaS vs. manufacturing). Too many overrides make the matrix hard to maintain.
Import Benchmarks via CSV
You can bulk-import benchmark values via CSV โ the only CSV import in the admin console. This guide covers the import. ๐ก Tip โ Who can use this For platform admins, under Benchmarks. Quick reference | Step | Action | |------|--------| | 1 | Export the CSV, edit it, and import it back | Step 1 โ Import benchmarks On the Benchmarks page, use Export CSV to get the current matrix as a spreadsheet. Edit the benchmark values in the exported file, then use Import CSV to upload it. The import returns accepted/rejected counts and per-row errors (e.g. a value that's out of range or a metric that doesn't exist). After a successful import, the matrix reloads with the new values. ๐ Note โ Export first, then edit The most reliable import workflow is to export the current CSV, edit the values in place (keeping the structure and headers intact), and import it back. This avoids column-matching issues. ๐ก Tip โ Fix errors row by row If the import rejects some rows, the error report tells you which rows and why. Fix those rows in your CSV and re-import โ accepted rows from the first pass are already applied.
Manage Branding & Content (CMS)
The CMS section lets you customize the platform's branding and injected content โ logos, wordmarks, footer text, legal links, and analytics/head HTML. These settings apply across the app. This guide covers the CMS. ๐ก Tip โ Who can use this For platform admins, under CMS. Quick reference | Step | Action | |------|--------| | 1 | Set branding, footer, and links | Step 1 โ Configure branding and content Go to CMS. You can manage: - Branding โ upload a Logo Mark (replaces the default icon in the sidebar, login, and PDF covers), a Favicon, and set the Wordmark and Sub-mark text. - Footer Disclaimer โ the text shown in the footer (supports {{terms_link}} and {{privacy_link}} placeholders). - Legal Links โ Terms of Use URL and Privacy Policy URL. - Help & Analytics โ the Help URL (the sidebar/profile Help link; hides if empty), Custom Head HTML (injected into every page's <head> for analytics/meta tags), and Custom Body HTML (injected before </body> for chat widgets or tracking pixels). Click Save Content to persist all settings. ๐ Note โ Brand assets are stored securely Logo and favicon uploads go to the platform's brand-assets storage and are referenced by URL. Removing a logo reverts to the default icon. โ ๏ธ Warning โ Custom HTML is powerful The Custom Head and Body HTML fields inject raw HTML on every page. Use them carefully โ a syntax error or malicious snippet there affects the entire app. Only inject trusted, verified code (analytics scripts, chat widgets).
Upload a Logo & Favicon
You can replace the platform's logo mark and favicon (the browser tab icon) from the CMS section. This guide covers the brand uploads. ๐ก Tip โ Who can use this For platform admins, under CMS (Branding). Quick reference | Step | Action | |------|--------| | 1 | Upload a logo mark and/or favicon | Step 1 โ Upload brand assets In the CMS section, under Branding: - Logo Mark โ upload a PNG, SVG, or WebP (max 1 MB). This replaces the default icon in the sidebar, login page, and PDF report covers. - Favicon โ upload a PNG or ICO (max 1 MB). This becomes the browser tab icon. Both upload to the brand-assets storage and are referenced by URL. You can remove a logo to revert to the default. ๐ Note โ Logos appear across the app The logo mark shows in the sidebar on every page and on PDF covers, so choose a clean, recognizable mark that works at small sizes. ๐ก Tip โ Use a square logo with transparency A square PNG with a transparent background works best for the logo mark โ it sits cleanly on the sidebar regardless of theme. Avoid wide wordmarks; the wordmark text is a separate field.
Manage Document Categories
Document categories help organize the shared vault โ clients and advisors pick a category when uploading. You manage the global category list from the admin console. This guide covers it. ๐ก Tip โ Who can use this For platform admins, under Document Categories. Quick reference | Step | Action | |------|--------| | 1 | Add, rename, reorder, or delete categories | Step 1 โ Manage categories Go to Document Categories. You can: - Add a new category (name and sort order). - Rename a category inline (on-blur saves). - Reorder by adjusting sort order. - Delete a category (with confirmation). Categories apply globally to both client and advisory document uploads. ๐ Note โ Deleting doesn't remove documents Deleting a category removes it from the picker for future uploads, but existing documents that used it keep their data. Still, avoid deleting categories in active use to prevent confusion. ๐ก Tip โ Keep the list short and clear A handful of clear categories (e.g. Financials, Contracts, Reports, Notes) is more useful than a long, overlapping list. Users are more likely to categorize correctly when the options are obvious.
Manage Advisory Domains
Advisory domains are the expertise areas used in partner profiles and client onboarding (e.g. Leadership & Strategy, Operations, Technology). You manage the master list from the admin console. This guide covers it. ๐ก Tip โ Who can use this For platform admins, under Domains. Quick reference | Step | Action | |------|--------| | 1 | Add, rename, toggle, or delete domains | Step 1 โ Manage domains Go to Domains (Advisory Expertise Domains). You can: - Add Domain โ name and optional description. - Rename a domain inline (on-blur saves). - Toggle Active/Inactive โ inactive domains are hidden from pickers but preserved. - Delete a domain. This list drives the domain pickers partners set in their profiles and clients select during onboarding. ๐ Note โ Domains drive partner matching The onboarding approval suggests partners ranked by domain overlap with the client's requested areas. Keeping the domain list accurate and current directly improves those suggestions. ๐ก Tip โ Deactivate rather than delete If a domain is no longer used, deactivating it (rather than deleting) preserves historical data on partners and clients who selected it, while hiding it from new pickers.
Manage Industries
Industries are the classification codes (ISIC/NACE-style) used in client onboarding and benchmark overrides. You manage the master list from the admin console. This guide covers it. ๐ก Tip โ Who can use this For platform admins, under Industries. Quick reference | Step | Action | |------|--------| | 1 | Add, rename, toggle, or delete industries | Step 1 โ Manage industries Go to Industries. You can: - Add Industry โ a code (uppercased, max 5 chars), name, and optional description. - Rename an industry inline (on-blur saves). - Toggle Active/Inactive โ inactive industries are hidden from onboarding. - Delete an industry. Industries are used in client onboarding (the client picks their industry) and in benchmarks (you can set industry-specific benchmark overrides per metric). ๐ Note โ Industries anchor benchmark overrides When you create an industry-specific benchmark override, it's keyed to the industry. Keeping the industry list aligned with how you want to benchmark avoids orphaned overrides. ๐ก Tip โ Use standard classification codes Using recognized industry codes (ISIC/NACE) makes the list consistent and comparable. Avoid ad-hoc freeform industries that fragment the data.
Edit AI System Prompts
Pulse AI's behavior is shaped by system prompts โ the instructions that tell the AI how to write briefings, deep-dives, chats, advisory drafts, and assist text. You can view and edit these prompts from the admin console. This guide covers the AI prompt settings. ๐ก Tip โ Who can use this For platform admins, under Settings (AI Configuration). Quick reference | Step | Action | |------|--------| | 1 | Edit a prompt and save (or reset to default) | Step 1 โ Edit an AI prompt Go to Settings (the AI Configuration page). You'll see tabs for each AI surface โ the executive briefing, pillar deep-dive, copilot chat, AI assist, and the auto-advisor. Each tab shows a description of what that prompt controls and a textarea with the current prompt text. To change one: 1. Edit the prompt text in the textarea. 2. Click Save Prompt. The change takes effect immediately and invalidates any cached AI output for that surface, so new generations use the new prompt. Use Reset to default to restore the textarea to the built-in default (this doesn't auto-save โ you still need to click Save to apply it). ๐ Note โ Saved prompts override the defaults The built-in defaults live in the code, but any prompt you save is stored in the database and takes precedence. Resetting to default and saving restores the code's version. โ ๏ธ Warning โ Changes affect all AI output Editing a system prompt changes how Pulse AI writes for every client on that surface. Test thoughtfully โ a vague or conflicting prompt can degrade output quality platform-wide. It's wise to keep a copy of the previous prompt before experimenting.
Trigger Submission Reminders
You can manually trigger submission reminders โ notifications to clients who haven't submitted data for the current month. This guide covers the reminder tool. ๐ก Tip โ Who can use this For platform admins, via the reminders API endpoint. Quick reference | Step | Action | |------|--------| | 1 | Trigger reminders (API-only, no UI page) | Step 1 โ Trigger reminders Submission reminders are triggered via the admin API (POST /api/admin/reminders), not a dedicated UI page. The endpoint iterates all orgs/workspaces; for each workspace missing a financial_snapshots row for the current month, it notifies the org's client users (a submission_reminder notification) and inserts a tracking row in submission_reminders. It returns the count of reminders sent. ๐ Note โ It's a manual trigger There's no automated cron for reminders in the current codebase โ an admin triggers them manually via the API when they want to nudge laggard submitters. ๐ก Tip โ Trigger at a consistent cadence If you use reminders, trigger them on a regular schedule (e.g. mid-month and end-of-month) so clients come to expect the nudge. Avoid over-triggering, which desensitizes clients to the notification.
Logo on White Background
Your main logo is designed for dark surfaces. The Logo on White Background is its light-friendly twin: the same brand mark, tuned for places the platform renders on white โ client onboarding screens, the mobile top bar, and transactional emails. Uploading one keeps your brand crisp everywhere instead of washing out a dark-optimized logo on light backgrounds. ๐ก Tip โ Who can use this Platform administrators, via the CMS in the admin portal. Firm-level light logos (for advisory firms with their own branding) are managed per firm by the platform team. Quick reference | Step | Action | |------|--------| | 1 | Open the CMS page in the admin portal | | 2 | Find the Logo on White Background card | | 3 | Upload your light-friendly logo | Step 1: Open the CMS page Sign in to the admin portal and open the CMS page from the admin menu. This page holds the platform's global content and brand settings. CMS page in the admin portal Step 2: Find the Logo on White Background card Scroll to the Logo on White Background card. If a light logo has already been uploaded, you'll see it with a Remove button; otherwise the card shows just the upload control. Logo on White Background card Step 3: Upload your light-friendly logo Click Upload Logo and choose your file โ PNG, SVG, or WebP, up to 1 MB. Use a version of your logo with dark or mid-tone artwork and (if applicable) transparent padding, so it reads cleanly against white. The upload replaces any existing light logo immediately: onboarding screens, the mobile top bar, and outgoing emails switch to the new artwork right away. To revert to the default styling, click Remove. ๐ Note โ Where this logo appears Onboarding, the mobile top bar, and emails โ the "white surfaces". Dark surfaces (like the dashboard sidebar and login screen) continue to use your main dark-surface logo. Generated PDF reports also continue to use the standard brand treatment. โ ๏ธ Warning โ Watch file size and format Uploads over 1 MB or in other formats (e.g. JPG, BMP) are rejected. Convert or compress the file first โ SVG is ideal for logos.
Manage Org Document Storage (Admin Control)
As an admin, you can access any organization's document vault with full permissions โ useful for reviewing uploads or managing administrative attachments. This guide covers the admin document view. ๐ก Tip โ Who can use this For platform admins, on an org's documents sub-page. Quick reference | Step | Action | |------|--------| | 1 | Open an org's document storage with full access | Step 1 โ Access org documents From an org's detail page, the Shared Document Manager link opens the org's document workspace. The admin view renders with role="admin" and full lead-partner-equivalent access โ you can view, download, and manage documents in both zones, review versions, and see the activity log. The page loads the org's first workspace's documents, categories, and current versions, and applies the pricing-derived file-size and storage limits. ๐ Note โ Admin access is full Unlike clients (Client Zone only) or non-lead partners (read-only), the admin role has full access to both zones. This is intentional for oversight, but use it judiciously โ avoid modifying a client's documents unless there's a clear reason. ๐ก Tip โ Use it for support and audits The admin document view is handy when a client reports a missing or broken document, or when you need to audit what's been uploaded. You can diagnose and, if necessary, manage files directly from here.
Pulse Connect โ Keys & Tier Access
Pulse Connect is the platform's external API: clients and firms mint API keys to use Pulse data in their own tools (AI assistants, dashboards) against the Data API and MCP server. This page is the platform team's control center for it: every key across every tenant, plus the tier list that decides who can use Connect at all. ๐ก Tip โ Who can use this Platform administrators only. End-user key management lives in the client Settings and firm Settings portals (see the client and firm help articles). Quick reference | Step | Action | |------|--------| | 1 | Open the Connect API Keys page | | 2 | Review keys across all tenants | | 3 | Revoke a key | | 4 | Edit the Allowed Tiers list | Step 1: Open the Connect API Keys page In the admin portal, click Connect Keys in the sidebar menu (under Pricing). It shows the total key count and everything below. Pulse Connect admin overview Step 2: Review keys across all tenants The table lists every API key on the platform: masked prefix, tenant (organization or firm, with an ORG/FIRM badge and name), status, last-used time, and creation date. Revoked keys remain listed for audit. "Last used" stamps update as keys are exercised โ a key marked ACTIVE that has never been used is a candidate for cleanup with its owner. All keys table Step 3: Revoke a key Each active key has a Revoke button. Use it for support requests ("kill my leaked key"), offboarding, or housekeeping. Revocation takes effect on the key's next request โ no deploy or restart needed. ๐ Note โ There is a platform kill switch If Pulse Connect ever needs to be switched off entirely (incident response, maintenance), setting the environment variable CONNECT_ENABLED=false and redeploying disables both the API and MCP endpoints platform-wide (503 responses), hides the client UI, and blocks new key creation โ without touching any keys. Step 4: Edit the Allowed Tiers list The Allowed Tiers field is a comma-separated list of client tiers that may use Pulse Connect with organization keys (default: executive,partner). Changes apply at request time โ a tier removed from the list loses API access on its very next call, and a tier added gains it immediately. Editing requires a save reason, like the pricing page. Allowed tiers editor โ ๏ธ Warning โ Firm keys are not governed by this list The tier list applies to organization (client) keys only. Firm keys are governed by firm suspension instead โ a suspended firm's keys are blocked automatically. Also note client keys stop working on their own when the client's account becomes inactive (expired plan, suspended firm, or deactivation), mirroring the portal's lockout rules. ๐ Note โ Trial accounts Trial-tier organizations are excluded by default. If you add trial to the list, remember trials still expire by their own subscription rules โ Connect access follows automatically.
Pulse Webhooks โ Endpoints, Delivery Log & Scheduler
Pulse Webhooks push platform events to HTTPS endpoints owned by the platform team and by firms: CRM syncs, marketing automation, monitoring. This page is the platform-side control center โ every endpoint across every tenant, the delivery log with resend, and the scheduler switch that turns the delivery engine on. ๐ก Tip โ Who can use this Platform administrators, at Webhooks in the admin navigation (after Connect Keys). Firms manage their own endpoints from their portal's Settings; this page oversees everything. Quick reference | Step | Action | |------|--------| | 1 | Open the Webhooks page | | 2 | Enable the delivery scheduler | | 3 | Create and manage endpoints | | 4 | Read the delivery log and resend | Step 1: Open the Webhooks page In the admin portal sidebar, click Webhooks (directly after Connect Keys). The page has three zones: the Delivery Scheduler card, the Webhook Endpoints manager (platform endpoints), and the Recent Deliveries log with filters. Admin Webhooks page overview Step 2: Enable the delivery scheduler Deliveries are processed by a background job that ticks every 30 seconds. On a fresh environment it starts Paused โ click Enable on the Delivery Scheduler card and confirm it shows Active with the 30-seconds schedule. While paused, nothing is lost: events accumulate in the outbox and flow when re-enabled. A platform-wide kill switch (WEBHOOKS_ENABLED environment variable) can pause the entire webhook system without touching any endpoints โ the page and nav also disappear while it is off. Delivery scheduler card showing Active โ ๏ธ Warning โ The scheduler bakes in the internal API key The cron job calls the processor with the environment's internal key. Set the production INTERNAL_API_KEY before enabling the scheduler โ if you rotate the key later, disable and re-enable the schedule so it picks up the new value. Step 3: Create and manage endpoints Create Endpoint opens the shared dialog: HTTPS URL, description, and event subscriptions grouped by domain (Lifecycle, Billing, Engagement, Messaging, Platform โ messaging events are marked high-volume). Platform endpoints receive every subscribed event across all organizations; firm endpoints created in firm settings receive only their own clients' events. Each endpoint row shows its subscription count, status, consecutive failures, last delivery outcome, and actions: Edit, Reveal/Rotate Secret, Send Test, and enable/disable. Endpoints table with delivery log ๐ Note โ Auto-disable protects everyone An endpoint that fails 25 consecutive deliveries is disabled automatically and its owners are notified (platform admins, or the firm's admins for firm endpoints). Re-enabling resets its failure budget. Dead-lettered deliveries (rows that exhausted the retry ladder) stay in the log for inspection and one-click Resend. Step 4: Read the delivery log and resend Recent Deliveries lists every delivery attempt with filters by endpoint and status (pending / succeeded / failed / dead). Use Resend on a failed or dead row to requeue it with a fresh retry ladder โ handy after a client fixes their receiving service. Deliveries are at-least-once; consumers deduplicate on the X-Pulse-Delivery header. โ Important โ Consumers must verify signatures Every delivery is signed: the X-Pulse-Signature header is t=<unix-seconds>,v1=<hex> where v1 = HMAC-SHA256(secret, "<t>.<rawBody>"), alongside X-Pulse-Event, X-Pulse-Delivery, and X-Pulse-Timestamp. Consumers should verify against the endpoint's secret and reject timestamps older than 5 minutes: import { createHmac, timingSafeEqual } from 'node:crypto'; export function verifyPulseSignature(secret, header, rawBody, toleranceSec = 300) { const m = /^t=(\d+),v1=([0-9a-f]+)$/.exec(header); if (!m) return false; const [, t, v1] = m; if (Math.abs(Math.floor(Date.now() / 1000) - Number(t)) > toleranceSec) return false; const expected = createHmac('sha256', secret).update(`${t}.${rawBody}`).digest('hex'); return expected.length === v1.length && timingSafeEqual(Buffer.from(expected), Buffer.from(v1)); }