KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > oddjob > framework > ServiceWrapper


1 /*
2  * Copyright (c) 2005, Rob Gordon.
3  */

4 package org.oddjob.framework;
5
6 import java.io.IOException JavaDoc;
7 import java.io.ObjectInputStream JavaDoc;
8 import java.io.ObjectOutputStream JavaDoc;
9 import java.io.Serializable JavaDoc;
10 import java.lang.reflect.InvocationHandler JavaDoc;
11 import java.lang.reflect.Method JavaDoc;
12 import java.lang.reflect.Proxy JavaDoc;
13 import java.util.Arrays JavaDoc;
14 import java.util.HashMap JavaDoc;
15 import java.util.HashSet JavaDoc;
16 import java.util.Map JavaDoc;
17 import java.util.Set JavaDoc;
18
19 import org.apache.commons.beanutils.DynaBean;
20 import org.apache.log4j.MDC;
21 import org.oddjob.Iconic;
22 import org.oddjob.Resetable;
23 import org.oddjob.Stateful;
24 import org.oddjob.Stoppable;
25 import org.oddjob.images.IconHelper;
26 import org.oddjob.logging.Log4jArchiver;
27 import org.oddjob.logging.LogEnabled;
28 import org.oddjob.state.JobStateHandler;
29
30 /**
31  * Wraps a Runnable object and adds state to it.
32  * <p>
33  * This is a helper class for parent jobs which depend on their
34  * child being Stateful - this pretends an un Stateful Runnable
35  * is Statful thus allowing the parent to accept plain Runnables
36  * as children.
37  *
38  * @author Rob Gordon.
39  */

40 public class ServiceWrapper extends BaseWrapper
41 implements InvocationHandler JavaDoc {
42     
43     private Service service;
44     
45     private Object JavaDoc wrapped;
46     private transient DynaBean dynaBean;
47     
48     private transient Map JavaDoc methods;
49     
50     private Object JavaDoc proxy;
51     
52     protected ServiceWrapper() { }
53     
54     private ServiceWrapper(Service service) {
55        setWrapped(service);
56     }
57     
58     public static Runnable JavaDoc wrapperFor(Service service) {
59         ServiceWrapper wrapper = new ServiceWrapper(service);
60         Set JavaDoc interfaces = new HashSet JavaDoc();
61         interfaces.addAll(Arrays.asList(interfacesFor(service.getComponent())));
62         interfaces.add(Runnable JavaDoc.class);
63         interfaces.add(Stateful.class);
64         interfaces.add(Resetable.class);
65         interfaces.add(DynaBean.class);
66         interfaces.add(Stoppable.class);
67         interfaces.add(Iconic.class);
68         interfaces.add(LogEnabled.class);
69         interfaces.add(ContextAware.class);
70         interfaces.add(Initializable.class);
71         interfaces.add(Destroyable.class);
72         if (!(service instanceof Serializable JavaDoc)) {
73             interfaces.add(Transient.class);
74         }
75         wrapper.proxy =
76             Proxy.newProxyInstance(Thread.currentThread().getContextClassLoader(),
77                 (Class JavaDoc[]) interfaces.toArray(new Class JavaDoc[0]),
78                 wrapper);
79         
80         wrapper.stateHandler = new JobStateHandler(wrapper.proxy);
81         wrapper.iconHelper = new IconHelper(wrapper.proxy);
82         
83         return (Runnable JavaDoc) wrapper.proxy;
84     }
85     
86     public Object JavaDoc invoke(Object JavaDoc proxy, Method JavaDoc method, Object JavaDoc[] args) throws Throwable JavaDoc {
87         Object JavaDoc destination = methods.get(method);
88         if (destination == null) {
89             // hashCode etc
90
destination = this;
91         }
92         return method.invoke(destination, args);
93     }
94     
95     protected Object JavaDoc getWrapped() {
96         return wrapped;
97     }
98
99     protected DynaBean getDynaBean() {
100         return dynaBean;
101     }
102
103     protected Object JavaDoc getProxy() {
104         return proxy;
105     }
106
107     protected void setWrapped(Service service) {
108         this.service = service;
109         this.wrapped = service.getComponent();
110         this.dynaBean = new WrapDynaBean(wrapped);
111         this.methods = new HashMap JavaDoc();
112         
113         Class JavaDoc[] interfaces = interfacesFor(wrapped);
114         for (int i = 0; i < interfaces.length; ++i) {
115             addMethods(interfaces[i], wrapped);
116         }
117         addMethods(Stateful.class, this);
118         addMethods(Resetable.class, this);
119         addMethods(DynaBean.class, this);
120         addMethods(Stoppable.class, this);
121         addMethods(Iconic.class, this);
122         addMethods(Runnable JavaDoc.class, this);
123         addMethods(LogEnabled.class, this);
124         addMethods(ContextAware.class, this);
125         addMethods(Initializable.class, this);
126         addMethods(Destroyable.class, this);
127     }
128     
129     private void addMethods(Class JavaDoc from, Object JavaDoc destination) {
130         Method JavaDoc[] ms = from.getDeclaredMethods();
131         for (int i = 0; i < ms.length; ++i) {
132             methods.put(ms[i], destination);
133         }
134     }
135     
136     public void run() {
137         lock.accquire("Job executing.");
138         String JavaDoc oldMDC = (String JavaDoc)MDC.get(Log4jArchiver.MDC);
139         try {
140             MDC.put(Log4jArchiver.MDC, getLogger());
141             if (!stateHandler.requestJobStateExecuting()) {
142                 logger().debug("Can't execute job [" + this + "] because state is ["
143                         + stateHandler.getJobState() + "]");
144                 return;
145             }
146             iconHelper.changeIcon(IconHelper.EXECUTING);
147
148             // runtime configuration.
149
if (!configure()) {
150                 return;
151             }
152             logger().info("Starting service[" + wrapped + "]");
153             
154             service.start();
155
156             logger().info("Started service [" + wrapped + "]");
157         } catch (Throwable JavaDoc t) {
158             logger().warn("Exception starting [" + wrapped + "]", t);
159             setJobStateException(t);
160         }
161         finally {
162             if (oldMDC != null) {
163                 MDC.put(Log4jArchiver.MDC, oldMDC);
164             }
165             else {
166                 MDC.remove(Log4jArchiver.MDC);
167             }
168             lock.release();
169         }
170     }
171         
172     public void onStop() throws RuntimeException JavaDoc {
173         lock.accquire("Job executing.");
174         String JavaDoc oldMDC = (String JavaDoc)MDC.get(Log4jArchiver.MDC);
175         try {
176             MDC.put(Log4jArchiver.MDC, getLogger());
177             service.stop();
178             int result = getResult();
179             if (result == 0) {
180                 setJobStateComplete();
181             } else {
182                 setJobStateNotComplete();
183             }
184         } catch (Exception JavaDoc e) {
185             throw new RuntimeException JavaDoc(e);
186         }
187         finally {
188             if (oldMDC != null) {
189                 MDC.put(Log4jArchiver.MDC, oldMDC);
190             }
191             else {
192                 MDC.remove(Log4jArchiver.MDC);
193             }
194             lock.release();
195         }
196     }
197
198     /**
199      * Custom serialsation.
200      */

201     private void writeObject(ObjectOutputStream JavaDoc s)
202     throws IOException JavaDoc {
203         if (destroyed) {
204             throw new IllegalStateException JavaDoc("[" + this + "] destroyed");
205         }
206         s.defaultWriteObject();
207         s.writeObject((Serializable JavaDoc) getWrapped());
208         s.writeObject(stateHandler);
209         s.writeObject(iconHelper);
210     }
211
212     /**
213      * Custom serialisation.
214      */

215     private void readObject(ObjectInputStream JavaDoc s)
216     throws IOException JavaDoc, ClassNotFoundException JavaDoc {
217         s.defaultReadObject();
218         Object JavaDoc wrapped = s.readObject();
219         Service service = Service.serviceFor(wrapped);
220         setWrapped(service);
221         stateHandler = (JobStateHandler) s.readObject();
222         stateHandler.setSource(proxy);
223         iconHelper = (IconHelper) s.readObject();
224         iconHelper.setSource(proxy);
225     }
226     
227 }
228
Popular Tags