Réponse courte

Par défaut, Ollama décharge un modèle de la mémoire après 5 minutes d’inactivité. Pour garder un modèle chargé indéfiniment sur macOS, il faut définir la variable d’environnement OLLAMA_KEEP_ALIVE via launchctl — pas un export dans .zshrc, qu’Ollama Desktop (une app GUI) ne voit jamais. Comme launchctl setenv se réinitialise à chaque redémarrage, la solution fiable est un LaunchAgent qui pose la variable et lance Ollama Desktop dans une séquence maîtrisée, à chaque login.

Pourquoi export OLLAMA_KEEP_ALIVE=-1 dans .zshrc ne fonctionne pas

C’est l’erreur la plus courante en essayant de configurer le keep-alive d’Ollama sur Mac. Voici pourquoi ça échoue :

  • Ollama Desktop est une application GUI. Les apps GUI macOS n’héritent pas des variables définies dans les fichiers de config shell (.zshrc, .bash_profile, .zprofile).
  • Seules les variables posées via launchctl setenv sont visibles par les apps GUI lancées depuis le Finder, Spotlight ou la barre de menu.
  • Les valeurs posées par launchctl setenv sont limitées à la session — elles disparaissent à chaque redémarrage, la correction doit donc se relancer automatiquement à chaque login.
  • Même quand la variable est bien posée, si Ollama Desktop démarre avant qu’elle ne soit en place (un problème d’ordre de démarrage), il retombe silencieusement sur le délai par défaut de 5 minutes.

Étape par étape : configurer OLLAMA_KEEP_ALIVE de façon permanente avec un LaunchAgent

La méthode la plus fiable est un unique LaunchAgent qui exécute toute la séquence de démarrage dans le bon ordre : poser la variable → lancer Ollama → attendre le serveur → précharger le modèle.

1. Désactiver le lancement automatique d’Ollama Desktop au login

La version actuelle d’Ollama Desktop n’a pas d’option “lancer au démarrage” dans ses propres réglages. Il faut la désactiver au niveau système : Réglages Système → Général → Éléments de connexion et extensions, puis désactiver Ollama dans la liste des éléments de connexion. Ça évite que les deux mécanismes se concurrencent.

2. Créer le fichier LaunchAgent

Enregistrer ceci sous ~/Library/LaunchAgents/com.user.ollama-keepalive.plist :

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>Label</key>
    <string>com.user.ollama-keepalive</string>
    <key>ProgramArguments</key>
    <array>
        <string>/bin/sh</string>
        <string>-c</string>
        <string>launchctl setenv OLLAMA_KEEP_ALIVE -1 &amp;&amp; open -a Ollama &amp;&amp; for i in $(seq 1 30); do curl -s http://localhost:11434/api/tags &gt;/dev/null 2&gt;&amp;1 &amp;&amp; break; sleep 1; done &amp;&amp; /usr/local/bin/ollama run qwen2.5:14b "" &gt;/dev/null 2&gt;&amp;1</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
    <key>StandardOutPath</key>
    <string>/tmp/ollama-keepalive.out</string>
    <key>StandardErrorPath</key>
    <string>/tmp/ollama-keepalive.err</string>
</dict>
</plist>

À personnaliser avant utilisation :

  • Remplacer qwen2.5:14b par le nom de ton modèle (liste disponible via ollama list).
  • Vérifier le chemin du binaire ollama avec which ollama — le PATH d’un LaunchAgent diffère de celui d’un shell interactif.
  • Définir OLLAMA_KEEP_ALIVE à -1 (pour toujours) ou une durée précise comme 24h.

Erreur de syntaxe fréquente : && doit être écrit &amp;&amp; dans un fichier .plist. Un && non échappé casse le XML silencieusement.

3. Valider et charger le LaunchAgent

plutil -lint ~/Library/LaunchAgents/com.user.ollama-keepalive.plist
launchctl bootstrap gui/$(id -u) ~/Library/LaunchAgents/com.user.ollama-keepalive.plist

4. Vérifier que le modèle reste chargé

ollama ps

Le champ UNTIL doit afficher Forever (ou la durée choisie) à côté du modèle — même après plusieurs minutes d’inactivité.

Gérer le LaunchAgent : aide-mémoire des commandes

ActionCommande
Charger le LaunchAgentlaunchctl bootstrap gui/$(id -u) ~/Library/LaunchAgents/com.user.ollama-keepalive.plist
Décharger le LaunchAgentlaunchctl bootout gui/$(id -u)/com.user.ollama-keepalive
Forcer une exécution immédiatelaunchctl kickstart -k gui/$(id -u)/com.user.ollama-keepalive
Voir le statut détaillé (nombre d’exécutions, code de sortie, env)launchctl print gui/$(id -u)/com.user.ollama-keepalive
Vérifier la valeur actuelle de la variablelaunchctl getenv OLLAMA_KEEP_ALIVE

Après toute modification du .plist, il faut toujours faire un bootout puis un bootstrap — recharger un job déjà enregistré ne prend pas en compte les changements du fichier.

Diagnostiquer un OLLAMA_KEEP_ALIVE qui ne fonctionne pas

Si le modèle continue de se décharger après 5 minutes malgré cette configuration, vérifie dans cet ordre :

  1. Le LaunchAgent s’est-il réellement exécuté ?

    launchctl print gui/$(id -u)/com.user.ollama-keepalive | grep -E "runs|last exit"
    

    runs ≥ 1 et last exit code = 0 confirment une exécution réussie.

  2. Vérifier les logs du script :

    cat /tmp/ollama-keepalive.out
    cat /tmp/ollama-keepalive.err
    
  3. Confirmer que le serveur Ollama a bien reçu le réglage :

    grep -i keep_alive ~/.ollama/logs/server.log | tail -3
    

    Doit afficher -1s (ou la valeur choisie), pas 5m0s (valeur par défaut).

  4. Le test en conditions réelles : redémarrer complètement le Mac, se reconnecter, et vérifier ollama ps sans aucune action manuelle. C’est le seul test qui écarte définitivement un problème de timing au login.

FAQ

Est-ce que OLLAMA_KEEP_ALIVE=-1 garde le modèle chargé pour toujours ? Oui, -1 indique au serveur Ollama de ne jamais décharger le modèle pour cause d’inactivité. Il se déchargera toujours si tu exécutes ollama stop <modèle> ou si le serveur redémarre.

Pourquoi launchctl setenv seul ne survit-il pas à un redémarrage ? launchctl setenv écrit uniquement dans l’environnement de la session de login en cours. Ce n’est pas persisté sur disque, donc ça doit être réappliqué à chaque login — exactement ce que fait la clé RunAtLoad du LaunchAgent.

Est-ce que le paramètre keep_alive d’un appel API écrase OLLAMA_KEEP_ALIVE ? Oui. Toute valeur keep_alive envoyée dans une requête /api/generate ou /api/chat prend le pas sur le réglage global OLLAMA_KEEP_ALIVE pour cet appel précis. Si un outil client envoie systématiquement sa propre valeur, ton réglage global sera ignoré pour ses requêtes.

Peut-on précharger automatiquement un modèle au démarrage ? Oui — le LaunchAgent ci-dessus le fait en exécutant ollama run <modèle> "" (un prompt vide) une fois que le serveur est confirmé comme répondant, ce qui force le modèle en mémoire sans attendre une vraie requête utilisateur.