« Sur la mémoire unifiée du M4, taille de lot, longueur de contexte et cache KV partagent une même courbe budgétaire : choisissez d’abord la forme de charge, puis les paramètres exécutables — sinon vous livrez une démo qui marche une fois et un exploitant incapable de la reproduire la semaine suivante. »

Sur cette page : scénarios de sélection · lots et mémoire · acceptation et métriques · FAQ

Cette checklist s’applique à un Mac mini M4 ou équivalent Apple Silicon : elle relie choix de pile, bornes de lot et preuve reproductible avant passage sur nœud distant. Pour le contexte, ouvrez aussi llama.cpp contre Ollama, la matrice de routage multi-modèles, la matrice OpenTelemetry GenAI et le guide RAG : chunks et quotas vectoriels afin d’isoler générateur et indexation.

Scénarios de sélection

1. Interactif : latence de queue ; hors ligne : jetons/s soutenus ; recherche et fine-tuning : boucles Trainer, PEFT, checkpoints Hugging Face.

2. Embeddings, index et navigateur compètent avec le modèle ; sans plafonds, un lot « sûr » chute quand les prompts varient.

3. Préremplissage et décodage ne chargent pas la mémoire pareil ; ne mélangez pas interactif et batch dans un même processus.

Tableau d’aide — validez avec taille de modèle, quantification et tokenizer réels.

Scénario MLX-LM (MLX) Transformers (MPS)
Inférence Apple Silicon Souvent premier choix : MLX aligné sur mémoire unifiée ; lots et quant explicites. OK sur MPS ; surveillez lot, dtype, padding — mesurez E2E.
Stack Hugging Face entraînement Conversion et serving de poids ; training selon toolchain. Trainer, PEFT, Accelerate si fine-tuning fréquent.
Long contexte, sessions concurrentes KV sous une enveloppe ; politiques de cache explicites. Même KV ; processus séparés avec plafonds.
Avec Ollama / llama.cpp Piste MLX native ; ne confondez pas les CLI. Éval Python ; prod via matrice multi-modèles.

Le cache KV grossit avec séquence et couches ; le lot gonfle souvent la crête au préremplissage.

Tableau des lots et de la mémoire unifiée

Repères pour tests d’acceptation : couleur de pression dans le Moniteur d’activité, I/O swap, tenue stable d’au moins dix minutes — pas un classement d’une minute. Réservez de la marge pour macOS, navigateur et agents de télémétrie ; sur une configuration 24 Go typique, beaucoup d’équipes conservent 8 à 12 Go libres avant de valider un réglage comme « prêt production ».

Charge Lot et contexte de départ À surveiller dans la mémoire unifiée
Chat interactif (faible latence de queue) Lot 1 ; contexte au plus court compatible qualité. RSS de crête, couleur pression, I/O swap ; régressions sur le premier jeton.
Évaluation hors ligne ou export Augmenter le lot et max_tokens par paliers ; journaliser le débit à chaque étape. KV plus pics de préremplissage ; planifier hors jobs d’indexation.
Synthèse RAG Plafonner les jetons de chunks avant l’appel LLM ; séparer lot d’embedding et décodage. Crête combinée retriever et générateur ; voir la matrice RAG pour les quotas.

MLX-LM. Remplacez les identifiants ; --max-kv-size si disponible.

# Génération ponctuelle (CLI) python -m mlx_lm.generate --model ID_OU_CHEMIN_MODELE \ --prompt PROMPT.txt --max-tokens 512 --temp 0.7 # Service local (selon version mlx-lm) python -m mlx_lm.server --model ID_OU_CHEMIN_MODELE --port 8080

Transformers + MPS. PYTORCH_ENABLE_MPS_FALLBACK=1, dtype figé, padding et masque explicites si lot > 1.

export PYTORCH_ENABLE_MPS_FALLBACK=1 python - <<'PY' import torch from transformers import AutoModelForCausalLM, AutoTokenizer mid = "ORG/MODEL_ID" tok = AutoTokenizer.from_pretrained(mid) model = AutoModelForCausalLM.from_pretrained( mid, torch_dtype=torch.float16, device_map="mps" ) inputs = tok(["Bonjour le monde"], return_tensors="pt").to("mps") with torch.inference_mode(): out = model.generate(**inputs, max_new_tokens=128, do_sample=False) print(tok.decode(out[0], skip_special_tokens=True)) PY

Étapes d’acceptation et indicateurs de supervision

Étapes. (1) Geler révision, poids, tokenizer. (2) Scripts interactifs vs hors ligne ; p50/p95 séparés. (3) Journaliser jetons préremplissage/décodage, lot, device, cache, erreurs. (4) Crête mémoire, swap, thermique. (5) Champs alignés OTel GenAI. (6) Soak 2–4 h sur hôte dédié (veille, Spotlight).

Métriques. time_to_first_token, tokens_per_sec_decode, proxy kv_cache_bytes, mem_pressure_peak, oom_or_fallback_count. Seuils sur régression vs baseline, pas constante universelle.

  • Réussi : débit dans la bande, pas de swap prolongé, SLA respecté.
  • À creuser : décodage avec GPU idle — bande passante ou lot.
  • Échec : swap soutenu, repli MPS répété, file non bornée.

FAQ

MLX-LM et Transformers sur le même M4 ? Oui, à condition de séparer les processus et d’imposer des plafonds mémoire ou de concurrence : sinon la bande passante mémoire unifiée se partage sans signal clair et les deux piles se sabotent mutuellement en charge.

Lot ≠ débit observé ? Les phases préremplissage et décodage sollicitent des chemins différents ; la réutilisation du cache KV déplace le point de coude. Mesurez et journalisez chaque phase plutôt qu’une moyenne unique sur la session.

Après acceptation locale ? Archivez scripts, versions de modèle et noms de métriques dans le runbook de routage, puis rejouez le même paquet sur un nœud Mac mini M4 distant pour valider disque, horloge et stabilité longue durée avant d’exposer du trafic client.

Sans compte : tarifs, achat, accueil, aide.

Synthèse : le scénario choisit la pile dominante ; le lot et le KV déterminent si la mémoire unifiée reste exploitable ; scripts reproductibles plus champs d’observabilité transforment la démo ponctuelle en livrable.