KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > commons > modeler > mbeans > SimpleRemoteConnector


1 /*
2  * Copyright 1999,2004 The Apache Software Foundation.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16 package org.apache.commons.modeler.mbeans;
17
18 import java.io.IOException JavaDoc;
19 import java.io.InputStream JavaDoc;
20 import java.net.URL JavaDoc;
21 import java.net.URLConnection JavaDoc;
22 import java.util.HashMap JavaDoc;
23 import java.util.Iterator JavaDoc;
24 import java.util.Map JavaDoc;
25 import java.util.jar.Attributes JavaDoc;
26 import java.util.jar.Manifest JavaDoc;
27
28 import javax.management.Attribute JavaDoc;
29 import javax.management.AttributeNotFoundException JavaDoc;
30 import javax.management.MBeanException JavaDoc;
31 import javax.management.MBeanServer JavaDoc;
32 import javax.management.ObjectName JavaDoc;
33 import javax.management.ReflectionException JavaDoc;
34
35 import org.apache.commons.logging.Log;
36 import org.apache.commons.logging.LogFactory;
37 import org.apache.commons.modeler.Registry;
38
39 /**
40  * Based on jk2 proxy.
41  *
42  * Proxy using a very simple HTTP based protocol.
43  *
44  * For efficiency, it'll get bulk results and cache them - you
45  * can force an update by calling the refreshAttributes and refreshMetadata
46  * operations on this mbean.
47  *
48  * TODO: implement the user/pass auth ( right now you must use IP based security )
49  * TODO: eventually support https
50  * TODO: support for metadata ( mbean-descriptors ) for description and type conversions
51  * TODO: filter out trivial components ( mutexes, etc )
52  *
53  * @author Costin Manolache
54  */

55 public class SimpleRemoteConnector
56 {
57     private static Log log = LogFactory.getLog(SimpleRemoteConnector.class);
58
59     // HTTP port of the remote JMX
60
String JavaDoc webServerHost="localhost";
61     int webServerPort=8080;
62
63     // URL of the remote JMX servlet ( or equivalent )
64
String JavaDoc statusPath="/jkstatus";
65
66     // Not used right now
67
String JavaDoc user;
68     String JavaDoc pass;
69
70     // Domain we mirror
71
String JavaDoc domain;
72
73     // XXX Not used - allow translations
74
String JavaDoc localDomain;
75     String JavaDoc filter;
76
77     //
78
long lastRefresh=0;
79     long updateInterval=5000; // 5 sec - it's min time between updates
80

81     String JavaDoc prefix="";
82
83     Registry reg;
84
85     MBeanServer JavaDoc mserver;
86
87     // Last view
88
HashMap JavaDoc mbeans=new HashMap JavaDoc();
89
90     public SimpleRemoteConnector()
91     {
92     }
93
94     /* -------------------- Public methods -------------------- */
95
96     public String JavaDoc getWebServerHost() {
97         return webServerHost;
98     }
99
100     public void setWebServerHost(String JavaDoc webServerHost) {
101         this.webServerHost = webServerHost;
102     }
103
104     public int getWebServerPort() {
105         return webServerPort;
106     }
107
108     public void setWebServerPort(int webServerPort) {
109         this.webServerPort = webServerPort;
110     }
111
112     public long getUpdateInterval() {
113         return updateInterval;
114     }
115
116     public void setUpdateInterval(long updateInterval) {
117         this.updateInterval = updateInterval;
118     }
119
120     public String JavaDoc getUser() {
121         return user;
122     }
123
124     public void setUser(String JavaDoc user) {
125         this.user = user;
126     }
127
128     public String JavaDoc getPass() {
129         return pass;
130     }
131
132     public String JavaDoc getDomain() {
133         return domain;
134     }
135
136     public void setDomain(String JavaDoc domain) {
137         this.domain = domain;
138     }
139
140     public void setPass(String JavaDoc pass) {
141         this.pass = pass;
142     }
143
144     public String JavaDoc getStatusPath() {
145         return statusPath;
146     }
147
148     public void setStatusPath(String JavaDoc statusPath) {
149         this.statusPath = statusPath;
150     }
151
152     public String JavaDoc getFilter() {
153         return filter;
154     }
155
156     public void setFilter(String JavaDoc filter) {
157         this.filter = filter;
158     }
159
160     /* ==================== Start/stop ==================== */
161
162     public void destroy() {
163         try {
164             // We should keep track of loaded beans and call stop.
165
// Modeler should do it...
166
Iterator JavaDoc mbeansIt=mbeans.values().iterator();
167             while( mbeansIt.hasNext()) {
168                 MBeanProxy proxy=(MBeanProxy)mbeansIt.next();
169                 ObjectName JavaDoc oname=proxy.getJmxName();
170                 Registry.getRegistry().getMBeanServer().unregisterMBean(oname);
171             }
172         } catch( Throwable JavaDoc t ) {
173             log.error( "Destroy error", t );
174         }
175     }
176
177     public void init() throws IOException JavaDoc {
178         try {
179             //if( log.isDebugEnabled() )
180
log.info("init " + webServerHost + " " + webServerPort);
181             reg=Registry.getRegistry();
182             // Get metadata for all mbeans on the remote side
183
//refreshMetadata();
184
// Get current values and mbeans
185
refreshAttributes();
186         } catch( Throwable JavaDoc t ) {
187             log.error( "Init error", t );
188         }
189     }
190
191     public void start() throws IOException JavaDoc {
192         System.out.println("XXX start");
193         if( reg==null)
194             init();
195     }
196
197     /** Refresh the proxies, if updateInterval passed
198      *
199      */

200     public void refresh() {
201         long time=System.currentTimeMillis();
202         if( time - lastRefresh < updateInterval ) {
203             return;
204         }
205         System.out.println("refresh... ");
206         lastRefresh=time;
207         //refreshMetadata();
208
refreshAttributes();
209     }
210
211     public void refreshAttributes() {
212         try {
213             int cnt=0;
214             // connect to apache, get a list of mbeans
215
if( filter==null ) {
216                 filter=domain + ":*";
217             }
218
219             InputStream JavaDoc is=getStream( "qry=" + filter);
220             if( is==null ) return;
221
222             Manifest JavaDoc mf=new Manifest JavaDoc(is);
223             
224             HashMap JavaDoc currentObjects=new HashMap JavaDoc(); // used to remove older ones
225
Map JavaDoc entries=mf.getEntries();
226             Iterator JavaDoc it=entries.keySet().iterator();
227             while( it.hasNext() ) {
228                 String JavaDoc name=(String JavaDoc)it.next();
229                 Attributes JavaDoc attrs=(Attributes JavaDoc)entries.get( name );
230
231                 ObjectName JavaDoc oname=new ObjectName JavaDoc(name);
232                 currentObjects.put( oname, "");
233                 MBeanProxy proxy=(MBeanProxy)mbeans.get(oname);
234                 if( proxy==null ) {
235                     log.debug( "New object " + name);
236                     String JavaDoc code=attrs.getValue("modelerType");
237                     if(log.isDebugEnabled())
238                         log.debug("Register " + name + " " + code );
239
240                     proxy= new MBeanProxy(this, code);
241                     mbeans.put( oname, proxy );
242
243                     // Register
244
MBeanServer JavaDoc mserver=Registry.getRegistry().getMBeanServer();
245                     if( ! mserver.isRegistered(oname ) ) {
246                         mserver.registerMBean(proxy, oname);
247                     }
248                 }
249                 Iterator JavaDoc it2=attrs.keySet().iterator();
250                 while( it2.hasNext() ) {
251                     Object JavaDoc o=it2.next();
252                     String JavaDoc att=(o==null) ? null : o.toString();
253                     if( "modelerType".equals( att )) continue;
254                     String JavaDoc val=attrs.getValue(att);
255                     proxy.update(att, val);
256                     cnt++;
257                 }
258             }
259             
260             // Now we have to remove all the mbeans that are no longer there
261
Iterator JavaDoc existingIt=mbeans.keySet().iterator();
262             while( existingIt.hasNext() ) {
263                 ObjectName JavaDoc on=(ObjectName JavaDoc)existingIt.next();
264                 if(currentObjects.get( on ) != null )
265                     continue; // still alive
266
if( log.isDebugEnabled() )
267                     log.debug("No longer alive " + on);
268                 try {
269                     mserver.unregisterMBean(on);
270                 } catch( Throwable JavaDoc t ) {
271                     log.info("Error unregistering " + on + " " + t.toString());
272                 }
273             }
274             
275             log.info( "Refreshing attributes " + cnt);
276         } catch( Exception JavaDoc ex ) {
277             log.info("Error ", ex);
278         }
279     }
280
281     // Not used right now - assume the metadata is available locally
282
// Could use mbeans-descriptors.xml or other formats.
283
// Will be called if code= is not found locally
284
public void refreshMetadata() {
285         try {
286             int cnt=0;
287             int newCnt=0;
288             InputStream JavaDoc is=getStream("getMetadata=" + domain + ":*");
289             if( is==null ) return;
290
291             log.info( "Refreshing metadata " + cnt + " " + newCnt);
292         } catch( Exception JavaDoc ex ) {
293             log.info("Error ", ex);
294         }
295     }
296
297     public Object JavaDoc invoke(Object JavaDoc oname, String JavaDoc name, Object JavaDoc params[], String JavaDoc signature[])
298         throws MBeanException JavaDoc, ReflectionException JavaDoc {
299         try {
300             // we support only string values
301
InputStream JavaDoc is=this.getStream("invoke=" + name + "&name=" + oname.toString() );
302             if( is==null ) return null;
303 // String res=is.readLine();
304
// if( log.isDebugEnabled())
305
// log.debug( "Invoking " + jkName + " " + name + " result " + res);
306

307             //this.refreshMetadata();
308
this.refreshAttributes();
309         } catch( Exception JavaDoc ex ) {
310             throw new MBeanException JavaDoc(ex);
311         }
312         return null;
313     }
314
315
316     public void setAttribute(ObjectName JavaDoc oname, Attribute JavaDoc attribute)
317         throws AttributeNotFoundException JavaDoc, MBeanException JavaDoc,
318         ReflectionException JavaDoc
319     {
320         try {
321             // we support only string values
322
String JavaDoc val=(String JavaDoc)attribute.getValue();
323             String JavaDoc name=attribute.getName();
324             InputStream JavaDoc is=this.getStream("set=" + name + "&name=" + oname.toString()
325                     + "&value=" + val);
326             if( is==null ) return;
327 // String res=is.readLine();
328
// if( log.isDebugEnabled())
329
// log.debug( "Setting " + jkName + " " + name + " result " + res);
330

331             //this.refreshMetadata();
332
this.refreshAttributes();
333         } catch( Exception JavaDoc ex ) {
334             throw new MBeanException JavaDoc(ex);
335         }
336     }
337
338     /** connect to apache using http, get a list of mbeans. Can be
339      * overriten to support different protocols ( jk/Unix domain sockets, etc )
340       */

341     protected InputStream JavaDoc getStream(String JavaDoc qry) throws Exception JavaDoc {
342         try {
343             String JavaDoc path=statusPath + "?" + qry;
344             URL JavaDoc url=new URL JavaDoc( "http", webServerHost, webServerPort, path);
345             log.debug( "Connecting to " + url);
346             URLConnection JavaDoc urlc=url.openConnection();
347             InputStream JavaDoc is=urlc.getInputStream();
348             return is;
349         } catch (IOException JavaDoc e) {
350             log.info( "Can't connect to jkstatus " + webServerHost + ":" + webServerPort
351             + " " + e.toString());
352             return null;
353         }
354     }
355
356
357 }
358
359
Popular Tags