Output file ĐẠI HỌC QUỐC GIA HÀ NỘI TRƯỜNG ĐẠI HỌC CÔNG NGHỆ PHẠM ĐÌNH PHONG NGHIÊN CỨU VỀ KIỂM CHỨNG BẤT BIẾN CỦA ĐỐI TƯỢNG SỬ DỤNG LẬP TRÌNH HƯỚNG KHÍA CẠNH Ngành Công nghệ thông tin Chuyên ngành Cô[.]
Trang 1ĐẠI HỌC QUỐC GIA HÀ NỘI
TRƯỜNG ĐẠI HỌC CÔNG NGHỆ
PHẠM ĐÌNH PHONG
NGHIÊN CỨU VỀ KIỂM CHỨNG BẤT BIẾN CỦA ĐỐI TƯỢNG
Trang 2Lời cảm ơn
Với lòng biết ơn sâu sắc, em xin chân thành cảm ơn thầy giáo PGS TS Nguyễn Việt Hà, người đã trực tiếp định hướng đề tài và tận tình hướng dẫn em hoàn thành luận văn này Em cũng chân thành cảm ơn thầy TS Phạm Ngọc Hùng đã có những nhận xét, đánh giá trong quá trình hoàn thiện luận văn
Em xin được bày tỏ lòng biết ơn đối với các thầy giáo, cô giáo Khoa Công nghệ thông tin Trường Đại học Công nghệ đã tận tình chỉ bảo, giảng dạy em suốt thời gian học tại trường cũng như việc hoàn thành luận văn này
Cuối cùng, xin được bày tỏ tình cảm tới những người thân trong gia đình, các bạn
bè trong tập thể lớp Cao học K15T2, K15T3 và K15CNPM đã động viên, hỗ trợ em về mọi mặt
Em xin chân thành cảm ơn!
Hà Nội, tháng 09 năm 2010
Phạm Đình Phong
Trang 3Lời cam đoan
Tôi xin cam đoan rằng, ngoại trừ các nội dung được trích từ tài liệu tham khảo hoặc các công trình khác như đã ghi rõ trong luận văn, các kết quả nêu trong luận văn này là do chính tôi thực hiện
Hà Nội, tháng 09 năm 2010
Phạm Đình Phong
Trang 4MỤC LỤC
Lời cảm ơn ii
Lời cam đoan iii
MỤC LỤC iv
Danh mục bảng biểu vi
Danh mục hình vẽ vii
Danh mục ký hiệu, từ viết tắt viii
MỞ ĐẦU 1
Chương 1 – Lập trình hướng khía cạnh 4
1.1 Giới thiệu 4
1.2 Các vấn đề tồn tại trong lập trình hướng đối tượng 5
1.2.1 Các mối quan tâm của hệ thống 5
1.2.2 Giải quyết các mối quan tâm cắt ngang bằng OOP 7
1.2.3 Các vấn đề gặp phải khi thực thi các mối quan tâm cắt ngang bằng OOP8 1.3 Lập trình hướng khía cạnh 10
1.3.1 Lịch sử hình thành 10
1.3.2 Cú pháp của AOP và mô hình lập trình 11
1.3.3 Quản lý các mối quan tâm bằng lập trình hướng khía cạnh 12
1.3.4 Đan kết 13
1.3.5 Phương pháp lập trình hướng khía cạnh 14
1.3.6 Lợi ích của lập trình hướng khía cạnh 15
1.3.7 Nhược điểm của phương pháp lập trình hướng khía cạnh 17
1.3.8 Các công cụ AOP 18
1.4 AspectJ 19
1.4.1 Thực thi cắt ngang 19
1.4.2 Joint Point 20
1.4.3 Pointcut 22
1.4.4 Advice 26
1.4.5 Introduction 29
1.4.6 Aspect 30
1.5 Kết luận 33
Chương 2 - Công cụ kiểm chứng mô hình Java PathFinder 34
2.1 Giới thiệu 34
2.2 Công cụ kiểm chứng mô hình Java PathFinder 34
2.2.1 Lịch sử của Java PathFinder 35
2.2.2 Các thành phần của Java PathFinder 35
2.2.3 Những gì có thể được kiểm chứng bởi Java PathFinder 37
2.2.4 Kiểm chứng mô hình trong Java PathFinder 37
2.3 Các đề án mở rộng của Java PathFinder 40
2.4 Kết luận 41
Chương 3 – Kiểm chứng bất biến của chương trình Java sử dụng lập trình hướng khía cạnh 42
3.1 Đặt vấn đề 42
3.2 Ngôn ngữ mô hình hóa thống nhất UML 43
3.2.1 Thuộc tính 43
Trang 53.2.2 Liên kết 44
3.2.3 Thao tác 44
3.3 Ngôn ngữ ràng buộc đối tượng OCL 45
3.3.1 Biểu diễn biểu thức OCL 45
3.3.2 Bất biến (invariant) 46
3.4 Ví dụ minh họa 48
3.5 Kiểm chứng bất biến sử dụng AOP 50
3.6 Vấn đề kế thừa các bất biến ở lớp con 51
3.7 Kiểm chứng bất biến của lớp con có ràng buộc thay đổi so với lớp cha 55
3.8 Kiểm chứng bất biến liên quan đến các thuộc tính được thêm vào lớp con 60
3.9 Thực nghiệm 62
3.10 Kết luận 64
Chương 4 – Sinh tự động các ca kiểm thử bằng công cụ Java PathFinder 65
4.1 Tổng quan 65
4.2 Thực thi ký hiệu 65
4.3 Sinh tự động các ca kiểm thử bằng thực thi ký hiệu 67
4.4 Kiểm chứng bất biến bằng việc chèn khẳng định 71
4.4.1 Khẳng định trong Java và Java PathFinder 71
4.4.2 Xác định các bất biến 72
4.4.2.1 Đặt khẳng định trong đoạn mã 72
4.4.2.2 Kiểm tra bất biến trong phương thức main 72
4.4.2.3 Bất biến như là một tiến trình (Invariant as a Thread) 74
4.4.3 So sánh phương pháp AOP và phương pháp chèn khẳng định 75
4.5 Kết quả thực nghiệm 76
4.5.1 Kết quả thực nghiệm sinh các ca kiểm thử tự động 76
4.5.2 Kết quả thực nghiệm kiểm chứng bất biến bằng chèn khẳng định 79
4.6 Kết luận 80
KẾT LUẬN 81
TÀI LIỆU THAM KHẢO 83
Trang 6Danh mục bảng biểu
Bảng 1.1 So sánh giữa aspect và lớp
Bảng 3.1 Một số kết quả thực nghiệm
Trang 7Danh mục hình vẽ
Hình 1.1 Các mối quan tâm trong một hệ thống
Hình 1.2 Thực thi các mối quan tâm cắt ngang bằng OOP
Hình 1.3 Chồng chéo mã nguồn
Hình 1.4 Dàn trải mã nguồn
Hình 1.5 Sự khác nhau giữa biên dịch chương trình thông thường và có aspect Hình 1.6 Mối quan hệ giữa các thuật ngữ AOP
Hình 1.7 Thực thi các mối quan tâm cắt ngang bằng AOP
Hình 1.8 Các giai đoạn phát triển AOP
Hình 1.9 Ví dụ về định nghĩa pointcut
Hình 2.1 Sự bố trí các tầng của JPF
Hình 2.2 Các thành phần của JPF
Hình 2.3 Bùng nổ không gian trạng thái do sự đan xen giữa các luồng
Hình 3.1 Biểu diễn các ràng buộc trên sơ đồ UML
Hình 3.2 Ví dụ biểu đồ lớp của hệ thống card ATM
Hình 3.3 Quy trình kiểm chứng bất biến
Hình 4.1 Thực thi ký hiệu
Trang 8Danh mục ký hiệu, từ viết tắt
Từ viết tắt Thuật ngữ Ý nghĩa
AOP Aspect-Oriented Programming Lập trình hướng khía cạnh
API Application Programming
Eclipse Bộ công cụ phát triển phần mềm IBM International Business Machines
Corp
Một trong những nhà sản xuất máy tính lớn nhất thế giới
JDK Java Development Kit Bộ phát triển ứng dụng Java
JPF Java PathFinder Bộ công cụ kiểm chứng mô hình
cho ngôn ngữ Java JVM Java Virtual Machine Máy ảo Java
LTW Load-time Weaving Đan kết lúc nạp chương trình
MJI Model Java Interface Giao diện Java mẫu
OCL Object Constraint Language Ngôn ngữ ràng buộc đối tượng OOP Object-Oriented Programming Lập trình hướng đối tượng
RTW Run-time Weaving Đan kết lúc thực thi
SPIN Simple Promela INterpreter
Công cụ thông dịch ngôn ngữ Promela (trong kiểm chứng mô hình)
SUT System Under Test Hệ thống được kiểm thử
Syntropy Một phương pháp phân tích và thiết
kế hướng đối tượng thế hệ thứ hai UML Unified Modeling Language Ngôn ngữ mô hình hóa thống nhất
XML eXtensible Markup Language Ngôn ngữ đánh dấu mở rộng
Trang 9MỞ ĐẦU
Những năm gần nay, với sự phát triển của phương pháp lập trình hướng đối tượng (OOP) [1, 2, 12] đã mang lại nhiều bước tiến mới cho lập trình nói chung và đưa ngành Công nghệ phần mềm lên một bước phát triển mới Ưu điểm lớn nhất của lập trình hướng đối tượng là một hệ thống phần mềm được xây dựng bởi tập các lớp rời rạc Mỗi lớp có nhiệm vụ hoàn toàn xác định, các nhiệm vụ của nó được vạch ra một cách rõ ràng Trong một ứng dụng hướng đối tượng, các lớp cộng tác với nhau để đạt được mục tiêu chung của ứng dụng Tuy nhiên, có các phần của một hệ thống không chỉ gánh nhiệm vụ giới hạn trong một lớp, chúng cắt ngang toàn bộ hệ thống và ảnh hưởng đến nhiều lớp Đó chính là sự đan nhau phức tạp giữa các thành phần bên trong ứng dụng Bên cạnh đó, tính tĩnh trong cách tiếp cận hướng đối tượng không cho phép phần mềm thích ứng với những thay đổi mới đáp ứng yêu cầu người dùng Một hướng tiếp cận mới trong việc phát triển phần mềm là lập trình hướng khía cạnh (AOP: Aspect-Oriented Programming) [10, 22, 3] Hướng tiếp cận này còn khá mới mẻ nhưng hứa hẹn những lợi điểm giải quyết được những yêu cầu có tính đan xen phức tạp, đồng thời mang lại cho phần mềm khả năng thay đổi và bổ sung yêu cầu mới sau khi đã hoàn chỉnh hay thậm chí đã đưa vào sử dụng
Ngôn ngữ mô hình hóa thống nhất (Unified Modelling Language - UML [4]) được chấp nhận rộng rãi như là một chuẩn cho phân tích và thiết kế hướng đối tượng Việc biểu diễn và mô hình hóa cấu trúc tĩnh của hệ thống hướng đối tượng được dùng phổ biến trong các sơ đồ lớp UML Tuy nhiên, không phải các cấu trúc chi tiết nào cũng có thể được biểu diễn một cách dễ dàng trong một sơ đồ lớp Ngôn ngữ ràng buộc đối tượng (Object Constraint Language - OCL [29]), một phần của UML, là ngôn ngữ dùng cho việc mô tả các ràng buộc thêm vào trên các mô hình hướng đối tượng Các ràng buộc OCL được sử dụng để mô tả các bất biến trên các lớp và các kiểu, các tiền điều kiện và hậu điều kiện của các thao tác Các ràng buộc OCL luôn luôn được kết nối tới một mô hình hướng đối tượng UML Một bất biến (invariant) là một ràng buộc liên quan đến một lớp, kiểu hay giao diện trong một mô hình UML Bất biến được biểu diễn như một biểu thức lôgic giới hạn giá trị của một thuộc tính hay liên kết hay nó có thể biểu diễn mối quan hệ giữa các giá trị của các thuộc tính, các liên kết Kết quả của biểu thức phải là đúng đối với tất cả các thể hiện của lớp được tham chiếu Giai đoạn đảm bảo chất lượng phần mềm ngày càng trở nên quan trọng Trong giai đoạn này, các đặc tả UML và các ràng buộc OCL đã được tạo ra bởi các nhà thiết
kế phần mềm, chương trình chính đã được cài đặt bởi các nhà phát triển phần mềm dựa trên các đặc tả UML Như vậy làm thế nào để kiểm chứng được bất biến của các đối tượng được thể hiện bằng các ràng buộc OCL có bị vi phạm tại thời điểm thực thi hay không Sau khi nghiên cứu phương pháp AOP, chúng tôi thấy có thể sử dụng
Trang 10phương pháp này để cài đặt các mã kiểm chứng để kiểm chứng các bất biến của các phần mềm được thiết kế theo phương pháp hướng đối tượng dựa trên các ràng buộc OCL đã được thiết kế Đã có những nghiên cứu trước đó liên quan đến phương pháp này [3, 23] Theo đó, công việc kiểm chứng được tách biệt hoàn toàn khỏi chương trình chính bằng cách tạo ra các aspect chứa mã kiểm chứng Các aspect này sẽ được đan tự động vào chương trình chính và khi chương trình được thực thi, công việc kiểm chứng sẽ được thực hiện tự động Tuy nhiên các nghiên cứu chưa xem xét việc kiểm chứng bất biến cho các lớp con được kế thừa bên dưới Chúng tôi quan tâm tới việc xem xét các bất biến của các đối tượng theo quan hệ kế thừa, cụ thể là nghiên cứu kiểm chứng bất biến liên quan đến các thuộc tính được thêm mới vào lớp con và bất biến của lớp con có ràng buộc thay đổi so với lớp cha
Việc kiểm thử tính đúng đắn của các phương thức cần có bộ dữ liệu làm đầu vào cho các phương thức cần kiểm thử Một bộ dữ liệu vào như vậy được gọi là một ca kiểm thử (test case) Việc chọn các bộ dữ liệu như thế nào để có thể phủ toàn bộ các đường thực thi có thể (possible execution path) là rất khó Nếu có công cụ sinh tự động các ca kiểm thử phủ toàn bộ các đường thực thi có thể thì ta có thể chứng minh tính đúng đắn của phương thức thông qua các ca kiểm thử được sinh ra Java PathFinder (JPF) [19, 25, 30, 31] với phần mở rộng của nó là thực thi ký hiệu dùng để sinh tự động các ca kiểm thử phủ được toàn bộ các đường thực thi có thể cho các phương thức của các đối tượng trong chương trình được cài đặt bằng ngôn ngữ Java Chúng tôi sử dụng công cụ thực thi ký hiệu để sinh tự động các ca kiểm thử nhằm kiểm tra lại phương pháp kiểm chứng bất biến bằng AOP
Nội dung nghiên cứu: Tìm hiểu và nghiên cứu về kiểm chứng phần mềm, lập trình hướng khía cạnh (Aspect Oriented Programming - AOP) và sử dụng AOP để kiểm chứng bất biến của đối tượng bao gồm:
Nghiên cứu về lý thuyết kiểm chứng phần mềm, các phương pháp, công cụ kiểm chứng phần mềm
Nghiên cứu phương pháp lập trình hướng khía cạnh và AspectJ - một đặc tả ngôn ngữ cho việc cài đặt các aspect bằng ngôn ngữ lập trình Java
Mở rộng phương pháp sử dụng AOP để kiểm chứng các bất biến của đối tượng trong chương trình Java tại thời điểm thực thi được đề xuất trong [23] bao gồm kiểm chứng bất biến liên quan đến các thuộc tính được thêm mới vào ở lớp con và bất biến của lớp con có ràng buộc thay đổi so với lớp cha
Để kiểm tra tính đúng đắn của các phương thức cần có các ca kiểm thử làm
dữ liệu đầu vào Do đó chúng tôi nghiên cứu công cụ kiểm chứng mô hình Java PathFinder và phần mở rộng thực thi ký hiệu (Symbolic Execution) [15] của nó để sinh tự động các ca kiểm thử cho các phương thức của các đối tượng trong chương trình hướng đối tượng Java
Trang 11Sử dụng công cụ Java PathFinder để kiểm chứng bất biến được khai báo dưới dạng các khẳng định (assertion) trong chương trình Java và so sánh với phương pháp kiểm chứng bất biến sử dụng AOP
Cấu trúc luận văn: Luận văn gồm các phần: Mở đầu, 4 chương, kết luận và tài liệu
tham khảo:
Chương 1 giới thiệu phương pháp lập trình hướng khía cạnh Chúng tôi trình bày quá trình hình thành phương pháp lập trình hướng khía cạnh, ưu điểm và nhược điểm của nó đồng thời trình bày về AspectJ – một cài đặt phổ biến của AOP trên ngôn ngữ lập trình hướng đối tượng Java
Chương 2 trình bày tổng quan về công cụ kiểm chứng mô hình Java PathFinder (JPF) và các mở rộng của nó
Chương 3 trình bày và mở rộng kỹ thuật kiểm chứng bất biến của đối tượng trong chương trình hướng đối tượng Java tại thời điểm thực thi sử dụng phương pháp AOP Chúng tôi trình bày kỹ thuật sử dụng AOP để kiểm chứng bất biến của đối tượng Java Phương pháp này đã có các nghiên cứu được công bố [23, 3] và chúng tôi mở rộng xem xét các bất biến theo quan hệ kế thừa Cụ thể là chúng tôi đề xuất kỹ thuật kiểm chứng bất biến liên quan đến các thuộc tính được thêm vào lớp con và bất biến của lớp con có ràng buộc thay đổi so với lớp cha
Chương 4 trình bày phương pháp sử dụng công cụ thực thi ký hiệu là một mở rộng của JPF để sinh các ca kiểm thử tự động cho các phương thức của đối tượng trong chương trình hướng đối tượng Java nhằm mục đích kiểm tra lại phương pháp kiểm chứng sử dụng AOP Chương này cũng trình bày phương pháp kiểm chứng bất biến được khai báo dưới dạng các khẳng định trong chương trình Java sử dụng JPF và
so sánh với phương pháp kiểm chứng bất biến sử dụng AOP Một vài thực nghiệm của thực thi ký hiệu và của kiểm chứng bất biến bằng việc chèn các khẳng định cũng được trình bày
Trang 12Chương 1 – Lập trình hướng khía cạnh
1.1 Giới thiệu
Hệ thống phần mềm có thể được xem là một thể hiện kết hợp nhiều vấn đề Một
hệ thống tiêu biểu có thể gồm nhiều dạng vấn đề như xử lý nghiệp vụ, hiệu suất, bảo toàn dữ liệu, bảo mật, bẫy lỗi, … và còn có những vấn đề của quá trình phát triển hệ thống như tính dễ quản lý, dễ bảo trì và phát triển Trong việc thiết kế phần mềm, các nhà thiết kế phần mềm thường tập chung sự quan tâm vào các chức năng chính, cơ bản của hệ thống Trong ứng dụng của các doanh nghiệp, đó chính là các logic nhiệp vụ cơ bản Ví dụ như trong ứng dụng quản lý nhgiệp vụ bảo hiểm, các mô-đun chức năng chính được thiết kế cho việc quản lý các giao dịch bảo hiểm do khách hàng hoặc nhân viên phòng nghiệp vụ thực hiện Trong ứng dụng quản lý nhân sự, các mô-đun quản lý chính là quản lý hồ sơ nhân viên, tính toán lương và các chế độ cho nhân viên Trong hai ứng dụng trên, các mô-đun xử lý nghiệp vụ chính có thể được thực hiện riêng rẽ nhưng có những mối quan tâm liên quan đến nhiều mô-đun như tính năng lưu vết, xác thực quyền hạn, truy cập cơ sở dữ liệu, bẫy lỗi, … Các tính năng đó là cần thiết đối với mỗi mô-đun chính của hệ thống và dàn trải trên nhiều môđun của hệ thống Các mối quan tâm dàn trải trên nhiều mô-đun của hệ thống đó được gọi là các mối quan tâm cắt ngang (cross-cutting concerns) Do vậy đối với mỗi mô-đun, lập trình viên ngoài việc quan tâm đến những vấn đề cơ bản còn phải tính đến những mối quan tâm cắt ngang
và sự trộn lẫn nhiều đoạn mã để xử lý những yêu cầu khác nhau Sự trộn lẫn nhiều đoạn mã như vậy gọi là vấn đề đan nhau Do vấn đề đan nhau có ở nhiều mô-đun nên các đoạn xử lý liên quan cũng xuất hiện ở nhiều mô-đun Những vấn đề này ảnh hưởng đến vấn đề thiết kế và phát triển phần mềm như hệ thống khó xây dựng, khó quản lý, phát triển và tái sử dụng kém
Lập trình hướng đối tượng (Object-Oriented Programming - OOP) [1, 2, 12] là phương pháp lập trình phổ biến nhất hiện nay được sử dụng để quản lý các mối quan tâm nghiệp vụ chính, tuy nhiên phương pháp này chưa đủ mạnh để xử lý hiệu quả rất nhiều các mối quan tâm cắt ngang hệ thống, đặc biệt là các ứng dụng phức tạp
Phương pháp lập trình hướng khía cạnh (Aspect-Oriented Programming - AOP) [10, 22, 3] là phương pháp lập trình mới cho phép chúng ta thực hiện các vấn đề riêng biệt một cách linh hoạt và kết hợp chúng lại để tạo nên hệ thống sau cùng AOP bổ sung cho kỹ thuật lập trình hướng đối tượng bằng việc cung cấp một dạng mô-đun khác bằng cách kéo các mối quan tâm cắt ngang vào một khối, đó chính là aspect Với AOP, ta có thể cài đặt các mối quan tâm cắt ngang hệ thống trong các aspect thay vì dàn trải chúng trên các mô-đun nghiệp vụ chính liên quan Quá trình bộ đan aspect (weaver) kết hợp các mô-đun nghiệp vụ chính với các aspect thành hệ thống cuối cùng
Trang 13được gọi là quá trình đan (weaving) Như vậy, AOP đã mô-đun hóa các mối quan tâm cắt ngang một cách rõ ràng, tách biệt với các mô-đun nghiệp vụ chính giúp cho việc thiết kế, thực thi và bảo trì hệ thống dễ dàng hơn và tốn ít chi phí, công sức Các aspect của hệ thống có thể thay đổi, thêm hoặc xóa lúc biên dịch và có thể tái sử dụng
Lập trình hướng khía cạnh là kỹ thuật lập trình mới cho phép đóng gói những hành vi liên quan đến nhiều đối tượng và rất có thể sẽ là bước phát triển kế tiếp trong phương pháp lập trình Tuy nhiên AOP không thay thế OOP mà nó là sự bổ sung cho OOP, cho phép chúng ta giải quyết các bài toán phức tạp tốt hơn và hiệu quả hơn Trong các phần tiếp theo, chúng ta sẽ khảo sát những vấn đề mà lập trình hướng đối tượng làm tốt và những vấn đề phát sinh từ các đối tượng và làm thế nào AOP có thể lấp khoảng trống này AspectJ [11, 13, 26], một cài đặt phổ biến của AOP trên ngôn ngữ Java cũng được giới thiệu trong chương này
1.2 Các vấn đề tồn tại trong lập trình hướng đối tượng
Phát triển phần mềm đã đi được một quãng đường khá dài Khi sự hữu ích của phát triển phần mềm được phát hiện, sự cải tiến nó đã trở nên bắt buộc để tìm kiếm các
kỹ thuật để mô hình hóa các bài toán của thế giới thực một cách hiệu quả hơn Nhiều năm trước, phương pháp luận chung cho việc giải quyết một bài toán là chia nó thành các môđun chức năng nhỏ hơn và mỗi chức năng được cấu thành từ nhiều dòng lệnh Phương pháp luận này đã làm việc tốt nhưng một trạng thái hệ thống được điều khiển bởi một số lượng lớn các biến toàn cục mà chúng có thể được thay đổi bởi bất kỳ dòng lệnh nào trong ứng dụng Sự xuất hiện của phương pháp luận hướng đối tượng kéo trạng thái của hệ thống vào các đối tượng riêng lẻ, chúng có thể trở nên riêng tư và được điều khiển thông qua các phương thức truy cập và logic
Kỹ thuật OOP rất xuất xắc trong việc đóng gói các hành vi vào chủ thể lớp (class), miễn là chúng riêng biệt Tuy nhiên, trong các bài toán thực tế có những hành
vi dàn trải trên nhiều lớp Trong hầu hết các ngôn ngữ lập trình hướng đối tượng truyền thống như C++ [2] hay Java [1, 12] đều không hỗ trợ việc đóng gói các hành vi dàn trải trên nhiều môđun, dẫn đến mã chương trình có thể nằm lẫn lộn, rải rác và khó quản lý Hiện tại, OOP được lựa chọn cho hầu hết các dự án phần mềm Nó tập chung vào giải quyết các nghiệp vụ chính nhưng nó không phải là phương pháp tốt để quản
lý các hành vi dàn trải trên nhiều mô-đun
1.2.1 Các mối quan tâm của hệ thống
Sự chia tách các mối quan tâm là một nguyên lý cơ bản của kỹ nghệ phần mềm Nguyên lý này giúp quản lý tính phức tạp của phát triển phần mềm bằng việc khai báo, đóng gói và khai thác các phần của phần mềm liên quan đến một mối quan tâm đặc thù Một mối quan tâm (concern) là một yêu cầu cụ thể hoặc một sự cân nhắc nào đó cần phải được đưa ra nhằm thỏa mãn mục đích chung của toàn hệ thống Một hệ thống phần mềm là việc thực thi tập các mối quan tâm đó Ví dụ trong một hệ thống quản lý
Trang 14nghiệp vụ bảo hiểm bao gồm việc thực thi các mối quan tâm sau: quản lý khách hàng, quản lý hợp đồng bảo hiểm, tính lãi suất cho các hợp đồng bảo hiểm có yếu tố tiết kiệm, thực hiện chi trả bảo hiểm, tạo báo cáo, xác thực quyền hạn, lưu vết giao dịch,
… Bên cạnh các mối quan tâm của hệ thống, một dự án phần mềm cần chỉ ra được các mối quan tâm khác liên quan đến toàn bộ các thuộc tính chất lượng của hệ thống như tính dễ hiểu, dễ quản lý, dễ bảo trì và phát triển
Các mối quan tâm được chia thành hai loại: mối quan tâm chính được cài đặt chức năng chính của một mô-đun và mối quan tâm cắt ngang là yêu cầu ngoài, mức hệ thống và dàn trải trên nhiều mô-đun Một ứng dụng của một doanh nghiệp không những quan tâm đến các mối quan tâm nghiệp vụ chính mà còn phải quan tâm đến các mối quan tâm cắt ngang hệ thống như xác thực quyền hạn, lưu vết giao dịch, bẫy lỗi, truy cập tài nguyên chung, đảm bảo tính toàn vẹn của giao dịch, … Tất cả các mối quan tâm này đều cắt ngang một số mô-đun Ví dụ như mối quan tâm về việc lưu vết giao dịch liên quan đến tất cả các môđun giao dịch chính, mối quan tâm về truy cập dữ liệu liên quan đến các mô-đun có truy xuất cơ sở dữ liệu, mối quan tâm về xác thực quyền hạn liên quan đến các mô-đun có yêu cầu về quản lý quyền truy cập Hình 1.1 minh họa việc thực thi các mô-đun trong một hệ thống chứa cả các mối quan tâm mức
hệ thống và các mối quan tâm nghiệp vụ Ở đây, một hệ thống được mô tả như một sự tổng hợp của nhiều mối quan tâm Hệ thống trở nên chồng chéo lên nhau bởi các kỹ thuật cài đặt hiện tại, chính vì thế, sự độc lập giữa các mối quan tâm không được đảm bảo
Hình 1.1 Các mối quan tâm trong một hệ thống
Trang 151.2.2 Giải quyết các mối quan tâm cắt ngang bằng OOP
Trong quá trình phát triển phần mềm các nhà phát triển thường xác định các mối quan tâm và sau đó chia tách chúng cho các nhóm phát triển khác nhau để mô-đun hóa chúng Có những trở ngại lớn cho các nhóm phát triển khi mô-đun hóa các mối quan tâm là làm sao xử lý hiệu quả các mối quan tâm cắt ngang hệ thống Trong thực tế, phương pháp OOP thường được sử dụng để mô-đun hóa các mối quan tâm của một hệ thống phần mềm Tuy nhiên, thực tế thì, mặc dù OOP giải quyết rất tốt trong việc mô-đun hóa các mối quan tâm nghiệp vụ chính nhưng lại gặp khó khăn trong việc mô-đun hóa các mối quan tâm cắt ngang hệ thống
Trong OOP, các mô-đun chính có thể được kết nối lỏng với nhau thông qua giao diện, nhưng không dễ gì làm việc này với các mối quan tâm cắt ngang hệ thống Lý do chính là một mối quan tâm được thực thi thành hai phần: Phần phía server (phần phục vụ) và phần phía client (phần được phục vụ) OOP mô-đun hóa phần client khá tốt bằng các lớp và các giao diện Tuy nhiên, ở phía server, một mối quan tâm lại là một loại cắt ngang hệ thống, bao gồm các yêu cầu gửi đến server, dàn trải trên các client
Hình 1.2 Thực thi các mối quan tâm cắt ngang bằng OOP
Xét một ví dụ điển hình về việc thực thi một mối quan tâm cắt ngang hệ thống trong OOP: Một mô-đun lưu vết cung cấp các dịch vụ thông qua một giao diện trừu tượng Việc sử dụng giao diện nới lỏng kết nối giữa các client và việc thực thi các giao diện Các client sử dụng các dịch vụ lưu vết thông qua giao diện dành cho hầu hết các phần không quan tâm đến chi tiết cài đặt mà họ đang sử dụng Khi có bất cứ thay đổi nào đến các cài đặt mà chúng đang sử dụng sẽ không yêu cầu thay đổi đến bản thân các client Tương tự như thế, việc thay thế sự thực thi lưu vết bằng một sự thực thi khác chỉ là vấn đề về việc khởi tạo đúng loại thực thi Kết quả là một sự thực thi về lưu vết có thể được chuyển đổi với sự thực thi khác với ít hoặc không thay đổi cho các
Trang 16mô-đun client riêng lẻ Tuy nhiên, trong cấu hình này, các client vẫn phải chứa các đoạn mã để gọi các API Những lời gọi này cần phải có trong tất cả các mô-đun có yêu cầu cần lưu vết và được trộn lẫn với các đoạn mã dành cho logic nghiệp vụ chính Hình 1.2 minh họa cách thực thi mối quan tâm lưu vết trong một hệ thống phần mềm quản lý nghiệp vụ bảo hiểm sử dụng các kỹ thuật truyền thống như OOP Thậm chí khi sử dụng mô-đun lưu vết được thiết kế tốt đưa ra API trừu tượng và che giấu chi tiết về việc định dạng và phân lớp các thông điệp lưu vết, thì mỗi mô-đun client như mô-đun Subscribing, Claim hay Database đều phải chứa các đoạn mã để triệu gọi API lưu vết Kết quả tổng thể là gây ra sự lộn xộn, chồng chéo giữa các mô-đun cần lưu vết
và bản thân các mô-đun lưu vết
1.2.3 Các vấn đề gặp phải khi thực thi các mối quan tâm cắt ngang bằng OOP
Khi thực thi các mối quan tâm cắt ngang bằng phương pháp OOP, hệ thống sẽ gặp phải một số vấn đề trong đó có hai vấn đề chính là sự chồng chéo mã nguồn và dàn trải mã nguồn
Chồng chéo mã nguồn (Code tangling): Các mô-đun trong hệ thống có thể đồng thời phải thực hiện nhiều yêu cầu khác nhau Ví dụ như trong quá trình phát triển một mô-đun nào đó, ngoài việc đảm bảo yêu cầu chính của mô-đun đó, lập trình viên luôn phải tính tới các mối quan tâm khác như hiệu năng, đồng bộ, an ninh, lưu vết, lưu trữ, Các mối quan tâm này làm cho việc xuất hiện rất nhiều loại mã chương trình của các mối quan tâm khác nhau trong quá trình cài đặt mô-đun Hiện tượng này gọi là chồng chéo mã nguồn Hình 1.3 minh họa vấn đề chồng chéo mã nguồn do sự thực thi của nhiều mối quan tâm trên cùng một mô-đun
Hình 1.3 Chồng chéo mã nguồn
Dàn trải mã nguồn (Code scattering): Mã nguồn của các yêu cầu mức hệ thống (an ninh, lưu vết, lưu trữ, ) được cài đặt ở trong rất nhiều mô-đun Ví dụ như chức năng lưu vết được cài đặt ở tất các các mô-đun quan trọng cần lưu vết Như vậy việc cài đặt mã nguồn cho một mối quan tâm bị xé nhỏ vào rất nhiều mô-đun khác
Trang 17nhau Hiện tượng này gọi là dàn trải mã nguồn Hình 1.4 minh họa vấn đề dàn trải mã nguồn do đặt nhiều đoạn mã giống nhau trong nhiều mô-đun khác nhau nhằm thực thi một chức năng nào đó Ở đây, trong ví dụ hệ thống quản lý nghiệp vụ bảo hiểm, nhiều mô-đun trong hệ thống phải chứa đoạn mã để đảm bảo rằng những người dùng hợp lệ mới có thể truy cập các các chức năng nghiệp vụ của hệ thống
Hiệu suất làm việc thấp: Việc đồng thời cài đặt nhiều mối quan tâm làm cho lập trình viên phải phân tán tư tưởng vào nhiều mối quan tâm một lúc, giảm hiệu suất làm việc
Khả năng sử dụng lại mã nguồn kém: Một mô-đun thực tế đã cài đặt rất nhiều mối quan tâm một lúc, nếu như hệ thống khác có nhu cầu sử dụng chức năng tương tự
có thể chưa chắc đã sử dụng lại mô-đun này do nó còn phụ thuộc vào các mối quan tâm khác
Chất lượng mã nguồn thấp: Việc chồng chéo mã nguồn trong quá trình cài đặt
sẽ gây ra những vấn đề tiềm ẩn mà lập trình viên có thể không phát hiện ra được khi lập trình, do sự chú ý của mình bị ảnh hưởng bởi quả nhiều mối quan tâm
Trang 18Khó bảo trì hệ thống: Việc xây dựng hệ thống tại thời điểm nào đó thường bị giới hạn trong một khung nhìn với những yêu cầu cụ thể nào đó, thể hiện ở các mối quan tâm hiện có của hệ thống Nếu như trong tương lai có sự thay đổi nào đó cần bổ sung vào hệ thống, do việc cài đặt không được mô-đun hóa nên việc sửa đổi sẽ làm ảnh hưởng tới rất nhiều mô-đun, có thể gây ra những sửa đổi không đồng bộ và không thống nhất với nhau Vì thế đòi hỏi thêm chí phí và thời gian để kiểm thử và đảm bảo việc thay đổi trên là không gây ra lỗi
1.3 Lập trình hướng khía cạnh
1.3.1 Lịch sử hình thành
Lập trình hướng khía cạnh (AOP) là một tiếp cận thiết kế phần mềm được phát minh tại trung tâm nghiên cứu Xerox Palo Alto trong những năm 1990 Nó kế thừa các kết quả của các phương pháp lập trình khác như lập trình tự sinh (generative programming), siêu lập trình (meta-programming), lập trình tự điều chỉnh (reflective programming), lập trình có khả năng thích ứng (adaptive programming), lập trình hướng chủ đề (subject-oriented programming), lập trình có mục đích (intentional programming), … Mục đích của AOP là để các nhà thiết kế và các nhà phát triển tách các mối quan tâm cắt ngang mà một hệ thống phần mềm gặp phải tốt hơn Các mối quan tâm cắt ngang là các phần tử của một hành vi hệ thống không được xác định một cách dễ dàng đối với các thành phần cụ thể trong một kiến trúc ứng dụng Các mối quan tâm cắt ngang thông thường là xử lý lỗi, các kiểm tra bảo mật, lưu vết các sự kiện, xử lý giao dịch, … Mỗi thành phần trong ứng dụng phải chứa mã đặc trưng cho mỗi mối quan tâm cắt ngang, tạo ra mã của thành phần phức tạp hơn và khó thay đổi hơn
Hình 1.5 Sự khác nhau giữa biên dịch chương trình thông thường và có aspect
Để xác định các mối quan tâm cắt ngang, AOP cũng cấp các kỹ thuật cho sự nhận dạng có hệ thống, sự chia tách, sự biểu diễn và kết cấu Mỗi quan tâm cắt ngang được đóng gói trong các mô-đun riêng gọi là các aspect Trong quá trình thực thi, các aspect
Trang 19được đan kết vào chương trình thực thi để thực thi các mối quan tâm cắt ngang hệ thống
1.3.2 Cú pháp của AOP và mô hình lập trình
Cắt ngang là một kỹ thuật AOP cho phép nhận dạng các mối quan tâm và cấu trúc chúng vào trong các mô-đun bằng cách chúng có thể được triệu gọi tại các điểm khác nhau thông qua ứng dụng Có hai loại cắt ngang, tĩnh và động Cắt ngang động sửa đổi hành vi thực thi của một đối tượng bằng việc đan kết hành vi mới tại các điểm quan tâm cụ thể Cắt ngang tĩnh thay thế cấu trúc tĩnh của một thành phần bằng việc xen thêm các phương thức và các thuộc tính tại thời điểm thực thi Các cấu trúc ngôn ngữ cơ bản và cú pháp được sử dụng để khai báo cắt ngang trong AOP như sau:
Joint point là một điểm thực thi có thể nhận dạng trong một chương trình Nó
có thể là một lời gọi tới một phương thức hay một lệnh gán cho một thuộc tính của đối tượng Các joint point là quan trọng, chúng là nơi mà các hành vi của aspect được đan kết vào trong chương trình
Pointcut là một cấu trúc chương trình lựa chọn ra một nhóm các join point và tập hợp ngữ cảnh tại các join point này Hay nói cách khác, pointcut nhận dạng một joint point trong chương trình mà tại đó một mối quan tâm cắt ngang cần được áp dụng Ví dụ như, một pointcut có thể lựa chọn một join point là lời gọi tới một phương thức, nó cũng có thể nắm bắt ngữ cảnh của phương thức đó, chẳng hạn như đối tượng đích chứa phương thức được gọi và các tham số của phương thức đó Pointcut dùng để chỉ ra các quy tắc đan còn join point là các vị trí thỏa mãn các quy tắc đó
Ví dụ sau khai báo một pointcut khi phương thức setValue của lớp Stock được gọi:
pointcut log(String msg): args(msg) &
execution(void Stock.setValue(float));
Advice là một đoạn mã thực thi logic một mối quan tâm cắt ngang Nó được thực thi khi một pointcut cụ thể được đạt tới Advice có thể được thực thi trước (before advice), sau (after advice) hoặc “xung quanh” (around advice) join point
Ví dụ một before advice được cài đặt trong AspectJ:
before (String msg): log(msg){
//Đoạn mã thực thi }
Introduction là chỉ thị cắt ngang có thể tạo các thay đổi tĩnh đối với các thành phần ứng dụng Một introduction có thể tạo ra các thay đổi tĩnh cho các mô-đun mà không ảnh hưởng trực tiếp đến các hành vi của chúng Ví dụ, một instruction có thể thêm một phương thức hoặc một trường vào một lớp trong ứng dụng
Trang 20Aspect trong AOP tương ứng với một lớp trong lập trình hướng đối tượng Nó đóng gói các pointcut, các advice và các intruction
Ví dụ một aspect được cài đặt bằng AspectJ:
public aspect LoggingModule {
pointcut log(String msg):args(msg) &
execution(void Stock.setValue(float));
before (String msg): log(msg){
//Đoạn mã thực thi }
}
Hình 1.6 Mối quan hệ giữa các thuật ngữ AOP
1.3.3 Quản lý các mối quan tâm bằng lập trình hướng khía cạnh
Với việc sử dụng các kỹ thuật thiết kế thông thường, một mối quan tâm cắt ngang
có thể được mô-đun hóa bằng việc sử dụng một giao diện để đóng gói sự thực hiện mối quan tâm từ việc triệu gọi các thành phần phía client Mặc dù giao diện làm giảm
sự móc nối giữa các client và sự thực thi mối quan tâm, các client vẫn cần mã nhúng
để triệu gọi các phương thức giao diện từ bên trong logic nghiệp vụ
Với thiết kế và lập trình hướng khía cạnh, mỗi mối quan tâm cắt ngang được cài đặt một cách riêng rẽ trong một thành phần là aspect Aspect định nghĩa các điểm thực thi trong các thành phần phía client đòi hỏi sự thực hiện mối quan tâm cắt ngang Đối với mỗi điểm thực thi, aspect định nghĩa các hành vi cần thiết để thực hiện hành vi của aspect, ví dụ như gọi một API lưu vết Trong hình 1.7, mối quan tâm cắt ngang là việc
Trang 21lưu vết sự thực thi các mô-đun Subscribing, Claim và Database được cài đặt trong một aspect là Logging aspect Tiếp đó, Logging aspect có các lời gọi API tới Logging module để thực thi các phương thức cần thiết Trong quá trình thực thi ứng dụng, Logging aspect được đan tự động vào các mô-đun nghiệp vụ chính để thực hiện việc lưu vết giao dịch Bộ phận phát triển các mô-đun Subscribing, Claim và Database không cần quan tâm đến việc thực thi việc lưu vết trong quá trình phát triển
Hình 1.7 Thực thi các mối quan tâm cắt ngang bằng AOP
Quan trọng hơn là các mô-đun phía client không chứa bất kỳ mã để triệu gọi sự thực thi aspect nào Điều này dẫn đến các thành phần phía client không bị xen lẫn bởi các lời gọi để thực thi một hoặc nhiều mối quan tâm
Việc sử dụng một aspect được xác định theo một quy tắc nhất định gọi là quy tắc đan Các quy tắc đan là đầu vào cho một tiện ích lập trình gọi là bộ đan Một bộ đan kết hợp mã ứng dụng với các aspect để tạo ra hệ thống cuối cùng Các ngôn ngữ lập trình hướng khía cạnh như AspectJ cung cấp các công cụ đan kết và vì thế các ngôn ngữ AOP và các công cụ là cần thiết để thực hiện hiệu quả các thiết kế hướng khía cạnh
1.3.4 Đan kết
Việc thực hiện một thiết kế hướng khía cạnh đòi hỏi sự hỗ trợ của ngôn ngữ lập trình để thực thi các aspect riêng lẻ Ngôn ngữ cũng định nghĩa các luật cho việc đan kết một thực thi của aspect với toàn bộ mã chương trình Việc đan kết có thể tuân theo một số chiến lược:
1) một bộ tiền xử lý mã nguồn đặc biệt được thực thi trong qua trình biên dịch
Trang 222) một bộ hậu xử lý vá các tệp nhị phân
3) một trình biên dịch nhận biết AOP sinh ra các tệp nhị phân được đan kết 4) đan kết lúc nạp (load-time weaving – LTW): ví dụ, trong Java việc đan kết advice liên quan bằng việc nạp từng lớp advice vào trong JVM
5) đan kết lúc thực thi (run-time weaving – RTW): bằng việc chặn từng join point tại thời điểm thực thi và thực thi tất cả các advice liên quan
Hầu hết các ngôn ngữ AOP hỗ trợ việc đan kết lúc biên dịch (CTW) sử dụng một trong ba tùy chọn đầu Trong Java, trình biên dịch sinh ra các tệp lớp nhị phân Java chuẩn mà bất kỳ JVM chuẩn nào cũng có thể thực thi Sau đó các tệp class được sửa đổi dựa trên các aspect đã được định nghĩa CTW không phải lúc nào cũng là lựa chọn tốt và đôi khi không khả thi (ví dụ với Java Server Page) LTW đưa ra giải pháp tốt hơn và mềm dẻo hơn Trong Java, LTW đòi hỏi trình nạp JVM để có thể biến đổi các lớp lúc thực thi JDK v5.0 hỗ trợ tính năng này thông qua một kỹ thuật chuẩn đơn giản LTW phải xử lý mã bytecode của Java lúc thực thi và tạo các cấu trúc dữ liệu biểu diễn bytecode của một lớp cụ thể Quá trình xử lý này có thể diễn ra chậm Một khi tất cả các lớp được nạp, LTW không có ảnh hưởng gì đến tốc độ thực thi của ứng dụng AspectJ [11, 13, 26], JBoss AOP [27] và AspectWerkz [28] hiện hỗ trợ LTW RTW là một lựa chọn tốt nếu các aspect phải có hiệu lực lúc đang chạy Tuy nhiên, như LTW, RTW có thể có những nhược điểm về mặt hiệu suất tại thời điểm thực thi trong khi các aspect đang được đan kết
1.3.5 Phương pháp lập trình hướng khía cạnh
Hiện nay phương pháp lập trình hướng khía cạnh đang được quan tâm phát triển
và đang dần được hoàn thiện Phương pháp này không phải thay thế các phương pháp lập trình truyền thống mà là bổ sung và làm phong phú thêm phương pháp lập trình truyền thống AOP cung cấp một giải pháp cho việc pháp triển các hệ thống bằng việc tách các mối quan tâm cắt ngang thành các mô-đun và ghép nối lỏng các mô-đun này vào các mối quan tâm nghiệp vụ chính của hệ thống Về cơ bản quá trình phát triển phần mềm theo AOP gồm có 3 bước sau đây:
1) Phân tích các yêu cầu để xác định vấn đề chung và vấn đề đan nhau: trong
bước này ta sử dụng phương pháp phân tích và thiết kế hướng khía cạnh Oriented Analyis and Design) để phân tích các yêu cầu của bài toán nhằm tách các mối quan tâm nghiệp vụ chính và mối quan tâm cắt ngang hệ thống Sau bước này ta thu được bản phân tích mà các mối quan tâm nghiệp vụ chính và các mối quan tâm cắt ngang được tách riêng
(Aspect-2) Xây dựng thể hiện từng vấn đề riêng biệt: sau khi các mối quan tâm cắt ngang
được tách ra khỏi các mối quan tâm nghiệp vụ chính thì ta có thể dùng phương pháp lập trình truyền thống như lập trình hướng thủ tục hoặc lập trình hướng đối tượng để
Trang 23cài đặt các mối quan tâm nghiệp vụ chính, còn các mối quan tâm cắt ngang thì được cài đặt trong một aspect theo quy tắc mà công cụ AOP được sử dụng quy định Như vậy, mối quan tâm nghiệp vụ chính được xây dựng độc lập với các mối quan tâm cắt ngang
Hình 1.8 Các giai đoạn phát triển AOP
3) Tổng hợp các thể hiện: sau khi các mối quan tâm nghiệp vụ chính và các mối
quan tâm cắt ngang được cài đặt một các riêng rẽ, để hệ thống có thể hoạt động được thì các mối quan tâm cần phải được kết hợp theo một số quy tắc nào đó Quá trình kết hợp này gọi là quá trình tích hợp hay quá trình đan được thực hiện bằng cách sử dụng các quy tắc đan Sau quá trình đan ta nhận được hệ thống cuối cùng mà các mối quan tâm nghiệp vụ chính và mối quan tâm cắt ngang đã được đan kết với nhau để thực hiện mục tiêu theo yêu cầu Ví dụ một luật tích hợp: “Tất cả các hoạt động của hệ thống cần phải được lưu vết lại” sẽ được cài đặt trên một ngôn ngữ AOP nào đó để chỉ ra các quy tắc đan Như vậy, mối quan tâm lưu vết sẽ được bộ đan tích hợp vào các mô-đun nghiệp vụ theo đúng quy tắc chỉ ra
1.3.6 Lợi ích của lập trình hướng khía cạnh
AOP là một kỹ thuật mới đầy triển vọng, hứa hẹn đem lại nhiều lợi ích cho việc phát triển phần mềm Việc cấu trúc hóa các ứng dụng với các aspect và thực thi trực tiếp bằng sử các ngôn ngữ lập trình hướng khía cạnh có khả năng cải thiện chất lượng các hệ thống phần mềm Các aspect tạo ra các hệ thống phần mềm lớn và phức tạp có thể được sản xuất và tổ chức lại đơn giản hơn và cho chất lượng cao hơn Dưới đây là một số lợi ích chính của AOP:
Có thể nhận dạng và miêu tả một cách rõ ràng các mối quan tâm cắt ngang giúp các kiến trúc sư có thể xem xét các hành vi cắt ngang dưới dạng các aspect tại giai đoạn sớm của vòng đời dự án
Phân chia trách nhiệm rõ ràng cho các mô-đun riêng lẻ: AOP cho phép tách các mối quan tâm cắt ngang ra khỏi các mối quan tâm nghiệp vụ chính Do vậy một
Trang 24mô-đun chỉ nhận trách nhiệm với mối quan tâm nghiệp vụ chính của nó mà không cần
có nghĩa vụ gì với các mối quan tâm cắt ngang nó Ví dụ như, một mô-đun thực hiện một giao dịch nghiệp vụ chính và các thông tin thay đổi trong quá trình thực hiện giao dịch phải được lưu lại thì nó chỉ cần quan tâm đến việc thực hiện giao dịch mà không cần quan tâm đến thao tác lưu vết giao dịch Việc lưu vết giao dịch sẽ được thực hiện trong một aspect bằng AOP Điều này giúp cho việc phân chia trách nhiệm rõ ràng hơn
và khả năng theo dõi được cải thiện
Dễ dàng phát triển hệ thống: AOP mô-đun hóa các aspect riêng lẻ do đó khi
hệ thống cần chức năng mới, nhà phát triển chỉ cần tạo ra một aspect thực hiện các yêu cầu mới đó mà không cần thay đổi các mô-đun nghiệp vụ chính Khi thêm mô-đun mới đó vào hệ thống, các aspect hiện có sẽ đan kết với chúng và tạo nên sự phát triển chặt chẽ Như vậy hệ thống sẽ đáp ứng nhanh hơn với những yêu cầu mới
Tái sử dụng mã nguồn: AOP cho phép các nhà phát triển dễ dàng sử dụng lại
mã nguồn của một aspect trong nhiều thành phần và do đó giảm các nỗ lực thể hiện mã chương trình
Khả năng mô-đun hóa và đóng gói: AOP làm tăng tính mô-đun hóa và đóng gói như mã thành phần tốt hơn ngắn gọn và gọn gàng
Cho phép để lại quyết định thiết kế tương lai: Một thiết kế tốt phải tính đến cả yêu cầu hiện tại và tương lai, việc xác định yêu cầu tương lai là một công việc khó khăn Nếu bỏ sót những yêu cầu tương lai có thể sẽ phải thay đổi hay thực hiện lại nhiều phần hệ thống Với AOP, người thiết kế hệ thống có thể để lại các quyết định thiết kế cho những yêu cầu tương lai nhờ thực hiện theo các aspect riêng biệt
Rút ngắn thời gian bàn giao sản phẩm: Việc kết nối muộn các giải pháp thiết
kế giúp cho chu trình thiết kế được nhanh hơn Bên cạnh đó, việc tách biệt rõ ràng các trách nhiệm của các mô-đun giúp cho người lập trình không gặp nhiều khó khăn trong việc thực thi các mô-đun, từ đó tăng năng suất làm việc của các nhà lập trình Việc tái
sử dụng mã nguồn tốt hơn giúp giảm thời gian phát triển hệ thống Hơn thế nữa, hệ thống tiến triển dễ dàng hơn giúp cho hệ thống có thể đáp ứng nhanh hơn với các yêu cầu mới Tất cả những điều trên giúp cho hệ thống có thể phát triển và triển khai nhanh hơn
Giảm thiểu chi phí thực thi: Bằng cách tránh việc sửa đổi nhiều mô-đun khi phải cài đặt một chức năng cắt ngang, AOP giúp giảm chi phí cài đặt các chức năng cắt ngang Với AOP, các lập trình viên có thể tập trung vào các chức năng chính của của các mô-đun nghiệp vụ và tận dụng được khả năng chuyên môn của họ vào các công việc chính nên chi phí của các yêu cầu nghiệp vụ chính cũng được giảm xuống Như vậy, việc thực thi các chức năng của toàn hệ thống sẽ được giảm thiểu đáng kể
Trang 251.3.7 Nhược điểm của phương pháp lập trình hướng khía cạnh
Phương pháp lập trình hướng khía cạnh có nhiều ưu điểm kể trên, tuy nhiên nó cũng có một số hạn chế sau:
Liệu các aspect có phá vỡ tính đóng gói của các đối tượng? Bình thường các aspect tuân theo các luật điều khiển truy cập Bằng cách này hay cách khác, các aspect
có thể phá vỡ tính đóng gói của các đối tượng Nhưng chúng làm theo cách có thể kiểm soát được Các aspect có thể truy cập đến phần riêng tư của các đối tượng mà chúng tham chiếu đến nhưng không làm tổn hại đến sự đóng gói giữa các đối tượng của các lớp khác nhau Ví dụ trong AspectJ, để bỏ qua các luật truy cập ta thêm bổ ngữ đặc biệt privileged vào trước từ khóa aspect:
privileged aspect EmployeeVerifier {
pointcut verify_experience(Manager staff, int val):
target(staff)&& set(int Manager.experience)&& args(val); void around(Manager staff, int val):
Khi chúng ta mắc sai lầm trong việc diễn đạt thực thi cắt ngang có thể gây lỗi tràn ngập toàn chương trình
Việc thay đổi các joint point của một chương trình (ví dụ như đổi tên hay di chuyển các phương thức) mà không được lường trước bởi người viết aspect sẽ gây ra các lỗi
Vấn đề bảo mật có thể bị phá vỡ bởi việc sử dụng AOP để cài thêm các đoạn
mã tại các vị trí phù hợp