[Flex] Parsley, Inversion of Control (IoC) và Dependency Injection (DI)

Quan điểm của tôi là trước khi tìm hiều về Parsley thì cần phải hiểu về IoC (Inversion of Control) và DI (Dependency Injection). 2 khái niệm này không xa lạ với những lập trình viên server side, nhất là những ai sử dụng Java mà tiêu biểu là Spring. Tuy nhiên nếu chi đi từ việc phát triển UI/Client side như tôi thì 2 khái niệm này là khá mới mẻ …

Trong bài viết này, tôi giữ nguyên tên gọi IoC và DI mà không cố gắng tìm bản tiếng Việt vì quả thật là rất khó để có thể tìm một danh từ tiếng Việt cho IoC cũng như DI. Bạn hãy hiểu thông qua định nghĩa của chúng hơn là tìm một cái tên thuần Việt cho chúng.

IoC – Inversion of Control là gì ?

Về bản chất thì IoC có thể hiểu như việc khi bạn thiết kế 1 class thì class đó nên phụ thuộc vào một abstract class hay  interface chứ không phu thuộc (hoặc được dẫn xuất) từ một lớp cụ thể. IoC gắn liền với các ý tưởng thiết kế trong OOP, vì lập trình hướng thủ tục (POP – Procedure Oriented Programming), các module cấp phía trẹn lại phụ thuộc vào các module cấp dưới, và vấn đề là nếu các module cấp dưới có sự thay đổi thì phải  thay đổi cả các module cấp phía trên. Bạn có thể hiểu như là control của cấp trên phụ thuộc vào cấp dưới. Với OOP thì lập trình viên sẽ đi theo hướng thiết kế các lớp cấp cao phụ thuộc vào 1 abstract class hay interface, hơn là phụ thuộc (hay dẫn xuất) từ môt lớp cấp dưới, và khi đó tất cả sự thay đổi của các lớp cấp dưới đều không ảnh hưởng đến cấp phía trên … Như vây sự phụ thuộc được đảo ngược lại – khái niệm IoC có thể diễn gỉải theo cách này.

Với một framework thì các phương thức mà lập trình viên kế thừa từ framework sẽ được gọi bởi chính framework hơn là từ mã chương trình của lập trình viên viết. Việc điều phối, sắp xếp hoạt động của các luồng trong ứng dụng cũng do framework quản lý, và IoC cho phép một framework hoạt động như một hệ điều khiển mở rộng hơn là đóng vai trò chính điều khiển ứng dụng.

Với Cairngorm, PureMVC thì IoC được tiếp cận theo hướng mở rộng các lớp của framework và framework sẽ được định hướng cho biết các interface nào thích hợp để truy cập và thao tác các ứng dụng các đối tượng cụ thể. Parsley, Swiz cung cấp metadata annotation để móc nối với hoạt động của framwork.

DI – Dependency Injection là gì ?

Thường thì bạn sẽ định nghĩa các đối tượng trong ứng dụng một cách cụ thể trong chính mã nguồn. Với DI, đó là một cơ chế bên ngoài “tiêm” một biến định nghĩa instance của một đối tượng. DI thường được áp dụng trong Unitest, cho phép bạn tạo ra các đối tượng có quan hệ lỏng lẻo với nhau và dễ dàng thay thế các đối tượng “demo” mà bạn phải hardcode sẵn trong mã nguồn. Quá trình test sẽ kiểm định các đối tượng một cách độc lập chứ không quan tâm đến mối quan hệ giữa các đối tượng khác nhau.

Ngoài ra, việc áp dụng DI cũng tăng khả năng tái sử dụng mã nguồn, vì khi việc phụ thuộc giữa các đối tượng không còn được hard code trực tiếp trong mã nguồn nữa thì quá trình tái sử dụng có thể dễ dàng hơn, vì đơn giản là thay đổi các đối tượng được “tiêm” từ bên ngoài vào mà thôi …

Các tính năng của Parsley

Để minh họa cho việc cài đặt IoC và DI, trong bài tiếp theo tôi sẽ nói về framework Parsley với một ứng dụng nhỏ để minh họa. Có thể điểm qua các chức năng của Parsley như sau:

  • Flexible IOC Container: Hỗ trợ cấu hình với AS3 Metadata, MXML, XML , ActionScript
  • Dependency Injection: “tiêm” theo kiểu hoặc id cho cả hàm dựng (constructor), phương thức, thuộc tính …
  • Decoupled Bindings: Thông qua cơ chế đăng ký, Parsley cho phép binding dữ liệu khi nguồn dữ liệu và đối tượng đích tách biệt nhau.
  • Messaging Framework: đối tượng gửi và nhận hoàn toàn tách rời, có thể làm cơ sở cho kiến trúc MVC
  • Dynamic View Wiring:  Tạo kết giữa các  component Flex cho các đối tượng khai báo trong container
  • Advanced container features: Bất đồng bộ khởi tạo các đối tượng, vòng đời đối tượng, ngữ cảnh  cấu hình mô-đun
  • Integration with Flex Modules: Cho phép cấu hình được nạp và giải phóng cùng với module Flex
  • Localization: Tích hợp với Flex ResourceManager cho các ứng dụng Flex, ngoài ra còn có Framework dành riêng cho việc localization (bản địa hóa) cho các ứng dụng Flash.
  • Extensibility: Dễ dàng tạo ra các thẻ cấu hình do chính lập trình viên định nghĩa và có thể được sử dụng như AS3 Metadata, MXML hoặc tag XML.