MirrorSphere.  Brand Review
Home Standards Email KB PDF Voice

MirrorSphere Content Standards

Single source of truth for brand, voice and structural rules across HaloPSA email templates and HaloPSA knowledge-base articles. Derived from the live reference template -550 BitLocker — New Ticket - rb, the KB master mockup _mockup-744-BitLocker.html, the machine-checkable rules encoded in build-email-template-scorecard.ps1, and the customer-reply voice exemplars captured from production tickets.


1. Purpose & scope

This document is the canonical brand and content reference for anyone — human author or Claude — producing or reviewing a MirrorSphere customer-facing artefact. It covers both transactional email templates (rendered by HaloPSA's EmailTemplate engine) and KB articles (rendered as description_html on the customer portal). The same brand DNA — palette, typography, voice, footer — applies to both. Format-specific rules live in their dedicated sections.

Audience: tech writers, automation engineers, Claude (acting as content drafter or reviewer), and anyone running the audit/scorecard scripts.


2. Brand DNA (applies to email + KB)

2.1 Palette

The brand uses exactly eight colours. Do not invent new ones, and do not use the Material-style variants listed in section 7.

RoleNameHexUsed for
Primary darkSlate#394852Hero bg, footer bg, body headings, button text on light
Primary accentTeal#4CBDEELinks, eyebrows, button bg, accent borders, H2 underline
Secondary accentOrange#E5833BTitle "dot", warn accents, "Managed IT Services" tag
Muted blue-greyGrey-blue#92A9BDTagline text, secondary metadata, muted pills
SuccessSuccess green#34a853Approved states, checklist ticks, success callouts
ErrorError red#c0392bRejected states, danger callouts
SurfacePanel#f2f5f8Callout backgrounds, ticket-box backgrounds, code bg
SurfacePage#f0f2f5Outer page background

Supporting tones derived from the palette (do not introduce new ones):

HexRole
#6B8295Body paragraph copy (a darker grey-blue)
#1a2732Lede paragraph copy (heaviest body weight)
#dde5ecHairline borders, table row separators
#e0e8eeCard / FAQ / TOC borders
#f8fafcTOC fill, FAQ question background
#2d3a43Signoff band (slightly darker than slate footer)

2.2 Accent gradient stripe

Used everywhere there's a transition from dark to light (under hero, above footer). Always horizontal, always 3px tall:

height: 3px;
background: linear-gradient(90deg, #4CBDEE 0%, #92A9BD 100%);

2.3 Typography

font-family: 'Montserrat', Arial, Helvetica, sans-serif;

Montserrat is loaded from Google Fonts at weights 400, 500, 600, 700, 800. The system fallback chain (Arial, Helvetica, sans-serif) is mandatory for email clients that don't support webfonts.

ElementSizeWeightLetter-spacingNotes
Hero H126-28px800-0.02emUPPERCASE; trailing . in #E5833B
Hero tagline8-12px600-7000.18-0.20emUPPERCASE, grey-blue
Eyebrow8-10px7000.12-0.20emUPPERCASE, teal
H216-17px700-0.01em2px teal underline (#4CBDEE)
H314px700normalslate
Lede15-16px600normal#1a2732, line-height 1.6
Body p13px400normal#6B8295, line-height 1.7-1.75
Body strong13px700normal#394852
Code12pxnormalnormal'SFMono-Regular', Consolas, monospace; bg #f2f5f8
Footer legal9px400normal#6B8295 on slate
https://assets.unlayer.com/projects/0/1749050347969-MS_Inline%20logo_Strap_White%20wording_3x-8.png

Branded footer is mandatory on both emails and KB articles. It has three pieces:

1. Footer main band (slate #394852, padding 16px 28px-32px):

> MirrorSphere · Bloxham Mill, Barford Road, Bloxham, OX15 4FF · www.mirrorsphere.com · <phone> &nbsp;&nbsp;&nbsp; Managed IT Services (in orange)

2. Gradient stripe (3px, the accent gradient).

3. Legal block (slate, smaller text):

> This email/article, including its contents and any attachments, is intended solely for the named recipient(s). It may contain confidential and/or legally privileged information. Unauthorised access, use, disclosure, distribution, or copying is strictly prohibited. If received in error, please notify the sender immediately and delete it. MirrorSphere Ltd, registered in England & Wales. Bloxham Mill, Barford Road, Bloxham, Banbury, OX15 4FF · Co. No. 6388568 · VAT: GB918941394

Required tokens that the scorecard checks for: MirrorSphere, Bloxham or OX15 4FF, and one of (VAT, registered in England, Co. No).


3. Voice & content conventions (applies to both)

3.1 Tone

Calm, professional, helpful. Second person ("you", "your"). Sentence case in headings (not Title Case, not ALL CAPS except where the design calls for it in eyebrows/hero titles). Concise.

The customer-reply exemplars (integrations/anthropic/brand-voice/exemplars.md) capture the live tone: warm openers ("I hope you are well!"), conditional politeness ("Could you kindly confirm…"), short paragraphs, explicit next-step asks, sign-offs like "Many thanks in advance!" or "Let me know if that works for you." This is the tone we mirror in transactional content.

3.2 Spelling — UK English

UseDo not use
authorisationauthorization
organisationorganization
behaviourbehavior
customisecustomize
centrecenter
licence (noun) / license (verb)mixed usage
programmeprogram (except software)

3.3 Brand name

Always MirrorSphere — one word, two capitals.

Forbidden variants: Mirror Sphere, Mirrorsphere, mirrorsphere, MS (as a standalone brand reference).

3.4 Phone format

+44 (0) 1295 595 444

With the (0), grouped 4-3-3. In email templates use the merge variable $TEAMPHONENUMBER where Halo populates the team-specific line; the literal form above is reserved for the footer/CTA where the brand line is constant.

3.5 Punctuation

MarkConventionHTML entity
Em-dashReal em-dash with a space either side — like this&mdash;
Right single quoteCurly&rsquo;
Left double quoteCurly&ldquo;
Right double quoteCurly&rdquo;
Right-pointing chevronFor breadcrumbs and "view ›" links&rsaquo;
Right arrowOn CTA buttons&rarr;

Do not use straight quotes (', ") or two hyphens (--) in body content. They look unfinished.

3.6 Breadcrumbs

Use &rsaquo; with non-breaking spaces either side, italicised:

<em>Services &rsaquo; Users and Services &rsaquo; USB Enablement</em>

3.7 Emphasis convention

TagMeaning
<strong>A button label, menu item, or actionable thing to click
<em>A referenced UI element, screen name, or field name
<code>A literal command, URL, file path, code value, or token to type

Examples:

3.8 Step naming

Article kindPattern
Process articleStep N — verb phrase (em-dash, sentence case)
Reference articleWhat is X? style

4. Email template rules (Halo EmailTemplate)

4.1 Required structure

Every transactional email template must contain all 14 elements that build-email-template-scorecard.ps1 checks. The core nine (coreKeys) drive the brand score:

ElementHow it appears in HTML
620px max-width table layoutwidth="620" or max-width: 620px
Montserrat font stackMontserrat referenced in styles or font-family
Slate #394852hero/footer background
Orange #E5833Btitle dot, accent text
Teal #4CBDEElinks, button bg, accent stripes
Grey-blue #92A9BDtagline / muted text
MirrorSphere logoassets.unlayer.com/projects/0/…MS_Inline…
Dark mode block@media (prefers-color-scheme: dark)
Outlook-dark block[data-ogsc] selector pairs
Mobile media query@media … max-width: 6[0-4]0px
Outlook MSO conditional<!--[if !mso]>
Preheaderdisplay: none; max-height: 0; invisible-text block
Branded footerMirrorSphere + (OX15 4FF or Bloxham)
Legal blockVAT, Co. No, or registered in England

The brand-score formula: % of the nine core checks the template passes. ≥80 = Branded (compliant); 40–79 = Partial / needs work; <40 = Off-brand / legacy.

4.2 Layout primitives

The reference template (-550-BitLocker - New Ticket - rb) uses:

outer table (width 100%, bg #f0f2f5)
└── inner table (width 620, max-width 620, table-layout fixed)
    ├── hero (bg slate + svg circles)
    ├── 3px gradient stripe
    ├── body (bg #ffffff, padding 28px 32px 8px)
    │   ├── greeting paragraphs
    │   ├── ticket box (#f2f5f8, border-left 4px teal)
    │   ├── details box (#f2f5f8, border-left 4px teal)
    │   ├── what-happens-next box (orange border-left)
    │   ├── signoff paragraphs
    │   └── CTA card (slate bg, teal left border, teal pill button)
    ├── footer main (bg slate)
    ├── 3px gradient stripe
    └── legal block (bg slate, 9px copy)

4.3 Dark-mode handling

Two parallel mechanisms (you need both):

4.4 Mobile responsiveness

@media only screen and (max-width: 640px) {
  .outer-wrap { padding: 0 !important; }
  .header-logo td { display: block !important; width: 100% !important; }
  .header-title { display: block !important; text-align: center !important; }
  .cta-text, .cta-btn { display: block !important; width: 100% !important; }
  /* …pill rows and footer collapse to one-column too */
}

4.5 Halo merge variables

Casing is effectively case-insensitive (the 2026-05-26 audit found $remotelink, $faultid, $symptom2, $apsubject all working in production). Be consistent, prefer uppercase, but don't flag lowercase as a bug.

Critical link distinction — get this wrong and you send agents to the customer portal or vice-versa:

VariableResolves toUse in
$LINKTOREQUESTagent.mirrorsphere.com/tickets/{id}Internal / technician / "rb" (runbook) templates
$LINKTOREQUESTUSERportal.mirrorsphere.com/ticket?id={id}End-user / customer-facing templates

Other commonly used variables:

VariableMeaning
$FAULTIDTicket number
$SYMPTOM / $SYMPTOM2PLAINTicket summary + plain-text detail
$USERNAME / $FIRSTNAMERequester name
$GREETINGTime-of-day greeting ("Good morning")
$SITESite name
$STATUSTicket status
$SERIOUSNESS2Priority label
$DATEOCCUREDTicket logged date
$REQUESTTYPERequest type label
$TEAMEMAIL / $TEAMPHONENUMBERTeam contact info
$SECTIONDepartment / team name
$ORPHONEOrganisation phone (for footer line)

Custom-field variables follow the field code's casing: $CFAssetNameforCannedText, $CF00280. Mixed case is normal and correct for $CF… tokens — don't auto-uppercase them.

Subject: the email subject lives in header_text (not in <title> and not in the HTML body). Subject can use merge variables.

4.6 The body_html vs design.html question

HaloPSA stores email templates in two body fields:

Canonical body = design.html when non-empty, else body_html. Halo treats the Unlayer output as authoritative on render. In current production data they never diverge, but the scorecard flags divergence (html_divergence) so it can be cleaned up.

4.7 Origin (custom vs standard)

HaloPSA assigns IDs to email templates with a meaningful sign:

ID rangeOriginMeaning
id < 0CustomTenant-created (MirrorSphere built); naming often includes -rb, AUTO-, client prefix
id > 0StandardHalo seeded built-in slot (New Ticket Logged, Ticket Closed, Password Reset, Feedback 1-4, etc.)

The 174 negative-ID templates in this tenant are all MirrorSphere-built. The 115 positive-ID templates are all recognised Halo defaults. The scorecard uses this to classify "Custom" vs "Standard".

4.8 Audience inference

The scorecard auto-classifies External vs Internal from the strongest signal first:

  1. Link target (highest confidence):
  1. Name keywords (medium confidence):

Internal-name override beats portal-only link (because approval-flow emails embed a portal link for the approver to click but are still internal process emails).

Never hardcode https://agent.mirrorsphere.com/... or https://portal.mirrorsphere.com/... URLs inside the template body — use the $LINKTOREQUEST / $LINKTOREQUESTUSER variables instead so Halo can re-target correctly per ticket. The scorecard reports any matches of href="(https?://...(halopsa\.com|agent\.mirrorsphere\.com|portal)...)" as wins to fix.


5. KB article rules (Halo KBArticle)

5.1 Halo field placement — the most important rule

Halo fieldUse for
description_htmlThe fully-branded HTML article. Customers see this immediately under the "Description" heading on the portal.
description (plain)One utility sentence for search/notification fallback. E.g. "Step-by-step guide for requesting and retrieving your BitLocker recovery key."
resolution_htmlLeave empty. Halo hides the "Resolution" heading when there's no content.
faqlistsRequired on creation. "Ticket Guides" = id 182.

Why this matters: the agent edit view and the customer portal both render "Description" and "Resolution" as visible section headings. Putting branded content in Resolution leaves an awkward "Resolution" label sitting above the hero. Description placement makes the hero the first thing the reader sees under the first heading.

5.2 Article structure (in order)

Hero (logo + title + tagline)
Eyebrow (KB N · Category · Audience)
Lede paragraph (one-sentence summary)
Opening callouts:
  · What is X?
  · Who is this for?
Pill row (3-4 from vocabulary)
TOC                              — only if 5+ H2 sections
--- horizontal rule ---
H2 body sections with id="..." anchors
  · ordered/unordered lists for steps
  · callouts (info / warn / tip / time / success / danger)
  · tables / flow cards / step cards / email rows
  · screenshots wrapped in <figure>+<figcaption>
"If something goes wrong"        — strongly recommended
FAQ accordion                    — optional
"Need more help?" key/value table — recommended
CTA card (one urgent action)
Signoff line (KB N · Category · fallback prompt)
Branded footer (always)

5.3 Component vocabulary

These are the 16 KB components authors may use. Don't invent new ones — if something doesn't fit, the master template needs extending.

ClassPurpose
.kb-heroHero banner: logo + title + tagline. Exactly one per article, at top.
.kb-eyebrowTiny uppercase teal label, e.g. "KB 744 · Account Management · Self Service".
.kb-ledeOne-sentence summary, heavier than body text but lighter than a callout.
.kb-calloutInfo box. Variants: default (info), is-warn, is-success, is-tip, is-time, is-danger.
.kb-pill-row3-4 metadata pills from the vocabulary in section 5.4.
.kb-tocTable of contents. Only for articles with 5+ H2 sections.
.kb-flow-cards3-4 horizontal "buckets" with SVG icons. For at-a-glance summaries.
.kb-flow-pipeline5-6 sequential coloured pills with arrows. For linear "state" flows.
.kb-email-rowNumbered circle + title + description + screenshot. One per email.
.kb-tableReference table — dark header, zebra striping.
.kb-step-cardDark-header card with eyebrow + title + body. For config steps or failure scenarios.
.kb-checklistGreen callout with ✓ bullets. For "what success looks like".
.kb-faqStacked Q+A cards. Optional.
.kb-keyvalue2-column label/value table. For "Need more help?" escalation.
.kb-ctaDark card with urgency message + phone button. One per article, near the end.
.kb-signoffQuiet "KB N · Category · fallback prompt" line above the footer.

Callout colour mapping:

VariantBorder-leftBackgroundUse for
(default)#4CBDEE#f2f5f8Neutral information
is-warn#E5833B#fff8e1"Be aware" / caveat
is-success#34a853#ecfdf5Confirmation / what success looks like
is-tip#92A9BD#f8fafcQuiet recommendation
is-time#f59e0b#fffbebTime-limited / deadline notes
is-danger#c0392b#fef2f2Hard constraint / data-loss warning

5.4 Pill vocabulary

Pick 3-4 pills. Drop any that aren't relevant — don't pad with "Approval: Not Required" filler.

LabelValues
AudienceEnd User · Approver · Manager · Technician
Process Time"~5 mins" · "~30 mins" · "~1 hour"
Last ReviewedMonth + year, e.g. "May 2026"
Article TypeSelf-Service · Process Guide · Reference · Troubleshooting
DifficultyEasy · Medium · Advanced
ApprovalRequired · Not Required (only when relevant)
PlatformWindows · Mac · Mobile · All
Access LevelStandard · Privileged · Admin

Colour rotation across the row: blue (default) → orange (.is-orange) → dark (.is-dark) → muted (.is-muted). Use whichever order reads best.

5.5 Headings & anchors

5.6 Images & screenshots

Body links: #4CBDEE text, 1px solid rgba(76,189,238,.35) border-bottom that solidifies on hover. Do not strip the border-bottom — it's the signal that the text is interactive.

CTA buttons (.kb-cta-btn) override the body underline (border-bottom: none).

5.8 Inline-style policy

KB articles use classes only for layout. Inline style="…" is forbidden in body content (the master template's <style> block is the only place styles live). The exception is <img> width attributes inside the HTML the WYSIWYG inserts.


6. Scoring criteria

The machine-checkable spec used by build-email-template-scorecard.ps1 (email) and the proposed equivalents for KB articles. Each check returns a boolean. The "brand score" is the percentage of core checks passed.

Check keyLabelApplies toTest (rough description)
width620620px layoutEmailwidth="620" or max-width: 620px
montserratMontserrat fontBothmatches Montserrat in style/font-family
slateSlate #394852Bothmatches #394852 (case-insensitive)
orangeOrange #E5833BBothmatches #E5833B
blueTeal #4CBDEEBothmatches #4CBDEE
greyblueGrey-blue #92A9BDBothmatches #92A9BD
logoMS logoBothmatches MS_Inline or assets.unlayer.com
darkmodeDark modeEmailmatches @media (prefers-color-scheme: dark)
outlookdarkOutlook-dark blockEmailmatches [data-ogsc]
mobileMobile media queryEmailmatches @media … max-width: 6[0-4]0px
msoOutlook MSO conditionalEmailmatches <!--[if !mso]> or <!--[if mso]>
preheaderPreheader textEmailmatches display:none;max-height:0
footerBranded footerBothmatches MirrorSphere AND (OX15 4FF OR Bloxham)
legalLegal blockBothmatches VAT OR Co. No OR registered in England
kb_heroHero block presentKBmatches class="kb-hero"
kb_eyebrowEyebrow labelKBmatches class="kb-eyebrow"
kb_ledeLede paragraphKBmatches class="kb-lede"
kb_pill_rowPill row metadataKBmatches class="kb-pill-row"
kb_tocTOC (long articles)KBmatches class="kb-toc" (only required when 5+ H2)
kb_calloutAt least one calloutKBmatches class="kb-callout"
kb_h1_uniqueSingle H1KBexactly one <h1> element
kb_h2_idsH2 anchorsKBevery <h2> has an id attribute
kb_signoffSignoff lineKBmatches class="kb-signoff"
kb_ctaCTA cardKBmatches class="kb-cta"
kb_accent_stripeAccent gradient stripeBothmatches linear-gradient(90deg,#4CBDEE 0%,#92A9BD 100%)
kb_description_placementBranded HTML in description_htmlKBnon-empty description_html, empty resolution_html
kb_plain_desc_shortPlain description is one sentenceKBdescription field length 20-200 chars, no HTML
kb_no_inline_styleNo inline styles in bodyKBno style="…" attributes outside the <style> block
link_var_consistencyLink variable matches audienceEmailInternal templates use $LINKTOREQUEST; External use $LINKTOREQUESTUSER
no_hardcoded_portalNo hardcoded portal/agent URLsEmailno href="https://...halopsa.com..." or `href="https://(agentportal).mirrorsphere.com..."`
cf_var_casing$CF… vars match field code casingEmailinformational only — $CF… mixed case is correct
material_red_absentNo Material redBothno #c62828
material_green_absentNo Material greenBothno #2e7d32
uk_spellingUK EnglishBothno authorize, organize, behavior, customize, center
brand_name_consistentBrand name canonicalBothno Mirror Sphere, Mirrorsphere, mirrorsphere (case-insensitive)
straight_quotes_absentCurly quotes onlyBothno &apos; or unescaped straight apostrophes in body copy

Email core checks (drive the brand score): width620, montserrat, slate, darkmode, mobile, mso, preheader, footer, logo.

KB core checks (proposed): kb_hero, kb_eyebrow, kb_lede, kb_pill_row, kb_callout, kb_signoff, kb_cta, montserrat, slate, kb_accent_stripe, kb_description_placement, kb_h1_unique, footer, brand_name_consistent.


7. Forbidden patterns

Quick reference of what NOT to do. Anything in this list should be auto-flagged.

Don't doDo instead
Use Material-style colours (#2e7d32, #c62828)Use #34a853 (Success) and #c0392b (Error)
Spell the brand "Mirror Sphere" or "Mirrorsphere"Always MirrorSphere
Use American spelling (authorize, organization, behavior)UK English — authorise, organisation, behaviour
Wrap content in inline-styled <div style="…">Use the .kb-callout (or other) class
Hardcode https://agent.mirrorsphere.com/tickets/123 in an emailUse $LINKTOREQUEST or $LINKTOREQUESTUSER
Hardcode https://portal.mirrorsphere.com/ticket?id=… in an emailUse $LINKTOREQUESTUSER
Send technicians to the customer portal$LINKTOREQUEST for agent templates (audit caught this in -506)
Use emoji as decoration in body textWords, callouts, or SVG icons inside .kb-flow-card
Write a custom footer per templateUse the canonical branded footer block
Use straight quotes ' " or --Curly quotes &rsquo; &ldquo; &rdquo; and em-dash &mdash;
Put branded content in resolution_htmlPut it in description_html
Have two <h1> elements in one KB articleOne H1 (the hero title), H2s for sections
Use "Click here" link textQuote the button label exactly: <strong>Submit</strong>
Pad pill row with "Approval: Not Required"Drop irrelevant pills, keep 3-4 meaningful ones
Reuse body content of the pill row in the body copyThe pills replace that content, they don't duplicate it
Skip dark-mode + Outlook-dark blocks on an emailBoth @media (prefers-color-scheme: dark) and [data-ogsc]
Skip the preheader on an emailAdd a display:none;max-height:0 block at the top
Use the system font stack without Montserrat first'Montserrat', Arial, Helvetica, sans-serif
Set width="900" on an email outer tableEmail layout is 620px; 900 is the KB layout
Use sales language or jargon in KB bodyMatch the customer-reply tone in the exemplars

8. Reference templates

The canonical examples Claude and authors should imitate. Read these first before writing new content.

Email

KB article

Voice

Audit tooling

Halo API quick reference


Last updated: 2026-05-28. Brand DNA derived from -550-BitLocker - New Ticket - rb (email) and _mockup-744-BitLocker.html (KB). Checks encoded in build-email-template-scorecard.ps1. Voice from integrations/anthropic/brand-voice/exemplars.md.