KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > jboss > aspects > dbc > DesignByContractAspect


1 /*
2   * JBoss, Home of Professional Open Source
3   * Copyright 2005, JBoss Inc., and individual contributors as indicated
4   * by the @authors tag. See the copyright.txt in the distribution for a
5   * full listing of individual contributors.
6   *
7   * This is free software; you can redistribute it and/or modify it
8   * under the terms of the GNU Lesser General Public License as
9   * published by the Free Software Foundation; either version 2.1 of
10   * the License, or (at your option) any later version.
11   *
12   * This software is distributed in the hope that it will be useful,
13   * but WITHOUT ANY WARRANTY; without even the implied warranty of
14   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15   * Lesser General Public License for more details.
16   *
17   * You should have received a copy of the GNU Lesser General Public
18   * License along with this software; if not, write to the Free
19   * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
20   * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
21   */

22 package org.jboss.aspects.dbc;
23
24 import java.lang.reflect.Constructor JavaDoc;
25 import java.lang.reflect.Method JavaDoc;
26 import java.lang.reflect.Modifier JavaDoc;
27
28 import org.jboss.aop.joinpoint.ConstructorCalledByConstructorInvocation;
29 import org.jboss.aop.joinpoint.ConstructorCalledByMethodInvocation;
30 import org.jboss.aop.joinpoint.ConstructorInvocation;
31 import org.jboss.aop.joinpoint.Invocation;
32 import org.jboss.aop.joinpoint.MethodCalledByConstructorInvocation;
33 import org.jboss.aop.joinpoint.MethodCalledByMethodInvocation;
34 import org.jboss.aop.joinpoint.MethodInvocation;
35 import org.jboss.aspects.dbc.condition.ConstructorConditionManager;
36 import org.jboss.aspects.dbc.condition.ExecutableCondition;
37 import org.jboss.aspects.dbc.condition.InvariantCondition;
38 import org.jboss.aspects.dbc.condition.MethodConditionManager;
39
40 /**
41  * TODO:
42  * -Once version of beanshell in cvs allows importObject() (2.0, currently in beta),
43  * make invariants use that, so don't have to use $tgt for class invariants
44  * -Add $old funtionality
45  *
46  * @author <a HREF="mailto:kabir.khan@jboss.org">Kabir Khan</a>
47  * @version $Revision: 37406 $
48  */

49 public class DesignByContractAspect
50 {
51    public static boolean verbose;
52
53    ExecutableCondition[] preconditions;
54    ExecutableCondition[] postconditions;
55    InvariantCondition[] invariants;
56    
57    Method JavaDoc method;
58    Constructor JavaDoc constructor;
59    boolean isPublic;
60    boolean isStatic;
61    boolean isSynchronized;
62    
63    boolean initialised;
64    
65    //Keep track of if this checks have already been made for this joinpoint
66
//as the result of previous checks on the stack
67
ThreadLocal JavaDoc done = new ThreadLocal JavaDoc();
68    
69    public DesignByContractAspect()
70    {
71       done.set(Boolean.FALSE);
72    }
73    
74    public void setVerbose(boolean vbs)
75    {
76       verbose = vbs;
77    }
78    
79    public boolean getVerbose()
80    {
81       return verbose;
82    }
83    
84    public Object JavaDoc invoke(MethodInvocation invocation) throws Throwable JavaDoc
85    {
86       if (!initialised)
87       {
88          initialise(invocation.getMethod());
89       }
90       Object JavaDoc[] args = invocation.getArguments();
91       return invoke(invocation, args);
92    }
93
94    public Object JavaDoc invoke(MethodCalledByMethodInvocation invocation) throws Throwable JavaDoc
95    {
96       if (!initialised)
97       {
98          initialise(invocation.getCalledMethod());
99       }
100       Object JavaDoc[] args = invocation.getArguments();
101       return invoke(invocation, args);
102    }
103
104    public Object JavaDoc invoke(MethodCalledByConstructorInvocation invocation) throws Throwable JavaDoc
105    {
106       if (!initialised)
107       {
108          initialise(invocation.getCalledMethod());
109       }
110       Object JavaDoc[] args = invocation.getArguments();
111       return invoke(invocation, args);
112    }
113
114    public Object JavaDoc invoke(ConstructorInvocation invocation) throws Throwable JavaDoc
115    {
116       if (!initialised)
117       {
118          initialise(invocation.getConstructor());
119       }
120       Object JavaDoc[] args = invocation.getArguments();
121       return invoke(invocation, args);
122    }
123
124    public Object JavaDoc invoke(ConstructorCalledByMethodInvocation invocation) throws Throwable JavaDoc
125    {
126       if (!initialised)
127       {
128          initialise(invocation.getCalledConstructor());
129       }
130       Object JavaDoc[] args = invocation.getArguments();
131       return invoke(invocation, args);
132    }
133
134    public Object JavaDoc invoke(ConstructorCalledByConstructorInvocation invocation) throws Throwable JavaDoc
135    {
136       if (!initialised)
137       {
138          initialise(invocation.getCalledConstructor());
139       }
140       Object JavaDoc[] args = invocation.getArguments();
141       return invoke(invocation, args);
142    }
143
144
145    private Object JavaDoc invoke(Invocation invocation, Object JavaDoc[] args) throws Throwable JavaDoc
146    {
147       if (isSynchronized)
148       {
149          if (isStatic)
150          {
151             synchronized (method.getDeclaringClass())
152             {
153                return doInvoke(invocation, args);
154             }
155          }
156          else
157          {
158             synchronized (invocation.getTargetObject())
159             {
160                return doInvoke(invocation, args);
161             }
162          }
163       }
164       return doInvoke(invocation, args);
165    }
166
167    private Object JavaDoc doInvoke(Invocation invocation, Object JavaDoc[] args) throws Throwable JavaDoc
168    {
169       logStart();
170       Object JavaDoc ret = null;
171       boolean wasDone = ((Boolean JavaDoc)done.get()).booleanValue();
172
173       try
174       {
175          done.set(Boolean.TRUE);
176          if (!wasDone && isPublic && (constructor == null))
177          {
178             checkInvariants(invocation, null);
179          }
180          if (!wasDone)
181          {
182             checkPreConditions(invocation, args);
183          }
184             
185          ret = invocation.invokeNext();
186
187          if (!wasDone && isPublic)
188          {
189             checkInvariants(invocation, ret);
190             checkPostConditions(invocation, args, ret);
191          }
192       }
193       finally
194       {
195          if (!wasDone)
196          {
197             done.set(Boolean.FALSE);
198          }
199       }
200       
201       logEnd();
202       return ret;
203    }
204    
205    
206    private void logStart()
207    {
208       if (verbose)
209       {
210          if (method != null)
211          {
212             System.out.println("[dbc] ======= Invoking method: " + method);
213          }
214          else
215          {
216             System.out.println("[dbc] ======= Invoking constructor: " + constructor);
217          }
218       }
219    }
220    
221    private void logEnd()
222    {
223       if (verbose)
224       {
225          if (method != null)
226          {
227             System.out.println("[dbc] ======= Invoked method: " + method);
228          }
229          else
230          {
231             System.out.println("[dbc] ======= Invoked constructor: " + constructor);
232          }
233       }
234    }
235    
236    private void initialise(Method JavaDoc m)
237    {
238       method = m;
239       int modifiers = m.getModifiers();
240       initialise(modifiers);
241       
242       preconditions = MethodConditionManager.getPreConditions(m);
243       postconditions = MethodConditionManager.getPostConditions(m);
244       
245       if (isPublic)
246       {
247          invariants = MethodConditionManager.getInvariants(m);
248       }
249    }
250    
251    private void initialise(Constructor JavaDoc c)
252    {
253       constructor = c;
254       int modifiers = c.getModifiers();
255       initialise(modifiers);
256
257       preconditions = ConstructorConditionManager.getPreConditions(c);
258       postconditions = ConstructorConditionManager.getPostConditions(c);
259       
260       if (isPublic)
261       {
262          invariants = ConstructorConditionManager.getInvariants(c);
263       }
264    }
265    
266    private void initialise(int modifiers)
267    {
268       isSynchronized = Modifier.isSynchronized(modifiers);
269       isStatic = Modifier.isStatic(modifiers);
270       isPublic = Modifier.isPublic(modifiers);
271       
272       initialised = true;
273    }
274    
275    private void checkPreConditions(Invocation invocation, Object JavaDoc[] args)
276    {
277       if (verbose) System.out.println("[dbc] === checkPreconditions() for " + ((method != null) ? method.toString() : constructor.toString()));
278       for (int i = 0 ; i < preconditions.length ; i++)
279       {
280          preconditions[i].evaluateCondition(this, invocation, args, null);
281      }
282    }
283
284    private void checkPostConditions(Invocation invocation, Object JavaDoc[] args, Object JavaDoc ret)
285    {
286       if (verbose) System.out.println("[dbc] === checkPostconditions() for " + ((method != null) ? method.toString() : constructor.toString()));
287       for (int i = 0 ; i < postconditions.length ; i++)
288       {
289          postconditions[i].evaluateCondition(this, invocation, args, ret);
290       }
291    }
292
293    private void checkInvariants(Invocation invocation, Object JavaDoc ret)
294    {
295       if (verbose) System.out.println("[dbc] === checkInvariants() for " + ((method != null) ? method.toString() : constructor.toString()));
296       boolean isConstructor = (constructor != null);
297       for (int i = 0 ; i < invariants.length ; i++)
298       {
299          invariants[i].evaluateCondition(invocation, isStatic, isConstructor, ret);
300       }
301    }
302 }
303
Popular Tags