Pour partager cette vidéo sur les réseaux sociaux ou sur un site, voici son url :
Sujets que vous pourriez aussi aimer :Verrouiller et protéger une application Access
Nous poursuivons ici le développement de l'
application Access VBA pour évaluer des candidats avec des QCM. Jusqu'alors nous avions chargé l'ensemble des questionnaires dans une liste déroulante du formulaire d'accueil. Nous avions aussi créé une
zone d'authentification pour reconnaître le candidat afin de pouvoir archiver ses résultats à l'issue du test. Nous avions créé un
formulaire d'inscription géré en
Visual Basic Access afin d'inscrire les informations des candidats en
base de données.
Désormais nous souhaitons transformer le concept en application à part entière. Pour cela :
- Au démarrage de la base de données, le formulaire Listes doit s'ouvrir automatiquement. Ainsi les questionnaires seront naturellement proposés au choix du candidat, après identification.
- L'ensemble des objets Access, tels que les tables et formulaires, doivent être masqués. Ainsi le candidat n'aura pas accès aux objets de conception de l'application.
Mais avant cela, nous devons réaliser quelques travaux préparatifs qui permettront l'enregistrement des réponses du candidat en
base de données. Nous devons donc :
- Créer une table liée à la table des inscrits pour enregistrer ces données et les attacher au candidat,
- Modifier la source de données du formulaire questions, pour que seuls 20 énoncés soient proposés aléatoirement,
- Passer le paramètre du candidat en cours d'évaluation à ce même formulaire pour permettre l'enregistrement des informations qui lui sont liées,
Structure de base de données et Relations
Pour réaliser tous ces travaux, nous allons récupérer l'application en cours de développement, telle que nous l'avions laissée.
Pour enregistrer les résultats d'évaluation des candidats inscrits en base de données, nous devons créer une nouvelle table, liée à la
table msy_inscrits. Cette liaison doit s'opérer au niveau de la clé primaire, soit sur l'identifiant. La
règle de l'intégrité référentielle permettra ainsi, par le jeu des relations, d'enregistrer autant de résultats souhaités pour un candidat inscrit dans la table parent. En d'autres termes, chaque candidat pourra passer autant de tests qu'il le souhaite. Cette table liée devra enregistrer les informations suivantes :
- Clé externe, pour la liaison avec la table parent,
- Numéro automatique, pour l'identification unique de chaque enregistrement,
- Date d'évaluation,
- Nom du questionnaire,
- Note obtenue,
- Durée d'évaluation.
Nous allons concevoir cette
nouvelle table en mode Création afin de maîtriser le paramétrage de chacun des champs qu'elle doit comporter.
- Cliquer sur l'onglet Créer en haut de la fenêtre Access pour activer son ruban,
- Dans la section Tables du ruban, cliquer sur le bouton Création de table,
- Taper le premier nom de champ : res_num, en haut de l'éditeur de création de table,
- Dans la colonne Type de données, choisir NuméroAuto à l'aide de la liste déroulante,
- Puis, cliquer sur le bouton Clé primaire du ruban Création,
Nous venons de créer le champ qui permettra d'identifier chaque enregistrement de façon unique. Le
type de données NuméroAuto permet une incrémentation automatique qui ne réutilise jamais un numéro déjà employé, même si l'enregistrement correspondant a été supprimé.
- Créer ensuite le champ res_id avec le type de données Texte court,
Ce champ sera utilisé comme une
clé étrangère. Il permettra la
relation avec la clé primaire de la table parent des inscrits. Les deux champs liés doivent être du même type. Comme la
clé primaire de la table parent est un
texte court, le type correspondant pour la liaison est lui aussi un
texte court.
- Créer le champres_date avec le type de données Date/Heure,
- Dans l'onglet Général, choisir le format Date, complet,
- Dans le masque de saisie, taper l'expression suivante : 00/00/0000,
Le
masque de saisie permet de guider l'utilisateur lorsqu'il entre de nouvelles informations. Le symbole 0 est utilisé pour n'autoriser que la saisie de chiffres. Donc l'utilisateur ne peut pas saisir d'autres caractères. Ces chiffres sont regroupés et séparés naturellement par des slash pour reproduire un format Date.
- Dans la propriété Valeur par défaut, saisir la formule suivante : =Date(),
De cette façon, tout nouvel enregistrement sera automatiquement associé à la date du jour. Mais l'utilisateur peut la changer. L'intérêt est de ne pas avoir à insérer cette donnée en
VBA Access au moment d'inscrire les résultats du candidat qui vient de terminer l'évaluation.
- Créer le champ res_nom avec le type de données Texte court,
- Régler sa propriété Taille du champ à 50,
Ce champ servira à mémoriser le nom du questionnaire sur lequel le candidat s'est évalué. Les noms des questionnaires sont relativement courts. Il est donc opportun de limiter la taille des caractères autorisés pour ce champ, question de calibrage des ressources notamment.
- Créer le champ res_note avec le type de données Numérique,
- Régler sa propriété Taille du champ sur Octet,
Un
Octet est un
entier court dont les capacités se situent entre 0 et 255. Ce type est donc largement suffisant pour accueillir une note comprise entre 0 et 20.
- Créer le champ res_duree avec le type de données Numérique,
- Définir sa propriété Taille du champ sur Entier,
Comme l'indique l'aide en ligne, un entier peut stocker un nombre compris entre -32 768 et 32 767. Nous souhaitons stocker les durées d'évaluation sous forme de minutes. Donc un entier long qui va au-delà du milliard serait surdimensionné.
- Enregistrer la table (CTRL + S) sous le nom resultats,
Comme l'indique la capture ci-dessous, la table nouvellement créée apparaît désormais dans la liste des objets Access, dans le volet situé sur la gauche de la fenêtre.
Il s'agit maintenant de relier cette table à celle des inscrits, pour que tous les résultats dépendants puissent y être enregistrés.
- Fermer la table resultats,
- Cliquer sur l'onglet Outils de base de données en haut de la fenêtre Access,
- Dans la section Relations du ruban, cliquer sur le bouton Relations,
- Dans la boîte de dialogue qui suit, sélectionner les tables msy_inscrits et resultats,
- Puis, cliquer sur le bouton Ajouter puis sur le bouton Fermer,
Les deux représentations de tables apparaissent dans la fenêtre Relations avec tous les champs que chacune d'elle comporte. Il s'agit de relier le
champ inscrit_identifiant de la table parent (
Clé primaire) au
champ res_id de la table enfant (
Clé externe).
- Cliquer et glisser le champ inscrit_identifiant sur le champ res_id,
- Dans la boîte de dialogue qui suit, cocher les trois cases et valider par Ok,
La
règle de l'intégrité référentielle empêchera la création de tout nouvel enregistrement n'ayant pas de parent dans la
table msy_inscrits. Il s'agit d'une sécurité fondamentale d'un
gestionnaire de base de données. En d'autres termes, les résultats d'un candidat qui n'est pas inscrit dans la table parent, ne pourront pas être enregistrés dans la table enfant. Les
actions Mettre à jour et Effacer en cascade permettent d'intervenir et de nettoyer proprement une
base de données relationnelles, lorsque des modifications sont apportées aux enregistrements de la table parent. Par exemple, si un candidat se désinscrit, son enregistrement disparaît de la table msy_inscrits. Dans le même temps, le gestionnaire de base de données, par le jeu des
relations, supprimera tous les enregistrements qui lui sont liés, dans la table resultats. Ainsi, il ne sera pas nécessaire de déclencher un code Visual Basic Access pour générer un traitement récurrent de la table dépendante.
- Enregistrer les relations (CTRL + S) et fermer la fenêtre.
Source de données et transfert de paramètres
Pour poursuivre la préparation de notre application d'évaluation, nous souhaitons transmettre l'identifiant du candidat au
formulaire questions. C'est cet identifiant qui permettra à la fin du test, d'inscrire les résultats, dans la table liée que nous venons de construire. De plus, comme vous l'avez sans doute remarqué, chacune des tables propose un nombre différent de questions. Par exemple, les questionnaires Informatique générale et Microsoft Access proposent 99 questions. Nous souhaitons évaluer les candidats sur 20 d'entre elles. Et nous voulons que ces 20 questions soient tirées aléatoirement. Ainsi aucun test ne ressemblera à un autre.
- Afficher le formulaire questions en mode création,
- Cliquer sur le bouton Feuille de propriétés du ruban Création si elle n'est pas visible,
- Activer l'onglet événement de la feuille de propriétés du formulaire,
- Cliquer sur le petit bouton de son événement Sur chargement,
Nous basculons ainsi dans l'
éditeur de code Visual Basic Access, entre les bornes de la
procédure Form_Load. Tout code saisi entre ces bornes se déclenche donc au chargement du formulaire. Et comme vous le constatez, un code est déjà présent. Il s'agit des instructions que nous avions ajoutées dans la
formation pour transmettre des données entre deux formulaires.
Un premier code, depuis le
formulaire Listes ouvert en mode Design, avait permis d'inscrire dans le
Label transf, le nom du questionnaire choisi par l'utilisateur à l'aide de la liste déroulante.
Au chargement du formulaire questions, nous récupérons ce paramètre à l'aide de la
propriété Caption de cette étiquette. Ce paramètre n'est autre que le nom de la table correspondant au questionnaire. La
propriété RecordSource de l'objet Me désignant le formulaire actif, avait ainsi permis de modifier à la volée la source de données du formulaire. Ceci est rendu possible parce que le formulaire a été bâti sur l'une des tables de questionnaires. Et, chacune de ces tables possède la même structure.
Comme nous connaissons le nom de la table source, nous allons pouvoir exécuter une
requête SQL de sélection sur ce questionnaire. Comme nous l'avions révisé dans la
formation VBA Access sur l'authentification et l'inscription, la syntaxe d'une requête sélection en SQL est la suivante :
SELECT noms_des_champs FROM nom_de_la_table
Les noms des champs à extraire doivent être listés, séparés par des virgules. En SQL, lorsque nous les souhaitons tous, nous pouvons remplacer leur énumération par le symbole *, comme suit :
SELECT * FROM nom_de_la_table
Cette requête a par contre l'inconvénient de sélectionner tous les enregistrements, soit les 99 questions dans le cas des deux tables précédemment citées. Pour limiter la sélection à 20 enregistrements, nous pouvons utiliser le
mot clé TOP, comme suit :
SELECT TOP 20 * FROM nom_de_la_table
Dans ce cas, tous les champs des 20 premiers enregistrements sont extraits de la table citée après le
mot clé FROM. Or nous souhaitons que cette sélection de 20 questions varie aléatoirement à chaque début de test. Cela signifie qu'il faut faire un tri aléatoire. Le tri se réalise grâce aux
mots clés ORDER BY en SQL. Et pour que ce tri soit réalisé de façon aléatoire, nous devons exploiter la
fonction SQL RND qui demande en paramètre, le nom du champ sur lequel le tri aléatoire doit être réalisé. Le champ à utiliser est fort logiquement celui de la clé primaire, soit N°. Ce qui donne :
SELECT TOP 20 * FROM nom_de_la_table ORDER BY RND([N°])
Le nom de la table est connu au chargement du formulaire. Il s'agit donc d'une variable (transf.Caption) Ã
concaténer à la syntaxe SQL, par le
code VBA Access.
- Dans le code, remplacer l'affectation de la source du formulaire, comme suit :
Me.RecordSource= 'SELECT TOP 20 * FROM [' & transf.Caption & '] ORDER BY RND([N°])'
- Enregistrer les modifications (CTRL + S) et basculer sur l'application Access (ALT + F11),
- Double cliquer sur le formulaire Listes depuis le volet des objets Access, pour l'exécuter,
- Saisir un identifiant existant dans la table msy_inscrits, par exemple : 123456,
- Cliquer sur le bouton Ok pour valider l'authentification,
- Puis, choisir le questionnaire Microsoft Excel par exemple, dans la liste déroulante,
Nous sommes redirigés vers le formulaire questions qui charge bien le questionnaire Microsoft Excel. Comme vous le remarquez, la barre de navigation en bas du formulaire, indique que 20 enregistrements ont été sélectionnés. De plus, si vous comparez la première question proposée avec le premier enregistrement de la table, vous constatez qu'elles sont différentes. Pour en avoir le coeur net, il suffit de fermer le formulaire question, d'exécuter de nouveau le formulaire Listes, de s'identifier et ce choisir le questionnaire Microsoft Excel.
La gestion aléatoire des questionnaires a été réglée à l'aide d'une simple ligne de code, grâce à une
requête SQL adaptée. Nous devons maintenant transmettre l'identifiant du candidat évalué, au formulaire questions. Ce transfert doit s'opérer depuis le formulaire Listes qui accède déjà au formulaire questions en mode Design, pour lui passer le nom du test. Il suffit d'ajouter une ligne de code pour l'identifiant. Mais avant cela, il faut prévoir une étiquette (Label) de réception sur le formulaire questions.
- Afficher le formulaire questions en mode création,
- Dans la section Contrôles du ruban Création, sélectionner le contrôle étiquette,
- Puis, la tracer vers le bas du formulaire à proximité des autres contrôles masqués,
- Saisir le texte id par exemple,
En l'absence de saisie, un Label (contrôle étiquette) disparaît aussitôt.
- Activer l'onglet Autres de sa feuille de propriétés,
- Dans sa propriété Nom, saisir id_candidat,
Un contrôle se pilote en effet par son nom dans le
code VBA. Et comme il s'agit d'une étiquette, c'est sa
propriété Caption qui permet d'accéder à son contenu.
- Enregistrer les modifications et fermer le formulaire,
- Afficher maintenant le formulaire Listes en mode création,
- Sélectionner la liste déroulante présente sur le formulaire,
- Activer l'onglet Evénement de sa feuille de propriétés,
- Cliquer sur le petit bouton de son événement Avant MAJ,
Nous basculons ainsi dans l'
éditeur de code VBA Access, entre les bornes de la
procédure événementielle Liste_BeforeUpdate. Nous y retrouvons les lignes que nous avions codées, notamment pour transmettre le paramètre du questionnaire au formulaire questions. En mode Design, avant l'enregistrement des modifications, nous devons en profiter pour transférer l'identifiant du candidat. Pour cela, nous devons ajouter l'instruction nécessaire entre la ligne : Form_questions.transf.Caption = Liste.Text, et la ligne : DoCmd.Close acForm, 'questions', acSaveYes.
- Entre les deux instructions énoncées précédemment, ajouter la ligne de code suivante :
Form_questions.id_candidat.Caption = identifiant.Value
Nous inscrivons dans l'intitulé de l'étiquette id_candidat, l'information contenue dans la zone de texte de l'identifiant. Cette zone se nomme idenitifiant et c'est sa
propriété value qui permet d'extraire ce qu'elle contient.
- Enregistrer les modifications et basculer sur l'application Access,
- Exécuter le formulaire Listes avec la touche F5,
- Saisir l'identifiant 123456 par exemple puis cliquer sur le bouton Ok,
- Choisir le questionnaire Microsoft Excel dans la liste déroulante,
Le
code VBA nous redirige instantanément vers le
formulaire questions qui charge aléatoirement le test Excel. Et comme vous le remarquez, l'information de l'identifiant saisi, apparaît bien en bas du questionnaire, dans l'étiquette id_candidat que nous venons d'ajouter.
Bien sûr cette information ne doit pas être visible. Il en va de même pour la zone de saisie REPONSES qui affiche le numéro du choix à fournir à la question posée. Cette information ne doit être accessible que par le
code VBA, afin qu'il puisse comparer la réponse donnée avec le bon numéro. Nous allons donc masquer ces deux contrôles, ce qui n'empêchera pas le
code Visual Basic de les exploiter.
- Afficher le formulaire questions en mode création,
- Sélectionner ensemble les contrôles REPONSES et id_candidats à l'aide de la touche CTRL,
- Activer l'onglet Format de la feuille de propriétés,
Lorsque plusieurs contrôles sont sélectionnés, la feuille de propriétés propose seulement les propriétés communes aux deux objets. C'est entre autres ce que nous enseigne le
support de formation sur les trucs et astuces dans Access.
- Régler la propriété Visible sur False par un double clic sur la valeur par exemple,
- Enregistrer les modifications et fermer le formulaire,
- Exécuter le formulaire Listes,
- Saisir un identifiant valable et valider par Ok,
- Choisir un questionnaire à l'aide de la liste déroulante,
Le transfert s'opère en effet mais comme vous le constatez, une erreur de code est générée. Nous tentons d'accéder au contrôle REPONSES pour activer sa zone de saisie (SetFocus). Or ce dernier est désormais masqué (Visible=False).
Pour pallier le problème, il suffit de supprimer cette ligne de code.
- Cliquer sur le bouton Débogage de la boîte de dialogue,
- Supprimer la ligne REPONSES.SetFocus qui apparaît en surbrillance jaune,
- Cliquer sur le bouton Réinitialiser de la barre d'outils de l'éditeur de code,
- Puis enregistrer les modifications et basculer de nouveau sur l'application Access,
- Fermer les formulaires puis relancer le processus depuis le formulaire Listes,
Nous basculons bien vers le formulaire questions sur le test choisi et pour lequel les 20 questions ont été générées aléatoirement. Et surtout, vous remarquez que les informations confidentielles sont désormais invisibles, mais toujours accessibles par le code.
Protection des données et verrouillage de l'application
Notre application d'évaluation des candidats prend forme petit à petit. Dans une prochaine étape, nous développerons le code capable de récolter les réponses fournies par le candidat au fur et à mesure de son évaluation. Une fois toutes les réponses consolidées, nous pourrons ainsi inscrire ses résultats dans la table, en les attachant à son identifiant.
Mais avant cela, pour transformer notre projet en véritable application, nous allons réaliser quelques paramétrages. Nous souhaitons que seul le formulaire Listes soit accessible au démarrage et qu'il s'ouvre automatiquement. Pour cela, autrefois nous aurions dû avoir recours à une
macro autoexec pour déclencher l'ouverture du formulaire désigné. Désormais ces réglages sont directement personnalisables depuis les options d'Access. De plus, nous souhaitons masquer tous les objets tels que les tables et formulaires afin d'empêcher la modification des sources par des tiers. Ces réglages sont accessibles au même endroit.
- Cliquer sur l'onglet Fichier en haut de la fenêtre Access,
- En bas de la liste qui apparaît, choisir Options,
- Dans la boîte de dialogue qui suit, sélectionner la rubrique Base de données active,
- Au centre, dans la zone Afficher le formulaire, choisir Listes,
- Décocher la case Afficher la barre d'état,
- Décocher la case Activer le mode Page,
- Décocher la case Autoriser les modifications de structure...,
- Plus bas, décocher la case Afficher le volet de navigation,
- En dessous, décocher les cases permettant d'autoriser les menus,
- Valider ces réglages par Ok et valider le message qui suit en fermant la base de données,
Pour vérifier que ces personnalisations ont pris effet, il s'agit de relancer la base de données.
- Depuis le dossier où elle est enregistrée, double cliquer sur la base de données pour l'ouvrir,
Comme vous le constatez, le
formulaire Listes s'affiche automatiquement à l'ouverture. Le volet des objets Access a disparu. Parmi les rubans, seul le ruban Accueil demeure mais il ne propose plus que des fonctions de bases. Si vous vous authentifiez et que vous choisissez un questionnaire, l'application se déroule parfaitement. Nos données sont donc protégées quand dans le même temps, l'application apparaît plus fonctionnelle, et ce n'est qu'un début.
Fort heureusement, il est encore possible d'accéder aux objets de conception de la base de données :
- Fermer la base de données,
- Tout en maintenant la touche MAJ (Shift) enfoncée, double cliquer sur la base de données pour l'exécuter,
Cette astuce a permis de l'ouvrir en ignorant les paramétrages réalisés depuis les options d'Access.