JavaRush /Blog Java /Random-FR /Création d'une application Web simple à l'aide de servlet...
fatfaggy
Niveau 26
Киев

Création d'une application Web simple à l'aide de servlets et de jsp (partie 2)

Publié dans le groupe Random-FR
Je continue de décrire le processus de création d'une application Web à l'aide de servlets, jsp, Maven et Tomcat. Début de l'article , si nécessaire.
Nous créons des entités.
Créons une classe User dans le package d'entités, dans laquelle nous créerons deux variables de chaîne privées, le nom et le mot de passe. Créons des constructeurs (par défaut et celui qui accepterait les deux valeurs), des getters/setters, remplaçons la méthode toString() juste au cas où, ainsi que les méthodes equals() et hashCode(). public class User { private String name; private String password; public User() { } public User(String name, String password) { this.name = name; this.password = password; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } @Override public String toString() { return "User{" + "name='" + name + '\'' + ", password='" + password + '\'' + '}'; } @Override public boolean equals(Object o) { if (this == o) return true; if (o == null || getClass() != o.getClass()) return false; User user = (User) o; if (name != null ? !name.equals(user.name) : user.name != null) return false; return password != null ? password.equals(user.password) : user.password == null; } @Override public int hashCode() { int result = name != null ? name.hashCode() : 0; result = 31 * result + (password != null ? password.hashCode() : 0); return result; } } Nous pouvons maintenant commencer à créer une liste d'utilisateurs, dans laquelle nous ajouterons nos utilisateurs et à partir de laquelle nous les afficherons. Mais il y a un problème. Nous ne créons pas nos objets servlets ; Tomcat les crée pour nous. Les méthodes que nous y remplaçons sont également déjà définies pour nous et nous ne pouvons pas ajouter de paramètre. Comment alors créer une liste commune qui serait visible dans nos deux servlets ? Si nous créons simplement notre propre objet de liste dans chaque servlet, il s'avérera que nous ajouterons des utilisateurs à une liste, mais l'affichage d'une liste d'utilisateurs utilisant le servlet ListServlet sera complètement différent. Il s’avère que nous avons besoin d’un objet commun aux deux servlets. De manière générale, nous avons besoin d'un objet qui serait commun à toutes les classes de notre programme ; le seul objet pour tout le programme. J'espère que vous avez entendu quelque chose sur les modèles de conception. Et c'est peut-être pour certains le premier véritable besoin d'utiliser le modèle Singleton dans leur programme. Vous pouvez faire preuve de créativité et créer des singletons sympas, avec des doubles vérifications et une synchronisation (oui, nous avons une application multithread, puisque Tomcat exécute des servlets dans différents threads), mais j'utiliserai l'option avec initialisation précoce, car dans ce cas, il tout à fait convenable.
Création d'un modèle.
Ensuite, nous créerons une classe (et y implémenterons le modèle singleton) dans le package model, et nous l'appellerons également de manière assez colorée Model. Créons-y un objet de liste d'utilisateurs privé et créons deux méthodes : une pour que vous puissiez ajouter un utilisateur, et la seconde - laissez-le simplement renvoyer une liste de chaînes (noms d'utilisateur). Puisque notre objet utilisateur est constitué d'un nom et d'un mot de passe, nous ne souhaitons pas « révéler » les mots de passe des utilisateurs, nous ne renverrons donc qu'une liste de leurs noms. public class Model { private static Model instance = new Model(); private List model; public static Model getInstance() { return instance; } private Model() { model = new ArrayList<>(); } public void add(User user) { model.add(user); } public List list() { return model.stream() .map(User::getName) .collect(Collectors.toList()); } }
Un peu sur mvc.
Puisque vous avez entendu parler de singleton, cela signifie que vous avez probablement entendu parler d'un autre modèle de conception - MVC (model-view-controller, ou en russe model-view-controller, ou tout comme en anglais model-view-controller). Son essence est de séparer la logique métier de la présentation. Autrement dit, séparez le code qui détermine quoi faire du code qui détermine comment afficher . La vue (vue ou simplement vues) est responsable de la forme sous laquelle certaines données sont présentées. Dans notre cas, les vues sont nos pages JSP. C'est pourquoi je les ai mis dans un dossier appelé vues. Le modèle correspond aux données réelles avec lesquelles le programme fonctionne. Dans notre cas, il s'agit d'utilisateurs (liste d'utilisateurs). Eh bien, les contrôleurs sont le lien qui les relie. Ils récupèrent les données du modèle et les transfèrent vers les vues, ou reçoivent des données de Tomcat, les traitent et les transfèrent au modèle. La logique métier (c'est-à-dire ce qu'il faut faire ) doit y être décrite, et non dans le modèle ou dans la vue. Ainsi, chacun fait ce qu'il veut :
  • le modèle stocke les données
  • Les vues dessinent une belle représentation des données
  • les contrôleurs traitent les données
Cela leur permet d’être tous assez simples et maintenables. Et pas un vidage monstrueux de tout le code dans une seule classe. MVC n’est pas seulement adapté à la programmation web, mais il est encore très courant (sinon toujours) dans ce domaine. Dans notre cas, les servlets feront office de contrôleurs. Oui, c'est une description très superficielle et même approximative de ce modèle, mais cet article ne concerne pas les modèles de conception, mais comment créer une application Web simple :) Qui veut en savoir plus - Google sait tout ! :) Revenons à nos points de vue.
Créez un formulaire pour ajouter un utilisateur.
Ajoutons un formulaire au fichier add.jsp, composé de deux entrées de texte (une normale, l'autre de type mot de passe) et un bouton pour envoyer des données au serveur. Ici, le formulaire a un attribut de méthode avec la valeur post. Cela signifie que les données de ce formulaire seront envoyées au serveur sous la forme d'une requête POST. L'attribut action n'est pas spécifié, ce qui signifie que cette demande sera envoyée à la même adresse que celle à laquelle nous sommes allés sur cette page (/add). Ainsi, notre servlet, qui est liée à cette adresse, à réception d'une requête GET, renvoie cette jsp avec le formulaire d'ajout d'utilisateurs, et si elle reçoit une requête POST, alors ce formulaire y a envoyé ses données (que nous récupérerons de l'objet de requête dans la méthode doPost(), traitez-le et transférez-le vers le modèle pour l'enregistrer). Il est à noter que les entrées ont ici un paramètre name (pour un champ avec un nom, il a la valeur name, et pour un champ avec un mot de passe, il a la valeur pass). C'est un point assez important. Puisque pour obtenir ces données (nom et mot de passe qui seront saisis) à partir de la requête (déjà à l'intérieur du servlet), nous utiliserons exactement ces nom et passe. Mais plus là-dessus plus tard. Le bouton d'envoi des données lui-même se présente à nouveau sous la forme d'un bouton, et non d'une entrée, comme c'est généralement le cas. Je ne sais pas à quel point cette option est universelle, mais elle fonctionne pour moi dans Chrome :)
Traitement d'une requête POST avec un servlet.
Revenons à la servlet AddServlet. Nous savons déjà que pour que notre servlet puisse « capter » les requêtes GET, nous avons remplacé la méthode doGet() de la classe HttpServlet. Pour apprendre à notre servlet à intercepter également les requêtes POST, nous remplaçons également la méthode doPost(). Il reçoit des objets de requête et de réponse similaires de Tomcat, avec lesquels nous travaillerons. Tout d’abord, extrayons de la requête le nom et transmettons les paramètres envoyés par le formulaire (si vous les avez nommés différemment dans le formulaire, alors ce sont les noms que vous écrivez). Ensuite, nous créerons notre objet utilisateur en utilisant les données reçues. Ensuite, nous obtiendrons l'objet modèle et ajouterons l'utilisateur créé au modèle. @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String name = req.getParameter("name"); String password = req.getParameter("pass"); User user = new User(name, password); Model model = Model.getInstance(); model.add(user); }
Transfert de données vers la vue.
Passons maintenant à la servlet ListServlet. Nous avons déjà implémenté la méthode doGet(), qui transfère simplement le contrôle à la vue list.jsp. Si vous ne l'avez pas encore, faites-le par analogie avec la même méthode du servlet AddServlet. Maintenant, ce serait bien d'obtenir une liste de noms d'utilisateur du modèle et de les transmettre à la vue, qui les recevra là et les affichera joliment. Pour ce faire, nous utiliserons à nouveau l'objet de requête que nous avons reçu de Tomcat. Nous pouvons ajouter un attribut à cet objet, en lui donnant un nom et, en fait, l'objet lui-même que nous aimerions transférer à la vue. Du fait que lors du transfert du processus d'exécution d'un servlet vers une vue, nous y passons les mêmes objets de requête et de réponse que le servlet lui-même a reçu, puis en ajoutant notre liste de noms à l'objet de requête, nous pouvons alors à partir de cette requête objet dans la vue, créez notre liste de noms d'utilisateurs et obtenez. Nous en avons terminé avec la classe ListServlet, voici donc le code de la classe entière. package app.servlets; import app.model.Model; import javax.servlet.RequestDispatcher; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; import java.util.List; public class ListServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { Model model = Model.getInstance(); List names = model.list(); req.setAttribute("userNames", names); RequestDispatcher requestDispatcher = req.getRequestDispatcher("views/list.jsp"); requestDispatcher.forward(req, resp); } }
Exécution de code Java dans des fichiers jsp.
Passons maintenant au fichier list.jsp. Ce fichier ne sera exécuté que lorsque le ListServlet aura réussi le processus d'exécution ici. De plus, dans cette servlet, nous avons déjà préparé une liste de noms d'utilisateurs à partir du modèle et l'avons transmise ici dans l'objet de requête. Étant donné une liste de noms, nous pouvons y exécuter une boucle for et imprimer chaque nom. Comme je l'ai déjà dit, les fichiers jsp peuvent exécuter du code java (en principe, c'est ce qui les différencie des pages html statiques). Pour exécuter du code, il suffit de placer une construction à l'endroit dont nous avons besoin. <% // java code %> À l'intérieur d'une telle construction, nous avons accès à plusieurs variables : request - notre objet de requête, que nous avons passé depuis la servlet, où il était simplement appelé req réponse - l'objet de réponse, dans Le servlet s'appelait resp out - un objet de type JspWriter (hérité du Writer habituel), à l'aide duquel nous pouvons « écrire » quelque chose directement dans la page html elle-même. Out.println("Hello world!") est très similaire à System.out.println("Hello world!"), mais ne les confondez pas ! out.println() "écrit" sur la page HTML et System.out.println - sur la sortie système. Si vous appelez la méthode System.out.println() à l'intérieur de la section avec du code jsp, vous verrez les résultats dans la console Tomcat, et non sur la page, comme vous pourriez le souhaiter :) Vous pouvez rechercher d'autres objets disponibles dans jsp ici . En utilisant l'objet request, nous pouvons obtenir la liste des noms transmis par le servlet (nous avons attaché l'attribut correspondant à cet objet), et en utilisant l'objet out, nous pouvons afficher ces noms. Faisons cela pour l'instant simplement sous la forme d'une liste html : Si l'on souhaite afficher la liste uniquement lorsqu'il y a des utilisateurs, et sinon afficher un avertissement indiquant qu'il n'y a pas encore d'utilisateurs, on peut réécrire un peu cette section : Maintenant que nous savoir comment transférer des données des servlets vers les vues - nous pouvons améliorer un peu notre AddServlet afin qu'une notification s'affiche concernant l'ajout réussi d'un utilisateur. Pour ce faire, dans la méthode doPost(), après avoir ajouté un nouvel utilisateur au modèle, nous pouvons ajouter le nom de cet utilisateur aux attributs de l'objet req et rendre le contrôle à la vue add.jsp. Et créez déjà une section avec du code Java, où vous pouvez vérifier si un tel attribut est dans la demande, et si tel est le cas, afficher un message indiquant que l'utilisateur a été ajouté avec succès. Après ces modifications, le code complet de la servlet AddServlet ressemblera à ceci : Ici, à la fin de la méthode doPost(), nous définissons un attribut avec le nom de l'utilisateur ajouté au modèle, puis appelons la méthode doGet( ), à laquelle nous transmettons la requête et la réponse actuelles. Et la méthode doGet() transfère déjà le contrôle à la vue, où elle envoie un objet de requête avec le nom de l'utilisateur ajouté attaché comme attribut. Il reste à corriger add.jsp lui-même pour qu'il affiche une telle notification si un tel attribut est présent. Ajout final.jsp
    <% List names = (List ) request.getAttribute("userNames"); if (names != null && !names.isEmpty()) { for (String s : names) { out.println("
  • " + s + "
  • "); } } %>
<% List names = (List ) request.getAttribute("userNames"); if (names != null && !names.isEmpty()) { out.println(" "); for (String s : names) { out.println("
  • " + s + "
  • "); } out.println("
    "); } else out.println("

    There are no users yet!

    "); %>
    package app.servlets; import app.entities.User; import app.model.Model; import javax.servlet.RequestDispatcher; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; public class AddServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { RequestDispatcher requestDispatcher = req.getRequestDispatcher("views/add.jsp"); requestDispatcher.forward(req, resp); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String name = req.getParameter("name"); String password = req.getParameter("pass"); User user = new User(name, password); Model model = Model.getInstance(); model.add(user); req.setAttribute("userName", name); doGet(req, resp); } } <%@ page contentType="text/html;charset=UTF-8" language="java" %> Add new user

    Super app!

    <% if (request.getAttribute("userName") != null) { out.println("

    User '" + request.getAttribute("userName") + "' added!

    "); } %>

    Add user

    Le corps de la page se compose d'un div avec un en-tête, suivi d'un conteneur div pour le contenu, vérifiant si un attribut avec le nom d'utilisateur existe, puis d'un div avec un formulaire pour ajouter des utilisateurs, et à la fin d'un pied de page avec un bouton pour revenir à la page principale. Il peut sembler qu'il y a trop de divs, mais nous les utiliserons plus tard lorsque nous ajouterons des styles :) Eh bien, la version finale est list.jsp. Ainsi , nous avons une application Web entièrement fonctionnelle qui peut également stocker et ajouter des utilisateurs. comme afficher une liste de leurs noms. Il ne reste plus qu'à l'embellir... :) <%@ page import="java.util.List" %> <%@ page contentType="text/html;charset=UTF-8" language="java" %> Users

    Super app!

    Users

    <% List names = (List ) request.getAttribute("userNames"); if (names != null && !names.isEmpty()) { out.println(" "); for (String s : names) { out.println("
  • " + s + "
  • "); } out.println("
    "); } else out.println("

    There are no users yet!

    "); %>
    Ajout de styles. Nous utilisons le framework W3.CSS.
    Pour le moment, notre application fonctionne, mais absolument folle :) Nous devons ajouter un arrière-plan, des couleurs pour le texte et les boutons, styliser les listes, faire l'alignement, ajouter des retraits, en général beaucoup de choses. Si vous écrivez des styles manuellement, cela peut prendre beaucoup de temps et de nerfs. Par conséquent, je suggère d'utiliser le framework CSS W3.CSS . Il dispose déjà de classes prêtes à l'emploi avec des styles ; il ne reste plus qu'à placer aux bons endroits les classes CSS que l'on souhaite appliquer à ces endroits. Afin de les ajouter à nos pages, nous devons d’abord inclure un fichier avec des styles. Cela peut être fait de deux manières : 1. parcourez nos pages et dans la section d'en-tête insérez un lien direct vers le fichier avec les styles. Cette option convient si vous disposez d'une connexion Internet constante. Ensuite, lorsque vous ouvrirez vos pages sur un serveur local, les styles seront extraits d’Internet. 2. Si vous souhaitez avoir tous les styles localement et ne pas dépendre d'une connexion Internet, vous pouvez simplement télécharger le fichier avec les styles et le placer quelque part dans le dossier Web (par exemple web/styles/w3.css), puis parcourez toutes nos pages (index.html, add.jsp, list.jsp) et entrez un lien vers ce fichier avec les styles dans la section d'en-tête. Après cela, parcourez simplement les balises et étiquetez-les avec les styles que vous aimez . Je ne m'étendrai pas là-dessus en détail, mais donnerai immédiatement mes versions toutes faites de mes trois fichiers avec des classes de style arrangées. index.html add.jsp list.jsp C'est tout :) Si vous avez encore des questions ou des commentaires, ou au contraire, quelque chose ne fonctionne pas, laissez un commentaire. Eh bien, je vais joindre quelques captures d’écran de ce qui en est ressorti. Et enfin. Si vous souhaitez vous entraîner avec ce projet, vous pouvez essayer : Super app!

    Super app!

    <%@ page contentType="text/html;charset=UTF-8" language="java" %> Add new user

    Super app!

    <% if (request.getAttribute("userName") != null) { out.println("
    \n" + " ×\n" + "
    User '" + request.getAttribute("userName") + "' added!
    \n" + "
    "); } %>

    Add user

    <%@ page import="java.util.List" %> <%@ page contentType="text/html;charset=UTF-8" language="java" %> Users list

    Super app!

    Users

    <% List names = (List ) request.getAttribute("userNames"); if (names != null && !names.isEmpty()) { out.println("
      "); for (String s : names) { out.println("
    • " + s + "
    • "); } out.println("
    "); } else out.println("
    \n" + " ×\n" + "
    There are no users yet!
    \n" + "
    "); %>
    Page d'accueil de l'application Ajouter une fenêtre utilisateur une liste d'utilisateurs
    • créez un servlet et un jsp pour supprimer un utilisateur et quelques autres pour modifier/modifier un utilisateur existant. Vous obtiendrez une véritable application web CrUD :) sur les servlets))
    • remplacer la liste (Liste ) pour travailler avec la base de données afin que les utilisateurs ajoutés ne disparaissent pas après le redémarrage du serveur :)
    Bonne chance!
    Commentaires
    TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
    GO TO FULL VERSION