InfraGuard

Thème clair / sombre

Basculez la console entre clair et sombre — un unique attribut data-theme sur la racine, conservé dans localStorage (infr-theme), un bouton dans la barre supérieure et toutes les couleurs sous forme de jetons de variables CSS --infr-*.

Vue d’ensemble — à quoi ça sert

La console InfraGuard est livrée avec deux thèmes : sombre (par défaut) et clair. Le thème se change par un unique attribut posé sur la racine du document (<html>), data-theme, dont la valeur permute l’ensemble des jetons de variables CSS --infr-* définis en SCSS. Tous les composants utilisent des jetons var(--infr-*) plutôt que des valeurs hexadécimales en dur : changer un seul mot (dark ↔ light) repeint donc instantanément toute l’interface.

La valeur par défaut est sombre — en tant que console de NOC (centre d’exploitation réseau), elle utilise un fond bleu-noir profond avec des accents de signal turquoise, afin que les couleurs de gravité (crit / warn / good) ressortent nettement sur un fond sombre.

<html data-theme="dark">   ← par défaut, sombre NOC
<html data-theme="light">  ← clair (environnements de bureau lumineux)

Le thème est une préférence purement front-end. Il n’est jamais stocké sur le serveur et n’a aucun rapport avec votre compte ni avec la base de données — il vit uniquement dans le localStorage du navigateur. Il survit à la déconnexion et, si quelqu’un se connecte avec le même compte depuis un autre appareil, cet appareil suit son propre réglage.


Quand l’utiliser

Une fois choisi, il persiste dans ce navigateur : vous ne le réglez donc normalement qu’une seule fois.


Disposition

Bouton de bascule dans la barre supérieure

L’enveloppe de la console (layouts/app.blade.php) comme l’écran de connexion (layouts/simple.blade.php) placent un bouton de changement de thème à droite de la barre supérieure.

Élément Valeur
Point d’accroche dans le balisage <button data-theme-toggle>
Icône mdi-theme-light-dark (demi-lune)
aria-label msg.action.theme (localisé)
Action Un clic bascule sombre ↔ clair
Position Zone d’actions de la barre supérieure (à côté du sélecteur de langue, à gauche du menu utilisateur)

L’écran avant connexion (invité) porte le même bouton : vous pouvez donc changer de thème sans vous authentifier.

Groupes de jetons de couleur

resources/scss/_variables.scss définit les mêmes noms de jetons avec des valeurs différentes dans deux blocs : :root[data-theme="dark"] et :root[data-theme="light"]. Jetons représentatifs :

Jeton Rôle dark light
--infr-bg Fond de page #0b1220 #f6f8fb
--infr-surface Surface de panneau / carte #111b2c #ffffff
--infr-fg Texte courant #e9eff8 #111a28
--infr-fg-muted Texte secondaire #8493ac #63728b
--infr-border Bordures #1e2c43 #dbe2ec
--infr-accent Accent (turquoise) #2dd4bf #0d9488
--infr-crit Gravité critique #fb7185 #e11d48
--infr-warn Gravité avertissement #fbbf24 #b45309
--infr-good Gravité saine #34d399 #0f9d6a
--infr-info Information #38bdf8 #0369a1

Au-delà de ceux-ci, chaque thème définit aussi --infr-surface-2/hi, --infr-border-2, --infr-accent-soft/ink, --infr-on-accent (texte de bouton sur l’accent), les couleurs d’état TCP (--infr-state-*), les couleurs de graphique (--infr-chart-2), l’ombre et la lueur (--infr-shadow / --infr-glow), ainsi que le verre de la barre supérieure (--infr-topbar-*). Chaque bloc déclare également color-scheme: dark|light afin que les contrôles de formulaire natifs et les barres de défilement s’accordent au thème.

La palette du terminal SSH fait exception. Les jetons --infr-term-* restent d’un sombre profond et immersif quel que soit data-theme. Même en thème clair, la console SSH conserve un terminal sombre.


Mode d’emploi

Basculer

  1. Cliquez sur l’icône demi-lune (Changer de thème) à droite de la barre supérieure.
  2. Elle bascule immédiatement sombre ↔ clair, et le choix est enregistré automatiquement.
  3. À la visite suivante ou au rechargement de la page, votre dernier choix est restauré.

Sous le capot (référence développeur)

Le front-end est câblé dans resources/js/app.js. Logique principale :

const THEME_KEY = 'infr-theme';                 // clé de localStorage
const get_theme = () => localStorage.getItem(THEME_KEY) || 'dark';   // sombre par défaut
const set_theme = (t) => {
    document.documentElement.setAttribute('data-theme', t);   // attribut de la racine
    localStorage.setItem(THEME_KEY, t);                        // persister
    window.dispatchEvent(new CustomEvent('infr:theme', { detail: t })); // recolorer les graphiques
};
// câbler le bouton de bascule
document.querySelectorAll('[data-theme-toggle]')
    .forEach(btn => btn.addEventListener('click',
        () => set_theme(get_theme() === 'dark' ? 'light' : 'dark')));

Résumé du comportement :

Étape Quoi
Clé de stockage localStorage['infr-theme'] = "dark" | "light"
Appliqué à attribut data-theme sur document.documentElement (le <html>)
Par défaut dark (lorsque localStorage est vide ou illisible)
Événement Chaque bascule déclenche un CustomEvent infr:theme sur window (detail = thème courant)
Synchronisation entre onglets Écoute l’événement storage → les autres onglets du même navigateur se synchronisent automatiquement

Prévention du flash de contenu non stylé (FOUC) — script exécuté avant le rendu

Un minuscule script en ligne tout en haut de <head> (partagé par app.blade.php et simple.blade.php, avant le chargement CSS par @vite) fixe data-theme avant qu’aucune feuille de style ne s’applique. Cela supprime le « flash sombre→clair » au rechargement.

<script>
  (function () {
    try { document.documentElement.setAttribute('data-theme',
            localStorage.getItem('infr-theme') || 'dark'); }
    catch (e) { document.documentElement.setAttribute('data-theme', 'dark'); }
  })();
</script>

Même là où localStorage est bloqué (navigation privée, stockage tiers bloqué, etc.), le catch retombe sans risque sur sombre.

Les graphiques et les éditeurs suivent le thème

<cm-editor v-model="script.body" lang="bash" :dark="is_dark_mode"></cm-editor>

Sources de données

Le thème n’a strictement aucun stockage en base ni côté serveur. Il n’utilise que :

Emplacement Contenu
localStorage['infr-theme'] Choix de l’utilisateur, par navigateur (dark/light)
<html data-theme> État appliqué à l’exécution
resources/scss/_variables.scss Valeurs réelles des jetons --infr-* pour chaque thème (compilées dans le CSS)
resources/js/app.js Bascule / persistance / câblage des événements

L’annexe C (jetons du thème clair/sombre) de CLAUDE.md fait référence pour la conception de la palette.


Accès

Le thème est une préférence d’interface sans rapport avec l’authentification ni l’autorisation.


Dépannage et FAQ

Q. Le thème est réinitialisé au rechargement. Si le navigateur bloque localStorage (navigation privée, réglages de confidentialité stricts, blocage du stockage tiers), le choix ne peut pas être enregistré et il revient à chaque fois au sombre par défaut. Accordez l’accès au stockage pour le site.

Q. Je l’ai changé dans un onglet, mais un autre onglet ne s’est pas mis à jour. La bascule se propage aux autres onglets du même navigateur via l’événement storage. Si ce n’est pas répercuté immédiatement, cet onglet n’a peut-être pas encore chargé le câblage de l’écouteur (app.js) — rechargez-le. Des appareils/navigateurs différents ont des stockages distincts et ne se synchronisent pas (c’est voulu).

Q. Je suis passé en clair, mais le terminal SSH reste sombre. C’est le comportement attendu. Le terminal utilise une palette dédiée --infr-term-* qui reste très sombre quel que soit le thème de l’application (lisibilité / immersion).

Q. Un composant s’affiche mal (le thème ne s’y applique pas). Ce composant a codé en dur des valeurs hexadécimales au lieu d’utiliser les jetons. Par convention, les composants ne doivent utiliser que des jetons var(--infr-*). Recherchez les valeurs hexadécimales directes dans resources/scss/pages avec le grep de non-régression :

rg -n "#[0-9a-fA-F]{3,6}" resources/scss/pages

Q. Je veux qu’il suive le mode sombre de mon système d’exploitation. L’implémentation actuelle ne suit pas la préférence du système (prefers-color-scheme). La valeur initiale est toujours dark, et elle ne mémorise que ce que l’utilisateur a explicitement choisi avec le bouton. L’intégration au système figure à la feuille de route.


Voir aussi

상단바 오른쪽의 테마 · 언어 전환
상단바 오른쪽의 테마 · 언어 전환