| autocomplete_communeA | Recherche de communes françaises par nom, code postal ou code INSEE. Idéal pour autocomplétion. Source : geo.api.gouv.fr (DINUM/Etalab). Un (au moins) parmi nom, codePostal, code est requis. Alias acceptés : q/query/search → nom, codepostal/postal_code → codePostal, code_insee/insee → code. |
| get_commune_by_codeA | Récupère une commune par son code INSEE. Retourne un objet LookupResult discriminé par found. found: true → champs commune à plat (nom, codesPostaux, centre…). found: false → { found: false, key, lookupStatus: 'not_found', message } orientant vers autocomplete_commune pour disambiguer. Alias acceptés : code_insee/codeInsee/insee → code. |
| geocode_adresseA | Géocode une adresse française en coordonnées GPS. Source : IGN Géoplateforme (data.geopf.fr). Précision au numéro de rue. Le champ score (0-1) qualifie la fiabilité du match : >= 0.8 fiable, < 0.5 = match douteux (souvent un fallback rue/commune sans rapport avec l'adresse demandée). Le champ booléen confidence_low vaut true dans ce cas : ne PAS utiliser point pour une décision quand confidence_low: true. Le champ type indique aussi la granularité (housenumber > street > locality > municipality). |
| reverse_geocodeA | Géocodage inverse : à partir de coordonnées GPS, retrouve l'adresse la plus proche. Source : IGN Géoplateforme. Couverture France métropolitaine + DOM uniquement : des coordonnées hors zone (ex. New York) ou en pleine mer renvoient null (pas une erreur — c'est l'absence de résultat, pas une panne). |
| populationA | Population d'une COMMUNE (code INSEE 5 car.), d'un DÉPARTEMENT (2-3 car.) OU d'un IRIS infracommunal (9 car.) — granularité auto-détectée par la longueur du code. Retourne un LookupResult discriminé par found. IRIS (9 car., ex 751103701 = commune 75110 + IRIS 3701) : population totale du quartier au Recensement 2022 (champ population, comptes bruts), + libelle, code_commune, type_iris (H/A/D/Z). Source : INSEE RP 2022 (table ingérée, géo 01/01/2024). Maille la plus fine (quartier) pour les villes ; en zone peu dense la commune = 1 IRIS (type_iris Z, code COM+0000). Pour le profil démographique détaillé d'un îlot ou d'un bassin (âge, CSP, familles, revenu), utiliser profil_iris. Commune (5 car., ex 75056 Paris, 13055 Marseille, 2A004 Ajaccio) : PMUN/PCAP/PTOT. Source INSEE Melodi (DS_POPULATIONS_REFERENCE). PMUN = base légale DREES. Commune fusionnée → found: false + orientation autocomplete_commune. INSEE n'expose PAS les arrondissements PLM (75101-75120, 13201-13216, 69381-69389) → passer la commune-mère ou le département. Département (2-3 car., ex 75, 59, 2A, 971) : Mayotte (976) ABSENTE de Melodi → lookupNotFound.
Alias acceptés : code_insee/codeInsee/insee, code_dept/dept/departement/code_departement, code_iris/iris → code. |
| profil_irisA | Profil démographique au grain QUARTIER (IRIS) — la « demande » d'un territoire (âge, CSP, familles, revenu), à croiser avec l'offre de soins pour l'aide à l'implantation. Source : INSEE RP 2022 + FILOSOFI 2021 (tables ingérées, géo 01/01/2024). Retourne un LookupResult discriminé par found. Entrée : EXACTEMENT un de point (lat+lon) OU code_iris (9 car.). rayon_km optionnel (0 < r ≤ 10) → DEUX modes : SANS rayon_km → profil de l'ÎLOT seul (~2000 hab) sous le point / du code. mode: "ilot", revenu_median = médiane réelle de l'îlot. AVEC rayon_km → AGRÉGAT du BASSIN = îlots dont le CENTROÏDE est dans le disque (chaque îlot compté 1 fois). mode: "bassin", population_bassin, nb_iris_agreges, et revenu_median_pondere = PROXY (moyenne pondérée population des médianes des îlots couverts — PAS une vraie médiane de bassin) + couverture {revenu_pct_population, iris_revenu_manquants} car FILOSOFI ne couvre que les communes ≥5000 hab.
Les parts age (part_65_plus/75_plus) et csp (cadres, prof_interm, employés, ouvriers, agriculteurs, artisans_comm, retraités, autres) sont des ratios sur comptes bruts (Σ/Σ). Pour une simple population de commune/dept, utiliser population. not_found motivé si code absent ou point hors métropole / en mer. |
| entreprises_in_radiusA | Recherche d'entreprises françaises avec filtres NAF, code postal, département ou rayon géographique. Couvre tous secteurs (santé via NAF 8690B, 4773Z, 8710A, 8621Z, etc.). Source : DINUM Recherche Entreprises (SIRENE + RNE). Renvoie CA, dirigeants, tranches d'effectif et dates de création. Deux modes EXCLUSIFs (endpoints DINUM distincts) : (1) proximité — lat+lon+radiusKm (optionnellement + naf), résolu nativement via /near_point ; (2) administratif — q (texte libre) et/ou naf + codePostal/departement, via /search. La recherche de proximité ne supporte PAS q ni codePostal/departement (combinaison rejetée avec une erreur explicite : choisir un seul mode). radiusKm borné à 50 km. Réduction de payload (V0.13) : includeDirigeants: false strip la liste des dirigeants RNE de chaque entreprise du résultat — utile en énumération volume (Geo Intel) où les dirigeants ne sont pas exploités et où les groupes type Biogroup peuvent en lister 20+ par entité (gonflement inutile du payload). Défaut true pour préserver le contrat V0.12 (backward-compat strict). |
| entreprise_by_sirenA | Récupère le détail d'une entreprise française par son SIREN (9 chiffres) : raison sociale, NAF, finances historiques, dirigeants, établissements. Source : DINUM Recherche Entreprises. Format de retour : objet LookupResult discriminé par found. found: true → l'entreprise est retournée à plat (champs siren, nomComplet, etablissements, enrichmentStatus, …)
found: false → { found: false, key, lookupStatus: 'not_found' | 'ambiguous', message }. not_found : SIREN non indexé par DINUM (souvent diffusion partielle INSEE — l'entreprise peut quand même exister dans SIRENE). ambiguous : régression API à signaler.
⚠️ Quand found: true, la liste etablissements peut être tronquée. Le champ nombreEtablissements (compté SIRENE) reflète le total réel. Lire enrichmentStatus pour savoir si la liste est complète : success : etablissements contient tous les sites
partial : sites manquants (multi-département ou NAF différent du siège) — voir enrichmentWarning
failed : l'enrichissement a échoué (rate limit, panne API) — seul le siège est listé
not_attempted : entreprise monosite ou data SIRENE manquante
Pour énumération exhaustive multi-département, utiliser entreprises_in_radius par zone géographique. Coût : 1 ou 2 appels API DINUM par invocation (rate limit ~1 req/s effectif). |
| data_freshnessA | Retourne la fraîcheur des dumps de données ingérés côté serveur : FINESS DREES (bimestriel), Annuaire Santé Ameli (hebdomadaire), RPPS / Annuaire Santé ANS (mensuel), Centres de Santé CNAM (hebdomadaire). Pour chaque source : last_success_at ISO timestamp, last_success_row_count, last_attempt_at, last_attempt_status, staleness_days (jours depuis la dernière ingestion réussie), cadence_hint (cadence attendue côté éditeur). Usage typique : avant un audit territorial ou une analyse temporelle, le caller appelle ce tool pour savoir si les données sont à jour. Une staleness_days > 90 côté FINESS = alerte (dernier sync DREES manqué), > 14 côté Ameli = alerte (job hebdo cassé), > 45 côté RPPS = alerte (job mensuel cassé), > 14 côté CDS = alerte (job hebdo cassé). Les sources LIVE (DINUM Recherche Entreprises, INSEE SIRENE V3.11, ANS FHIR live) ne sont PAS listées ici puisqu'elles n'ont pas de cycle d'ingestion — leur fraîcheur est celle des API amont (live, ~secondes). Cache serveur : 5 minutes. Coût : 1 SELECT sur ingest_log au pire (sinon hit cache). |
| compare_raison_sociale_finess_vs_rppsA | Compare la raison sociale FINESS DREES vs RPPS / Annuaire Santé ANS pour un même num_finess. Primitive brute SANS interprétation métier — retourne juste les deux libellés + un statut de comparaison. Le caller décide quoi faire de la divergence. Utilité : RPPS reflète souvent plus rapidement les rebrandings post-M&A que FINESS DREES (ex: un site racheté reste 'DIAGNOVIE' chez DREES alors qu'il est déjà 'BIOGROUP NORD' chez l'ANS). Ce tool expose la divergence factuelle ; il NE DIT PAS qui a racheté qui (ça repose sur de la connaissance d'enseignes commerciales non publique). Statut renvoyé (champ statut présent uniquement sur la branche found: true) : exact_match : FINESS et ≥1 RPPS sont strictement égaux après normalisation
divergent_after_normalization : aucune RPPS ne matche FINESS — vraie divergence
rpps_absent : aucune RPPS n'a déclaré ce FINESS (pivot impossible)
Format : objet LookupResult discriminé par found. Quand num_finess est absent de FINESS DREES, le tool retourne {found: false, lookupStatus: 'not_found', message, ...} — il n'y a PAS de champ statut dans ce cas. |
| compare_adresse_cnam_vs_finessA | Compare l'adresse d'un centre de santé côté CNAM (Annuaire santé Ameli) vs FINESS DREES pour un même num_finess. Primitive brute SANS interprétation métier — retourne les deux adresses, un score_dice (0..1, informatif ; null si non comparable car finess_absent) et un statut. Le caller décide quoi faire de la divergence. Utilité : signaler un déménagement propagé par une source mais pas (encore) par l'autre (ex: CNAM '5 RUE DE L'ARQUEBUSE AUTUN' vs FINESS '15 BD BERNARD GIBERSTEIN AUTUN' pour le même FINESS). Équivalent côté centre de santé de compare_raison_sociale_finess_vs_rpps. Statut (présent uniquement sur found: true) : match : adresses strictement égales après normalisation
match_after_abbreviation_normalization : égales après expansion des abréviations de voie FR (R/RUE, BD/BOULEVARD, AV/AVENUE…) — MÊME adresse, simple abréviation DREES vs CNAM, PAS un déménagement
divergent_after_normalization : adresses réellement différentes (déménagement non synchronisé entre sources)
finess_absent : le CDS existe côté CNAM mais le num_finess est absent de FINESS DREES (latence sync bimensuelle)
Format : objet LookupResult discriminé par found. Si le num_finess n'est PAS un centre de santé CNAM, le tool retourne {found: false, lookupStatus: 'not_found', message} (utiliser etablissement_by_finess pour un établissement non-CDS). |
| historique_etablissementA | Reconstitue la timeline complète d'un établissement de santé (ouvertures, fermetures, changements de NAF/enseigne) en croisant FINESS DREES ↔ resolver SIRET (RPPS + DINUM) ↔ SIRENE INSEE V3.11. Lit les periodesEtablissement complètes pour chaque SIRET candidat. V0.7.0 : SIRET candidats élargis via le resolver — inclut désormais les SIRET fermés du SIREN parent qui matchent l'adresse FINESS (invisibles côté RPPS seul). Permet de tracer la fermeture exacte d'un site même quand FINESS le liste encore actif. Usage typique : Tracer l'historique d'un site après une fusion-acquisition Identifier la date de fermeture exacte d'un SIRET encore listé actif côté FINESS Comprendre une cascade de rebrandings via les changements de enseigne1Etablissement au fil des périodes
Format : objet LookupResult. Quand found: true, retourne finess (vue DREES synthétique) + siret_timelines (1 entrée par SIRET candidat avec periodes chronologiques). Coût : 1 RPC FINESS + 1 SELECT rpps + N appels DINUM + N appels INSEE en parallèle (N ≤ 5 typiquement). Pas de cache. |
| reconcilier_finess_sireneA | Croise FINESS DREES ↔ SIRENE INSEE V3.11 et calcule un score de cohérence (Sørensen-Dice sur bigrammes) pour chaque SIRET candidat. Utile pour confirmer/infirmer un appariement num_finess ↔ SIRET avant prospection ou cross-check qualité. Logique : Récupère FINESS (raison sociale + adresse libellée) Récupère SIRET candidats via la table RPPS Pour chaque SIRET, lookup SIRENE puis calcule 3 sous-scores : nom : Dice sur raison sociale (FINESS vs SIRENE.uniteLegale)
adresse : Dice sur adresse complète
telephone : binaire 0/1 (toujours 0 actuellement : SIRENE n'expose pas le tel)
Score global = pondération (nom 0.5, adresse 0.4, tel 0.1) Verdict brut : match (≥0.8) / partial (0.5..0.8) / mismatch (<0.5)
Algorithme PUBLIC (Sørensen-Dice est dans la littérature depuis 1948). Aucune valeur ajoutée Unilabs ici — c'est une primitive ouverte. La connaissance propriétaire (mapping enseignes ↔ SELAS) reste côté Geo Intel. Format : objet LookupResult. Quand found: true, retourne { num_finess, candidates, skipped } : candidates : tableau trié par score_global décroissant (meilleur match en premier)
skipped : SIRET candidats qu'on n'a PAS pu réconcilier (lookup SIRENE rejected ou not_found) avec la reason. Permet au caller de distinguer 'aucun SIRET candidat trouvé' (found: false LookupResult.not_found) de 'N SIRETs candidats mais tous rejetés par SIRENE' (candidates: [] + skipped: [...]).
|
| verifier_site_actifA | Vérifie si un établissement de santé FINESS est encore en activité en croisant FINESS DREES ↔ RPPS (pivot SIRET) ↔ DINUM (liste complète des SIRET du SIREN, incluant les fermés). Détecte les SIRET fermés encore listés actifs côté FINESS (DREES a 1-2 mois de retard). V0.16 — fix succession M&A : quand un site a changé d'exploitant (rachat), l'ancien SIRET fermé et le repreneur actif coexistent à la même adresse. Le resolver privilégie désormais le SIRET ACTIF co-localisé avec le FINESS (distance géodésique ≤ 100 m, recalibré V0.16.1 — le géocodage DREES place le point FINESS à plusieurs dizaines de mètres de l'adresse réelle) — avant, le verdict pouvait être ferme à tort, le best_match étant choisi sur la seule ressemblance d'adresse. Parmi les co-localisés, seul l'actif de la bande la plus proche prime : un voisin actif d'une autre adresse ne bascule pas le verdict. Un site RÉELLEMENT fermé reste ferme (aucun SIRET actif co-localisé). Logique : Lookup FINESS pour récupérer raison sociale + adresse + téléphone DREES SIRET candidats via le resolver : pivot RPPS, puis fallback géo DINUM /near_point (récupère TOUS les SIRET autour de l'adresse FINESS, actifs ET fermés — capte le repreneur invisible côté RPPS) best_match = le SIRET ACTIF co-localisé avec le FINESS s'il en existe un ; sinon le meilleur candidat (possiblement fermé). La co-localisation est une distance géo, pas un score textuel.
2 verdicts distincts :
verdict_site (actif / ferme / indetermine) : basé sur best_match.actif. C'est le verdict qui compte pour un audit territorial.
verdict_groupe (actif / ferme / indetermine) : basé sur l'état admin de l'UL parente (champ actif DINUM). Une UL active peut très bien avoir un site fermé.
Format de retour : objet LookupResult discriminé par found. Quand found: true, le payload contient finess (vue DREES), candidates (liste enrichie — chaque candidat porte distance_finess_m), best_match, sirens_explored, verdict_site, verdict_groupe, succession ({ detected, exploitants_precedents } — les SIRET fermés co-localisés avec le repreneur ; fait brut, le tool ne qualifie PAS de « rachat »), explication. Quand num_finess est absent de FINESS DREES, le tool retourne {found: false, lookupStatus: 'not_found', message, ...}. Coût : 1 RPC FINESS + 1 SELECT rpps + N appels DINUM (N = nombre de SIREN distincts, typiquement 1). DINUM gère son propre fallback INSEE V3.11 pour les SIREN diffusion partielle. |
| etablissement_by_siretA | Récupère le détail d'un établissement par son SIRET (14 chiffres) via l'API SIRENE INSEE V3.11 : raison sociale de l'unité légale, enseigne commerciale, NAF de l'établissement, dates de création/fermeture, statut administratif actif/fermé, adresse complète, tranche d'effectif. Source : SIRENE INSEE V3.11 (api.insee.fr). Format de retour : objet LookupResult discriminé par found. found: true → établissement à plat (siret, siren, actif, dateFermeture, enseigne, adresse, …)
found: false → { found: false, key, lookupStatus: 'not_found', message }. Cas typiques : clé INSEE_SIRENE_API_KEY non configurée côté serveur (message explicite), SIRET inexistant SIRENE, diffusion partielle INSEE.
⚠️ Différence avec entreprise_by_siren : ce tool renvoie UN établissement précis (un site), alors que entreprise_by_siren renvoie l'unité légale + sa liste d'établissements. Pour détecter un SIRET fermé encore listé actif côté FINESS, lire actif: false + dateFermeture. Pas de coords : l'endpoint INSEE /siret/<siret> ne renvoie pas les coordonnées GPS. Pour géolocaliser, croiser avec geocode_adresse côté caller ou utiliser entreprises_in_radius. Rate limit INSEE : 30 req/min (retry-after géré côté serveur). |
| etablissements_finess_in_radiusA | Recherche d'établissements de santé FINESS dans un rayon géographique (PostGIS ST_DWithin). Filtrable par familles. 24 valeurs disponibles : mco, ssr, sld, had, psychiatrie, dialyse, ambulatoire, labo, imagerie, pharmacie, msp_cpts, ehpad, residence_autonomie, senior_accompagnement, ssiad, aide_domicile, handicap_enfants, handicap_adultes, addictologie, enfance_protection, pmi, hebergement_social, prevention_sante, groupement. Source : FINESS / DREES (dump CSV ingéré localement). Note : champ email toujours null (non exposé par FINESS public). Note : raison_sociale provient du dump DREES qui abrège les libellés longs (~38 car. max, ex 'CERBALLIANCE HA' pour 'CERBALLIANCE HAZEBROUCK'). Pour le nom légal complet, cross-check via SIREN/SIRET (entreprise_by_siren / etablissement_by_siret). Lentille : un filtre familles compte les établissements par leur catégorie FINESS principale. Les activités hébergées dans un site d'une autre catégorie (ex. plateau de biologie d'un hôpital sous famille=labo) ne sont pas comptées — voir le champ perimetre de la réponse. La famille imagerie renvoie le plus souvent 0 résultat (FINESS ne répertorie pas les cabinets d'imagerie). |
| etablissements_finess_by_categorieA | Liste des établissements FINESS par famille, avec filtre département ou commune optionnel. Pas de rayon — pour énumération exhaustive d'une zone administrative. 24 familles disponibles : mco, ssr, sld, had, psychiatrie, dialyse, ambulatoire, labo, imagerie, pharmacie, msp_cpts, ehpad, residence_autonomie, senior_accompagnement, ssiad, aide_domicile, handicap_enfants, handicap_adultes, addictologie, enfance_protection, pmi, hebergement_social, prevention_sante, groupement. V0.19.0 : accepte nom_commune (string) comme alternative à code_insee (résolu via geo.api.gouv.fr). XOR strict — passer SOIT departement SOIT code_insee SOIT nom_commune (combinable avec departement qui agit alors comme hint de désambiguïsation pour homonymes type "Saint-Martin"). Aucun param zone = France entière (acceptée). Source : FINESS / DREES. Note : champ email toujours null (non exposé par FINESS public). Note : raison_sociale provient du dump DREES qui abrège les libellés longs (~38 car. max, ex 'CERBALLIANCE HA' pour 'CERBALLIANCE HAZEBROUCK'). Pour le nom légal complet, cross-check via SIREN/SIRET (entreprise_by_siren / etablissement_by_siret). Lentille : un filtre familles compte les établissements par leur catégorie FINESS principale. Les activités hébergées dans un site d'une autre catégorie (ex. plateau de biologie d'un hôpital sous famille=labo) ne sont pas comptées — voir le champ perimetre de la réponse. La famille imagerie renvoie le plus souvent 0 résultat (FINESS ne répertorie pas les cabinets d'imagerie). |
| etablissement_by_finessA | Récupère le détail complet d'un établissement de santé par son numéro FINESS (9 chiffres) : raison sociale, catégorie + famille, adresse complète (voie + CP + ville + code INSEE + département), coordonnées GPS, téléphone. Retourne un objet LookupResult discriminé par found. found: true → champs FINESS à plat. found: false → { found: false, key, lookupStatus: 'not_found', message }. Le référentiel DREES a 1-2 mois de retard sur le terrain : pour des structures émergentes (CPTS récentes, MSP en agrément), cross-check ARS / Service Public. Source : FINESS / DREES. Note : champ email toujours null (non exposé par FINESS public). Note : raison_sociale provient du dump DREES qui abrège les libellés longs (~38 car. max, ex 'CERBALLIANCE HA' pour 'CERBALLIANCE HAZEBROUCK'). Pour le nom légal complet, cross-check via SIREN/SIRET (entreprise_by_siren / etablissement_by_siret). |
| centres_sante_in_radiusA | Recherche des Centres de Santé (CDS) dans un rayon géographique (PostGIS ST_DWithin). Source : Annuaire santé Ameli, Assurance Maladie (mention obligatoire L.1461-2 CSP — sync hebdomadaire CNAM). Différenciateur métier vs etablissements_finess_in_radius filtré famille=124 : expose carte_vitale, APCV, spécialités exercées sur place (Annexe A nomenclature CNAM, ~70 codes). CDS = structures de soins ambulatoires non lucratives encadrées L.6323-1 CSP (associations, mutuelles, communes, hôpitaux). Volume ~3K en France. Filtres : specialite_codes : array Annexe A (ex: ['01'] médecine générale, ['53'] dentaire). Match any-of — retourne les CDS qui exercent AU MOINS UNE des spécialités demandées.
accepte_carte_vitale : true / false / omis. Quasi-totalité accepte CV en pratique → filtre surtout utile en false pour audits.
type_etab_codes : ['124'] CDS standard, ['125'] CDS dentaire (deprecated CNAM, en voie d'extinction).
Coords = centroïde commune (~3 km moyenne) — pour précision adresse, pivoter via etab_finess retourné avec etablissement_by_finess. PAS d'horaires/tarifs/secteur 1/2 (retirés du nouvel annuaire CNAM post-2025). Alias acceptés : radius/radius_meters → radius_km, latitude/longitude → lat/lon. |
| centres_sante_by_finessA | Récupère le détail d'un Centre de Santé (CDS) par son numéro FINESS. Différenciateur métier vs etablissement_by_finess : expose carte_vitale, APCV, et spécialités exercées sur place (Annexe A CNAM). Retourne un LookupResult discriminé par found. found: true → payload CDS complet (raison sociale, accepte_carte_vitale/apcv, specialites.codes/libelles alignés, type_etab 124/125, adresse, coords centroïde commune, telephone). found: false → {found: false, key, lookupStatus: 'not_found', message} quand le numéro FINESS pointe vers une structure non-CDS (hôpital, EHPAD, labo) ou un CDS très récent (CNAM latence ~1 sem).
Source : Annuaire santé Ameli, Assurance Maladie (sync hebdomadaire CNAM, mention obligatoire L.1461-2 CSP). Pour les structures non-CDS, utiliser etablissement_by_finess. Alias acceptés : numFiness/finess/etab_finess → num_finess. |
| professionnels_in_radiusA | Recherche de professionnels de santé libéraux conventionnés dans un rayon géographique. Précision géo HYBRIDE depuis le géocodage BAN (Chantier C) : ~77 % des PS sont géolocalisés à l'adresse précise (rue/bâtiment, distance_km exacte au m près), ~23 % restent au centroïde commune (~3 km, repli pour adresses non géocodables — DROM, Monaco, CEDEX, lieux-dits). Lire geo_precision PAR résultat — ne pas présumer une précision uniforme. Codes type_ps Ameli présents en base (3) : '1' médecins, '2' auxiliaires médicaux (fourre-tout : IDE, kinés, sages-femmes, podologues, orthophonistes, orthoptistes, IPA), '5' chirurgiens-dentistes. Pour cibler une profession précise (ex: IDE seuls, kinés seuls, podologues seuls), passer par specialite_codes plutôt que type_ps_codes qui ratisse plus large. Liste exhaustive des codes spécialité disponibles via le tool lister_nomenclature(referentiel:'ameli_specialites'). Multi-sites : par défaut un PS exerçant sur N adresses apparaît N fois — utiliser dedupe_by_ps=true pour regrouper par praticien et lister les sites en sous-objet. Distance retournée en km vol d'oiseau (haversine PostGIS) — pour distance routière, croiser avec un service externe (OSRM, ORS). Chaque PS géolocalisé porte geo_precision ∈ {"adresse", "centroide_commune"} : "adresse" = coords BAN précises, distance_km exacte, classement individuel fiable ; "centroide_commune" = ~3 km, distance_km IDENTIQUE pour tous les PS d'une même commune (non discriminante intra-commune — filtre de zone uniquement, pas de classement/choix d'un PS individuel). Param precise_only (défaut false) : à true, exclut les PS au centroïde commune et ne renvoie que les ~77 % géocodés à l'adresse BAN (distance_km exacte) — recommandé pour les rayons courts (<3 km) et le classement intra-commune. PÉRIMÈTRE : libéraux conventionnés UNIQUEMENT. HORS PÉRIMÈTRE : médecins exclusivement hospitaliers/salariés, biologistes médicaux salariés en LBM, anatomopathologistes hospitaliers, médecins du travail, médecine légale. Pour effectifs tous statuts, voir Annuaire Santé ANS (RPPS, esante.gouv.fr) — non couvert par ce serveur. Source : Annuaire santé Ameli (Assurance Maladie), MAJ hebdomadaire. Réutilisation soumise à l'art. L.1461-2 CSP — citer la source et la date de sync. |
| professionnels_par_specialite_deptA | Liste des professionnels de santé libéraux conventionnés d'un département, avec filtres optionnels par spécialité ou type de PS. Pour énumération administrative — pas de rayon. Codes type_ps Ameli présents en base (3) : '1' médecins, '2' auxiliaires médicaux (fourre-tout : IDE, kinés, sages-femmes, podologues, orthophonistes, orthoptistes, IPA), '5' chirurgiens-dentistes. Pour cibler une profession précise (ex: IDE seuls), passer par specialite_code plutôt que type_ps_code qui ratisse plus large. Liste exhaustive des codes spécialité disponibles via le tool lister_nomenclature(referentiel:'ameli_specialites'). Pagination : utiliser offset pour récupérer les pages suivantes quand truncated=true. Multi-sites : utiliser dedupe_by_ps=true pour regrouper par praticien. PÉRIMÈTRE : libéraux conventionnés UNIQUEMENT. HORS PÉRIMÈTRE : médecins exclusivement hospitaliers/salariés, biologistes médicaux salariés en LBM, anatomopathologistes hospitaliers, médecins du travail, médecine légale. Pour effectifs tous statuts, voir Annuaire Santé ANS (RPPS, esante.gouv.fr) — non couvert par ce serveur. Source : Annuaire santé Ameli (Assurance Maladie), MAJ hebdomadaire. Réutilisation soumise à l'art. L.1461-2 CSP — citer la source et la date de sync. |
| lister_nomenclatureA | Découverte des nomenclatures de codes du serveur (tool unique paramétré par referentiel) — à appeler avant de filtrer un autre tool plutôt que deviner les codes. ⚠️ Les 3 nomenclatures sont DISTINCTES : un même nombre y désigne des choses différentes (ex '10' = Médecin côté ANS, Neurochirurgien côté Ameli). Ne JAMAIS passer un code d'un référentiel à un paramètre d'un autre — le filtre renverrait vide sans erreur. referentiel :
ameli_specialites — codes specialite_code Ameli (libéraux conventionnés Assurance Maladie / CNAM) : libellé natif, type_ps_code de rattachement, count, libelle_clarifie (désambigüise les libellés partagés, ex "Médecin généraliste" = 01/22/23 ; "Psychiatre" = 33/75), is_libelle_partage. Pour filtrer professionnels_in_radius / professionnels_par_specialite_dept (param specialite_code(s)).
ameli_types_ps — codes type_ps Ameli : libelle_source, libelle_clarifie (résout l'ambiguïté du code "2" fourre-tout), count, et specialites_presentes (spécialités regroupées). Payload léger via include_specialites: false (→ nb_specialites).
rpps_savoir_faire — spécialités médicales savoir_faire_code RPPS / Annuaire Santé ANS (ex 'SM04' Cardiologie). Pour filtrer densite_sante (cible professionnels) / professionnels_rpps_*. Filtre par profession_code (défaut '10' Médecin ; string vide ou 'null' = tous savoir_faire).
Paginé : limit (défaut 50), réponse expose total et truncated. PÉRIMÈTRE : libéraux conventionnés UNIQUEMENT. HORS PÉRIMÈTRE : médecins exclusivement hospitaliers/salariés, biologistes médicaux salariés en LBM, anatomopathologistes hospitaliers, médecins du travail, médecine légale. Pour effectifs tous statuts, voir Annuaire Santé ANS (RPPS, esante.gouv.fr) — non couvert par ce serveur. Source : Annuaire santé Ameli (Assurance Maladie), MAJ hebdomadaire. Réutilisation soumise à l'art. L.1461-2 CSP — citer la source et la date de sync. |
| professionnels_rpps_in_radiusA | Trouve les PS dans un rayon via RPPS (Annuaire Santé ANS — tous statuts : libéraux + salariés + mixtes + remplaçants ; vs professionnels_in_radius Ameli = libéraux conventionnés seuls). Param critique precise_only — Défaut false (mode hybride). À true : ne renvoie que les PS géolocalisés précisément (distance_km exacte au m près) — recommandé pour rayons courts (<3 km), classement intra-commune, "PS à <500 m d'une adresse". Chaque résultat porte geo_precision ∈ : "adresse" — coords BAN rue/lieu-dit/bâtiment, distance_km exacte.
"etablissement_finess" — coords du site FINESS (via num_finess), distance_km exacte au site.
"centroide_commune" — centroïde commune (~3 km), distance_km IDENTIQUE pour tous les PS de la commune — ne PAS l'utiliser pour classer individuellement, seulement comme filtre de zone.
Couverture actuelle : ~68,5 % précis, ~31,5 % centroide_commune résiduel. Mode hybride = précis (granularité adresse) + centroïde (granularité commune) fusionnés et triés globalement par distance_km. Filtres : profession_codes (ex: ["10"] Médecin, ["60"] Infirmier), savoir_faire_codes (spécialité fine DES/DESC), mode_exercice_codes. Codes mode_exercice ANS : L libéral, S salarié, M mixte, R remplaçant, B bénévole, A autre. Catégorie par défaut : Civil (C, ~97 % — libéraux, salariés privés, hospitaliers contractuels). Opt-in : include_agents_publics: true ajoute Agents publics (M, ~0,3 % — PH titulaires, ARS, CNAM, Éducation nationale, PMI, militaires SSA) ; include_etudiants: true ajoute Étudiants (E, ~2,5 % — internes, externes, élèves IDE/SF). Réf : https://mos.esante.gouv.fr/NOS/TRE_R09-CategorieProfessionnelle/. ATTENTION nomenclatures : les codes ANS (profession_code, savoir_faire_code) sont une nomenclature DISTINCTE des codes Ameli (specialite_code, type_ps_code) — un même nombre désigne des choses différentes (ex: '10' = Médecin côté ANS, Neurochirurgien côté Ameli). Ne JAMAIS passer un code Ameli à un paramètre ANS : le filtre renverrait vide sans erreur. Découvrir les codes ANS via lister_nomenclature(referentiel:'rpps_savoir_faire'). Source : Annuaire Santé, Agence du Numérique en Santé (ANS) — Licence Ouverte v2.0 |
| professionnels_rpps_par_deptA | Liste tous les PS d'un département via RPPS (libéraux + salariés). Pour les libéraux conventionnés uniquement, préférer professionnels_par_specialite_dept (Ameli). Re-paginer via offset tant que truncated=true. Chaque résultat géolocalisé porte geo_precision ∈ {"adresse", "etablissement_finess", "centroide_commune"} — lire ce champ pour évaluer la fiabilité des coords (précise BAN/FINESS au m près vs centroïde commune ~3 km, non discriminant intra-commune). Filtres optionnels : profession_code, savoir_faire_code, mode_exercice_code. Catégorie par défaut : Civil (C, ~97 % — libéraux, salariés privés, hospitaliers contractuels). Opt-in : include_agents_publics: true ajoute Agents publics (M, ~0,3 % — PH titulaires, ARS, CNAM, Éducation nationale, PMI, militaires SSA) ; include_etudiants: true ajoute Étudiants (E, ~2,5 % — internes, externes, élèves IDE/SF). Réf : https://mos.esante.gouv.fr/NOS/TRE_R09-CategorieProfessionnelle/. ATTENTION nomenclatures : les codes ANS (profession_code, savoir_faire_code) sont une nomenclature DISTINCTE des codes Ameli (specialite_code, type_ps_code) — un même nombre désigne des choses différentes (ex: '10' = Médecin côté ANS, Neurochirurgien côté Ameli). Ne JAMAIS passer un code Ameli à un paramètre ANS : le filtre renverrait vide sans erreur. Découvrir les codes ANS via lister_nomenclature(referentiel:'rpps_savoir_faire'). Source : Annuaire Santé, Agence du Numérique en Santé (ANS) — Licence Ouverte v2.0 |
| rpps_dans_etablissementA | Liste les PS rattachés à un établissement FINESS (num_finess 9 chiffres). Pivot RPPS↔FINESS — répond à "qui travaille dans ce labo / hôpital / clinique ?". Le mode_exercice distingue les libéraux exerçant sur place (vacations) des salariés. Couverture : RPPS expose ce lien quand le PS l'a déclaré ; salariés CH/CHU/cliniques bien couverts. Sortie compacte : coords et distance_km sont null (le tool est par établissement, pas spatial — pour la géoloc, pivoter via etablissement_by_finess sur le num_finess). Catégorie par défaut : Civil (C, ~97 % — libéraux, salariés privés, hospitaliers contractuels). Opt-in : include_agents_publics: true ajoute Agents publics (M, ~0,3 % — PH titulaires, ARS, CNAM, Éducation nationale, PMI, militaires SSA) ; include_etudiants: true ajoute Étudiants (E, ~2,5 % — internes, externes, élèves IDE/SF). Réf : https://mos.esante.gouv.fr/NOS/TRE_R09-CategorieProfessionnelle/. Source : Annuaire Santé, Agence du Numérique en Santé (ANS) — Licence Ouverte v2.0 |
| densite_santeA | Densité de santé pour 100 000 habitants — cible: professionnels (RPPS) OU cible: etablissements (FINESS). Niveau département (code_dept) OU commune (code_insee / nom_commune). Exactement un scope des trois requis. Croise le count (RPPS ou FINESS) et INSEE Melodi (population municipale PMUN, recensement 2023). cible='professionnels' (RPPS) — méthodo DREES par défaut : médecins (profession_code='10') en activité régulière (mode_exercice L, S, M), hors étudiants. Filtres : profession_code (60 infirmier, 21 pharmacien, 50 sage-femme…), savoir_faire_code (ex 'SM04' Cardiologie — 'SM02' = Anesthésie-réanimation ; voir lister_nomenclature referentiel rpps_savoir_faire), mode_exercice_codes (['L'] = libéraux seuls). cible='etablissements' (FINESS) — famille OBLIGATOIRE : labo, pharmacie, ehpad, mco, ssr, psychiatrie, dialyse, imagerie, had, msp_cpts, handicap_enfants, handicap_adultes, addictologie, pmi, prevention_sante, etc. Sans famille le ratio mélangerait labos/hôpitaux/EHPAD → non-sens. Sémantique conditionnelle de code_dept : seul = scope de calcul (dept entier) ; combiné avec nom_commune = hint de résolution UNIQUEMENT (filtre les homonymes), le calcul reste sur la commune résolue. Paris/Marseille/Lyon : densité par code_insee INDISPONIBLE (RPPS/FINESS rattachés aux arrondissements, INSEE n'expose la population qu'à la commune entière) → RangeError ; utiliser code_dept (75, 13, 69). compare_national: true ajoute la densité France entière (DOM inclus) + écart en % (positif = sur-doté, négatif = sous-doté).
Alias : dept/departement → code_dept, codeInsee/insee → code_insee. Ne renvoie AUCUNE interprétation métier (pas de seuil "désert médical" auto). Catégorie par défaut : Civil (C, ~97 % — libéraux, salariés privés, hospitaliers contractuels). Opt-in : include_agents_publics: true ajoute Agents publics (M, ~0,3 % — PH titulaires, ARS, CNAM, Éducation nationale, PMI, militaires SSA) ; include_etudiants: true ajoute Étudiants (E, ~2,5 % — internes, externes, élèves IDE/SF). Réf : https://mos.esante.gouv.fr/NOS/TRE_R09-CategorieProfessionnelle/. ATTENTION nomenclatures : les codes ANS (profession_code, savoir_faire_code) sont une nomenclature DISTINCTE des codes Ameli (specialite_code, type_ps_code) — un même nombre désigne des choses différentes (ex: '10' = Médecin côté ANS, Neurochirurgien côté Ameli). Ne JAMAIS passer un code Ameli à un paramètre ANS : le filtre renverrait vide sans erreur. Découvrir les codes ANS via lister_nomenclature(referentiel:'rpps_savoir_faire'). Source : Annuaire Santé, Agence du Numérique en Santé (ANS) — Licence Ouverte v2.0 |
| panorama_sante_territoireA | Panorama santé d'une commune française en 1 appel (V0.9). Agrège en parallèle : population (INSEE Melodi), densités médecins + infirmiers + pharmaciens avec comparaison nationale (méthodo DREES), nombre d'établissements FINESS par famille (default ["labo","pharmacie","ehpad","mco","msp_cpts"]), et un bloc DEMANDE (V0.22.0 — profil démographique de la commune agrégé depuis ses IRIS : âge, CSP, familles, revenu pondéré, à CROISER avec l'OFFRE ci-dessus pour l'aide à l'implantation ; demande: null si commune hors couverture IRIS (DOM non ingéré) — pour le détail au quartier ou un bassin par rayon, utiliser profil_iris). Remplace 7-10 appels MCP individuels par 1 seul. Ne renvoie AUCUNE interprétation métier (pas de qualification automatique 'désert médical') — le caller LLM applique sa grille. V0.19.0 : accepte nom_commune (string) comme alternative à code_insee. departement (V0.19) = hint resolver UNIQUEMENT (panorama ne calcule pas par dept ; un departement seul lève une erreur explicite). Granularité mixte : les densités professionnels et la population sont calculées au niveau commune ; le décompte FINESS est agrégé au niveau département dérivé du code INSEE (limitation V0.9 — pas de RPC count_finess_by_commune encore). Le champ niveauEtablissements du résultat indique "departement" (succès), "indisponible" (dept indérivable, ex code DOM tronqué) — utiliser cette information pour ne pas confondre ratios commune et dept. Paris/Marseille/Lyon NON supporté : le panorama par commune dépend de la densité par commune, indisponible pour ces villes (INSEE n'expose la population qu'à la commune entière, les praticiens RPPS aux arrondissements). Un code PLM (commune-mère 75056 ou arrondissement) lève une RangeError. Pour ces villes, interroger les tools individuels au niveau code_dept (75/69/13). Alias acceptés : codeInsee/insee/code → code_insee. Sources : RPPS / Annuaire Santé ANS (mensuel), FINESS DREES (bimensuel), INSEE Melodi (PMUN 2023). |
| inspect_siteA | Vue 360 d'un établissement de santé en 1 appel (V0.10). Pendant naturel de panorama_sante_territoire côté site : agrège en parallèle (a) identification FINESS DREES (raison sociale, adresse, téléphone), (b) statut administratif SIRENE via le resolver SIRET (verdicts site + groupe, best_match, SIREN explorés, dinum_errors, explication LLM-friendly), (c) professionnels rattachés via num_finess (sample borné + flag truncated si le site a plus de PS — PAS un count total), (d) historique INSEE (timeline périodes administratives par SIRET candidat). Remplace 3 appels MCP individuels (verifier_site_actif + rpps_dans_etablissement + historique_etablissement) par 1 seul. Utile pour : prospection (qualifier un site avant outreach), audit territorial (cross-check rapide d'un FINESS suspect), enrichissement CRM en batch. Format de retour : objet LookupResult. Quand found: true, payload avec 4 sections (finess, statut_site, professionnels, historique). La section historique peut être available: false quand le FINESS existe mais qu'aucun SIRET candidat n'a été identifié (RPPS vide + DINUM 0 match) — dans ce cas le message reprend celui de historique_etablissement. Quand num_finess est absent de FINESS DREES, retourne {found: false, lookupStatus: 'not_found', message}. Coût : 3 sous-appels parallèles. Cache PostgreSQL absorbe la duplication FINESS-RPC ; le pivot RPPS→DINUM est exécuté en double (verifier + historique partagent la cascade), surcoût p95 ≤ 600 ms — acceptable pour un agrégateur. Pour les besoins ciblés (juste le verdict, juste l'historique), préférer les tools individuels. Payload lourd (~7K tokens) : passer historique_detail: false pour un retour allégé (résumé au lieu des timelines SIRENE complètes) en usage batch. Alias acceptés : numFiness/finess/id → num_finess. |
| rpps_search_by_nameA | Trouve un PS par identité (matching trigram tolérant aux accents/typos). Usage : "Dr Martin à Paris" → nom: "Martin", departement: "75". Nom obligatoire ; prenom et departement affinent. Tri par match_score ∈ [0..1] décroissant (score trigram pg_trgm). Un score <0.5 = homonymie partielle à confirmer côté caller. Sans departement, des homonymes exacts ("Pierre Martin") ont TOUS le même score ~1.0 et ne sont pas départagés — toujours filtrer par dept ou prénom sur un nom commun. truncated: true = d'autres résultats existent (restreindre, ne pas parcourir).
Chaque résultat géolocalisé porte geo_precision ∈ {"adresse", "etablissement_finess", "centroide_commune"} — lire ce champ pour évaluer la fiabilité des coords (précise BAN/FINESS au m près vs centroïde commune ~3 km, non discriminant intra-commune). Catégorie par défaut : Civil (C, ~97 % — libéraux, salariés privés, hospitaliers contractuels). Opt-in : include_agents_publics: true ajoute Agents publics (M, ~0,3 % — PH titulaires, ARS, CNAM, Éducation nationale, PMI, militaires SSA) ; include_etudiants: true ajoute Étudiants (E, ~2,5 % — internes, externes, élèves IDE/SF). Réf : https://mos.esante.gouv.fr/NOS/TRE_R09-CategorieProfessionnelle/. Source : Annuaire Santé, Agence du Numérique en Santé (ANS) — Licence Ouverte v2.0 |
| professionnel_by_rppsA | Récupère la fiche complète d'un PS par identifiant national (rpps_id / IDNPS, 11 ou 12 chiffres — IDs émis depuis 2020 ont un préfixe "81" = 12 chars ; anciens IDs = 11 chars). Renvoie N entrées quand le PS exerce sur plusieurs sites (1 par site, chacun avec sa propre geo_precision — un même PS peut donc cumuler un site précis FINESS et un site au centroïde commune). Chaque résultat géolocalisé porte geo_precision ∈ {"adresse", "etablissement_finess", "centroide_commune"} — lire ce champ pour évaluer la fiabilité des coords (précise BAN/FINESS au m près vs centroïde commune ~3 km, non discriminant intra-commune). Fallback automatique sur l'API FHIR ANS live (gateway.api.esante.gouv.fr/fhir/v2) si non trouvé en base locale (snapshot mensuel J-30 max). Le champ source distingue db (base locale) de ans_fhir (live). include_freshness n'affecte que source: "db". Source : Annuaire Santé, Agence du Numérique en Santé (ANS) — Licence Ouverte v2.0 |
| finess_sirene_coverage_in_radiusA | Compare la couverture du référentiel FINESS DREES (sites physiques agréés LBM/pharmacie/etc.) au référentiel SIRENE DINUM (SIRET physiques actifs au NAF cible) dans un rayon géographique. Métrique : ratio sites FINESS / SIRET SIRENE. Utile pour détecter une sur-déclaration FINESS (sites encore listés mais SIRET fermés) ou une sous-déclaration DREES (sites SIRENE non agréés FINESS). Inclut une méthodologie explicite + caveats. V0.13.2 : si familles n'est pas passé, le scope FINESS est auto-dérivé du NAF cible (garantit un ratio cohérent — sinon finess_sites mélangerait toutes les familles co-localisées dans le rayon). Le matching FINESS↔SIRET est gaté par activité NAF↔famille (cas Hôpital Franco-Britannique : IFSI et labo au 4 rue Kléber ne sont plus confondus). Source : FINESS DREES + DINUM Recherche Entreprises + SIRENE INSEE. |
| panorama_implantation_completA | Étude d'implantation labo en 1 appel (V0.23). Géocode l'adresse cible puis agrège EN PARALLÈLE 7 sections : territoire (densités PS commune vs national + établissements), demande (profil démographique du BASSIN — rayon — via profil_iris : âge, CSP, revenu pondéré), concurrents (labos FINESS), pourvoyeurs (MCO/EHPAD/SSR/dialyse — drivers écosystémiques), prescripteurs (médecins RPPS + IDEL Ameli), cds (centres de santé), referentiels (qualité couverture FINESS↔SIRENE). Remplace ~15 appels MCP individuels par 1. Renvoie des RÉSUMÉS (count / top-N / moyenne), JAMAIS de listes brutes. AUCUNE interprétation métier (pas de 'désert médical' ni de verdict GO/NO-GO) — le caller LLM applique sa grille. DÉGRADATION (lis couverture — 1 drapeau par section) : "ok" | "partiel:<raison>" | "indisponible:<raison>". Si une source est down, SA section est flaggée et le RESTE est renvoyé — comble alors le trou via l'outil unitaire correspondant (etablissements_finess_in_radius, professionnels_rpps_in_radius, densite_sante, centres_sante_in_radius…). Échec d'ANCRAGE (géocodage KO / adresse douteuse / code INSEE indérivable) = rejet total (RangeError). Pièges internalisés : Paris/Lyon/Marseille basculés sur le département (meta.plm_mode=true) ; prescripteurs expose precis_count (PS géolocalisés à l'adresse, pas au centroïde commune) ; cds sans distance individuelle (centroïde commune). WORKFLOW : appelle CET outil pour DÉMARRER une étude, puis creuse les sections partiel/indisponible via les unitaires, puis enrichir_concurrents sur le top 3 de concurrents.top. Sources : IGN (géocodage), FINESS DREES, RPPS/ANS, Ameli/CNAM, INSEE/FILOSOFI, SIRENE/DINUM. |
| enrichir_concurrentsA | Enquête approfondie sur le top concurrents (V0.23). Pour chaque FINESS : statut actif + taille d'équipe + historique récent (inspect_site), signal M&A — rebranding en cours — (compare raison sociale FINESS vs RPPS), groupe parent (entreprise_by_siren : Biogroup/Cerballiance/… + est_grand_groupe). Cap dur max=3 (inspect_site ~7 K tokens/appel — JAMAIS 10+). Drapeau couverture PAR concurrent ("ok" | "partiel:<raison>") : un concurrent qui échoue n'annule pas les autres. Typiquement appelé sur concurrents.top[0..2].finess renvoyés par panorama_implantation_complet. Sources : FINESS/ANS, RPPS/ANS, SIRENE/DINUM. |