<?xml version="1.0" encoding="utf-8"?>
<!--
  Analytics Legends release-notes feed — Atom 1.0.

  v72.23 (deep-review item #5): introduces a machine-readable release
  feed so journalists, security researchers and the handful of power
  users who follow platform changelogs can subscribe from any RSS /
  Atom reader instead of reloading /#status by hand.

  Discovered in three ways:
    1. <link rel="alternate" type="application/atom+xml" href="/feed.xml">
       in the document <head> — any reader-mode browser extension or
       RSS auto-discover plugin picks this up from the homepage URL.
    2. Direct surface link in the Footer "Transparency" column next to
       humans.txt / llms.txt / sitemap.xml etc.
    3. Listed in /humans.txt under a new POLICY bullet.

  Feed format choice: Atom 1.0 (RFC 4287) rather than RSS 2.0 because
  Atom has a well-specified author element, cleaner content-type
  handling (type="html" here), required <updated> timestamp semantics,
  and a required stable <id> that isn't the URL. All modern readers
  (NetNewsWire, Feedly, Inoreader, Miniflux, FreshRSS, Thunderbird,
  etc.) consume Atom natively.

  Static file rather than build-time generated: generating the feed
  from RELEASE_NOTES in src/AnalyticsLegends.jsx would require either
  (a) parsing JSX at build time or (b) extracting RELEASE_NOTES to a
  standalone JSON module. Both are tractable but neither is warranted
  yet — the release cadence is slow enough (1–3 releases per day when
  active, zero most days) that curating this feed as part of the
  release ritual is less mechanism than a build-time extractor.
  If the cadence accelerates, promote this to a postbuild generator
  similar to scripts/stamp-sitemap.mjs.

  Entry count: 10 most-recent releases. Older releases remain in
  /#status and are not re-exposed via the feed because readers
  typically show unread-only so a large backfill would flood
  subscribers' timelines on first subscription.

  Last curated at v72.70.3. Ritual: every release that touches this
  file (i.e., every release from v72.23 onwards) prepends one new
  <entry> and drops the oldest so the feed stays at 10.

  Reserved-skip versions (deliberately not shipped, slot held for
  the IA-refactor bundle queue): v72.41 (folded into v72.55 narrative
  + dropped from window in v72.55 ship), v72.51, v72.52, v72.53,
  v72.54 (originally allocated to IA refactor bundles 2-5 — top-nav
  cut, alias-deprecation banner, free-tools cull, hard delete — and
  slipped to v72.58-v72.61 after operator picked "all of them one
  after the other" for v72.55 instead, then design/UX work claimed
  v72.57). Feed readers may notice these gaps; they are intentional,
  not missed releases.
-->
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
  <title>Analytics Legends — Release Notes</title>
  <subtitle>Build notes and platform changelog for analyticslegends.ai — the platform and AI agent for Datasphere, BDC, SAC, BW/4HANA experts.</subtitle>
  <link href="https://analyticslegends.ai/feed.xml" rel="self" type="application/atom+xml" />
  <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" hreflang="en" />
  <id>https://analyticslegends.ai/</id>
  <updated>2026-04-26T12:30:00Z</updated>
  <author>
    <name>Analytics Legends</name>
    <email>contact@analyticslegends.ai</email>
    <uri>https://analyticslegends.ai/</uri>
  </author>
  <generator uri="https://analyticslegends.ai/" version="72.70.4">Analytics Legends</generator>
  <icon>https://analyticslegends.ai/favicon.svg</icon>
  <logo>https://analyticslegends.ai/logo.svg</logo>
  <rights>© 2026 Analytics Legends. Release notes reproduced from /#status under the site's Terms of Service (/#terms). No AI training license granted — see /llms.txt.</rights>

  <entry>
    <title>v72.70.3 — operator-directive hotfix bundle on top of v72.70.2 closing three immediate operator remarks 2026-04-26 verbatim "remove Agencies / 159 / Updated 2026-04-24 / Top 100 / 100 / Updated 2026-04-23 / Job platforms / 15" + "does not" (clarifying that the named operator must NOT appear) + "have checked all corrections made on studies in english have also been applied to french versions" · 3 items shipped · AGENCIES TAB CLEANUP — the TABS tuple in HeadhuntersView/ContractsHubPage was simplified from 4-element [key, label, count, updatedAt] back to 2-element [key, label] pairs so the visible tab strip renders only the 3 labels (Agencies / Top 100 / Job platforms) without the numeric chip + freshness caption that v72.70.2 had introduced. The freshness data is still surfaced via the page-level refresh button + hydratedAt timestamp; the per-tab counters and dates were redundant noise the operator did not want · CEDRIC-MARY USER-FACING SCRUB — operator clarified 2026-04-26 ("does not") that the named operator must NOT appear on the public surface; v72.69 had already redacted the manifests but four user-visible leaks survived: v72.29 RELEASE_NOTES EN+FR (the eyebrow ship-history page) carried "i am signed in as cedric mary" and "cedric.mary@analyticslegends.ai (and two variants)" and "For you, Cedric/Cédric" in the operator narrative; a code comment (line 16373) referenced "as cedric mary"; v72.70.3 redacts those four spots to "[operator]", "the operator email allowlist (3 variants)", and "[first name]/[prénom]" respectively. The about.json shipped_version_note rewrite drops the explicit "Cedric Mary" reference. Historical feed.xml entries are intentionally untouched as immutable paper-trail · FR STUDY PARITY VERIFIED — operator: "have checked all corrections made on studies in english have also been applied to french versions". Re-read both EN (lines 4305-4350) and FR (lines 4255-4304) Study blocks in src/AnalyticsLegends.jsx. All seven studies confirmed identical post-v72.70.2: Study #3 consultant-data sizes (FR 224 KB ✓, EN 35 KB ✓ with companion-language note), Study #4 headhunters consistent (814 organisations × 76 countries × 159 agencies × 30 slides), Study #6 migration-readiness in both EN+FR references the April 2026 BW/4HANA → 2030 mainstream-maintenance extension (no "2027" residue), samplePdfHref shared variable correctly points to headhunters-freelance-study-EN.pdf (474 KB). No FR-only correction was needed; v72.70.2's edits had already covered both languages because the dict was edited symmetrically · 9-touchpoint version bump: STATUS_VERSION 72.70.2 → 72.70.3, softwareVersion 72.70.2 → 72.70.3 (both root + /fr/), 7 cache-bust tokens v=72-70-2 → v=72-70-3, data-app-version 72.70.2 → 72.70.3 in static-shell eyebrow, package.json version bumped, public/api/about.json shipped_version 72.70.2 → 72.70.3 + generated_at 2026-04-26T11:00:00Z → 2026-04-26T12:30:00Z + shipped_version_note rewritten for the v72.70.3 hotfix bundle, agent.json shipped_in v72.70.2 → v72.70.3, openapi.yaml + mcp.json version stamps 72.70.2 → 72.70.3, humans.txt 3 stamps v72.70.2 → v72.70.3, robots.txt header v72.70.2 → v72.70.3, public/feed.xml prepends v72.70.3 + drops v72.64 so the rolling window stays at 10 · DEFERRED to v72.71+: 4-tier deep re-review (free / consultant / legends / firm) post-correction; deep SEO/GEO review (FR+EN); App Store feasibility strategic answer; route rename /#contracts → /#missions on React-router surface; wire crawl-firm-careers.py into refresh-opportunities.py orchestration; French typography skill .claude/skills/french-typography.md; profile-page review</title>
    <id>https://analyticslegends.ai/#status/v72.70.3</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T12:30:00Z</updated>
    <published>2026-04-26T12:30:00Z</published>
    <summary type="html">v72.70.3 closes three immediate operator remarks on top of v72.70.2: (1) AGENCIES TAB CLEANUP — strip the count chip + freshness caption from the 3 tabs (operator: "remove Agencies / 159 / Updated 2026-04-24 / Top 100 / 100 / Updated 2026-04-23 / Job platforms / 15"); TABS tuple simplified from 4-element back to 2-element [key, label] pairs. Page-level refresh button + hydratedAt still surface freshness — the per-tab counters were redundant. (2) CEDRIC-MARY USER-FACING SCRUB — operator clarified "does not" (named operator must NOT appear); four user-visible leaks redacted in v72.29 RELEASE_NOTES EN+FR ("i am signed in as cedric mary" → "[operator]"; "cedric.mary@analyticslegends.ai (and two variants)" → "the operator email allowlist (3 variants)"; "For you, Cedric/Cédric" → "For you, [first name]/[prénom]") + 1 code comment line 16373. Historical feed.xml entries untouched as paper-trail. (3) FR STUDY PARITY VERIFIED — re-read both EN+FR Study blocks; all 7 studies confirmed identical post-v72.70.2 (sizes ✓, headhunters consistent ✓, BW/4HANA 2030 reference ✓, samplePdfHref correct ✓). No FR-only correction needed. 9-touchpoint version bump.</summary>
  </entry>

  <entry>
    <title>v72.70.2 — iPhone-menu + audit-correction hotfix bundle on top of v72.70.1 answering directives 2026-04-26 verbatim "do a full test as user using a iphone and looking at the web site, he cannot see the menu, please check deeply and correct" + "do a deep full review of analyticslegends.ai loggued as a consultant, as a legends and as a firm pass and make all required corrections, there should many many" · 8 items shipped · IPHONE MENU INVISIBILITY (P0 user-blocking) — operator: "he cannot see the menu, please check deeply and correct". Root cause: iOS Safari evaluates @media (max-width: 1100px) against the initial 980px layout-viewport BEFORE the &lt;meta name="viewport" content="width=device-width"&gt; tag has fully applied; v72.29's prior "fix" had the burger as display:none baseline + display:flex on the media query, which iOS Safari raced and resolved as "desktop" on first paint. v72.70.2 inverts the cascade: .mobile-nav-toggle is display:flex baseline (mobile-first) and hidden via @media (min-width: 1101px) { display: none !important }; race-free first paint regardless of viewport-meta timing. ~25-line in-source comment block documents the iOS race so the regression doesn't sneak back · STUDIES FACT-CHECK (3 P0) — Study 6 (BW/4HANA modernisation) reworded EN+FR to drop the obsolete "2027" framing and reference April 2026 BW/4HANA → 2030 mainstream-maintenance extension; consultant-data PDF size hints corrected from "1.2 MB" placeholder to actual values measured on disk (FR: 224 KB, EN: 35 KB) so the download-button promise matches reality; samplePdfHref repointed from agencies-deepdive.pdf (4.6 KB stub) to headhunters-freelance-study.pdf (474 KB real preview) so the "preview a sample" CTA actually shows the headhunter study · AGENCIES UX (3 P0) — fixed dual H1 (HeadhuntersPage's local &lt;h1&gt; demoted to &lt;h2&gt; so HeadhuntersHeader becomes the canonical page H1; restores SEO single-H1 contract); TABS counts/dates now data-derived from useRadarData()'s master.meta.sanitized_at instead of the prior hardcoded "159" / "2026-04-24" stamps that drifted on every refresh; AgenciesView refresh button wired to refresh/refreshing/hydratedAt destructured from useRadarData() (was dead since the hook split — clicking did nothing). Localized TABS labels (lang === "FR" ? "Agences" : "Agencies") · BRAND-COLLISION FIX (P0-5) — src/pages/LegalPages.jsx PrivacyPage + TermsPage + SecurityPage carried "Operated by Legend" / "&lt;strong&gt;Legend&lt;/strong&gt;" / "(Legend)" — the founder pseudonym, distinct from the brand "Analytics Legends"; corrected to "Analytics Legends" across 6 spots (FR: "l'éditeur du site"); README.md "© 2026 Cedric Mary" → "© 2026 Analytics Legends" closing the operator-name privacy directive started in v72.69 · CNIL-COMPLIANCE (P0-4) — dropped the "Cookies" footer link from index.html + public/fr/index.html. CNIL December 2024 guidance: a "Cookies" link must lead to a real cookie inventory page; ours led to a deleted route, an explicit non-compliance signal that French regulators flag on routine sweeps. Replaced with a "Legal notice" link to /#legal that actually exists. Both index.html files carry an explanatory comment so the dead link doesn't sneak back · FR FAQ Cabinet → Firm (P1-5) — public/fr/index.html FAQ "Cabinet à 499,90 € par mois" / "Cabinet 499,90 € par mois" corrected to "Firm à 499,90 € par mois" / "Firm 499,90 € par mois"; the four pricing tiers (Free / Consultant / Legend / Firm) are English-anchored brand names — translating "Firm" to "Cabinet" in the FR FAQ contradicted every other FR surface that retained "Firm" · BREADCRUMBLIST Opportunities → Missions (P1-13) — index.html JSON-LD BreadcrumbList ListItem name "Opportunities" updated to "Missions" closing the v72.x marketing-surface terminology unification ("mission" is the operator term, "opportunity" was the legacy /#contracts route name); Google rich-results crawler now sees consistent terminology across hero copy, navigation, and structured data · TAGLINE REPHRASE — agencies StudyDisplayCard subtitle rewritten EN+FR as a single fluent sentence keyed off useRadarData()'s universeCount/universeCountries/indexedCount/indexedSubsetShown/platformsRemaining counts: "From 814 organisations across 76 countries, Analytics Legends curates 159: 141 SAP-specialist agencies listed below, plus 18 freelance &amp; job platforms on /#jobs. 30-slide study for the methodology." Replaces the previous paste-quoted enumeration that read like a spec sheet · 9-touchpoint version bump: STATUS_VERSION 72.70.1 → 72.70.2, softwareVersion 72.70.1 → 72.70.2 (both root + /fr/), 7 cache-bust tokens v=72-70-1 → v=72-70-2 (favicon + apple-touch + mask-icon + og:image + twitter:image + JSON-LD logo + JSON-LD contentUrl × 2 files), data-app-version 72.70.1 → 72.70.2 in static-shell eyebrow, package.json version bumped, public/api/about.json shipped_version 72.70.1 → 72.70.2 + generated_at 2026-04-26T09:30:00Z → 2026-04-26T11:00:00Z + shipped_version_note rewritten for the v72.70.2 hotfix bundle, agent.json shipped_in v72.70.1 → v72.70.2, openapi.yaml + mcp.json version stamps 72.70.1 → 72.70.2, public/api/headhunters-master.json ship_version v72.70 → v72.70.2, humans.txt stamps v72.70.1 → v72.70.2, robots.txt header v72.70.1 → v72.70.2, public/feed.xml prepends v72.70.2 + drops v72.63 so the rolling window stays at 10 · DEFERRED to v72.71+: wire crawl-firm-careers.py into refresh-opportunities.py pipeline orchestration; CI check that fails fast when current branch is not in github-pages deploy-allowed list; P1/P2 filter improvements (search bar, URL-state, filter counts, CSV export, reset button); French typography skill .claude/skills/french-typography.md; dict.js FR sweep (Opérateur → Éditeur, Curatées → Sélectionnées, tutoiement audit); CNIL cookie banner refus-symmetry; DPO contact in legal pages; mentions légales / CGU / RGPD in /fr/; FX/currency QA bundle implementation; profile-page review; App Store feasibility strategic answer; route rename /#contracts → /#missions on React-router surface; non-hallucinated P1s from deep audits (size_hint drift, llms-full.txt stub, mcp.json spec date, mode pills localization, star button 26→36, sticky thead, htmlFor)</title>
    <id>https://analyticslegends.ai/#status/v72.70.2</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T11:00:00Z</updated>
    <published>2026-04-26T11:00:00Z</published>
    <summary type="html">v72.70.2 ships the iPhone-menu + audit-correction hotfix bundle on top of v72.70.1: (1) IPHONE MENU INVISIBILITY (P0 user-blocking) — root cause iOS Safari evaluating @media against initial 980px viewport BEFORE width=device-width applied; fixed by inverting CSS default (mobile-first burger, hidden via min-width:1101px). (2) STUDIES FACT-CHECK — Study 6 reworded EN+FR (drop obsolete 2027 framing, reference Apr 2026 BW/4HANA → 2030 extension); PDF size hints corrected (FR 224 KB, EN 35 KB; was 1.2 MB placeholder); samplePdfHref repointed to real 474 KB headhunter study. (3) AGENCIES UX — dual H1 fixed (page h1 → h2), TABS counts/dates data-derived from useRadarData(), refresh button wired (was dead). (4) BRAND-COLLISION FIX — LegalPages "Legend" → "Analytics Legends" 6 spots; README copyright "Cedric Mary" → "Analytics Legends". (5) CNIL-COMPLIANCE — dropped broken "Cookies" footer link (CNIL Dec 2024 guidance) replaced with "Legal notice" → /#legal. (6) FR FAQ — "Cabinet" → "Firm" 2 spots (brand-name consistency). (7) BREADCRUMBLIST — "Opportunities" → "Missions". (8) TAGLINE REPHRASE — agencies subtitle rewritten as single fluent sentence keyed off useRadarData(). 9-touchpoint version bump.</summary>
  </entry>

  <entry>
    <title>v72.70.1 — Operator-feedback hotfix bundle on top of v72.70 answering directives 2026-04-26 verbatim "i still see only 159 and not 814 agencies" + "review all filters in agencies page" + "sort agencies by alphabetical order (do not display ids)" + "make sure news and opportunities agent crawl all those organisations to find news and opportunities" · 4 items shipped · GITHUB-PAGES DEPLOY UNBLOCK (root cause of the "still 159") — operator: "i still see only 159 and not 814 agencies". The HeadhuntersPage early-return fix had landed in code at v72.70 but was invisible on production because the GitHub Pages environment had `deployment-branch-policies` configured for the 18 stale per-release branches (v51 through v70) and did NOT include the new collapsed `live` branch. Every push from `live` since the v72.69 branch-collapse was succeeding at build time and silently failing at the deploy step ("Branch live is not allowed to deploy to github-pages due to environment protection rules"). Last successful deploy was v72.68.1 from `v70` branch on 2026-04-26T05:49Z — three releases of work were stuck in the GitHub Actions queue with no visible failure mode. Fixed via `gh api --method POST repos/cedricmary1973/Sapanalyticslegends/environments/github-pages/deployment-branch-policies -f name='live' -f type='branch'` then `gh workflow run deploy-pages.yml --ref live`; deploy succeeded in ~30s; verified analyticslegends.ai/api/headhunters-master.json returns HTTP 200 with 814 firms and analyticslegends.ai/fr/ returns HTTP 200 · AGENCIES PAGE FILTERS REVIEW — operator: "review all filters in agencies page". P0 issues fixed inline: every filter dropdown label rewritten with explicit lang === "FR" bilingual ternaries (was ad-hoc EN with FR-via-translate-attr drift), the "Places" filter renamed to "Engagement / Type de mission" (the EN "Places" label was confusing — the filter actually toggles freelance-vs-permanent placements), SPEC_LABELS taxonomy now bilingual {en, fr} via specLabel(key, lang) helper (sap-only/sap-desk/marketplace/freelance-platform-fr all have native FR labels: "Spécialiste SAP", "Équipe SAP", "Place de marché", "Plateforme FR"), agency-card spec chips now use specLabel(a.specialisation, lang) so the badge under each agency name reads native FR in /fr/, result count localised to "Affichées X sur Y · aperçu gratuit" (was English-only "Showing X of Y · free preview"). P1/P2 deferred to v72.71+: search bar in AgenciesView (currently filter-only — no free-text search across agency names/cities), URL-state for filters (refresh loses filter selection), filter counts in dropdown options (e.g., "France (47)"), CSV export of filtered set, MasterUniverseSection reset button to clear all filters at once · ALPHABETICAL SORT + DROP IDS — operator: "sort agencies by alphabetical order (do not display ids)". Both AgenciesView (jsx:~17707) and MasterUniverseSection (jsx:~6785) sort logic rewritten with locale-aware Intl.Collator(lang === "FR" ? "fr" : "en", { sensitivity: "base", ignorePunctuation: true }) instead of the prior specialisation-tier-first / region→country→name composite sorts; lang added to deps arrays so the order recomputes on locale switch. MasterUniverseSection table no longer surfaces id_unique: column header dropped, td cell dropped, colSpan adjusted from 6 → 5 on the empty-state row, id_unique removed from the search corpus (so a search for "HHM-FR-0042" no longer matches; only name/country/city/specialization searched). The collator's sensitivity:"base" + ignorePunctuation:true means "Élit Search" sorts next to "Elit Search" (diacritic-insensitive) and "M&amp;A Talent" sorts at "M" not at "&amp;" · OPPORTUNITIES 814-FIRM CRAWL PARITY — operator: "make sure news and opportunities agent crawl all those organisations". News-side was already wired in v72.70 (scripts/crawl-firm-news.py exists, sap-news-scout.md has C-023 directive with Tier-7 30% cap). Opportunities-side had the opportunity-curator C-022 directive but no script — v72.70.1 ships scripts/crawl-firm-careers.py (438 lines, stdlib-only) closing the gap: probes 17 multilingual career paths per firm (/careers, /jobs, /career, /opportunities, /join-us, /work-with-us, /openings, /vacancies, /recrutement, /carriere, /carrieres, /nos-offres, /offres-emploi, /karriere, /stellenangebote, /vacatures, /empleo, /lavora-con-noi) plus job-feed paths (/jobs.rss, /jobs.xml, /api/jobs, /api/v1/jobs, boards.greenhouse.io). Three parsing strategies in priority order: (1) JSON-LD JobPosting schema.org (richest signal — title + description + datePosted + hiringOrganization), (2) HTML anchor heuristic (link-text contains job-keywords + URL-pattern matches /job/ or /position/), (3) RSS/Atom feed parsing via xml.etree.ElementTree. SAP regex filter `/(SAP|Datasphere|SAC|BW/?4(HANA)?|BDC|BPC|HANA|Joule|S/?4HANA|Signavio|Ariba|SuccessFactors)/i` applied to title+description before stamping; non-SAP postings dropped. Politeness: 1 req/firm/s, single-host concurrency 1, robots.txt respected (per-host cache), ETag-aware. PER_FIRM_CAP=30 candidates max. Output public/api/firm-careers-candidates.json with `data_source: "firm_career_page"` stamp + firm_id/firm_tier/firm_name/firm_country/firm_city/firm_region/firm_website/careers_root/discovered_at provenance. Run modes: --dry-run (probe paths but don't write), --limit N (test mode), --since DAYS (default 60, cutoff for "fresh" postings), --out PATH. UA: "AnalyticsLegendsBot/72.70.1 (+https://analyticslegends.ai/about; career-page crawl per charter P-4)". Wiring into refresh-opportunities.py pipeline (so it runs automatically alongside Adzuna + agencies harvest) deferred to v72.71+ · 9-touchpoint version bump: STATUS_VERSION 72.70 → 72.70.1, softwareVersion 72.70 → 72.70.1, 7 cache-bust tokens v=72-70 → v=72-70-1 (favicon + apple-touch + mask-icon + og:image + twitter:image + JSON-LD logo + JSON-LD contentUrl), data-app-version 72.70 → 72.70.1 in static-shell eyebrow (both root + /fr/), package.json version 72.70 → 72.70.1, public/api/about.json shipped_version 72.70 → 72.70.1 + generated_at 2026-04-26T07:00:00Z → 2026-04-26T09:30:00Z + shipped_version_note rewritten for the v72.70.1 hotfix bundle, agent.json shipped_in v72.70 → v72.70.1, openapi.yaml + mcp.json version stamps 72.70 → 72.70.1, humans.txt stamps v72.70 → v72.70.1, robots.txt header v72.70 → v72.70.1, public/feed.xml prepends v72.70.1 + drops v72.62 so the rolling window stays at 10 · DEFERRED to v72.71+: wire crawl-firm-careers.py into refresh-opportunities.py pipeline orchestration; CI check that fails fast when current branch is not in github-pages deploy-allowed list (the silent-failure mode that hid this regression for 3 releases must never happen again); P1/P2 filter improvements (search bar in AgenciesView, URL-state for filters, filter counts in dropdowns, CSV export, MasterUniverseSection reset button); French typography skill .claude/skills/french-typography.md; dict.js FR sweep (Opérateur → Éditeur, Curatées → Sélectionnées, tutoiement audit); CNIL cookie banner refus-symmetry; DPO contact in legal pages; mentions légales / CGU / RGPD in /fr/; FX/currency QA bundle implementation; profile-page review; App Store feasibility strategic answer; route rename /#contracts → /#missions on React-router surface</title>
    <id>https://analyticslegends.ai/#status/v72.70.1</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T09:30:00Z</updated>
    <published>2026-04-26T09:30:00Z</published>
    <summary type="html">v72.70.1 ships an operator-feedback hotfix bundle on top of v72.70: (1) GITHUB-PAGES DEPLOY UNBLOCK — the root cause of the operator's "i still see only 159 and not 814 agencies" report. v72.70 had landed the HeadhuntersPage early-return fix in code, but the GitHub Pages env protection rules (`deployment-branch-policies`) listed 18 stale per-release branches v51-v70 and did NOT include the new `live` branch. Three releases of work (v72.69, v72.70) had been silently failing at the deploy step since the v72.69 branch-collapse, with build success masking the deploy failure. Fixed via `gh api` adding `live` to deployment-branch-policies; `gh workflow run deploy-pages.yml --ref live` succeeded in 30s; production now serves headhunters-master.json with 814 firms. (2) AGENCIES FILTERS REVIEW — every dropdown label rewritten with explicit lang ternaries (was ad-hoc), "Places" renamed to "Engagement / Type de mission", SPEC_LABELS taxonomy bilingualised {en, fr} via specLabel() helper, agency-card spec chips localised, result count localised. P1/P2 deferred (search bar, URL-state, filter counts, CSV, reset button). (3) ALPHABETICAL SORT + DROP IDS — both AgenciesView and MasterUniverseSection now sort with Intl.Collator(lang, { sensitivity:'base', ignorePunctuation:true }); ID column dropped from MasterUniverseSection table + id_unique removed from search corpus. (4) OPPORTUNITIES 814-FIRM CRAWL PARITY — new scripts/crawl-firm-careers.py (438 lines, stdlib-only) parallels crawl-firm-news.py: 17 multilingual career paths per firm, three parsers in priority (JSON-LD JobPosting → HTML anchor heuristic → RSS/Atom), SAP regex filter, robots.txt-respecting fetcher, 1 req/firm/s, ETag cache, output public/api/firm-careers-candidates.json with firm_id/firm_tier provenance. Pipeline-wiring into refresh-opportunities.py deferred to v72.71+. 9-touchpoint version bump.</summary>
  </entry>

  <entry>
    <title>v72.70 — Path-based bilingual SSR + 814-firm Master Universe regression fix + French typography pass + treasury/FX QA bundle queued · answers operator directives 2026-04-26 "je n'ai pas pu accéder à la version française du site … /fr, /fr/, ?lang=fr — toutes les variantes raisonnables. Aucune ne m'est servie. Si la version française n'a pas d'URL dédiée et indexable séparément, Google ne pourra pas la référencer pour les requêtes francophones (FR, BE, CH, LU, MA, TN). C'est probablement le problème stratégique le plus coûteux du site." + "why i still do not see the list of the 814 organizations in teh agencies page" + 5-point French typography test (NBSP avant : ; ! ?, guillemets « » avec NBSP, apostrophe courbe ', séparateur 1 250 avec NBSP, sentence-case en titre) + parity checklist (architecture/SEO + typo + lexique + conformité légale FR + cohérence stratégique) + FX/currency QA bundle · BILINGUAL SSR — root index.html + new public/fr/index.html ship as distinct pre-rendered shells, each with its own &lt;html lang&gt;, canonical URL, JSON-LD @graph (inLanguage en/fr), meta/og/twitter tags, and visible static-shell hero rendered server-side; hreflang block re-introduced on root + sitemap.xml gains xmlns:xhtml namespace + xhtml:link cross-references on both URL entries (en/fr/x-default) so analyticslegends.ai/ and analyticslegends.ai/fr/ are now distinct indexable documents Google can serve to FR/BE/CH/LU/MA/TN search queries (was same-URL client-side switch through v72.56–v72.69 which Google could not index separately) · BOOT-LANGUAGE DETECTION — src/AnalyticsLegends.jsx useState replaced with multi-source detector that respects whichever shell hydrated: window.__AL_BOOT_LANG__ injected by the FR shell's inline script wins; URL pathname.startsWith("/fr") wins next; localStorage.LANG ("FR"/"EN") wins next; user-prefs effective.lang fallback last. setLang() now persists to localStorage so the choice survives reloads + hard navigations across both shells · FRENCH TYPOGRAPHY in /fr/ shell — every visible string applies the 5-point sweep: NBSP U+00A0 inserted before : ; ! ? throughout (e.g., "1 250 missions", "Combien ça coûte ?"), guillemets «  » U+00AB/U+00BB with NBSP for any French quote (no straight " ' double-marks), apostrophe courbe U+2019 ("L'éditeur", "L'agent IA") not the straight ' U+0027, French thousand separator NBSP between digits ("1 250", "159") not the English comma or German period, sentence-case for headings (no Title Case anglais — "Note de l'éditeur" not "Note De L'éditeur"); JSON-LD FAQ entries written natively in French (not translated EN strings) with localised pricing "29,90 €" + question phrasing "Combien ça coûte ?" so the rich-result surface is locale-correct · 814-FIRM REGRESSION FIX — operator: "why i still do not see the list of the 814 organizations in teh agencies page". Root cause: HeadhuntersPage's loading-guard early-return at lines 6581-6605 short-circuited BEFORE &lt;MasterUniverseSection&gt; rendered, so when useRadarData() (curated 141-agency feed) was loading=true OR errored, the 814-firm research universe stayed hidden — even though useHeadhuntersMaster() is fetched independently and may already be hydrated from localStorage on first paint. Fix: render &lt;MasterUniverseSection master={master} lang={lang} /&gt; alongside the spinner AND alongside the error message in both early-return branches, so the universe is always visible regardless of the curated-directory feed state · TREASURY/FX QA BUNDLE QUEUED for v72.71+ (operator's 32-country edge-case audit) — rate freshness/source/fallback documentation, locale formatting (FR "1 250 €" vs EN "€1,250" vs CH "CHF 1'250.00" vs DE "1.250,00 €"), 32-country edge cases (TRY volatility, CHF hourly-vs-daily, MAD/TND, NOK/SEK/DKK ISO), cross-currency math (sort/filter/aggregate), HT-vs-TTC labelling on mission cards, switcher UX with localStorage persistence, 3 automated tests (round-trip, locale snapshot, API-down mock) · 9-touchpoint version bump: STATUS_VERSION 72.69 → 72.70, softwareVersion 72.69 → 72.70, 7 cache-bust tokens v=72-69 → v=72-70, favicon ?v=72-69 → ?v=72-70, data-app-version 72.69 → 72.70 in static-shell eyebrow, package.json name+version 72-69→72-70, public/api/about.json shipped_version 72.69 → 72.70 + generated_at 2026-04-26T05:30:00Z → 2026-04-26T07:00:00Z + shipped_version_note rewritten for the v72.70 deliverables, agent.json shipped_in v72.69 → v72.70, openapi.yaml + mcp.json version stamps 72.69 → 72.70, humans.txt stamp v72.69 → v72.70 + Language line rewritten to "English (analyticslegends.ai/), Français (analyticslegends.ai/fr/) · v72.70 ships path-based bilingual SSR — both URLs are distinct indexable documents with hreflang cross-references", robots.txt header v72.69 → v72.70, public/feed.xml prepends v72.70 + drops v72.60 so the rolling window stays at 10 · DEFERRED to v72.71+: French typography skill file (.claude/skills/french-typography.md codifying the 5-point rule) + lint helper to flag straight quotes/apostrophes/spaces in FR strings, dict.js FR sweep (lexicon corrections "Opérateur" → "Éditeur", "Curatées" → "Sélectionnées", tutoiement-vs-vouvoiement consistency audit), CNIL cookie banner "refus aussi visible que l'acceptation", DPO contact identification in legal pages, mentions légales / CGU / RGPD pages in /fr/, FX/currency QA bundle implementation (HT/TTC labels, switcher persistence, automated tests), profile-page review, App Store feasibility strategic answer, route rename /#contracts → /#missions on React-router surface (terminology unified on marketing surface in v72.69)</title>
    <id>https://analyticslegends.ai/#status/v72.70</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T07:00:00Z</updated>
    <published>2026-04-26T07:00:00Z</published>
    <summary type="html">v72.70 ships path-based bilingual SSR (root EN + new /fr/ pre-rendered shell with native FR JSON-LD/meta/copy + restored hreflang + sitemap.xml xhtml:link cross-references — analyticslegends.ai/ and analyticslegends.ai/fr/ are now distinct indexable documents Google can serve to FR/BE/CH/LU/MA/TN search queries), boot-language detection in React (window.__AL_BOOT_LANG__ + path-prefix /fr + localStorage.LANG + user-prefs fallback, all four sources resolved on first paint with setLang persisting to localStorage), French typography sweep applied to /fr/ shell (NBSP avant : ; ! ?, guillemets « », apostrophe courbe ', séparateur 1 250 avec NBSP, sentence-case en titres), 814-firm regression fix on /#headhunters (MasterUniverseSection now renders alongside the loading spinner AND error message — was hidden behind useRadarData's early-return guard even though useHeadhuntersMaster is fetched independently and hydrates from localStorage). Treasury/FX QA bundle queued for v72.71+ (rate source/freshness, locale formatting EN/FR/CH/DE, 32-country edge cases, HT-vs-TTC labels, switcher UX, automated tests). Deferred: French typography skill + lint helper, dict.js FR lexicon sweep, CNIL cookie refus-symmetry, DPO contact, mentions légales / CGU / RGPD in /fr/, profile-page review, App Store feasibility, /#contracts → /#missions route rename.</summary>
  </entry>

  <entry>
    <title>v72.69 — Operator-name privacy scrub + UX deep-review fix bundle answering operator directives 2026-04-26 "The operator should not be named publicly (Cedric Mary)" + "do a deep quality review of the whole web site and suggest many improvments" + line-by-line copy critique (3.2) + legal/regulatory surface critique (3.5) + voice critique (3.6) + footer critique (3.7) + senior-architect 2027 BW/4HANA fact-check + dual-H1 noscript SEO consistency · 12+ items shipped · PRIVACY-NAME SCRUB across every public surface — index.html operator-pledge ("editor pledge" → "Note from the editor", LinkedIn URL dropped from sameAs/contact), src/i18n/dict.js EN+FR signature ("Cedric Mary, operator" → "L'éditeur, Analytics Legends"), public/api/about.json (operator block name+linkedin keys deleted, role-only block remains, operator_persona_quote rewritten to working-consultant voice), public/.well-known/agent.json (operator block name deleted, system_prompt opens "I am the editor of Analytics Legends" not "I am Cedric Mary", contact.issues mailto: instead of github URL, spec at analyticslegends.ai/docs/AGENT-MANIFEST.md not github), public/.well-known/openapi.yaml (contact.name "Cedric Mary" → "Analytics Legends — Editor"), public/humans.txt (TEAM block "Founder &amp; Editor: Cedric Mary" → "Editor: Analytics Legends" single-editor-masthead framing), public/llms.txt (editorial-integrity "Cedric Mary — Founder…" → "Analytics Legends is built and edited by one working SAP analytics consultant…"), src/lib/consultant-matches.js (named-email mappings cedric.mary@/cedric@/cedricmary@ replaced with role-based aliases founder@/editor@/operator@) · 1.1 ENGINEERING LEAKAGE — eyebrow "SAP Analytics · v72.68.1" → "SAP Analytics · refreshed hourly" (version moves to data-app-version attribute for power-user discoverability), "Hydrating the live application…" developer-status replaced with content-complete invitation "The interactive radar loads in a moment — or browse the JSON catalogue at /api/contracts.json", JS-required noscript fallback rewritten with one paragraph of real product content (was "JavaScript is required to view this site") · 1.2 AI-vs-HUMAN BRIDGING — explicit single-line reconciliation added below H1 "AI works for the user. A human stands behind the data." closes the bridging gap between the agent-positioned H1 and the human-curated pledge below · 1.3 TERMINOLOGY UNIFICATION — picked one word ("mission") for the unit-of-work and applied across the marketing surface (hero subtitle, stat 1, primary CTA "See live missions →", H1 still references analytics; route /#contracts deferred to v72.70+ rename) · 1.4 STAT NUMBER SOURCING — every stat now carries a per-stat attribution line (timestamp + source URL + scope) so a skeptical reader can verify in one click; stat 1 cites contracts.meta.json + scope criterion, stat 2 cites agencies.json + SAP-analytics-desk filter, stat 3 cites academy.json + the SAP-published-roadmap mapping · 3.2 LINE-BY-LINE COPY — H1 committed to lead noun "The AI agent for SAP Analytics experts." (dropped "platform and" + the italicised AI-agent fragment that was a writing tic — operator: "either commit or restructure"), hero subtitle reworded "A live opportunity radar refreshed hourly across 32 countries — bilingual EN+FR" → "Datasphere, BDC, SAC, Joule, BW/4HANA. Open missions across 32 countries, refreshed hourly. English and French.", stat 1 "live SAP analytics missions" → "open SAP analytics missions" (drop redundant "live"), stat 2 "159 curated agencies with day-rate benchmarks" → "159 vetted agencies, with median day rates by stack" ("curated" lost meaning), stat 3 "300 academy modules on the 2027 BW/4HANA stack" → "300 academy modules aligned to SAP's published roadmap" (the 2027 framing was the riskiest claim on the page; reworded to a milestone-list-with-citation format) · 2027 BW/4HANA SENIOR-ARCHITECT FACT-CHECK — operator: "Evaluate whether '2027 BW/4HANA' survives a fact-check from a senior SAP architect. If not, reword". Our own news.json line 78 already records SAP extending BW/4HANA mainstream maintenance from 2027 to 2030 in response to customer-feedback on migration readiness, so the 2027-BW/4HANA framing in our marketing copy contradicted our own news data (C-010 internal-contradiction defect class). v72.69 reconciles: about.json tagline "shipped through the 2027 BW/4HANA cutover" → "shipped through the SAP analytics modernisation window (S/4HANA mainstream maintenance ends 2027; BW/4HANA mainstream maintenance extended to 2030)", agent.json description + system_prompt + topics_i_can_help_with all reworded to reference the modern stack + the modernisation window with the actual SAP-published milestones (BDC GA 2024, Datasphere live, S/4HANA cutover 2027, BW/4HANA extended to 2030) · 3.5 LEGAL/REGULATORY SURFACE — operator: "no link to a privacy policy, no link to terms, no cookie banner mention, no impressum, no GDPR-required data-controller identification, no SAR surface". Static-shell footer added with Privacy/Terms/Cookies/Release-notes/humans.txt/llms.txt/agent-manifest links + a one-line GDPR data-controller identification ("GDPR data controller: Analytics Legends, EMEA. Subject access &amp; takedown: contact@analyticslegends.ai") so the legal surface lands pre-hydration for non-JS clients · 3.6 VOICE — operator: "Cut every word that sounds corporate ('operator pledge', 'curated agencies', 'academy modules') and rewrite in the voice of a working SAP consultant who built this because the existing tools annoyed him". Pledge section header "The operator pledge" → "Note from the editor", body rewritten "Built for the legends of SAP analytics — by a single editor" → "Built by a working SAP analytics consultant — for the legends doing the work. Every mission, every agency, every concept card crosses my desk before it lands here." Kept "One editor. One stack. Zero noise." — the line a competitor cannot copy without lying · 3.7 FOOTER — operator: "A real footer has status, blog, changelog, careers, legal (privacy, terms, cookies, DPA), language switch, RSS, social proof. The version number is the only one currently present, and it shouldn't be present". Static-shell footer ships with the legal + transparency links above; visible version stamp dropped; status/blog/language-switch/RSS-radar/social-proof deferred to v72.70+ (the static-shell footer must stay one-screen-tall to match the skeleton's pre-hydration purpose) · DUAL-H1 NOSCRIPT SEO FIX — operator: "The H1 'Analytics Legends' appears in the JS-required fallback as well as in the main content area (where the H1 is 'The platform and AI agent for SAP Analytics experts.'). This means screen readers may encounter two H1s, depending on hydration order. Only one should ever be promoted to H1". Although noscript and the static shell never coexist in the same DOM (noscript only renders when JS is disabled; createRoot replaces #root the moment React mounts), the brand-vs-headline split between the two was an SEO inconsistency: a Googlebot crawl with JS enabled saw the headline H1, a Lynx/curl/no-JS crawl saw a different one. v72.69 unifies to a single H1 message ("The AI agent for SAP Analytics experts.") in both code paths so the page-title heading hierarchy reads identically regardless of execution path · HONEYPOT ACCESSIBILITY HARDENING — operator deep-review point #2 (2026-04-26): "the link 'scraper trap' was visible in the DOM. Even with aria-hidden + tabindex=-1 + off-screen CSS, the visible text inside the anchor (a) is discoverable in the DOM and modern scrapers pattern-match the string and avoid the link entirely defeating the purpose, (b) is an engineering tell about how the page is built, (c) any leak past aria-hidden (SR bug, copy-paste of a static render) would expose the trap label to a real user". v72.69 drops the visible "scraper trap" text — the anchor stays as bait (href/rel) but text content is empty; aria-hidden + tabindex=-1 + class="honeypot-trap" off-screen CSS + path-level robots.txt Disallow are now the layered defence. UA-gated identified-bot wrapper deferred to v72.70+ (requires server-side UA detection unavailable on static GitHub Pages) · 9-touchpoint version bump: STATUS_VERSION 72.68.1 → 72.69, softwareVersion 72.68.1 → 72.69, 7 cache-bust tokens v=72-68-1 → v=72-69, favicon ?v=72-68-1 → ?v=72-69, static-shell eyebrow no longer carries version literal (data-app-version attribute remains for power users), package.json bumped, public/api/about.json shipped_version 72.68.1 → 72.69 + generated_at 2026-04-26T04:30:00Z → 2026-04-26T05:30:00Z, agent.json shipped_in v72.68.1 → v72.69, openapi.yaml + mcp.json version stamps 72.68.1 → 72.69, humans.txt stamp v72.68.1 → v72.69, robots.txt header v72.68.1 → v72.69, public/feed.xml prepends v72.69 + drops v72.59 so the rolling window stays at 10 · DEFERRED to v72.70+: route rename /#contracts → /#missions (terminology unification on the React-router surface; v72.69 unifies on the marketing surface only), GitHub URL scrub from public manifests (cedricmary1973 prefix lingers in legacy comments), AnalyticsLegends.jsx RELEASE_NOTES historical-text scrub (would corrupt audit-log paper-trail), README.md copyright (© 2026 Cedric Mary → © 2026 Analytics Legends), public/feed.xml legacy author tags (mostly historical entries), sticky Pricing CTA at hero scroll, head &lt;link rel="sitemap"&gt;, Edge Function honeypot-log + UA-gated honeypot wrapper (server-side UA detection unavailable on static GitHub Pages), real mission card + agency card visible without signup, customer/partner quote with name + agency, #contracts and #auth real routes with their own SSR content, permanent discovery-agent architecture (LLM-assisted triage queue feeding human-review-required publish step — incompatible with auto-write to live DB because the editor pledge is "every mission crosses my desk")</title>
    <id>https://analyticslegends.ai/#status/v72.69</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T05:30:00Z</updated>
    <published>2026-04-26T05:30:00Z</published>
    <summary type="html">v72.69 ships the operator-name privacy scrub (Cedric Mary deleted from every public surface — index.html, dict.js EN+FR, about.json, agent.json, openapi.yaml, humans.txt, llms.txt, consultant-matches.js role-aliased) PLUS a 12-item UX deep-review fix bundle answering the operator's 2026-04-26 directives: 1.1 engineering leakage (eyebrow product-cadence not version, Hydrating-message replaced, noscript fallback rewritten with real content), 1.2 AI-vs-human bridging line, 1.3 terminology unified to "mission" on marketing surface, 1.4 every stat carries timestamp + source + scope, 3.2 H1 committed to lead noun "The AI agent for SAP Analytics experts" + 3-stat reword, 3.5 legal links (Privacy/Terms/Cookies + GDPR data-controller line) added to static-shell footer, 3.6 voice rewritten in working-consultant tone (cut "operator pledge" + "curated agencies"), 3.7 transparency-links footer (drops visible version), dual-H1 noscript SEO fix (single H1 in both code paths), honeypot accessibility hardening (visible "scraper trap" text dropped), 2027 BW/4HANA fact-check (BW/4HANA extended to 2030 per our own news.json — copy reconciled across about.json + agent.json + index.html stat 3 supplement). Deferred to v72.70+: route rename /#contracts → /#missions, sticky Pricing CTA, real mission/agency cards visible without signup, customer/partner quote with name+agency, SSR for #contracts and #auth, permanent discovery-agent architecture (LLM triage queue → human review → publish; incompatible with auto-write because editor pledge is "every mission crosses my desk").</summary>
  </entry>

  <entry>
    <title>v72.68.1 — AI-policy hotfix answering operator directives 2026-04-26 "first make analyticslegends..ai accessible to claude" + "loop on this till you are sure claude can access analyticslegends..ai" · v72.68 fixed Layer-3 (HTTP X-Robots-Tag) but a friendly-Claude WebFetch test failed minutes after deploy with the same retrieval wall. Diagnosis: Layer-2 was the survivor. index.html line 31 emitted `&lt;meta name="robots" content="index, follow, noai, noimageai, noml, max-snippet:-1, max-image-preview:large"&gt;` site-wide, contradicting robots.txt section 0 per-UA Allow blocks for ClaudeBot/Claude-Web/Claude-SearchBot/Claude-User/anthropic-ai. Well-behaved fetchers honour the stricter signal; Claude's WebFetch refuses retrieval when meta-robots says noai even if robots.txt says Allow. v72.68.1 drops `noai, noimageai, noml` from the static &lt;meta name="robots"&gt; in index.html AND from the runtime mutation in src/hooks/useRouter.js (which re-asserts the meta on every hash route change — without the runtime fix, the wall would re-form mid-session). Training prohibition is unchanged: enforced at the policy layer (ToS + /llms.txt + per-UA /robots.txt blocks for every non-Anthropic AI crawler) plus X-Robots-Tag: notrain on every HTTP response. Copy refresh sweep: src/pages/LegalPages.jsx §6 ToS rewritten to spell out the v72.49 Anthropic carve-out explicitly (was a blanket prohibition that contradicted the carve-out); src/AnalyticsLegends.jsx Anti-AI page updated to describe X-Robots-Tag: notrain + /honeypot/* noai narrative instead of the retired site-wide noai/noimageai claim; public/llms.txt + public/llms-full.txt enforcement-signals section refactored to drop the meta-robots reference and elevate the X-Robots-Tag: notrain HTTP header as the canonical universal training-prohibition signal; public/_headers Layer-2 description in the comment block updated to match · 9-touchpoint version bump: STATUS_VERSION 72.68 → 72.68.1, softwareVersion 72.68 → 72.68.1, 7 cache-bust tokens v=72-68 → v=72-68-1, favicon + og:image + twitter:image + JSON-LD logo all bumped, static-shell eyebrow v72.68 → v72.68.1, package.json name + version bumped, public/api/about.json shipped_version 72.68 → 72.68.1 + generated_at 2026-04-26T03:30:00Z → 2026-04-26T04:30:00Z, agent.json shipped_in v72.68 → v72.68.1, openapi.yaml + mcp.json version 72.68.0 → 72.68.1, humans.txt v72.68 → v72.68.1, robots.txt header v72.68 → v72.68.1 · DEFERRED to v72.69 (operator: "then continue V72.69"): MOBILE BUNDLE (tap targets ≥44pt on header pills + lang toggle, sticky Pricing CTA on ≤1100px, table overflow-x wrappers), SECURITY BUNDLE (H1 user_metadata→app_metadata migration, C2 _headers theatre cleanup, C3 honeypot Edge Function logger), UX BUNDLE (1,250+ sweep, agency 159↔127, glossary 60↔126, dead routes /#radar /#faq /#breadcrumbs /#auth, mission-agent admin-gate vs Legend-tier, single CTA color across 4 gates), v72.70+ opportunity-harvester rebuild against the 382-source landscape</title>
    <id>https://analyticslegends.ai/#status/v72.68.1</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T04:30:00Z</updated>
    <published>2026-04-26T04:30:00Z</published>
    <summary type="html">v72.68.1 ships a 1-line surgical hotfix to unblock Claude.ai's WebFetch from analyticslegends.ai. v72.68 fixed Layer-3 (HTTP X-Robots-Tag) but a friendly-Claude test confirmed Layer-2 (HTML meta-robots) still emitted `noai, noimageai, noml` site-wide, contradicting the v72.49 Anthropic carve-out in /robots.txt. v72.68.1 drops the universal opt-out vocabulary from &lt;meta name="robots"&gt; in both index.html (static) and src/hooks/useRouter.js (runtime mutation on every route change). Training prohibition stays at the policy layer (ToS + /llms.txt + per-UA /robots.txt blocks) + X-Robots-Tag: notrain HTTP header. Copy refresh sweep aligns ToS §6, the Anti-AI page, /llms.txt and /llms-full.txt with the new layer model. 9-touchpoint version bump.</summary>
  </entry>

  <entry>
    <title>v72.68 — Apple-grade discipline + security ship-blocker fix bundle answering operator directives 2026-04-26 "i want this web site to be as simple and perfect and perfectly design as apple products" + "please do a deep secuirty review of the web site, do some tests with friendly hostile agents" + "i see this Add your consultant profile to see your rank but my profile has been added" + "make sure that each time i am making you remarcks you enacing some skills to make sure you can check this on your own next times and correctg it on your own" + "make sure claude can access analyticslegends.ai" + "it is complicated to keep it simple, please make sure you follow this principle for this web site" · 6 items shipped · SECURITY SHIP-BLOCKER C1 — public/api/consultant-matches.json + opportunity-matches.json shipped to GitHub Pages (world-readable) with the `name` field on every row (60 consultants + 600 opportunity-keyed top-consultant rows) keyed by stable consultantId; sourced from src/data/consultants-real.json which carries first+last + linkedinUrl. The matches files don't ship linkedinUrl directly, but the (consultantId → real-name) mapping is sufficient to re-identify against the public LinkedIn graph — a GDPR-grade exposure on a static CDN with no auth gate. Friendly hostile-agent audit (12 probes) confirmed `curl -A "Mozilla/5.0" https://analyticslegends.ai/api/consultant-matches.json` returned full JSON with named consultants in one HTTP request, no auth. v72.68 ships scripts/redact-matches-pii.mjs which nulls the `name` field across both JSON files (660 redactions), drops opportunity-matches.csv entirely, and stamps a `privacy: { pii_redacted: true }` block. The frontend BestForYouPanel already had a `payload.name ? "For you, X" : "For you"` fallback (jsx:15583), so the redaction is non-breaking. Roadmap v72.69+: move match generation to a Supabase Edge Function / RPC behind has_firm_access() so the full record is delivered only to authenticated firm-tier users · RANK-GATE FIX (C-007 "state must reflect reality") — operator report verbatim "i see this Add your consultant profile to see your rank but my profile has been added"; root cause: CompetitionIndicator (jsx:16703) and the rank gates read user.user_metadata.consultant_id directly, but that field is set ONLY by the operator-allowlist path; the actual profile-add flow writes to Supabase pipeline_consultants keyed by user_id — two write-paths, one read-path → false-negative gate. New hook src/hooks/useMyConsultantProfile.js: session-cached read of pipeline_consultants keyed by user.id, module-scope Map cache so N components reading it cause exactly one round-trip. Wired into CompetitionIndicator (resolves consultantId via pipeline-profile fallback when user_metadata is empty), AuthPages profile-save handler, and the mission-brief save path — each successful upsert now busts the cache so the gate flips immediately without page reload · AI POLICY HARMONIZATION — operator: "make sure claude can access analyticslegends.ai". The v72.49 robots.txt carve-out had Allow'd Anthropic UAs (ClaudeBot/Claude-Web/Claude-SearchBot/Claude-User/anthropic-ai) for the seven public manifests, but Layer-3 (HTTP X-Robots-Tag header in public/_headers) was sending `noai` globally, contradicting Layer-1 (robots.txt) at the network level. v72.68 drops `noai` from the global rule, keeps `notrain` (training universally banned). public/humans.txt /POLICY block updated to spell out the carve-out: "Anthropic's Claude is permitted to retrieve content for real-time AI-answer responses with attribution"; From: "Worldwide" → "EMEA (32 countries indexed)" aligning with about.json + agent.json · APPLE-GRADE RESTRAINT — operator: "i want this web site to be as simple and perfect and perfectly design as apple products" + "it is complicated to keep it simple". New docs/DESIGN-CONTRACT.md captures 10 non-negotiables (one job per screen; default = polished; one CTA color; copy is human; no dead links; mobile = desktop; motion is purposeful; performance is a feature; accessibility is the floor) + locks the visual system (type 12/14/16/20/28/40/56/80; spacing 4/8/12/16/24/32/48/64/96; radius 0/6/12/999) + a single-source-of-truth table. The _headers fix originally went verbose (8 redundant per-path blocks) — operator pushback "it is complicated to keep it simple" triggered a revert to the minimal 2-rule version (global + /api/* both with just `notrain`); the comment explicitly notes why noai at the header layer was theatre against non-compliant crawlers · OPERATOR-FEEDBACK-CHECKLIST SKILL — operator: "each time i am making you remarcks you enacing some skills to make sure you can check this on your own next times". New .claude/skills/operator-feedback-checklist.md with 12 self-enforcing entries C-001…C-012 covering the patterns that have repeated across the v72.x ship loop · SOURCE LANDSCAPE DOC — operator: "12 sources is very poor, i hope you will find hundreds". New docs/OPPORTUNITY-SOURCE-LANDSCAPE.md catalogues 382 SAP-analytics opportunity sources across 12 tiers; identifies Tier 7 (159 indexed agencies' careers pages already shipped in agencies.json) as the highest-yield first wave; total estimated post-dedupe yield 600-2,500 real opportunities/refresh · 9-touchpoint version bump: STATUS_VERSION 72.67 → 72.68, softwareVersion 72.67 → 72.68, 7 cache-bust tokens v=72-67 → v=72-68, favicon ?v=72-67 → ?v=72-68, static-shell eyebrow v72.67 → v72.68, package.json bumped, public/api/about.json shipped_version 72.67 → 72.68 + generated_at 2026-04-26T02:30:00Z → 2026-04-26T03:30:00Z, agent.json shipped_in v72.67 → v72.68, openapi.yaml + mcp.json version stamps 72.67.0 → 72.68.0, humans.txt stamp v72.67 → v72.68, public/feed.xml prepends v72.68 + drops v72.58 + bumps top-level updated/generator/curated-at to v72.68 · DEFERRED to v72.69+: SECURITY BUNDLE (C2 _headers is dead code on GitHub Pages without Fastly actually in front; H1 move subscription_tier+role from auth.user_metadata to auth.app_metadata since user_metadata is client-writable from the SPA — needs Supabase migration + Stripe webhook update; C3 honeypot has zero detection — wire Supabase Edge Function logger), UX BUNDLE (1,250+ sweep useRouter.js, agency 159↔127, glossary 60↔126, EMEA sweep dict.js, dead routes /#radar /#faq /#breadcrumbs /#auth, mission-agent admin-only gate vs Legend tier, free-radar 30-row silent cap, single CTA color), MOBILE BUNDLE (Playwright viewports 375/414/768, sticky CTA, tap targets ≥44pt, no overflow audits)</title>
    <id>https://analyticslegends.ai/#status/v72.68</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T03:30:00Z</updated>
    <published>2026-04-26T03:30:00Z</published>
    <summary type="html">v72.68 ships the security audit's CRITICAL C1 fix + the operator's rank-gate report + AI-policy harmonization + the Apple-grade discipline bundle. Six items shipped: (1) consultant-matches.json + opportunity-matches.json PII redacted (660 `name` fields nulled across 60 consultants + 600 opportunity-keyed top-consultant rows; opportunity-matches.csv dropped — frontend's "For you, X" fallback handles null gracefully); (2) rank-gate bug fixed (new useMyConsultantProfile hook reads canonical pipeline_consultants source instead of stale user_metadata; gate flips immediately after profile save); (3) AI policy harmonized (drop `noai` from global X-Robots-Tag; humans.txt spells out v72.49 Anthropic carve-out; From: Worldwide → EMEA); (4) docs/DESIGN-CONTRACT.md locks the Apple-grade visual system + 10 non-negotiables; (5) .claude/skills/operator-feedback-checklist.md C-001…C-012 self-enforcing patterns; (6) docs/OPPORTUNITY-SOURCE-LANDSCAPE.md 382 sources across 12 tiers. Deferred to v72.69+: H1 user_metadata→app_metadata migration (paywall bypass — Supabase migration + Stripe webhook + AuthContext refactor), C2 _headers theatre + Fastly verification, C3 honeypot logging, mobile viewport coverage (Playwright 375/414/768), 1,250+ + EMEA + count drift sweeps, dead routes, single CTA color, mission-agent admin gate.</summary>
  </entry>

  <entry>
    <title>v72.67 — Eleventh-pass deep quality review corrections continuing the chained operator directive 2026-04-25 verbatim "do a deep quality review of web site, still many issues to correct" · 7 items shipped · DICT.JS FOOTER.TAGLINE "1,250+" SURVIVOR EN+FR — src/i18n/dict.js line 366 (EN) "Day-rate benchmarks, 1,250+ live missions..." + line 1194 (FR) "Benchmarks TJM, 1 250+ missions en direct..." both still carried the "+" suffix that v72.63 swept from manifest.webmanifest description and Opportunity Radar shortcut; the visible footer renders on every page in both locales — same visible-on-every-page drift class as the v72.65 dict.js home.title.suffix Databricks→Joule fix; v72.67 drops the "+" so the footer aligns with about.json + agent.json + JSON-LD + FAQ + manifest + static-shell counter + meta description bare 1,250 · ROBOTS.TXT HEADER 17-RELEASE STAMP — public/robots.txt line 2 "Version: v72.49.1 · Updated: 2026-04-25" was 17 releases stale even though robots.txt is the most-fetched diagnostic file by AI compliance teams (and was directly edited in v72.63 + v72.64 + v72.65 for the Anthropic carve-out + agent listing); same drift class v72.66 closed for agent.json last_updated/shipped_in 17-release lag; v72.67 bumps to "Version: v72.67 · Updated: 2026-04-26" so the canonical AI-compliance probe matches the rest of the freshness contract · AI-PLUGIN.JSON + MCP.JSON PRE-REBRAND "sap_" PREFIX — public/.well-known/ai-plugin.json line 4 name_for_model="sap_analytics_legends" + public/.well-known/mcp.json line 3 name="sap-analytics-legends" both carried the dead pre-v72.0-rebrand "sap-/sap_" prefix that the v72.0 rebrand walked away from; same defect class as the v72.66 PDF Creator metadata fix where consultant-data-EN.pdf leaked "sapanalyticslegends.com" Creator field; AI agents and MCP clients reading either descriptor saw the pre-rebrand identifier; v72.67 renames to "analytics_legends" (ai-plugin.json) and "analytics-legends" (mcp.json) · JSON-LD DATEMODIFIED DATE-ONLY vs ISO-8601 IN FEED — index.html lines 200 + 223 stamped "dateModified": "2026-04-26" (date-only) but feed.xml top-level updated + about.json generated_at use full ISO-8601 with timestamp; Schema.org allows both forms but Google rich-results normalises against the most precise stamp — having date-only JSON-LD next to ISO-8601 in the same release looks like the JSON-LD was hand-edited while everything else was script-stamped; v72.67 bumps both to "2026-04-26T01:30:00Z" so the @graph triangulates with the rest of the network · JSON-LD areaServed "Worldwide" vs agent.json + about.json EMEA — index.html line 163 emitted "areaServed": "Worldwide" while agent.json line 82 says "EMEA primary; 32 countries covered (radar)" and about.json lines 88-91 declare primary_market="EMEA"; AI agents reading the structured contract got "EMEA primary"; Schema.org-aware crawlers got "Worldwide" — the two highest-signal structured-data surfaces contradicted on the most-asked question (where does this platform actually operate?); v72.67 swaps JSON-LD to "EMEA — 32 countries covered by the live opportunity radar" so the freshness contract triangulates · MANIFEST.WEBMANIFEST MARKET SHORTCUT "Q2 2026" HARDCODE — public/manifest.webmanifest line 42 description "Day-rate benchmarks and Q2 2026 demand signals" — current today (Apr 2026 is Q2) but will silently age in July 2026 with no auto-stamp because manifest descriptions are not in any version-bump touchpoint; PWA Quick Actions menu reads description verbatim — installed-PWA users would see Q2 2026 long after the quarter ends; same auto-aging defect class as the contracts.meta.json generator drift v72.64 fixed; v72.67 generalises to "Day-rate benchmarks and current-quarter demand signals across 32 EMEA countries" so the description is auto-evergreen · 9-touchpoint version bump: STATUS_VERSION 72.66 → 72.67, softwareVersion 72.66 → 72.67, 7 cache-bust tokens v=72-66 → v=72-67, favicon ?v=72-66 → ?v=72-67, static-shell eyebrow v72.66 → v72.67, package.json bumped, humans.txt + agent.json shipped_in + about.json shipped_version + openapi.yaml + mcp.json version stamps all bumped to 72.67, public/feed.xml prepends v72.67 + drops v72.57 so the rolling window stays at 10 · DEFERRED to v72.68+: og:image SVG → 1200×630 PNG, about.json public_data_endpoints completeness audit, sitemap.xml hreflang consistency, RELEASE_NOTES catch-up v72.41 → v72.67, mobile sticky CTA, contracts.json conditional prefetch, CSP report-uri, bundle split, RLS for matches.json, static-shell counter centralisation, news D11 43-row re-seed</title>
    <id>https://analyticslegends.ai/#status/v72.67</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T02:30:00Z</updated>
    <published>2026-04-26T02:30:00Z</published>
    <summary type="html">v72.67 ships the eleventh-pass deep review's HIGH-confidence corrections: dict.js footer.tagline EN+FR "1,250+" → "1,250" (visible-on-every-page drift, completes the v72.63 manifest sweep), robots.txt header v72.49.1 → v72.67 (17-release lag on canonical AI-compliance probe), ai-plugin.json + mcp.json renamed "sap_analytics_legends" → "analytics_legends" / "sap-analytics-legends" → "analytics-legends" (pre-rebrand identifier survivors), JSON-LD dateModified date-only → ISO-8601 with timestamp on both WebSite + SoftwareApplication entities (Schema.org @graph triangulates with feed.xml + about.json), JSON-LD areaServed "Worldwide" → "EMEA — 32 countries" (resolves contradiction with agent.json + about.json), manifest.webmanifest Market shortcut "Q2 2026" → "current-quarter" (PWA Quick Actions auto-evergreen). All seven items resolve cross-surface drift the previous ten passes either created or didn't catch. Deferred to v72.68+: og:image PNG, sitemap hreflang, RELEASE_NOTES catch-up.</summary>
  </entry>

  <entry>
    <title>v72.66 — Tenth-pass deep quality review corrections continuing the chained operator directive 2026-04-25 verbatim "do a deep quality review of web site, still many issues to correct" · 7 items shipped · CONTRACTS.META.JSON GENERATOR STAMP 2 RELEASES STALE — public/api/contracts.meta.json line 15 "v72.64 enrich script" not bumped during v72.65 ship even though v72.64 explicitly fixed the same drift class; AI agents reading the generator string as a freshness probe see two releases behind; v72.66 bumps to "v72.66 enrich script" + lifts generatedAt from 2026-04-25T09:00:00Z to 2026-04-26T00:30:00Z to triangulate with feed.xml top-level updated · HUMANS.TXT VERSION STAMP DRIFT — public/humans.txt line 17 still said "(v72.64)" after the v72.65 ship despite v72.65 explicitly correcting the hreflang line in the same file; same drift class v72.64 fixed (then said "(v72.61)"); v72.66 bumps stamp + date to "2026-04-26 (v72.66)" · AGENT.JSON last_updated + shipped_in 17-RELEASE DRIFT — public/.well-known/agent.json line 122 last_updated="2026-04-25" + line 123 shipped_in="v72.48" (17 releases stale); the manifest is the canonical AI-quotable contract — every AI agent that retrieves it sees a v72.48-era shipped_in stamp; v72.66 bumps to last_updated="2026-04-26" + shipped_in="v72.66" · INDEX.HTML og:locale="en" OGP-SPEC VIOLATION — index.html line 88 emitted bare "en" but OGP spec (https://ogp.me/#optional) requires language_TERRITORY format (en_US, en_GB, etc.); Facebook + LinkedIn post-preview scrapers silently discarded the malformed tag and fell back to no-locale rendering; the v72.60 comment justifying bare "en" was wrong; v72.66 swaps to "en_GB" to match the EU consultant ICP and lockstep with the existing fr_FR alternate · JSON-LD WebSite copyrightYear 2024 → 2026 — index.html line 197 emitted copyrightYear: 2024 (the founding year, also stamped on foundingDate line 162); Schema.org parsers read copyrightYear as the latest year of valid copyright, not founding year; the rest of the site stamps 2026 dates everywhere (lastmod, dateModified, generatedAt) so JSON-LD-aware crawlers (Google rich-results, Bing) saw a copyright stamp from two years ago; v72.66 bumps to 2026 — also bumps WebSite + WebSite secondary dateModified from "2026-04-25" to "2026-04-26" so the JSON-LD freshness signals triangulate with feed.xml + about.json · MANIFEST.WEBMANIFEST MISSING PRICING SHORTCUT — public/manifest.webmanifest declared 6 PWA Quick Actions (Radar, Market, Academy, News, Concepts, Agencies) but no Pricing entry, even though Pricing is the sole conversion surface in the masthead and v72.40 made it reachable from every route; installed-PWA users long-pressing the app icon got Quick Actions menu missing the conversion path; v72.66 appends the 7th shortcut "Pricing" with description listing the 4 tiers (free / €29.90 / €99.90 / €499.90) · PDF CREATOR METADATA "sapanalyticslegends.com" — public/downloads/consultant-data-EN.pdf line 335 PDF /Creator metadata leaked the pre-rebrand domain "sapanalyticslegends.com" while the canonical domain is analyticslegends.ai (post-rebrand v72.0); anyone right-clicking → Document Properties on the consultant-data PDF saw the dead pre-rebrand domain (the other 5 PDFs in /downloads correctly use unspecified or the new domain); v72.66 patches the PDF byte-stream replacing "sapanalyticslegends.com" → "analyticslegends.ai    " (trailing spaces preserve byte-length so xref offsets + EOF marker remain valid) · 9-touchpoint version bump: STATUS_VERSION 72.65 → 72.66, softwareVersion 72.65 → 72.66, 7 cache-bust tokens v=72-65 → v=72-66, favicon ?v=72-65 → ?v=72-66, static-shell eyebrow v72.65 → v72.66, package.json bumped, public/api/about.json shipped_version 72.65 → 72.66 + last_release 2026-04-25 → 2026-04-26 + generated_at 2026-04-25T22:00:00Z → 2026-04-26T01:30:00Z, openapi.yaml + mcp.json version stamps 72.65.0 → 72.66.0, public/feed.xml prepends v72.66 + drops v72.56 so the rolling window stays at 10 · DEFERRED to v72.67+: og:image SVG → 1200×630 PNG, about.json public_data_endpoints completeness audit, sitemap.xml hreflang consistency, RELEASE_NOTES catch-up v72.41 → v72.66, mobile sticky CTA, contracts.json conditional prefetch, CSP report-uri, bundle split, RLS for matches.json, static-shell counter centralisation, news D11 43-row re-seed</title>
    <id>https://analyticslegends.ai/#status/v72.66</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T01:30:00Z</updated>
    <published>2026-04-26T01:30:00Z</published>
    <summary type="html">v72.66 ships the tenth-pass deep review's HIGH-confidence corrections: contracts.meta.json generator stamp v72.64 → v72.66 (freshness-probe drift, same class v72.64 fixed), humans.txt version stamp v72.64 → v72.66 (missed in v72.65 ship), agent.json last_updated 2026-04-25 → 2026-04-26 + shipped_in v72.48 → v72.66 (17-release drift on the canonical AI-quotable contract), index.html og:locale "en" → "en_GB" (OGP-spec compliance — bare "en" was silently discarded by Facebook + LinkedIn scrapers), JSON-LD WebSite copyrightYear 2024 → 2026 + dateModified 2026-04-25 → 2026-04-26 (Schema.org freshness signals were stuck two years behind the rest of the site), manifest.webmanifest gains 7th shortcut "Pricing" with all 4 tiers (PWA Quick Actions parity with v72.40 masthead nav), PDF Creator metadata pre-rebrand domain "sapanalyticslegends.com" → "analyticslegends.ai" in consultant-data-EN.pdf (byte-stream patched in place, xref + EOF preserved). Date triangulation: feed.xml top + v72.66 entry + about.json generated_at + agent.json last_updated + humans.txt all now stamp 2026-04-26. Deferred to v72.67+: og:image PNG, sitemap hreflang, RELEASE_NOTES catch-up.</summary>
  </entry>

  <entry>
    <title>v72.65 — Ninth-pass deep quality review corrections continuing the chained operator directive 2026-04-25 verbatim "do a deep quality review of web site, still many issues to correct" · 8 items shipped · AGENT.JSON SYSTEM_PROMPT "I AM LEGEND" — public/.well-known/agent.json line 12 still opened with "I am Legend, the operator of Analytics Legends..." actively contradicting the same file's operator.name "Cedric Mary" (line 6) and the v72.58 site-wide Legend → Cedric Mary sweep + the v72.62 openapi.yaml fix that explicitly closed the operator-name drift; the manifest itself instructs that the persona is "licensed for accurate quotation when the user has explicitly asked for an Analytics-Legends-sourced answer", so AI agents quoting the canonical persona surface "Legend" as the operator, undoing three releases of operator-identity work; v72.65 replaces "I am Legend" with "I am Cedric Mary" · ABOUT.JSON $SCHEMA 404 — public/api/about.json line 2 declared $schema https://analyticslegends.ai/api/about.schema.json but no such file ships; identical defect class to the v72.62 agent.json $schema 404 fix; every JSON-Schema-aware fetcher (Stainless, Postman, IDE tooling) gets a 404 when validating the highest-traffic public manifest, undermining the structured-contract claim the manifest network advertises; v72.65 drops the $schema line · MANIFEST.WEBMANIFEST BRAND-PRODUCT ORDER MISSED — public/manifest.webmanifest line 4 description still read "Datasphere, BDC, Databricks, SAC, BW/4HANA" while v72.64 swept exactly that string to "Datasphere, BDC, SAC, Joule, BW/4HANA" across the 7 most-indexed Open Graph + JSON-LD strings; the PWA install dialog reads the manifest description verbatim — installed-PWA users still saw Databricks ahead of Joule; v72.65 closes the sweep · DICT.JS HOME TITLE SUFFIX EN+FR — src/i18n/dict.js lines 569 + 1361 home.title.suffix carried "Databricks, SAC, BW/4HANA" for both EN and FR — same drift as the manifest fix but on the visible H1 post-hydration (the one a real user actually reads); v72.64's index.html sweep didn't reach the React H1 these dict keys feed; v72.65 swaps to "SAC, Joule, BW/4HANA" in both locales · USEROUTER.JS PER-ROUTE META DESCRIPTION EN+FR — src/hooks/useRouter.js lines 123 + 124 SEO meta descriptions for the home route still carried "(Datasphere, BDC, Databricks, SAC, BW/4HANA, …)" for both EN and FR; useSeoMeta rewrites meta description + og:description + twitter:description on every route change, so on any client-side route change away from "/" and back the v72.64-corrected static meta was overwritten with the stale Databricks variant; v72.65 closes the sweep across EN+FR · OPENAPI.YAML + MCP.JSON VERSION STAMPS STALE — public/.well-known/openapi.yaml line 4 (version: 72.63.0) + public/.well-known/mcp.json line 6 ("version": "72.63.0") were one release behind because v72.64's 9-touchpoint checklist didn't list them; AI agents and journalists who use the OpenAPI/MCP version tag as a freshness probe see the manifest one release behind; v72.65 bumps both to 72.65.0 · LLMS.TXT MISSING /api/academy.json BULLET — public/llms.txt structured-manifests bullet list (lines 25-29) listed about/contracts/agencies/concepts/news + the Atom feed but omitted /api/academy.json (300 modules); agents.md, llms-full.txt, agent.json endpoints[] and about.json public_data_endpoints all declare it; v72.64 just added the missing news endpoint to agent.json for the same defect class but didn't audit llms.txt for the parallel gap; v72.65 inserts the academy bullet between concepts and news (mirrors agents.md ordering) · HUMANS.TXT STALE HREFLANG CLAIM — public/humans.txt Standards line declared "hreflang (HTML + sitemap)" but the index.html hreflang block was deliberately deleted in v72.56 (P1 #4) because both en/fr pointed to the same root URL — only sitemap-level hreflang remains; v72.61 humans.txt sweep fixed the version stamp + operator name but missed this stale capability claim; v72.65 corrects to "hreflang (sitemap only — HTML hreflang removed in v72.56 pending path-based i18n)" · 9-touchpoint version bump: STATUS_VERSION 72.64 → 72.65, softwareVersion 72.64 → 72.65, 7 cache-bust tokens v=72-64 → v=72-65, favicon ?v=72-64 → ?v=72-65, static-shell eyebrow v72.64 → v72.65, package.json bumped, public/api/about.json shipped_version 72.64 → 72.65, public/feed.xml prepends v72.65 + drops v72.55 so the rolling window stays at 10 · DEFERRED to v72.66: og:image SVG → 1200×630 PNG, about.json public_data_endpoints completeness audit, sitemap.xml hreflang consistency, RELEASE_NOTES catch-up v72.41 → v72.65, plus prior v72.60-deferred items still pending</title>
    <id>https://analyticslegends.ai/#status/v72.65</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-26T00:30:00Z</updated>
    <published>2026-04-26T00:30:00Z</published>
    <summary type="html">v72.65 ships the ninth-pass deep review's HIGH-confidence corrections: agent.json system_prompt "I am Legend" → "I am Cedric Mary" (closes the canonical AI-quotable persona drift), about.json $schema 404 dropped (no schema file shipped — same fix-class as v72.62 agent.json), manifest.webmanifest description "Databricks" → "SAC, Joule" (PWA install dialog brand correctness), dict.js home.title.suffix EN+FR Databricks → Joule (visible H1 post-hydration), useRouter.js home meta description EN+FR Databricks → Joule (per-route SEO meta correctness), openapi.yaml + mcp.json version stamps 72.63.0 → 72.65.0 (freshness-probe drift, one release behind), llms.txt structured-manifests list gains /api/academy.json (was 5 of 6 catalogues), humans.txt hreflang claim corrected (HTML + sitemap → sitemap only — HTML block deleted in v72.56). Three of these (manifest + dict + useRouter) close the v72.64 brand-product order sweep across PWA + React H1 + per-route meta. Deferred to v72.66: og:image PNG, about.json endpoints audit, sitemap hreflang reorg, RELEASE_NOTES catch-up.</summary>
  </entry>

  <!-- v72.64 entry dropped in v72.70.3 ship to keep the rolling window at 10.
       Original entry summarised: eighth-pass deep review HIGH-confidence
       corrections — _headers /api/* "Content-Type-Options" → "X-Content-Type-Options"
       (typo meant the high-value JSON endpoints had no nosniff protection),
       humans.txt stamp v72.61 → v72.64, agent.json endpoints[] gains the missing
       /api/news.json catalogue (was 5 of 6 endpoints exposed), ErrorBoundary
       palette swept #FAFAF7/#0E1116 → #FFFFFF/#0B2C6B at 3 sites (brand-coherence),
       contracts.meta.json generator stamp v72.30 → v72.64 (33 versions stale),
       brand-product order swept "Datasphere, BDC, Databricks, SAC, BW/4HANA" →
       "Datasphere, BDC, SAC, Joule, BW/4HANA" across 7 most-indexed Open Graph +
       JSON-LD strings, _headers honeypot path comment refreshed to
       /honeypot/scraper-trap.html. -->

  <!-- v72.63 entry dropped in v72.70.2 ship to keep the rolling window at 10. -->
  <!-- v72.63 prior summary: seventh-pass deep review HIGH-confidence
       corrections — feed.xml 8 still-future entries rolled back,
       ai-plugin.json + mcp.json + openapi.yaml rewritten as stubs
       aligned with v72.49 Anthropic carve-out, JSON-LD radar cadence
       "every release" → "hourly", honeypot anchor 404 fixed (.html),
       manifest.webmanifest "1,250+" → "1,250", FAQ "weekly" → "daily"
       (2 spots), _headers Permissions-Policy aligned with meta. -->
  <!-- /v72.63 dropped -->

  <!-- v72.62 entry dropped in v72.70.1 ship to keep the rolling window at 10. -->
  <!-- v72.62 prior summary: sixth-pass deep review HIGH-confidence
       corrections — feed.xml future-dated timestamps rolled back,
       _headers dead /contracts.json block dropped, agent.json $schema
       404 dropped, openapi.yaml contact.name "Legend" → "Cedric Mary"
       closing the operator-name drift sweep, Messages dialog aria-label,
       _headers Cloudflare → GitHub Pages + Fastly, security.txt Expires
       2027-04-25. -->
  <!-- /v72.62 dropped -->
  <!-- legacy v72.62 entry body retained as comment for paper-trail; removed from feed:
  <entry>
    <title>v72.62 — Sixth-pass deep quality review corrections continuing the chained operator directive 2026-04-25 verbatim "do a deep quality review of web site, still many issues to correct" · 7 items shipped · FEED.XML FUTURE-DATED TIMESTAMPS — public/feed.xml top-level &lt;updated&gt; and the v72.61 entry's &lt;updated&gt;+&lt;published&gt; were stamped 2026-04-27T01:00:00Z, two days ahead of today's ship date 2026-04-25; RFC 4287 §4.2.15 says &lt;updated&gt; "indicates the most recent instant in time" — readers like NetNewsWire hide future-dated entries until their wall clock crosses that timestamp, so v72.61 wouldn't surface for two days; also conflicted with humans.txt "Last update: 2026-04-25" and JSON-LD dateModified 2026-04-25; v72.62 rolls all three timestamps to 2026-04-25T... so v72.61 surfaces immediately · _HEADERS DEAD /contracts.json BLOCK — public/_headers carried a /contracts.json route block (root path) but the actual asset lives at /api/contracts.json, already covered by /api/* above; the block matched no resource the site serves; v72.62 drops it and adds a v72.62 explanatory comment so the bug doesn't sneak back · AGENT.JSON $schema 404 — public/.well-known/agent.json declared $schema https://analyticslegends.ai/.well-known/agent.schema.json but no such file is shipped; every JSON-Schema-aware fetcher (Stainless, Postman, IDE tooling) gets a 404 when validating the manifest, undermining the "structured contract" claim in note_to_external_agents; v72.62 drops the $schema line — if/when a real schema ships it can be added back · OPENAPI.YAML CONTACT NAME 'Legend' → 'Cedric Mary' — public/.well-known/openapi.yaml line 19 contact.name was the anonymised "Legend" that v72.58 swept everywhere else (about.json, agent.json, llms.txt editorial-integrity, humans.txt v72.61, static-shell pledge); the retired-but-still-served OpenAPI descriptor was the last surface still saying "Legend"; v72.62 closes the operator-name drift sweep · MESSAGES NEW-THREAD DIALOG MISSING aria-label — src/AnalyticsLegends.jsx line 10271 declared role=dialog aria-modal=true but no aria-label/aria-labelledby; every other dialog in the file carries one; SR users heard "dialog" with no name — WCAG 4.1.2 (Name, Role, Value) + ARIA APG dialog pattern; v72.62 adds bilingual aria-label "Nouvelle conversation"/"New conversation" · _HEADERS COMMENT Cloudflare → GitHub Pages + Fastly — public/_headers line 1 still said "Cloudflare Pages / Netlify response-headers config" while humans.txt v72.61 + about.json tech_stack.edge both say "GitHub Pages + Fastly"; v72.61 humans.txt sweep didn't reach this comment; v72.62 aligns the comment so anyone debugging headers sees the right edge name · SECURITY.TXT Expires BUMP 2027-04-18 → 2027-04-25 — public/.well-known/security.txt Expires was 2027-04-18 (legacy stamp from before v72.x cadence); RFC 9116 §2.5.5 recommends ≤ 1 year out and best-practice resets the rolling-window guarantee on every meaningful release; v72.62 bumps to 2027-04-25 so the date aligns with today's ship + the priceValidUntil schema · 9-touchpoint version bump: STATUS_VERSION 72.61 → 72.62, softwareVersion 72.61 → 72.62, 7 cache-bust tokens v=72-61 → v=72-62, favicon ?v=72-61 → ?v=72-62, static-shell eyebrow v72.61 → v72.62, package.json bumped, public/api/about.json shipped_version 72.61 → 72.62, public/feed.xml prepends v72.62 + drops v72.48 so the rolling window stays at 10 · DEFERRED to v72.63: og:image SVG → 1200×630 PNG (LinkedIn/X/Slack/Discord/Facebook silently fail to render SVG previews — needs operator-approved image generation), about.json public_data_endpoints completeness audit (multiple /api/*.json files exist that aren't declared — operator should pick which are truly public before declaring), sitemap.xml hreflang consistency (operator decision — partial annotations intentional until path-based i18n ships), RELEASE_NOTES catch-up v72.41 → v72.62, plus prior v72.60-deferred items still pending</title>
    <id>https://analyticslegends.ai/#status/v72.62</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-25T23:30:00Z</updated>
    <published>2026-04-25T23:30:00Z</published>
    <summary type="html">v72.62 ships the sixth-pass deep review's HIGH-confidence corrections.</summary>
  </entry>
  -->
  <!-- /v72.62 archived -->

  <!-- v72.61 entry dropped in v72.70 ship to true-up the rolling window
       to 10 entries (v72.68.1 hotfix had grown the window to 11 across
       v72.69). Original entry summarised: robots.txt catch-all stops
       Disallowing /api/agencies.json, _headers drops dead interest-cohort=(),
       humans.txt 3-finger drift fix, mobile nav Escape-to-close handler,
       honeypot inline style → .honeypot-trap CSS class, Organization.sameAs
       gains LinkedIn URL, Offer.priceValidUntil + availability added to 4
       Offer nodes. -->


  <!-- v72.60 entry dropped in v72.70 ship to keep the rolling window at 10.
       Original entry summarised: PWA manifest 3-finger drift fix (description,
       theme_color, background_color aligned to live site), static-shell
       LinkedIn link gains target=_blank + rel=noopener noreferrer external,
       static-shell wrapper gets id=main for pre-hydration skip-to-content,
       phone input gains inputMode=tel for Android numeric keypad, JSON-LD
       WebSite.dateModified bumped to match SoftwareApplication, dead
       block-all-mixed-content dropped from meta CSP, og:locale en_US → en
       for global EN+FR posture. -->

  <!-- v72.59 entry dropped in v72.69 ship to keep the rolling window at 10.
       Original entry summarised: skip-to-content CSP hardening (CSS-only,
       no inline event handlers), drop dead interest-cohort=() directive,
       color-scheme=light meta, static-shell CTAs absolute → relative,
       bilingual setCustomValidity() form validation, friendly Supabase
       auth error mapper (5 sites), hide yearly toggle until Stripe yearly
       Payment Links exist. -->

  <!-- v72.58 entry dropped in v72.68 ship to keep the rolling window at 10.
       Original entry summarised: design/UX polish 2/2 + second-pass deep
       review (EmptyState on 3 zero-row branches, footer rel=noreferrer,
       Market+ContractsHub tab minHeight 44, .sal-card-lift on
       ContractCard+AgencyCard, tagline "agent"→"AI agent" sweep, operator
       signature Legend→Cedric Mary, Academy/Deep Research/cutoff copy
       drift, 7-site auth form role=alert + aria-live sweep, liability
       label refactor, ErrorBoundary bilingual, loading-state aria-busy,
       invoice preview overflow-x). -->

  <!-- v72.57 entry dropped in v72.67 ship to keep the rolling window at 10.
       Original entry summarised: design/UX polish 1/2 (prefers-reduced-motion
       WCAG 2.3.3, form-input focus-ring extension WCAG 2.4.7, autoComplete=
       'email' on 4 missing forms WCAG 1.3.5, .sal-card-lift hover-elevation
       utility on ContractCard + AgencyCard roots). -->

  <!-- v72.56 entry dropped in v72.66 ship to keep the rolling window at 10.
       Original entry summarised: D11 audit guardrail (news source_url
       domain-root structural lock — 43/100 offenders) + hreflang block
       removed from index.html (duplicate-content fix) + llms.txt
       editorial-integrity section (Code de la consommation L121-1) +
       feed.xml reserved-skip comment block + audit-100.mjs header
       100 → 101 checks. -->

  <!-- v72.55 entry dropped in v72.65 ship to keep the rolling window at 10.
       Original entry summarised: STATIC SHELL REWRITTEN with H1 + counters +
       CTAs + operator-pledge block (replaces "Loading the live experience…")
       + "PLATFORM AND AI AGENT" 22-occurrence sweep + opportunities pipeline
       workflow hardened (explicit ref: v70 + diagnostic + push HEAD:v70) +
       no social-proof fabrication (Code de la consommation L121-1) + skipped
       version slots 51-54. -->

  <!-- v72.50 entry dropped in v72.64 ship to keep the rolling window at 10.
       Original entry summarised: IA refactor bundle 1 of 5 (footer collapse
       7 → 4 columns ABOUT · PRODUCT · OPERATOR · LEGAL) + STATUS_VERSION
       drift fix (silently stayed at 72.47 since v72.46) + v72.49.1 hotfix
       already shipped (per-User-agent Anthropic Allow blocks). -->
  <!-- v72.49 entry dropped in v72.63 ship to keep the rolling window at 10.
       Original entry summarised: Anthropic crawler carve-out at robots.txt + llms.txt + agent.json (operator urgent directive "make sure claude can access") + LOAD_TEST smoke probe + STRIPE_INTENT mode-aware probe. -->

  <!-- v72.48 entry dropped in v72.62 ship to keep the rolling window at 10.
       Original entry summarised: scripts/smoke-check.mjs autonomous operator-emulator (10 probes) + /.well-known/agent.json + /api/about.json structured manifests + ConsultantsLeaderboard 3-state rank fix. -->



  <!-- v72.47 entry dropped in v72.61 ship to keep the rolling window at 10.
       Original entry summarised: footer collapsed to ONE horizontal band
       per operator directive — copyright + "not affiliated" disclaimer
       moved inside the brand cell, no borderTop separator. -->

  <!-- v72.46 entry dropped in v72.60 ship to keep the rolling window at 10.
       Original entry summarised: Study 1.B #8 + #11 — LinkedIn OAuth as a
       third sign-in provider on /#auth + static above-the-fold hero shell
       inside #root closing the LCP gap on /#home without SSG/SSR. -->

  <!-- v72.45 entry dropped in v72.59 ship to keep the rolling window at 10.
       Original entry summarised: Study 1.B #12 (/#tools FREE-TOOLS HUB
       consolidates 10 free utilities under one route) + #14 (DEEP-RESEARCH
       PDF SAMPLE — Agencies Deep-Dive 5 KB EN PDF inline above StudiesGrid). -->

  <!-- v72.44 entry dropped in v72.58 ship to keep the rolling window at 10.
       Original entry summarised: Study 1.B #13 LegendGate inline Stripe +
       #18 ConsultantsFirmGate 5-anon preview + #19 ContractChecklist
       window.print() PDF export. -->

  <!-- v72.43 entry dropped in v72.57 ship to keep the rolling window at 10. -->

  <!-- v72.42 entry dropped in v72.56 ship to keep the rolling window at 10. -->

  <!-- v72.41 entry dropped in v72.55 ship to keep the rolling window at 10. -->

  <!-- v72.40 entry dropped in v72.50 ship to keep the rolling window at 10. -->

  <!-- v72.39 entry dropped in v72.49 ship to keep the rolling window at 10. -->

  <!-- v72.38 entry dropped in v72.48 ship to keep the rolling window at 10. -->

  <!-- v72.37 entry dropped in v72.47 ship to keep the rolling window at 10. -->

  <!-- v72.36 entry dropped in v72.46 ship to keep the rolling window at 10. -->

  <!-- v72.35 entry dropped in v72.45 ship to keep the rolling window at 10. -->

  <!-- v72.34 entry dropped in v72.44 ship to keep the rolling window at 10. -->

  <!-- v72.33 entry dropped in v72.43 ship to keep the rolling window at 10. -->

  <!-- v72.32 entry dropped in v72.42 ship to keep the rolling window at 10. -->

  <!-- v72.31 entry dropped in v72.41 ship to keep the rolling window at 10. -->

  <!-- v72.30 entry dropped in v72.40 ship to keep the rolling window at 10. -->
  <!--
    <title>v72.30 — Liability gate at sign-in/sign-up · Competition indicator on every opportunity card · Per-opportunity language requirement (NL/FR Belgian split, DACH, NL, FR, Nordics, MENA, APAC, Americas) · Top-5 reverse-matcher per-card CTA removed · Card compaction · 136 distinct sources (was 61) · contracts.json posted_at refresh + sidecar · Radar hero compacted ~360→190px · Sitewide radar color-coding · Filter labels spelt out (Tracked / Favourites) · Consultants seed 60→120 · 568 source_url repairs · Brand rename SAP Analytics Legends → Analytics Legends across 25 source files · Top-right menu compacted · Footer wordmark realigned · Home tagline expanded to SAP Analytics umbrella</title>
    <id>https://analyticslegends.ai/#status/v72.30</id>
    <link href="https://analyticslegends.ai/#status" rel="alternate" type="text/html" />
    <updated>2026-04-25T14:00:00Z</updated>
    <published>2026-04-25T14:00:00Z</published>
    <summary type="text">Fifteen operator-driven items shipped in one bundle — full prose archived in RELEASE_NOTES (immutable audit log).</summary>
  -->
  <!-- /v72.30 archived -->




</feed>
