Cas pratiques
Installer Node.js, npm et Yarn dans un pack
Un pack outillage : versions figées et surchargeables, exposées comme des commandes natives.
Ce tutoriel construit un pack nodejs qui installe Node.js, npm et Yarn dans des
versions précises, et expose trois commandes — node, npm, yarn — utilisables
directement depuis le host, sans rien installer sur la machine elle-même.
Pourquoi un pack pour ça ?
Installer Node.js, npm et Yarn directement sur une machine pose toujours la même question : quelle version, et pour combien de temps ? Un projet fige des versions précises, un autre en exige d’autres ; nvm ou des installations manuelles finissent par cohabiter tant bien que mal.
Un pack nodejs déplace le problème : la toolchain est décrite une fois, dans un
xbee-pack.yaml versionné (potentiellement dans son propre dépôt Git, partagé par
toute une équipe), avec des versions par défaut qui restent
surchargeables projet par projet — sans jamais toucher à
la machine hôte. Une fois provisionné puis installé (voir plus bas), il s’utilise comme
un outil natif : xbee node, xbee npm, xbee yarn. Contrairement au pack hello des
tutoriels précédents, pensé pour un service qu’on démarre/arrête (up/down), ce
pack-ci est un outil qu’on invoque à la demande — il n’a besoin ni d’up, ni de down,
ni même d’un environnement.
Créer le pack
xbee new pack nodejs
cd nodejsÉcrire le xbee-pack.yaml
schema-version: "1.0"
description: "Toolchain Node.js : node, npm et yarn, dans des versions figées et surchargeables."
require: ubuntu:24.04
var:
node:
version: "20"
npm:
version: "10.4.0"
yarn:
version: "1.22.19"
provision: |
apt-get update
wget -qO- https://deb.nodesource.com/setup_{{ .node.version }}.x | bash -
DEBIAN_FRONTEND=noninteractive apt-get install -y nodejs
npm install -g npm@{{ .npm.version }} yarn@{{ .yarn.version }}
command:
node: node
npm: npm
yarn: yarnvar.node.version,var.npm.versionetvar.yarn.versionfont partie du modèle de données du pack : ce sont ces valeurs par défaut qu’un projet surchargera pour figer ses propres versions — voir plus bas.provisionregroupe les commandes shell qui installent réellement Node.js, npm et Yarn dans l’image — l’étape qui construit l’image du pack lui-même, juste après celle du système (provision system) ; voir Packs.deploy, qui construit lui aussi sa propre image par-dessus, sert plutôt à intégrer une couche applicative buildée à partir de code source — sans build à intégrer ici, il n’a pas lieu d’être : mieux vaut toujours remonter au niveauprovisionquand il n’y a rien à construire, seulement à installer.up,downetconfigurerestent eux aussi inutiles : ce pack n’est pas un service.command.node,command.npmetcommand.yarnexposent trois commandes de pack (xbee <cmdPack>), chacune un raccourci Shell vers le binaire correspondant. Les arguments passés après le nom de la commande lui sont transmis tels quels — comme dans l’exemplexbee --name tom catalina rundes Commandes CLI.
{{ .node.version }}, {{ .npm.version }} et {{ .yarn.version }} sont interpolés au
moment de l’exécution de provision — voir
Modèle de données. Lors de la
création de l’image du pack, le modèle de données résulte de la fusion de const et
var : les templates y accèdent directement, sans préfixe var. ni const..
Provisionner
xbee packprovision system prépare ubuntu:24.04, puis provision installe Node.js, npm et
Yarn dans les versions déclarées — voir Packs.
build (aucune dépendance builder) et deploy (aucune couche applicative à
intégrer) n’ont ici rien à faire.
Exposer les commandes du pack
Le xbee-pack.yaml décrit les commandes du pack — node, npm, yarn — mais ne les
expose pas : tant que le pack n’est pas installé, xbee node --version échoue, même
depuis le répertoire du pack lui-même. Deux façons de l’installer — voir
Installer un pack :
xbee install <chemin-ou-origin>expose ses commandes globalement, utilisables depuis n’importe quel répertoire. Sans projet associé, chaque appel doit alors monter lui-même son répertoire sur/xbee/app, le répertoire par défaut de.xbee.app(voir le tutoriel Pack minimal) — au format-v hôte:containerdes Commandes CLI — et fixer un--namepour réutiliser le même container d’un appel à l’autre :xbee install ./nodejs xbee npm -v .:/xbee/app --name nodetools install xbee node -v .:/xbee/app --name nodetools app.js xbee yarn -v .:/xbee/app --name nodetools add lodashpackage.json,node_modulesou tout autre fichier créé par ces commandes restent sur le host, dans le répertoire monté — pas dans le container.Mieux, pour un projet : un
xbee-install.yamlréférence le pack une fois pour toutes, et n’expose ses commandes que dans son propre répertoire — chaque appel y reçoit en plus ce répertoire monté automatiquement sur/xbee/app, sans jamais préciser-vni--name. C’est cette seconde approche que suit la suite de ce tutoriel.
Une mini application, avec xbee-install.yaml
Créez un nouveau répertoire, à côté de nodejs/ (pas dedans) :
mkdir hello-express
cd hello-expressÉcrire le xbee-install.yaml
schema-version: "1.0"
pack: ../nodejspackréférence le packnodejsde ce tutoriel, avec la même syntaxe que lepackd’un hôte d’environnement — voir Utiliser le pack dans un environnement — y compris la forme longueorigin/var, pour surcharger les versions depuis ce projet sans toucher au packnodejs.- Dès que ce fichier est présent, les commandes qu’expose
nodejs—node,npm,yarn— s’invoquent directement depuis ce répertoire, chacune avec ce répertoire monté sur/xbee/app: plus besoin de-vni de--name.
xbee node --version
xbee npm --version
xbee yarn --versionChaque appel démarre un container xbee, y exécute la commande, puis rend la main — un outil qui se comporte comme s’il était installé nativement.
Installer une dépendance et écrire l’application
xbee npm install expressnpm s’exécute dans le pack, mais écrit package.json, package-lock.json et
node_modules/ dans le répertoire courant, sur le host, monté automatiquement grâce à
l’xbee-install.yaml.
// app.js
const express = require('express');
const app = express();
const port = 3000;
app.get('/', (req, res) => {
res.send('Hello World!');
});
app.listen(port, () => {
console.log(`Server listening on http://localhost:${port}`);
});Lancer et vérifier
xbee node app.jsdémarre le serveur dans le pack, au premier plan — le terminal reste occupé tant que le process tourne. Depuis un autre terminal, dans le même répertoire :
curl http://localhost:3000
# Hello World!Le container démarré par la commande tourne en réseau host : localhost:3000 à
l’intérieur du pack est directement localhost:3000 sur le host, sans publication de
port à gérer. Ctrl+C dans le premier terminal arrête le serveur ; le container,
propre à cet appel, est alors supprimé.
Surcharger les versions
Comme toute valeur var, les versions se surchargent sans toucher au pack nodejs
lui-même — par exemple depuis un hôte d’environnement qui le référence via pack,
exactement comme dans
Utiliser le pack dans un environnement :
host:
a:
pack:
origin: ./nodejs
var:
node:
version: "18"
yarn:
version: "1.22.10"Pour aller plus loin
- Le détail des types d’actions disponibles dans
provisionau-delà du raccourcishell(url,copy,github, …) — voir Actions. - Le rôle de
buildetdeploypour un pack qui intègre une couche applicative buildée à partir de code source — non couvert par ce tutoriel. - Toutes les propriétés reconnues dans un
xbee-pack.yaml— voir xbee-pack.yaml. - Les options de commande de pack (
-v,--name,--detached,--rm,--env) — voir Commandes CLI. - Référencer plusieurs packs dans un même
xbee-install.yaml(packen liste, avecalias) — non couvert par ce tutoriel.