7. برنامه وب MVC [personne] – نسخه ۳
مطالعهٔ پیشنهادی در [ref1]: فصل ۹
7.1. Introduction
ما پیشنهاد میکنیم کد جاوااسکریپت را به صفحات HTML که به مرورگر ارسال میشوند اضافه کنیم. این مرورگر است که کد جاوااسکریپت جاسازیشده در صفحهای را که نمایش میدهد اجرا میکند. این فناوری مستقل از فناوری مورد استفاده توسط سرور وب برای تولید سند HTML است (جاوا/سرولیتها/JSP، ASP.NET, ASP, PHP, Perl, Python و غیره).
[formulaire.jsp]
نمای تولیدشده از این صفحه به شرح زیر خواهد بود:

دکمههایی که دارای متن برچسبگذاری شده هستند از کد جاوااسکریپت جاسازیشده در صفحه HTML استفاده میکنند:
برچسب | نوع HTML | تابع |
<submit> | همان عملکردی را که دکمه [Envoyer] در نسخههای قبلی داشت، انجام میدهد: مقادیر وارد شده را به کنترلر ارسال میکند | |
<button> | دکمه جدید – اعتبار دادههای وارد شده را بهصورت محلی قبل از ارسال به کنترلر بررسی میکند | |
<reset> | فرم را به حالتی بازمیگرداند که در ابتدا توسط مرورگر دریافت شده بود | |
<button> | محتویات هر دو فیلد ورودی را پاک میکند |
در اینجا مثالی از نحوه استفاده از دکمههای [Envoyer] و [Effacer] آورده شده است:
![]() | ![]() |
![]() | ![]() |
ما همچنین از کد جاوااسکریپت برای مدیریت لینک [Retour au formulaire] برای ویو [erreurs] و [réponse] استفاده خواهیم کرد. بیایید ویو [réponse] را بهعنوان مثال در نظر بگیریم:
![]() | 1 ![]() |
تفاوت در URL نمایشدادهشده در [1] است. در نسخه قبلی، این بود:
در اینجا، اقدام دیگر بخشی از URL نیست، زیرا به جای GET، از طریق POST ارسال خواهد شد. این تغییر به این معناست که تنها URL نمایش داده شده توسط مرورگر [http://localhost:8080/personne3/main] خواهد بود، صرفنظر از اقدام درخواستی.
7.2. پروژه اکلیپس
برای ایجاد پروژه Eclipse [mvc-personne-03] برای برنامه وب [/personne3]، پروژه [mvc-personne-02] را با دنبال کردن رویهای که در بخش 6.2، صفحه 78 توضیح داده شده است، کپی کنید.
![]() | ![]() |
7.3. پیکربندی برنامه وب [personne3]
فایل web.xml برای اپلیکیشن /personne3 به شرح زیر است:
<?xml version="1.0" encoding="UTF-8"?>
<web-app id="WebApp_ID" version="2.4"
xmlns="http://java.sun.com/xml/ns/j2ee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
<display-name>mvc-personne-03</display-name>
<!-- ServletPersonne -->
<servlet>
<servlet-name>personne</servlet-name>
<servlet-class>
istia.st.servlets.personne.ServletPersonne
</servlet-class>
<init-param>
<param-name>urlReponse</param-name>
<param-value>
/WEB-INF/vues/reponse.jsp
</param-value>
</init-param>
<init-param>
<param-name>urlErreurs</param-name>
<param-value>
/WEB-INF/vues/erreurs.jsp
</param-value>
</init-param>
<init-param>
<param-name>urlFormulaire</param-name>
<param-value>
/WEB-INF/vues/formulaire.jsp
</param-value>
</init-param>
<init-param>
<param-name>lienRetourFormulaire</param-name>
<param-value>
Retour au formulaire
</param-value>
</init-param>
</servlet>
<!-- نگاشت ServletPersonne-->
<servlet-mapping>
<servlet-name>personne</servlet-name>
<url-pattern>/main</url-pattern>
</servlet-mapping>
<!-- فایلهای خانگی -->
<welcome-file-list>
<welcome-file>index.jsp</welcome-file>
</welcome-file-list>
</web-app>
این فایل به جز چند جزئیات با نسخه قبلی یکسان است:
- خط ۶: نام نمایشی برنامه وب به [mvc-personne-03] تغییر یافته است
پارامتر [urlControleur] حذف شده است. در نسخه قبلی، از آن برای تعیین هدف POST برای نما [formulaire] استفاده میشد. در این نسخه جدید، هدف، رشته خالی، c.a.d خواهد بود. آدرس URL نمایشدادهشده توسط مرورگر. ما توضیح دادهایم که این همیشه [http://localhost:8080/personne3/main] خواهد بود، که همان چیزی است که برای POST در نمای [formulaire] نیاز داریم.
صفحه اصلی [index.jsp] به این صورت تغییر میکند:
<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<%
response.sendRedirect("/personne3/main");
%>
- خط ۵: صفحه [index.jsp] مشتری را به نشانی URL کنترلکننده [ServletPersonne] در برنامه [/personne3] هدایت میکند.
7.4. کد نما
7.4.1. ویوی [formulaire]
این نما اکنون به این صورت درآمده است:

این توسط صفحه زیر تولید میشود: JSP [formulaire.jsp]:
<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<%//دادهها از قالب بازیابی میشوند
String nom = (String) session.getAttribute("nom");
String age = (String) session.getAttribute("age");
%>
<html>
<head>
<title>Personne - formulaire</title>
<script language="javascript">
// -------------------------------
function effacer(){
// پاک کردن فیلدهای ورودی
with(document.frmPersonne){
txtNom.value="";
txtAge.value="";
}//با
}//پاک کردن
// -------------------------------
function envoyer(){
//بررسی پارامترها قبل از ارسال آنها
with(document.frmPersonne){
//نام نباید خالی باشد
champs=/^\s*$/.exec(txtNom.value);
if(champs!=null){
// نام خالی است
alert("Vous devez indiquer un nom");
txtNom.value="";
txtNom.focus();
//بازگشت به رابط کاربری گرافیکی
return;
}//اگر
//سن باید یک عدد صحیح مثبت باشد
champs=/^\s*\d+\s*$/.exec(txtAge.value);
if(champs==null){
// سن نادرست است
alert("Age incorrect");
txtAge.focus();
//بازگشت به رابط کاربری بصری
return;
}//اگر
//پارامترها صحیح هستند – آنها را به سرور ارسال کنید
submit();
}//با
}//ارسال
</script>
</head>
<body>
<center>
<h2>Personne - formulaire</h2>
<hr>
<form name="frmPersonne" method="post">
<table>
<tr>
<td>Nom</td>
<td><input name="txtNom" value="<%= nom %>" type="text" size="20"></td>
</tr>
<tr>
<td>Age</td>
<td><input name="txtAge" value="<%= age %>" type="text" size="3"></td>
</tr>
<tr>
</table>
<table>
<tr>
<td><input type="submit" value="Submit"></td>
<td><input type="button" value="[Envoyer]" onclick="envoyer()"></td>
<td><input type="reset" value="Rétablir"></td>
<td><input type="button" value="[Effacer]" onclick="effacer()"></td>
</tr>
</table>
<input type="hidden" name="action" value="validationFormulaire">
</form>
</center>
</body>
</html>
چه چیز جدیدی وجود دارد:
- خط ۵۶: فرم دارای نام [frmPersonne] است. این نام در کد جاوااسکریپت استفاده خواهد شد. به عدم وجود ویژگی [action] توجه کنید، که به این معنی است که فرم [frmPersonne] به URL نمایشدادهشده توسط مرورگر ارسال خواهد شد.
- خط ۷۰: دکمه [Submit] جایگزین دکمه [Envoyer] در نسخههای قبلی است.
- خط ۷۱: کلیک روی دکمه [Envoyer] (از نوع [Button]) تابع جاوااسکریپت [envoyer] را که در خط ۲۴ تعریف شده است اجرا میکند
- خط ۷۲: دکمه [Rétablir] عملکرد خود را تغییر نداده است
- خط ۷۳: کلیک روی دکمه [Effacer] (از نوع [Button]) تابع جاوااسکریپت [effacer] را که در خط ۱۶ تعریف شده است اجرا میکند
قبل از بررسی کد جاوااسکریپت، بیایید چند کنوانسیون را به یاد بیاوریم:
جاوااسکریپت صفحهٔ نمایشدادهشده و محتوای آن را بهعنوان درختی از اشیاء مدیریت میکند که ریشهٔ آن شیء [document] است. این سند ممکن است حاوی یک یا چند فرم باشد. [document.frmPersonne] به فرم با نام [frmPersonne] اشاره دارد که در خط 56 تعریف شده است. این فرم نیز حاوی اشیاء است. میدانهای ورودی بخشی از این هستند. بنابراین، [document.frmPersonne.txtNom] به شیء تصویرِ میدان ورودی HTML که در خط 60 تعریف شده است، اشاره میکند. شیء [txtNom] دارای خواص مختلفی است، از جمله خاصیت [value] که به محتوای فیلد ورودی اشاره دارد. بنابراین، [document.frmPersonne.txtNom.value] به محتوای فیلد ورودی [txtNom] اشاره دارد.
- خطوط ۱۶–۲۲: تابع جاوااسکریپت [effacer] یک رشتهٔ خالی را در فیلدهای ورودی [txtNom, txtAge] قرار میدهد.
- خطوط ۲۴–۴۹: تابع جاوااسکریپت [envoyer] اعتبار مقادیر موجود در فیلدهای ورودی [txtNom, txtAge] را قبل از ارسال آنها بررسی میکند. این تابع برای این منظور از عبارات باقاعده (regular expressions) استفاده میکند.
- خط ۲۸: بررسی میکند که آیا مقدار فیلد ورودی [txtNom] با الگوی /s* مطابقت دارد که به معنای صفر یا چند فضای خالی است. اگر پاسخ مثبت باشد، این بدان معناست که کاربر نامی وارد نکرده است. اگر تطابقی با الگو وجود داشته باشد، متغیر champs مقداری غیر از اشارهگر null خواهد داشت؛ در غیر این صورت، مقدار آن null خواهد بود.
- خط ۲۹: اگر تطابقی با قالب وجود داشته باشد
- خط ۳۰: پیامی به کاربر نمایش داده میشود
- خط ۳۲: رشته خالی در فیلد [txtNom] قرار میگیرد (ممکن است یک دنباله از فاصله باشد)
- خط ۳۳: مکاننما چشمکزن روی فیلد [txtNom] قرار میگیرد
- خط ۳۴: عملکرد متوقف میشود. بنابراین سرور هیچ دادهای از POST برای مقادیر وارد شده دریافت نمیکند.
- خطوط ۳۸–۴۵: فرآیندی مشابه برای فیلد [txtAge] دنبال میشود.
- خط ۴۷: اگر به این نقطه برسیم، یعنی مقادیر وارد شده صحیح هستند. سپس فرم [frmPersonne] را به وب سرور ارسال میکنیم. در این صورت، همه چیز دقیقاً مانند حالتی پیش میرود که ما دکمه با برچسب [Submit] را کلیک کرده باشیم.
7.4.2. نما [reponse]
این نما مقادیر وارد شده در فرم را نمایش میدهد، مشروط بر اینکه معتبر باشند:
![]() | ![]() |
در مقایسه با نسخه قبلی، ویژگی جدید تنها زمانی ظاهر میشود که از لینک [Retour au formulaire] در نمای [réponse] استفاده کنید:
![]() | ![]() |
تفاوت در URL نمایشدادهشده در [1] است. در نسخه قبلی، این بود:
در اینجا، اقدام دیگر بخشی از URL نیست، زیرا به جای GET، از طریق POST ارسال خواهد شد. صفحه جدید JSP [reponse.jsp] است lqqqaaaaaaaaaqqAAAaaa
به شرح زیر:
<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<%
//دادهها از مدل بازیابی میشوند
String nom=(String)request.getAttribute("nom");
String age=(String)request.getAttribute("age");
String lienRetourFormulaire=(String)request.getAttribute("lienRetourFormulaire");
%>
<html>
<head>
<title>Personne</title>
</head>
<body>
<h2>Personne - réponse</h2>
<hr>
<table>
<tr>
<td>Nom</td>
<td><%= nom %>
</tr>
<tr>
<td>Age</td>
<td><%= age %>
</tr>
</table>
<br>
<form name="frmPersonne" method="post">
<input type="hidden" name="action" value="retourFormulaire">
</form>
<a href="javascript:document.frmPersonne.submit();">
<%= lienRetourFormulaire %>
</a>
</body>
</html>
چه چیز جدیدی وجود دارد:
- خطوط ۳۵–۳۷: لینک [Retour au formulaire] حاوی جاوااسکریپت است. کلیک روی این لینک باعث اجرای کد جاوااسکریپت در ویژگی [href] میشود. همانطور که در تحلیل [formulaire.jsp] دیدیم، میدانیم که این کد مقادیر فیلدهای <input>، <select> و سایر فیلدها را در فرم [frmPersonne] ارسال میکند.
- خطوط ۳۲–۳۴: فرم [frmPersonne] را تعریف میکنند. این فرم تنها یک فیلد از نوع <input type="hidden" ...> دارد، یعنی یک فیلد مخفی. این فیلد، [action]، برای ارسال نام عملی که باید اجرا شود – در این مورد، [retourFormulaire] – به کنترلر استفاده میشود.
7.4.3. نما [erreurs]
این نما هرگونه خطای ورودی در فرم را نشان میدهد. تغییری که اعمال شده همانند نمای [réponse] است:
![]() | ![]() |
تفاوت در URL نمایشدادهشده در [1] است. در نسخه قبلی، این بود:
در اینجا، اقدام دیگر جزئی از URL نیست، زیرا به جای GET از طریق POST ارسال خواهد شد. صفحه جدید JSP [reponse.jsp] به شرح زیر است:
<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<%@ page import="java.util.ArrayList" %>
<%
// استخراج دادهها از مدل
ArrayList erreurs=(ArrayList)request.getAttribute("erreurs");
String lienRetourFormulaire=(String)request.getAttribute("lienRetourFormulaire");
%>
<html>
<head>
<title>Personne</title>
</head>
<body>
<h2>Les erreurs suivantes se sont produites</h2>
<ul>
<%
for(int i=0;i<erreurs.size();i++){
out.println("<li>" + (String) erreurs.get(i) + "</li>\n");
}//برای
%>
</ul>
<br>
<form name="frmPersonne" method="post">
<input type="hidden" name="action" value="retourFormulaire">
</form>
<a href="javascript:document.frmPersonne.submit();">
<%= lienRetourFormulaire %>
</a>
</body>
</html>
ویژگیهای جدید:
- خطوط ۳۰–۳۲: نحوهٔ جدید رسیدگی به کلیکهای لینک. توضیحات ارائهشده در مورد این موضوع در تحلیل [réponse.jsp] نیز در اینجا صدق میکند.
7.5. آزمون نما
برای آزمایش نماهای قبلی، صفحات آنها JSP را در پوشه /WebContent/JSP پروژه Eclipse کپی میکنیم:

سپس، در پوشه JSP، صفحات به شرح زیر اصلاح میشوند:
[formulaire.jsp]:
...
<%
//-- تست: ایجاد قالب صفحه
session.setAttribute("nom","tintin");
session.setAttribute("age","30");
%>
<%//دادهها را از قالب بازیابی میکند
String nom = (String) session.getAttribute("nom");
String age = (String) session.getAttribute("age");
%>
خطوط ۴–۵ برای ایجاد قالب مورد نیاز صفحه در خطوط ۹–۱۰ اضافه شدهاند.
[reponse.jsp]:
...
<%
//-- تست: ایجاد قالب صفحه
request.setAttribute("nom","milou");
request.setAttribute("age","10");
request.setAttribute("lienRetourFormulaire","Retour au formulaire");
%>
<%
//بازیابی دادهها از قالب
String nom=(String)request.getAttribute("nom");
String age=(String)request.getAttribute("age");
String lienRetourFormulaire=(String)request.getAttribute("lienRetourFormulaire");
%>
...
خطوط ۴–۶ برای ایجاد قالب مورد نیاز صفحه در خطوط ۱۱–۱۳ اضافه شدهاند.
[erreurs.jsp]:
<%
//-- تست: ایجاد قالب صفحه
ArrayList<String> erreurs1=new ArrayList<String>();
erreurs1.add("erreur1");
erreurs1.add("erreur2");
request.setAttribute("erreurs",erreurs1);
request.setAttribute("lienRetourFormulaire","Retour au formulaire");
%>
<%
//بازیابی دادهها از قالب
ArrayList erreurs=(ArrayList)request.getAttribute("erreurs");
String lienRetourFormulaire=(String)request.getAttribute("lienRetourFormulaire");
%>
خطوط ۴–۸ برای ایجاد قالب مورد نیاز صفحه در خطوط ۱۳–۱۴ اضافه شدهاند.
اگر هنوز تامکت را راهاندازی نکردهاید، آن را راهاندازی کنید، سپس آدرسهای URL زیر را درخواست کنید:
![]() | ![]() |
![]() |
ما واقعاً در حال دریافت دیدگاههای مورد انتظار هستیم.
7.6. کنترلر [ServletPersonne]
کنترلر [ServletPersonne] برای برنامه وب [/personne3] اقدامات زیر را مدیریت خواهد کرد:
خیر. | درخواست | مبدأ | در حال پردازش |
۱ | [GET /personne3/main] | URL وارد شده توسط کاربر | - ارسال نمای خالی [formulaire] |
2 | [POST /personne3/main] با پارامترها [txtNom, txtAge, action=validationFormulaire] ارسال شد | کلیک کردن دکمه [Envoyer] در نما [formulaire] | - مقادیر پارامتر را بررسی کنید [txtNom, txtAge] - اگر نادرست باشند، نما [erreurs(erreurs)] را ارسال کنید - اگر صحیح هستند، نما [reponse(nom,age)] را ارسال کنید |
3 | [POST /personne3/main] با پارامترها [action=retourFormulaire] حذف شد | روی [بازگشت به کلیک کنید فرم] در نماها [réponse] و [erreurs]. | - ارسال نمای از پیش پرشده [formulaire] با آخرین مقادیر واردشده |
بنابراین ما یک اکشن جدید برای رسیدگی داریم: [POST /personne3/main] با پارامتر ارسالشده [action=retourFormulaire]، که جایگزین اکشن قدیمی [GET /personne3/main?action=retourFormulaire] میشود.
7.6.1. اسکلت کنترلکننده
اسکلت کنترلر برای [ServletPersonne] با نسخه قبلی یکسان است.
ویژگیهای جدید:
- خط ۱۱: آرایه [paramètres] دیگر شامل پارامتر [urlControleur] نیست، که از فایل [web.xml] حذف شده است.
روشهای [init, doValidationFormulaire] بدون تغییر باقی ماندهاند. روشهای [doGet, doInit, doRetourFormulaire] کمی تغییر کردهاند.
7.6.2. متد [doGet]
روش [doGet] باید اقدام [POST /personne3/main] را با پارامتر ارسالشده [action=retourFormulaire] پردازش کند:
- خطوط ۶–۹: پردازش اقدام [POST /personne3/main] با پارامتر ارسالشده [action=retourFormulaire]
7.6.3. روش [doInit]
این متد درخواست شماره ۱، [GET /personne3/main] را پردازش میکند. کد آن به شرح زیر است:
تغییر این است که ویو [formulaire] که در خط ۸ نمایش داده شده، دیگر عنصر [action] را در قالب خود ندارد.
7.6.4. متد [doRetourFormulaire]
این متد درخواست شماره 1، [POST /personne3/main]، را با [action=retourFormulaire] در عناصر ارسالشده پردازش میکند. کد آن به شرح زیر است:
تغییر این است که نمای [formulaire] که در خط 14 نمایش داده میشود، دیگر عنصر [action] را در قالب خود ندارد.
7.7. Tests
پس از ادغام پروژه Eclipse [personne-mvc-03]، Tomcat را راهاندازی یا مجدداً راهاندازی کنید. URL [http://localhost:8080/personne3] را درخواست کرده، سپس آزمونهای نشاندادهشده بهعنوان مثال در بخش 7.1 را تکرار کنید.















