Présentation
Jank se définit comme un dialecte complet de Clojure qui s’appuie sur le compilateur C++ de Clang. Le projet propose un REPL interactif où chaque expression est traduite en code C++ puis exécutée par un JIT LLVM. La page officielle indique que le langage compile directement en binaire C++ et qu’il peut être géré avec Leiningen, l’outil de build habituel des projets Clojure.
Interopérabilité C++ native
Contrairement à la JVM, Jank expose le système de types C++ sans couche de conversion. Les directives (:include "...") permettent d’inclure des en‑têtes C++ et les appels cpp/… invoquent directement des fonctions, des classes ou des exceptions C++. L’exemple suivant montre l’utilisation de boost::filesystem : le code Clojure inclut l’en‑tête, renomme la fonction file_size et capture l’exception boost::filesystem::filesystem_error sans wrapper supplémentaire.
(ns my.app.filesystem
(:include "boost/filesystem.hpp")
(:refer-global :rename {boost.filesystem.file_size file-size}))
(defn file-info [file-path]
(try
(let [bytes (file-size (cpp/cast std.string file-path))]
{:path file-path
:size bytes})
(catch boost.filesystem.filesystem_error e
{:path file-path
:error (.what e)})))Cette approche élimine le besoin de déclarer des fonctions d’enregistrement ou de sérialiser des structures, ce qui réduit le temps de développement et les risques d’erreurs de marshalling.
Compilation, JIT et système de build
Le moteur de Jank repose sur un compilateur JIT basé sur LLVM. Chaque fragment de code Clojure est transformé en AST Clang, puis en IR LLVM avant d’être exécuté. Le niveau d’optimisation est configurable via le profil Leiningen : le profil :base utilise optimization-level 0 pour le développement rapide, tandis que le profil :release fixe optimization-level 3 pour la génération de code optimisé. Le fichier project.clj montre comment déclarer des dépendances natives, par exemple les bibliothèques imgui‑glfw et gl‑sys, avec des versions datées 2026.06‑6.
(defproject imgui+glfw "0.1-SNAPSHOT"
:dependencies [[org.jank-lang.commons/imgui-glfw-sys "2026.06-6"]
[org.jank-lang.commons/imgui-opengl2-sys "2026.06-6"]
[org.jank-lang.commons/gl-sys "2026.06-1"]]
:plugins [[org.jank-lang/lein-jank "2026.06-2"]]
:middleware [leiningen.jank/middleware]
:profiles {:base {:jank {:target-dir "target/debug"
:optimization-level 0}}
:release {:jank {:target-dir "target/release"
:optimization-level 3}}})Le système détecte automatiquement les bibliothèques installées ou les compile à partir du code source, ce qui simplifie l’intégration de nouvelles dépendances.
Cas d’usage : développement de jeux
Jank se présente comme un environnement où la programmation fonctionnelle et le REPL cohabitent avec les exigences de performances des moteurs de jeu. Le code d’exemple initialise GLFW et ImGui via des appels cpp/…, crée une fenêtre, puis exécute une boucle de rendu où chaque appel ImGui est exprimé en Clojure. Aucun pont externe n’est nécessaire ; les fonctions C++ sont appelées directement, ce qui minimise la latence entre le code de haut niveau et le rendu graphique.
(ns imgui+glfw.main
(:include "GLFW/glfw3.h"
"imgui.h" "imgui_impl_glfw.h" "imgui_impl_opengl2.h"))
(defn -main []
(cpp/glfwInit)
(let [window* (cpp/glfwCreateWindow 400 300 "jank" cpp/nullptr cpp/nullptr)]
(cpp/glfwMakeContextCurrent window*)
(cpp/ImGui.CreateContext)
(cpp/ImGui_ImplGlfw_InitForOpenGL window* true)
(cpp/ImGui_ImplOpenGL2_Init)
(while (cpp/! (cpp/glfwWindowShouldClose window*))
(cpp/glfwPollEvents)
(cpp/ImGui_ImplOpenGL2_NewFrame)
(cpp/ImGui_ImplGlfw_NewFrame)
(cpp/ImGui.NewFrame)
(when (cpp/ImGui.Begin "jank")
(cpp/ImGui.Text "Hello, jank and imgui!"))
(cpp/ImGui.End)
(cpp/ImGui.Render)
(cpp/ImGui_ImplOpenGL2_RenderDrawData (cpp/ImGui.GetDrawData))
(cpp/glfwSwapBuffers window*))
(cpp/glfwTerminate)))En combinant la mutabilité contrôlée de Clojure avec l’accès direct aux API C++, Jank offre une alternative aux moteurs de script traditionnels qui reposent sur des bindings explicites.