Spécification de la Fiche Langue
Source unique de vérité. Ce document définit la forme canonique de chaque fiche langue. Chaque fiche DOIT contenir tous les champs de niveau supérieur énumérés ici, même lorsque la valeur est
nullou[]. Une fiche avec un champ manquant n'est pas conforme. Cette uniformité permet aux outils automatisés, aux linters, aux scripts d'enrichissement et aux relecteurs humains de faire confiance à la structure de la fiche.
Principes de Conception
-
Forme uniforme. Les 8 000+ fiches ont les mêmes champs de niveau supérieur. Les valeurs inconnues sont
null, les tableaux vides sont[], les objets vides sontnull(pas{}). Cela signifie que le code n'a jamais besoin de vérifier « ce champ existe-t-il ? » — seulement « est-il rempli ? » -
Sourcer tout. Chaque affirmation factuelle remonte à une source primaire nommée et versionnée. Les affirmations non sourcées sont invérifiables. Le champ
dataSources(et les annotationssourcepar champ dans les sous-objets) rendent la provenance explicite. -
Préserver le désaccord. Lorsque les autorités divergent (Wikidata dit 50 000 locuteurs, Ethnologue dit 20 000), nous stockons les deux avec attribution de source. Nous ne faisons pas de moyenne, ne résolvons pas et ne prenons pas parti. Les utilisateurs peuvent naviguer la nuance.
-
Null signifie inconnu, non inapplicable. Si un champ est
null, cela signifie « nous n'avons pas encore trouvé de données pour ceci ». Si un champ ne s'applique vraiment pas (par ex.,grammatical genderpour une langue des signes), la valeur devrait l'expliquer :{ "grammatical": false, "inclusiveGuidance": "Non applicable — la LSF n'a pas de genre grammatical." } -
Fusionner uniquement. Les scripts d'enrichissement ajoutent des données, ne les remplacent jamais. Les valeurs curées manuellement ont priorité sur les données automatisées.
Architecture à Trois Couches
| Couche | Localisation | Objectif |
|---|---|---|
| Fiches langue | shared/language-cards/<code>.json | Configuration par langue : identité, classification, ressources, tout |
| Fiches genre | shared/language-cards/genera/<genus>.json | Propriétés d'exécution partagées pour les langues connexes (curées, non auto-générées) |
| Arbre des langues | shared/language-cards/language-tree.json | Hiérarchie Glottolog complète — données de référence pour l'interface Lab et la découverte de langues |
Modèle d'Héritage
Lorsqu'une fiche définit "extends": "family-dravidian", l'exécution fusionne la fiche parent
dans l'enfant en utilisant _deepMerge() (dans lib/registers.js). Cela permet aux fiches genre de définir des registres partagés, des systèmes de formalité et des conseils de genre qui
s'écoulent vers toutes les langues membres — sans dupliquer les données sur des centaines de
fiches individuelles.
Sémantique de Fusion
| Valeur enfant | Comportement | Pourquoi |
|---|---|---|
null | Hériter du parent | null signifie « je ne définis pas ceci » — la valeur du parent s'écoule |
| Non-null | Remplacer le parent | Les données de l'enfant sont plus spécifiques — ont priorité |
| Objet imbriqué | Fusion récursive | Les champs enfants remplacent, les champs parents sont préservés |
| Tableau | Remplacer entièrement | Les tableaux ne fusionnent pas élément par élément — le tableau enfant gagne |
Champs d'Identité (Jamais Hérités)
Certains champs appartiennent à la fiche elle-même et ne doivent JAMAIS être hérités d'un parent :
code, extends, _migration, aliases, iso639_1, iso639_3
Même si une fiche parent définit aliases: ["macro-code"], une fiche enfant n'héritera PAS
de ces alias. Ces champs sont toujours les propres valeurs de l'enfant (y compris
null s'il n'est pas défini).
Pourquoi : Sans cette règle, chaque langue crie hériterait aliases: ["cre"]
du parent macrolangue, rendant chaque variété un alias de la macro.
Exemple : Comment une Fiche Crie se Résout
┌───────────────────────┐
│ family-algic.json │ formality: null, registers: null
│ (no registers) │
└──────────┬────────────┘
│ extends
┌──────────┴────────────┐
│ genus-cree.json │ formality: { system: "obviative-animate", ... }
│ (sourced registers) │ registers: { formal: {...}, informal: {...} }
└──────────┬────────────┘
│ extends
┌──────────┴────────────┐
│ crk.json │ code: "crk", extends: "genus-cree"
│ (Plains Cree) │ formality: null → inherits from genus-cree
│ │ registers: null → inherits from genus-cree
│ │ script: "Cans" → own value, no inheritance
│ │ code: "crk" → identity field, never inherited
└───────────────────────┘
À l'exécution, getLanguageCard("crk") retourne un objet fusionné avec les registres de genus-cree + les propriétés de family-algic (le cas échéant) + l'identité et les métadonnées propres de crk.
Modèle de Fiche Genre
Les fiches genre vivent dans shared/language-cards/genera/ et définissent les propriétés partagées
pour un groupe de langues. Elles suivent le même schéma que les fiches régulières mais avec
des conventions différentes :
{
// Identity — genus cards use a prefixed code, NOT an ISO 639-3 code
"code": "genus-cree", // "genus-", "family-", or "macrolanguage-" prefix
"name": "Cree Languages", // Human-readable group name
"extends": "family-algic", // Genus cards can extend family cards (chaining)
// Formality — shared across the group, sourced from typological databases
"formality": {
"system": "obviative-animate",
"description": "Cree languages use an obviative/proximate system...",
"default": "formal",
"source": "WALS 37A, 38A + Wolfart 1973"
},
// Registers — shared presets, if the group shares a formality system
"registers": {
"formal": {
"label": "Formal (Proximate)",
"description": "...",
"prompt": "...",
"isDefault": true
},
"informal": {
"label": "Informal",
"description": "...",
"prompt": "..."
}
},
// Gender — shared grammatical gender behavior
"gender": {
"grammatical": false, // Cree doesn't have grammatical gender
"inclusiveGuidance": null // so no inclusive guidance needed
},
// Everything else is null — individual cards provide their own
// classification, geography, resources, etc.
"classification": null,
"methodSupport": null,
// ...
}
Règle clé : Les fiches genre ne doivent contenir QUE les données véritablement partagées dans l'ensemble du groupe et sourcées à partir de références faisant autorité. Si un système de formalité varie entre les membres, il appartient aux fiches individuelles, pas au genre.
Modèle Canonique
Chaque fiche DOIT avoir cette forme exacte de niveau supérieur. Les schémas de sous-objets sont documentés dans la Référence des Champs ci-dessous.
{
// ═══════════════════════════════════════════════════════════════════════
// § 1. IDENTITY
// Who is this language? What codes identify it?
// Sources: ISO 639-3 registry, ISO 639-1, BCP 47/IANA.
// ═══════════════════════════════════════════════════════════════════════
"code": "xxx", // REQUIRED. ISO 639-3 code. This IS the card ID and filename.
"name": "English Name", // REQUIRED. English reference name from ISO 639-3 registry.
"nativeName": null, // Endonym (name in the language itself). Source: Wikidata P1705.
// Examples: "nêhiyawêwin / ᓀᐦᐃᔭᐍᐏᐣ", "日本語", "Esperanto".
"alternateNames": [], // Other names this language is known by. Source: Glottolog, Ethnologue.
// Not aliases (those are code-level). These are name-level variants.
// Example: ["Qafar af", "Afaraf", "'Afar Af"] for Afar (aar).
"iso639_3": "xxx", // REQUIRED. Three-letter ISO 639-3 code. Same as `code`.
"iso639_1": null, // Two-letter ISO 639-1 code (e.g., "en", "fr"). null if none.
"bcp47": null, // IETF BCP 47 tag. Often same as iso639_1. Can include subtags
// (e.g., "iu-Cans-CA"). null if unknown.
"aliases": [], // Alternative code-level identifiers that resolve to this card.
// Example: ["fil"] for tl (Tagalog), ["iu"] for iku (Inuktitut).
// Used by code resolution: user types "fil", system loads tl.json.
"isoScope": "I", // REQUIRED. ISO 639-3 scope:
// "I" = Individual language
// "M" = Macrolanguage (e.g., Chinese, Arabic, Cree)
// "S" = Special (e.g., mis, mul, zxx)
"isoType": "L", // REQUIRED. ISO 639-3 type:
// "L" = Living "E" = Extinct "A" = Ancient
// "H" = Historical "C" = Constructed
"macrolanguage": null, // If this language is part of a macrolanguage, the macrolanguage
// ISO 639-3 code (e.g., "cre" for Plains Cree, "ara" for Arabic
// varieties). Source: ISO 639-3 macrolanguages.tab.
"extends": null, // Genus card key if shared properties are inherited from a genus
// card (e.g., "genus-cree", "genus-eskimo-aleut").
// null for most languages.
// ═══════════════════════════════════════════════════════════════════════
// § 2. CLASSIFICATION
// Where does this language sit in the family tree?
// Source: Glottolog. NEVER hand-build classifications.
// ═══════════════════════════════════════════════════════════════════════
"glottocode": null, // Glottolog identifier (e.g., "plai1258", "stan1293").
// null if the language is not in Glottolog.
"classification": null, // Genealogical classification from Glottolog. When populated:
// {
// "family": "Algic", // Top-level family. null for isolates.
// "familyGlottocode": "algi1248", // Glottocode of the family.
// "genus": "Plains Creeic", // WALS-style genus.
// "genusGlottocode": "plai1264", // Glottocode of the genus.
// "ancestry": ["Algic", "Algonquian-Blackfoot", "Algonquian",
// "Cree-Montagnais-Naskapi", "Cree", "Plains Creeic"]
// }
// For isolates: family = language name, genus = language name,
// ancestry = [language name].
"isIsolate": false, // true if a language isolate (no known genetic relatives).
// Source: Glottolog CLDF.
// ═══════════════════════════════════════════════════════════════════════
// § 3. GEOGRAPHY
// Where is this language spoken?
// Sources: Glottolog (coordinates, countries), census data, Ethnologue.
// ═══════════════════════════════════════════════════════════════════════
"macroarea": null, // Glottolog macroarea. One of: "Africa", "Australia",
// "Eurasia", "North America", "Papunesia", "South America".
// null if unknown. Source: Glottolog CLDF.
"coordinates": null, // Representative geographic point. When populated:
// { "lat": 52.1, "lng": -106.6, "source": "glottolog-5.3" }
// This is a representative point, not a boundary.
"countries": [], // ISO 3166-1 alpha-2 country codes where this language is spoken.
// Example: ["CA", "US"]. Source: Glottolog.
"regions": [], // Detailed regional breakdown with admin codes & speaker estimates.
// Each entry:
// {
// "country": "Canada",
// "countryCode": "CA",
// "officialStatus": "recognized", // official, co-official,
// // recognized, none
// "region": "Saskatchewan, Alberta, Manitoba",
// "speakerEstimate": "~20,000",
// "coordinates": [-106.6, 52.1], // [lng, lat]
// "admin1Codes": ["CA-SK", "CA-AB", "CA-MB"]
// }
"arealContext": null, // Linguistic area / Sprachbund membership. DISTINCT from
// contactInfluences (which is language-specific contact history).
// This field captures zone-level typological convergence patterns
// — i.e., what linguistic area the language exists within and
// what features are common across that area.
// {
// "zone": "Mainland Southeast Asian Sprachbund",
// "arealFeatures": "Tonal convergence, classifier systems,
// topic-prominence, monosyllabicity trend.",
// "typicalContacts": ["Classical Chinese", "Sanskrit/Pali"],
// "source": "areal-linguistics (Enfield 2005)"
// }
// NOT the same as contactInfluences. A language can exist within
// a convergence area without having specific contact history with
// any particular language in that area.
// ═══════════════════════════════════════════════════════════════════════
// § 4. WRITING SYSTEMS
// How is this language written?
// Sources: Wikidata P282, ISO 15924, manual research.
// Note: Some languages have NO standardized orthography. Some have
// competing orthographies. Some use multiple scripts routinely (e.g.,
// Serbian: Cyrillic + Latin; Japanese: Kanji + Hiragana + Katakana).
// Sign languages may use notation systems (SignWriting, HamNoSys) or
// none at all.
// ═══════════════════════════════════════════════════════════════════════
"script": null, // Primary ISO 15924 script code (e.g., "Latn", "Cyrl", "Cans",
// "Jpan"). null if no written form or unknown.
"scriptUnicodeName": null, // Unicode script block name derived from the script field.
// e.g., "Latin", "Cyrillic", "Canadian_Aboriginal", "CJK".
// Used by code_switching metric plugin. Auto-populated by
// enrich-script-unicode-names.mjs. null if script is null.
"scripts": [], // All writing systems with detail. Array of:
// {
// "code": "Cans",
// "name": "Unified Canadian Aboriginal Syllabics",
// "primary": true
// }
// A language with multiple scripts has multiple entries.
// A language with no written form has [].
"dir": null, // Writing direction: "ltr" (left-to-right) or "rtl" (right-to-left).
// null if no written form or unknown.
"scriptConverter": null, // Script converter key if we have a converter for this language
// (e.g., "crk" for SRO↔Syllabics). null for most languages.
"orthographicStatus": null, // Writing system standardization status. When populated:
// {
// "status": "standardized",
// // "standardized" — official/agreed orthography exists
// // "competing" — multiple orthographies in active use
// // "emerging" — orthography under development
// // "none" — primarily oral, no standard writing
// "notes": "Uses SIL-developed Latin orthography since 1960s.",
// "source": "ethnologue" // or "manual-curation"
// }
// Crucial for LRLs where orthographic variation directly impacts
// MT training data quality and evaluation consistency.
// ═══════════════════════════════════════════════════════════════════════
// § 5. DEMOGRAPHICS & VITALITY
// How many people speak this language? Is it endangered?
// Sources: Census, Ethnologue, UNESCO Atlas, Wikidata, Glottolog AES.
//
// CRITICAL: Store ALL estimates separately with source attribution.
// Never average or "resolve" conflicting data. Speaker counts are
// politically contested for many languages. Present the evidence,
// let the reader assess.
// ═══════════════════════════════════════════════════════════════════════
"speakerEstimates": [], // Array of speaker count estimates from different authorities.
// Each entry:
// {
// "source": "wikidata", // or "ethnologue-28",
// // "census-ph-2020", etc.
// "count": 20000, // Point estimate. null if range-only.
// "date": "2026-06-07", // When this data was retrieved.
// "countRange": { "min": 15000, "max": 25000 }, // Optional range.
// "note": "Wikidata has 2 estimates: 15,000 and 25,000"
// }
// Empty array means we have not yet found speaker count data.
"vitality": null, // Endangerment / vitality assessment. When populated:
// {
// "unescoStatus": "severely-endangered",
// // Enum: "safe", "vulnerable", "definitely-endangered",
// // "severely-endangered", "critically-endangered",
// // "extinct"
// "aesStatus": "shifting",
// // Glottolog AES label (free text from AES data).
// "egids": "6b",
// // Ethnologue Expanded Graded Intergenerational Disruption
// // Scale. Levels: 0 (international) to 10 (extinct).
// "trend": "declining",
// // Qualitative trend: "stable", "growing", "declining",
// // "shifting", "moribund", "awakening"
// "source": "glottolog-aes-5.3",
// "notes": "Intergenerational transmission breaking down."
// }
// ═══════════════════════════════════════════════════════════════════════
// § 5.5. DOCUMENTATION & DIGITAL PRESENCE
// How well-documented is this language? What digital footprint does it
// have? These fields answer the practical question: "What can I
// actually DO with this language?"
// Sources: Glottolog (references), Wikipedia, Common Voice, Tatoeba.
// ═══════════════════════════════════════════════════════════════════════
"documentationDepth": null, // How well-documented is this language in the literature?
// {
// "referenceCount": 42,
// // Number of published references in Glottolog.
// "med": "grammar",
// // Most Extensive Description type. One of:
// // "long_grammar", "grammar", "grammar_sketch",
// // "dictionary", "phonology", "text", "wordlist",
// // "comparative", "minimal", "unknown"
// "source": "glottolog-5.3"
// }
"digitalPresence": null, // Digital footprint across web platforms. When populated:
// {
// "wikipedia": {
// "edition": true, // Has its own Wikipedia edition?
// "articleCount": 75000, // Number of articles.
// "editionCode": "crk", // Wikipedia subdomain code.
// "source": "wikimedia-api-2026"
// },
// "commonVoice": {
// "validatedHours": 12.5,
// "totalHours": 25.0,
// "speakers": 45,
// "sentences": 1200,
// "source": "common-voice-20.0"
// },
// "tatoeba": {
// "sentenceCount": 342,
// "source": "tatoeba-2026"
// }
// }
"dialectCount": null, // Number of recognized dialects in Glottolog.
// Derived from child_dialect_count in languoid.csv.
// Simple integer. null if 0 or unknown.
// Source: glottolog-5.3.
// ═══════════════════════════════════════════════════════════════════════
// § 6. FORMALITY, REGISTERS & GENDER
// How does politeness work in this language? What translation registers
// do we offer? How should gender be handled?
//
// This section drives Champollion's register-preset system — the
// mechanism by which users select formal/informal/professional tone.
// These fields require genuine linguistic research, not automation.
// ═══════════════════════════════════════════════════════════════════════
"formality": null, // Formality system description. When populated:
// {
// "system": "T-V",
// // One of: "T-V", "speech-levels", "keigo", "particles",
// // "register-levels", "register-and-code-switching",
// // "code-switching", "none"
// "description": "French uses a vous/tu distinction...",
// "default": "formal-vous" // Key into the `registers` object.
// }
"registers": null, // Translation register presets. When populated, keyed by preset ID:
// {
// "formal-vous": {
// "label": "Formal (vouvoiement)",
// "description": "One sentence: when to use this preset.",
// "prompt": "The actual LLM system prompt instruction that
// steers translation tone. Must name specific
// linguistic features (pronouns, verb forms, particles).",
// "deeplFormality": "prefer_more"
// // Only if methodSupport.deepl.formality is true.
// // One of: "prefer_more", "prefer_less", "default".
// }
// }
"gender": null, // Grammatical gender and inclusive guidance. When populated:
// {
// "grammatical": true, // Does the language have gram. gender?
// "inclusiveGuidance": "Use gender-neutral forms when possible.
// Prefer 'iel' (neologism) or rephrase to
// avoid gendered agreement."
// }
// For languages without grammatical gender (Turkish, Finnish):
// { "grammatical": false, "inclusiveGuidance": null }
"codeSwitching": null, // Code-switching behavior (for languages where mixing with another
// language is the norm, not an error). When populated:
// {
// "contactLanguage": "Spanish",
// "contactIso639_3": "spa",
// "mixedVarietyName": "Jopará", // null if no named mixed variety
// "prevalence": "dominant", // "rare", "common", "dominant"
// "morphologicalIntegration": true,
// "pipelineStrategy": "hybrid-fst",
// "notes": "Jopará IS the everyday language of most Paraguayans..."
// }
// ═══════════════════════════════════════════════════════════════════════
// § 7. LINGUISTIC PROFILE
// What makes this language what it is? What are the specific challenges
// for machine translation? What rules govern its typography?
// What languages have shaped it through contact?
//
// These fields require genuine linguistic expertise. For many languages
// (especially low-resource), this section will remain null until a
// qualified researcher or community member contributes.
// ═══════════════════════════════════════════════════════════════════════
"linguisticChallenges": null, // MT-relevant challenges, keyed by challenge ID.
// When populated:
// {
// "polysynthesis": "Cree is highly polysynthetic. A single verb
// can incorporate subject, object, tense...",
// "animacy": "Verb conjugation changes based on whether the
// subject/object is animate or inanimate...",
// "neologisms": "Avoid literal translations of modern software
// concepts. Maintain Cree metaphorical logic..."
// }
// Aim for 3–6 challenges per language when researched.
"contactInfluences": [], // How other languages have shaped this one. Array of:
// {
// "source": "English",
// "sourceIso639_3": "eng", // null if proto-language/unknown
// "type": "superstrate",
// // Enum: "superstrate", "substrate", "adstrate",
// // "learned_borrowing", "lexical_borrowing",
// // "relexification"
// "domains": ["education", "government", "technology"],
// "depth": "deep",
// // Enum: "light", "moderate", "heavy", "structural",
// // "defining"
// "period": "1870–present",
// "notes": "Residential school era and ongoing...",
// "citation_needed": false
// // true if no published academic source found.
// // See language-card-citation-procedure.md.
// }
"rules": null, // Typography, plural, and capitalization rules. When populated:
// {
// "typography": {
// "quoteStart": "\u201c",
// "quoteEnd": "\u201d",
// "usesSpaces": true, // false for CJK, Thai, Lao, Khmer
// "punctuationSpacing": {
// "doublePunctuation": "none" // "thin-nbsp" for French
// }
// },
// "plurals": {
// "categories": ["one", "other"]
// // From CLDR. Possible values:
// // "zero", "one", "two", "few", "many", "other"
// },
// "capitalization": {
// "hasCase": true
// // true for Latin, Cyrillic, Greek, Armenian scripts.
// // false for CJK, Arabic, Devanagari, etc.
// }
// }
// Source: CLDR + ISO 15924 derivation.
"typologicalProfile": null, // Grambank typological features. When populated:
// {
// "featuresDocumented": 195,
// "featuresCoverage": 1, // 0.0–1.0 fraction of features
// "wordOrderDominant": "SVO",
// "hasDefiniteArticle": true,
// "hasIndefiniteArticle": true,
// "hasGenderSystem": true,
// "hasCaseMorphology": true,
// "hasEvidentiality": false,
// "hasToneSystem": false,
// "source": "grambank-1.0.3"
// }
// Auto-populated by enrich-grambank-typology.mjs.
"phonologicalInventory": null, // PHOIBLE phoneme inventory. When populated:
// {
// "consonants": 24,
// "vowels": 16,
// "tones": 0,
// "totalPhonemes": 40,
// "isTonal": false,
// "inventorySize": "moderately-large",
// // Enum: "small", "moderately-small", "average",
// // "moderately-large", "large"
// "source": "phoible-2.0"
// }
// Auto-populated by enrich-phoible-phonemes.mjs.
// ═══════════════════════════════════════════════════════════════════════
// § 8. ENCYCLOPEDIC
// General knowledge about the language for human context. History,
// dialect situation, institutional resources, representative sayings.
// This section is for understanding, not computation.
// ═══════════════════════════════════════════════════════════════════════
"encyclopedic": null, // General knowledge. When populated:
// {
// "family": "Algic", // Redundant with classification
// // but useful for human readers.
// "dialects": {
// "split": true, // Is there significant variation?
// "classification": "Plains Cree (y-dialect)",
// "variants": ["crk", "cwd", "csw"] // ISO codes of variants
// },
// "demographics": {
// "speakers": "Approx. 20,000 active speakers",
// "regions": ["Saskatchewan", "Alberta", "Manitoba"]
// },
// "history": "Plains Cree is the most widely spoken Algonquian
// language in western Canada...",
// "resources": {
// "wikipedia": "https://en.wikipedia.org/wiki/Plains_Cree",
// "foundations": [{ "name": "ALTLab", "url": "https://..." }],
// "dictionaries": [{ "name": "itwêwina", "url": "https://..." }]
// }
// }
"culturalAphorism": null, // A representative saying, proverb, or teaching in the language.
// When populated:
// {
// "text": "ê-wîcêhtonaniwahk kâ-kî-isi-wâpahtamâhk ôma pimâtisiwin",
// "transliteration": null, // Romanized form if non-Latin script.
// "translation": "Through helping each other we come to understand
// this life",
// "literal": "By-helping-one-another we-have-come-to-see this life",
// "source": "Cree teaching, documented in nêhiyawêwin educational
// resources"
// }
// Choose sayings that reveal something about the language's
// worldview or structure. Must be sourced.
"varieties": [], // For macrolanguages or languages with significant dialectal
// variation, the individual varieties with their own tool coverage.
// Each entry:
// {
// "name": "Cusco Quechua",
// "iso639_3": "quz",
// "region": "Cusco, Peru",
// "fstCoverage": true,
// "corpusCoverage": true,
// "nllbCoverage": false,
// "mutualIntelligibility": "Primary variety for this card",
// "notes": "SQUOIA FST was built for this variety."
// }
// ═══════════════════════════════════════════════════════════════════════
// § 9. DIGITAL RESOURCES & TOOLING
// What NLP tools, corpora, models, and datasets exist for this language?
// What translation APIs support it? What eval benchmarks are available?
//
// This is Champollion's operational core — these fields determine what
// we can actually DO with this language.
// ═══════════════════════════════════════════════════════════════════════
"resources": null, // NLP resources available for this language. When populated:
// {
// "fsts": [{ // Finite-state transducers
// "name": "GiellaLT Plains Cree FST (lang-crk)",
// "url": "https://github.com/giellalt/lang-crk/releases",
// "type": "morphological-analyzer"
// }],
// "corpora": [{ // Text corpora
// "name": "EDTeKLA Cree Language Textbook Corpus",
// "type": "parallel", // "parallel", "monolingual"
// "pairs": ["en-crk"],
// "url": "https://...",
// "exposure": "open-web" // "open-web", "restricted",
// // "holdout"
// }],
// "models": [{ // Pre-trained models
// "name": "NLLB-200 (crk_Cans)",
// "url": "https://...",
// "type": "nmt"
// }],
// "tools": [], // Other NLP tools
// "wordlists": [{ // Standardized wordlists
// "name": "Lexibank",
// "conceptCount": 200,
// "source": "lexibank"
// }],
// "treebanks": [{ // Syntactic treebanks
// "name": "UD_Korean-GSD",
// "tokens": 80000,
// "source": "universal-dependencies-2.14"
// }]
// }
// IMPORTANT: Only actual NLP/digital resources belong here.
// "This language has a WALS entry" is NOT a resource — that
// goes in databaseCoverage.
"databaseCoverage": null, // Which typological/reference databases cover this language.
// Separated from resources to avoid conflating "has a database
// entry" with "has usable NLP tooling."
// {
// "wals": true,
// "grambank": true,
// "phoible": true,
// "cldr": true,
// "lexibank": true,
// "commonVoice": true,
// "source": "derived"
// }
"corpusAvailability": null, // What text/parallel corpora exist for NLP use?
// {
// "bibleTranslation": {
// "textAvailable": true,
// "audioAvailable": true,
// "source": "bible-brain-api"
// },
// "opusCorpora": ["wikimedia", "ubuntu", "gnome"],
// "source": "multi-source"
// }
"keyboardSupport": null, // Input method / keyboard availability. When populated:
// {
// "keymanKeyboards": 3,
// // Number of Keyman keyboards available.
// "cldrKeyboard": true,
// // CLDR has keyboard layout data.
// "source": "keyman-api + cldr"
// }
"methodSupport": { // REQUIRED. Which Champollion translation methods support this
// language. Each method is an object with at minimum
// { "supported": boolean }.
"googleTranslate": { "supported": false },
"deepl": { "supported": false },
"microsoftTranslator": { "supported": false },
"libreTranslate": { "supported": false },
"nllb": { "supported": false },
// When NLLB is supported, include the code:
// { "supported": true, "code": "crk_Cans" }
"llm": { "supported": true }
// LLM is always true (quality varies by language).
// Optional: "verifiedDate": "2026-06-07" for audit trail.
},
"metricModelSupport": null, // Which MT evaluation models produce reliable scores.
// When populated:
// {
// "xlmr": "high", // "high", "medium", or "low"
// // XLM-R training representation tier.
// "africomet": false // true if AfriCOMET covers this language.
// }
// Drives automatic COMET model selection in metrics_comet.py.
// Auto-populated by enrich-metric-model-support.mjs.
"metricPlugins": null, // Which per-language metric plugin packs are available.
// When populated:
// {
// "formalityMarkers": true // Formality marker resource file exists
// // at plugins/resources/formality/{code}.json
// }
// Each key corresponds to a resource pack in
// arena/mt_eval_harness/plugins/resources/{packName}/.
// To add a new metric pack for a language, create the resource
// file and set the flag here. No code changes required.
"evalPack": null, // Evaluation dependency pack for language-specific metrics.
// When populated, declares the Python dependencies and
// post-install steps required by this language's eval standards.
// The harness uses this for dependency gating: if deps are
// missing, the harness warns the user and skips LYSS metrics
// (rather than crashing).
// When populated:
// {
// "pythonDeps": {
// "pyhfst": "pyhfst>=1.4", // PyPI package specs
// "requests": "requests>=2.28",
// "spacy": "spacy>=3.7"
// },
// "postInstall": [ // Commands to run after pip
// {
// "command": "spacy download en_core_web_md",
// "label": "spaCy English model (for LYSS-sem)"
// }
// ],
// "requiresFst": true, // true if GiellaLT FST needed
// "description": "LYSS equivalence linter + FST validation"
// }
"evalMetrics": null, // Language-specific evaluation metrics (LYSS standards).
// When populated, the harness dynamically imports these
// MetricPlugin classes from eval_standards/<lang>/ and applies
// them to every run targeting this language — regardless of
// which method (contestant) is being evaluated.
// Keyed by metric ID:
// {
// "lyss-eq": {
// "module": "eval_standards.crk.metrics",
// "class": "CrkLinterMetric",
// "description": "LYSS deterministic variant-class linter"
// },
// "lyss-sem": {
// "module": "eval_standards.crk.metrics",
// "class": "CrkSemanticMetric",
// "description": "LYSS FST-based semantic validator",
// "dependencies": ["spacy>=3.7"],
// "spacy_models": ["en_core_web_md"]
// }
// }
// Architecture: eval standards are referees, not contestants.
// They live in the harness (eval_standards/), not in method
// plugins. This ensures all methods are scored equally.
// Discovery: plugin_discovery.py reads this field via
// language_cards.get_eval_metrics() and instantiates metrics
// using importlib. Dependencies are checked against evalPack.
"omt1600": null, // Meta's OMT-1600 (One Model for Translation) coverage assessment.
// When populated:
// {
// "covered": true,
// "tier": "R1", // Meta's resource tier
// "evalMetrics": ["chrF++", "BLASER-3"],
// "notes": "Plains Cree: no web-crawled bitext..."
// }
"evalDatasets": [], // Evaluation dataset IDs available for this language.
// Example: ["flores-plus-devtest", "edtekla-dev-v1"].
// Empty means no standardized eval set exists.
"pipelineReadiness": null, // Assessment of readiness for Champollion's translation pipeline.
// When populated:
// {
// "tier": "tier-2-feasible",
// // "watch-list" — cataloged but no path to translation
// // "tier-3-cataloged" — basic metadata present
// // "tier-2-feasible" — tools exist, pipeline possible
// // "tier-1-ready" — pipeline operational
// "hasFST": true,
// "hasParallelCorpus": true,
// "hasEvalBenchmark": true,
// "blockers": ["Syllabics post-processing validation"],
// "notes": "FST-gated pipeline operational. EDTeKLA corpus..."
// }
// ═══════════════════════════════════════════════════════════════════════
// § 10. PROVENANCE & METADATA
// Where does this data come from? Who reviewed it? When was it
// generated? What's its overall quality level?
//
// This section exists to make the card auditable. Every automated
// enrichment, every human review, every source consulted should
// leave a trace here.
// ═══════════════════════════════════════════════════════════════════════
"dataSources": [], // REQUIRED. Sources consulted for this card's data.
// Can be a flat array (backwards-compatible):
// ["iso639-3-2024", "glottolog-5.3", "wikidata"]
//
// Or a structured per-field object (preferred for new cards):
// {
// "classification": ["glottolog-5.3"],
// "vitality": ["glottolog-aes-5.3", "unesco-atlas-2024"],
// "speakerEstimates": ["wikidata", "census-ca-2021"],
// "rules": ["cldr-48"],
// "methodSupport": ["google-translate-2026-06"]
// }
"supportTier": "cataloged", // Auto-derived tier summarizing the card's depth:
// "cataloged" — identity + classification only
// "emerging" — + vitality + speakerEstimates
// "developing" — + resources + methodSupport
// "supported" — full research: registers, challenges, etc.
"humanReviewed": null, // null until a qualified human reviews the card. When populated:
// {
// "reviewer": "Prof. Kenneth Jamandre",
// "affiliation": "University of the Philippines Diliman",
// "date": "2026-06-08",
// "scope": "full", // "full", "partial", "vitality-only"
// "notes": "Verified speaker count, vitality assessment,
// and contact influences for Tagalog."
// }
"notes": null, // Free-text notes about this language or this card's data quality.
// Example: "Low-resource language under active development.
// Translation pipeline uses FST-gated approach."
"firstDocumented": null, // Year of first known documentation. Negative for BCE.
// Example: -1500 (Sanskrit, ~1500 BCE), 1787 (some languages).
// Source: Glottolog CLDF.
"lastDocumented": null, // Year of last known documentation (relevant for extinct languages).
// Source: Glottolog CLDF.
"_generated": null // Auto-populated by enrichment scripts. When populated:
// {
// "by": "generate-all-cards.mjs",
// "at": "2026-06-07T12:34:56Z",
// "sources": ["iso639-3", "glottolog-5.3", "wikidata"],
// "completeness": "partial",
// // "partial" — has identity + classification + coords
// // "substantial" — + vitality + speakerEstimates + script
// // "complete" — all automatable fields populated
// "lastEnriched": "2026-06-07"
// }
}
Référence des Champs
§ 1. Champs d'Identité
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
code | string | ✅ | ✅ | Registre ISO 639-3 |
name | string | ✅ | ✅ | Registre ISO 639-3 |
nativeName | string | null | — | ✅ | Wikidata P1705 |
alternateNames | string[] | — | ✅ | Glottolog, Ethnologue |
iso639_3 | string | ✅ | ✅ | Registre ISO 639-3 |
iso639_1 | string | null | — | ✅ | ISO 639-1 |
bcp47 | string | null | — | Partiel | Registre de sous-étiquettes IANA |
aliases | string[] | — | ❌ | Curation manuelle |
isoScope | string | ✅ | ✅ | Registre ISO 639-3 |
isoType | string | ✅ | ✅ | Registre ISO 639-3 |
macrolanguage | string | null | — | ✅ | ISO 639-3 macrolanguages.tab |
extends | string | null | — | ❌ | Curation manuelle |
§ 2. Champs de Classification
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
glottocode | string | null | — | ✅ | Glottolog |
classification | object | null | — | ✅ | Glottolog |
isIsolate | boolean | — | ✅ | Glottolog CLDF |
§ 3. Champs de Géographie
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
macroarea | string | null | — | ✅ | Glottolog CLDF |
coordinates | object | null | — | ✅ | Glottolog |
countries | string[] | — | ✅ | Glottolog |
regions | object[] | — | ❌ | Recensement, Ethnologue, manuel |
arealContext | object | null | — | ✅ | Coordonnées + zones d'aire linguistique |
§ 4. Champs de Système d'Écriture
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
script | string | null | — | ✅ | Wikidata P282 |
scriptUnicodeName | string | null | — | ✅ | Dérivé de script via ISO 15924 → mappage Unicode |
scripts | object[] | — | Partiel | Wikidata, manuel |
dir | string | null | — | ✅ | Dérivable du script |
scriptConverter | string | null | — | ❌ | Manuel |
orthographicStatus | object | null | — | Partiel | Ethnologue, manuel |
§ 5. Champs Démographiques et de Vitalité
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
speakerEstimates | object[] | — | ✅ | Wikidata, Ethnologue, recensement |
vitality | object | null | — | ✅ | Glottolog AES, UNESCO |
§ 5.5 Champs de Documentation et de Présence Numérique
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
documentationDepth | object | null | — | ✅ | Références Glottolog |
digitalPresence | object | null | — | ✅ | Wikipedia, Common Voice, Tatoeba |
dialectCount | number | null | — | ✅ | Glottolog |
§ 6. Champs de Formalité, Registre et Genre
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
formality | object | null | — | ❌ | Recherche linguistique |
registers | object | null | — | ❌ | Recherche linguistique |
gender | object | null | — | ❌ | Recherche linguistique |
codeSwitching | object | null | — | ❌ | Recherche linguistique |
§ 7. Champs de Profil Linguistique
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
linguisticChallenges | object | null | — | ❌ | Recherche linguistique |
contactInfluences | object[] | — | ❌ | Linguistique publiée |
rules | object | null | — | ✅ | CLDR |
typologicalProfile | object | null | — | ✅ | Grambank 1.0.3 — auto-rempli par enrich-grambank-typology.mjs |
phonologicalInventory | object | null | — | ✅ | PHOIBLE 2.0 — auto-rempli par enrich-phoible-phonemes.mjs |
§ 8. Champs Encyclopédiques
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
encyclopedic | object | null | — | ❌ | Recherche manuelle |
culturalAphorism | object | null | — | ❌ | Contribution communautaire |
varieties | object[] | — | ❌ | Recherche manuelle |
§ 9. Champs de Ressources Numériques
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
resources | object | null | — | Partiel | Manuel + automatisé |
databaseCoverage | object | null | — | ✅ | Dérivé de l'enrichissement |
corpusAvailability | object | null | — | ✅ | Bible Brain, OPUS, Lexibank |
keyboardSupport | object | null | — | ✅ | API Keyman, CLDR |
methodSupport | object | ✅ | Partiel | Vérification API |
metricModelSupport | object | null | — | ✅ | Article XLM-R, article AfriCOMET |
metricPlugins | object | null | — | ✅ | Enrichissement de fiche — déclare quels packs de plugins de métrique s'appliquent (par ex., { formalityMarkers: true }) |
omt1600 | object | null | — | ✅ | Évaluation méta |
evalDatasets | string[] | — | ✅ | Registre de jeux de données |
pipelineReadiness | object | null | — | Partiel | Dérivé + manuel |
resources.fsts[].install: Les entrées FST dans l'objetresourcespeuvent inclure un sous-objetinstallavec les champs :repo,releaseTag,assetPattern,format,maturity, et optionnellementbundlePattern. Cela remplace l'ancien dict codé en durGIELLALT_FST_REGISTRY. Voirget_fst_install_info()danslanguage_cards.py.
§ 10. Champs de Provenance
| Champ | Type | Requis | Automatisable | Source |
|---|---|---|---|---|
dataSources | array | object | ✅ | ✅ | Auto + manuel |
supportTier | string | — | ✅ | Dérivé de l'exhaustivité de la fiche |
humanReviewed | object | null | — | ❌ | Relecteur humain |
notes | string | null | — | ❌ | Manuel |
firstDocumented | number | null | — | ✅ | Glottolog CLDF |
lastDocumented | number | null | — | ✅ | Glottolog CLDF |
_generated | object | null | — | ✅ | Scripts d'enrichissement |
Politique de Code de Langue
Champollion utilise ISO 639-3 comme identifiant canonique. Les autres codes standards sont enregistrés comme alias et se résolvent au code ISO 639-3 à l'exécution.
| Priorité | Standard | Exemple | Champ | Utilisation |
|---|---|---|---|---|
| 1 (canonique) | ISO 639-3 | crk | code | Nom de fichier de fiche, clés de config, paramètres API |
| 2 (alias) | ISO 639-1 | iu | aliases[] | Accepté en CLI, résolu en ISO 639-3 |
| 3 (alias) | BCP 47 | fil | aliases[] | Accepté en CLI, résolu en ISO 639-3 |
| Référence | Glottocode | plai1258 | glottocode | Classification uniquement, pas pour l'exécution |
Ordre de résolution : Lorsqu'un utilisateur fournit un code :
- Correspondance directe sur
card.code→ trouvé - Correspondance sur
card.aliases[]→ trouvé, retourner la fiche canonique - Correspondance sur
card.iso639_1→ trouvé (secours) - Non trouvé → erreur
Historique de Migration : ISO 639-1 → ISO 639-3
Avant la v8, les noms de fichiers de fiche utilisaient les codes ISO 639-1 lorsqu'ils étaient disponibles (fr.json,
de.json, ja.json). Dans la migration 639-3, toutes les fiches ont été renommées en leurs
équivalents ISO 639-3 :
| Avant | Après | Pourquoi |
|---|---|---|
fr.json | fra.json | 639-3 est canonique |
de.json | deu.json | 639-3 est canonique |
zh.json | cmn.json | Macrolangue → individuelle par défaut |
ar.json | arb.json | Macrolangue → Arabe standard moderne |
ms.json | zsm.json | Macrolangue → Malais standard |
Qu'est-il arrivé aux anciens codes ?
- L'ancien code 639-1 est dans
card.iso639_1 - L'ancien code 639-1 est dans
card.aliases[] resolveCode("fr")retourne"fra"à l'exécution — rétrocompatible- Les utilisateurs peuvent toujours écrire
"fr"dans leur config — cela se résout de manière transparente
Ce qui a changé architecturalement :
_deepMerge()ignore maintenant les valeursnull(hérite du parent)_deepMerge()a maintenant un champ d'identité défini (code, extends, alias jamais hérités)formality.defaultest maintenant dérivé des drapeaux de registreisDefault: true- 205 fiches dérivées de Grambank ont reçu une correction structurelle
formality.default - 38 fiches genre/famille/macrolangue fournissent des cibles d'héritage
Cas Limites
Langues des Signes
Les langues des signes (par ex., ASE — American Sign Language) sont des langues légitimes avec des codes ISO 639-3. Elles ont une géographie et des comptages de locuteurs mais :
scriptest généralementnull(pas de forme écrite standard)scriptspeut inclure"Sgnw"(SignWriting) si un système de notation est utilisédirestnulllinguisticChallengesdevrait aborder la grammaire spatiale, les classificateurs, etc.gender.grammaticalest généralementfalse
Langues Anciennes et Historiques
Les langues comme le latin (lat, isoType H) et le sanskrit (san, isoType H) sont
toujours utilisées dans des contextes spécifiques (liturgique, académique) mais n'ont pas de locuteurs natifs :
vitalitypeut noter « pas de locuteurs natifs » avec"trend": "stable"(pas en déclin — la communauté qui l'utilise est stable, juste petite)speakerEstimatesdevrait noter que ce sont des locuteurs L2, pas L1firstDocumented/lastDocumentedles situent dans le temps
Langues Construites
L'espéranto (epo, isoType C), Lojban, etc. :
classificationpeut pointer vers une famille « construite » ou nullcontactInfluencesreflète le matériel source (par ex., l'espéranto s'inspire des langues romanes, germaniques, slaves)vitalityest inhabituel — communauté de locuteurs croissante mais pas de patrie native
Macrolangues
L'arabe (ara), le chinois (zho), le cri (cre), le quechua (que) sont des macrolangues
qui englobent plusieurs langues individuelles :
isoScope: "M"varietiesdevrait lister les langues individuelles avec leurs codes ISOmethodSupportdevrait refléter ce que la fiche macrolangue supporte (généralement la variété standardisée)- Les variétés individuelles devraient également avoir leurs propres fiches
Langues Sans Orthographe Standardisée
De nombreuses langues (en particulier les langues de tradition orale) n'ont pas de système d'écriture standardisé, ou ont des orthographies concurrentes :
scriptestnullscriptsest[]direstnullnotesdevrait expliquer la situation orthographiquelinguisticChallengesdevrait noter comment cela affecte la TA (par ex., pas de données d'entraînement)
Diglossie
Les langues comme l'arabe (MSA vs. dialectes) ou le guarani (Jopará vs. guarani pur) :
codeSwitchingcapture la situation de variété mixteregisterspeut offrir des présets pour différents niveauxvarietiespeut lister la paire diglossique
Types d'Influence de Contact
| Type | Signification | Exemple |
|---|---|---|
superstrate | Langue dominante imposée à une communauté | Français → Anglais (post-1066) |
substrate | Langue native influençant une langue imposée | Celtique → Anglais |
adstrate | Langue voisine avec influence mutuelle | Norrois → Anglais |
learned_borrowing | Emprunts par l'éducation/l'érudition | Latin → Anglais |
lexical_borrowing | Emprunts de vocabulaire directs par contact | Espagnol → Philippin |
relexification | Remplacement de vocabulaire en gros | Portugais → Papiamento |
Profondeurs d'Influence de Contact
| Profondeur | Signification |
|---|---|
light | Quelques mots empruntés, impact structurel minimal |
moderate | Vocabulaire significatif dans des domaines spécifiques |
heavy | Vocabulaire omniprésent et certaines caractéristiques structurelles |
structural | Grammaire, syntaxe et phonologie affectées |
defining | Identité centrale façonnée par le contact (créoles, langues mixtes) |
Rédiger de Bons Présets de Registre
Bons présets d'invite :
- Nommer explicitement la caractéristique de formalité (par ex., « 해요체 », « forme vous », « forme siz »)
- Expliquer le pronom ou la forme verbale spécifique à utiliser
- Donner un contexte pour quand ce registre est approprié
- Mentionner les considérations de script si applicable
Ne pas mettre les conseils d'inclusion de genre dans l'invite de preset. Les conseils de genre
appartiennent à card.gender.inclusiveGuidance — ils sont injectés séparément.
❌ Bad: "Standard Thai. Professional register."
✔ Good: "Professional Thai. Use คุณ (khun) for second person, เรา (rao)
for first person when needed. Clear, concise phrasing
appropriate for digital interfaces."
Convention de Nommage des Presets
Les clés de preset doivent être descriptives et en minuscules avec tirets :
- Langues T-V :
formal-vous,informal-tu,formal-Sie,casual-du - Niveaux de discours :
polite-haeyo,formal-hapsyo,casual-hae - Neutre :
professional,neutral-professional - Alternance de code :
taglish-professional,pure-filipino
Procédure d'Enrichissement
Ordre de Traitement par Fiche
Lors de l'enrichissement d'une fiche, consultez les sources dans cet ordre. Documentez chaque source consultée, même si elle n'a retourné aucune donnée.
- Registre ISO 639-3 →
code,name,isoScope,isoType - ISO 639-3 macrolanguages.tab →
macrolanguage - Glottolog languoid.csv →
glottocode,classification,coordinates,countries - Glottolog CLDF →
macroarea,isIsolate,firstDocumented,lastDocumented - Glottolog AES →
vitality(statut d'endangérment) - Wikidata SPARQL →
nativeName,speakerEstimates,script,scripts,dir - CLDR →
rules(typographie, pluriels, capitalisation) - NLLB-200 / FLORES+ →
methodSupport.nllb,evalDatasets - Vérification API → entrées
methodSupportrestantes - Articles de modèles ML →
metricModelSupport(données d'entraînement XLM-R, couverture AfriCOMET) Script :node scripts/enrich-metric-model-support.mjs
Gestion des Conflits
Lorsque les sources divergent :
- Stocker les deux avec attribution de source
- Ne pas faire de moyenne ou prendre parti
- Noter la divergence dans le champ
notepertinent - Préférer la source primaire la plus récente uniquement lorsqu'une valeur unique est nécessaire pour le calcul
Validation
Exécutez le linter après tout enrichissement ou modification manuelle :
node scripts/lint-language-cards.mjs # all cards
node scripts/lint-language-cards.mjs --lang crk # single card
Liste de Contrôle de PR
Lors de la soumission d'une fiche langue nouvelle ou modifiée :
- Fichier nommé
<code>.jsondansshared/language-cards/ - Tous les champs de niveau supérieur du modèle canonique sont présents
-
classificationrempli à partir de Glottolog (pas construit à la main) -
dataSourcesliste toutes les sources consultées - Entrées
methodSupportvérifiées par rapport aux listes de langues API réelles - Entrées
contactInfluencesont des sources publiées oucitation_needed: true -
linguisticChallengesavec 3–6 défis pertinents pour la TA (si recherchés) -
rulesrempli à partir de CLDR (si les données de locale existent) - Le linter passe sans erreurs
Références Professionnelles
| Standard | Maintenu Par | Notre Utilisation |
|---|---|---|
| ISO 639-3 | SIL International | Codes de langue canoniques, relations de macrolangues |
| Glottolog | Max Planck Institute | Classification, coordonnées, endangérment AES |
| WALS | Max Planck Institute | Définitions de genre, caractéristiques typologiques |
| ISO 15924 | Unicode/ISO | Codes de script |
| CLDR | Unicode Consortium | Données de locale, règles de pluriel, typographie |
| Wikidata | Wikimedia Foundation | Comptages de locuteurs, endonymies, données de script |
| Ethnologue | SIL International | EGIDS, estimations de locuteurs, DLS |
| Atlas UNESCO | UNESCO | Classification d'endangérment |
| Katig Collective | UP Diliman | Capsules de langues philippines |
Voir aussi : Procédure de Citation de Fiche Langue pour des conseils détaillés source par source.