ADR 0088 – Accueil « Maintenant » côté front : layout focus, lignes de l'accueil, barre de charge découpée, digest et puces
Accepté (2026-10-17, dans le cadre de l'ADR 0086 §1 validé par Aurélien)
ADR 0088 – Accueil « Maintenant » côté front : layout focus, lignes de l’accueil, barre de charge découpée, digest et puces
Statut : Accepté (2026-10-17, dans le cadre de l’ADR 0086 §1 validé par Aurélien)
Suite de l’ADR 0087 (moteur de dashboards, côté backend). Cet ADR décrit ce que le front en fait : lignes A2 à A4 du backlog du jalon 4. Maquettes : canvas « Second Brain · Charte graphique », planche Accueil · Maintenant (web). L’enchaînement (chain), la coquille allégée et la version mobile détaillée sont les lignes suivantes du fil A.
Contexte
Le client généré porte DashboardDefinition.layout et capture, et sur les widgets column, split, chain, sources et items. Le front n’a aucune connaissance du domaine : il ne sait ni ce qu’est une tâche ni quel champ est une échéance. Tout ce qui suit se déduit des clés du YAML et des définitions déjà exposées.
Décision
Layout focus et capture
layout: focus: deux colonnes, principale 7/12 et latérale 5/12, chacune dans l’ordre du YAML. Un widget sanscolumnva dans la colonne principale. Sous 900 px, une seule colonne : la principale puis la latérale (l’ordre du DOM, sans réordonnancement CSS, donc le même pour les lecteurs d’écran). Le répartiteur est une fonction pure (focusColumns).capture: true: le composantQuickCaptureexistant passe dans l’en-tête, à droite de la date ; l’import de fichiers reste dessous. Sanscapture, la rangée de capture actuelle ne change pas. Sanslayout, la grille de deux colonnes de l’ADR 0038 est inchangée,widthy compris.
Lignes de l’accueil
Dans un dashboard focus, un widget view affiche ses lignes avec TaskRows au lieu de la liste de l’ADR 0030. Les colonnes se lisent par leur rôle déclaré dans le widget, pas par leur nom :
| Cellule | Source |
|---|---|
| Quand (« en retard · 7 j », « aujourd’hui », « demain », « dans 3 j »), en alerte si passé | le champ reschedule du widget |
| Estimation (« 45 min », « — » si absente) | le champ sum du widget |
| Contexte (projet…) avec une pastille de la couleur du type du nœud cité | les autres colonnes, hors title et type |
| Case « Fait » | une action rapide de la ligne qui écrit un état final du workflow de son aspect (workflow.final) ; absente si la ligne n’en offre pas |
| Bouton « Reporter » (demain) | présent si le widget déclare reschedule, même écriture que « Replanifier » (reschedule(), ADR 0038) |
- « Fait » passe par l’écriture annulable (ADR 0049, API des lots, action rapide ADR 0025) : « Annuler » reste proposé 10 secondes, les vues se relisent. Un refus du serveur (workflow, condition) s’affiche dans le widget.
- Configuration : l’aspect
tachegagne l’action rapide « Fait » (set: { statut: fait }), ajoutée en dernier pour ne pas déplacer l’index des actions existantes. Le front la reconnaît parce qu’elle écrit un état final, pas parce qu’elle s’appelle « Fait ». Une facture « Payée aujourd’hui » n’en est pas une (elle n’écrit pas le workflow) ; un autre aspect obtient sa case en déclarant une action vers un état final. - Le glisser vers « Demain » de l’ADR 0070 reste sur la liste des autres dashboards ; dans
focus, le bouton le remplace (cible tactile de 44 px sur téléphone).
Barre de charge découpée
Pour un widget view avec split (qui exige sum et capacity, ADR 0087) :
- le front évalue la condition
splitsur chaque ligne reçue et cumulesumen « en retard » (condition vraie) et « prévu » (les autres) ; « libre » est la capacité moins le total, jamais négative. La barre est colorée par la charte (alerte, accent, fond), jamais par le YAML ; - le texte devient « 4 h 10 engagées sur 6 h » (avec « au moins » quand la vue est tronquée, « (n sans estimation) » et « Trop chargé de … »), la légende donne les trois parts, le nom accessible de la barre les répète ;
- les totaux réutilisent la règle d’estimation de l’ADR 0070 (
dayLoad) : seules les valeurs numériques positives comptent, les autres sont comptées à part.
L’évaluateur (core/where-eval.ts) est un petit analyseur à descente récursive, testé, du sous-ensemble du langage where (ADR 0028) nécessaire :
- opérandes : champ de colonne, texte entre apostrophes (
''pour une apostrophe), nombre,true,false,null,todayetnowavec décalage± N d|w|m; - opérateurs :
== != < <= > >=,&& || !, parenthèses, et un champ booléen seul.
Limites assumées, documentées en tête du fichier :
- il ne lit que
ViewRow.values, donc les colonnes de la vue (le serveur l’impose au chargement poursplit, ADR 0087) ; un champ absent vautnull; - un ordre avec
nullou deux types différents est faux, comme en SQL ;!=avecnullest vrai ; - une date seule comparée à un instant se compare au jour local de l’instant ; deux instants se comparent par l’heure ;
todayest le jour du fuseau du navigateur, celui que le client envoie déjà au serveur pour les vues ;- les champs calculés,
nodeet toute syntaxe inconnue sont refusés (SplitUnsupported). Dans ce cas le widget retombe sur la barre simple (« Charge estimée : … sur 6 h ») sans casser l’accueil.
Si le langage where grandit, le serveur reste l’arbitre à l’écriture des définitions ; l’évaluateur front doit alors suivre, sinon la barre simple s’affiche. Le risque est un découpage faux sans erreur si la sémantique diverge sur un cas limite : la table des cas est dans where-eval.spec.ts.
Widget digest
- Une requête par source de vue, avec pour limite celle de la source plus celles des sources précédentes (au pire, toutes les lignes précédentes sont des doublons) :
digestFetchLimit. Le serveur ne dédoublonne pas (ADR 0087). - Première source gagnante : une ligne n’apparaît qu’une fois, dans la première source qui la porte ; chaque source montre au plus sa
limitlignes une fois les doublons retirés, sans être complétée au-delà (buildDigest, fonction pure). - L’affichage réutilise le composant de vue liste sans requête propre (ADR 0030) : une seule liste dont les colonnes et les références sont l’union de celles des sources.
ViewListgagne une entrée facultativetags(étiquette par id de nœud), rendue en puce devant le titre. - La puce prend la couleur du type du nœud (
data-node-type, charte C3), pas une couleur libre : la maquette montre des couleurs par source, la décision de l’ADR 0087 prévaut. - Une source en erreur est signalée (« Une vue est indisponible ») sans masquer les autres ; pendant un rechargement la dernière liste reste affichée.
Widget links
Des puces vers l’Inbox (/inbox, avec le compteur « à trier » de l’InboxStore), une revue (/reviews/<nom>) et une vue (/views/<nom>, compteur facultatif avec count: true, plafonné comme le widget counter). Une requête par vue comptée. Une puce sans cible reconnue est ignorée.
Fichiers
features/dashboards/ : focus-model.ts (répartition, digest, puces, libellé d’échéance, purs), task-rows.ts, load-bar.ts, focus-widgets.ts (DigestWidget, LinksWidget) ; ViewWidget gagne l’entrée focus ; core/where-eval.ts, core/day-plan.ts (splitLoad), core/quick-actions.ts (completionAction).
Alternatives écartées
- Reconnaître « Fait » par son libellé ou par le champ
statut: c’est du domaine dans le code. L’état final du workflow est déjà dans la définition. - Évaluer
splitpar une requête serveur : écarté dans l’ADR 0087 ; le front a déjà les lignes. - Une liste par source dans le digest : ne donnerait pas la liste unique étiquetée de la maquette et compliquerait le dédoublonnage.
- Réordonner les colonnes par CSS (
order) sur mobile : l’ordre visuel différerait de l’ordre de lecture.
Conséquences
- Aucune migration ; une action rapide ajoutée à
config/aspects/tache.yaml. /dashboards/aujourdhuireste atteignable et inchangé (grille de l’ADR 0038).- L’enchaînement (
chain), la coquille allégée, la barre basse mobile et le raffinement de la planche mobile restent à faire (lignes A5 et suivantes) :chainest lu mais pas encore affiché. - Limite connue, légende de la barre de charge : les libellés de
load-bar.ts(« Charge du jour », « engagées », « en retard », « libres ») sont écrits dans le composant, pas dans le YAML ; ils supposent une charge répartie en retard / du jour / libre. Les rendre configurables (cléslegenddu widget) demanderait une évolution du méta-schéma des dashboards ; ce n’est pas fait. Les autres libellés génériques de l’accueil et d’« Enchaîner » sont neutres (« terminé », « élément »). - Écarts de grammaire de
where-evalavec le serveur (guillemets doubles, nombres négatifs,(a) == brefusés ici ;== nullsur un champ nombre contenant du texte) : documentés en tête du fichier, sans effet sur les conditions acceptées des deux côtés ; une condition refusée donne la barre sans découpage.