Skip to content

7. تطبيق example-04: rdvmedecins-pf-spring

7.1. النقل

نقوم الآن بنقل التطبيق السابق إلى بيئة Spring / Tomcat:

سنعتمد على تطبيقين تمت كتابتهما مسبقًا. سنستخدم:

  • الطبقات [DAO] و [JPA] من الإصدار 02 JSF / Spring،
  • الطبقة [web] / Primefaces من الإصدار 03 PF / EJB،
  • ملفات تكوين Spring من الإصدار 02

نقوم هنا بعمل مشابه لما تم القيام به لنقل التطبيق JSF2 / EJB / Glassfish إلى بيئة JSF2 / Spring Tomcat. ولذلك سنقدم شرحًا أقل. يمكن للقارئ، إذا لزم الأمر، الرجوع إلى هذا النقل.

نضع جميع المشاريع اللازمة لعملية النقل في مجلد جديد [rdvmedecins-pf-spring] [1]:

  • [mv-rdvmedecins-spring-dao-jpa]: الطبقات [DAO] و [JPA] من الإصدار 02 JSF / Spring،
  • [mv-rdvmedecins-spring-metier]: الطبقة [métier] من الإصدار 02 JSF / Spring،
  • [mv-rdvmedecins-pf]: الطبقة [web] من الإصدار 03 Primefaces / EJB،
  • في [2]، نقوم بتحميلها في Netbeans،
  • في [3]، لم تعد تبعيات مشروع الويب صحيحة:
    • يجب تغيير التبعيات على الطبقات [DAO] و [JPA] و [métier] لتستهدف الآن مشاريع Spring؛
    • كان خادم Glassfish يوفر مكتبات JSF. لم يعد هذا هو الحال مع خادم Tomcat. لذا يجب إضافتها إلى التبعيات.

يتطور مشروع [web] على النحو التالي:

يحتوي الملف [pom.xml] من الطبقة [web] الآن على التبعيات التالية:


<dependencies>    
    <dependency>
      <groupId>${project.groupId}</groupId>
      <artifactId>mv-rdvmedecins-spring-metier</artifactId>
      <version>${project.version}</version>
    </dependency>
    <dependency>
      <groupId>com.sun.faces</groupId>
      <artifactId>jsf-api</artifactId>
      <version>2.1.7</version>
    </dependency>
    <dependency>
      <groupId>com.sun.faces</groupId>
      <artifactId>jsf-impl</artifactId>
      <version>2.1.7</version>
    </dependency>
    <dependency>  
      <groupId>org.primefaces</groupId>  
      <artifactId>primefaces</artifactId>  
      <version>3.3</version>  
    </dependency>
  </dependencies>

تظهر أخطاء. وهي ناتجة عن المراجع EJB للطبقة [web]. لندرس أولاً الفول [Application]:

نقوم بإزالة جميع الأسطر الخاطئة بسبب الحزم المفقودة، ونقوم بإعادة تسمية [IMetier] (وهذا هو اسمها في طبقة Spring [métier]) إلى واجهة [IMetierLocal] ونستخدم Spring لإنشاء مثيل لها:


package beans;

import java.util.ArrayList;
import java.util.List;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import rdvmedecins.metier.service.IMetier;

public class Application {

  // طبقة الأعمال
  private IMetier metier;
  // الأخطاء
  private List<Erreur> erreurs = new ArrayList<Erreur>();
  private Boolean erreur = false;

  public Application() {
    try {
      // إنشاء مثيل الطبقة [métier]
      ApplicationContext ctx = new ClassPathXmlApplicationContext("spring-config-metier-dao.xml");
      metier = (IMetier) ctx.getBean("metier");
    } catch (Throwable th) {
      // يتم تسجيل الخطأ
      erreur = true;
      erreurs.add(new Erreur(th.getClass().getName(), th.getMessage()));
      while (th.getCause() != null) {
        th = th.getCause();
        erreurs.add(new Erreur(th.getClass().getName(), th.getMessage()));
      }
      return;
    }
  }

  // مُستردات
  public Boolean getErreur() {
    return erreur;
  }

  public List<Erreur> getErreurs() {
    return erreurs;
  }

  public IMetier getMetier() {
    return metier;
  }
}
  • السطران 20-21: إنشاء مثيل للطبقة [métier] من ملف تكوين Spring. هذا الملف هو الملف المستخدم من قبل الطبقة [métier] [1]. نقوم بنسخه إلى مشروع الويب [2]:
  • الأسطر 22-31: ندير أي استثناء محتمل ونحفظ مكدسه.

وبذلك، لم يعد هناك أخطاء في bean [Application]. لننظر الآن إلى bean [Form] [1]، [2]:

نقوم بحذف جميع الأسطر الخاطئة (الاستيراد والتعليقات التوضيحية) بسبب الحزم المفقودة. وهذا يكفي لإزالة جميع أخطاء [3].

بالإضافة إلى ذلك، يجب إضافة getter و setter للحقل


  // فئة التطبيق
private Application application;

كانت بعض التعليقات التوضيحية التي تم حذفها في البينات [Application] و [Form] تعلن أن الفئات هي بينات ذات نطاق معين. الآن، يتم إجراء هذا التكوين في الملف [faces-config.xml] [4] التالي:


<?xml version='1.0' encoding='UTF-8'?>

<!-- =========== FULL CONFIGURATION FILE ================================== -->

<faces-config version="2.0"
              xmlns="http://java.sun.com/xml/ns/javaee" 
              xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
              xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facesconfig_2_0.xsd">

  <application>
    <!-- ملف الرسائل -->
    <resource-bundle>
      <base-name>
        messages
      </base-name>
      <var>msg</var>
    </resource-bundle>
    <message-bundle>messages</message-bundle>
  </application>
    <!-- البيان applicationBean -->
  <managed-bean>
    <managed-bean-name>applicationBean</managed-bean-name>
    <managed-bean-class>beans.Application</managed-bean-class>
    <managed-bean-scope>application</managed-bean-scope>
  </managed-bean>
    <!-- نموذج bean -->
  <managed-bean>
    <managed-bean-name>form</managed-bean-name>
    <managed-bean-class>beans.Form</managed-bean-class>
    <managed-bean-scope>session</managed-bean-scope>
    <managed-property>
      <property-name>application</property-name>
      <value>#{applicationBean}</value>
    </managed-property>
  </managed-bean>
</faces-config>

عادةً ما يكون النقل قد اكتمل. ومع ذلك، لا يزال هناك بعض التفاصيل التي يتعين علينا تسويتها. يمكننا محاولة تشغيل تطبيق الويب.

نترك للقارئ مهمة اختبار هذا التطبيق الجديد. يمكننا تحسينه قليلاً للتعامل مع الحالة التي تفشل فيها تهيئة bean [Application]. نعلم أنه في هذه الحالة، تمت تهيئة الحقول التالية:


  // الأخطاء
  private List<Erreur> erreurs = new ArrayList<Erreur>();
private Boolean erreur = false;

يمكن توقع هذه الحالة في الطريقة init للـ bean [Form]:


@PostConstruct
  private void init() {

    // هل تمت عملية التهيئة بنجاح؟
    if (application.getErreur()) {
      // استرداد قائمة الأخطاء
      erreurs = application.getErreurs();
      // يتم عرض قائمة الأخطاء
      setForms(false, false, true);
    }

    // يتم تخزين الأطباء والعملاء في ذاكرة التخزين المؤقت
    ...
  }
  • السطر 5: إذا تم تهيئة bean [Application] بشكل خاطئ،
  • السطر 7: يتم استرداد قائمة الأخطاء،
  • السطر 9: ونعرض صفحة الخطأ.

وبالتالي، إذا أوقفنا SGBD MySQL وأعدنا تشغيل التطبيق، فسنحصل الآن على الصفحة التالية:

Image

7.2. الخلاصة

تبين أن نقل تطبيق Primefaces / EJB / Glassfish إلى بيئة Primefaces / Spring / Tomcat كان أمرًا بسيطًا. لا تزال مشكلة تسرب الذاكرة التي تم الإبلاغ عنها في دراسة تطبيق JSF / Spring / Tomcat (الفقرة 4.3.5) قائمة.

وسيتم حلها بالطريقة نفسها.

7.3. اختبارات باستخدام Eclipse

نقوم باستيراد مشاريع Maven إلى Eclipse [1]:

نقوم بتشغيل مشروع الويب [2].

نختار خادم Tomcat [3]. وعندئذٍ تُعرض الصفحة الرئيسية للتطبيق في متصفح Eclipse الداخلي [4].