Hébergement d'un site Node.js Express sur Firebase avec des modules ES

Cette page explique comment configurer, déployer et héberger un site web avec Express sur Firebase. Notez que nous utiliserons ECMAScript avec des modules (import from et export).

Je recommande fortement de comprendre les concepts suivants avant de lire ce guide.

Le guide présenté sur cette page a été testé avec les versions suivantes :

Nous supposerons que Node.js et npm sont déjà installés. Dans mon cas, j'ai utilisé Volta avec lequel vous pouvez sélectionner une version de Node.js en fonction du projet sur lequel vous travaillez.

Créer un projet Firebase

La première chose à faire est de créer un projet Firebase. Notez que pour déployer des fonctions, vous avez besoin de l'offre payante (Blaze). Dans la page the Firebase console de votre projet, ajoutez une application web.

Créez un dossier sur votre machine locale et installez firebase à l'intérieur :

npm install firebase

Si les outils CLI de Firebase ne sont pas encore installés, exécutez la commande suivante :

npm install -g firebase-tools

Connectez-vous à votre compte Firebase :

$ firebase login

Exécutez la commande suivante pour configurer votre projet firebase :

firebase init hosting
firebase init functions

Votre projet est configuré. Ajoutons Express.

Express

Vous n'avez pas besoin d'installer Express puisqu'il est déjà installé avec Firebase. Mais vous devrez modifier la configuration dans le fichier functions/package.json. Tout d'abord, puisque nous utilisons des modules ES, ajoutez la ligne suivante dans functions/package.json :

"type": "module",

Vérifiez la version de node dans functions/package.json et mettez-la à jour pour qu'elle corresponde à votre installation de Node.js (node -v pour obtenir votre version) :

"engines": {
    "node": "18"
},

Dans le fichier firebase.json, redirigez les URLs suivantes vers la fonction myApp :

  "hosting": {
    "public": "public",
    "ignore": [
      "firebase.json",
      "**/.*",
      "**/node_modules/**"
    ],
    "rewrites": [
      {
        "source": "/**",
        "dynamicLinks": true,
        "function": "myApp"
      },
    ]
  },

Maintenant, créez la fonction myApp qui va gérer la route /example/. Routeur. Remplacez le fichier /functions/index.js par le contenu suivant :

// Import Firebase functions
import functions from "firebase-functions";

// Import express
import express from "express";
const app = express();

import {exampleRouter} from "./example.js";
app.use("/example", exampleRouter);

export const myApp = functions.https.onRequest(app);

Vous avez probablement remarqué que le code ci-dessus charge un module nommé example.js. Créez le fichier functions/example.js avec le contenu suivant :

// Import the router
import express from "express";
const router = new express.Router();

// Route /example/
router.get("/", (req, res) => {
    res.send(`<h1>Example page</h1>`);
});

// Export the router
export const exampleRouter = router;

Exécutez la commande suivante pour démarrer votre serveur :

firebase serve

La commande devrait afficher quelque chose comme :

✔  hosting[fir-express-fac3d]: Local server: http://localhost:5000

Il s'agit de l'URL de votre serveur local. Allez sur http://localhost:5000/example/. Si vous voyez la page suivante, tout va bien :

Page d'exemple de Firebase avec Express

J'ai remarqué que la commande firebase serve ne détecte pas toujours les changements, en particulier dans les fichiers package.json et firebase.json. Si vous rencontrez des problèmes, n'hésitez pas à stopper et redémarrer la commande firebase serve.

Routes multiples

Comme nous utilisons des modules, il est maintenant facile de créer un nouveau module pour chaque itinéraire. Créons une API qui gérera le routage dynamique Créez le fichier functions/api.js avec le contenu suivant :

// Import the router
import express from "express";
const router = new express.Router();

// Route /api/
router.get("/", (req, res) => {
    res.send(`<h1>Root of /api/</h1>`);
});

// Route /api/:id
router.get("/:id", (req, res) => {
  res.send(`<h1>/api/${req.params.id}</h1>`);
});

// Export the router
export const apiRouter = router;

Mettez à jour le fichier functions/index.js avec la nouvelle route :

// Import Firebase functions
import functions from "firebase-functions";

// Import express
import express from "express";
const app = express();

// /example/
import {exampleRouter} from "./example.js";
app.use("/example", exampleRouter);

// /api/
import {apiRouter} from "./api.js";
app.use("/api", apiRouter);

// Export
export const myApp = functions.https.onRequest(app);

Maintenant, si vous entrez http://localhost:5000/api/ dans votre navigateur, vous devriez obtenir la page suivante :

Nouvelle route sous Firebase / Express avec des modules

Plus amusant : vous pouvez également gérer le routage dynamique. Allez sur http://localhost:5000/api/hello, vous devriez voir :

Nouvelle route dans Firebase et routage dynamique Express avec les modules ES

Enfin, si vous allez sur http://localhost:5000/, vous verrez que les pages statiques sont toujours servies :

Hébergement de pages statiques avec Express et Firebase

Conflits

Bien sûr, vous vous demandez probablement ce qui se passe si la même URL peut être servie par des fonctions et un hébergement statique ? Firebase vérifie d'abord dans le dossier public. Si la page n'existe pas, les fonctions sont appelées. Créez le dossier et le fichier public/api/index.html avec le contenu suivant :

<h1>Static page</h1>

Allez sur http://localhost:5000/api/:

Firebase sert une page statique avant d'appeler des fonctions

C'est bien la page statique qui est servie au client.

Téléchargement

Vous pouvez télécharger le projet final sur Github :

Projet sur GitHub.

Voir aussi


Dernière mise à jour : 28/04/2023