Le templating de mon "composant" est cassé. Comment le réparer ?

Dans une instance Discourse que j’administre, j’ai un composant (hérité de l’ancien mainteneur de l’instance) pour afficher les logos des sponsors de cette instance dans le pied de page. Le composant fonctionnait bien jusqu’à récemment, mais il est maintenant rendu de manière incorrecte, affichant littéralement les directives de contrôle du modèle (et insérant littéralement les espaces réservés aux valeurs du modèle dans le HTML, de sorte que les chemins vers les images ne sont pas résolus) :

Le composant n’est pas maintenu dans un dépôt git, il est configuré directement sous « Admin » → « Appearance » → « Themes & components » → onglet « Components » :

Custom Code

Custom sections:

  • Common: CSS, Footer, JS

Uploads

Extra files

Export theme to view these files.
  • javascripts/discourse/api-initializers/theme-initializer.gjs

contenu de ces « sections »

tel que vu en cliquant sur « Edit Code » ; chemin vers les fichiers correspondants dans l’exportation indiqué entre parenthèses

CSS (common/common.scss)
.sponsors {
    .inner {
        display: flex;
        align-items: center;
        justify-content: space-around;
        margin-bottom: 10px;
    }

    .heading {
        font-size: 1.75em;
    }

    .sponsor-image {
        max-height: 55px;
    }

    .geoaargau {
        max-height: 45px;
    }
}
Footer (common/footer.html)
  {{#if displaySponsors}}
    <div class="sponsors-wrapper wrap">
      <div class="inner">
        <h3 class="heading">Sponsoren</h3>
        <a href="http://www.asseco-berit.ch/"><img src="{{theme-setting "theme_uploads.asseco_berit"}}" alt="Asseco Berit" class="sponsor-image asseco-berit"></a>
        <a href="http://www.geoaargau.ch/"><img src="{{theme-setting "theme_uploads.geoaargau"}}" alt="GEOAargau" class="sponsor-image geoaargau"></a>
      </div>
    </div>
  {{/if}}
JS (javascripts/discourse/api-initializers/theme-initializer.gjs)
import { apiInitializer } from "discourse/lib/api";

export default apiInitializer((api) => {
  // This is the plugin outlet, followed by a custom name for the component
  api.registerConnectorClass("above-footer", "sponsors", {

    setupComponent(args, component) {
        
     var topMenuRoutes = 
        component.siteSettings.top_menu.split('|')
        .map(function(route) {return '/' + route});
      
     var homeRoute = topMenuRoutes[0];
     
     api.onPageChange((url) => {

        if (url === "/" || url === homeRoute ){ 
          document.querySelector("html").classList.add("sponsors"); 
          component.set("displaySponsors", true); 
        } else {
          document.querySelector("html").classList.remove("sponsors"); 
          component.set("displaySponsors", false); 
        }
      });
    }
    
  });
});

L’exportation contient en plus :
about.json (466 Bytes)
ce que je suppose être généré à la volée lors de l’exportation, donc je ne pense pas que ce soit pertinent.

La partie pertinente du DOM effectif avec cette rupture est :

<div class="custom-footer-content">
    {{#if displaySponsors}}
    <div class="sponsors-wrapper wrap">
      <div class="inner">
        <h3 class="heading">Sponsoren</h3>
        <a href="http://www.asseco-berit.ch/"><img src="{{theme-setting " theme_uploads.asseco_berit"}}" alt="Asseco Berit" class="sponsor-image asseco-berit"></a>
        <a href="http://www.geoaargau.ch/"><img src="{{theme-setting " theme_uploads.geoaargau"}}" alt="GEOAargau" class="sponsor-image geoaargau"></a>
      </div>
    </div>
  {{/if}}
</div>

nous pouvons donc voir que la directive de contrôle {{#if ...}}...{{/if}} et les espaces réservés {{theme-setting "..."}} ont été utilisés comme HTML littéral plutôt que d’être exécutés / évalués / interpolés.

Comment et pourquoi cela a-t-il changé et comment dois-je le corriger ?

Est-ce peut-être lié à Upcoming Header Changes - Preparing Themes and Plugins? (Bien que je ne voie pas de changements dans la syntaxe de templating mentionnés là-dedans.)

1 « J'aime »

(Par « comment et pourquoi » je veux dire : Quel a été le changement sous-jacent, et ai-je manqué des notifications à ce sujet ? Je suis suffisamment sûr que ce qui a causé ce changement de comportement est arrivé dans cette instance par les mises à jour automatiques de Discourse activées, mais je voudrais connaître la cause profonde.)

Y a-t-il une erreur ou un avertissement dans la console pour fournir plus d’informations ?

1 « J'aime »

Dans la console du navigateur ? Peut-être — Je ne suis pas sûr de ce qui est « normal » là-dedans et de ce qui pourrait indiquer le problème. Puis-je simplement coller son contenu ici ou cela pourrait-il fuiter des informations sensibles ?

Oui, la console du navigateur – vous pouvez y coller :slight_smile: Souvent, si quelque chose est obsolète, la console affiche des informations utiles.

1 « J'aime »
Contenu complet de la console du navigateur lors du chargement de https://www.geowebforum.ch/c/feedback/2
ℹ️ Discourse v2026.3.0-latest — https://github.com/discourse/discourse/commits/38ad2acd2c — Ember v6.6.0 chunk.f47b6dc1cc59c827db42.d41d8cd9.js:275:35231
[PLUGIN discourse-weekly-newsletter] Pour éviter les erreurs dans les tests, ajoutez une clé `pluginId` à votre appel `modifyClass`. Cela garantira que la modification n'est appliquée qu'une seule fois. chunk.f47b6dc1cc59c827db42.d41d8cd9.js:209:136918
DEPRECATION NOTICE: Définir des classes de connecteur via registerConnectorClass est obsolète. Consultez https://meta.discourse.org/t/32727 pour des modèles plus modernes. [deprecation id: discourse.register-connector-class-legacy] chunk.f47b6dc1cc59c827db42.d41d8cd9.js:134:74065
Erreur lors de l'analyse de la valeur pour ‘-webkit-text-size-adjust’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:1:800
Erreur lors de l'analyse de la valeur pour ‘-moz-text-size-adjust’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:1:827
Propriété inconnue ‘text-size-adjust’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:1:849
Pseudo-classe ou pseudo-élément inconnu ‘-moz-focus-inner’. Règleset ignoré en raison d'un sélecteur incorrect. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:1:1615
’none’, URL ou fonction de filtre attendus mais trouvés ‘alpha(’. Erreur lors de l'analyse de la valeur pour ‘filter’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:622
Ruleset ignoré en raison d'un sélecteur incorrect. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:36117
Erreur lors de l'analyse de la valeur pour ‘justify-content’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:181379
Erreur lors de l'analyse de la valeur pour ‘text-wrap’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:205516
Erreur lors de l'analyse de la valeur pour ‘image-rendering’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:264428
Erreur lors de l'analyse de la valeur pour ‘-webkit-text-size-adjust’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:268491
Erreur lors de l'analyse de la valeur pour ‘-moz-text-size-adjust’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:268518
Propriété inconnue ‘text-size-adjust’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:268540
Erreur lors de l'analyse de la valeur pour ‘font-size’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:298136
’none’, URL ou fonction de filtre attendus mais trouvés ‘alpha(’. Erreur lors de l'analyse de la valeur pour ‘filter’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:447258
’none’, URL ou fonction de filtre attendus mais trouvés ‘alpha(’. Erreur lors de l'analyse de la valeur pour ‘filter’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:4:447681
’none’, URL ou fonction de filtre attendus mais trouvés ‘alpha(’. Erreur lors de l'analyse de la valeur pour ‘filter’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:6:33799
Erreur lors de l'analyse de la valeur pour ‘text-wrap’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:6:105390
Erreur lors de l'analyse de la valeur pour ‘text-wrap’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:6:105471
Erreur lors de l'analyse de la valeur pour ‘padding’. Déclaration supprimée. common_6dfc7bba61f3a7b80a86f119f30594abc84aaa6d.css:6:257744

Je suppose que je dois consulter Using Plugin Outlet Connectors from a Theme or Plugin

Donc, je pense que registerConnectorClass avec setupComponent est déprécié, voyez votre journal d’erreurs :

DEPRECATION NOTICE: Defining connector classes via registerConnectorClass is deprecated. See https://meta.discourse.org/t/32727 for more modern patterns. [deprecation id: discourse.register-connector-class-legacy] chunk.f47b6dc1cc59c827db42.d41d8cd9.js:134:74065

et je ne suis pas sûr que nous tolérions encore le HTML brut, comme dans votre composant de pied de page.

Ce composant devra donc être refactorisé selon les modèles modernes, et je vous conseillerais de le déplacer vers un composant approprié également, par opposition à l’endroit où il se trouve actuellement sous Administration.

Pour répondre à votre autre question

C’est dû au travail en cours de modernisation de Discourse et au passage à de nouvelles normes modernes avec les composants Glimmer.

3 « J'aime »

Si ce n’est pas du HTML brut (-template), quel est le contenu attendu de https://www.geowebforum.ch/admin/customize/themes/3/common/footer/edit ? Du Markdown, comme dans le contenu fourni par l’utilisateur ?

Pouvez-vous m’indiquer où trouver des informations sur la façon de le faire ? Je me sens un peu perdu car la documentation de Discourse semble éparpillée sur l’ensemble du méta-forum.

Pour cela, puis-je simplement décompresser “l’export” et le mettre dans un dépôt Git ?

Mon composant n’est-il pas déjà un composant Glimmer s’il contient un fichier *.gjs dans l’export ? Ou est-ce en fait le problème – Discourse actuel prenant mon composant pour un composant Glimmer (et l’exportant donc avec ce nom de fichier) bien qu’il ne le soit pas encore en termes de code ?

(Veuillez excuser mon ignorance. Je ne suis pas développeur web et je ne connais presque rien à Ember et Glimmer.)

1 « J'aime »

Je voulais dire : le HTML brut n’est plus correctement analysé avec la dernière version, par conséquent, vous voyez simplement le HTML déversé au lieu d’être rendu.

Oui, le fichier .gjs indiquait bien un composant glimmer, mais la méthode utilisée de registerConnectorClass dedans ne fonctionnera pas (ou plus)

C’est tout à fait compréhensible. Ce que dit Using Plugin Outlet Connectors from a Theme or Plugin essentiellement, c’est que, pour rendre des informations quelque part sur la page via cette méthode registerConnectorClass, la manière dont votre fichier footer.html le faisait, nous utilisons maintenant un élément spécifique, appelé plugin outlet (sortie de plugin). Pour un pied de page, l’outlet above-footer fonctionnerait bien.

C’est probablement une bonne idée de lire Beginner's guide to using Discourse Themes et Developing Discourse Themes & Theme Components

Cela peut aussi aider de jeter un œil à un composant de thème simple, pour comprendre la structure. Par exemple : GitHub - discourse/discourse-minimal-footer · GitHub

Et enfin, le bot Discourse pourrait vous aider énormément : il connaît bien les schémas Discourse, vous pouvez donc lui donner votre code actuel, lui expliquer le problème et lui demander de vous aider à le refactoriser.

2 « J'aime »