1/*
2 * Copyright (c) 2007, 2012, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.  Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26
27
28package com.sun.org.glassfish.gmbal ;
29
30import java.util.ResourceBundle ;
31
32import java.io.Closeable ;
33
34import java.lang.reflect.AnnotatedElement ;
35import java.lang.annotation.Annotation ;
36
37import javax.management.ObjectName ;
38import javax.management.MBeanServer ;
39
40/** An interface used to managed Open MBeans created from annotated
41 * objects.  This is mostly a facade over MBeanServer.
42 * Note that certain methods must be called in the correct order:
43 * <ol>
44 * <li> Methods suspendJMXRegistration, resumeJMXRegistration,
45 * getDomain, getMBeanServer, getResourceBundle, setRuntimeDebug,
46 * setRegistrationDebugLevel, setTypelibDebug, and close may be
47 * called at any time.
48 * <li> All calls to addAnnotation, stripPrefix, and
49 * stripPackageName must occur before any call to a createRoot method.
50 * <li>All of the register and registerAtRoot methods and unregister, getObject,
51 * getObjectName, and dumpSkeleton may only be called after
52 * a createRoot method is called.
53 * <li>Only one call to a createRoot method is permitted on any
54 * ManagedObjectManager.
55 * <li>A call to close returns the MOM to the pre-createRoot state.
56 * </ol>
57 * If these constraints are violated, an IllegalStateException is thrown.
58 */
59
60public interface ManagedObjectManager extends Closeable {
61    /** If called, no MBeans created after this call will be registered with
62     * the JMX MBeanServer until resumeJMXRegistration is called.  Each call
63     * increments a counter, so that nested and overlapping calls from multiple
64     * threads work correctly.
65         * May be called at any time.
66     */
67    void suspendJMXRegistration() ;
68
69    /** Decrements the suspend counter, if the counter is greater than 0.
70     * When the counter goes to zero, it causes all MBeans created since
71     * a previous call to suspendJMXRegistration incremented the counter from 0 to 1
72     * to be registered with the JMX MBeanServer.  After this call, all new
73     * MBean registration calls to the JMX MBeanServer happen within the
74     * register call.
75     * May be called at any time.
76     */
77    void resumeJMXRegistration() ;
78
79    /** Return true if object is assignment compatible with a class or interface
80     * that has an @ManagedObject annotation, otherwise false.  Only such objects
81     * may be registered to create MBeans.
82     * May be called at any time.
83     */
84    boolean isManagedObject( Object obj ) ;
85
86    /** Create a default root MBean.
87     * One of the createRoot methods must be called before any of the registration
88     * methods may be called.
89     * Only one call to a createRoot method is permitted after an
90     * ManagedObjectManager is created.
91     * @exception IllegalStateException if called after a call to any
92     * createRoot method.
93     * @return A default root MBean which supports only the AMX attributes.
94     */
95    GmbalMBean createRoot() ;
96
97    /** Create a root MBean from root, which much have a method with the
98     * @NameValue annotation.
99     * One of the createRoot methods must be called before any of the registration
100     * methods may be called.
101     * Only one call to createRoot is permitted after an ManagedObjectManager
102     * is created.
103     * @param root The Java object to be used to construct the root.
104     * @exception IllegalStateException if called after a call to any
105     * createRoot method.
106     * @return The newly constructed MBean.
107     */
108    GmbalMBean createRoot( Object root ) ;
109
110    /** Create a root MBean from root with the given name.
111     * One of the createRoot methods must be called before any of the registration
112     * methods may be called.
113     * Only one call to createRoot is permitted after an ManagedObjectManager
114     * is created.
115     * @param root The Java object to be used to construct the root.
116     * @param name The ObjectName name field to be used in the ObjectName of
117     * the MBean constructed from root.
118     * @exception IllegalStateException if called after a call to any
119     * createRoot method.
120     * @return The newly constructed MBean.
121     */
122    GmbalMBean createRoot( Object root, String name ) ;
123
124    /** Return the root of this ManagedObjectManager.
125     * May be called at any time.
126     * @return the root constructed in a createRoot operation, or null if called
127     * before a createRoot call.
128     */
129    Object getRoot() ;
130
131    /** Construct an Open Mean for obj according to its annotations,
132     * and register it with domain getDomain() and the appropriate
133     * ObjectName.  The MBeanServer from setMBeanServer (or its default) is used.
134     * Here parent is considered to contain obj, and this containment is
135     * represented by the construction of the ObjectName following the AMX
136     * specification for ObjectNames.
137     * <p>
138     * The MBeanInfo for the result is actually ModelMBeanInfo, and may contain
139     * extra metadata as defined using annotations defined with the
140     * @DescriptorKey and @DescriptorField meta-annotations.
141     * <p>
142     * Must be called after a successful createRoot call.
143     * <p>
144     * This version of register should not be used to register singletons.
145     * </ol>
146     * @param parent The parent object that contains obj.
147     * @param obj The managed object we are registering.
148     * @param name The name to use for registering this object.
149     * @return The MBean constructed from obj.
150     * @exception IllegalStateException if called before a createRoot method is
151     * called successfully.
152     */
153    GmbalMBean register( Object parent, Object obj, String name ) ;
154
155    /** Same as register( parent, obj, name ), but here the name
156     * is derived from an @NameValue annotation.
157     * <p>
158     * This version of register should also be used to register singletons.
159     *
160     * @param parent The parent object that contains obj.
161     * @param obj The managed object we are registering.
162     * @return The MBean constructed from obj.
163     * @exception IllegalStateException if called before a createRoot method is
164     * called successfully.
165     */
166    GmbalMBean register( Object parent, Object obj ) ;
167
168    /** Registers the MBean for obj at the root MBean for the ObjectManager,
169     * using the given name.  Exactly the same as mom.register( mom.getRoot(),
170     * obj, name ).
171     * <p>
172     * Must be called after a successful createRoot call.
173     * <p>
174     * This version of register should not be used to register singletons.
175     * @param obj The object for which we construct and register an MBean.
176     * @param name The name of the MBean.
177     * @return The MBean constructed from obj.
178     * @exception IllegalStateException if called before a createRoot method is
179     * called successfully.
180     */
181    GmbalMBean registerAtRoot( Object obj, String name ) ;
182
183    /** Same as registerAtRoot( Object, String ), but here the name
184     * is derived from an @ObjectKeyName annotation.  Exactly the same as
185     * mom.register( mom.getRoot(), obj ).
186     * <p>
187     * This version of register should also be used to register singletons.
188     * @param obj The managed object we are registering.
189     * @return The MBean constructed from obj.
190     * @exception IllegalStateException if called before a createRoot method is
191     * called successfully.
192     */
193    GmbalMBean registerAtRoot( Object obj ) ;
194
195
196    /** Unregister the Open MBean corresponding to obj from the
197     * mbean server.
198     * <p>
199     * Must be called after a successful createRoot call.
200     * @param obj The object originally passed to a register method.
201     */
202    void unregister( Object obj ) ;
203
204    /** Get the ObjectName for the given object (which must have
205     * been registered via a register call).
206     * <p>
207     * Must be called after a successful createRoot call.
208     * @param obj The object originally passed to a register call.
209     * @return The ObjectName used to register the MBean.
210     */
211    ObjectName getObjectName( Object obj ) ;
212
213    /** Get an AMXClient instance for the object obj, if obj is registered
214     * as an MBean in this mom.
215     * <p>
216     * Must be called after a successful createRoot call.
217     * @param obj The object corresponding to an MBean.
218     * @return An AMXClient that acts as a proxy for this MBean.
219     */
220    AMXClient getAMXClient( Object obj ) ;
221
222    /** Get the Object that was registered with the given ObjectName.
223     * Note that getObject and getObjectName are inverse operations.
224     * <p>
225     * Must be called after a successful createRoot call.
226     * @param oname The ObjectName used to register the object.
227     * @return The Object passed to the register call.
228     */
229    Object getObject( ObjectName oname ) ;
230
231    /** Add a type prefix to strip from type names, to shorten the names for
232     * a better presentation to the user.  This may only be called before a
233     * createRot method is called.
234     *
235     * @param str Class package name to strip from type name.
236     * @exception IllegalStateException if called after createRoot method.
237     */
238    void stripPrefix( String... str ) ;
239
240    /** Change the default type name algorithm so that if nothing else
241     * applies, the entire package prefix is stripped form the Class name.
242     * Otherwise, the full Class name is the type.
243     *
244     * @exception IllegalStateException if called after a createRoot method.
245     */
246    void stripPackagePrefix() ;
247
248    /** Return the domain name that was used when this ManagedObjectManager
249     * was created.  This is the JMX domain that will be used in all ObjectNames
250     * created by this ManagedObjectManager.
251     * <p>
252     * May be called at any time.
253     * @return Get the domain name for this ManagedObjectManager.
254     */
255    String getDomain() ;
256
257    /** Set the MBeanServer to which all MBeans using this interface
258     * are published.  The default value is
259     * java.lang.management.ManagementFactory.getPlatformMBeanServer().
260     * <p>
261     * Must be called before a successful createRoot call.
262     * @param server The MBeanServer to set as the MBeanServer for this
263     * ManagedObjectManager.
264     */
265    void setMBeanServer( MBeanServer server ) ;
266
267    /** Get the current MBeanServer.
268     * <p>
269     * May be called at any time.
270     * @return The current MBeanServer, either the default, or the value passed
271     * to setMBeanServer.
272     */
273    MBeanServer getMBeanServer() ;
274
275    /** Set the ResourceBundle to use for getting localized descriptions.
276     * If not set, the description is the value in the annotation.
277     * <p>
278     * Must be called before a successful call to a createRoot method.
279     * @param rb The resource bundle to use.  May be null.
280     */
281    void setResourceBundle( ResourceBundle rb ) ;
282
283    /** Get the resource bundle (if any) set by setResourceBundle.
284     * <p>
285     * May be called at any time.
286     * @return The resource bundle set by setResourceBundle: may be null.
287     */
288    ResourceBundle getResourceBundle() ;
289
290    /** Method to add an annotation to an element that cannot be modified.
291     * This is typically needed when dealing with an implementation of an
292     * interface that is part of a standardized API, and so the interface
293     * cannot be annotated by modifiying the source code.  In some cases the
294     * implementation of the interface also cannot be inherited, because the
295     * implementation is generated by a standardized code generator.  Another
296     * possibility is that there are several different implementations of the
297     * standardized interface, and it is undesirable to annotate each
298     * implementation with @InheritedAttributes.
299     * @param element The annotated element (class or method for our purposes).
300     * @param annotation The annotation we wish to add to the element.
301     * @exception IllegalStateException if called after a call to a createRoot
302     * method.
303     */
304    void addAnnotation( AnnotatedElement element, Annotation annotation ) ;
305
306    /** DebugLevel used to control how much debug info is printed for
307     * registration of objects.
308     */
309    public enum RegistrationDebugLevel { NONE, NORMAL, FINE } ;
310
311    /** Print debug output to System.out.
312     * <p>
313     * May be called at any time.
314     *
315     * @param level NONE is no debugging at all, NORMAL traces high-level
316     * construction of skeletons and type converters, and dumps results of new
317     * skeletons and type converters, FINE traces everything in great detail.
318     * The tracing is done with INFO-level logger calls.  The logger name is
319     * that package name (com.sun.org.glassfish.gmbal.impl).
320     */
321    void setRegistrationDebug( RegistrationDebugLevel level ) ;
322
323    /** Enable generation of debug log at INFO level for runtime MBean operations
324     * to the com.sun.org.glassfish.gmbal.impl logger.
325     * <p>
326     * May be called at any time.
327     *
328     * @param flag true to enable runtime debug, false to disable.
329     */
330    void setRuntimeDebug( boolean flag ) ;
331
332    /** Enabled generation of debug log for type evaluator debugging.  This
333     * happens as part of the registration process for the first time a particular
334     * class is processed.
335     * <p>
336     * May be called at any time.
337     *
338     * @param level set to 1 to just see the results of the TypeEvaluator, >1 to
339     * see lots of details.  WARNING: values >1 will result in a large amount
340     * of output.
341     */
342    void setTypelibDebug( int level ) ;
343
344    /** Set debugging for JMX registrations.  If true, all registrations and
345     * deregistrations with the MBeanServer are traced.
346     *
347     * @param flag True to enalbed registration tracing.
348     */
349    void setJMXRegistrationDebug( boolean flag ) ;
350
351    /** Dump the skeleton used in the implementation of the MBean for obj.
352     * Obj must be currently registered.
353     * <p>
354     * Must be called after a successful call to a createRoot method.
355     *
356     * @param obj The registered object whose skeleton should be displayed.
357     * @return The string representation of the skeleton.
358     */
359    String dumpSkeleton( Object obj ) ;
360
361    /** Suppress reporting of a duplicate root name.  If this option is enabled,
362     * createRoot( Object ) and createRoot( Object, String ) will return null
363     * for a duplicate root name, otherwise a Gmbal error will be reported.
364     * Note that this applies ONLY to createRoot: the register methods are
365     * unaffected.  Also note that any other errors that might occur on
366     * createRoot will be reported normally.
367     * <p>
368     * Must be called before a successful call to a createRoot method.
369     */
370    void suppressDuplicateRootReport( boolean suppressReport ) ;
371}
372