|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
![]() MUIbase est un système de gestion de base de données relationnelles (SGBDR pour les intimes) programmable et disposant d'une interface graphique en MUI. Dis comme ça quand on n'est pas connaisseur, ça ne dit pas grand-chose, en plus simple c'est une base de données disposant d'un langage de programmation permettant de réaliser des tâches personnalisées et d'une interface graphique en MUI permettant de mettre les données et les résultats en forme en construisant des interfaces MUI. À qui cela s'adresse ? S'il est vrai qu'il faut avoir quelques notions de ce qu'est une base de données relationnelle et être familier avec les notions de "tables", de "champs" et autre "requêtes" cela n'est pas réellement obligatoire. De même, il n'est pas non plus vraiment nécessaire d'être un programmeur hors pair pour écrire des petites macros permettant de réaliser des tâches simples, et concernant la construction des interfaces graphiques MUI tout se fait à la souris donc là encore aucune connaissance préalable n'est requise. Il n'y a donc pas de raison de bouder MUIbase ! Rapide présentation et petit historique MUIbase est développé sur Amiga sous forme de partagiciel par Steffen Gutmann depuis 1994, il s'agit d'une évolution de son précédent SGBD AmigaBase (voir test de la version 2.6 sur Obligement) qui était développé depuis 1989 8-o. En juin 2006 la version 2.0 Amiga a été mise sous licence générale GNU (GPL) tandis que l'auteur continuait de proposer des versions partagicielles pour Linux et Windows (après avoir porté la partie graphique sous GTK), finalement milieu 2007 les autres versions ont suivi, tous les codes sources sont maintenant accessibles depuis un projet sur SourceForge. Grâce à cette ouverture des codes sources en plus des versions Linux, Windows et Amiga 68k, nous disposons maintenant de versions pour AmigaOS 4, MorphOS et même AROS, donc il y en a pour tous les goûts. Et malgré l'ouverture de ses codes sources et surtout grâce au courage et à la motivation de son auteur (grandement poussé par quelques utilisateurs acharnés ;-)) MUIbase continue d'évoluer très rapidement. Installation de la version Amiga L'installation est très simple, il suffit de lancer le script Installer fourni et répondre à quelques questions, en plus cerise sur le gâteau hormis les traditionnels anglais et allemand, la procédure d'installation parle également le français (grâce à votre serviteur ;-)) ce qui fait une excuse en moins pour ne pas l'essayer. MUIbase Amiga n'a que peu de dépendances en dehors de MUI lui-même (au minimum la version 3.8, mais cela ne devrait poser de problème à personne : qui utilise encore une version antérieure ?) et quelques classes MUI additionnelles mais finalement plutôt classiques à savoir TextEditor, BetterString, et NList. Toutefois, si l'on désire relire des bases créées ou modifiées sur des plates-formes Linux ou Windows il faudra disposer de la bibliothèque codesets.library v6.5 pour pouvoir relire et modifier les chaînes de caractères au format UTF-8. Je conseille d'installer la documentation utilisateur (qui est également traduite en français) ainsi que les démos. Première utilisation et rapide tour du propriétaire Après l'installation, il est tout de suite possible de lancer MUIbase, à ce moment une fenêtre s'ouvre avec une guêpe sur fond de ruche en arrière-plan. ![]()
![]() Pour basculer dans le mode d'édition de structure on utilise le menu "Projet/Éditeur de structure", la nouvelle fenêtre présentée permet de gérer à la fois la structure de la base et la façon dont elle est présentée. Pour gérer la structure c'est la partie gauche de la fenêtre qui est utilisée, en haut on gère les tables (si on pense à une base de données clients on va vouloir avoir dans la base à la fois des personnes, des commandes et des factures, en reprenant l'analogie des classeurs on va faire trois classeurs pour ranger nos fiches, un classeur est une table) en bas on gère les champs (les informations que l'on met sur la fiche). Dans la partie droite de la fenêtre il s'agit de tout ce qui concerne l'affichage, quoi qu'il arrive chaque projet MUIbase dispose toujours d'une fenêtre spéciale nommée "Fenêtre racine", ensuite pour chaque table du projet MUIbase propose de gérer une "fiche de table" (tiens on retombe innocemment sur l'analogie des fiches ;-)) qui pourra soit être affichée d'un seul bloc dans la fenêtre racine (défaut) soit être affichée dans une fenêtre séparée spécifique. La fenêtre racine peut être utilisée pour toute sorte de choses, par exemple dans la démo "Movie" elle permet est constituée de boutons permettant d'ouvrir chacune des trois tables dans sa fenêtre propre, au contraire dans la démo "Account" elle montre la fiche de la table "Account". Présentation sous forme de rapide tutoriel Pour démontrer la puissance et la simplicité de MUIbase je vous propose un petit tutoriel largement inspiré du chapitre "Travaux dirigés" du manuel utilisateur de MUIbase sans toutefois autant approfondir histoire de vous laisser quelques surprises. ;-) Le but de ce tutoriel sera de vous guider dans la création d'une mini base de données "généalogique" en vous montrant comment créer des tables, des champs, comment créer des relations (ben oui on a une base relationnelle ce n'est pas pour rien ;-)), comment écrire des requêtes et finalement comment écrire une petite macro (plutôt appelée "programme" dans le manuel). Pour commencer il faut que MUIbase soit sur un projet vide, c'est l'état par défaut dans lequel il s'ouvre, sinon si vous avez déjà un projet ouvert, vous pouvez sélectionner le menu "Projet/Nouveau". Puisque votre projet est vide, il fait lui créer sa structure, pour ce faire vous allez sélectionner le menu "Projet/Éditeur de structure". Voilà le travail peut maintenant commencer. Comme notre projet doit être une base de données généalogique il va falloir stocker des personnes, il vous faut donc une table "Personne". Pour créer cette nouvelle table vous allez donc cliquer sur le bouton "Nouveau" situé dans la zone "Tables", cela ouvre une fenêtre "Nouvelle table" vous demandant quelques informations sur la nouvelle table que vous souhaitez créer dont notamment son nom. Vous allez saisir le nom "Personne", attention dans MUIbase certaines règles sont à appliquer sur le nommage des objets : le nom doit obligatoirement débuter par une majuscule, ensuite tout caractère ASCII alphanumérique peut être employé (mais pas de caractères accentués ou autre cédille). Vous laissez les autres options à leur valeur par défaut et vous cliquez sur "Ok", voilà vous venez de créer votre première table MUIbase :-). L'étape suivante consiste à indiquer quelles sont les informations que vous souhaitez avoir dans votre nouvelle table. Cela se passe dans la zone dénommée "Champs". Pour le projet de généalogie vous aurez besoin du nom et du prénom des personnes, vous devrez donc créer deux champs dans la table "Personne". Pour ajouter votre premier champ, cliquez simplement sur le bouton "Nouveau" situé au bas de la zone "Champs", cela ouvre une fenêtre "Nouveau champ" vous demandant des informations sur le champ à ajouter. Au premier coup d'oeil un champ nécessite plus d'informations qu'une table, mais pas de panique cela reste relativement simple : en premier lieu on vous demande le nom du champ à ajouter vous allez commencer par ajouter le champ destiné à contenir le nom de la personne, vous le nommerez "Nom" (les mêmes restrictions que pour le nom des tables s'appliquent), ensuite vous devez renseigner le type du champ, en effet selon l'information que vous voulez stocker vous n'avez pas besoin du même type de données, MUIbase vous propose les types suivant :
En guise d'exercice vous allez rajouter un deuxième champ "Prenom" également de type chaîne, vous devriez obtenir quelque chose de similaire à l'image suivante. ![]() ![]() Maintenant pour ajouter un enregistrement il vous suffit de sélectionner le menu "Table/Nouvel enregistrement" (pour que ce menu soit activé il se peut que vous ayez besoin de cliquer dans la fenêtre racine), les champs de la table deviennent alors accessibles et il vous est alors possible de saisir les informations demandées, pour nous faire la main nous allons faire la généalogie de la famille Curie, nous allons donc commencer par saisir les individus suivants :
LISP est un langage fonctionnel qui s'écrit en utilisant beaucoup de parenthèses et avec une notation polonaise c'est-à-dire que toute opération est mise entre parenthèses, à l'intérieur on commence par indiquer l'opération à appeler puis, séparés par des espaces, les opérandes de cette opération (chaque opérande pouvant être lui-même le résultat d'un appel d'opération). Par exemple pour tester si deux variables a et b sont égales vous utiliserez l'opérateur d'égalité = de la façon suivante :
Si vous vouliez afficher "a égale b" si a=b et "a diffère de b" dans le cas contraire vous écririez :
Voilà pour un rapide aperçu, plus de détails ainsi que la liste de toutes les fonctions disponibles dans le langage de programmation sont donnés au chapitre 15 "Programmation de MUIbase" du manuel. L'écriture d'une requête dans MUIbase se fait à l'aide de l'éditeur de requêtes auquel vous accédez via le menu "Programme/Requêtes...". L'éditeur est séparé en trois parties : tout en haut une barre de boutons permettant de charger, enregistrer, exécuter et nommer des requêtes, en dessous un champ de saisie permettant de taper la requête ou d'afficher la requête sélectionnée, puis encore en dessous une zone dans laquelle s'afficheront les résultats de l'exécution de la requête affichée au-dessus. Une requête de recherche de donnée est toujours de la forme SELECT <éléments> FROM <table> par exemple pour afficher tous les prénoms des individus de la table "Personne" vous écririez :
Cliquez ensuite sur le bouton "Exécuter...", vous devriez obtenir un résultat semblable à l'image suivante. ![]() En guise d'exercice essayez de rajouter le nom de famille dans l'affichage. Vos requêtes peuvent être mémorisées, pour cela il vous suffit de leur donner un nom dans la zone plus à gauche en haut de l'éditeur, attention cependant toute modification est automatiquement mémorisée, il faut donc se méfier lorsque l'on a enregistré une requête. Pour rechercher une requête mémorisée, il suffit de cliquer sur le bouton "popup" situé juste à droite, puis de sélectionner la requête voulue dans la liste, vous pouvez également en supprimer une, en dupliquer une ou en débuter une nouvelle. Il se peut que vous vouliez trier les résultats, il suffit pour cela de rajouter à la fin de la requête la clause ORDER BY puis de lister dans l'ordre les éléments selon lesquels il faut trier, attention ces éléments doivent être des éléments sélectionnés pour l'affichage, c'est-à-dire apparaissant dans la clause SELECT, il est interdit de trier selon un champ non sélectionné même si la table auquel il appartient apparaît dans la clause FROM, quelques exemples : SELECT Prenom FROM Personne ORDER BY Prenom OK SELECT Prenom FROM Personne ORDER BY Nom KO SELECT Prenom, Nom FROM Personne ORDER BY Nom, Prenom OK SELECT Prenom FROM Personne ORDER BY Nom, Prenom KO Voilà, c'est bien beau de lister la totalité des enregistrements d'une table, mais ce n'est pas bien utile, alors maintenant vous aimeriez bien savoir comment il faut faire pour écrire des requêtes un peu plus poussées... La réponse tient en un seul mot : la clause WHERE qui permet de mettre des critères de sélection, elle se rajoute après la clause FROM mais avant l'éventuelle ORDER BY. À la suite d'une clause FROM on rajoute une ou plusieurs conditions que l'enregistrement doit valider pour pouvoir être affiché, par exemple :
...donne la liste des individus dont le nom de famille est exactement "Curie". À noter que la clause WHERE peut porter sur des champs de la table sélectionnée qui ne sont pas affichés (au contraire de ORDER BY). En guise d'exercice vous pouvez essayer de lister tous les individus dont le nom contient "Curie", en utilisant la fonction LIKE qui permet de chercher si une chaîne est égale à un motif utilisant une ou plusieurs fois le caractère joker "*", par exemple (LIKE param "a*") indique si param commence par un "a". Voilà pour une présentation rapide des requêtes. Relations ou références Abordons maintenant l'un des points clé des bases de données relationnelles : les relations ou références. Elles permettent de faire des liens entre des enregistrements d'une même table ou de tables différentes, dans notre exemple de généalogie, une relation qu'il paraît évidemment important de modéliser est la relation parent-enfant. Tout d'abord, un petit mot en général une relation est bidirectionnelle, par exemple la relation parent-enfant peut se faire de l'enfant vers son parent ou du parent vers chacun de ses enfants, il n'est pas nécessaire dans la base de données de mémoriser les deux sens en effet si l'on sait que B est l'enfant de A on peut en déduire automatiquement que A est le parent de B, il faut donc faire un choix. En base de données on choisit toujours de mémoriser le lien de l'enfant vers le parent, c'est-à-dire que l'on mémorise dans l'enfant quel est son parent, cela vient d'une explication évidente qu'un enfant ne peut avoir qu'un seul parent (ne parlons pas pour le moment de père et de mère) alors qu'un parent n'a a priori pas un nombre connu à l'avance d'enfants, il serait donc difficile de définir à l'avance le nombre de champs destiné à mémoriser les enfants qu'il faudrait mettre dans la table parent. Dans les relations de "1 vers plusieurs" (1 parent peut avoir plusieurs enfants, 1 élève peut faire plusieurs devoirs, 1 client peut avoir plusieurs commandes...) on stocke toujours la référence dans la table qui ne peut avoir qu'un seul lien (un enfant donnée n'a qu'un seul parent, un devoir particulier n'appartient qu'à un seul élève, une commande spécifique n'a été passé que par un seul client) on dit que la table fille référence son parent. Dans notre cas nous voulons savoir le lien de parenté entre les individus, pour cela vous devez revenir dans l'éditeur de structure afin d'ajouter des champs dans notre table Personne, puis ajoutez un champ nommé "Pere" et de type "Référence", vous devez obtenir quelque chose de similaire à l'image suivante. ![]() Vous pouvez remarquer que l'on vous propose de choisir parmi une liste de noms, pas très pratique allez-vous me dire quand plusieurs personnes possèdent le même nom de famille de savoir différencier dans ce cas Pierre Curie de Ève Curie... Tout à fait, je vous propose donc de modifier cela afin d'afficher un ou plusieurs champs de l'enregistrement plutôt que son seul nom, pour cela retournez dans l'éditeur de structure. Nous allons maintenant nous occuper de la partie droite de l'éditeur, celle qui se dénomme "Affichage", elle permet de contrôler les aspects graphiques plutôt que structurels de la base elle-même. Comme nous désirons modifier l'affichage du champ Pere, double-cliquez sur celui-ci dans la liste cela doit vous ouvrir une fenêtre "Affichage du champ" contenant deux onglets. L'onglet "Général" vous permet de configurer des choses plus ou moins communes à tous les types de champ comme le titre qui apparaît en face du champ dans la fenêtre principale (par exemple ici vous avez la possibilité de modifier le texte, qui par défaut prend le nom du champ, pour passer de "Pere" à "Père" ce sera plus joli dans la fenêtre), la position de ce titre, la justification du texte, la police, la couleur d'arrière-plan, etc. L'onglet "Extras" quant à lui permet de configurer des options d'affichage propre au type de données du champ, par exemple ici pour notre champ référence, il nous est proposé de sélectionner les champs que l'on désire afficher, par défaut seul "Nom" est sélectionné (en fait le premier champ de la table), mais nous allons ajouter Prénom, vous pouvez également modifier l'ordre par un glissé-déplacé. Renouvelez l'opération pour le champ "Mere", puis quittez l'éditeur de structure. Vous pouvez maintenant saisir les relations suivantes :
Pour terminer nous allons maintenant aborder la conception de programmes MUIbase. L'un des points forts de MUIbase est la présence de son langage de programmation puissant, il permet de réaliser une quantité d'actions incroyables sur la base de données. Chaque projet MUIbase peut disposer de son propre programme qui est enregistré avec le projet lui-même. Pour pouvoir saisir/modifier le programme d'un projet il suffit d'utiliser le menu "Programme/Éditer" qui ouvre une nouvelle fenêtre constituée d'une partie éditeur de texte et de trois boutons situés en dessous. L'écriture se fait en utilisant le même langage dérivé du LISP que celui qui est employé dans les requêtes. Je vous propose d'écrire une macro permettant de lister les enfants de la personne courante, dans MUIbase chaque table dispose d'un "enregistrement courant", il s'agit de l'enregistrement actuellement activé (et affiché) dans la fiche de la table (même si la fiche n'est pas visible). Pour cela, il suffira de parcourir la table Personne et vérifier pour chaque individu si son champ père ou son champ mère référence la personne courante (je sais, les connaisseurs feraient une requête pour obtenir cela, mais ici le but est de montrer l'utilisation des macros de manière simple). Nous allons donc créer une fonction "enfants", qui ne prendra aucun paramètre, cela se fait à l'aide de la fonction DEFUN, de la façon suivante :
Nous venons de créer la fonction "enfants" qui ne prend aucun paramètres et qui pour le moment ne fait rien. Si l'on voulait avoir des paramètres on ajouterait entre les parenthèses suivant le nom de la fonction une liste séparée par des espaces au format <nom_variable>:<type>, par exemple la fonction calcAge prend en paramètres la date de naissance et la date du jour :
Reprenons notre exemple sur le listage des enfants, nous devons parcourir les individus de la table Personne, pour cela MUIbase propose la fonction FOR ALL. Sa syntaxe est simple :
Nous voulons maintenant tester si un enregistrement donné de la table Personne référence l'enregistrement courant comme étant son père ou sa mère. Le problème c'est qu'en parcourant l'ensemble des individus de la table Personne, nous modifions par la même occasion l'enregistrement courant de cette même table. Il est donc nécessaire de mémoriser au préalable la valeur de l'enregistrement courant dans une variable temporaire, cela se fait en utilisant la fonction LET de la manière suivante :
Ici nous définissons une variable nommée "parent" et dont la valeur est positionnée sur l'enregistrement courant de la table Personne, en effet dans MUIbase on désigne l'enregistrement courant d'une table simplement en utilisant son nom. Il faut noter que la fonction LET permet de définir des variables ayant une durée de vie limitée à l'intérieur des parenthèses, il n'est donc possible d'utiliser notre variable "parent" qu'avant la parenthèse de fin identifiée par le commentaire "fin de LET". Pour tester si un individu est le père ou la mère d'un autre, cela se fait assez simplement en utilisant la commande IF et le connecteur booléen OR. La syntaxe d'un test IF est la suivante :
Il n'est pas obligatoire de spécifier la partie à évaluer quand le prédicat est faux si cela n'est pas nécessaire, dans ce cas il ne se passera rien si le prédicat est faux. Comme nous voulons tester si l'enregistrement courant au démarrage de la fonction est le père ou la mère de l'enregistrement en cours d'examen, notre prédicat est en fait composé de deux prédicats reliés par le connecteur logique OR. Pour tester si un champ référence un enregistrement donné il suffit d'utiliser l'opérateur d'égalité, avec d'un côté l'enregistrement à tester et de l'autre le nom du champ référence. Dans notre cas on veut regarder si le champ Pere pointe sur l'enregistrement mémorisé dans la variable parent (attention à la casse, un nom de champ commence toujours par une minuscule dans MUIbase) :
Cela nous donne :
Lorsque l'enregistrement a pour père ou mère notre enregistrement parent, nous voulons afficher son nom et son prénom, dans le cas contraire on ne fait rien. Pour imprimer on utilise la fonction MUIbase PRINTF, cette fonction prend un nombre variable de paramètre mais au moins un. Le premier paramètre de la fonction est une chaîne de caractères, par exemple pour afficher "bonjour tout le monde" on utilise :
Toutefois, ce paramètre permet également de formater le texte à afficher (d'ailleurs on le nomme "chaîne de formatage") et d'y inclure la valeur de variables ou de champs, pour cela PRINTF reconnaît l'utilisation de paramètres de formatage introduits par le caractère pourcent (%) par exemple pour afficher "je suis né en <xxxx>, une bonne année !" et afficher à la place de <xxxx> la valeur contenue dans la variable "naissance" on écrit :
Ici j'ai utilisé %i car naissance est de type entier, toutefois pour les autres types de donnée connus par MUIbase il existe d'autres paramètres de formatage : %s pour les chaînes de caractères, %f pour les nombres réels, etc. Les plus aguerris d'entre vous auront reconnu que la fonction marche de la même manière que la fonction C du même nom, cependant je les enjoins tout de même à consulter le manuel de MUIbase car il existe de subtiles différences. Il est possible d'avoir autant de paramètres que l'on veut il faut juste bien faire coïncider le nombre et la position des paramètres dans la chaîne de formatage avec ceux listés après la chaîne de formatage, exemple avec deux paramètres :
En exercice je vous laisse remettre tout ça en ordre pour obtenir la fonction enfants (pour ceux qui n'auraient pas compris le code est fourni plus bas, s'ils veulent tout de même continuer). Une fois cela fait, cliquez sur "Compiler & Fermer" si vous n'avez pas d'erreurs vous devriez voir la fenêtre se fermer, dans le cas contraire un message sera affiché dans la barre de titre. Voilà, maintenant c'est bien beau nous avons notre fonction, mais nous aimerions bien l'exécuter ! Pour cela, nous allons ajouter un bouton sur la fiche de la table Personne et indiquer à MUIbase d'exécuter notre fonction à chaque fois que l'on clique sur ce bouton. Allez dans l'éditeur de structure (Projet/Éditeur de structure), cliquez sur le bouton "Nouveau" de la zone "Champs" (par exemple : pas le premier en haut, celui en bas), nommez-le "Enfants" et donnez-lui le type "Bouton", normalement à ce stade un champ "Déclencheur" devrait faire son apparition en bas de la fenêtre, ce champ indique quelle est la fonction exécutée lors du clic sur le bouton. Vous pouvez soit taper directement le nom de la fonction à appeler, soit cliquer sur le petit bouton situé à droite du champ pour sélectionner la fonction dans la liste des fonctions disponibles. Attention il n'est pas fait de vérification sur l'existence de la fonction, aussi je conseille de passer par la sélection dans la liste pour éviter des mauvaises surprises. Cliquez sur le bouton "Ok" puis sortez du mode éditeur de structure. Normalement vous devriez voir le nouveau bouton en dessous de vos champs de base de données, vous pouvez alors naviguer via le panneau de contrôle vers la personne pour qui vous souhaitez connaître les enfants puis cliquer sur votre bouton. Il se peut que rien n'apparaissent à l'écran, c'est tout à fait normal, en fait la fonction PRINTF écrit sur la "sortie standard", par défaut MUIbase positionne sa sortie standard sur un fichier sur disque que vous pouvez configurer via le menu "Programme/Fichier de sortie". Mots de la fin Voilà, ce rapide tour est terminé, je n'ai évidemment pas tout abordé (par exemple la possibilité de piloter MUIbase par son port ARexx) j'ajouterais juste que grâce à la richesse du langage de programmation de MUIbase il est possible de faire un grand nombre de choses très puissantes, que Steffen, son auteur, est plutôt motivé et travaille déjà sur les nouveautés de la version future, il est très ouvert alors si vous avez des remarques, des demandes particulières n'hésitez pas à le contacter, ni à lui faire savoir votre reconnaissance par un petit geste financier. Annexe : code source de la fonction enfants
|