broken image
broken image
broken image
  • A propos
  • Portfolio
  • Blog
  • Références
  • Nocodext
  • Bubble plugins
  • Medes IE
  • …  
    • A propos
    • Portfolio
    • Blog
    • Références
    • Nocodext
    • Bubble plugins
    • Medes IE
    Contactez-moi
    broken image
    broken image
    broken image
    • A propos
    • Portfolio
    • Blog
    • Références
    • Nocodext
    • Bubble plugins
    • Medes IE
    • …  
      • A propos
      • Portfolio
      • Blog
      • Références
      • Nocodext
      • Bubble plugins
      • Medes IE
      Contactez-moi
      broken image

      Import dynamique d'une lib de Charts dans Bubble

      · Blog posts

      Une amie développe un dashboard contenant des graphiques

      Malgré une configuration adéquate, son graphique refuse de s'afficher.

      A partir de là 10000 questions peuvent se posent sur "pourquoi" ?

      Allez hop c'est parti pour une session de 1h de mentorat.

      En général le point de départ c'est de partir...du début.
      Ouais ok sans blague merci pour cette belle tautologie.


      Commencons par le "trivial", on peut déjà écarter un paquet d'hypothèses d'un revers de manche.
      D'abord on questionne la dispo de la ressource
      Ensuite on questionne la configuration de la ressource

      Dans cet exemple de code, on distingue tout de suite un vrai problème...

      broken image

      myChart peut (ou pas du tout) être disponible au moment de son instanciation.


      Extrait d'un petit dialogue intérieur :

      - Comment ca il est pas dispo ? ben si ya "new Chart" donc c'est bon.
      - pas forcément : c'est pas parce que il est instancié qu'il ...existe
      - ben si il existe : la preuvre, ya son script d'import en haut.

      - ok mais tu touches bien là toute la problématique : entre le moment où Chart est importé et disponible dans le DOM (via window.Chart), et le moment où il est instancié, c'est pas dit que les 2 soit bien synchro.

      "Synchro" ha ba tiens ca me fait une super transition pour expliquer le fond du problème.

      Ici en effet le code ne se soucie pas de savoir si Chart est dispo. Il considère qu'il l'est. Point.

      Et ben non :

      si Chart avait été importé dans le bloc header la page web, OK ca fonctionnerait comme ca:

      1. d'abord je charge les scripts (les CSS, les meta...) du header

      2. ensuite seulement j'interprête le body.
      ...


      Mais dans le code ci-dessus, l'import n'est pas placé dans le bloc header, il est placé et executé au beau milieu de la page, donc il est asynchrone.

      Le code lui n'attend pas l'import asynchrone. Donc suivant la vivacité du réseau, y a de fortes chances que code et lib se croisent sans se capter. Des fois oui des fois non. Aléatoire.
      (tout ce qu'on déteste)

      "Ah oui c'est comme une course de relais : si j'attend pas que mon binôme arrive et me passe le relai en main, je vais pas aller bien loin".

      Voila une belle analogie dis-donc pour expliquer la notion de couplage et dépendance.

      C'est vrai ? ah ben ca fait plaisir merci

      De rien, bref...

      Bon c'est bien joli tout ca mais une question me brûle les lèvres : comment on attend ??

      En asynchrone ya 2 manières d'attendre, et donc 2 écoles :

      - probabiliste VS déterminisite

      Probabiliste

      -> c'est la méthode dite du doigt mouillé :
      exemple typique :

      "ba on va se dire que ca va probablement pas prendre plus d'une seconde pour s'importer, au-dela ca serait vraiment abusé.....mais espérons que ca abuse pas"

      dans les fait tu mets un setTimeout de 1000ms "comme ca t'es large" et hop tu executes la fonction qui setup le Chart. Ca devrait passer crème (...ou pas).

      De mon point de vue c'est la méthode à la fois bien foireuse, non fiable et très présomptueuse.

      C'est cette illusion envers soi-même de maitriser son environnement alors que -> que dalle

      (pour plein d'autres usecases l'ami setTimeout c'est ok hein...mais pas là)

      Déterministe

      "je ne vais pas pseudo-décider que l'import va prendre X secondes , car soyons honnêtes j'en sais foutre rien, je suis incapable de contrôler cette latence car ca dépend du CDN et donc d'un serveur distant, du réseau, c'est lent, instable, et imprévisible. Je ne peux pas garantir ce que je ne peux pas contrôler. Fort de ce constat, j'ai besoin qu'un tiers (en l'occurence pas moi) soit en mesure de garantir quand l'import sera fait. Et aussi quand il ne sera pas possible (CDN indispo, ...)"

      C'est la méthode où j'encadre l'incertitude.

      Alors je sais pas vous mais moi je vais suivre la méthode déterministe :D

      Et ben figurez que dans l'API standard Javascript ya une méthode aussi méconnue que géniale qui fait exactement ce job : import()

      Elle fait quoi ? pareil que < script src > mais programmatique.


      - de manière asynchrone via une bonne vieille Promise :

      • elle importe la lib via l'URL qu'on lui donne
      • on lui colle un callback dans sa fonction chainée then() (si Promesse tenue -> exec callback)
      • un callback dans la fonction chainée catch() pour gérer si ca aboutira pas (si Promesse non tenue/tenable)

      Voila c'est ce then() de import(url).then() qui à la fois force l'attente ET qui va garantir que la lib Charts est disponible.
      Et ca veut dire que le callback du then() ne sera executée que si la Promesse d'import est tenue. Donc la fonction de setup de Chart (= le callbackà) ne sera executée que si Chart est bien importé.


      OK ton exemple résoud nickel la problématique pour 1 charts.

      Mais si j'ai au moins 2 Charts, je fais comment parce que là je risque de re-importer une lib qui a déjà été importée auparavant. J'ai pas envie de faire ça mais je sais pas comment faire autrement.

      Alors j'ai déjà donné un indice subliminal dans mon explication ci-dessus :

      lorsque la lib est importée, elle devient disponible dans window.Chart.
      Si elle est pas dispo, la prop est undefined. Simple.
      et window c'est l'objet racine global de la page, qui contient tout.

      Donc tu peux faire comme ca :

      if (window.Chart === undefined){
      // import + setup
      import(url).then(initChart);
      }
      else {
      // setup direct
      initChart()
      }
      ou encore en monde inlined :
      window.Chart && initChart()

      et au final on aboutit toujours à initChat.
      Et en plus on duplique même pas accidentellement le code de setup du Chart.
      Et ca c'est cool.

      Par contre garde en tête que l'import dynamique est à considérer comme une solution "on-the-fly".
      Autrement dit, si t'en a besoin en one-shot c'est bon, mais au dela c'est pas une bonne pratique,
      car dans l'exemple que je te donne, on trimbale à la fois la gestion l'import ET l'execution.
      Or dans un usage "classique" la lib est déjà dispo en global, on gère QUE le setup du Chart.

      Ah ben justement si je pousse le bouchon : je veux non pas 2 mais 3 charts.


      Ok là tu commences à industrialiser l'usage des Charts.
      il est temps de rendre l'import et la disponibilité de Chart de manière globale au site ou à la page sans recourir à l'import dynamique avec import().

      Il faut mettre une balise statique dans le bloc header. Statique par oppositon à dynamique : en HTML. Dispo à 1 endroit, instancié N fois.

      Voila la résolution finale :

      broken image

      S'abonner
      Billet précédent
      Billet suivant
      Bubble & graphQL : la désillusion
       Revenir au site
      strikingly iconPropulsé par Strikingly
      Photo de profil
      Annuler
      Utilisation des cookies
      Nous utilisons des cookies pour améliorer l'expérience de navigation, la sécurité et la collecte de données. En acceptant, vous consentez à l'utilisation de cookies à des fins publicitaires et d'analyse. Vous pouvez modifier vos paramètres de cookies à tout moment. En savoir plus
      Accepter tout
      Paramètres
      Refuser Tout
      Paramètres des Cookies
      Cookies nécessaires
      Ces cookies sont destinés pour des fonctionnalités de base telles que la sécurité, la gestion du réseau et l'accessibilité. Ces cookies ne peuvent pas être désactivés.
      Cookies pour les statistiques
      Ces cookies nous aident à mieux comprendre comment les visiteurs interagissent avec notre site web et nous aident à découvrir les erreurs de navigation.
      Préférence pour les Cookies
      Ces cookies permettent au site web de se souvenir des choix que vous avez faits afin de fournir une fonctionnalité et une personnalisation améliorées.
      Enregistrer