JSModule

C’est une fonctionnalité de MyDMAM qui permet d’implémenter une Interface Java (simple) avec un code JavaScript, en utilisant de façon transparente les API Nashorn, Reflexion et Proxy de Java.

Cela permet notamment de rendre configurable un algorithme sans avoir besoin d’intervenir coté Java (de modifier le classpath, de distribuer des nouveaux jars ou de modifier les actuelles).

Du aux natures différentes de Java et JavaScript, tout n’est pas forcément possible, mais Nashorn fait de son mieux pour le binding entre les objets Java et JavaScripts.

Il est prévu dans le futur que le code JS créé puisse être envoyé dans le navigateur web afin d’avoir un module universel (Java/backend et JavaScript/frontend).

Implémenter un JSModule

Cela ne nécessite pas de dépendances, ni de paramètre à activer et peut se faire avec une version redistribuable de MyDMAM.

Il faut repérer l’interface à implémenter, et connaitre son nom de module, afin que l’appel à l’API se fasse entre le bon module et la bonne classe. En effet, on ne peut implémenter qu’un module fait pour, car c’est la classe qui appelle ce module qui le fait fonctionner.

Exemple : hd3gtv.mydmam.pathindexing.IdExtractorFileName pour le module IdExtractorFileName. Ce module permet de remplir le champ « Id » lors de l’indexation de fichiers, en l’extrayant depuis son nom. Suivant votre nomenclature, il ne peut pas y avoir de méthode générique. Vous pouvez donc définir vous-même la façon de faire cette extraction de texte depuis le nom du fichier.

Lancer avec CLI la fonction de création automatique de template, il va créer pour vous un fichier JS prêt à être modifié.

mydmam-cli.bash jsinjava -template IdExtractorFileName -class "hd3gtv.mydmam.pathindexing.IdExtractorFileName"

Dans le dossier conf/app.d, il va créer le fichier IdExtractorFileName-module.js. Il peut être renommé. Ce fichier fera partie de la configuration d’instance MyDMAM, il sera conservé lors de la mise à jour.

Modifiez le code suivant vos besoins. Il s’agit d’un vrai fichier JS qui sera exécuté par un vrai moteur JS. Tout ce qui est possible de faire en JS est possible ici (sauf l’accès à des fonctionnalités de navigateur web, comme le DOM, car… vous n’êtes pas dans un navigateur web).

Un exemple ici : https://github.com/hdsdi3g/MyDMAM/issues/286

Pour tester ce code (tout erreur sera remontée à Java et stoppera l’action qui l’appelle) :

mydmam-cli.bash jsinjava -class "hd3gtv.mydmam.pathindexing.IdExtractorFileName" -module IdExtractorFileName -method getId -args "<exemple de nom de fichier a tester.ext>"

Dans l’exemple d’IdExtractorFileName, il y a deux méthodes : getId et isValidId. L’une extrait et l’autre dit si l’extraction est possible ou pas.

Cette fonction de test va effectivement lancer Java et le moteur Nashorn, qui va interpréter le script, puis va instancier un proxy dynamique de l’Interface IdExtractorFileName.class. Un mapping entre les méthodes d’IdExtractorFileName sera fait avec les nœuds de la clé content. Les objets JS et Java seront convertis au mieux selon le sens de l’exécution : paramètre Java vers JavaScript, retour JavaScript vers Java pour la réponse.

Créer un nouveau JSModule

Pour des besoins d’ajout de fonctionnalités et autres modifications de MyDMAM (encouragés), il peut être utile de sortir du cote métier hors Java et indépendant des mises à jours de MyDMAM.

Pour cela il faut « juste » créer une interface sur mesure. Les @JSComment et @JSVarName sont là pour égayer le template JavaScript créé automatiquement, en lui donnant des noms de paramètres, et des commentaires.

La partie problématique peut-être les échanges de variable entre Java et JavaScript. Privilégiez le retour de primitives et de chaines de caractères. Si vous devez créer un Object quelconque dans JavaScript, passez lui en paramètre un Supplier Java qui va créer cet Object coté Java pour le donner à JS quand il le voudra.

Le scope dans Javascript est limité à ce qui est passé dans la classe NashornEngine ; l’accès à tout autre Object ou classe est volontairement impossible (pour éviter qu’un “petit” fichier de config js puisse causer des problèmes de sécurité dans MyDMAM comme de détourner des informations).

Enfin, pour appeler un Module coté Java, utilisez l’appel :

MyDMAM.factory.getInterfaceDeclaredByJSModule(<votre classe>, <le nom du module>, supplier);

Avec supplier qui doit produire une instance de votre d’Object “par défaut”, dans le cas où le module n’existe pas.