Lesson: Notifications
JMX API 定义了一种机制,使 MBean 能够生成通知,例如,以 signal 通知状态更改,检测到的事件或问题。
要生成通知,MBean 必须实现interfaceNotificationEmitter或扩展NotificationBroadcasterSupport。要发送通知,您需要构造javax.management.Notification类或子类(例如AttributeChangedNotification)的实例,并将该实例传递给NotificationBroadcasterSupport.sendNotification。
每个通知都有一个来源。源是生成通知的 MBean 的对象名称。
每个通知都有一个序列号。当订单很重要时,此数字可用于 Order 来自同一来源的通知,并且存在以错误的 Sequences 处理通知的风险。序列号可以为零,但是对于给定 MBean 的每个通知,序列号最好递增。
Standard MBeans中的Hello MBean 实现实际上实现了通知机制。但是,为简单起见,本类中省略了此代码。 Hello
的完整代码如下:
package com.example;
import javax.management.*;
public class Hello
extends NotificationBroadcasterSupport
implements HelloMBean {
public void sayHello() {
System.out.println("hello, world");
}
public int add(int x, int y) {
return x + y;
}
public String getName() {
return this.name;
}
public int getCacheSize() {
return this.cacheSize;
}
public synchronized void setCacheSize(int size) {
int oldSize = this.cacheSize;
this.cacheSize = size;
System.out.println("Cache size now " + this.cacheSize);
Notification n = new AttributeChangeNotification(this,
sequenceNumber++, System.currentTimeMillis(),
"CacheSize changed", "CacheSize", "int",
oldSize, this.cacheSize);
sendNotification(n);
}
@Override
public MBeanNotificationInfo[] getNotificationInfo() {
String[] types = new String[]{
AttributeChangeNotification.ATTRIBUTE_CHANGE
};
String name = AttributeChangeNotification.class.getName();
String description = "An attribute of this MBean has changed";
MBeanNotificationInfo info =
new MBeanNotificationInfo(types, name, description);
return new MBeanNotificationInfo[]{info};
}
private final String name = "Reginald";
private int cacheSize = DEFAULT_CACHE_SIZE;
private static final int DEFAULT_CACHE_SIZE = 200;
private long sequenceNumber = 1;
}
此Hello
MBean 实现扩展了NotificationBroadcasterSupport
类。 NotificationBroadcasterSupport
实现NotificationEmitter
interface。
操作和属性的设置方式与标准 MBean 示例中的设置方式相同,不同之处在于CacheSize
属性的 setter 方法现在定义了oldSize
的值。该值记录设置操作之前CacheSize
属性的值。
该通知是从扩展javax.management.Notification
的 JMX 类AttributeChangeNotification
的实例n
构造的。通知是根据以下信息在setCacheSize()
方法的定义内构造的。此信息作为参数传递到AttributeChangeNotification
。
-
通知源的对象名称,即
Hello
MBean,由this
表示 -
序列号
sequenceNumber
,设置为 1 并递增。 -
A timestamp
-
通知消息的内容
-
已更改的属性的名称,在这种情况下为
CacheSize
-
更改的属性类型
-
旧的属性值,在这种情况下为
oldSize
-
新的属性值,在这种情况下为
this.cacheSize
然后将通知n
传递给NotificationBroadcasterSupport.sendNotification()
方法。
最后,定义MBeanNotificationInfo实例以描述 MBean 为给定类型的通知生成的不同通知实例的 Feature。在这种情况下,发送的通知类型为AttributeChangeNotification
条通知。
运行 MBean 通知示例
再次,您将使用 JConsole 与Hello
MBean 进行交互,这次发送和接收通知。此示例需要 Java SE 平台的版本 6.
-
如果尚未这样做,请将jmx_examples.zip保存到
work_dir
目录中。 -
通过在终端窗口中使用以下命令来解压缩 samples 类包。
unzip jmx_examples.zip
- 从
work_dir
目录中编译示例 Java 类。
javac com/example/*.java
- 启动
Main
应用程序。
java com.example.Main
生成确认Main
正在 await 发生的事情。
- 在同一台计算机上的另一个终端窗口中启动 JConsole。
jconsole
将显示“新建连接”对话框,其中列出了可以连接的正在运行的 JMX 代理。
- 在“新建连接”对话框中,从列表中选择
com.example.Main
,然后单击“连接”。
显示平台当前活动的摘要。
- 单击“ MBeans”选项卡。
此面板显示当前在 MBean 服务器中注册的所有 MBean。
- 在左框架中,展开 MBean 树中的
com.example
节点。
您将看到由Hello
创建和注册的示例 MBean Hello
。如果单击Hello
,则会在 MBean 树中看到其 Notifications 节点。
- 展开 MBean 树中的
Hello
MBean 的 Notifications 节点。
请注意该面板是空白的。
- 单击订阅按钮。
当前收到的通知数(0)显示在“通知”节点标签中。
- 展开 MBean 树中的
Hello
MBean 的“属性”节点,并将CacheSize
属性的值更改为 150.
在您启动Main
的终端窗口中,显示此属性更改的确认。请注意,“通知”节点中显示的接收到的通知数已更改为 1.
- 再次展开 MBean 树中
Hello
MBean 的 Notifications 节点。
显示通知的详细信息。
- 要关闭 JConsole,请选择连接->退出。