15 April 2017

Tổng quan về Struts 2 Framework

Tổng quan về Struts 2 Framework
Mục đích: Chủ đề của bài này đề cập đến khái niệm tổng quát của Struts 2.x Framework. Chúng tôi sẽ tiếp cận tổng quát khái niệm từng thành phần của Struts dựa trên tổng quát mô hình MVC Pattern và nền tảng căn bản của Struts1 Framework để chúng ta tiếp cận Framework này một cách nhanh chóng dự trên kiến thức cơ bản mà chúng ta đã có về Struts 1. Dựa trên khái niệm này, chúng ta sẽ áp dụng Struts 2 Framework này trong phần phân tích và thiết kế ứng dụng web cụ thể để thấy rõ cách thức thiết kế, cách cài đặt ứng dụng cụ thể sử dụng Struts 2 trong việc xây dựng ứng dụng Web
Tổng quan về Struts 2 Framework
  • Đây là Framework hỗ trợ thiết kế và xây dựng ứng dụng web theo mô hình MVC 2 thông qua việc cung cấp hàng loạt các thư viện và tiện ích để hỗ trợ người dùng phát triên ứng dụng Web theo mô hình MVC một cách nhanh chóng và dễ dàng
  • Struts 2 Framework hỗ trợ việc xây dựng ứng dụng Web theo mô hình MVC2 nhưng đơn giản hóa hơn mô hình Struts 1 Framework như là rút gọn tập tin cấu hình hay sử dụng annotation thay thế cho tập tin cấu hình
  • Một số đặc tính cải tiến của Strut2 Framework
    • JavaBeans được sử dụng thay thế Action form và có phương thức chỉ định để kích hoạt thực thi (mặc định là phương thức execute không có tham số truyền và kiểu trả về là kiểu String) nhằm tăng khả năng tái sử dụng của các object trong các ứng dụng và các framework khác. Đặc biệt, chúng dễ dàng thuật tiện cho testing từng thành phần chức năng và thành phần
    • Sử dụng cả annotation và tập tin cấu hình XML rút gọn
    • Sử dụng ngôn ngữ mới Object Graphic Notation Language (OGNL) thay thế cho EL của JSP
    • Sử dụng bộ taglib duy nhất thay cho 4-5 bộ taglib trong Struts 1 Framework và JSTL 1.1 trong JSP
  • Để nhanh chóng tiếp cận Struts2 chúng ta sẽ so sánh điểm khác biệt trên Struts1
Struts 1
Struts 2
Sử dụng ActionServlet làm Controller
Sử dụng FilterDispatcher làm Controller
Dùng HTML form kết hợp với ActionFormobject để đón nhận giá trị nhập và xử lý validation nếu cần
Các thuộc tính trong Action class (cụ thể là Java class) để đón nhận giá trị nhập từ form và thực hiện xử lý cùng với validation nếu cần
Action bắt buộc implement Action interface
Action class không cần bắt buộc implement Action interface
Duy nhất một instance của Action đón nhận để xử lý mọi request. Cơ chế để đảm bảo xử lý đồng bộ (thread-safe) đòi hỏi phức tạp hơn
Một request sẽ có một instance đón nhận xử lý
Cung cấp rất nhiều taglib gây khó khăn cho người dung khi tiếp cận và sử dụng
Cung cấp duy nhất một taglib duy nhất đảm bảo đầy đủ các thành phần hỗ trợ xử lý từ đơn giản đến nâng cao, kể cả JSTL
Sử dụng EL và JSTL
Sử OGNL để xử lý
Dùng cơ chế biên dịch của JSP để kết nối các thành phần trong xử lý
Sử dụng ValueStack để cho phép taglib truy vập giá trị trong quá trình xử lý
Chia thành module để chuyển đổi thao tác và đòi hỏi kết hợp của switchAction để tạo sự kết hợp giữa các thành phần khi làm việc theo nhóm
Sử dụng cơ chế interceptor để đảm bảo tích hợp nhiều thành phần và nâng cấp ứng dụng một cách uyển chuyển linh hoạt, đặc biệt là tích hợp mà không làm ảnh hưởng các thành phần có sẵn khi làm việc theo nhóm
  • Cơ chế hoạt động tương tự như mô hình MVC của Struts1 Framework nhưng điểm khác biệt nó là pull-framework nghĩa là dữ liệu được lấy trực tiếp từ action để đưa đến view
    • Controller: FilterDispatcher là servlet Filter có nhiệm vụ đón nhận request và dựa trên cấu hình (có thể là xml hay annotation) để xác định action cụ thể để đón nhận request cho xử lý
    • Model: Action là một java class đảm bảo đặc tính của một object trong mô hình hướng đối tượng và thỏa tính chất của JavaBean
    • View: Result là một kết xuất hay một dạng xác định action hay trang chuyển về và trình bày trên Web Browser
  • Cơ chế hoạt động của Struts 2 Framework

    • Khi user gửi yêu cầu truy xuất ứng dụng web, request được chuyển đến FilterDispatcher, đây là Filter được tạo sẵn trong Framework để làm chức năng như Controller
    • FilterDispatcher dựa trên tập tin cấu hình xác định xem action có được ứng dụng Interceptor hay không
    • Nếu có, framework sẽ gọi Interceptor theo tuần tự. Khi gọi xong một Interceptor, framework sẽ checking tiếp Interceptor trong stack cho đến khi Interceptor cuối cùng
    • Nếu không có áp dụng interceptor hay interceptor cuối cùng được thực thi thì framework sẽ gọi action
    • Action đón nhận dữ liệu, thực hiện xử lý và kích hoạt phương thức chỉ định thực thi (mặc định là phương thức execute – người dùng có thể định nghĩa phương thức tên khác và chỉ định trong tập tin cấu hình)
    • Sau khi hàm execute xử lý hoàn tất, phương thức sẽ trả ra Result – có thể nhãn tương tự như ActionMapping bên Struts1.
    • Tại bước này, nếu ứng dụng có áp dụng interceptor là Result sẽ được apply theo chiều ngược chiều gọi ban đầu để trả kết quả trở về hay chuyển đến action tiếp theo
  • Nhìn tổng quan mô hình hoạt động giống hoàn toàn khái niệm Struts1 và MVC2, điểm khác biệt ở đây là tất cả mọi thứ phải thông qua struts.xml hay annotation và một phần nào đó Struts che dấu FilterDispatcher đối với người lập trình để tạo nên tính linh hoạt trong việc xây dựng và bảo trì ứng dụng  Web, đặc biệt là việc mapping kết xuất giữa các trang không còn lệ thuộc và đặt trong code servlet dẫn đến việc mapping trở nên linh hoạt và uyển chuyển hơn
  • Điểm đặc biệt của Struts2 áp dụng FilterDispatcher so với Struts1 với Action Servlet theo đánh giá chủ quan của tác giả bài viết là Filter có thể lọc 02 chiều so với Servlet và đặc biệt làm giảm tải việc xử lý cuối cùng và nó cũng là điểm ứng dụng của DispatcherAction trong Struts1
  • Các thành phần chính yếu và thường dùng của Struts2 Framework
    • FilterDispatcher
      • Khởi tạo Action class
      • Thực thi phương thức chỉ định theo tập tin cấu hình hay annotation
      • Đọc giá trị string trả về sau khi thực thi để xác định result hay view về phía người dùng
      • Trong quá trình thực thi, Filter thực hiện
        • Tìm kiếm phương thức execute() hay phương thức được chỉ định trong cấu hình
        • Phát sinh result hay view tương ứng dựa trên kết quả String trả về của hàm execute hay phương thức chỉ định
      • Cú pháp mapping trong web.xml
<filter>
<filter-name>struts2</filter-name>
<filter-class>org.apache.struts2.dispatcher.FilterDispatcher</servlet-class>
</filter>
<filter-mapping>
<filter-name>struts2</servlet-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
    • Action Class hay ActionSupport Class
      • Chứa đựng các thuộc tính mapping trên form và các thành phần xử lý của object (business logic) và phương thức chỉ định thực thi
      • Là java class bình thường và không cần thiết phải extends Action hay ActionSupport class
      • Struts2 Framework cung cấp cơ chế tự động mapping các tham số trong request trong form đến các thuộc tính trong Action với các thuộc tính cùng tên và có phương thức setXxx
        • Trong quá trình mapping struts2 framework sử dụng OGNL thay thế EL để ép kiểu tự động từ form đến kiểu dữ liệu của Action property – do vậy, không nhất thiết lúc nào cũng khai báo kiểu dữ liệu là String và thực hiện ép kiểu bằng tay
    • Struts Config (struts.xml)
<!DOCTYPE struts PUBLIC “-//Apache Software Foundation//DTD Struts Configuration 2.0//EN” “http://struts.apache.org/dtds/struts-2.0.dtd”>
<struts>
[<include file=”xml File”/>]
<package name=”default” namespace=”/” extends=”struts-default” [method=”method_name”]>
<action name=”action_Name” class=”package.className”>
<result name=”stringValue”>/pageView</result>
</action>
</package>
</struts>
      • package: nhóm thông tin cấu hình của những thành phần có chung thuộc tính
        • name: xác định tên của package
        • namespace: phân biệt giữa các package khác tránh xung đột giữa các action với nhau
        • extends: xác định class cha tương tự như khái niệm kế thừa
        • abstract: bằng true nếu lớp là kế thừa
      • action: ánh xạ một action với một class action
        • name: xác định tên action
        • class: xác định java class để xử lý action
        • method: xác định phương thức được gọi khi request được chuyển tới. Nếu tham số này không tồn tại thì phương thức execute mặc định được tìm kiếm và thực thi
      • result: xác định tên result hay page kết xuất của một action
        • name: xác định tên result. Nếu không có mặc định là giá trị success
        • type: xác định loại result. Nếu không có mặc định là FilterDispatcher thực hiện forward đến trang kết quả
          • chain: chuyển đến action tiếp theo và copy giá trị đế valueStack và chuyển sang Action mới
          • redirect: chuyển trang như gọi response.sendRedirect
          • redirectAction: chuyển đến Action khác sử dụng phương thức response.sendRedirect
      • include: Cho phép nhúng nhiều module hay tích hợp nhiều module vào trong ứng dụng
        • file: xác định tên file được include vào tập tin struts.xml
      • ActionSupport class mở rộng từ Action và được hỗ trợ validation và I18n và nhiều thành phần khác vì nó được implement từ nhiều thành phần như Validateable, ValidationAware, TextProvider, LocalProvider, and Serializable interfaces
    • Result và ResultType
      • Result được gửi làm hai thành phần
      • Result
        • Định nghĩa action tiếp theo trong việc xử lý khi Action hoàn tất xử lý
      • Result type
        • Xác định chi tiết của việc chuyển Result như chain, redirect, redirectAction
    • Ví dụ
 Action
public class TestAction
...
public String execute(){
if (username.equals(“admin”)) {
setMessage(MESSAGE + getUserName());
return “success”;
} else {
return “error”;
}
}
}
 struts.xml
...
<action name=” testAction“ class=”example.TestAction“>
<result name=”success”>/example/DisplayDetails.jsp</result>
<result name=”error”>/example/error.jsp</result>
</action>
...
    • ValueStack
      • Stack lưu trữ object trong Frameworks và các thành phần trong một request
      • Hỗ trợ người dùng sử dụng taglib truy cập các giá trị trong ValueStack
      • Cung cấp cho việc truy cập liên quan đến context hiện hành làm việc từ request, session đến application …
      • Một số đối tượng mặc định của ValueStack
    • ActionContext
      • Vùng lưu trữ tổng để chứa tất cả dữ liệu liên quan đến request và nằm hoàn toàn trong trong ValueStacks
      • Khi dữ liệu được truyền đến container hay struts 2 framework thì interceptor params hỗ trợ trích xuất dữ liệu và đưa cặp name và value của parameter vào ValueStack
    • Một số taglib hỗ trợ, chúng ta sẽ tiếp cận trong các thành phần cụ thể trong từng ứng dụng trong từng bài
      • Về giao diện có hỗ trợ đầy đủ các control trình bày giao diện, đặc biệt các control hỗ trợ thuộc tính label cho phép developer đính kèm theo control là nhãn trình bày mà không cần phải tốn công ghi tên nhãn trước control
      • Ngoài ra, về form, mặc định form của taglib sẽ phát sinh ra dạng table cùng với layout để trình bày form với đầy đủ các thành phần của css cùng javascript để hỗ trợ cho việc xử lý và trình bày. Do vậy, để đơn giản form và việc phát sinh form tự động chúng ta áp dụng thuộc tính theme=”simple” để form phát sinh mà không apply template hay layout phức tạp dẫn đến tình trạng bể form khi xử lý giao diện đặc biệt trong table
      • Để hỗ trợ trình bày hay in dữ liệu từ thuộc tính của action hay JavaBean, Struts 2 taglib cung cấp tag property
      • Vì tích hợp các tag của JSTL để không còn sử dụng JSTL, các tag trong struts 2 tương tự JSTL ngoại trừ tag forEach và forToken được thay bằng iterator. Hơn thế nữa tag if đã có elseif và else, ….
  • OGNL
    • Viết tắt của Object Graph Navigation Language
    • Hỗ trợ tương tự như EL của JSP nhưng cho phép truy cập ValueStack thay đổi giá trị trong ValueStack lẫn trong JavaBean (EL chỉ cho phép truy cập không cho thay đổi)
    • Loại dữ liệu của OGNL thường là Map.
    • Trong expression, chúng ta có thể truy cập trực tiếp thành phần dùng OGNL mà không cần phải có ký hiệu đặc biệt gì cả, đơn giản rất nhiều so với EL. Lưu ý, các thành phần này phải nằm trong context mặc định của ứng dụng như root. Trong Struts2, context cao nhất là ActionContext hay các object được tạo từ JavaBeans.
    • Để reference đến thành phần object bên trong hay khác root, chúng ta phải dùng dấu #. Ví dụ như để truy cập thuộc tính USER trong session, chúng ta phải truy cập #session.USER
    • Để định trị giá trị 1 cách chính xác, chúng ta dùng cú pháp %{} thay cho ${} trong EL. Đối với thành phần trong JavaBean chúng ta có thể ghi trực tiếp tên thuộc tính mà không cần cú pháp nêu trên

  • Truy cập HttpServletRequest
    • Chúng ta có 02 cách: truy cập từ ActionContext hay implement class với ServletRequestAware
      • Để truy cập từ ActionContext trong code Java
HttpServletRequest request = ServletActionContext.getRequest();
      • Implement class action với ServletRequestAware, chúng ta
        • Khai báo biến HttpServletRequest request;
        • public HttpServletRequest getServletRequest() { return this.request; }
        • Gọi hàm getServletRequest khi cần truy cập request
  • Truy cập HttpSession
    • Chúng ta có 02 cách: truy cập từ ActionContext hay implement class với SessionAware
      • Để truy cập từ ActionContext trong code Java
Map attibutes = ActionContext.getContext().getSession();
      • Implement class action với SessionAware, chúng ta
        • Khai báo biến Map session;
        • Public Map getSession() { return this.session; }
        • Gọi hàm getSession khi cần truy cập request
  • Các bước thực hiện xây dựng ứng dụng web áp dụng Struts2 Framework
    • Bước 1: Tạo ứng dụng project Web application
      • Chọn Web Servers hỗ trợ JavaEE và có hỗ trợ JavaEE 5
      • Chọn hay đưa các thành phần hỗ trợ Struts 2 Frameworks
    • Bước 2: Tạo tất cả giao diện cho ứng dụng – trang JSP
    • Bước 3: Tạo tất cả action class để đón nhận xử lý
      • Định nghĩa các thuộc tính theo form nhập liệu trong các view từ bước 2 và định nghĩa đầy đủ get và set cho chúng
      • Cài đặt phương thức execute()  hay bất kỳ thực hiện xử lý cho action khi có yêu cầu
    • Bước 4: Cấu hình tập tin struts.xml hay thiết lập kết nối bằng annotation giữa View và Action
    • Step 5: Build, Deploy và Test ứng dụng

0 nhận xét:

Post a Comment

 

BACK TO TOP

Xuống cuối trang