Class: Seasar::Aop::S2AopFactory
- Inherits:
-
Object
- Object
- Seasar::Aop::S2AopFactory
- Defined in:
- lib/seasar/aop/s2aop-factory.rb
Overview
アスペクトを適用したクラスを生成するファクトリクラスです。
Constant Summary collapse
- @@index =
0
- @@mutex =
::Mutex.new
Class Method Summary collapse
-
.creat_method_interceptors_map(component_class, aspects) ⇒ Object
クラスの各メソッドに適用するアスペクトを分類します。.
-
.create(component_class, aspects) ⇒ Object
クラスにアスペクトを適用します。.
-
.generate_enhanced_class(component_class) ⇒ Object
元のクラスを継承した新規クラスを返します。 新規クラスの名前には、「EnhancedByS2Aop###」が付加されます。.
-
.weave_aspect(component_class, enhanced_class, method_name, interceptors) ⇒ Object
メソッドにアスペクトを織り込みます。(メソッドをinvokeクロージャで置き換えます).
Class Method Details
.creat_method_interceptors_map(component_class, aspects) ⇒ Object
クラスの各メソッドに適用するアスペクトを分類します。
-
args
-
Class component_class
-
Array aspects
-
-
return
-
Hash
-
82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 |
# File 'lib/seasar/aop/s2aop-factory.rb', line 82 def creat_method_interceptors_map(component_class, aspects) methods = Seasar::Util::ClassUtil.get_aspectable_methods(component_class) method_interceptors_map = {} methods.each {|method_name| interceptors = [] aspects.each {|aspect| if aspect.pointcut.applicable?(method_name) interceptors << aspect.interceptor end } if 0 < interceptors.length method_interceptors_map[method_name] = interceptors end } return method_interceptors_map end |
.create(component_class, aspects) ⇒ Object
クラスにアスペクトを適用します。
-
args
-
Class component_class
-
Array aspects
-
-
return
-
Class
-
38 39 40 41 42 43 44 45 |
# File 'lib/seasar/aop/s2aop-factory.rb', line 38 def create(component_class, aspects) enhanced_class = S2AopFactory.generate_enhanced_class(component_class) method_interceptors_map = S2AopFactory.creat_method_interceptors_map(component_class, aspects) method_interceptors_map.each {|method_name, interceptors| S2AopFactory.weave_aspect(component_class, enhanced_class, method_name, interceptors) } return enhanced_class end |
.generate_enhanced_class(component_class) ⇒ Object
元のクラスを継承した新規クラスを返します。新規クラスの名前には、「EnhancedByS2Aop###」が付加されます。
-
args
-
Class component_class
-
-
return
-
Class
-
55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 |
# File 'lib/seasar/aop/s2aop-factory.rb', line 55 def generate_enhanced_class(component_class) #return Class.new(component_class) consts = component_class.name.split(/::/) enhanced_class_name = nil @@mutex.synchronize { enhanced_class_name = consts.pop + '_EnhancedByS2Aop_' + @@index.to_s @@index += 1 } if consts.size == 0 namespace = Object else namespace = eval(consts.join('::')) end clazz = Class.new(component_class) # TODO: should throw exception? if contant has already defined in the namespace(module) namespace.const_set(enhanced_class_name, clazz) unless namespace.const_defined?(enhanced_class_name) return clazz end |
.weave_aspect(component_class, enhanced_class, method_name, interceptors) ⇒ Object
メソッドにアスペクトを織り込みます。(メソッドをinvokeクロージャで置き換えます)
-
args
-
Class component_class
-
Class enhanced_class
-
String|Symbol method_name
-
Array interceptors
-
-
return
-
none
-
109 110 111 112 113 114 115 116 117 118 119 120 121 |
# File 'lib/seasar/aop/s2aop-factory.rb', line 109 def weave_aspect(component_class, enhanced_class, method_name, interceptors) enhanced_class.__send__(:define_method, method_name) {|*args, &procedure| invoker = MethodInvocation.new invoker.method = component_class.instance_method(method_name).bind(self) invoker.interceptors = interceptors invoker.enhanced_class = enhanced_class invoker.component_class = component_class invoker.args = args invoker.procedure = procedure invoker.this = self return invoker.proceed } end |