{"id":6,"date":"2026-02-06T21:18:30","date_gmt":"2026-02-06T21:18:30","guid":{"rendered":"https:\/\/www.harperfamily.ca\/?page_id=6"},"modified":"2026-10-10T12:29:29","modified_gmt":"2026-10-10T12:29:29","slug":"home","status":"publish","type":"page","link":"https:\/\/www.harperfamily.ca\/","title":{"rendered":"Welcome to the Harper Family"},"content":{"rendered":"<style> \/* ============================================================ Welcome to the Harper Family \u2014 site root landing page Self-contained. No external stylesheets, fonts, or scripts. Published through scripts\/publish.js, which strips newlines so WordPress's wpautop filter cannot inject paragraph or break tags into this stylesheet. Do not hand-edit the published page. ============================================================ *\/ \/* --- Kadence theme container reset: let the page run full-bleed --- *\/ .entry-content, .entry-content-wrap { padding: 0 !important; margin: 0 !important; } .content-area { margin-top: 0 !important; margin-bottom: 0 !important; } .content-bg, .entry.single-entry { box-shadow: none !important; background: transparent !important; } .hf-home { width: 100% !important; max-width: 100% !important; margin-left: 0 !important; margin-right: 0 !important; } \/* --- Design tokens: warm and vibrant, deliberately unlike the resume page --- *\/ .hf-home { --hf-ink: #2b1b17; --hf-body: #6b4a40; --hf-muted: #8a6a5f; --hf-faint: #b09a91; --hf-line: #f2ddd3; --hf-surface: #ffffff; --hf-surface-alt: #fff8f4; --hf-coral: #f2552c; --hf-coral-dark: #d63c16; --hf-teal: #0d9488; --hf-radius: 20px; --hf-shadow: 0 1px 2px rgba(80,35,20,.05), 0 10px 30px rgba(80,35,20,.08); --hf-shadow-lift: 0 20px 48px rgba(80,35,20,.16); } \/* --- Base --- *\/ .hf-home, .hf-home * { box-sizing: border-box; } .hf-home { font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif; color: var(--hf-body); line-height: 1.65; background: var(--hf-surface); overflow-x: hidden; -webkit-font-smoothing: antialiased; } .hf-home p, .hf-home h1, .hf-home h2, .hf-home h3, .hf-home h4, .hf-home ul, .hf-home ol, .hf-home figure { margin: 0; padding: 0; } \/* wpautop paragraph-wraps inline children of a block container, which we cannot prevent from here: every anchor is inline. Two defences. First, drop the empty paragraphs it leaves behind, so they never occupy a grid or flex slot. Second, where such a wrapper would itself become the flex item in place of the links, take it back out of the layout so the real children keep their own gap and alignment. *\/ .hf-home p:empty { display: none; } .hf-hero-actions > p, .hf-footer-links > p, .hf-card-foot > p, .hf-badges > p { display: contents; } .hf-home ul { list-style: none; } .hf-home a { color: inherit; text-decoration: none; } .hf-home img { max-width: 100%; height: auto; display: block; } .hf-home h1, .hf-home h2, .hf-home h3 { color: var(--hf-ink); letter-spacing: -.02em; line-height: 1.15; } .hf-home a:focus-visible { outline: 3px solid var(--hf-teal); outline-offset: 3px; border-radius: 6px; } \/* --- Hero --- *\/ \/* The family home in autumn, behind a warm scrim. Layer order is top-down, so the photo is listed last. The radial is centred on the text block and is the darkest layer: the photo's sky is pale grey, and white type over pale grey is unreadable, so the copy needs its own pool of shadow while the brick and maples stay visible out at the edges. *\/ .hf-hero { position: relative; overflow: hidden; color: #fff; padding: 96px 24px 88px; min-height: 480px; display: flex; align-items: center; justify-content: center; text-align: center; background: radial-gradient(900px 440px at 50% 46%, rgba(38,11,5,.82) 0%, rgba(38,11,5,.46) 62%, rgba(38,11,5,.12) 100%), radial-gradient(700px 400px at 12% 6%, rgba(255,176,60,.26), transparent 64%), linear-gradient(180deg, rgba(48,15,8,.60) 0%, rgba(74,21,12,.52) 40%, rgba(110,32,18,.66) 100%), url('https:\/\/www.harperfamily.ca\/wp-content\/uploads\/2026\/10\/harper-home-hero.jpg') center 46% \/ cover no-repeat, #3a1c14; } \/* Fade the photo into the page below it instead of ending on a hard edge. *\/ .hf-hero::after { content: ''; position: absolute; left: 0; right: 0; bottom: 0; height: 110px; pointer-events: none; background: linear-gradient(180deg, transparent, rgba(255,255,255,.92) 88%, #fff 100%); } .hf-hero-inner { position: relative; z-index: 1; max-width: 860px; margin: 0 auto; } .hf-chip { display: inline-flex; align-items: center; gap: 9px; padding: 7px 16px; border-radius: 999px; margin-bottom: 22px; font-size: .82rem; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; background: rgba(255,255,255,.17); border: 1px solid rgba(255,255,255,.34); color: #fff; } .hf-chip-dot { width: 8px; height: 8px; border-radius: 50%; background: #6ee7b7; box-shadow: 0 0 0 4px rgba(110,231,183,.26); } .hf-hero h1 { color: #fff; font-size: 3.5rem; font-weight: 800; letter-spacing: -.038em; margin-bottom: 18px; text-shadow: 0 2px 18px rgba(0,0,0,.55), 0 1px 3px rgba(0,0,0,.38); } .hf-hero h1 em { font-style: normal; display: block; color: #ffe8a3; } .hf-hero-lede { font-size: 1.16rem; color: rgba(255,255,255,.96); max-width: 620px; margin: 0 auto 32px; text-shadow: 0 1px 10px rgba(0,0,0,.5); } .hf-hero-actions { display: flex; gap: 14px; justify-content: center; flex-wrap: wrap; } .hf-btn { display: inline-flex; align-items: center; gap: 9px; padding: 14px 26px; border-radius: 999px; font-size: .98rem; font-weight: 700; transition: transform .2s ease, box-shadow .2s ease, background .2s ease; } .hf-btn svg { flex-shrink: 0; } \/* These MUST stay qualified with \"a\" to outrank \".hf-home a { color: inherit }\" above (0,1,1). A bare \".hf-btn-solid\" is only (0,1,0), so it loses, the button inherits the hero's white text and goes white-on-white. *\/ .hf-home a.hf-btn-solid { background: #fff; color: var(--hf-coral-dark); box-shadow: 0 10px 26px rgba(90,20,10,.26); } .hf-home a.hf-btn-solid:hover { background: #fff; color: var(--hf-coral-dark); transform: translateY(-2px); box-shadow: 0 16px 34px rgba(90,20,10,.32); } .hf-home a.hf-btn-ghost { background: rgba(255,255,255,.14); color: #fff; border: 1.5px solid rgba(255,255,255,.55); } .hf-home a.hf-btn-ghost:hover { background: rgba(255,255,255,.26); color: #fff; transform: translateY(-2px); } \/* --- Section shell --- *\/ .hf-section { max-width: 1100px; margin: 0 auto; padding: 72px 24px; } .hf-section-alt { background: var(--hf-surface-alt); border-top: 1px solid var(--hf-line); border-bottom: 1px solid var(--hf-line); max-width: 100%; } .hf-section-alt > .hf-inner { max-width: 1100px; margin: 0 auto; } .hf-head { text-align: center; max-width: 640px; margin: 0 auto 44px; } .hf-eyebrow { display: block; font-size: .78rem; font-weight: 750; letter-spacing: .14em; text-transform: uppercase; color: var(--hf-coral); margin-bottom: 11px; } .hf-head h2 { font-size: 2.1rem; font-weight: 780; margin-bottom: 12px; } .hf-head p { font-size: 1.03rem; color: var(--hf-muted); } \/* --- Service cards: free-flowing cascade --- Every card is the same shape \u2014 hero band, then body, then the action pinned to the bottom edge \u2014 so they no longer need a fixed column count to look tidy. auto-fit lets them reflow to whatever the viewport allows (three wide, two, then one) while align-items:stretch plus the auto margin on the action row keeps every row squared off rather than ragged. *\/ .hf-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(300px, 1fr)); gap: 28px; align-items: stretch; } .hf-card { position: relative; display: flex; flex-direction: column; overflow: hidden; background: var(--hf-surface); border: 1px solid var(--hf-line); border-radius: var(--hf-radius); box-shadow: var(--hf-shadow); transition: transform .26s ease, box-shadow .26s ease, border-color .26s ease; } .hf-card:hover { transform: translateY(-5px); box-shadow: var(--hf-shadow-lift); border-color: var(--hf-ca, var(--hf-coral)); } \/* Hero band: the per-app icon, large, on its own colour. *\/ .hf-card-hero { position: relative; overflow: hidden; height: 104px; flex-shrink: 0; display: flex; align-items: center; justify-content: center; background: linear-gradient(135deg, var(--hf-ca, var(--hf-coral)) 0%, var(--hf-ca2, var(--hf-coral)) 100%); color: #fff; } .hf-card-hero::after { content: ''; position: absolute; inset: 0; pointer-events: none; opacity: .32; background-image: radial-gradient(rgba(255,255,255,.55) 1px, transparent 1px); background-size: 18px 18px; } .hf-card-glyph { position: relative; z-index: 1; filter: drop-shadow(0 2px 6px rgba(0,0,0,.18)); } .hf-card-hero .hf-card-avatar { position: relative; z-index: 1; width: 76px; height: 76px; border-radius: 50%; object-fit: cover; border: 3px solid rgba(255,255,255,.9); box-shadow: 0 4px 14px rgba(0,0,0,.2); } \/* Body: fixed rhythm so two cards side by side line up row for row. *\/ .hf-card-body { display: flex; flex-direction: column; flex: 1 1 auto; padding: 22px 24px 0; } .hf-card h3 { font-size: 1.24rem; font-weight: 770; margin-bottom: 3px; } .hf-card-host { display: block; font-size: .8rem; font-weight: 600; color: var(--hf-faint); word-break: break-all; margin-bottom: 13px; } .hf-badges { display: flex; flex-wrap: wrap; gap: 6px; margin-bottom: 13px; } .hf-badge { display: inline-flex; align-items: center; gap: 6px; font-size: .73rem; font-weight: 700; padding: 4px 10px; border-radius: 999px; background: var(--hf-cs, #fff1ec); color: var(--hf-ca, var(--hf-coral)); } .hf-badge-live::before { content: ''; width: 7px; height: 7px; border-radius: 50%; background: #10b981; } .hf-badge-lock, .hf-badge-pending { background: #f4f1ef; color: #7a6a63; } .hf-card-desc { font-size: .95rem; color: var(--hf-body); margin-bottom: 20px; } \/* The action sits on its own full-width row, always at the card's foot. It is the card's only anchor. Cards are divs on purpose: an anchor is an inline element, so wpautop paragraph-wraps it, the first block-level child then force-closes that paragraph, and the orphaned closing tag renders as an empty grid cell \u2014 the phantom \"spacer card\". Qualified with \"a\" to outrank \".hf-home a { color: inherit }\" (0,1,1). *\/ .hf-card-foot { margin-top: auto; margin-left: -24px; margin-right: -24px; border-top: 1px solid var(--hf-line); background: var(--hf-cs, #fff1ec); } .hf-home a.hf-card-go { padding: 15px 24px; display: flex; align-items: center; justify-content: space-between; gap: 10px; font-size: .92rem; font-weight: 750; color: var(--hf-ca, var(--hf-coral)); } \/* Stretched link: the anchor's hit area covers the whole card, so the card stays clickable without nesting blocks inside the anchor. *\/ .hf-card-go::after { content: ''; position: absolute; inset: 0; } .hf-card { cursor: pointer; } .hf-card-go svg { transition: transform .22s ease; flex-shrink: 0; } .hf-card:hover .hf-card-go svg { transform: translateX(4px); } \/* A service that exists but is not reachable yet: shown, never linked, so the page never ships a dead href. Flip it to an anchor once DNS and TLS land. *\/ .hf-card-pending { border-style: dashed; box-shadow: none; cursor: default; } .hf-card-pending:hover { transform: none; box-shadow: none; border-color: var(--hf-line); } .hf-card-pending .hf-card-hero { background: linear-gradient(135deg, #cbbfb9 0%, #ded5d0 100%); } .hf-card-pending .hf-card-foot { background: #faf6f4; } .hf-card-pending .hf-card-go { color: var(--hf-faint); } \/* --- Work section: single card, kept clear of the family grid --- *\/ .hf-work { max-width: 520px; margin: 0 auto; } \/* --- Footer --- *\/ .hf-footer { background: linear-gradient(135deg, #3a1c14 0%, #5b2318 100%); color: rgba(255,230,220,.78); padding: 40px 24px; text-align: center; } .hf-footer-name { color: #fff; font-weight: 750; font-size: 1.05rem; margin-bottom: 8px; } .hf-footer-links { display: flex; gap: 18px; justify-content: center; flex-wrap: wrap; margin: 14px 0 18px; } .hf-footer-links a { color: #ffd9a8; font-size: .9rem; font-weight: 650; } .hf-footer-links a:hover { color: #fff; text-decoration: underline; } .hf-footer-legal { font-size: .83rem; color: rgba(255,230,220,.6); padding-top: 18px; border-top: 1px solid rgba(255,255,255,.13); max-width: 560px; margin: 0 auto; } \/* --- Responsive --- *\/ @media (max-width: 860px) { .hf-hero { padding: 68px 20px 62px; min-height: 420px; } .hf-hero h1 { font-size: 2.5rem; } .hf-hero-lede { font-size: 1.04rem; } .hf-section { padding: 52px 20px; } .hf-head { margin-bottom: 32px; } .hf-head h2 { font-size: 1.68rem; } .hf-grid { gap: 22px; } } @media (max-width: 680px) { .hf-hero { padding: 56px 16px 52px; min-height: 360px; } .hf-hero h1 { font-size: 2.05rem; } .hf-section { padding: 44px 16px; } .hf-btn { width: 100%; justify-content: center; } .hf-grid { gap: 20px; } .hf-card-hero { height: 88px; } } @media (prefers-reduced-motion: reduce) { .hf-home * { transition: none !important; } } <\/style>\n<div class=\"hf-home\">\n<header class=\"hf-hero\">\n<div class=\"hf-hero-inner\">\n<div class=\"hf-chip\"><span class=\"hf-chip-dot\"><\/span> harperfamily.ca<\/div>\n<h1>Welcome to the <em>Harper Family<\/em><\/h1>\n<p class=\"hf-hero-lede\">This is our corner of the web &mdash; home to the apps and services we run for ourselves, and to the work we do out in the world. Have a look around.<\/p>\n<div class=\"hf-hero-actions\"> <a class=\"hf-btn hf-btn-solid\" href=\"#services\"> <svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><rect x=\"3\" y=\"3\" width=\"7\" height=\"7\" rx=\"1.6\"\/><rect x=\"14\" y=\"3\" width=\"7\" height=\"7\" rx=\"1.6\"\/><rect x=\"3\" y=\"14\" width=\"7\" height=\"7\" rx=\"1.6\"\/><rect x=\"14\" y=\"14\" width=\"7\" height=\"7\" rx=\"1.6\"\/><\/svg> Family services <\/a> <a class=\"hf-btn hf-btn-ghost\" href=\"https:\/\/www.harperfamily.ca\/index.php\/resume\/\"> <svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><path d=\"M14 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V8z\"\/><polyline points=\"14 2 14 8 20 8\"\/><line x1=\"8\" y1=\"13\" x2=\"16\" y2=\"13\"\/><line x1=\"8\" y1=\"17\" x2=\"13\" y2=\"17\"\/><\/svg> Craig&#8217;s Resume <\/a> <\/div>\n<\/p><\/div>\n<\/header>\n<section class=\"hf-section\" id=\"services\">\n<div class=\"hf-head\">\n<div class=\"hf-eyebrow\">For the family<\/div>\n<h2>Everything we run at home<\/h2>\n<p>Six services, all hosted on our own hardware and reachable from anywhere. Most ask you to sign in.<\/p>\n<\/p><\/div>\n<div class=\"hf-grid\">\n<div class=\"hf-card\" style=\"--hf-ca:#0d9488;--hf-ca2:#14b8a6;--hf-cs:#effbf8;\">\n<div class=\"hf-card-hero\"> <svg class=\"hf-card-glyph\" width=\"46\" height=\"46\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.9\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><rect x=\"3\" y=\"3\" width=\"7.5\" height=\"7.5\" rx=\"1.8\"\/><rect x=\"13.5\" y=\"3\" width=\"7.5\" height=\"7.5\" rx=\"1.8\"\/><rect x=\"3\" y=\"13.5\" width=\"7.5\" height=\"7.5\" rx=\"1.8\"\/><rect x=\"13.5\" y=\"13.5\" width=\"7.5\" height=\"7.5\" rx=\"1.8\"\/><\/svg> <\/div>\n<div class=\"hf-card-body\">\n<h3>Apps<\/h3>\n<div class=\"hf-card-host\">webapps.harperfamily.ca<\/div>\n<div class=\"hf-badges\"> <span class=\"hf-badge hf-badge-live\">1 app live<\/span> <span class=\"hf-badge\">Built in-house<\/span> <\/div>\n<p class=\"hf-card-desc\">Small web apps built for our own household. <strong>Calorie Counter<\/strong> estimates a meal&#8217;s calories from a spoken description, ingredient by ingredient. More on the way.<\/p>\n<div class=\"hf-card-foot\"> <a class=\"hf-card-go\" href=\"https:\/\/webapps.harperfamily.ca\/\"><span>Open Apps<\/span> <svg width=\"17\" height=\"17\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.4\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><line x1=\"5\" y1=\"12\" x2=\"19\" y2=\"12\"\/><polyline points=\"12 5 19 12 12 19\"\/><\/svg> <\/a> <\/div>\n<\/p><\/div>\n<\/p><\/div>\n<div class=\"hf-card\" style=\"--hf-ca:#7c3aed;--hf-ca2:#a855f7;--hf-cs:#f5f0ff;\">\n<div class=\"hf-card-hero\"> <svg class=\"hf-card-glyph\" width=\"46\" height=\"46\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.9\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><rect x=\"3\" y=\"4.5\" width=\"18\" height=\"16.5\" rx=\"2.4\"\/><line x1=\"16\" y1=\"2.5\" x2=\"16\" y2=\"6.5\"\/><line x1=\"8\" y1=\"2.5\" x2=\"8\" y2=\"6.5\"\/><line x1=\"3\" y1=\"10\" x2=\"21\" y2=\"10\"\/><rect x=\"6.6\" y=\"13\" width=\"3.2\" height=\"3.2\" rx=\".6\" fill=\"currentColor\" stroke=\"none\"\/><\/svg> <\/div>\n<div class=\"hf-card-body\">\n<h3>Calendar<\/h3>\n<div class=\"hf-card-host\">calendar.harperfamily.ca<\/div>\n<div class=\"hf-badges\"><span class=\"hf-badge hf-badge-lock\">Sign-in<\/span><\/div>\n<p class=\"hf-card-desc\">One shared family calendar, kept in step with Google and iCloud so everybody sees the same week.<\/p>\n<div class=\"hf-card-foot\"> <a class=\"hf-card-go\" href=\"https:\/\/calendar.harperfamily.ca\/\"><span>Open Calendar<\/span> <svg width=\"17\" height=\"17\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.4\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><line x1=\"5\" y1=\"12\" x2=\"19\" y2=\"12\"\/><polyline points=\"12 5 19 12 12 19\"\/><\/svg> <\/a> <\/div>\n<\/p><\/div>\n<\/p><\/div>\n<div class=\"hf-card\" style=\"--hf-ca:#ea8f06;--hf-ca2:#fbbf24;--hf-cs:#fff8e8;\">\n<div class=\"hf-card-hero\"> <svg class=\"hf-card-glyph\" width=\"46\" height=\"46\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.9\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><rect x=\"2\" y=\"4.5\" width=\"20\" height=\"15\" rx=\"2.4\"\/><polyline points=\"2.8 6.6 12 13.6 21.2 6.6\"\/><\/svg> <\/div>\n<div class=\"hf-card-body\">\n<h3>Mail<\/h3>\n<div class=\"hf-card-host\">webmail.harperfamily.ca<\/div>\n<div class=\"hf-badges\"><span class=\"hf-badge hf-badge-lock\">Sign-in<\/span><\/div>\n<p class=\"hf-card-desc\">Harper Family Mail &mdash; read and send from the family mailboxes in any browser.<\/p>\n<div class=\"hf-card-foot\"> <a class=\"hf-card-go\" href=\"https:\/\/webmail.harperfamily.ca\/\"><span>Open Mail<\/span> <svg width=\"17\" height=\"17\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.4\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><line x1=\"5\" y1=\"12\" x2=\"19\" y2=\"12\"\/><polyline points=\"12 5 19 12 12 19\"\/><\/svg> <\/a> <\/div>\n<\/p><\/div>\n<\/p><\/div>\n<div class=\"hf-card\" style=\"--hf-ca:#be123c;--hf-ca2:#f43f5e;--hf-cs:#fff0f3;\">\n<div class=\"hf-card-hero\"> <svg class=\"hf-card-glyph\" width=\"46\" height=\"46\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.9\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><path d=\"M4.5 11.5a8.5 8.5 0 0 1 8.5 8.5\"\/><path d=\"M4.5 4.5a15.5 15.5 0 0 1 15.5 15.5\"\/><circle cx=\"5.4\" cy=\"19.1\" r=\"1.8\" fill=\"currentColor\" stroke=\"none\"\/><\/svg> <\/div>\n<div class=\"hf-card-body\">\n<h3>News<\/h3>\n<div class=\"hf-card-host\">news.harperfamily.ca<\/div>\n<div class=\"hf-badges\"><span class=\"hf-badge hf-badge-lock\">Sign-in<\/span><\/div>\n<p class=\"hf-card-desc\">Our own news reader &mdash; curated Canadian, US, technology, gaming and home-lab feeds, all in one place and free of algorithmic noise.<\/p>\n<div class=\"hf-card-foot\"> <a class=\"hf-card-go\" href=\"https:\/\/news.harperfamily.ca\/\"><span>Open News<\/span> <svg width=\"17\" height=\"17\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.4\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><line x1=\"5\" y1=\"12\" x2=\"19\" y2=\"12\"\/><polyline points=\"12 5 19 12 12 19\"\/><\/svg> <\/a> <\/div>\n<\/p><\/div>\n<\/p><\/div>\n<div class=\"hf-card\" style=\"--hf-ca:#0284c7;--hf-ca2:#38bdf8;--hf-cs:#eef9ff;\">\n<div class=\"hf-card-hero\"> <svg class=\"hf-card-glyph\" width=\"46\" height=\"46\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.9\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><path d=\"M4 20h16a2 2 0 0 0 2-2V9a2 2 0 0 0-2-2h-7L11 4H4a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2z\"\/><\/svg> <\/div>\n<div class=\"hf-card-body\">\n<h3>Files<\/h3>\n<div class=\"hf-card-host\">nextcloud.harperfamily.ca<\/div>\n<div class=\"hf-badges\"><span class=\"hf-badge hf-badge-lock\">Sign-in<\/span><\/div>\n<p class=\"hf-card-desc\">Private file storage and sharing on our own Nextcloud, with nothing sitting on someone else&#8217;s cloud.<\/p>\n<div class=\"hf-card-foot\"> <a class=\"hf-card-go\" href=\"https:\/\/nextcloud.harperfamily.ca\/\"><span>Open Files<\/span> <svg width=\"17\" height=\"17\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.4\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><line x1=\"5\" y1=\"12\" x2=\"19\" y2=\"12\"\/><polyline points=\"12 5 19 12 12 19\"\/><\/svg> <\/a> <\/div>\n<\/p><\/div>\n<\/p><\/div>\n<div class=\"hf-card\" style=\"--hf-ca:#c87f0a;--hf-ca2:#f0b63f;--hf-cs:#fff7e6;\">\n<div class=\"hf-card-hero\"> <svg class=\"hf-card-glyph\" width=\"46\" height=\"46\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.9\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><rect x=\"2\" y=\"3.5\" width=\"20\" height=\"13.5\" rx=\"2.4\"\/><polygon points=\"10.2 7.6 15 10.25 10.2 12.9\" fill=\"currentColor\" stroke=\"none\"\/><line x1=\"8\" y1=\"20.8\" x2=\"16\" y2=\"20.8\"\/><line x1=\"12\" y1=\"17\" x2=\"12\" y2=\"20.8\"\/><\/svg> <\/div>\n<div class=\"hf-card-body\">\n<h3>Media<\/h3>\n<div class=\"hf-card-host\">plex.harperfamily.ca<\/div>\n<div class=\"hf-badges\"><span class=\"hf-badge hf-badge-lock\">Sign-in<\/span><\/div>\n<p class=\"hf-card-desc\">The family Plex library &mdash; films, shows and music, streamed to whichever screen you are near.<\/p>\n<div class=\"hf-card-foot\"> <a class=\"hf-card-go\" href=\"https:\/\/plex.harperfamily.ca\/web\/index.html\"><span>Open Media<\/span> <svg width=\"17\" height=\"17\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.4\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><line x1=\"5\" y1=\"12\" x2=\"19\" y2=\"12\"\/><polyline points=\"12 5 19 12 12 19\"\/><\/svg> <\/a> <\/div>\n<\/p><\/div>\n<\/p><\/div>\n<\/p><\/div>\n<\/section>\n<section class=\"hf-section hf-section-alt\" id=\"work\">\n<div class=\"hf-inner\">\n<div class=\"hf-head\">\n<div class=\"hf-eyebrow\">Work<\/div>\n<h2>Craig&#8217;s professional site<\/h2>\n<p>Separate from the family side, and the page to send a recruiter to.<\/p>\n<\/p><\/div>\n<div class=\"hf-work\">\n<div class=\"hf-card\" style=\"--hf-ca:#1d4ed8;--hf-ca2:#3b82f6;--hf-cs:#eff6ff;\">\n<div class=\"hf-card-hero\"> <img decoding=\"async\" src=\"https:\/\/www.harperfamily.ca\/wp-content\/uploads\/2026\/02\/craig-harper-profile.jpg\" alt=\"Portrait of Craig Harper\" class=\"hf-card-avatar\" width=\"76\" height=\"76\" loading=\"lazy\" \/> <\/div>\n<div class=\"hf-card-body\">\n<h3>Craig Harper<\/h3>\n<div class=\"hf-card-host\">Project &amp; programme management<\/div>\n<div class=\"hf-badges\"> <span class=\"hf-badge hf-badge-live\">Open to roles<\/span> <span class=\"hf-badge\">PMP &middot; SAFe 6 Agilist<\/span> <\/div>\n<p class=\"hf-card-desc\">Twenty-plus years leading enterprise technology programmes in financial services, energy and software &mdash; currently modernising a corporate risk data platform from PostgreSQL to Snowflake.<\/p>\n<div class=\"hf-card-foot\"> <a class=\"hf-card-go\" href=\"https:\/\/www.harperfamily.ca\/index.php\/resume\/\"><span>View the resume<\/span> <svg width=\"17\" height=\"17\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.4\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\"><line x1=\"5\" y1=\"12\" x2=\"19\" y2=\"12\"\/><polyline points=\"12 5 19 12 12 19\"\/><\/svg> <\/a> <\/div>\n<\/p><\/div>\n<\/p><\/div>\n<\/p><\/div>\n<\/p><\/div>\n<\/section>\n<footer class=\"hf-footer\">\n<div class=\"hf-footer-name\">The Harper Family<\/div>\n<div>harperfamily.ca<\/div>\n<div class=\"hf-footer-links\"> <a href=\"https:\/\/webapps.harperfamily.ca\/\">Apps<\/a> <a href=\"https:\/\/calendar.harperfamily.ca\/\">Calendar<\/a> <a href=\"https:\/\/webmail.harperfamily.ca\/\">Mail<\/a> <a href=\"https:\/\/news.harperfamily.ca\/\">News<\/a> <a href=\"https:\/\/nextcloud.harperfamily.ca\/\">Files<\/a> <a href=\"https:\/\/plex.harperfamily.ca\/web\/index.html\">Media<\/a> <a href=\"https:\/\/www.harperfamily.ca\/index.php\/resume\/\">Craig&#8217;s Resume<\/a> <\/div>\n<div class=\"hf-footer-legal\">&copy; 2026 The Harper Family. Built and maintained at home.<\/div>\n<\/footer><\/div>\n","protected":false},"excerpt":{"rendered":"<p>harperfamily.ca Welcome to the Harper Family This is our corner of the web &mdash; home to the apps and services we run for ourselves, and to the work we do out in the world. Have a look around. Family services Craig&#8217;s Resume For the family Everything we run at home Six services, all hosted on&#8230;<\/p>\n","protected":false},"author":1,"featured_media":0,"parent":0,"menu_order":0,"comment_status":"closed","ping_status":"closed","template":"","meta":{"_kad_post_transparent":"","_kad_post_title":"hide","_kad_post_layout":"","_kad_post_sidebar_id":"","_kad_post_content_style":"wide","_kad_post_vertical_padding":"remove","_kad_post_feature":"","_kad_post_feature_position":"","_kad_post_header":false,"_kad_post_footer":false,"_kad_post_classname":"","footnotes":""},"class_list":["post-6","page","type-page","status-publish","hentry"],"_links":{"self":[{"href":"https:\/\/www.harperfamily.ca\/index.php\/wp-json\/wp\/v2\/pages\/6","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.harperfamily.ca\/index.php\/wp-json\/wp\/v2\/pages"}],"about":[{"href":"https:\/\/www.harperfamily.ca\/index.php\/wp-json\/wp\/v2\/types\/page"}],"author":[{"embeddable":true,"href":"https:\/\/www.harperfamily.ca\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.harperfamily.ca\/index.php\/wp-json\/wp\/v2\/comments?post=6"}],"version-history":[{"count":29,"href":"https:\/\/www.harperfamily.ca\/index.php\/wp-json\/wp\/v2\/pages\/6\/revisions"}],"predecessor-version":[{"id":52,"href":"https:\/\/www.harperfamily.ca\/index.php\/wp-json\/wp\/v2\/pages\/6\/revisions\/52"}],"wp:attachment":[{"href":"https:\/\/www.harperfamily.ca\/index.php\/wp-json\/wp\/v2\/media?parent=6"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}