Mise en place d'automatisations au fablab
Utilisation de la plateforme M5Stack poour développer des solutions d'automatisation de l'enregistrement/l'emprunt de matériel/l'utilisation de machines dans le FabLab
- Présentation et mise en place de l'environnement de développement
- Objectifs
- Présentation de TimeTonic
- Présentation M5Stack
- Mise en place de plateformeIO
- Présentation des librairies utilisées
- Premier prototype et preuve de concept
- Création d'une bibliothèque uniformisée : M5lib
- Lecteur de badge comme clavier BT
- Réflexions sur l'ergonomie de UI
- Lecteur NFC ACR122U
- Compléments : API, webhooks, PWA
Présentation et mise en place de l'environnement de développement
présentation des objectifs et desccription des librairies, initialisation de TimeTonic et mise en place de l'environnement de développement
Objectifs
Dans le cadre de l’amélioration des processus au sein du fablab, un projet d’automatisation a été initié afin de moderniser et de simplifier la gestion des accès et des ressources. Ce projet s’articule autour de plusieurs objectifs principaux :
Automatisation de l’enregistrement via la carte étudiante
L’un des axes majeurs du projet consiste à automatiser l’enregistrement des utilisateurs grâce à leur carte étudiante. Cette solution vise à remplacer les méthodes manuelles d’identification par un système de scan rapide et sécurisé, facilitant ainsi l’accès au fablab tout en renforçant la traçabilité des entrées.
Création d’une base de données centralisée et complète
Le projet prévoit la mise en place d’une base de données exhaustive sur Timetonic. Celle-ci regroupera l’ensemble des enregistrements, des emprunts de matériel et des utilisations de machines. L’objectif est de disposer d’un historique fiable et consultable, permettant d’optimiser la gestion des équipements et d’assurer un suivi précis des activités.
Refonte du mode de gestion des emprunts et des utilisations
Le fonctionnement des emprunts et de l’utilisation des machines sera entièrement revu. Désormais, toutes les opérations passeront par le scan de la carte étudiante, supprimant la nécessité de solliciter les emplois étudiants pour valider les demandes. Ce nouveau mode opératoire vise à fluidifier les procédures, à réduire les délais et à responsabiliser les utilisateurs.
En résumé, ce projet d’automatisation s’inscrit dans une démarche d’innovation et d’efficacité, en s’appuyant sur des technologies modernes pour améliorer l’expérience des usagers et la gestion quotidienne du fablab.
Présentation de TimeTonic
TimeTonic est une plateforme collaborative no-code, conçue pour centraliser, organiser et automatiser la gestion de données, de projets et de processus métier. Flexible et visuelle, elle s’adresse aussi bien aux petites équipes qu’aux grandes entreprises, permettant de créer rapidement des applications métiers personnalisées sans compétences en programmation.
Fonctionnalités principales
-
Organisation visuelle et collaborative : TimeTonic propose des espaces de travail (« books ») où l’on peut structurer ses données sous forme de tableaux intelligents (Smart-tables®), aussi flexibles qu’un tableur mais aussi puissants qu’une base de données relationnelle. Chaque espace peut être personnalisé, partagé et enrichi de commentaires, fichiers, dates, couleurs, etc.
-
Multiples vues : Il est possible de passer d’une vue tableau à une vue Kanban, calendrier ou Gantt en un clic, pour s’adapter à chaque besoin métier.
-
Gestion documentaire et communication : Chaque espace dispose de sa propre messagerie, d’une adresse email dédiée et permet de centraliser fichiers, notes et discussions, facilitant la collaboration en temps réel.
-
Historique et traçabilité : Toutes les modifications sont historisées, assurant une parfaite traçabilité des actions.
Avantages de TimeTonic
-
Flexibilité extrême : La plateforme s’adapte à tous les métiers et à toutes les tailles d’organisation. Elle permet de créer des workflows sur-mesure, d’ajouter des champs, des règles d’automatisation et de personnaliser l’interface selon les besoins.
-
Simplicité d’utilisation : Aussi simple à prendre en main qu’un tableur ou des post-its, mais aussi puissante qu’une solution professionnelle avancée.
-
Collaboration en temps réel : Les équipes travaillent dans un espace commun, partagent des informations instantanément et évitent la dispersion des données (emails, fichiers, etc.).
-
Sécurité : TimeTonic est certifié SecNumCloud et ISO 27001, garantissant la sécurité des données.
Automatisation des processus
TimeTonic intègre un moteur d’automatisation puissant permettant de déclencher des actions dès qu’un événement se produit dans la base de données :
-
Automatisations natives : Modification automatique de champs, envoi d’emails (avec ou sans pièce jointe), création de nouveaux enregistrements, génération de fichiers ICS (calendrier), etc.
-
Automatisations avancées avec IA : Il est possible d’intégrer des automatisations utilisant l’intelligence artificielle, par exemple pour générer des suggestions, résumer des rapports, reformater des données ou traduire automatiquement du contenu. Ces automatisations se configurent en quelques étapes et s’intègrent directement dans les workflows existants.
-
Formules et règles personnalisées : Comme dans un tableur, il est possible de créer des formules pour automatiser des calculs ou des mises à jour de données.
Communication et intégration avec d’autres outils (API)
TimeTonic propose une API complète, permettant d’intégrer la plateforme à d’autres applications ou systèmes d’information :
-
API REST : L’API permet de lire, modifier, créer et supprimer des données dans les tables de TimeTonic, facilitant l’intégration avec des logiciels tiers, des sites web ou des applications mobiles.
-
Automatisation inter-applications : Grâce à des plateformes comme Pipedream, TimeTonic peut être connecté à des outils comme Slack, Gmail, Shopify, Google Sheets, etc. Il devient alors possible de synchroniser des données, déclencher des actions automatiques (création de tâches, alertes, notifications, etc.) ou maintenir une cohérence temps réel entre différents systèmes.
-
Cas d’usage concrets :
-
Création automatique de tâches à partir de ventes réalisées sur un site e-commerce.
-
Synchronisation des notifications avec Slack pour informer l’équipe en temps réel.
-
Gestion automatisée des stocks avec alertes email dès qu’un seuil est franchi.
-
En résumé, TimeTonic se distingue par sa capacité à centraliser l’information, à automatiser les tâches répétitives et à communiquer facilement avec l’ensemble de l’écosystème numérique de l’entreprise. C’est un véritable atelier numérique collaboratif, personnalisable et évolutif, qui permet de gagner en efficacité, en transparence et en réactivité
Présentation M5Stack
Dans le cadre de ce projet, nous utilisons la plateforme de développement M5Stack, et plus précisément le module M5Stack Basic associé à un module RFID I2C. Cette combinaison permet de réaliser rapidement des prototypes embarquant des fonctionnalités de lecture de badges RFID. M5Stack reprend tous les codes de développement d'Arduino, comme son language (C++), et est notamment compatible avec une grande partie de ses librairies.
1. La plateforme M5Stack
La M5Stack est une solution de développement modulaire dédiée à l’IoT (Internet of Things). Elle se distingue par sa facilité d’utilisation, son aspect compact et sa capacité à empiler différents modules pour ajouter des fonctionnalités selon les besoins du projet.
Principaux atouts :
-
Modularité : modules et unités empilables, connectables sans soudure.
-
Compatibilité logicielle : support de la programmation graphique (UIFlow), Arduino, MicroPython, ESP-IDF.
-
Connectivité : Wi-Fi et Bluetooth grâce au microcontrôleur ESP32.
-
Écosystème riche : de nombreux modules (capteurs, actionneurs, interfaces, etc.) sont disponibles.
2. Le M5Stack Basic
Le M5Stack Basic est le modèle d’entrée de gamme de la série. Il est particulièrement adapté à l’apprentissage, au prototypage rapide et au développement de solutions embarquées.
Caractéristiques principales :
-
Microcontrôleur : ESP32 (dual-core, 240 MHz)
-
Écran : TFT couleur 2,0" (320x240 px)
-
Connectivité : Wi-Fi, Bluetooth
-
Stockage : slot microSD
-
Contrôles : 3 boutons utilisateur, haut-parleur intégré
-
Batterie : LiPo 110 mAh rechargeable
-
Extension : ports Grove (I2C/UART), connecteur M-BUS, broches GPIO accessibles
-
Boîtier : plastique industriel compact et robuste
Le M5Stack Basic est donc une base idéale pour développer des applications connectées et interactives.
3. Le module RFID I2C (MFRC522)
Pour ajouter la fonctionnalité de lecture de badges RFID, nous utilisons un module RFID basé sur la puce MFRC522, qui communique avec le M5Stack via le protocole I2C.
Caractéristiques du module RFID :
-
Lecture/écriture de tags RFID/Mifare à 13,56 MHz
-
Interface : I2C (adresse 0x28)
-
Connexion : via port Grove du M5Stack
-
Applications : contrôle d’accès, pointage, gestion de stock, etc.
Intégration :
-
Le module RFID se branche simplement sur le port Grove du M5Stack Basic, ce qui permet une installation rapide et sans soudure.
Cette combinaison d’outils permet de disposer d’une plateforme puissante, flexible et facile à mettre en œuvre pour des projets impliquant la lecture de badges RFID et le développement de solutions IoT.
Mise en place de plateformeIO
Présentation de PlatformIO
PlatformIO est un environnement de développement intégré (IDE) moderne et multiplateforme, spécifiquement conçu pour le développement de logiciels embarqués. Il permet de programmer une grande variété de microcontrôleurs et de cartes, en offrant une gestion avancée des bibliothèques, de la compilation et du déploiement, tout en restant open source et sans verrouillage propriétaire.
Avantages de PlatformIO
-
Support multi-plateformes : fonctionne sous Windows, macOS, Linux.
-
Gestion centralisée des dépendances : les bibliothèques nécessaires sont automatiquement installées et mises à jour.
-
Automatisation : compilation, upload, gestion du port série et tâches personnalisées intégrées.
-
Flexibilité : compatible avec de nombreux frameworks (Arduino, ESP-IDF, etc.) et microcontrôleurs.
-
Débogage et analyse avancés : outils de test, d’analyse de code et de gestion de projet professionnels.
Intégration dans Visual Studio Code (VS Code)
PlatformIO s’intègre parfaitement à Visual Studio Code (VS Code), l’éditeur de code de Microsoft. L’extension PlatformIO IDE pour VS Code transforme ce dernier en un environnement puissant pour le développement embarqué.
Installation de PlatformIO dans VS Code
-
Installer VS Code : Téléchargez et installez Visual Studio Code depuis le site officiel.
-
Installer l’extension PlatformIO IDE :
-
Ouvrez VS Code.
-
Allez dans l’onglet Extensions (Ctrl+Shift+X).
-
Recherchez “PlatformIO IDE” et cliquez sur “Installer”.
-
-
Redémarrer VS Code si nécessaire pour activer l’extension.
Une fois installée, l’icône PlatformIO apparaît dans la barre latérale de VS Code, donnant accès à toutes les fonctionnalités de gestion de projets, compilation, upload et monitoring série.
Configuration pour développer sur M5Stack Basic
Le M5Stack Basic repose sur un microcontrôleur ESP32. Pour le programmer avec PlatformIO, il suffit de créer un nouveau projet en sélectionnant la carte appropriée et d’ajouter les bibliothèques nécessaires.
Étapes de configuration
-
Créer un nouveau projet PlatformIO :
-
Cliquez sur l’icône PlatformIO dans VS Code.
-
Sélectionnez “New Project”.
-
Donnez un nom au projet (ici FabLab stage).
-
Choisissez la carte : recherchez et sélectionnez
M5Stack Core ESP32(ID :m5stack-core-esp32). -
Sélectionnez le framework souhaité (Arduino ou ESP-IDF, par exemple).
-
Validez pour créer le projet.
-
-
Configurer le fichier platformio.ini :
Le fichierplatformio.iniest alor configuré automatiquementet contient normalement :[env:m5stack-core-esp32] platform = espressif32 board = m5stack-core-esp32 framework = arduinoVous pouvez personnaliser d’autres options (fréquence CPU, protocole d’upload, etc.) selon vos besoins. Les bibliothèques ajoutées au porjet via plateformeIO seront automattiquement ajoutées au fichier platformio.ini.
-
Développer et téléverser votre code :
-
Écrivez votre code dans le dossier
src. -
Utilisez les boutons “Build” (Ctrl+Alt+B) et “Upload” (Ctrl+Alt+U) de PlatformIO pour compiler et téléverser le programme sur le M5Stack Basic.
-
Le moniteur série intégré permet de visualiser les messages envoyés par la carte.
-
En résumé, PlatformIO, intégré à VS Code, offre un environnement moderne, puissant et flexible pour développer sur M5Stack Basic. Il facilite la gestion des bibliothèques, la compilation, l’upload et le monitoring, tout en permettant une personnalisation avancée et une grande évolutivité pour tous vos projets embarqués.
Présentation des librairies utilisées
M5Unified
La librairie M5Unified est le cœur du développement sur les appareils M5Stack. Elle offre une interface unifiée pour contrôler la majorité des composants matériels intégrés aux modules M5Stack, comme l’écran LCD, les boutons, le haut-parleur, le microphone, etc. Grâce à cette abstraction, le même code peut fonctionner sur différents modèles de M5Stack sans modification majeure. M5Unified est compatible avec les plateformes Arduino et ESP-IDF, ce qui facilite le développement et améliore la portabilité du code.
Wire
La librairie Wire permet la communication via le bus I2C, un protocole de communication série très utilisé pour connecter des capteurs et modules externes à une carte microcontrôleur. Elle sert notamment à dialoguer avec des périphériques comme le lecteur RFID ou d’autres capteurs branchés sur le port Grove du M5Stack.
WiFi
La librairie WiFi permet de connecter l’ESP32 (présent dans le M5Stack Basic) à un réseau sans fil. Elle offre des fonctions pour scanner les réseaux disponibles, se connecter à un point d’accès, gérer les événements Wi-Fi et obtenir une adresse IP. Elle est essentielle pour tout projet nécessitant une communication réseau, comme l’envoi ou la réception de données sur Internet.
HTTPClient
HTTPClient est une librairie qui facilite la réalisation de requêtes HTTP (GET, POST, etc.) depuis l’ESP32. Elle permet d’interagir facilement avec des serveurs web ou des API (comme ici celui de TimeTonic), d’envoyer des données ou de récupérer des informations à distance. Cette librairie est souvent utilisée en complément de WiFi pour des applications IoT connectées.
MFRC522_I2C
La librairie MFRC522_I2C permet de piloter un module lecteur RFID MFRC522 via le protocole I2C. Elle simplifie la lecture et l’écriture de badges RFID/Mifare en fournissant des fonctions haut niveau pour détecter, lire et écrire sur les cartes. Cette librairie est compatible avec Arduino et ESP32, et nécessite de spécifier l’adresse I2C du module et la broche de reset. Attention toutefois, un certain nombre de librairies porte ce nom et seule celle disponible sur le GitHub de M5Stack fonctionne avec leur capteur RFID.
ArduinoJson
ArduinoJson est une librairie puissante et optimisée pour la manipulation de données JSON sur microcontrôleurs. Elle permet de sérialiser (convertir des objets en texte JSON) et de désérialiser (analyser du texte JSON pour en extraire des données) facilement, ce qui est très utile pour échanger des données structurées avec des serveurs web ou des API (cellui de TimeTonic utilise principalement des objets JSON pour recevoir/envoyer des données). Elle gère les objets, les tableaux, les filtres et l’optimisation mémoire, ce qui la rend idéale pour les projets embarqués.
Résumé des rôles
| Librairie | Rôle principal |
|---|---|
| M5Unified | Contrôle du matériel M5Stack (écran, boutons, haut-parleur, etc.) |
| Wire | Communication I2C avec les modules externes |
| WiFi | Connexion réseau sans fil et gestion des événements Wi-Fi |
| HTTPClient | Envoi et réception de requêtes HTTP vers/depuis des serveurs web |
| MFRC522_I2C | Lecture/écriture de badges RFID via le module MFRC522 en I2C |
| ArduinoJson | Manipulation et traitement de données JSON (sérialisation/désérialisation) |
L’utilisation combinée de ces librairies permet de gérer efficacement le matériel, de communiquer avec des serveurs distants et de traiter des données structurées, couvrant ainsi l’ensemble des besoins fonctionnels du projet.
Premier prototype et preuve de concept
mise en place d'un exemple simple permettant la lecture de cartes RFID et la communication entre le M5Stack et l'API de TimeTonic.
Lecture de carte RFID
1. Connexion matérielle
Le module RFID MFRC522 se connecte au port GROVE A du M5Stack Basic, qui correspond aux broches I2C (SDA sur GPIO21, SCL sur GPIO22). L’adresse I2C par défaut du module est 0x28.
2. Initialisation logicielle
Il faut utiliser la bibliothèque MFRC522_I2C pour piloter le lecteur RFID, ainsi que les bibliothèques Wire (I2C) et M5Unified (pour gérer l’écran et l’initialisation du M5Stack).
L’initialisation consiste à :
-
Démarrer le M5Stack (
M5.begin()). -
Initialiser le bus I2C (
Wire.begin()). -
Initialiser le module RFID (
mfrc522.PCD_Init()).
3. Lecture du UID
Dans la boucle principale du programme, il s’agit de :
-
Vérifier la présence d’une nouvelle carte avec
mfrc522.PICC_IsNewCardPresent(). -
Lire la carte avec
mfrc522.PICC_ReadCardSerial(). -
Si une carte est détectée, parcourir le tableau
mfrc522.uid.uidByte[]qui contient le UID, et l’afficher sur l’écran du M5Stack ou sur le port série.
4. Fonction de conversation hexadécimale
Le capteur RFID renvoie les données lues de la carte dans un tableau sous forme de bits bruts. Il faut donc convertir ces données en une chaine de charactères hexadécimaux :
String uidhex(MFRC522 &rfid){
String uidStr;
for (byte i = 0; i < rfid.uid.size; i++) {
if (rfid.uid.uidByte[i] < 0x10) uidStr += "0";
uidStr += String(rfid.uid.uidByte[i], HEX);
if (i < rfid.uid.size - 1) uidStr += ":";
}
return uidStr;
}
Ce code renvoie une chaine de charactères contenant le numéro de série de la carte lue au format standard, c'est à dire : XX:XX:XX:XX ... où X est un caractère hexadécimal.
5. Exemple de code
#include <M5Unified.h>
#include <Wire.h>
#include "MFRC522_I2C.h"
MFRC522 mfrc522(0x28); // Adresse I2C du module RFID
void setup() {
M5.begin();
Wire.begin();
mfrc522.PCD_Init();
M5.Display.setTextSize(2);
M5.Display.println("Presentez une carte");
}
void loop() {
if (mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial()) {
String uid = uidhex(mfrc522);
M5.Display.print("UID : ");
M5.Display.println("uid");)
}
M5.delay(2000);
M5.Display.fillRect(0, 60, 320, 240, BLACK);
}
Ce code affiche le UID de chaque carte RFID présentée devant le lecteur sur l’écran du M5Stack.
5. Résumé du fonctionnement
-
Branchez le module RFID sur le port GROVE A du M5Stack.
-
Chargez le code exemple sur le M5Stack.
-
Approchez une carte RFID ou un appareil NFC du lecteur.
-
Le UID de la carte s’affiche instantanément à l’écran.
Cette méthode est fiable pour des applications telles que le contrôle d’accès, la gestion de présence ou l’inventaire.
Communication avec l'API de TimeTonic
Pour permettre au M5Stack de communiquer avec l’API de TimeTonic, il faut exploiter les capacités réseau du M5Stack (via l’ESP32), utiliser les librairies WiFi et HTTPClient, et structurer les requêtes selon les spécifications de l’API TimeTonic.
1. Préparer l’accès à l’API TimeTonic
L’API TimeTonic permet d’accéder, de lire et de modifier les données de vos espaces de travail à distance. Pour chaque requête, il est nécessaire de transmettre un sesskey (clé d’API/session), associé à votre compte utilisateur. Cette clé s’obtient via l’interface TimeTonic et doit être gardée confidentielle (elle ne sera donc publiée ici, si vous copiez l'exemple de code, pensez bien à mettre la votre).
Il est aussi important de repérer dès maintenant où trouver les différents codes permettant d'identifier les books, tables, lignes et colonnes dans TimeTonic :
Book ID : nom de l'espace de travail (attention, si celui-ci a été renommé, il gardera son 1er nom en ID, en cas de doute vérifier dans les paramètres du book dans la catégorie workspace informations).
Table ID : code à 6 chiffres accessible en cliquant sur les 3 points verticaux à droite de la fenêtre lorsque vous visualiser la table, puis en cliquant sur organize fields. L'ID sera entre parenthèse en haut de la fenêtre qui apparait.
Field ID : code à 6 chiffres accessible dans la même fenêtre que pour Table ID, sous la catégorie éponyme.
Row ID : correspond simplement au numéro de la ligne. Lorsqu'on voudra en créer une nouvelle en fin de tableau, on utilisera le code tmpNEW_ROW.
2. Interaction avec l'API
Lors du développement, il existe plusieurs manière d'interagir avec l'API de TimeTonic :
- Sur le site de TimeTonic : chaque modification de vue, de champ etc... est en fait une requête d'API faite de manière transparente.
- Avec l'outil Postman : cet outil permet de construire des requêtes et de voir en direct la réponse du serveur. C'est l'outil privilégié pour tester et construire des requêtes complexes avant de les implémenter dans le code. Il permet aussi de diagnostiquer et résoudre les problèmes lorsqu'on ne récupère pas les données désirées.
- Dans le code du M5 : avec la librairie HTTPClient, et une requête POST passée sous forme de String. Attention, il est nécessaire de formatter la requête correctement pour qu'elle soit interprêtée comme il faut (avec notamment des \" pour qu'ils n'interagissent pas avec les bornes de la String).
2. Exemple de requête : getAllBooks
La méthode getAllBooks permet de récupérer la liste de tous les « books » (espaces de travail) auxquels l’utilisateur a accès. Pour connaitre l'étendu des possibilité de l'API de TimeTonic, je vous renvois vers la documentation de celui-ci. La requête doit être envoyée en POST à l’URL suivante :
https://timetonic.com/live/api.php
Les paramètres à inclure sont :
-
version: version de l’API (ex : "6.20b") (optionnel) -
req: "getAllBooks" -
o_u: identifiant utilisateur (doit correspondre à celui du sesskey) -
u_c: identifiant utilisateur (idem) -
sesskey: votre clé d’API/session, qui peut être créée dans les paramètres de votre compte TimeTonic
3. Implémentation sur M5Stack (Arduino)
Voici comment structurer le code avec les librairies WiFi, HTTPClient et ArduinoJson :
#include <WiFi.h>
#include <HTTPClient.h>
#include <ArduinoJson.h>
const char* ssid = "fablabstaff";
const char* password = "xxxxxxxxx"; //Pensez à remplacer le SSID et le mot de passe par vos paramètres WiFi
HTTPClient http;
void setup() {
Serial.begin(115200);
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println("Connecte au WiFi");
http.begin("https://timetonic.com/live/api.php");
String postData = "req=getAllBooks"
"&o_u=USER"// Remplacez bien USER par votre nom d'utilisateur TimeTonic
"&u_c=USER"
"&sesskey=xxxxxxxxxxxxxxxxxxxxxxxxxx"; // Remplacez par votre sesskey
int httpResponseCode = http.POST(postData);
if (httpResponseCode > 0) {
String reponse = http.getString();
Serial.println("Réponse API :");
Serial.println(reponse);
// Traitement JSON (exemple)
DynamicJsonDocument doc(4096);
deserializeJson(doc, reponse);
if (doc["status"] == "ok") {
JsonArray books = doc["allBooks"];
for (JsonObject book : books) {
Serial.println(book["b_c"].as<String>()); // Affiche le code du book
}
}
}
else {
Serial.print("Erreur HTTP : ");
Serial.println(httpResponseCode);
}
http.end();
}
void loop() {
// Rien ici pour cet exemple
}
Ce code permet de récupérer les informatiosn de tous les espaces de travail présents dans un compte TimeTonic.
4. Points importants
-
Connexion sécurisée : L’API TimeTonic nécessite une connexion HTTPS, ce qui est supporté par l’ESP32.
-
Format POST : Les paramètres doivent être envoyés en POST, au format
application/x-www-form-urlencoded23. -
Traitement de la réponse : La réponse de l’API est en JSON, d’où l’utilisation de la librairie ArduinoJson pour extraire les informations utiles.
-
Gestion des erreurs : Toujours vérifier le code de retour HTTP et le champ
statusdans la réponse JSON.
5. Résumé
Pour communiquer avec l’API de TimeTonic depuis un M5Stack, il faut :
-
Se connecter au WiFi,
-
Construire une requête POST avec les bons paramètres,
-
Envoyer la requête à l’API,
-
Traiter la réponse JSON pour exploiter les données reçues.
Ce principe peut être adapté à toutes les autres méthodes de l’API TimeTonic, en changeant simplement le paramètre req et les paramètres associés.
Lecture et écriture sur TimeTonic
Maintenant que nous pouvons communiquer avec l'API TimeTonic via le M5Stack, il faut savoir utiliser les principales requêtes permettant de lire, créer et modifier les données contenues dans un book (espace de travail). Voici les étapes principales, avec le détail des fonctions API à utiliser et des exemples de structure de requête.
1. Lire les données d’une smart table
Pour récupérer le contenu d’une smart table, il faut utiliser la requête getTableValues. Cette requête retourne les lignes (rows) et les valeurs des champs (fields) d’une table donnée.
Paramètres nécessaires :
-
req: "getTableValues" -
o_uetu_c: identifiants utilisateur -
sesskey: clé de session API -
b_c: code du book (carnet) -
catCode: code de la table (catégorie)
Exemple de requête POST :
req=getTableValues&o_u=USER_ID&u_c=USER_ID&sesskey=SESSION_KEY&b_c=BOOK_CODE&catCode=TABLE_CODE
En version formatée pour le code C précédemment utilisé :
"req=getTableValues"
"&b_c=BOOK_CODE"
"&catCode=TABLE_CODE"
"&o_u=USER_ID"
"&u_c=USER_ID"
"&sesskey=SESSION_KEY"
La réponse contiendra un tableau JSON avec toutes les lignes et les valeurs des champs pour chaque ligne. Pour pouvoir exploiter ces données dans le code C, il faut utiliser un parseur, qui permet d'identifier et d'isoler chaque donnée lue.
2. Filtrage des données lues
Pour ne pas récupérer toutes les données de la table à chaque requête, on peut utiliser deux arguments dans celle-ci :
fieldIds: permet de sélectionner les champs que l'on veut récupérer, sous forme d'un tableau JSON
Par exemple :
&fieldIds = [7457220, 7457221]
Où 7457220 et 7457221 sont les IDs des champs que je veux récupérer.
filterRowIds: permet de sélectionner les lignes que l'on veut récupérer, ou bien au moyen d'une vue déjà existante dans la table, ou via une vue temporaire créée sous la forme d'un objet JSON.
Par exemple :
&filterRowIds={"applyViewFilters": 1181354}
Où 1181354 est l'ID de la vue que je souhaite utiliser. Pour récupérer cet ID, il faut inspecter la page lorsque vous êtes sur la vue qui vous intéresse, puis cliquer sur l'onglet "network". Dans les filtres en haut, sélectionner "Fetch/XHR" puis rafraichisser la page. Dans les fichiers qui se chargent alors, sélectionner newDashboard?getUtilisateur et défiler jusqu'à la section Request Headers. Dans celle-ci, trouvez la ligne Referer, elle contient en regard un lien terminant par /view/Un numéro. Ce numéro est l'ID de votre vue.
ATTENTION : le view ID peut maintenant être directement récupéré dans l'URL de la page : sélectionnez la vue souhaitée puis copiez le numéro après /view/ , il 'sagit du viewId.
Pour construire une vue avec un objet JSON, la manoeuvre est beaucoup plus compliquée : il faut remplacer l'ID de vue par un objet JSON avec une syntaxe particulière :
operator: correspond à l'opérateur logique entre les différents filtres (voir les possibilitées dans la documentation TimeTonic)id: numéro arbitraire à donner à la vue (doit être unique), s'il s'agit d'une vue temporaire, utiliser "tmpId"field_id: ID du champ dans lequel on veut faire le filtrage- predicate : opérateur logique du filtre (voir les possibilités dans la documentatio de TimeTonic)
operand: corps du filtre (l'élément contre lequel seront comparées les valeurs)
Voici un exemple d'objet JSON à mettre après "applyViewFilters": :
{
"filterGroup": {
"operator": "and",
"id": "tmpId",
"filters": [
{
"field_id": 7457220,
"json": {
"predicate": "contains",
"operand": "ABC"
}
},
{
"field_id": 7457221,
"json": {
"predicate": "is",
"operand": "abc"
}
}
]
}
}
NB : "filterGroup" (nom de l'objet JSON), "filters" (tableau JSON contenant les différents filtres) et "json"(objet JSON contenant les arguments de filtrage) sont des éléments statiques mais nécessaires de la syntaxe. toute erreur dans la syntaxe entrainera une réponse valide mais ne contenant aucune donnée de la table interrogée ("rowInfosLength": 0 dans la réponse).
3. Écrire des données dans une smart table
L’ajout ou la modification de données dans une smart table se fait avec la requête createOrUpdateTableRow. Pour modifier une ligne, il suffit d’indiquer l’identifiant de la ligne (rowId=ROW_ID_EXISTANTou rowId=tmpNEW_ROW) et de fournir les nouveaux champs à modifier dans fieldValues.
Paramètres nécessaires :
-
req: "createOrUpdateTableRow" -
o_uetu_c: identifiants utilisateur -
sesskey: clé de session API -
b_c: code du book (carnet) -
catCode: code de la table (catégorie) fieldValues: données à écrire. celles-ci doivent être sous la forme d'un objet JSON avec la syntaxe suivante :
{
"field ID": "Value",
"field ID 2": "Value 2",
"field ID 3": "Value 3"
}
Exemple de requête POST:
req=createOrUpdateTableRow&o_u=USER_ID&u_c=USER_ID&sesskey=SESSION_KEY&b_c=BOOK_CODE&catCode=TABLE_CODE&rowId=ROW_ID_EXISTANT&fieldValues={"FIELD_ID1":"NouvelleValeur"}
En version formatée pour le code C (bien noter les antislashs avant les guillemets contenus dans fieldValues : ils permettent de les considérer comme des caractères normaux sans interférer avec les balises de Strings):
"req=createOrUpdateTableRow"
"&o_u=USER_ID"
"&u_c=USER_ID"
"&sesskey=SESSION_KEY"
"&b_c=BOOK_CODE"
"&catCode=TABLE_CODE"
"&rowId=ROW_ID"
"&fieldValues={\"FIELD_ID\":\"NouvelleValeur\"}"
Seuls les champs à modifier doivent être précisés dans fieldValues.
4. Récupérer les identifiants nécessaires
Si les données que vous lisez/écrivez sont toujours au même endroit, vous pouvez manuellement regarder les IDs de chaque champ et les copier dans votre code. Cependant, si vous voulez écrire des données à des endroits dépendant de certains champs/valeurs, vous pouvez obtenir les IDs pertinents via les requêtes getAllBooks (pour les books) et getBookTables (pour les tables et champs). Avant de pouvoir lire ou écrire, il est indispensable de connaître :
-
Le code du book (
b_c) -
Le code de la table (
catCode) -
Les identifiants des champs (
fieldID1,fieldID2, etc.) -
L’identifiant de la ligne, si modification (
rowId)
5. Résumé des étapes
-
Authentification : Obtenir un
sesskeyvia l’API. -
Lister les tables : Utiliser
getAllBookspuisgetBookTablespour identifier le book et la table cible si nécessaire. -
Lire des données : Utiliser
getTableValuespour obtenir les lignes et champs. -
Écrire des données : Utiliser
createOrUpdateTableRowavecrowId=tmpNEW_ROWsi vous voulez créer une nouvelle ligne.
6. Bonnes pratiques
-
Utiliser systématiquement la méthode POST pour transmettre les paramètres.
-
Manipuler les objets JSON avec soin pour le paramètre
fieldValues, et utiliser un parseur pour pouvoir utiliser les données lues. -
Toujours vérifier le champ
statusdans la réponse de l’API pour s’assurer du succès de l’opération (le code de succès 200 indique simplement que la requête est parvenue à l'API, pas nécessairement qu'elle a été correctement exécutée).
En résumé, la lecture et l’écriture dans une smart table TimeTonic via l’API sont simples, mais nécessites une grande attention aux détails : il faut bien identifier les bons paramètres (book, table, champs), utiliser les requêtes appropriées, et les structurer correctement afin de traiter ou d'envoyer les données correctement.
Création d'une bibliothèque uniformisée : M5lib
Conception et codage d'une bibliothèque commune à tous les M5Stack déployés dans le FabLab afin de rendre le déploiement, la maintenance et l'évolution plus simples et efficaces. Du fait sa relative complexité, il n'est pas garanti qu'elle fonctionne sur les M5Stack Core 1 (elle est optimisée pour les Core 2).
Présentation
Présentation Générale
La bibliothèque M5lib vise à uniformiser la gestion d’une flotte de M5 Core2 au sein d’un FabLab, facilitant le déploiement, l’évolution et la maintenance. Sa structure repose sur des concepts avancés de programmation orientée objet : factory design pattern et polymorphisme.
Factory Design Pattern dans M5lib
Structure de Base
-
La classe M5lib est la classe de base commune à tous les types d’appareils M5 (accueil, servante, machine, ordinateur, matériel), définissant l’interface et le comportement standard minimal.
-
Plusieurs classes dérivées spécialisent ce comportement pour chaque type de M5 :
accueil,servante,machine,ordinateur,materiel, chacune héritant de M5lib.
Objectif du Pattern
Le factory design pattern permet d’instancier dynamiquement le bon type d’objet dérivé (accueil, servante, etc.) en fonction du contexte (par exemple, d’un paramètre de configuration ou d’une saisie utilisateur), tout en manipulant leur interface commune à travers des pointeurs ou références de type M5lib. Dans ce cas, cela veut dire que la déclaration du type d'objet dérivé dans le firmware du M5 permet automatiquement et de manière transparente d'adapter toutes les fonctions nécessaires au comportement de ce type de M5 (requêtes d'API, type d'emprunt...).
Avantages
-
Centralisation de la logique d’instanciation : éviter la duplication de code lors de la création de nouveaux modules.
-
Extensibilité et maintenance : ajouter un nouveau “type” d’objet devient trivial (ajout d’une seule classe dérivée et adaptation de la factory).
Polymorphisme dans M5lib
Implémentation
-
La classe
M5libdéclare des méthodes virtuelles pures (virtual ... = 0;) commeuploadlogetchangestatus. Ces fonctions ne sont alors pas appelables dans M5lib et n'existent pas en tant que tel tant que le type de M5 n'a pas été déterminé. -
Chaque classe dérivée (accueil, servante, etc.) implémente ces méthodes selon les besoins spécifiques de son rôle (par exemple, signature différente, formats d’upload différents…). Ainsi, pour un même appel de fonction, le comportement s'adapte parfaitement au cas d'utilisation du type de M5 concerné.
Usage
-
Grâce au polymorphisme, le reste du programme peut manipuler les objets à travers des pointeurs de type M5lib et appeler, par exemple,
uploadlogsans connaître la classe exacte : c’est la bonne implémentation qui sera automatiquement utilisée à l’exécution. -
Cela permet d’écrire du code générique, réutilisable, et facile à maintenir. De plus, si par la suite un nouveau cas d'utilisation est identifié comme nécessitant la création d'un nouveau type de M5, il ne faudra ajouter dans le code que les définitions de comportement spécifique à ce type, rendant l'évolutivité beaucoup plus simple.
Limites et inconvénients
Cette flexibilité du code ne vient pas sans compromis :
- Au cours du développement, il est apparu que la bibliothèque devenait trop grosse pour être déployée sur des M5Stack Core, et afin résoudre ces limitations matérielles, la bibliothèque a été optimisée pour fonctionner sur des M5Stack Core2 (qui possèdent plus de RAM et de stockage interne).
- La logique de polymorphisme et de type abstrait implique que chaque appareil embarque toutes les méthodes de toutes les classes, y compris de celles dont il n'a pas besoin. Cela ne pose pour le moment pas de problème, mais si la bibliothèque est amenée à grandir encore plus, une optimisation de ce côté pourrait s'avérer nécessaire. Son implémentation n'est pas compliquer : il suffit de rajouter des macros avant la définition de chaque classe afin de n'inclure que le code nécessaire, mais cela implique de définir le type de M5 à la compilation, rendant le déploiement plus technique et le code moins flexible.
Structure
Dépendances
La librairie fait appel à de nombreuses librairies :
- M5Unified : bibliothèque standard utilisée pour contrôler et interagir avec les M5
- M5GFX : bibliothèque graphique (normalement standard) permettant d'utiliser des fonctions d'affichage avancées afin de créer une UI
- UNIT_RFID_UHF : bibliothèque officielle de M5Stack afin de gérer le module RFID UHF
- MFRC522_I2C : bibliothèque officielle de M5Stack fin de gérer le module RFID (attention, il existe plusieurs versions de cette bilbiothèque et seule celle disponible sur le GitHub de M5Stack fonctionne)
- Wifi : bibliothèque standard permettant de contrôler la connexion WLAN du M5
- HTTPClient : bibliothèque permettant de faire des requêtes HTTP, notamment à l'API TimeTonic
- ArduinoJson : parseur JSON optimisé pour les ESP32, permet de manipulé les objets JSON retourné par l'API de TimeTonic
- Wire : bibliothèque standard permettant d'initialiser et de contrôler la connexion I2C du M5
Structure de code
La bibliothèque M5lib est conçue pour uniformiser le comportement de plusieurs dispositifs M5Stack Core2 dans l'environnement du FabLab, chacun jouant un rôle défini (accueil, servante, machine, etc.). Elle repose sur une architecture orientée objet claire et modulaire, facilitant l’évolution, la maintenance et l'intégration au back-end (TimeTonic).
Structure de la Bibliothèque M5lib
1. Classe de base abstraite : M5lib
-
Représente l’interface commune à tous les types de M5.
-
Contient les méthodes de base utilisées par tous les modules : lecture de carte RFID (
scancard), scan UHF (scanuhf), interaction utilisateur (showchoice,getuser), etc. -
Déclare des méthodes virtuelles pures (polymorphisme) à implémenter dans les classes dérivées :
uploadlog()etchangestatus().
2. Classes dérivées spécialisées
Chaque type de M5 (défini dans M5type) possède une classe dédiée, dérivée de M5lib :
| Classe | Hérite de | Spécificités |
|---|---|---|
accueil |
M5lib |
Méthodes supplémentaires : entree(), sortie(), regcard().Menu de motifs de visite. |
servante |
M5lib |
Gère la traçabilité des servantes utilisées. |
machine |
M5lib |
Pour l'enregistrement d’utilisation de machines. |
ordinateur |
M5lib |
Associe cartes/scans à une session ordinateur précise. |
materiel |
M5lib |
Permet le prêt/retour d’outils ou matériels via borrow(). |
Chaque classe surcharge au moins :
-
uploadlog: envoie les journaux d’usage à l’API TimeTonic avec une structure propre (identifiants de champs différents selon le type). -
changestatus: placeholder actuel (pour la plupart renvoie200) servant potentiellement à signaler un changement d’état matériel (ex : verrouillage machine, etc.).
3. Composants globaux manipulés
-
Périphériques :
-
MFRC522 mfrc522: pour la lecture RFID classique (Mifare). -
Unit_UHF_RFID uhf: pour les lectures UHF/EPC.
-
-
API & Données :
-
HTTPClient http: communication HTTP avec TimeTonic. -
JsonDocument doc: stockage de la réponse JSON.
-
-
Accès réseau :
-
Configuration du Wi-Fi intégrée dans
setupstd().
-
Résumé Visuel Simplifié
+---------------------------+
| M5lib | <--- classe abstraite
+---------------------------+
/ | | | \
/ | | | \
accueil servante machine ordinateur materiel <--- classes concrètes
Toutes implémentent :
+ uploadlog()
+ changestatus()
Chaque classe possède des méthodes propres, par exemple :
accueil fournit aussi :
+ entree()
+ sortie()
+ regcard()
Une évolution fluide : il suffit d’ajouter une nouvelle classe dérivée et d’enrichir la factory pour intégrer un nouveau comportement ou un nouveau rôle matériel dans le système du FabLab.
Structure détaillées
1. Classe Abstraite : M5lib
Classe de base commune à tous les types de M5. Elle définit les fonctionnalités fondamentales.
Fonctions membres
| Fonction | Rôle |
|---|---|
setupstd() |
Effectue l'initialisation matérielle commune : écran, Wi-Fi, RFID, UHF. Attention : la fonction est lboquante tant que le M5 n'est pas connecté au réseau prédéfinit. |
reducejson(String json) |
Réduit et structure le JSON de réponse de l’API TimeTonic pour simplifier l’accès aux champs utiles. Ne garde que le contenu de "fields" (endroit où est stocké entre autres les données demandées) et "rowInfos" (qui contient notamment le rowId des informations demandées) |
scancard() |
Scanne une carte RFID classique, retourne l’UID du tag sous forme de String. Contient une UI intégrée. Attention : la fonction est bloquante tant qu'elle n'a pas lu une carte. |
scanuhf(String* urfid) |
Scanne les tags RFID UHF via le module UHF externe, remplit le tableau passé en paramètre avec les EPC lues (max 200 EPC, ce qui est le max supporté par le module RFID UHF). Fonction actuellement inutilisée dans le code. |
showchoice(String choices[]) |
Affiche sur l’écran un menu de sélection contenant les String du tableau passé en paramètre : l’utilisateur peut naviguer puis valider un choix(jusqu’à 9 options), qui est retourné sous forme de String. |
virtual int uploadlog(String card, String action, String other) = 0 |
Méthode virtuelle pure pour uploader un log dans la table correspondante au type de M5. Prend en paramètre une carte lue, l'action effectuée par l'utilisateur et un agument optionnel (au choix, le motif de la visite, l'ordinateur ou l'outil emprunté). |
virtual int changestatus() = 0 |
Méthode virtuelle pure pour changer le statut d'emprunt/de présence (obsolète pour le moment car remplacé par automatisation TimeTonic). |
getuser(String* user) |
Lance un scan RFID (avec scancard() ), puis interroge l’API TimeTonic pour récupérer le nom, prénom, et rowId de l'utilisateur scanné. Peuple ensuite le tableau passé en paramètre : [nom, prénom, tag RFID, rowId]. |
borrow() |
Gère tout le cycle d’emprunt et retour d’un matériel/machine/ordinateur : identification (avec un appel getuser() ), log (avec un appel uploadlog() ), et contrôle utilisateur (gestion par l'utilisateur de la durée de son emprunt, avec à nouveau un scan de carte et un upload de log à la fin de l'emprunt. Boucles if/else à chaque étape du cycle pour gérer chaque type d'erreur (API, utilisateur inconnu, etc...). |
Attributs
user[4]: tableau de String contenant toutes les informations d'un utilisateur : [nom, prénom, tag RFID, rowId].urfid[200]: tableau de String pouvant contenir jusqu'à 200 EPC.sesskey: permet de modifier simplement et directement la clé d'API pour toutes les requêtes de la bibliothèques (en cas d'expiration par exemple)
2. Classes Dérivées
Chaque classe dérivée apporte des fonctionnalités propres à chaque typologie de M5 dans le FabLab.
a. Classe : accueil
Ajoute des méthodes spécifiques à la gestion d’accueil.
| Fonction | Rôle |
|---|---|
int uploadlog(...) override |
Upload des logs d’accueil à l’API avec les bons id (table, champs...). |
int changestatus() override |
Change le statut d’accueil (placeholder : actuellement valeur fixe pour compatibilité). |
void entree() |
Gère la procédure d’entrée : identification (avec getuser), choix du motif de visite (avec showchoice), upload du log d’arrivée (avec uploadlog) |
void sortie() |
Gère la sortie d’un utilisateur (avec getuser) et log cet évènement (avec uploadlog). |
void regcard() |
Enregistre une nouvelle carte RFID (avec un scancard puis une requete d'API spécifique) pour un utilisateur après inscription sur Timetonic (liaison rangée TimeTonic <-> badge RFID). La requête d'API récupère la dernière rangée créée avec une vue filtrée (vue chronologique dans TimeTonic), il faut donc faire l'association de carte immédiatement après l'inscription. |
Attributs spécifiques
String motifs[9]: Liste des motifs de visite disponibles à la sélection (préremplie pour plus de simplicité).String name : nom du M5, permet de définir l'action d'accueil effectuée : entrée, sortie ou 1ère inscription.
b. Classe : servante
Pour la traçabilité de l’usage des servantes.
| Fonction | Rôle |
|---|---|
int uploadlog(...) override |
Upload des logs liés à l’utilisation d’une servante (carte, action, ""). L'argument other ne sert pas pour les servantes. |
int changestatus() override |
Change le statut de la servante (obsolète, pour compatibilité). |
Attributs spécifiques
String rowid: id de la rangée de cette servante dans la table Servantes du book Inventaire dans TimeTonic (unique à chaque servante, et donc chaque appareil, voir table d'équivalence dans la doc privée).String name: nom du M5, permet de définir la servante concernée dans les logs.
c. Classe : machine
Gère l’utilisation des machines/outils fixes.
| Fonction | Rôle |
|---|---|
int uploadlog(...) override |
Upload logs liés à l’utilisation d’une machine (carte utilisateur, action). |
Attributs spécifiques
String rowid: id de la rangée de cette machine dans la table Machines du book Inventaire dans TimeTonic (unique à chaque machinr, et donc chaque appareil, voir table d'équivalence dans la doc privée).String name: nom du M5, permet de définir la machine concernée dans les logs.
d. Classe : ordinateur
Gère le suivi de l'emprunt des ordinateurs portables.
| Fonction | Rôle |
|---|---|
int uploadlog(...) override |
Upload logs spécifiques à l’usage d’un ordinateur (par exemple : session ouverte/fermée). |
Attributs spécifiques
- WIP
e. Classe : materiel
Gère les cycles d’emprunt et de retour d’outillage ou matériel divers.
| Fonction | Rôle |
|---|---|
int uploadlog(...) override |
Upload logs liés à l’utilisation (emprunt/retour) de matériels. |
Attributs spécifiques
- WIP
3. Utilisation de méthodes virtual / override
Les méthodes uploadlog et changestatus sont définies comme virtual dans la base, et nécessaires à la personnalisation du comportement selon chaque situation FabLab : chaque classe dérivée implémente les appels API avec les bons identifiants et formats de données.
Avec cette structure, chaque fonction de M5lib remplit un rôle précis dans la gestion, la traçabilité, l’ajout de dispositifs et l’intégration back-end dans l’écosystème du FabLab.
UI
Afin de simplifier, d'uniformiser et de clarifier l'affichage de texte et de l'interface dans le M5, Une classe UI a été créé. Elle permet de simplifier l'implémentation de l'interface utilisateur dans toutes les fonctions interagissant avec celui-ci.
Structure
Méthodes
showchoice : UI de sélection de choix multiples (anciennement dans M5lib), retourne la String du choix sélectionnétitre : affichage de texte en gros centré (taille 4, 13 charactères maximum avant dépassement de l'écran)soustitre : affichage de texte en moyen centré (taille 3, 17 charactères maximum)corps : affichage de texte en petit centré (taille 2, 26 charactères maximum)feedback : vibration pour retour utilisateur, à appeler à chaque fois qu'un bouton est presséLecteur de badge comme clavier BT
Principe
La saisie des numéros longs est fastidieuse : codes barres, numéros de cartes étudiants, etc. doivent pouvoir être "scannés" rapidement pour remplir des formulaires.
Pour les codes barres, la solution est connue et commerciale : il s'agit de "douchettes" laser, comme par exemple la série Honeywell 1470 :
L'appareil est reconnu comme un clavier par l'ordinateur auquel il est connecté. Ainsi, appuyer sur la gachette revient à saisir au clavier les numéros inscrits sur le code barre ou le QR code.
L'idée est de faire la même chose avec un M5Stack équipé d'un lecteur RFID pour saisir les numéros de carte étudiant.
On pourrait alternativement imprimer des codes barres à coller sur les cartes étudiant.
Cette approche est très différente de celle adoptée dans les autres chapitres du projet. Ici, Timetonic ou Fabtrack n'ont pas d'interaction avec le M5 Stack. La douchette ou le lecteur RFID sont -au fond- le prolongement de la main de l'utilisateur qui saisit le code. Dans les autres chapitres, le M5 Stack équipé du lecteur utilise l'API de Timetonic pour déclencher des actions. C'est radicalement différent (et plus complexe).
Bibliothèques utilisées
Emuler un clavier
Pour pouvoir interagir avec un maximum de dispositifs d'interrogation de Timetonic/Fabtrack, que ce soient des ordinateurs fixes ou des iPads mobiles dans l'espace, le scanner de cartes est sans fil et se connecte en bluetooth BLE.
Une bibliothèque qui permet cela pour les plateformes à base d'ESP32 est disponible ici. (archive)
La disposition du clavier qui est émulée est celle du clavier QWERTY-US exclusivement !
Il faut donc que ce soit le clavier choisi dans l'environnement/OS. Sinon, le résultat peut être surprenant.
Accesoirement, on constate que le clavier bluetooth, même lorsqu'aucune carte n'est transmise, cause des frappes malignes. L'ajout d'un appel à la fonction releaseAll semble résourdre le problème. C'est un point à éclaircir.
Testé totalement sur macOS.
Sous Windows, le périphérique bluetooth est reconnu, se connecte, transmets correctement nom et niveau de charge batterie, mais aucune donnée ne semble transmise : dans le menu "bluetooth et autres appareils", il n'apparaît pas dans la section claviers/souris mais dans "autres appareils" :
Reste à faire :
- tester sous Linux (le PC de l'entrée)
- tester avec les iPad.
Lire les cartes RFID
Pour lire les cartes, on utilise la même bibliothèque ce celle déjà employée par Mathieu de Rooster, qui explique son fonctionnement ici.
Implémentation
Le code ci-dessous permet, en utilisant les bibliothèques précédentes, d'émuler un clavier bluetooth pour envoyer les caractères lus sur une carte RFID.
Le programme comporte :
- une fonction qui permet de transmettre également la valeur du niveau de charge de la batterie (comme le fait tout périphérique bluetooth)
- un contrôle de longueur de la chaîne lue et convertie avant son envoie par la fonction
print, et la prise en charge d'une erreur si la longueur n'est pas exactement celle attendue pour les cartes Izly et cartes d'étudiants. - un forçage de la fonction
releaseAllaprès chaque transmission pour éviter les caractères surnuméraires. - on a ajouté des signaux sonores pour confirmer la lecture
#include <M5Unified.h>
#include "BleKeyboard.h"
#include "MFRC522_I2C.h"
BleKeyboard bleKeyboard("M5CardReader", "M5Stack", 100);
MFRC522 mfrc522(0x28);
void setup() {
M5.begin();
Wire.begin();
Serial.begin(115200);
bleKeyboard.begin();
M5.Lcd.println("M5Stack BLE Keyboard");
mfrc522.PCD_Init();
M5.Display.setTextSize(2);
M5.Display.setFont(&fonts::efontCN_12);
M5.Speaker.begin();
M5.Speaker.setVolume(50);
}
void loop() {
M5.update();
String uid = "";
M5.Lcd.clear();
M5.Display.setTextDatum(MC_DATUM);
M5.Display.setTextSize(3);
M5.Display.drawString("Présentez", 160, 100);
M5.Display.drawString("votre carte", 160, 140);
while (1) {
M5.Display.setTextSize(1);
float batLevel = M5.Power.getBatteryLevel();
M5.Display.drawString("Batterie : " + String(batLevel), 160, 40);
bleKeyboard.setBatteryLevel(M5.Power.getBatteryLevel());
if (mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial()) {
for (byte i = 0; i < mfrc522.uid.size; i++) {
if (mfrc522.uid.uidByte[i] < 0x10) {
uid += "0";
}
uid += String(mfrc522.uid.uidByte[i], HEX);
if (i < mfrc522.uid.size - 1) {
uid += ":";
}
}
M5.Lcd.clear();
int L = uid.length();
if (L == 20) {
M5.Display.setTextSize(3);
M5.Display.drawString("Carte scannée", 160, 120);
M5.Speaker.tone(440, 250); // Frequence Hz, duree ms
M5.delay(100);
M5.Speaker.tone(880, 250);
//M5.Display.drawString(uid, 160, 120);
int L = uid.length();
//M5.Display.drawString(String(L), 160, 160);
String uidDeb = "";
String uidFin = "";
for (int j = 0; j < 10 ; j++) {
uidDeb += uid[j];
uidFin += uid[j+10];
}
//M5.Display.drawString(uidDeb, 160, 200);
//M5.Display.drawString(uidFin, 160, 240);
bleKeyboard.print(uidDeb);
M5.delay(100);
bleKeyboard.print(uidFin);
M5.delay(2000);
bleKeyboard.releaseAll();
break;
}
else {
M5.Display.setTextSize(3);
M5.Display.drawString("Erreur de lecture", 160, 80);
M5.Display.drawString("Réessayez svp", 160, 120);
M5.Speaker.tone(440, 250); // Frequence Hz, duree ms
M5.delay(100);
M5.Speaker.tone(220, 250);
M5.delay(2000);
bleKeyboard.releaseAll();
break;
}
}
}
}
Réflexions sur l'ergonomie de UI
Etat des lieux
Aujourd'hui, les informations liées à l'accueil et les emprunts sont enregistrées dans un logiciel développé en interne, FabTrack, accessible uniquement aux emplois-étudiants, avec une interface web accessible via deux PC Linux :
Les enregistrements des participants à des ateliers spécifiques fait appel à des formulaires web de style Google Form/Framaform. Enfin, les données liées à l'usage des machines ne sont pas collectées, et seules les informations de maintenance sont notées, sur papier :