Posted on 2006-11-19 19:59
canonical 閱讀(2736)
評論(6) 編輯 收藏 所屬分類:
設計理論
? 隨著IoC(Inversion of Control)容器的流行,AOP(Apsect Oriented Programming)似乎逐漸成為了主流技術的一部分,但是除了Transaction, Lazy Load, Cache, Log等少量樣板應用之外,AOP的技術價值究竟何在? 它能否在廣泛的領域發揮作用? 為什么考慮到傳統領域之外的應用時,我們的想象力是如此的貧乏?回答這些問題需要對AOP的技術實質作詳細的審視.
? 傳統上, 程序的結構是靜態的. 定義了一個類, 它的成員變量和成員函數就是確定的了,定義了一個函數, 它的具體實現也是確定的. 傳統程序設計主要定義了一些固化的規則來規范這些確定性組分的組合關系,如類繼承體系所表達的推理關系. 而AOP是一種動態代碼織入技術, 抽象的說, 一維拓撲的基本元素是線段與邊, 而AOP通過mixin, interceptor等機制可以自由的實現這些元素之間的自由組合而不拘泥于預制的規則. AOP就像是一把鋒利的砍刀, 我們用它從最終所期望的程序結構中隨意的砍下一部分來, 起個名字,就叫Aspect吧. 實際上AOP技術本身并沒有限定程序中哪些部分可以作為Aspect, 這種技術本身并不保證你可以抽象得出真正有價值的Aspect, 它只是一種純粹的程序結構操縱技術而已.
? AOP技術有兩個主要組成部分: 定位技術和定位后的組裝技術. 定位技術是AOP所宣稱的無侵入性的關鍵所在. 如果我們使用interface等機制來實現功能,則要在程序各處寫下調用語句:
??? interfaceA.methodA();
??? ...
??? interfaceA.methodB();
這可以看作是一種占位技術. 定位技術則一般不需要預先在程序中寫下什么調用語句, 根據外部的某些定位規則,我們可以在基礎的程序結構中搜索到適當的位置. 在理論上說,這種定位方式非常靈活, 即可以是非常精準的定位到某個點,也可以是非常寬泛的定位到一組切入點. 但是, 這里的一個隱含假設是程序基礎結構本身已經具備了良好的,具有某種均一性的坐標系, 只有這樣我們才能夠擁有定位所需的基本信息. 想象一下,如果整個程序只有一個函數, 所有功能的實現通過傳入不同的參數值來實現, 則這樣的程序結構中是沒有什么可定位性而言的. 早期AOP定位所能夠依賴的坐標只有類,方法名稱, 方法參數類型等, 而這些信息本身又具有自己的業務含義,隨著業務的發展,它們本身的名稱也可能需要不斷的變化,這直接造成AOP所依賴的坐標系的不穩定性.今天還有效的位置描述, 明天也許就突然包括了某些不應該包含進來的程序位置或者排除了某些應在其中的位置. 在JDK5.0中補充的annotation機制為程序補充了新的坐標維度, 基于它無疑可以建立更加靈活而且專用的坐標系統, 它對于AOP的價值必然會逐漸被發掘出來. 在javascript這樣的動態語言中,雖然它們內置的動態性直接支持程序結構的動態組裝, 但是在定位支持方面卻要比java這樣的語言弱上很多, 在其上建立AOP應用未見得比java更具優勢. 從另外一個角度上說, 定位方式也并不總比占位方式優越. 我們需要牢牢記住"一次描述"的優勢在于可以"多次應用". 有的時候我們用很多唇舌去描述一個物品看起來像什么什么樣, 有多么大, 多么重, 還不如直接拿給人看, 說:嘿, 就是這個(this).同樣在程序中, 占位方式可能更加直接簡單,甚至因為代碼明確寫在那里,概念也更加明確,更加完整. 此外, 在一些特定的程序結構中, 需要定位的位置大大減少, 我們也不需要復雜的定位機制. 例如在witrix的jsplet框架中, 因為它特殊的規范一致性造成程序的處理點只有一個, 應用AOP是一個非常直接的過程.
? AOP的第二個組成部分是組裝技術. 程序結構的組裝在java中早已不是什么技術難點, 很多人干起這活來都是輕車熟路. 但是組裝不僅僅意味著程序結構的融合, 它同時意味著程序運行時狀態空間的融合. 在AOP的基礎模型中, 在切入點可以得到的變量有this指針,調用函數對象和傳入參數列表, 但是AOP本身并沒有進一步規范化這些變量的具體形式, 因此在一般情況下, 這些變量對于interceptor來說是只讀的, interceptor之間也無法通過這些變量交換信息并協同運行. 這實際上意味著在切點處inteceptor的狀態空間是極端受限的. 而當一個切面橫跨很多切點的時候, 在interceptor中一般只能對切點處狀態空間的共性部分進行操作, 這進一步限制了interceptor的能力.實際上目前AOP的主要應用都是無狀態的,或者是基于全局狀態空間的(例如transaction interceptor只訪問線程上下文), 這反映出對于AOP的primitive方式的應用的一種局限性. 在witrix平臺的BizFlow設計中,通過對狀態空間明確建模, 實現了基于AOP概念的一種新的應用方式.
? AOP需要對程序坐標空間和狀態空間的良好規劃, 才能保證無縫的織入, 保證信息交互通道的通暢.應用AOP所指的不僅僅是配置使用現有的AOP實現, 基于這種程序結構操控技術我們所需要做的抽象工作還很多.
?