On peut charger des modules JS avec dotclear, l’usage est de les suffixer .mjs (ça n’a rien d’obligatoire), mais ça reste lourd question emploi. Un exemple rapide (et fonctionnel) côté administration dans un plugin de test pour charger le module JS de notification du plugin notifyMe1 :
Côté PHP :
echo
Page::jsJson('debug_config', [
'notify' => false,
'title' => 'DEBUG',
'wait' => false,
'module' => urldecode(Page::getPF('notifyMe/js/notify.mjs')),
]) .
My::jsLoad('module.mjs', null, true);
Et côté JS :
/*global dotclear */
// Solution 1 import direct
import { notifyBrowser } from './index.php?pf=notifyMe/js/notify.mjs';
// Dom ready
dotclear.ready(() => {
const debug = dotclear.getData('debug_config');
notifyBrowser('Et voilà !', debug.title, false, debug.wait);
});
// Solution 2 avec async/await
dotclear.ready(async () => {
const debug = dotclear.getData('debug_config');
if (debug.notify) {
const notifyMe = await import(`./${debug.module}`);
await notifyMe.notifyBrowser('Async', debug.title, false, debug.wait);
}
});
Avec la solution 1 je trouve dommage de devoir définir l’URL de chargement du module de cette manière ; je n’ai pas (encore) trouvé de moyen de faire plus facile, en particulier en récupérant l’URL du module notify.mjs
(vu qu’il n’est pas chargé de manière systématique).
Quant à la solution 2 c’est un poil plus élégant mais ça reste lourd à gérer.
Je me demande s’il n’y a pas une architecture plus simple qui pourrait être étendue à l’ensemble de Dotclear — la question se posera pour jQuery et ses différentes extensions codées côté Dotclear. Sauf qu’il faudra peut-être revoir le gestionnaire d’URL pour le chargement des ressources (CSS, JS, …) en notant qu’il permet le chargement des versions minifiées d’icelles si elles sont présentes ?
Bref rien de facile vu l’historique.
Pour être complet, le module notify.mjs
:
Code javascript complet
export { notifyBrowser };
/* Browser notification
(adpated from https://developer.mozilla.org/fr/docs/Web/API/Notification)
-------------------------------------------------------*/
function notifyBrowser(msg, title = 'Dotclear', silent = false, wait = false) {
const notify_options = {
body: msg,
icon: 'images/favicon.ico',
silent,
requireInteraction: wait,
};
if ('Notification' in window) {
// Check if user has already granted notification for this session
if (Notification.permission === 'granted') {
// Notifications granted, push it
const notification = new Notification(title, notify_options);
if (wait === false) {
setTimeout(notification.close.bind(notification), 4000);
}
}
// Else, check if notification has not already been denied
else if (Notification.permission !== 'denied') {
// Ask permission for notification for this session
Notification.requestPermission((permission) => {
// Store user's answer
if (!('permission' in Notification)) {
Notification.permission = permission;
}
// If notification granted, push it
if (permission === 'granted') {
const notification = new Notification(title, notify_options);
if (wait === false) {
setTimeout(notification.close.bind(notification), 4000);
}
}
});
}
}
}
-
Il est livré avec une version standard du code de notification et une version sous forme de module. ↩︎