Votre première recette : un programme absent de la bibliothèque, en paquet QTS
La bibliothèque de recettes de l’App Builder compile une longue liste de programmes. Quand le vôtre n’y figure pas, un projet peut apporter sa propre recette : deux fichiers dans son dossier recipes/, au format de la bibliothèque. Ce guide fait un paquet QTS pour les NAS x86_64 et ARM 64 bits à partir de cmatrix 2.0, un petit programme de terminal qui utilise ncurses, fourni par la bibliothèque.
- ProjetPaquet à partir des sources
- Recetterecipe.json, build.sh
- Vérificationle lint dans l’éditeur
- Compilationdeux applications, deux processeurs
- Paquetmake qpkg
Les images viennent du panneau et de l’éditeur de Bucket & Code Server IDE, chaque étape étant faite comme ce guide la décrit. Le dossier de données est /share/ZFS530_DATA/BucketVS.
01Créer le projet
Sur la page Projets, Nouveau projet demande d’abord le modèle. Choisissez Paquet à partir des sources : un paquet QTS de programmes que vous compilez à partir des sources avec vos propres recettes, pour x86_64 et arm64.
Nommez-le cmatrix. Le nom du projet devient le nom du paquet. Écrit en minuscules et sans les caractères interdits dans un nom de recette, il devient aussi celui de sa recette de départ et de ses deux applications. L’étape Service indique ce que fait le paquet pendant qu’il fonctionne. Outil en ligne de commande, déjà choisi à l’ouverture de l’étape, place dans /usr/bin un lien vers le bin/cmatrix du paquet tant que le paquet est démarré. Le dossier du projet contient alors :
| Chemin | Ce que c’est |
|---|---|
recipes/<name>/ | la recette de départ : recipe.json et build.sh |
recipes.txt | les recettes que compilent les deux applications, un nom par ligne : celles de ce projet et celles de la bibliothèque |
Makefile | make app, make build, make lint, make qpkg |
licenses.txt | les licences que contient le paquet, une ligne par recette |
qpkg/ | le paquet : qpkg.cfg et le script de démarrage et d’arrêt issu de l’étape Service |
Le Makefile compile deux applications : <name> pour le processeur de ce NAS et <name>-arm64 pour les NAS ARM 64 bits, une compilation croisée sur un NAS x86_64. Les deux se compilent dans le builder Ubuntu 24.04 et sont liées en statique ; si cet environnement manque, Créer cet environnement sur la page Toolchains le crée. Compiler juste après la création est désactivé pour ce modèle : la recette de départ désigne une source factice avec un sha256 de 64 zéros, donc une compilation échoue tant que la recette ne désigne pas votre programme.
02La recette de départ
Ouvrir dans l’éditeur, dans la vue du projet, ouvre le dossier du projet dans l’éditeur. recipe.json dit quoi compiler ; build.sh dit comment.
| Champ | Ce qu’il indique |
|---|---|
name, version | le nom de la recette (celui de son dossier) et la version du programme |
summary, category, license, homepage | ce que le panneau en affiche |
source | l’adresse de l’archive source et son sha256 ; un téléchargement qui ne correspond pas est refusé |
deps | les recettes dont elle a besoin au préalable, de la bibliothèque ou de ce projet |
env_packages | les outils de compilation que l’environnement builder installe pour elle (jamais de bibliothèques) |
static, nss | si elle est liée en statique, et si elle recherche des utilisateurs ou des noms d’hôte |
check | une commande, exécutée dans le préfixe terminé, qui prouve que le programme fonctionne |
build.sh définit trois phases, chacune exécutée dans la source décompressée. Dans la recette de départ, ce sont celles de CMake, et ses commentaires donnent pour chacune la forme autoconf et Meson :
do_configure() {
# an autoconf source: configure_std; meson: meson_std. In a static app CMake ends the link line with -Wl,-Bdynamic
# after a library it found as a file (lib<name>.a), and the link then asks for a shared libc;
# CMAKE_LINK_SEARCH_END_STATIC keeps the line static to its end (D312)
if [ "$STATIC" = 1 ]; then cmake_std -DCMAKE_LINK_SEARCH_END_STATIC=ON; else cmake_std; fi
}
do_build() {
cmake --build _build -j"$JOBS" # autoconf: make_j; meson: meson compile -C _build
}
do_install() {
cmake --install _build # autoconf: make install; meson: meson install -C _build
}
cmake_std, configure_std et meson_std transmettent le préfixe de l’application, le mode de liaison et, pour une application ARM, la cible croisée, si bien que le même fichier sert aux deux applications.
03La source de votre programme
Prenez l’adresse de l’archive de la version et laissez le terminal de l’éditeur calculer son sha256 :
curl -fsSL https://github.com/abishekvashok/cmatrix/archive/refs/tags/v2.0.tar.gz | sha256sum
ad93ba39acd383696ab6a9ebbed1259ecf2d3cf9f49d6b97038c66f80749e99a -
cmatrix se compile avec CMake et dessine avec ncurses, qui figure dans la bibliothèque. Son script CMake trouve ncurses sous forme de fichier, libncurses.a. Dans une application statique, CMake place alors -Wl,-Bdynamic après ce fichier, à la fin de la ligne d’édition de liens : l’édition de liens demanderait une libc partagée et s’arrêterait. Le do_configure de la recette de départ garde la ligne statique jusqu’au bout, donc build.sh reste tel quel :
do_configure() {
if [ "$STATIC" = 1 ]; then cmake_std -DCMAKE_LINK_SEARCH_END_STATIC=ON; else cmake_std; fi
}
Dans recipe.json, la vérification devient bin/cmatrix -V, l’option qui affiche la version de cmatrix 2.0 (à --version, il répond par son texte d’aide) :
{
"name": "cmatrix",
"version": "2.0",
"summary": "cmatrix: the falling characters of The Matrix in a terminal",
"category": "tool",
"license": "GPL-3.0-or-later",
"homepage": "https://github.com/abishekvashok/cmatrix",
"source": {
"url": "https://github.com/abishekvashok/cmatrix/archive/refs/tags/v2.0.tar.gz",
"sha256": "ad93ba39acd383696ab6a9ebbed1259ecf2d3cf9f49d6b97038c66f80749e99a"
},
"deps": ["ncurses"],
"env_packages": [],
"static": true,
"nss": false,
"check": "bin/cmatrix -V"
}
- Un dossier de recette contient
recipe.json,build.shet le fichier vendor querecipe.jsonpeut nommer, et rien d’autre. Un correctif va dansbuild.shsous forme de here-document. recipes.txtnomme déjà la recette de départ ; les recettes de la bibliothèque dont elle dépend s’ajoutent à la compilation dans leur ordre.
04Vérifier la recette
Chaque fois que vous enregistrez un fichier de recette, les recettes du projet sont vérifiées et les constats apparaissent dans la vue Problèmes, chacun avec son fichier et sa ligne. La vérification lit recipe.json et analyse build.sh avec bash -n ; elle n’exécute jamais la recette. Les 64 zéros de la recette de départ en sont un exemple : un avertissement sur la ligne du sha256, tant que la vraie somme n’y figure pas.
La même vérification s’exécute dans le terminal et dans une tâche de CI :
make lint # bvs recipe lint . (le dossier du projet) bvs recipe lint --json . # les constats en JSON, pour une étape de CI
La carte Recettes de la vue du projet liste les recettes du projet telles que ses applications les utilisent, chacune avec son résultat de lint et ses constats. Un clic sur une ligne ouvre le dossier de la recette dans l’éditeur, et le menu de la ligne copie la commande de lint.
05Compiler les deux applications
Compiler, dans la vue du projet, exécute le Makefile du projet : il crée les deux applications si elles manquent et les compile l’une après l’autre. Sur la page Apps, la page de chaque application nomme le projet d’où viennent ses recettes, et le journal de compilation nomme chaque recette dans son ordre, ncurses en premier.
- Une compilation lit les recettes du projet une seule fois, à son démarrage. Un fichier enregistré ensuite ne compte qu’à la compilation suivante.
- Une recette de projet qui porte le nom d’une recette de la bibliothèque remplace cette recette dans les applications de ce projet seulement, et le journal de compilation l’indique.
- Après la dernière recette, la vérification de chaque recette s’exécute de nouveau sur le préfixe terminé :
bin/cmatrix -Vpour celle-ci. Sur un NAS x86_64, l’application ARM est une compilation croisée, et ses vérifications ne s’exécutent que là où qemu-user est enregistré ; sans lui, la compilation les note comme non exécutées.
06Empaqueter et installer
licenses.txt indique ce que contient le share/licenses/ du paquet : une ligne par recette que contient le paquet, avec sa licence et les fichiers de licence de son archive source. La ligne de départ nomme la source factice. cmatrix a besoin de deux lignes, parce que ncurses y est lié :
cmatrix GPL-3.0-or-later COPYING ncurses X11 COPYING
make qpkg, dans le terminal de l’éditeur, empaquette avec le QDK de la page Toolchains la dernière compilation réussie de chaque application, un fichier par architecture, et laisse de côté une application qui n’en a aucune. Une application liée dynamiquement est refusée : ses programmes chercheraient leurs bibliothèques dans le préfixe de l’application, que le paquet ne crée pas.
make qpkg
Les paquets arrivent dans build/qpkg/build/, nommés d’après QPKG_NAME et QPKG_VER de qpkg.cfg : cmatrix_0.1.0_x86_64.qpkg et cmatrix_0.1.0_arm_64.qpkg. Chacun contient bin/, sbin/, share/ (sans man, doc ni info) et etc/ de l’application : ici cmatrix, et ce que ncurses y a installé, ses outils et sa base de données de terminaux. KEEP, en tête de scripts/make-qpkg.sh, nomme les chemins qu’un paquet doit contenir à la place, par exemple bin/cmatrix share/terminfo.
Avec les fichiers de signature de code dans qpkg/, à côté de qpkg.cfg, ou dans un dossier que nomme QPKG_CERT_DIR, le paquet est signé, et Déploiement de test, dans la vue du projet (réservé aux admins), l’installe sur ce NAS. Votre propre App Center montre la signature et la publication plus en détail. Transmission de A à Z suit du début à la fin un projet Paquet à partir des sources de cinq recettes : d’un NAS où rien n’est configuré jusqu’au paquet signé et installé, qui répond dans le navigateur.
07Une deuxième recette
Bucket: New recipe ajoute une recette à partir de la même recette de départ. Lancez-la depuis la palette de commandes (Ctrl+Shift+P) pendant qu’un fichier du projet est ouvert, ou faites un clic droit sur le dossier recipes ou sur le dossier d’une recette dans l’Explorateur. Elle demande le nom (lettres minuscules, chiffres et + . _ -), écrit recipe.json et build.sh, ouvre recipe.json et vérifie le projet.
- Ajoutez le nouveau nom à
recipes.txtpour les applications créées à partir de maintenant. Une application créée avant garde sa liste : Modifier, sur sa page, y ajoute la recette. - Une recette dont la compilation a besoin de paquets npm, Go ou Cargo les liste dans un fichier vendor.
npm-vendor.py,go-vendor.pyetcargo-vendor.py, dans/usr/bin/bucketvs/share/bucketvs/tools/, écrivent cette liste ; ils ont besoin d’un runtime Python de la page Toolchains. - Les recettes de projet s’exécutent en root dans l’environnement builder, comme celles de la bibliothèque, et tout développeur peut les écrire et les compiler. Un viewer voit les noms des recettes d’une application dans son journal de compilation, jamais les fichiers des recettes.
- Une recette de projet reste dans son projet. Elle n’entre dans la bibliothèque de recettes, et dans le catalogue signé que reçoit chaque NAS, que par une modification relue de Bucket & Code Server IDE lui-même.