Nous avons récemment migré nos applications Ember.js sous Embroider, le nouveau builder pour Ember.js. Embroider offre une fonctionnalité intéressante appelée “route splitting”, qui permet d’envoyer uniquement les fichiers JavaScript nécessaires pour une ou un groupe de routes. Cela réduit la taille du JavaScript téléchargé par les utilisateurs, à condition que le découpage des routes soit bien pensé.
Cependant, l’activation de cette fonctionnalité nécessite plusieurs options, dont staticComponents
,
qui a pour effet de résoudre tous les composants nécessaires et de les inclure dans la construction finale.
En activant cette option et en suivant le guide de migration pour les composants helpers, les tests unitaires de nos composants ne passaient plus.
Le défi des tests unitaires avec Embroider et les composants Glimmer
Lors de la migration vers les composants Glimmer, nous nous étions rendu compte que Glimmer ne supportait plus nativement les tests unitaires, nous avions utilisé une parade proposée par la communauté sur le Discord d’Ember, que vous pouvez retrouver en détail sur cet article et dont voici la solution :
import { getContext } from '@ember/test-helpers';
import GlimmerComponentManager from '@glimmer/component/-private/ember-component-manager';
export default function createComponent(lookupPath, named = {}) {
const { owner } = getContext();
const { class: componentClass } = owner.factoryFor(lookupPath);
const componentManager = new GlimmerComponentManager(owner);
return componentManager.createComponent(componentClass, { named });
}
Qui permet dans un test unitaire de faire :
const component = createComponent('component:component-name', { argument });
Cette solution est désormais obsolète, car avec Embroider et l’option staticComponents
la méthode factoryFor
ne retourne rien.
Cela parait cohérent avec la volonté d’Embroider qui souhaite créer des builds statiques analysables.
Une nouvelle solution avec importSync de @embroider/macros
La nouvelle solution que nous utilisons se sert d’importSync
proposé par @embroider/macros
,
qui permet à Embroider de signaler l’existence d’un module et de l’inclure dans le build.
Voici donc le code avec la modification :
import { getContext } from '@ember/test-helpers';
import GlimmerComponentManager from '@glimmer/component/-private/ember-component-manager';
import { importSync } from '@embroider/macros';
export default function createComponent(lookupPath, named = {}) {
const { owner } = getContext();
const componentClass = importSync(`../../components/${lookupPath}`).default;
const componentManager = new GlimmerComponentManager(owner);
return componentManager.createComponent(componentClass, { named });
}
Et son usage
const component = createComponent('component-name', { argument });
Grâce à cette simple modification, nous pouvons à nouveau continuer de tester unitairement nos composants Glimmer et commencer à utiliser les fonctionnalités proposées par Embroider.