Revise reference documentation for Spring JMX annotations
This commit revises the reference documentation for Spring JMX
annotations for various reasons including, but not limited to, the
following.
- Type names such as ManagedResource are often ambiguous, especially
when discussing an annotation like @ManagedResource instead of
org.springframework.jmx.export.metadata.ManagedResource which is a
class.
- AnnotationTestBean implements IJmxTestBean, even though an annotated
MBean is not required to implement any interfaces, and in fact the
example is meant to demonstrate that an annotated POJO suffices.
- @ManagedOperationParameter annotations are unnecessarily declared in
the @ManagedOperationParameters container.
- The documentation sometimes refers to JmxTestBean when it should
instead refer to AnnotationTestBean.
- Inconsistent and confusing wording for annotation attributes,
properties, managed attributes, etc.
- The tables refer to "source-level metadata types/parameters" when
they should refer to Spring JMX annotations and their attributes.
- The annotation and attribute tables have inconsistent ordering and
naming for column headers.
- @ManagedNotification and @ManagedMetric are not mentioned.
- The AutodetectCapableMBeanInfoAssembler example is broken since it
uses the non-annotated JmxTestBean instead of the AnnotationTestBean.
As a side note, the JmxTestBean in our test suite still contains
XDoclet "annotations" which can be safely removed. 😉
Closes gh-33466
This commit is contained in:
parent
6e640f0800
commit
1af6480217
|
@ -11,10 +11,10 @@ controlling the management interfaces of your beans.
|
||||||
|
|
||||||
|
|
||||||
[[jmx-interface-assembler]]
|
[[jmx-interface-assembler]]
|
||||||
== Using the `MBeanInfoAssembler` Interface
|
== Using the `MBeanInfoAssembler` API
|
||||||
|
|
||||||
Behind the scenes, the `MBeanExporter` delegates to an implementation of the
|
Behind the scenes, the `MBeanExporter` delegates to an implementation of the
|
||||||
`org.springframework.jmx.export.assembler.MBeanInfoAssembler` interface, which is
|
`org.springframework.jmx.export.assembler.MBeanInfoAssembler` API, which is
|
||||||
responsible for defining the management interface of each bean that is exposed.
|
responsible for defining the management interface of each bean that is exposed.
|
||||||
The default implementation,
|
The default implementation,
|
||||||
`org.springframework.jmx.export.assembler.SimpleReflectiveMBeanInfoAssembler`,
|
`org.springframework.jmx.export.assembler.SimpleReflectiveMBeanInfoAssembler`,
|
||||||
|
@ -28,35 +28,31 @@ or any arbitrary interface.
|
||||||
[[jmx-interface-metadata]]
|
[[jmx-interface-metadata]]
|
||||||
== Using Source-level Metadata: Java Annotations
|
== Using Source-level Metadata: Java Annotations
|
||||||
|
|
||||||
By using the `MetadataMBeanInfoAssembler`, you can define the management interfaces
|
By using the `MetadataMBeanInfoAssembler`, you can define the management interfaces for
|
||||||
for your beans by using source-level metadata. The reading of metadata is encapsulated
|
your beans by using source-level metadata. The reading of metadata is encapsulated by the
|
||||||
by the `org.springframework.jmx.export.metadata.JmxAttributeSource` interface.
|
`org.springframework.jmx.export.metadata.JmxAttributeSource` interface. Spring JMX
|
||||||
Spring JMX provides a default implementation that uses Java annotations, namely
|
provides a default implementation that uses Java annotations, namely
|
||||||
`org.springframework.jmx.export.annotation.AnnotationJmxAttributeSource`.
|
`org.springframework.jmx.export.annotation.AnnotationJmxAttributeSource`. You must
|
||||||
You must configure the `MetadataMBeanInfoAssembler` with an implementation instance of
|
configure the `MetadataMBeanInfoAssembler` with an implementation instance of the
|
||||||
the `JmxAttributeSource` interface for it to function correctly (there is no default).
|
`JmxAttributeSource` interface for it to function correctly, since there is no default.
|
||||||
|
|
||||||
To mark a bean for export to JMX, you should annotate the bean class with the
|
To mark a bean for export to JMX, you should annotate the bean class with the
|
||||||
`ManagedResource` annotation. You must mark each method you wish to expose as an operation
|
`@ManagedResource` annotation. You must annotate each method you wish to expose as an
|
||||||
with the `ManagedOperation` annotation and mark each property you wish to expose
|
operation with the `@ManagedOperation` annotation and annotate each property you wish to
|
||||||
with the `ManagedAttribute` annotation. When marking properties, you can omit
|
expose with the `@ManagedAttribute` annotation. When annotating properties, you can omit
|
||||||
either the annotation of the getter or the setter to create a write-only or read-only
|
either the annotation of the getter or the setter to create a write-only or read-only
|
||||||
attribute, respectively.
|
attribute, respectively.
|
||||||
|
|
||||||
NOTE: A `ManagedResource`-annotated bean must be public, as must the methods exposing
|
NOTE: A `@ManagedResource`-annotated bean must be public, as must the methods exposing
|
||||||
an operation or an attribute.
|
operations or attributes.
|
||||||
|
|
||||||
The following example shows the annotated version of the `JmxTestBean` class that we
|
The following example shows an annotated version of the `JmxTestBean` class that we
|
||||||
used in xref:integration/jmx/exporting.adoc#jmx-exporting-mbeanserver[Creating an MBeanServer]:
|
used in xref:integration/jmx/exporting.adoc#jmx-exporting-mbeanserver[Creating an MBeanServer].
|
||||||
|
|
||||||
[source,java,indent=0,subs="verbatim,quotes",chomp="-packages"]
|
[source,java,indent=0,subs="verbatim,quotes",chomp="-packages"]
|
||||||
----
|
----
|
||||||
package org.springframework.jmx;
|
package org.springframework.jmx;
|
||||||
|
|
||||||
import org.springframework.jmx.export.annotation.ManagedResource;
|
|
||||||
import org.springframework.jmx.export.annotation.ManagedOperation;
|
|
||||||
import org.springframework.jmx.export.annotation.ManagedAttribute;
|
|
||||||
|
|
||||||
@ManagedResource(
|
@ManagedResource(
|
||||||
objectName="bean:name=testBean4",
|
objectName="bean:name=testBean4",
|
||||||
description="My Managed Bean",
|
description="My Managed Bean",
|
||||||
|
@ -67,20 +63,20 @@ used in xref:integration/jmx/exporting.adoc#jmx-exporting-mbeanserver[Creating a
|
||||||
persistPeriod=200,
|
persistPeriod=200,
|
||||||
persistLocation="foo",
|
persistLocation="foo",
|
||||||
persistName="bar")
|
persistName="bar")
|
||||||
public class AnnotationTestBean implements IJmxTestBean {
|
public class AnnotationTestBean {
|
||||||
|
|
||||||
private String name;
|
|
||||||
private int age;
|
private int age;
|
||||||
|
private String name;
|
||||||
@ManagedAttribute(description="The Age Attribute", currencyTimeLimit=15)
|
|
||||||
public int getAge() {
|
|
||||||
return age;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setAge(int age) {
|
public void setAge(int age) {
|
||||||
this.age = age;
|
this.age = age;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ManagedAttribute(description="The Age Attribute", currencyTimeLimit=15)
|
||||||
|
public int getAge() {
|
||||||
|
return this.age;
|
||||||
|
}
|
||||||
|
|
||||||
@ManagedAttribute(description="The Name Attribute",
|
@ManagedAttribute(description="The Name Attribute",
|
||||||
currencyTimeLimit=20,
|
currencyTimeLimit=20,
|
||||||
defaultValue="bar",
|
defaultValue="bar",
|
||||||
|
@ -91,13 +87,12 @@ used in xref:integration/jmx/exporting.adoc#jmx-exporting-mbeanserver[Creating a
|
||||||
|
|
||||||
@ManagedAttribute(defaultValue="foo", persistPeriod=300)
|
@ManagedAttribute(defaultValue="foo", persistPeriod=300)
|
||||||
public String getName() {
|
public String getName() {
|
||||||
return name;
|
return this.name;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ManagedOperation(description="Add two numbers")
|
@ManagedOperation(description="Add two numbers")
|
||||||
@ManagedOperationParameters({
|
@ManagedOperationParameter(name = "x", description = "The first number")
|
||||||
@ManagedOperationParameter(name = "x", description = "The first number"),
|
@ManagedOperationParameter(name = "y", description = "The second number")
|
||||||
@ManagedOperationParameter(name = "y", description = "The second number")})
|
|
||||||
public int add(int x, int y) {
|
public int add(int x, int y) {
|
||||||
return x + y;
|
return x + y;
|
||||||
}
|
}
|
||||||
|
@ -109,36 +104,37 @@ used in xref:integration/jmx/exporting.adoc#jmx-exporting-mbeanserver[Creating a
|
||||||
}
|
}
|
||||||
----
|
----
|
||||||
|
|
||||||
In the preceding example, you can see that the `JmxTestBean` class is marked with the
|
In the preceding example, you can see that the `AnnotationTestBean` class is annotated
|
||||||
`ManagedResource` annotation and that this `ManagedResource` annotation is configured
|
with `@ManagedResource` and that this `@ManagedResource` annotation is configured
|
||||||
with a set of properties. These properties can be used to configure various aspects
|
with a set of attributes. These attributes can be used to configure various aspects
|
||||||
of the MBean that is generated by the `MBeanExporter` and are explained in greater
|
of the MBean that is generated by the `MBeanExporter` and are explained in greater
|
||||||
detail later in xref:integration/jmx/interface.adoc#jmx-interface-metadata-types[Source-level Metadata Types].
|
detail later in xref:integration/jmx/interface.adoc#jmx-interface-metadata-types[Spring JMX Annotations].
|
||||||
|
|
||||||
Both the `age` and `name` properties are annotated with the `ManagedAttribute`
|
Both the `age` and `name` properties are annotated with `@ManagedAttribute`,
|
||||||
annotation, but, in the case of the `age` property, only the getter is marked.
|
but, in the case of the `age` property, only the getter method is annotated.
|
||||||
This causes both of these properties to be included in the management interface
|
This causes both of these properties to be included in the management interface
|
||||||
as attributes, but the `age` attribute is read-only.
|
as managed attributes, but the `age` attribute is read-only.
|
||||||
|
|
||||||
Finally, the `add(int, int)` method is marked with the `ManagedOperation` attribute,
|
Finally, the `add(int, int)` method is annotated with `@ManagedOperation`,
|
||||||
whereas the `dontExposeMe()` method is not. This causes the management interface to
|
whereas the `dontExposeMe()` method is not. This causes the management interface to
|
||||||
contain only one operation (`add(int, int)`) when you use the `MetadataMBeanInfoAssembler`.
|
contain only one operation (`add(int, int)`) when you use the `MetadataMBeanInfoAssembler`.
|
||||||
|
|
||||||
|
NOTE: The `AnnotationTestBean` class is not required to implement any Java interfaces,
|
||||||
|
since the JMX management interface is derived solely from annotations.
|
||||||
|
|
||||||
The following configuration shows how you can configure the `MBeanExporter` to use the
|
The following configuration shows how you can configure the `MBeanExporter` to use the
|
||||||
`MetadataMBeanInfoAssembler`:
|
`MetadataMBeanInfoAssembler`:
|
||||||
|
|
||||||
[source,xml,indent=0,subs="verbatim,quotes"]
|
[source,xml,indent=0,subs="verbatim,quotes"]
|
||||||
----
|
----
|
||||||
<beans>
|
<beans>
|
||||||
|
|
||||||
<bean id="exporter" class="org.springframework.jmx.export.MBeanExporter">
|
<bean id="exporter" class="org.springframework.jmx.export.MBeanExporter">
|
||||||
<property name="assembler" ref="assembler"/>
|
<property name="assembler" ref="assembler"/>
|
||||||
<property name="namingStrategy" ref="namingStrategy"/>
|
<property name="namingStrategy" ref="namingStrategy"/>
|
||||||
<property name="autodetect" value="true"/>
|
<property name="autodetect" value="true"/>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<bean id="jmxAttributeSource"
|
|
||||||
class="org.springframework.jmx.export.annotation.AnnotationJmxAttributeSource"/>
|
|
||||||
|
|
||||||
<!-- will create management interface using annotation metadata -->
|
<!-- will create management interface using annotation metadata -->
|
||||||
<bean id="assembler"
|
<bean id="assembler"
|
||||||
class="org.springframework.jmx.export.assembler.MetadataMBeanInfoAssembler">
|
class="org.springframework.jmx.export.assembler.MetadataMBeanInfoAssembler">
|
||||||
|
@ -151,102 +147,116 @@ The following configuration shows how you can configure the `MBeanExporter` to u
|
||||||
<property name="attributeSource" ref="jmxAttributeSource"/>
|
<property name="attributeSource" ref="jmxAttributeSource"/>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
|
<bean id="jmxAttributeSource"
|
||||||
|
class="org.springframework.jmx.export.annotation.AnnotationJmxAttributeSource"/>
|
||||||
|
|
||||||
<bean id="testBean" class="org.springframework.jmx.AnnotationTestBean">
|
<bean id="testBean" class="org.springframework.jmx.AnnotationTestBean">
|
||||||
<property name="name" value="TEST"/>
|
<property name="name" value="TEST"/>
|
||||||
<property name="age" value="100"/>
|
<property name="age" value="100"/>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
</beans>
|
</beans>
|
||||||
----
|
----
|
||||||
|
|
||||||
In the preceding example, an `MetadataMBeanInfoAssembler` bean has been configured with an
|
In the preceding example, a `MetadataMBeanInfoAssembler` bean has been configured with an
|
||||||
instance of the `AnnotationJmxAttributeSource` class and passed to the `MBeanExporter`
|
instance of the `AnnotationJmxAttributeSource` class and passed to the `MBeanExporter`
|
||||||
through the assembler property. This is all that is required to take advantage of
|
through the assembler property. This is all that is required to take advantage of
|
||||||
metadata-driven management interfaces for your Spring-exposed MBeans.
|
annotation-driven management interfaces for your Spring-exposed MBeans.
|
||||||
|
|
||||||
|
|
||||||
[[jmx-interface-metadata-types]]
|
[[jmx-interface-metadata-types]]
|
||||||
== Source-level Metadata Types
|
== Spring JMX Annotations
|
||||||
|
|
||||||
The following table describes the source-level metadata types that are available for use in Spring JMX:
|
The following table describes the annotations that are available for use in Spring JMX:
|
||||||
|
|
||||||
[[jmx-metadata-types]]
|
[[jmx-metadata-types]]
|
||||||
.Source-level metadata types
|
.Spring JMX annotations
|
||||||
|
[cols="1,1,3"]
|
||||||
|===
|
|===
|
||||||
| Purpose| Annotation| Annotation Type
|
| Annotation | Applies to | Description
|
||||||
|
|
||||||
| Mark all instances of a `Class` as JMX managed resources.
|
|
||||||
| `@ManagedResource`
|
| `@ManagedResource`
|
||||||
| Class
|
| Classes
|
||||||
|
| Marks all instances of a `Class` as JMX managed resources.
|
||||||
|
|
||||||
| Mark a method as a JMX operation.
|
| `@ManagedNotification`
|
||||||
| `@ManagedOperation`
|
| Classes
|
||||||
| Method
|
| Indicates a JMX notification emitted by a managed resource.
|
||||||
|
|
||||||
| Mark a getter or setter as one half of a JMX attribute.
|
|
||||||
| `@ManagedAttribute`
|
| `@ManagedAttribute`
|
||||||
| Method (only getters and setters)
|
| Methods (only getters and setters)
|
||||||
|
| Marks a getter or setter as one half of a JMX attribute.
|
||||||
|
|
||||||
| Define descriptions for operation parameters.
|
| `@ManagedMetric`
|
||||||
| `@ManagedOperationParameter` and `@ManagedOperationParameters`
|
| Methods (only getters)
|
||||||
| Method
|
| Marks a getter as a JMX attribute, with added descriptor properties to indicate that it is a metric.
|
||||||
|
|
||||||
|
| `@ManagedOperation`
|
||||||
|
| Methods
|
||||||
|
| Marks a method as a JMX operation.
|
||||||
|
|
||||||
|
| `@ManagedOperationParameter`
|
||||||
|
| Methods
|
||||||
|
| Defines a description for an operation parameter.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
The following table describes the configuration parameters that are available for use on these source-level
|
The following table describes some of the common attributes that are available for use in
|
||||||
metadata types:
|
these annotations. Consult the Javadoc for each annotation for further details.
|
||||||
|
|
||||||
[[jmx-metadata-parameters]]
|
[[jmx-metadata-parameters]]
|
||||||
.Source-level metadata parameters
|
.Spring JMX annotation attributes
|
||||||
[cols="1,3,1"]
|
[cols="1,1,3"]
|
||||||
|===
|
|===
|
||||||
| Parameter | Description | Applies to
|
| Attribute | Applies to | Description
|
||||||
|
|
||||||
| `ObjectName`
|
| `objectName`
|
||||||
|
| `@ManagedResource`
|
||||||
| Used by `MetadataNamingStrategy` to determine the `ObjectName` of a managed resource.
|
| Used by `MetadataNamingStrategy` to determine the `ObjectName` of a managed resource.
|
||||||
| `ManagedResource`
|
|
||||||
|
|
||||||
| `description`
|
| `description`
|
||||||
| Sets the friendly description of the resource, attribute or operation.
|
| `@ManagedResource`, `@ManagedNotification`, `@ManagedAttribute`, `@ManagedMetric`,
|
||||||
| `ManagedResource`, `ManagedAttribute`, `ManagedOperation`, or `ManagedOperationParameter`
|
`@ManagedOperation`, `@ManagedOperationParameter`
|
||||||
|
| Sets the description of the resource, notification, attribute, metric, or operation.
|
||||||
|
|
||||||
| `currencyTimeLimit`
|
| `currencyTimeLimit`
|
||||||
|
| `@ManagedResource`, `@ManagedAttribute`, `@ManagedMetric`
|
||||||
| Sets the value of the `currencyTimeLimit` descriptor field.
|
| Sets the value of the `currencyTimeLimit` descriptor field.
|
||||||
| `ManagedResource` or `ManagedAttribute`
|
|
||||||
|
|
||||||
| `defaultValue`
|
| `defaultValue`
|
||||||
|
| `@ManagedAttribute`
|
||||||
| Sets the value of the `defaultValue` descriptor field.
|
| Sets the value of the `defaultValue` descriptor field.
|
||||||
| `ManagedAttribute`
|
|
||||||
|
|
||||||
| `log`
|
| `log`
|
||||||
|
| `@ManagedResource`
|
||||||
| Sets the value of the `log` descriptor field.
|
| Sets the value of the `log` descriptor field.
|
||||||
| `ManagedResource`
|
|
||||||
|
|
||||||
| `logFile`
|
| `logFile`
|
||||||
|
| `@ManagedResource`
|
||||||
| Sets the value of the `logFile` descriptor field.
|
| Sets the value of the `logFile` descriptor field.
|
||||||
| `ManagedResource`
|
|
||||||
|
|
||||||
| `persistPolicy`
|
| `persistPolicy`
|
||||||
|
| `@ManagedResource`, `@ManagedMetric`
|
||||||
| Sets the value of the `persistPolicy` descriptor field.
|
| Sets the value of the `persistPolicy` descriptor field.
|
||||||
| `ManagedResource`
|
|
||||||
|
|
||||||
| `persistPeriod`
|
| `persistPeriod`
|
||||||
|
| `@ManagedResource`, `@ManagedMetric`
|
||||||
| Sets the value of the `persistPeriod` descriptor field.
|
| Sets the value of the `persistPeriod` descriptor field.
|
||||||
| `ManagedResource`
|
|
||||||
|
|
||||||
| `persistLocation`
|
| `persistLocation`
|
||||||
|
| `@ManagedResource`
|
||||||
| Sets the value of the `persistLocation` descriptor field.
|
| Sets the value of the `persistLocation` descriptor field.
|
||||||
| `ManagedResource`
|
|
||||||
|
|
||||||
| `persistName`
|
| `persistName`
|
||||||
|
| `@ManagedResource`
|
||||||
| Sets the value of the `persistName` descriptor field.
|
| Sets the value of the `persistName` descriptor field.
|
||||||
| `ManagedResource`
|
|
||||||
|
|
||||||
| `name`
|
| `name`
|
||||||
|
| `@ManagedOperationParameter`
|
||||||
| Sets the display name of an operation parameter.
|
| Sets the display name of an operation parameter.
|
||||||
| `ManagedOperationParameter`
|
|
||||||
|
|
||||||
| `index`
|
| `index`
|
||||||
|
| `@ManagedOperationParameter`
|
||||||
| Sets the index of an operation parameter.
|
| Sets the index of an operation parameter.
|
||||||
| `ManagedOperationParameter`
|
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
@ -255,14 +265,14 @@ metadata types:
|
||||||
|
|
||||||
To simplify configuration even further, Spring includes the
|
To simplify configuration even further, Spring includes the
|
||||||
`AutodetectCapableMBeanInfoAssembler` interface, which extends the `MBeanInfoAssembler`
|
`AutodetectCapableMBeanInfoAssembler` interface, which extends the `MBeanInfoAssembler`
|
||||||
interface to add support for autodetection of MBean resources. If you configure the
|
interface to add support for auto-detection of MBean resources. If you configure the
|
||||||
`MBeanExporter` with an instance of `AutodetectCapableMBeanInfoAssembler`, it is
|
`MBeanExporter` with an instance of `AutodetectCapableMBeanInfoAssembler`, it is
|
||||||
allowed to "`vote`" on the inclusion of beans for exposure to JMX.
|
allowed to "vote" on the inclusion of beans for exposure to JMX.
|
||||||
|
|
||||||
The only implementation of the `AutodetectCapableMBeanInfo` interface is
|
The only implementation of the `AutodetectCapableMBeanInfo` interface is
|
||||||
the `MetadataMBeanInfoAssembler`, which votes to include any bean that is marked
|
the `MetadataMBeanInfoAssembler`, which votes to include any bean that is marked
|
||||||
with the `ManagedResource` attribute. The default approach in this case is to use the
|
with the `ManagedResource` attribute. The default approach in this case is to use the
|
||||||
bean name as the `ObjectName`, which results in a configuration similar to the following:
|
bean name as the `ObjectName`, which results in configuration similar to the following:
|
||||||
|
|
||||||
[source,xml,indent=0,subs="verbatim,quotes"]
|
[source,xml,indent=0,subs="verbatim,quotes"]
|
||||||
----
|
----
|
||||||
|
@ -274,26 +284,29 @@ bean name as the `ObjectName`, which results in a configuration similar to the f
|
||||||
<property name="assembler" ref="assembler"/>
|
<property name="assembler" ref="assembler"/>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<bean id="testBean" class="org.springframework.jmx.JmxTestBean">
|
|
||||||
<property name="name" value="TEST"/>
|
|
||||||
<property name="age" value="100"/>
|
|
||||||
</bean>
|
|
||||||
|
|
||||||
<bean id="assembler" class="org.springframework.jmx.export.assembler.MetadataMBeanInfoAssembler">
|
<bean id="assembler" class="org.springframework.jmx.export.assembler.MetadataMBeanInfoAssembler">
|
||||||
<property name="attributeSource">
|
<property name="attributeSource">
|
||||||
<bean class="org.springframework.jmx.export.annotation.AnnotationJmxAttributeSource"/>
|
<bean class="org.springframework.jmx.export.annotation.AnnotationJmxAttributeSource"/>
|
||||||
</property>
|
</property>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
|
<bean id="testBean" class="org.springframework.jmx.AnnotationTestBean">
|
||||||
|
<property name="name" value="TEST"/>
|
||||||
|
<property name="age" value="100"/>
|
||||||
|
</bean>
|
||||||
|
|
||||||
</beans>
|
</beans>
|
||||||
----
|
----
|
||||||
|
|
||||||
Notice that, in the preceding configuration, no beans are passed to the `MBeanExporter`.
|
Notice that, in the preceding configuration, no beans are passed to the `MBeanExporter`.
|
||||||
However, the `JmxTestBean` is still registered, since it is marked with the `ManagedResource`
|
However, the `AnnotationTestBean` is still registered, since it is annotated with
|
||||||
attribute and the `MetadataMBeanInfoAssembler` detects this and votes to include it.
|
`@ManagedResource` and the `MetadataMBeanInfoAssembler` detects this and votes to include
|
||||||
The only problem with this approach is that the name of the `JmxTestBean` now has business
|
it. The only downside with this approach is that the name of the `AnnotationTestBean` now
|
||||||
meaning. You can address this issue by changing the default behavior for `ObjectName`
|
has business meaning. You can address this issue by configuring an `ObjectNamingStrategy`
|
||||||
creation as defined in xref:integration/jmx/naming.adoc[Controlling `ObjectName` Instances for Your Beans].
|
as explained in xref:integration/jmx/naming.adoc[Controlling `ObjectName` Instances for
|
||||||
|
Your Beans]. You can also see an example which uses the `MetadataNamingStrategy` in
|
||||||
|
xref:integration/jmx/interface.adoc#jmx-interface-metadata[Using Source-level Metadata: Java Annotations].
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
[[jmx-interface-java]]
|
[[jmx-interface-java]]
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 2002-2017 the original author or authors.
|
* Copyright 2002-2024 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -20,19 +20,15 @@ package org.springframework.jmx;
|
||||||
* @author Rob Harrop
|
* @author Rob Harrop
|
||||||
* @author Juergen Hoeller
|
* @author Juergen Hoeller
|
||||||
*/
|
*/
|
||||||
public interface IJmxTestBean {
|
public interface IJmxTestBean extends ITestBean {
|
||||||
|
|
||||||
int add(int x, int y);
|
int add(int x, int y);
|
||||||
|
|
||||||
long myOperation();
|
long myOperation();
|
||||||
|
|
||||||
int getAge();
|
|
||||||
|
|
||||||
void setAge(int age);
|
void setAge(int age);
|
||||||
|
|
||||||
void setName(String name) throws Exception;
|
int getAge();
|
||||||
|
|
||||||
String getName();
|
|
||||||
|
|
||||||
// used to test invalid methods that exist in the proxy interface
|
// used to test invalid methods that exist in the proxy interface
|
||||||
void dontExposeMe();
|
void dontExposeMe();
|
||||||
|
|
|
@ -0,0 +1,25 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2002-2024 the original author or authors.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* https://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.springframework.jmx;
|
||||||
|
|
||||||
|
public interface ITestBean {
|
||||||
|
|
||||||
|
void setName(String name) throws Exception;
|
||||||
|
|
||||||
|
String getName();
|
||||||
|
|
||||||
|
}
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 2002-2016 the original author or authors.
|
* Copyright 2002-2024 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -19,12 +19,6 @@ package org.springframework.jmx;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedResource
|
|
||||||
* (description="My Managed Bean", objectName="spring:bean=test",
|
|
||||||
* log=true, logFile="build/jmx.log", currencyTimeLimit=15, persistPolicy="OnUpdate",
|
|
||||||
* persistPeriod=200, persistLocation="./foo", persistName="bar.jmx")
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedNotification
|
|
||||||
* (name="My Notification", description="A Notification", notificationType="type.foo,type.bar")
|
|
||||||
* @author Rob Harrop
|
* @author Rob Harrop
|
||||||
* @author Juergen Hoeller
|
* @author Juergen Hoeller
|
||||||
*/
|
*/
|
||||||
|
@ -39,33 +33,21 @@ public class JmxTestBean implements IJmxTestBean {
|
||||||
private boolean isSuperman;
|
private boolean isSuperman;
|
||||||
|
|
||||||
|
|
||||||
/**
|
@Override
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedAttribute
|
public void setAge(int age) {
|
||||||
* (description="The Age Attribute", currencyTimeLimit=15)
|
this.age = age;
|
||||||
*/
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getAge() {
|
public int getAge() {
|
||||||
return age;
|
return age;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setAge(int age) {
|
|
||||||
this.age = age;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedOperation(currencyTimeLimit=30)
|
|
||||||
*/
|
|
||||||
@Override
|
@Override
|
||||||
public long myOperation() {
|
public long myOperation() {
|
||||||
return 1L;
|
return 1L;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedAttribute
|
|
||||||
* (description="The Name Attribute", currencyTimeLimit=20,
|
|
||||||
* defaultValue="bar", persistPolicy="OnUpdate")
|
|
||||||
*/
|
|
||||||
@Override
|
@Override
|
||||||
public void setName(String name) throws Exception {
|
public void setName(String name) throws Exception {
|
||||||
if ("Juergen".equals(name)) {
|
if ("Juergen".equals(name)) {
|
||||||
|
@ -80,20 +62,11 @@ public class JmxTestBean implements IJmxTestBean {
|
||||||
this.name = name;
|
this.name = name;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedAttribute
|
|
||||||
* (defaultValue="foo", persistPeriod=300)
|
|
||||||
*/
|
|
||||||
@Override
|
@Override
|
||||||
public String getName() {
|
public String getName() {
|
||||||
return name;
|
return name;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedAttribute(description="The Nick
|
|
||||||
* Name
|
|
||||||
* Attribute")
|
|
||||||
*/
|
|
||||||
public void setNickName(String nickName) {
|
public void setNickName(String nickName) {
|
||||||
this.nickName = nickName;
|
this.nickName = nickName;
|
||||||
}
|
}
|
||||||
|
@ -106,30 +79,15 @@ public class JmxTestBean implements IJmxTestBean {
|
||||||
this.isSuperman = superman;
|
this.isSuperman = superman;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedAttribute(description="The Is
|
|
||||||
* Superman
|
|
||||||
* Attribute")
|
|
||||||
*/
|
|
||||||
public boolean isSuperman() {
|
public boolean isSuperman() {
|
||||||
return isSuperman;
|
return isSuperman;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedOperation(description="Add Two
|
|
||||||
* Numbers
|
|
||||||
* Together")
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedOperationParameter(index=0, name="x", description="Left operand")
|
|
||||||
* @@org.springframework.jmx.export.metadata.ManagedOperationParameter(index=1, name="y", description="Right operand")
|
|
||||||
*/
|
|
||||||
@Override
|
@Override
|
||||||
public int add(int x, int y) {
|
public int add(int x, int y) {
|
||||||
return x + y;
|
return x + y;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Test method that is not exposed by the MetadataAssembler.
|
|
||||||
*/
|
|
||||||
@Override
|
@Override
|
||||||
public void dontExposeMe() {
|
public void dontExposeMe() {
|
||||||
throw new RuntimeException();
|
throw new RuntimeException();
|
||||||
|
|
|
@ -22,7 +22,7 @@ import javax.management.modelmbean.ModelMBeanOperationInfo;
|
||||||
|
|
||||||
import org.junit.jupiter.api.Test;
|
import org.junit.jupiter.api.Test;
|
||||||
|
|
||||||
import org.springframework.jmx.IJmxTestBean;
|
import org.springframework.jmx.ITestBean;
|
||||||
import org.springframework.jmx.export.assembler.AbstractMetadataAssemblerTests;
|
import org.springframework.jmx.export.assembler.AbstractMetadataAssemblerTests;
|
||||||
import org.springframework.jmx.export.metadata.JmxAttributeSource;
|
import org.springframework.jmx.export.metadata.JmxAttributeSource;
|
||||||
|
|
||||||
|
@ -93,7 +93,7 @@ class AnnotationMetadataAssemblerTests extends AbstractMetadataAssemblerTests {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected IJmxTestBean createJmxTestBean() {
|
protected ITestBean createJmxTestBean() {
|
||||||
return new AnnotationTestSubBean();
|
return new AnnotationTestSubBean();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 2002-2018 the original author or authors.
|
* Copyright 2002-2024 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -16,7 +16,7 @@
|
||||||
|
|
||||||
package org.springframework.jmx.export.annotation;
|
package org.springframework.jmx.export.annotation;
|
||||||
|
|
||||||
import org.springframework.jmx.IJmxTestBean;
|
import org.springframework.jmx.ITestBean;
|
||||||
import org.springframework.jmx.support.MetricType;
|
import org.springframework.jmx.support.MetricType;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
@ -29,7 +29,7 @@ import org.springframework.stereotype.Service;
|
||||||
logFile = "build/jmx.log", currencyTimeLimit = 15, persistPolicy = "OnUpdate", persistPeriod = 200,
|
logFile = "build/jmx.log", currencyTimeLimit = 15, persistPolicy = "OnUpdate", persistPeriod = 200,
|
||||||
persistLocation = "./foo", persistName = "bar.jmx")
|
persistLocation = "./foo", persistName = "bar.jmx")
|
||||||
@ManagedNotification(name = "My Notification", notificationTypes = { "type.foo", "type.bar" })
|
@ManagedNotification(name = "My Notification", notificationTypes = { "type.foo", "type.bar" })
|
||||||
public class AnnotationTestBean implements IJmxTestBean {
|
public class AnnotationTestBean implements ITestBean {
|
||||||
|
|
||||||
private String name;
|
private String name;
|
||||||
|
|
||||||
|
@ -40,21 +40,13 @@ public class AnnotationTestBean implements IJmxTestBean {
|
||||||
private boolean isSuperman;
|
private boolean isSuperman;
|
||||||
|
|
||||||
|
|
||||||
@Override
|
|
||||||
@ManagedAttribute(description = "The Age Attribute", currencyTimeLimit = 15)
|
|
||||||
public int getAge() {
|
|
||||||
return age;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setAge(int age) {
|
public void setAge(int age) {
|
||||||
this.age = age;
|
this.age = age;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@ManagedAttribute(description = "The Age Attribute", currencyTimeLimit = 15)
|
||||||
@ManagedOperation(currencyTimeLimit = 30)
|
public int getAge() {
|
||||||
public long myOperation() {
|
return this.age;
|
||||||
return 1L;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -69,7 +61,7 @@ public class AnnotationTestBean implements IJmxTestBean {
|
||||||
@Override
|
@Override
|
||||||
@ManagedAttribute(defaultValue = "foo", persistPeriod = 300)
|
@ManagedAttribute(defaultValue = "foo", persistPeriod = 300)
|
||||||
public String getName() {
|
public String getName() {
|
||||||
return name;
|
return this.name;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ManagedAttribute(description = "The Nick Name Attribute")
|
@ManagedAttribute(description = "The Nick Name Attribute")
|
||||||
|
@ -90,7 +82,11 @@ public class AnnotationTestBean implements IJmxTestBean {
|
||||||
return isSuperman;
|
return isSuperman;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@ManagedOperation(currencyTimeLimit = 30)
|
||||||
|
public long myOperation() {
|
||||||
|
return 1L;
|
||||||
|
}
|
||||||
|
|
||||||
@ManagedOperation(description = "Add Two Numbers Together")
|
@ManagedOperation(description = "Add Two Numbers Together")
|
||||||
@ManagedOperationParameter(name="x", description="Left operand")
|
@ManagedOperationParameter(name="x", description="Left operand")
|
||||||
@ManagedOperationParameter(name="y", description="Right operand")
|
@ManagedOperationParameter(name="y", description="Right operand")
|
||||||
|
@ -99,9 +95,8 @@ public class AnnotationTestBean implements IJmxTestBean {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test method that is not exposed by the MetadataAssembler.
|
* Method that is not exposed by the MetadataAssembler.
|
||||||
*/
|
*/
|
||||||
@Override
|
|
||||||
public void dontExposeMe() {
|
public void dontExposeMe() {
|
||||||
throw new RuntimeException();
|
throw new RuntimeException();
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,7 +17,6 @@
|
||||||
package org.springframework.jmx.export.annotation;
|
package org.springframework.jmx.export.annotation;
|
||||||
|
|
||||||
import org.springframework.beans.factory.FactoryBean;
|
import org.springframework.beans.factory.FactoryBean;
|
||||||
import org.springframework.jmx.IJmxTestBean;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Juergen Hoeller
|
* @author Juergen Hoeller
|
||||||
|
@ -36,7 +35,7 @@ public class AnnotationTestBeanFactory implements FactoryBean<FactoryCreatedAnno
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Class<? extends IJmxTestBean> getObjectType() {
|
public Class<? extends AnnotationTestBean> getObjectType() {
|
||||||
return FactoryCreatedAnnotationTestBean.class;
|
return FactoryCreatedAnnotationTestBean.class;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -18,10 +18,8 @@ package org.springframework.jmx.export.assembler;
|
||||||
|
|
||||||
import javax.management.Attribute;
|
import javax.management.Attribute;
|
||||||
import javax.management.Descriptor;
|
import javax.management.Descriptor;
|
||||||
import javax.management.MBeanAttributeInfo;
|
|
||||||
import javax.management.MBeanInfo;
|
import javax.management.MBeanInfo;
|
||||||
import javax.management.MBeanNotificationInfo;
|
import javax.management.MBeanNotificationInfo;
|
||||||
import javax.management.MBeanOperationInfo;
|
|
||||||
import javax.management.ObjectInstance;
|
import javax.management.ObjectInstance;
|
||||||
import javax.management.ObjectName;
|
import javax.management.ObjectName;
|
||||||
import javax.management.modelmbean.ModelMBeanAttributeInfo;
|
import javax.management.modelmbean.ModelMBeanAttributeInfo;
|
||||||
|
@ -31,7 +29,7 @@ import javax.management.modelmbean.ModelMBeanOperationInfo;
|
||||||
import org.junit.jupiter.api.Test;
|
import org.junit.jupiter.api.Test;
|
||||||
|
|
||||||
import org.springframework.jmx.AbstractJmxTests;
|
import org.springframework.jmx.AbstractJmxTests;
|
||||||
import org.springframework.jmx.IJmxTestBean;
|
import org.springframework.jmx.ITestBean;
|
||||||
import org.springframework.jmx.support.ObjectNameManager;
|
import org.springframework.jmx.support.ObjectNameManager;
|
||||||
|
|
||||||
import static org.assertj.core.api.Assertions.assertThat;
|
import static org.assertj.core.api.Assertions.assertThat;
|
||||||
|
@ -48,76 +46,68 @@ public abstract class AbstractJmxAssemblerTests extends AbstractJmxTests {
|
||||||
|
|
||||||
protected abstract String getObjectName();
|
protected abstract String getObjectName();
|
||||||
|
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testMBeanRegistration() throws Exception {
|
void mBeanRegistration() throws Exception {
|
||||||
// beans are registered at this point - just grab them from the server
|
// beans are registered at this point - just grab them from the server
|
||||||
ObjectInstance instance = getObjectInstance();
|
ObjectInstance instance = getObjectInstance();
|
||||||
assertThat(instance).as("Bean should not be null").isNotNull();
|
assertThat(instance).as("Bean should not be null").isNotNull();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testRegisterOperations() throws Exception {
|
void registerOperations() throws Exception {
|
||||||
IJmxTestBean bean = getBean();
|
assertThat(getBean()).isNotNull();
|
||||||
assertThat(bean).isNotNull();
|
|
||||||
MBeanInfo inf = getMBeanInfo();
|
MBeanInfo inf = getMBeanInfo();
|
||||||
assertThat(inf.getOperations()).as("Incorrect number of operations registered").hasSize(getExpectedOperationCount());
|
assertThat(inf.getOperations()).as("Incorrect number of operations registered").hasSize(getExpectedOperationCount());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testRegisterAttributes() throws Exception {
|
void registerAttributes() throws Exception {
|
||||||
IJmxTestBean bean = getBean();
|
assertThat(getBean()).isNotNull();
|
||||||
assertThat(bean).isNotNull();
|
|
||||||
MBeanInfo inf = getMBeanInfo();
|
MBeanInfo inf = getMBeanInfo();
|
||||||
assertThat(inf.getAttributes()).as("Incorrect number of attributes registered").hasSize(getExpectedAttributeCount());
|
assertThat(inf.getAttributes()).as("Incorrect number of attributes registered").hasSize(getExpectedAttributeCount());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testGetMBeanInfo() throws Exception {
|
void getMBeanAttributeInfo() throws Exception {
|
||||||
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
||||||
assertThat(info).as("MBeanInfo should not be null").isNotNull();
|
assertThat(info).as("MBeanInfo should not be null").isNotNull();
|
||||||
}
|
assertThat(info.getAttributes())
|
||||||
|
.hasSize(getExpectedAttributeCount())
|
||||||
@Test
|
.allSatisfy(element -> {
|
||||||
void testGetMBeanAttributeInfo() throws Exception {
|
|
||||||
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
|
||||||
MBeanAttributeInfo[] inf = info.getAttributes();
|
|
||||||
assertThat(inf).as("Invalid number of Attributes returned").hasSize(getExpectedAttributeCount());
|
|
||||||
|
|
||||||
for (MBeanAttributeInfo element : inf) {
|
|
||||||
assertThat(element).as("MBeanAttributeInfo should not be null").isNotNull();
|
assertThat(element).as("MBeanAttributeInfo should not be null").isNotNull();
|
||||||
assertThat(element.getDescription()).as("Description for MBeanAttributeInfo should not be null").isNotNull();
|
assertThat(element.getDescription()).as("Description for MBeanAttributeInfo should not be null").isNotNull();
|
||||||
}
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testGetMBeanOperationInfo() throws Exception {
|
void getMBeanOperationInfo() throws Exception {
|
||||||
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
||||||
MBeanOperationInfo[] inf = info.getOperations();
|
assertThat(info).as("MBeanInfo should not be null").isNotNull();
|
||||||
assertThat(inf).as("Invalid number of Operations returned").hasSize(getExpectedOperationCount());
|
assertThat(info.getOperations())
|
||||||
|
.hasSize(getExpectedOperationCount())
|
||||||
for (MBeanOperationInfo element : inf) {
|
.allSatisfy(element -> {
|
||||||
assertThat(element).as("MBeanOperationInfo should not be null").isNotNull();
|
assertThat(element).as("MBeanOperationInfo should not be null").isNotNull();
|
||||||
assertThat(element.getDescription()).as("Description for MBeanOperationInfo should not be null").isNotNull();
|
assertThat(element.getDescription()).as("Description for MBeanOperationInfo should not be null").isNotNull();
|
||||||
}
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testDescriptionNotNull() throws Exception {
|
void descriptionNotNull() throws Exception {
|
||||||
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
||||||
|
|
||||||
assertThat(info.getDescription()).as("The MBean description should not be null").isNotNull();
|
assertThat(info.getDescription()).as("The MBean description should not be null").isNotNull();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testSetAttribute() throws Exception {
|
void setAttribute() throws Exception {
|
||||||
ObjectName objectName = ObjectNameManager.getInstance(getObjectName());
|
ObjectName objectName = ObjectNameManager.getInstance(getObjectName());
|
||||||
getServer().setAttribute(objectName, new Attribute(NAME_ATTRIBUTE, "Rob Harrop"));
|
getServer().setAttribute(objectName, new Attribute(NAME_ATTRIBUTE, "Rob Harrop"));
|
||||||
IJmxTestBean bean = (IJmxTestBean) getContext().getBean("testBean");
|
assertThat(getBean().getName()).isEqualTo("Rob Harrop");
|
||||||
assertThat(bean.getName()).isEqualTo("Rob Harrop");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testGetAttribute() throws Exception {
|
void getAttribute() throws Exception {
|
||||||
ObjectName objectName = ObjectNameManager.getInstance(getObjectName());
|
ObjectName objectName = ObjectNameManager.getInstance(getObjectName());
|
||||||
getBean().setName("John Smith");
|
getBean().setName("John Smith");
|
||||||
Object val = getServer().getAttribute(objectName, NAME_ATTRIBUTE);
|
Object val = getServer().getAttribute(objectName, NAME_ATTRIBUTE);
|
||||||
|
@ -125,7 +115,7 @@ public abstract class AbstractJmxAssemblerTests extends AbstractJmxTests {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testOperationInvocation() throws Exception{
|
void operationInvocation() throws Exception{
|
||||||
ObjectName objectName = ObjectNameManager.getInstance(getObjectName());
|
ObjectName objectName = ObjectNameManager.getInstance(getObjectName());
|
||||||
Object result = getServer().invoke(objectName, "add",
|
Object result = getServer().invoke(objectName, "add",
|
||||||
new Object[] {20, 30}, new String[] {"int", "int"});
|
new Object[] {20, 30}, new String[] {"int", "int"});
|
||||||
|
@ -133,7 +123,7 @@ public abstract class AbstractJmxAssemblerTests extends AbstractJmxTests {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testAttributeInfoHasDescriptors() throws Exception {
|
void attributeInfoHasDescriptors() throws Exception {
|
||||||
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
||||||
|
|
||||||
ModelMBeanAttributeInfo attr = info.getAttribute(NAME_ATTRIBUTE);
|
ModelMBeanAttributeInfo attr = info.getAttribute(NAME_ATTRIBUTE);
|
||||||
|
@ -145,42 +135,35 @@ public abstract class AbstractJmxAssemblerTests extends AbstractJmxTests {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testAttributeHasCorrespondingOperations() throws Exception {
|
void attributeHasCorrespondingOperations() throws Exception {
|
||||||
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
ModelMBeanInfo info = getMBeanInfoFromAssembler();
|
||||||
|
|
||||||
ModelMBeanOperationInfo get = info.getOperation("getName");
|
ModelMBeanOperationInfo get = info.getOperation("getName");
|
||||||
assertThat(get).as("get operation should not be null").isNotNull();
|
assertThat(get).as("get operation should not be null").isNotNull();
|
||||||
assertThat(Integer.valueOf(4)).as("get operation should have visibility of four").isEqualTo(get.getDescriptor().getFieldValue("visibility"));
|
assertThat(get.getDescriptor().getFieldValue("visibility")).as("get operation should have visibility of four").isEqualTo(4);
|
||||||
assertThat(get.getDescriptor().getFieldValue("role")).as("get operation should have role \"getter\"").isEqualTo("getter");
|
assertThat(get.getDescriptor().getFieldValue("role")).as("get operation should have role \"getter\"").isEqualTo("getter");
|
||||||
|
|
||||||
ModelMBeanOperationInfo set = info.getOperation("setName");
|
ModelMBeanOperationInfo set = info.getOperation("setName");
|
||||||
assertThat(set).as("set operation should not be null").isNotNull();
|
assertThat(set).as("set operation should not be null").isNotNull();
|
||||||
assertThat(Integer.valueOf(4)).as("set operation should have visibility of four").isEqualTo(set.getDescriptor().getFieldValue("visibility"));
|
assertThat(set.getDescriptor().getFieldValue("visibility")).as("set operation should have visibility of four").isEqualTo(4);
|
||||||
assertThat(set.getDescriptor().getFieldValue("role")).as("set operation should have role \"setter\"").isEqualTo("setter");
|
assertThat(set.getDescriptor().getFieldValue("role")).as("set operation should have role \"setter\"").isEqualTo("setter");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testNotificationMetadata() throws Exception {
|
void notificationMetadata() throws Exception {
|
||||||
ModelMBeanInfo info = (ModelMBeanInfo) getMBeanInfo();
|
ModelMBeanInfo info = (ModelMBeanInfo) getMBeanInfo();
|
||||||
MBeanNotificationInfo[] notifications = info.getNotifications();
|
MBeanNotificationInfo[] notifications = info.getNotifications();
|
||||||
assertThat(notifications).as("Incorrect number of notifications").hasSize(1);
|
assertThat(notifications).as("Incorrect number of notifications").hasSize(1);
|
||||||
assertThat(notifications[0].getName()).as("Incorrect notification name").isEqualTo("My Notification");
|
assertThat(notifications[0].getName()).as("Incorrect notification name").isEqualTo("My Notification");
|
||||||
|
assertThat(notifications[0].getNotifTypes()).as("notification types").containsExactly("type.foo", "type.bar");
|
||||||
String[] notifTypes = notifications[0].getNotifTypes();
|
|
||||||
|
|
||||||
assertThat(notifTypes).as("Incorrect number of notification types").hasSize(2);
|
|
||||||
assertThat(notifTypes[0]).as("Notification type.foo not found").isEqualTo("type.foo");
|
|
||||||
assertThat(notifTypes[1]).as("Notification type.bar not found").isEqualTo("type.bar");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected ModelMBeanInfo getMBeanInfoFromAssembler() throws Exception {
|
protected ModelMBeanInfo getMBeanInfoFromAssembler() throws Exception {
|
||||||
IJmxTestBean bean = getBean();
|
return getAssembler().getMBeanInfo(getBean(), getObjectName());
|
||||||
return getAssembler().getMBeanInfo(bean, getObjectName());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected IJmxTestBean getBean() {
|
protected ITestBean getBean() {
|
||||||
Object bean = getContext().getBean("testBean");
|
return getContext().getBean("testBean", ITestBean.class);
|
||||||
return (IJmxTestBean) bean;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected MBeanInfo getMBeanInfo() throws Exception {
|
protected MBeanInfo getMBeanInfo() throws Exception {
|
||||||
|
|
|
@ -30,7 +30,7 @@ import org.junit.jupiter.api.Test;
|
||||||
|
|
||||||
import org.springframework.aop.framework.ProxyFactory;
|
import org.springframework.aop.framework.ProxyFactory;
|
||||||
import org.springframework.aop.testfixture.interceptor.NopInterceptor;
|
import org.springframework.aop.testfixture.interceptor.NopInterceptor;
|
||||||
import org.springframework.jmx.IJmxTestBean;
|
import org.springframework.jmx.ITestBean;
|
||||||
import org.springframework.jmx.JmxTestBean;
|
import org.springframework.jmx.JmxTestBean;
|
||||||
import org.springframework.jmx.export.MBeanExporter;
|
import org.springframework.jmx.export.MBeanExporter;
|
||||||
import org.springframework.jmx.export.metadata.JmxAttributeSource;
|
import org.springframework.jmx.export.metadata.JmxAttributeSource;
|
||||||
|
@ -156,7 +156,7 @@ public abstract class AbstractMetadataAssemblerTests extends AbstractJmxAssemble
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testWithCglibProxy() throws Exception {
|
void testWithCglibProxy() throws Exception {
|
||||||
IJmxTestBean tb = createJmxTestBean();
|
Object tb = createJmxTestBean();
|
||||||
ProxyFactory pf = new ProxyFactory();
|
ProxyFactory pf = new ProxyFactory();
|
||||||
pf.setTarget(tb);
|
pf.setTarget(tb);
|
||||||
pf.addAdvice(new NopInterceptor());
|
pf.addAdvice(new NopInterceptor());
|
||||||
|
@ -230,7 +230,7 @@ public abstract class AbstractMetadataAssemblerTests extends AbstractJmxAssemble
|
||||||
return 9;
|
return 9;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected IJmxTestBean createJmxTestBean() {
|
protected ITestBean createJmxTestBean() {
|
||||||
return new JmxTestBean();
|
return new JmxTestBean();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue