Débogage des analytics MCP
Analyses de produit pour les serveurs MCP. Une équipe livre un serveur MCP ; le SDK @posthog/mcp
l'enveloppe en une seule ligne ; chaque appel d'outil, intention d'agent et échec atterrissent dans PostHog sous forme d'événement $mcp_* que vous pouvez interroger, représenter graphiquement, alerter et regrouper — plus un tableau de bord dédié. Le frère de couche MCP de @posthog/ai.
Le différenciateur est l'intention : non pas « a exécuté query_run 14 fois » mais « essayait de trouver une cohorte d'attrition ». Non-objectif explicite : ceci ne remplace pas les analytics LLM / l'observabilité IA — les traces de génération, prompt/réponse et coût en tokens y appartiennent.
État : bêta, SDKs TypeScript et Python livrés, produit entier toujours derrière le flag d'accès anticipé mcp-analytics (products/mcp_analytics/frontend/featurePreviewGate.ts).
PostHog s'en sert lui-même — son propre serveur MCP s'instrumente automatiquement, et ces données alimentent le tableau de bord. Suivi public : méga-issue PostHog/posthog#64016, qui est la source actuelle de la feuille de route et de la liste de souhaits des clients.
Dépôts
GitHub est la source de vérité pour savoir où vit le code. Les chemins ci-dessous sont dans le dépôt ; pour les dépôts en dehors de ce monodépôt, résolvez un checkout local via references/local-repos.md plutôt que de supposer un emplacement.
| Domaine | Dépôt | Où regarder |
|---|---|---|
| Produit / tableau de bord | PostHog/posthog (ce dépôt) |
products/mcp_analytics/ — Django/DRF + exécuteurs de requêtes HogQL + Temporal, frontend Kea, le registre d'outils query-mcp-*, et les skills d'analyse |
| Serveur auto-instrumenté | PostHog/posthog (ce dépôt) |
services/mcp/ — serveur MCP de PostHog (Hono) ; le producteur d'événements dogfood. Héberge aussi les gestionnaires query-mcp-* générés |
| Référence de requête partagée | PostHog/posthog (ce dépôt) |
models-mcp.md — products/posthog_ai/skills/querying-posthog-data/references/ |
SDK TypeScript @posthog/mcp |
PostHog/posthog-js |
packages/mcp/ — la bibliothèque que les clients installent. Source de vérité du vocabulaire : src/extensions/constants.ts. docs/ARCHITECTURE.md couvre maintenant l'ancrage de conversation (ADR-0004) mais traîne sur la gestion de la nouvelle ère — où elle et CHANGELOG.md divergent, fiez-vous au changelog et à la source |
SDK Python posthog.mcp |
PostHog/posthog-python |
posthog/mcp/ — miroir de posthog.ai. Livré dans posthog (pip install posthog) ; mcp/fastmcp sont des dépendances pairs importées paresseusement, pas d'extra [mcp]. À parité TS depuis 7.40.0-7.42.1 — MCP SDK Python v2, ancrage de conversation, erreurs typées, client UA/vendor |
| Docs | PostHog/posthog.com |
contents/docs/mcp-analytics/ (incl. surfaces/), plus src/hooks/productData/mcp_analytics.tsx et l'entrée mcp_analytics dans src/data/tools.ts |
| Codemod d'installation | PostHog/context-mill |
context/skills/mcp-analytics/{config.yaml,description.md} |
| CLI Wizard | PostHog/wizard |
bin.ts, src/commands/mcp-analytics.ts, src/lib/programs/mcp-analytics/ |
| Harnais de test Wizard | PostHog/wizard-workbench |
apps/mcp-analytics/ fixtures |
Ne confondez pas :
PostHog/mcp-analyticsest le prototype archivé de ce SDK — bloqué à0.0.9avec une ancienne APItrack(server, {...}). Il a été publié sous le même nom@posthog/mcp, donc grep sur ce nom peut vous y amener. npm@posthog/mcprésout maintenant versPostHog/posthog-js.products/mcp_store/est la place de marché des serveurs MCP / passerelle d'équipe, pas ce produit. (Les notes plus anciennes mentionnent aussi un répertoireproducts/mcp/d'outils de compilation ; il n'existe plus — le serveur et ses outils de génération vivent dansservices/mcp/.)wizard mcp addinstalle le serveur MCP de PostHog dans un agent de codage. Ce n'est paswizard mcp-analytics, qui instrumente le propre serveur de l'utilisateur.
Les numéros de ligne dérivent et cette zone bouge vite — grep sur le symbole, ne faites jamais confiance à un numéro de ligne mémorisé. Confirmez qu'un checkout est sur une branche correcte avant de citer son code.
Règles strictes (violez-les et les nombres seront silencieusement faux)
Ce sont les modes de défaillance qui produisent une réponse plausible plutôt qu'une erreur.
- Résolvez toujours le nom d'outil effectif via
EFFECTIVE_TOOL_SQL. L'expression existe une seule fois, dansproducts/mcp_analytics/backend/hogql_queries/base.py:coalesce(nullIf(toString(properties.$mcp_exec_tool_call_name), ''), toString(properties.$mcp_tool_name)). Elle existe parce qu'un serveur à exécution simple peut rapporter l'outil de deux façons différentes, et les deux ères de données coexistent. Aujourd'huiservices/mcprésout l'outil interne lui-même et le transmet directement comme nom d'outil (execToolName()danssrc/hono/tool-executor.ts, qui se rabat sur le littéralexecquand la commande interne n'est pas reconnue), donc$mcp_tool_namecontient généralement déjà l'outil réel.$mcp_exec_tool_call_nameest enregistré dansposthog/taxonomy/taxonomy.pyet coalesced défensivement ici, mais rien sur master ne l'émet — traitez-le comme des lignes historiques plus du travail en cours, pas du comportement du producteur actuel. De toute façon, agrégez via la coalescence : rouler à la mainproperties.$mcp_tool_nameseul regroupe silencieusement les appels exec non reconnus sousexec, et manque toute donnée qui porte la propriété dédiée. - Les échecs viennent de
$mcp_is_error/$mcp_error_type/$mcp_error_status, jamais$exception.$exceptionpeut être désactivé, n'est pas émis quand aucune valeur d'erreur n'est passée, et ne correspond jamais aux événements du nouveau SDK — donc l'interroger renvoie rien plutôt que d'échouer. - Tiretez le bucket en cours. Chaque graphique à temps rempli de zéros et marque l'intervalle final incomplet via
products/mcp_analytics/frontend/timeBuckets.ts(resolveWindow,normalizeBucket,buildBucketKeys,lastBucketIsInProgress). L'omettre et une période partielle se lit comme une vraie baisse. harnessest dérivé, et sa logique existe en trois lieux qui doivent se déplacer en lockstep :products/mcp_analytics/backend/mcp_harness.py(source de vérité — voir sa docstring de module),products/mcp_analytics/frontend/dashboard/harnessRegistry.ts, etmodels-mcp.md.- Vérifiez quelle version du SDK utilise le serveur dogfood avant de faire confiance aux données dogfood.
services/mcpconsomme le SDK via un alias dans sonpackage.jsonet a historiquement traîné derrière la version publiée, donc les propriétés dépendantes de la version (types d'erreurs typés, identité$lib, redaction de payload) peuvent être absentes des données de PostHog lui-même même quand documentées comme actuelles. Une requête filtrant sur$lib = 'posthog-node-mcp'exclut silencieusement tout le trafic dogfood si cet épingle précède SDK 0.7.0. Notez aussi queservices/mcputilise le chemin du dispatcher personnalisé (PostHogMCP) plutôt queinstrument(), donc le comportement vivant uniquement dans le chemininstrument()— sessions stables, déduplications$identify, identité client basée sur_meta— ne lui a jamais s'appliquer à aucune version. - Sachez quel modèle de session a produit les données. Selon la spec stateless il n'y a pas de session transport, donc
$session_idn'est stable que si le serveur a opté pour l'ancrage de conversation —enableConversationId, qui est désactivé par défaut. Avec lui désactivé, les sessions d'un client stateless se fragmentent (souvent une par requête) ; avec lui activé,$session_idest dérivé d'un handle retourné par l'agent et survit aux reconnexions, redémarrages et pods. Vérifiez le flag avant de diagnostiquer les « sessions fragmentées » comme un problème d'ingestion. Voir references/stateless-and-sessions.md. - Il n'y a pas de fichiers de modèles SQL. Chaque requête de tableau de bord et de qualité d'outil est un exécuteur de requête typé derrière le point de terminaison générique
/query/. Unbackend/templates/*.sqlréférencé par des notes plus anciennes n'existe plus.
Vocabulaire des événements
Toutes les données vivent sur la table ClickHouse partagée events — il n'y a pas de table dédiée.
Chaque métrique est une agrégation sur $mcp_tool_call, généralement regroupée par $session_id.
La source de vérité pour les noms émis par le SDK est packages/mcp/src/extensions/constants.ts dans PostHog/posthog-js, exportée comme PostHogMCPAnalyticsEvent / PostHogMCPAnalyticsProperty (importez-les pour les requêtes type-safe). Les descriptions du côté PostHog — y compris les propriétés estampillées par le serveur et le mode exec que le SDK ne définit pas — vivent dans posthog/taxonomy/taxonomy.py.
Événements (tous préfixés par $ ; les noms sans $ seraient traités comme des événements clients) :
$mcp_tool_call (principal), $mcp_tools_list, $mcp_initialize, $mcp_missing_capability,
$mcp_resource_read / $mcp_resources_list, $mcp_prompt_get / $mcp_prompts_list,
$identify, $exception.
$mcp_initializen'est pas un ancrage de session fiable — mais vérifiez quel serveur vous regardez. La révision du 2026-07-28 supprime la poignée de maininitialize, donc un serveur client sur le chemininstrument()du SDK n'émet rien pour un client stateless. Le propre serveur de PostHog est l'exception :services/mcpdéclenche le même événement$mcp_initializedepuisserver/discoverque depuisinitialize(dispatcher.ts::recordDiscoveryRequestcouvre les deux points d'entrée), donc l'événement est présent dans les données dogfood de toute façon. Traitez son absence comme significative uniquement pour les serveurs clients. L'ancrage réel est maintenant le handle de conversation quand le serveur l'active — references/stateless-and-sessions.md couvre l'ordre de résolution et le protocole de livraison. Conséquence directe, pour les serveurs clients uniquement :frontend/mcpAnalyticsOnboardingLogic.tsdérivehas_initializede cet événement, donc un serveur client stateless se lit commenot-instrumentedjusqu'à son premier appel d'outil. L'onboarding se termine quand même —hasToolCallest vérifié en premier, dans ce sélecteur etstatusFromProbeDefinitions. Les projets surservices/mcpne sont pas affectés, puisqu'il émet l'événement depuisserver/discover.
Les tables de propriétés complètes — divisées par provenance (émis par SDK vs estampillé par le propre serveur de PostHog vs mode exec uniquement), les distinctions d'identifiants, le comportement du SDK par version, et la parité TypeScript/Python — sont dans references/event-vocabulary.md. Lisez cela avant d'écrire des requêtes ou de changer ce qui est capturé.
Lire les données
Préférez les skills d'analyse dédiées à HogQL écrit à la main ; elles encodent déjà le mode exec et la gestion harness que les règles strictes 1 et 4 décrivent :
exploring-mcp-tool-usage— porte d'entrée / routeur : prend une large question « comment va mon MCP » et dépêche vers le bon outil typé ou skill ciblé. Commencez ici.exploring-mcp-tool-quality— taux d'erreur, latence, portée, outils défaillants et lents.exploring-mcp-sessions— liste des sessions, appels d'outils par session, intention.exploring-mcp-intent-clusters— clusters « que les gens essaient de faire ».improving-mcp-tools— boucle de campagne évaluée : mesurer, faire un correctif borné, re-mesurer.
Les outils typés existent pour la plupart des questions et sont préférables au SQL brut : posthog:query-mcp-tool-stats,
-daily-stats, -failures, -failure-occurrences, -descriptions, -neighbors,
-sample-intents, -top-users, et posthog:query-mcp-harness-breakdown, plus les outils de session (posthog:mcp-analytics-sessions-list / -tool-calls / -generate-intent) et les outils de cluster d'intention. Ils sont déclarés dans products/mcp_analytics/mcp/tools.yaml.
Harness est l'étiquette conviviale pour le client appelant (Claude Code, Cursor, ChatGPT, Windsurf, et environ 30 autres buckets). Il est résolu à l'interrogation uniquement, sans colonne stockée : mcp_harness.py::HARNESS_TOKEN_SQL choisit le signal le plus fort disponible dans l'ordre de priorité, sur exactement trois propriétés — celles que les schémas SDK peuvent émettre ($mcp_vendor_client, avec le non-$ legacy mcp_vendor_client coalesced pour les lignes historiques -> surface user-agent Claude Code -> user-agent Grok -> $mcp_client_name -> token user-agent générique, tous deux depuis $mcp_client_user_agent), puis harness_label_sql() les bucketise (ou harness_label_or_token_sql(), qui nomme un client non reconnu verbatim au lieu de l'effondrer en « Other » — utilisez-le pour les listes top-N classées, jamais où les étiquettes alimentent un tableau ou un GROUP BY sans limite).
$mcp_client_name est une entrée mi-priorité, pas un synonyme de harness — le regrouper directement donne une réponse différente et plus désordonnée : sur les anciennes versions du SDK il ne voyageait que sur l'initialize de la session, et les surfaces mutualisées d'Anthropic se rapportent elles-mêmes avec un générique Anthropic/ClaudeAI que seul l'en-tête vendor peut désambigüiser. Les mcp_session_client_name et $mcp_oauth_client_name uniquement dogfood ne sont plus lus par la résolution harness — le serveur replie le nom épinglé par session dans $mcp_client_name par événement, et aucune propriété n'a jamais résolu un événement seul. Pour le SQL écrit à la main, models-mcp.md porte la référence de propriété et les exemples de requête fonctionnants.
Le pipeline, et où chaque étape se casse
- Instrumenter -> le serveur émet des événements
$mcp_*via le SDK. Se casse : gestionnaires non enveloppés (instrument()est idempotent et se dégrade en un no-op silencieux en cas d'échec) ; un serveur STDIO écrivant sur stdout avecconsole.*(corrompt le flux du protocole — connectez unlogger) ; un client posthog-node désactivé ou mal configuré. Pourservices/mcpil y a un seul chemin d'émission :src/hono/analytics.ts+src/hono/tool-executor.ts->getPostHogClient()(src/lib/posthog/client.ts) ->PostHogMCP, consommé via l'alias de dépendance@posthog/mcp-analytics(l'alias importe quand on grep les imports). Le shim MCPcat/AgentCat legacy et le shim de transition qui émettait doublement le non-$mcp_tool_call/mcp_initializeont tous deux été supprimés et sont testés en régression dansservices/mcp/tests/hono/.services/mcp/ARCHITECTURE.mddécrit toujours l'ancien design multi-émetteur et référence unlib/mcpcat.tssupprimé — faites confiance à la source, pas à ce document. - Ingérer -> les événements atterrissent dans ClickHouse
events. Se casse : problèmes ordinaires d'ingestion et de quota ;$session_idnon matérialisé, ce qui casse le regroupement de session. - Liste des sessions ->
backend/logic.py::list_mcp_sessionsexécute HogQL sur une fenêtre par défaut de 7 jours (DEFAULT_SESSIONS_DATE_FROM, résolu viaQueryDateRangeavec un tampon de chevauchement d'un jour de chaque côté) et cache pendant 30s (SESSIONS_CACHE_TTL_SECONDS). Se casse : tout en dehors de la fenêtre n'est simplement pas là ; les résultats peuvent être périmés jusqu'à 30s. - Graphiques et qualité d'outil -> sous-classes
AnalyticsQueryRunnertypées dansbackend/hogql_queries/(base.py,dashboard_series.py,harness_breakdown.py,tool_quality_tables.py,tool_tables.py), dépêchées via le point de terminaison générique/query/et énumérées dansbackend/facade/queries.py, avec schémas dansposthog/schema.py. Gate :hogql_queries/base.py::validate_mcp_analytics_access— le flag de fonctionnalité plus la ressource RBACmcp_analytics. Se casse : flag désactivé, RBAC refuse, ou les règles strictes 1-3 ignorées. - Génération d'intention (à la demande, par session) -> collecter les valeurs
$mcp_intent-> un résumé LLM d'au maximum deux phrases -> Postgresposthog_mcp_session. Un deuxième chemin au niveau du projet produit le digest d'intention / thèmes avec sortie structurée, limitée parMAX_DIGEST_THEMES;resolve_themes()dérive chaque champ comptable du corpus pour que le modèle ne puisse pas inventer les nombres. Les constantes du modèle vivent dansbackend/intent_generation.py. Se casse : aucun$mcp_intentcapturé du tout (l'agent n'a jamais rempli l'argumentcontextinjecté et aucunintentFallbackn'a été configuré), donc il n'y a rien à résumer ; problèmes de clé LLM ou de quota. - Clustering d'intention (derrière
mcp-analytics-intent-routing) -> embed (en cache dansMCPIntentEmbeddingCache) -> clustering agglomératif (cosinus, liaison moyenne,DEFAULT_DISTANCE_THRESHOLD) -> JSONBMCPIntentClusterSnapshot. Temporal end-to-end, pas de Celery. Recompute à la demande (trigger_intent_cluster_recompute, sérialisé avecselect_for_update()et un id de workflow déterministe par équipe) et la commande de gestioncluster_mcp_intentsdémarrent tous deux le workflow ; la run quotidienne est une Schedule Temporal (posthog/temporal/mcp_analytics/intent_clustering/schedule.py, derrière le flagmcp-analytics-clustering-schedule) qui déclencheIntentClusteringCoordinatorWorkflow, qui se disperse en un workflow enfant par équipe. Deux limites vous surprendront :MAX_SNAPSHOT_CLUSTERS(les snapshots gardent seulement les clusters supérieurs par volume, appliquées à l'écriture et de nouveau à la lecture) etMAX_QUERY_ROWS. Notez que le corpus ne dépend pas de l'étape 5 :fetch_intent_corpusprend le premier$mcp_intentde chaque session directement depuis ClickHouse et ne bascule que vers le résumé LLM stocké où l'un existe. Donc un projet peut clustering sans aucun résumé généré. Se casse : les clusters vides signifient presque toujours pas de valeurs$mcp_intentdans la fenêtre lookback (vérifiez le corpus avant de chasser la génération de résumé) ; flag de schedule désactivé ; embeddings périmés. Vérifiez aussi la liste blanche —intent_clustering/team_discovery.pyretourne actuellement unGUARANTEED_TEAM_IDS = [2]codé en dur, donc la schedule quotidienne couvre seulement le propre projet de PostHog et activer le flag ailleurs produit quand même rien jusqu'à ce que ça change. - Servir -> viewsets DRF à
/api/projects/{id}/mcp_analytics/{sessions,intent_clusters,feedback,missing_capabilities}(routeur dansbackend/presentation/urls.py) plus actions personnalisées (sessions/{id}/tool_calls,sessions/{id}/generate_intent,sessions/intent_digest,sessions/activity_overview,intent_clusters/recompute). Surface parallèle : exécuteurs de l'étape 4, exposés aux agents comme outilsquery-mcp-*. La lecture du cluster d'intention et les points de terminaison de recompute requièrentmcp-analytics-intent-routing; les autres points de terminaison utilisentmcp-analytics. - Frontend -> scène Kea
MCPAnalyticsScene.tsx, avec des onglets énumérés parMCPAnalyticsTabdansmcpAnalyticsSceneLogic.ts: activité, tableau de bord, sessions, qualité d'outil, clustering d'intention, notifications. L'onglet de destination est gated en volume pardashboardStagedansmcpAnalyticsOnboardingLogic.tset s'applique uniquement à la redirection nue/mcp-analytics— les liens profonds et les clics d'onglets explicites ne sont jamais remplacés. L'onglet clustering d'intention, le KPI du tableau de bord et la section cluster de détail d'outil sont tous gatés parmcp-analytics-intent-routing; un lien unflagged direct rend la page standard not-found.- Activité (
earlyData/) : feed live d'appels d'outils plus la carte thèmes d'intention. « Thème » (le digest LLM, onglet Activité) n'est pas « cluster » (le clustering d'embedding, son propre onglet). Confondre les deux est l'erreur la plus commune ici. - Qualité d'outil et le rapport d'outil par outil (
MCPAnalyticsToolDetail.tsx, sa propre scène enregistrée) : filtre de date partagé, drill-down des occurrences de défaillance avec contexte d'erreur copiable, et « créer une tâche de correctif » directement dansproducts/tasks. - Tableau de bord : tuiles
Metriccomposables quill et@posthog/quill-primitives, plus sessions notables sélectionnées par uneNotableRule— donc cette table peut légitimement être courte ou vide. - Notifications : destinations first-party pour événements MCP et rapports IA récurrents (
frontend/notifications/), câblage mince sur la destination hog-function générique et la machinerie d'abonnement.
- Activité (
Modèles Postgres (backend/models.py) : MCPSession (le magasin d'intention),
MCPIntentClusterSnapshot, MCPAnalyticsSubmission (rapports de feedback et de capacités manquantes), MCPIntentEmbeddingCache.
Ensemencement de données locales : ./manage.py seed_mcp_sessions --team-id N (backend/management/commands/), avec --sessions, --min-calls/--max-calls, --days, --missing-capabilities, --seed, et --clear. Les événements ensemencés sont tagués $mcp_seeded donc --clear supprime seulement les données ensemencées.
Quel dépôt changer
| Changement | Dépôt | Workflow |
|---|---|---|
| Comportement SDK, événements, options, instrumentation | PostHog/posthog-js |
Travaillez dans packages/mcp. Exécutez ses tests unitaires, compilez et lintez. Ajoutez un changeset. Livré à npm ; puis mettez à jour l'alias dans services/mcp/package.json pour le récupérer. |
| Tableau de bord, requêtes, clustering, API | ce dépôt | Un nouveau graphique signifie un exécuteur de requête dans backend/hogql_queries/ derrière validate_mcp_analytics_access — jamais un modèle SQL. Respectez les règles strictes 1-3. |
Un nouvel outil agent query-mcp-* |
ce dépôt (deux endroits) | 1) une entrée dans products/mcp_analytics/mcp/tools.yaml avec schema_ref, scopes, description, feature_flag ; 2) le schéma <Name>Query correspondant et <Name>QueryRunner dans backend/hogql_queries/ ; 3) régénérez les gestionnaires d'outils depuis services/mcp (voir ses scripts package.json). Le createQueryWrapper générique gère la forme d'outil — pas de TypeScript écrit à la main. |
| Événements dogfood du propre PostHog | ce dépôt | services/mcp/src/hono/analytics.ts + tool-executor.ts ; client dans src/lib/posthog/client.ts. |
| Docs | PostHog/posthog.com |
Gardez les tables d'événements et de propriétés dans contents/docs/mcp-analytics/events.mdx synchronisées avec both le TypeScript constants.ts et le Python posthog/mcp/constants.py. |
| Le codemod d'installation ou la commande wizard | PostHog/context-mill, PostHog/wizard |
Voir references/wizard-and-onboarding.md — en particulier la règle sur quels changements nécessitent une release wizard et lesquels non. |
Règle générale : un changement sur ce qui est capturé, ou comment les serveurs sont instrumentés appartient aux SDKs. Comment les données sont affichées, agrégées ou clustering appartient à ce produit. Les événements dogfood propres de PostHog appartiennent à services/mcp. Une nouvelle capacité orientée client s'étend généralement sur un SDK plus docs, et le produit aussi si elle a besoin d'une vue.
Le flux d'installation wizard, les canaux de distribution des skills, et l'onboarding dans l'application sont tous dans references/wizard-and-onboarding.md.
État actuel
Vérifié contre master, @posthog/mcp 0.11.7, posthog 7.44.0, et spec MCP 2026-07-28 le 2026-08-25. Traitez les versions et les fils ouverts comme périssables : re-vérifiez packages/mcp/CHANGELOG.md, l'alias épinglé dans services/mcp/package.json, et méga-issue 64016 plutôt que de faire confiance à cette section.
Les deux SDKs parlent maintenant la spec stateless et les SDKs v2 MCP. services/mcp parle les deux dialectes au niveau du protocole (src/lib/stateless-protocol.ts — détection de dialecte par requête, server/discover, pas de création de session pour les clients modernes). Le SDK TypeScript 0.10.9-0.11.7 instrumente les serveurs MCP TypeScript SDK v2 (détection structurelle dans detect.ts, les deux pairs @modelcontextprotocol optionnels), résout l'identité du client et la version du protocole via une chaîne de secours par requête, gate la création de Mcp-Session-Id sur la révision que déclare chaque requête, et capture $mcp_client_user_agent / $mcp_vendor_client. Le SDK Python a rattrapé en posthog 7.40.0-7.42.1 : MCP SDK Python v2, sessions ancrées en conversation compatibles en octets avec TS (derive_session_id_from_conversation), $mcp_error_type / $mcp_error_message typés, et la même capture UA/vendor. Les anciens fils de parité (posthog-python 803 et 830) ont été fermés non fusionnés et supersédés — ne les citez pas comme la source de ce qui a atterri. references/stateless-and-sessions.md est la référence pour tout cela.
Aussi livré : thèmes d'intention structurés, destinations de notification first-party et rapports récurrents, contrôle d'accès mcp_analytics, adoption partagée de ProductEmptyState, drill-down des occurrences de défaillance avec « créer une tâche de correctif », la migration de chaque graphique vers les exécuteurs de requête typés, le seeder de démo, et breakout d'outil interne en mode exec (règle stricte 1).
Ce qui traîne toujours, tous vérifiables dans ce dépôt : l'épingle d'alias services/mcp est 0.10.2 contre un SDK 0.11.7 (règle stricte 5 — aucun correctif côté SDK 0.11.x ou propriété émise par le SDK n'atteint les données dogfood, bien que le serveur indépendamment tamponne $mcp_client_user_agent et le legacy non-$ mcp_vendor_client indépendamment de l'épingle ; la résolution harness lit d'abord le $mcp_vendor_client émis par le SDK et coalescit le nom legacy pour ces lignes) ; l'émetteur de propriété exec est toujours absent de master (règle stricte 1) ; la schedule de clustering couvre toujours seulement GUARANTEED_TEAM_IDS = [2] ; et le produit reste derrière le flag mcp-analytics, donc un projet sans lui ne voit rien.