Catégories
Plugin et site web

Simplifiez votre pile avec un générateur de site statique sur mesure – Smashing Magazine

A propos de l'auteur

Bryan est un concepteur, développeur et éducateur passionné par les CSS et les sites statiques. Il travaille activement pour encadrer et enseigner aux développeurs et aux concepteurs la valeur…
Plus à propos
Bryan
Robinson

Dans le développement moderne, il existe de nombreux outils formidables pour développer des sites Web, mais ils sont souvent plus que ce qui est nécessaire pour un projet donné. Dans cet article, nous allons explorer comment prendre une humble page HTML et rendre son contenu modifiable dans un CMS sans framework et sans JavaScript côté client.

Avec l'avènement du mouvement Jamstack, les sites à service statique sont redevenus à la mode. La plupart des développeurs proposant du HTML statique ne créent pas de HTML natif. Pour avoir une solide expérience de développeur, nous nous tournons souvent vers des outils appelés Static Site Generators (SSG).

Ces outils sont dotés de nombreuses fonctionnalités qui rendent la création de sites statiques à grande échelle agréable. Qu'elles fournissent des connexions simples à des API tierces telles que les sources de données de Gatsby ou fournissent une configuration approfondie comme l'énorme collection de moteurs de modèles de 11ty, il y en a pour tous les goûts dans la génération de sites statiques.

Étant donné que ces outils sont conçus pour divers cas d'utilisation, ils doivent avoir de nombreuses fonctionnalités. Ces fonctionnalités les rendent puissants. Ils les rendent également assez complexes et opaques pour les nouveaux développeurs. Dans cet article, nous allons ramener le SSG à ses composants de base et créer le nôtre.

Qu'est-ce qu'un générateur de site statique?

À la base, un générateur de site statique est un programme qui effectue une série de transformations sur un groupe de fichiers pour les convertir en actifs statiques, tels que HTML. Quel type de fichiers il peut accepter, comment il les transforme et quels types de fichiers sortent différencient les SSG.

Jekyll, un SSG précoce et toujours populaire, utilise Ruby pour traiter les modèles Liquid et les fichiers de contenu Markdown en HTML.

Gatsby utilise React et JSX pour transformer les composants et le contenu en HTML. Il va alors plus loin et crée une application d'une seule page qui peut être servie de manière statique.

11ty rend le HTML à partir de moteurs de création de modèles tels que Liquid, Handlebars, Nunjucks ou des littéraux de modèle JavaScript.

Chacune de ces plates-formes possède des fonctionnalités supplémentaires pour nous faciliter la vie. Ils fournissent des thèmes, construisent des pipelines, une architecture de plugins, etc. Avec chaque fonctionnalité supplémentaire vient plus de complexité, plus de magie et plus de dépendances. Ce sont des fonctionnalités importantes, bien sûr, mais tous les projets n'en ont pas besoin.

Entre ces trois SSG différents, nous pouvons voir un autre thème commun: données + modèles = site final. Cela semble être la fonctionnalité de base des sites statiques générateurs. C'est la fonctionnalité sur laquelle nous baserons notre SSG.

À la base, un générateur de site statique est un programme qui effectue une série de transformations sur un groupe de fichiers pour les convertir en actifs statiques, comme HTML.

Notre nouvelle pile technologique de générateur de site statique: guidons, Sanity.io et Netlify

Pour créer notre SSG, nous avons besoin d'un moteur de modèles, d'une source de données et d'un hôte capable d'exécuter notre SSG et de créer notre site. De nombreux générateurs utilisent Markdown comme source de données, mais que se passerait-il si nous allions plus loin et connections nativement notre SSG à un CMS?

  • Source de données: Sanity.io
  • Récupération de données et création de modèles: nœud et guidon
  • Hôte et déploiement: Netlify.

Conditions préalables

  • NodeJS installé
  • Compte Sanity.io
  • Connaissance de Git
  • Connaissance de base de la ligne de commande
  • Connaissance de base du déploiement sur des services comme Netlify.

Remarque: Pour suivre, vous pouvez trouver le code dans ce référentiel sur GitHub.

Configurer notre structure de document en HTML

Pour commencer la structure de notre document, nous allons écrire du HTML brut. Pas besoin de compliquer encore les choses.

Dans la structure de notre projet, nous devons créer un endroit pour vivre nos fichiers source. Dans ce cas, nous allons créer un src répertoire et mettez notre index.html à l'intérieur.

Dans index.html, nous allons décrire le contenu que nous voulons. Ce sera une page à propos relativement simple.



    
    
    Title of the page!


    

The personal homepage of Bryan Robinson

Some pagraph and rich text content next

Bryan is on the internet

Gardons cela simple. Nous allons commencer par un h1 pour notre page. Nous suivrons cela avec quelques paragraphes d'informations biographiques, et nous ancrerons la page avec une liste de liens pour en savoir plus.

Convertissez notre HTML en un modèle qui accepte les données

Une fois que nous avons notre structure de base, nous devons mettre en place un processus pour combiner cela avec une certaine quantité de données. Pour ce faire, nous utiliserons le moteur de modèles Handlebars.

À la base, Handlebars prend une chaîne de type HTML, insère des données via des règles définies dans le document, puis génère une chaîne HTML compilée.

Pour utiliser Handlebars, nous devons initialiser un package.json et installer le package.

Courir npm init -y pour créer la structure d'un fichier package.json avec un contenu par défaut. Une fois que nous avons cela, nous pouvons installer Handlebars.

npm install handlebars

Notre script de construction sera un script Node. C'est le script que nous utiliserons localement pour créer, mais également ce que notre fournisseur de déploiement et notre hôte utiliseront pour créer notre code HTML pour le site en ligne.

Pour démarrer notre script, nous allons créer un index.js fichier et nécessitent deux packages en haut. Le premier est Handlebars et le second est un module par défaut dans Node pour accéder au système de fichiers actuel.

const fs = require('fs');
const Handlebars = require('handlebars');

Nous utiliserons le fs module pour accéder à notre fichier source, ainsi que pour écrire dans un fichier de distribution. Pour commencer notre build, nous allons créer un main fonction pour que notre fichier s'exécute lorsqu'il est appelé et un buildHTML fonction pour combiner nos données et notre balisage.

function buildHTML(filename, data) {
  const source = fs.readFileSync(filename,'utf8').toString();
  const template = Handlebars.compile(source);
  const output = template(data);

  return output
}

async function main(src, dist) {
  const html = buildHTML(src, { "variableData": "This is variable data"});
 
  fs.writeFile(destination, html, function (err) {
    if (err) return console.log(err);
      console.log('index.html created');
  });
}

main('./src/index.html', './dist/index.html');

le main() La fonction accepte deux arguments: le chemin de notre modèle HTML et le chemin que nous voulons que notre fichier construit vive. Dans notre fonction principale, nous exécutons buildHTML sur le chemin de la source du modèle avec une certaine quantité de données.

La fonction de génération convertit le document source en une chaîne et transmet cette chaîne à Handlebars. Handlebars compile un modèle en utilisant cette chaîne. Nous passons ensuite nos données dans le modèle compilé et Handlebars rend une nouvelle chaîne HTML remplaçant toutes les variables ou la logique du modèle par la sortie de données.

Nous renvoyons cette chaîne dans notre main fonction et utilisez la writeFile méthode fournie par le module de système de fichiers de Node pour écrire le nouveau fichier à l’emplacement spécifié si le répertoire existe.

Pour éviter une erreur, ajoutez un dist répertoire dans votre projet avec un .gitkeep fichier dedans. Nous ne voulons pas valider nos fichiers construits (notre processus de compilation le fera), mais nous voudrons nous assurer d'avoir ce répertoire pour notre script.

Avant de créer un CMS pour gérer cette page, confirmons qu'il fonctionne. Pour tester, nous allons modifier notre document HTML pour utiliser les données que nous venons de lui transmettre. Nous utiliserons la syntaxe de la variable Handlebars pour inclure le variableData contenu.

{{ variableData }}

Maintenant que notre HTML a une variable, nous sommes prêts à exécuter notre script de nœud.

node index.js

Une fois le script terminé, nous devrions avoir un fichier à /dist/index.html. Si nous lisons ouvrir ceci dans un navigateur, nous verrons notre balisage rendu, mais aussi notre chaîne "Ceci est des données variables".

Connexion à un CMS

Nous avons un moyen de rassembler des données avec un modèle, maintenant nous avons besoin d'une source pour nos données. Cette méthode fonctionnera avec n'importe quelle source de données dotée d'une API. Pour cette démo, nous utiliserons Sanity.io.

Sanity est une première source de données API qui traite le contenu comme des données structurées. Ils disposent d'un système de gestion de contenu open source pour rendre la gestion et l'ajout de données plus pratiques pour les éditeurs et les développeurs. Le CMS est ce que l’on appelle souvent un CMS «sans tête». Au lieu d'un système de gestion traditionnel où vos données sont étroitement couplées à votre présentation, un CMS headless crée une couche de données qui peut être consommée par n'importe quel frontal ou service (et peut-être plusieurs en même temps).

Sanity est un service payant, mais ils ont un plan «Standard» qui est gratuit et a toutes les fonctionnalités dont nous avons besoin pour un site comme celui-ci.

Configurer la santé mentale

Le moyen le plus rapide de démarrer avec un nouveau projet Sanity est d'utiliser la CLI Sanity. Nous commencerons par l'installer à l'échelle mondiale.

npm install -g @sanity/cli

La CLI nous donne accès à un groupe d'assistants pour la gestion, le déploiement et la création. Pour commencer, nous allons exécuter sanity init. Cela nous conduira à travers un questionnaire pour aider à démarrer notre Studio (ce que Sanity appelle leur CMS open-source).

Select a Project to Use:
   Create new project
   HTML CMS

Use the default dataset configuration?   
   Y // this creates a "Production" dataset

Project output path:
   studio // or whatever directory you'd like this to live in

Select project template
   Clean project with no predefined schemas

Cette étape créera un nouveau projet et un nouveau jeu de données dans votre compte Sanity, créera une version locale de Studio et liera les données et le CMS pour vous. Par défaut, le studio Le répertoire sera créé à la racine de notre projet. Dans les projets à plus grande échelle, vous souhaiterez peut-être le configurer en tant que référentiel distinct. Pour ce projet, c'est bien de garder cela lié.

Pour exécuter notre Studio localement, nous allons changer le répertoire dans le studio répertoire et exécutez sanity start. Cela exécutera Studio à localhost:3333. Lorsque vous vous connectez, un écran s'affiche pour vous informer que vous avez "Schéma vide". Avec cela, il est temps d'ajouter notre schéma, qui est la façon dont nos données seront structurées et modifiées.

Création d'un schéma d'intégrité

La façon dont vous créez des documents et des champs dans Sanity Studio consiste à créer des schémas dans le schemas/schema.js fichier.

Pour notre site, nous allons créer un type de schéma appelé "À propos des détails". Notre schéma découlera de notre HTML. En général, nous pourrions faire de la plupart de notre page Web un seul champ de texte enrichi, mais il est recommandé de structurer notre contenu de manière découplée. Cela offre une plus grande flexibilité dans la façon dont nous pourrions vouloir utiliser ces données à l'avenir.

Pour notre page Web, nous voulons un ensemble de données comprenant les éléments suivants:

  • Titre
  • Nom complet
  • Biographie (avec édition de texte riche)
  • Une liste de sites Web avec un nom et une URL.

Pour définir cela dans notre schéma, nous créons un objet pour notre document et définissons ses champs. Une liste annotée de notre contenu avec son champ type:

  • Titre – chaîne
  • Nom complet – chaîne
  • Biographie – tableau de «blocs»
  • Liste de sites Web – tableau d'objets avec des champs de nom et de chaîne d'URL.
types: schemaTypes.concat((
    /* Your types here! */

    {
        title: "About Details",
        name: "about",
        type: "document",
        fields: (
            {
                name: 'title',
                type: 'string'
            },
            {
                name: 'fullName',
                title: 'Full Name',
                type: 'string'
            },
            {
                name: 'bio',
                title: 'Biography',
                name: 'content',
                type: 'array',
                of: (
                    {
                        type: 'block'
                    }
                )
            },
            {
                name: 'externalLinks',
                title: 'Social media and external links',
                type: 'array',
                of: (
                    {
                        type: 'object',
                        fields: (
                            { name: 'text', title: 'Link text', type: 'string' },
                            { name: 'href', title: 'Link url', type: 'string' }
                        )
                    }
                )
            }
        )
    }
))

Ajoutez ceci à vos types de schémas, enregistrez et votre Studio se recompilera et vous présentera vos premiers documents. À partir de là, nous ajouterons notre contenu dans le CMS en créant un nouveau document et en remplissant les informations.

Structurer votre contenu de manière réutilisable

À ce stade, vous vous demandez peut-être pourquoi nous avons un «nom complet» et un «titre». C'est parce que nous voulons que notre contenu ait le potentiel d'être polyvalent. En incluant un champ de nom au lieu d'inclure le nom uniquement dans le titre, nous donnons plus d'utilisation à ces données. Nous pouvons ensuite utiliser les informations de ce CMS pour alimenter également une page de CV ou un PDF. Le champ biographie pourrait être utilisé par programme dans d'autres systèmes ou sites Web. Cela nous permet d'avoir une seule source de vérité pour une grande partie de ce contenu au lieu d'être dicté par le cas d'utilisation directe de ce site particulier.

Transférer nos données dans notre projet

Maintenant que nous avons rendu nos données disponibles via une API, intégrons-les à notre projet.

Installer et configurer le client JavaScript Sanity

Tout d'abord, nous devons accéder aux données dans Node. Nous pouvons utiliser le client JavaScript Sanity pour forger cette connexion.

npm install @sanity/client

Cela récupérera et installera le SDK JavaScript. À partir de là, nous devons le configurer pour récupérer les données du projet que nous avons configuré précédemment. Pour ce faire, nous allons configurer un script utilitaire dans /utils/SanityClient.js. Nous fournissons au SDK notre ID de projet et le nom de l'ensemble de données, et nous sommes prêts à l'utiliser dans notre script principal.

const sanityClient = require('@sanity/client');
const client = sanityClient({
    projectId: '4fs6x5jg',
    dataset: 'production',
    useCdn: true 
  })

module.exports = client;

Récupérer nos données avec GROQ

De retour dans notre index.js fichier, nous allons créer une nouvelle fonction pour récupérer nos données. Pour ce faire, nous utiliserons le langage de requête natif de Sanity, le GROQ open source.

Nous allons créer la requête dans une variable, puis utiliser le client que nous avons configuré pour récupérer les données en fonction de la requête. Dans ce cas, nous construisons un objet avec une propriété appelée about. Dans cet objet, nous voulons renvoyer les données de notre document spécifique. Pour ce faire, nous interrogeons en fonction du document _id qui est généré automatiquement lorsque nous créons notre document.

Pour trouver le document _id, nous naviguons vers le document dans Studio et le copions depuis l'URL ou passons en mode «Inspecter» pour afficher toutes les données du document. Pour accéder à Inspect, cliquez sur le menu "kabob" en haut à droite ou utilisez le raccourci Ctrl + Alt + je. Cette vue répertorie toutes les données de ce document, y compris notre _id. Sanity renverra un tableau d’objets de document. Par souci de simplicité, nous renverrons le 0th entrée.

Nous transmettons ensuite la requête au fetch méthode de notre client Sanity et il renverra un objet JSON de toutes les données de notre document. Dans cette démo, renvoyer toutes les données n'est pas un gros problème. Pour les implémentations plus importantes, GROQ permet une «projection» facultative pour ne renvoyer que les champs explicites que vous souhaitez.

const client = require('./utils/SanityClient') // at the top of the file

// ...

async function getSanityData() {
    const query = `{
        "about": *(_id == 'YOUR-ID-HERE')(0)
    }`
    let data = await client.fetch(query);
}

Conversion du champ de texte enrichi en HTML

Avant de pouvoir renvoyer les données, nous devons effectuer une transformation sur notre champ de texte enrichi. Alors que de nombreux CMS utilisent des éditeurs de texte enrichi qui renvoient directement du HTML, Sanity utilise une spécification open-source appelée Portable Text. Le texte portable renvoie un tableau d'objets (pensez au texte enrichi comme une liste de paragraphes et d'autres blocs multimédias) avec toutes les données sur le style du texte enrichi et les propriétés telles que les liens, les notes de bas de page et d'autres annotations. Cela permet à votre texte d'être déplacé et utilisé dans des systèmes qui ne prennent pas en charge HTML, comme les assistants vocaux et les applications natives.

Pour notre cas d'utilisation, cela signifie que nous devons transformer l'objet en HTML. Il existe des modules NPM qui peuvent être utilisés pour convertir du texte portable en diverses utilisations. Dans notre cas, nous utiliserons un package appelé block-content-to-html.

npm install @sanity/block-content-to-html

Ce package rendra tout le balisage par défaut de l'éditeur de texte enrichi. Chaque type de style peut être remplacé pour se conformer au balisage dont vous avez besoin pour votre cas d'utilisation. Dans ce cas, nous laisserons le package faire le travail pour nous.

const blocksToHtml = require('@sanity/block-content-to-html'); // Added to the top

async function getSanityData() {
    const query = `{
        "about": *(_type == 'about')(0)
    }`
    let data = await client.fetch(query);
    data.about.content = blocksToHtml({
        blocks: data.about.content
    })
    return await data
}

Utilisation du contenu de Sanity.io dans les guidons

Maintenant que les données sont sous une forme que nous pouvons utiliser, nous allons les transmettre à notre buildHTML fonction comme argument de données.

async function main(src, dist) {
    const data = await getSanityData();
    const html = buildHTML(src, data)

    fs.writeFile(dist, html, function (err) {
        if (err) return console.log(err);
        console.log('index.html created');
    });
}

Maintenant, nous pouvons changer notre HTML pour utiliser les nouvelles données. Nous utiliserons davantage d'appels de variables dans notre modèle pour extraire la plupart de nos données.

Pour rendre notre texte riche content variable, nous devrons ajouter une couche supplémentaire d'accolades à notre variable. Cela indiquera à Handlebars de rendre le HTML au lieu d'afficher le HTML sous forme de chaîne.

Pour notre externalLinks , nous devrons utiliser la fonctionnalité de bouclage intégrée de Handlebars pour afficher tous les liens que nous avons ajoutés à notre Studio.




    
    
    {{ about.title }}


    

The personal homepage of {{ about.fullName }}

{{{ about.content }}}

Bryan is on the internet

Configuration du déploiement

Mettons cela en direct. Nous avons besoin de deux composants pour que cela fonctionne. Premièrement, nous voulons un hôte statique qui construira nos fichiers pour nous. Ensuite, nous devons déclencher une nouvelle version de notre site lorsque le contenu est modifié dans notre CMS.

Déploiement sur Netlify

Pour l'hébergement, nous utiliserons Netlify. Netlify est un hôte de site statique. Il sert des actifs statiques, mais possède des fonctionnalités supplémentaires qui permettront à notre site de fonctionner correctement. Ils ont une infrastructure de déploiement intégrée qui peut exécuter notre script de nœud, des webhooks pour déclencher des builds et un CDN distribué à l'échelle mondiale pour s'assurer que notre page HTML est servie rapidement.

Netlify peut regarder notre référentiel sur GitHub et créer une compilation basée sur une commande que nous pouvons ajouter dans leur tableau de bord.

Tout d'abord, nous devons transmettre ce code à GitHub. Ensuite, dans le tableau de bord de Netlify, nous devons connecter le nouveau référentiel à un nouveau site dans Netlify.

Une fois que cela est connecté, nous devons dire à Netlify comment construire notre projet. Dans le tableau de bord, nous allons accéder à Paramètres> Créer et déployer> Paramètres de compilation. Dans ce domaine, nous devons changer notre «commande de construction» en «noeud index.js» et notre «répertoire de publication» en «./dist».

Lorsque Netlify construit notre site, il exécute notre commande, puis vérifie le dossier que nous répertorions pour le contenu et publie le contenu à l'intérieur.

Configurer un Webhook

Nous devons également dire à Netlify de publier une nouvelle version lorsque quelqu'un met à jour le contenu. Pour ce faire, nous allons configurer un Webhook pour informer Netlify que nous avons besoin de la reconstruction du site. Un Webhook est une URL accessible par programme par un autre service (tel que Sanity) pour créer une action dans le service d'origine (dans ce cas Netlify).

Nous pouvons configurer un «hook de construction» spécifique dans notre tableau de bord Netlify dans Paramètres> Build & Deploy> Build hooks. Ajoutez un hook, donnez-lui un nom et enregistrez. Cela fournira une URL qui peut être utilisée pour déclencher à distance une construction dans Netlify.

Ensuite, nous devons dire à Sanity de faire une demande à cette URL lorsque vous publiez des modifications.

Nous pouvons utiliser la CLI Sanity pour accomplir cela. À l'intérieur de notre /studio répertoire, nous pouvons exécuter sanity hook create se connecter. La commande demandera un nom, un ensemble de données et une URL. Le nom peut être celui que vous souhaitez, l'ensemble de données doit être production pour notre produit, et l'URL doit être l'URL fournie par Netlify.

Désormais, chaque fois que nous publions du contenu dans Studio, notre site Web sera automatiquement mis à jour. Aucun cadre nécessaire.

Prochaines étapes

Ceci est un très petit exemple de ce que vous pouvez faire lorsque vous créez votre propre outillage. Si des SSG plus complètes peuvent être ce dont vous avez besoin pour la plupart des projets, la création de votre propre mini-SSG peut vous aider à mieux comprendre ce qui se passe dans le générateur de votre choix.

  • Ce site ne publie qu'une seule page, mais avec un petit plus dans notre script de construction, nous pourrions le faire publier plus de pages. Il pourrait même publier un article de blog.
  • L '«expérience développeur» fait un peu défaut dans le référentiel. Nous pourrions exécuter notre script Node sur n'importe quel fichier sauvegardé en implémentant un paquet comme Nodemon ou ajouter un «rechargement à chaud» avec quelque chose comme BrowserSync.
  • Les données qui vivent dans Sanity peuvent alimenter plusieurs sites et services. Vous pouvez créer un site de CV qui l'utilise et publie un PDF au lieu d'une page Web.
  • Vous pouvez ajouter du CSS et faire en sorte que cela ressemble à un vrai site.
Éditorial fracassant(ra, yk, il)

Laisser un commentaire

Votre adresse de messagerie ne sera pas publiée. Les champs obligatoires sont indiqués avec *