| Commit in servicemix/base/src on MAIN | |||
| main/java/org/servicemix/jbi/management/ManagementContext.java | +1 | -18 | 1.15 -> 1.16 |
| /BaseStandardMBean.java | +48 | -37 | 1.5 -> 1.6 |
| /MBeanBuilder.java | +2 | -26 | 1.2 -> 1.3 |
| /CachedAttribute.java | +40 | -12 | 1.2 -> 1.3 |
| /BaseDynamicMBean.java | -317 | 1.2 removed | |
| test/java/org/servicemix/jbi/management/ManagementAttributesTest.java | +84 | added 1.1 | |
| +175 | -410 | ||
Fix for SM-33 - ensure getAttributes() returns current values for attributes
servicemix/base/src/main/java/org/servicemix/jbi/management
diff -u -r1.15 -r1.16 --- ManagementContext.java 13 Aug 2005 21:55:18 -0000 1.15 +++ ManagementContext.java 19 Aug 2005 07:40:09 -0000 1.16 @@ -46,7 +46,7 @@
/** * A Flow provides different dispatch policies within the NMR *
- * @version $Revision: 1.15 $
+ * @version $Revision: 1.16 $
*/
public class ManagementContext extends BaseLifeCycle implements ManagementContextMBean {
/**
@@ -456,23 +456,6 @@
}
}
- /**
- * Register an MBean
- *
- * @param resource
- * @param name
- * @param description
- * @throws JMException
- */
- public void registerMBean(ObjectName name, Object resource, String description) throws JMException {
- if (beanServer != null) {
- Object mbean = MBeanBuilder.buildMBean(resource, description);
- if (!beanServer.isRegistered(name)) {
- beanServer.registerMBean(mbean, name);
- beanMap.put(resource, name);
- }
- }
- }
/**
* Retrive an System ObjectName
servicemix/base/src/main/java/org/servicemix/jbi/management
diff -u -r1.5 -r1.6 --- BaseStandardMBean.java 13 Jul 2005 08:59:10 -0000 1.5 +++ BaseStandardMBean.java 19 Aug 2005 07:40:09 -0000 1.6 @@ -63,22 +63,21 @@
/** * An MBean wrapper for an Existing Object *
- * @version $Revision: 1.5 $
+ * @version $Revision: 1.6 $
*/
public class BaseStandardMBean extends StandardMBean
implements
ModelMBeanNotificationBroadcaster,
MBeanRegistration,
PropertyChangeListener {
- private final static Log log = LogFactory.getLog(BaseDynamicMBean.class); - private Map cachedAttributes = new LinkedHashMap();//used to maintain insertion ordering
+ private final static Log log = LogFactory.getLog(BaseStandardMBean.class); + private Map cachedAttributes = new LinkedHashMap();// used to maintain insertion ordering
private PropertyUtilsBean beanUtil = new PropertyUtilsBean();
private NotificationBroadcasterSupport broadcasterSupport = new NotificationBroadcasterSupport();
protected PooledExecutor pooledExecutor;
private MBeanAttributeInfo[] attributeInfos;
- private MBeanOperationInfo[] operationInfos;
private MBeanInfo beanInfo;
- //this values are set after registering with the MBeanServer//
+ // this values are set after registering with the MBeanServer//
private ObjectName objectName;
private MBeanServer beanServer;
@@ -97,7 +96,6 @@
MBeanOperationInfo[] ops) throws ReflectionException, NotCompliantMBeanException {
super(object, interfaceMBean);
this.attributeInfos = attrs;
- this.operationInfos = ops;
buildAttributes(object, this.attributeInfos);
this.beanInfo = new MBeanInfo(object.getClass().getName(), description, attrs, null, ops, getNotificationInfo());
this.pooledExecutor = new PooledExecutor(new BoundedBuffer(1000), 2);
@@ -141,8 +139,8 @@
Object result = null;
CachedAttribute ca = (CachedAttribute) cachedAttributes.get(name);
if (ca == null) {
- //the use of proxies in MX4J has a bug - in which the caps can be changed on - //an attribute
+ // the use of proxies in MX4J has a bug - in which the caps can be changed on + // an attribute
for (Iterator i = cachedAttributes.entrySet().iterator();i.hasNext();) {
Map.Entry entry = (Map.Entry) i.next();
String key = entry.getKey().toString();
@@ -153,18 +151,7 @@
}
}
if (ca != null) {
- try {
- result = beanUtil.getProperty(ca.getBean(), ca.getName());
- }
- catch (IllegalAccessException e) {
- throw new MBeanException(e);
- }
- catch (InvocationTargetException e) {
- throw new MBeanException(e);
- }
- catch (NoSuchMethodException e) {
- throw new MBeanException(e);
- }
+ result = getCurrentValue(ca);
}
else {
throw new AttributeNotFoundException("Could not locate " + name);
@@ -244,21 +231,28 @@
*/
public AttributeList getAttributes(String[] attributes) {
AttributeList result = null;
- if (attributes != null) {
- result = new AttributeList();
- for (int i = 0;i < attributes.length;i++) {
- CachedAttribute ca = (CachedAttribute) cachedAttributes.get(attributes[i]);
- result.add(ca.getAttribute());
+ try {
+ if (attributes != null) {
+ result = new AttributeList();
+ for (int i = 0;i < attributes.length;i++) {
+ CachedAttribute ca = (CachedAttribute) cachedAttributes.get(attributes[i]);
+ ca.updateValue(beanUtil);
+ result.add(ca.getAttribute());
+ }
}
- }
- else {
- //Do this to maintain insertion ordering
- for (Iterator i = cachedAttributes.entrySet().iterator();i.hasNext();) {
- Map.Entry entry = (Map.Entry) i.next();
- CachedAttribute ca = (CachedAttribute) entry.getValue();
- result.add(ca.getAttribute());
+ else {
+ // Do this to maintain insertion ordering
+ for (Iterator i = cachedAttributes.entrySet().iterator();i.hasNext();) {
+ Map.Entry entry = (Map.Entry) i.next();
+ CachedAttribute ca = (CachedAttribute) entry.getValue();
+ ca.updateValue(beanUtil);
+ result.add(ca.getAttribute());
+ }
}
}
+ catch (MBeanException e) {
+ log.error("Caught excdeption building attributes", e);
+ }
return result;
}
@@ -363,16 +357,15 @@
public void sendNotification(final Notification notification) throws MBeanException, RuntimeOperationsException {
if (notification != null) {
try {
- pooledExecutor.execute(new Runnable(){
- public void run(){
+ pooledExecutor.execute(new Runnable() {
+ public void run() {
broadcasterSupport.sendNotification(notification);
}
});
}
catch (InterruptedException e) {
- log.warn("failed to send Notification",e);
+ log.warn("failed to send Notification", e);
}
-
}
}
@@ -434,7 +427,6 @@
public void sendAttributeChangeNotification(Attribute oldAttr, Attribute newAttr) throws MBeanException,
RuntimeOperationsException {
if (!oldAttr.equals(newAttr)) {
-
AttributeChangeNotification notification = new AttributeChangeNotification(objectName, 1, ((new Date())
.getTime()), "AttributeChange", oldAttr.getName(), (((newAttr.getValue()).getClass()).toString()),
oldAttr.getValue(), newAttr.getValue());
@@ -475,6 +467,25 @@
*/
public void removeNotificationListener(NotificationListener l) throws ListenerNotFoundException {
broadcasterSupport.removeNotificationListener(l);
+ }
+
+ private Object getCurrentValue(CachedAttribute ca) throws MBeanException {
+ Object result = null;
+ if (ca != null) {
+ try {
+ result = beanUtil.getProperty(ca.getBean(), ca.getName());
+ }
+ catch (IllegalAccessException e) {
+ throw new MBeanException(e);
+ }
+ catch (InvocationTargetException e) {
+ throw new MBeanException(e);
+ }
+ catch (NoSuchMethodException e) {
+ throw new MBeanException(e);
+ }
+ }
+ return result;
}
/**
servicemix/base/src/main/java/org/servicemix/jbi/management
diff -u -r1.2 -r1.3 --- MBeanBuilder.java 22 Jun 2005 15:50:39 -0000 1.2 +++ MBeanBuilder.java 19 Aug 2005 07:40:09 -0000 1.3 @@ -34,34 +34,10 @@
/** * Builds a DynamicMBean wrappers for existing objects *
- * @version $Revision: 1.2 $
+ * @version $Revision: 1.3 $
*/
class MBeanBuilder {
- /**
- * Build an MBean
- *
- * @param theObject
- * @param description
- * @return the MBean wrapper
- * @throws JMException
- */
- static DynamicMBean buildMBean(Object theObject, String description) throws JMException {
- DynamicMBean result = null;
- if (theObject != null) {
- if (theObject instanceof MBeanInfoProvider) {
- MBeanInfoProvider info = (MBeanInfoProvider) theObject;
- result = new BaseDynamicMBean(info.getObjectToManage(), description, info.getAttributeInfos(), info
- .getOperationInfos());
- }
- else {
- //theObject is the object to wrap, need to introspect to find values
- MBeanAttributeInfo[] attrs = getAttributes(theObject);
- MBeanOperationInfo[] ops = getOperations(attrs, theObject);
- result = new BaseDynamicMBean(theObject, description, attrs, ops);
- }
- }
- return result;
- }
+
/**
* Build an MBean
servicemix/base/src/main/java/org/servicemix/jbi/management
diff -u -r1.2 -r1.3 --- CachedAttribute.java 22 Jun 2005 15:50:39 -0000 1.2 +++ CachedAttribute.java 19 Aug 2005 07:40:09 -0000 1.3 @@ -22,12 +22,13 @@
import java.lang.reflect.InvocationTargetException; import javax.management.Attribute; import javax.management.MBeanAttributeInfo;
+import javax.management.MBeanException;
import org.apache.commons.beanutils.PropertyUtilsBean; /** * A simple holder for an Attribute and a PropertyDescriptor *
- * @version $Revision: 1.2 $
+ * @version $Revision: 1.3 $
*/
public class CachedAttribute {
private Object bean;
@@ -35,16 +36,17 @@
private Attribute attribute;
private MBeanAttributeInfo attributeInfo;
private PropertyDescriptor propertyDescriptor;
-
/**
* Constructor
+ *
* @param attr
*/
- public CachedAttribute(Attribute attr){
+ public CachedAttribute(Attribute attr) {
this.attribute = attr;
this.name = attr.getName();
}
+
/**
* @return Returns the name.
*/
@@ -65,39 +67,65 @@
public Attribute getAttribute() {
return attribute;
}
-
+
/**
* Set the Attribute
+ *
* @param attribute
*/
- public void setAttribute(Attribute attribute){
+ public void setAttribute(Attribute attribute) {
this.attribute = attribute;
}
/**
+ * Ensdure attribute value is up to date
+ *
+ * @param beanUtil
+ * @throws MBeanException
+ */
+ public void updateValue(PropertyUtilsBean beanUtil) throws MBeanException {
+ try {
+ Object value = beanUtil.getProperty(bean, getName());
+ if (value != attribute.getValue()) {
+ this.attribute = new Attribute(getName(), value);
+ }
+ }
+ catch (IllegalAccessException e) {
+ throw new MBeanException(e);
+ }
+ catch (InvocationTargetException e) {
+ throw new MBeanException(e);
+ }
+ catch (NoSuchMethodException e) {
+ throw new MBeanException(e);
+ }
+ }
+
+ /**
* Update the Attribute
- * @param beanUtils
*
+ * @param beanUtils
* @param attribute The attribute to set.
* @throws IllegalAccessException
* @throws InvocationTargetException
* @throws NoSuchMethodException
*/
- public void updateAttribute(PropertyUtilsBean beanUtils,Attribute attribute) throws IllegalAccessException, InvocationTargetException,
- NoSuchMethodException {
+ public void updateAttribute(PropertyUtilsBean beanUtils, Attribute attribute) throws IllegalAccessException,
+ InvocationTargetException, NoSuchMethodException {
if (this.attribute != null && propertyDescriptor != null) {
- //update object value
+ // update object value
beanUtils.setProperty(bean, getName(), attribute.getValue());
}
this.attribute = attribute;
}
-
+
/**
* Update that attribute value
+ *
* @param value
*/
- public void updateAttributeValue(Object value){
- this.attribute = new Attribute(this.attribute.getName(),value);
+ public void updateAttributeValue(Object value) {
+ this.attribute = new Attribute(this.attribute.getName(), value);
}
/**
servicemix/base/src/main/java/org/servicemix/jbi/management
BaseDynamicMBean.java removed after 1.2
diff -N BaseDynamicMBean.java --- BaseDynamicMBean.java 22 Jun 2005 15:50:39 -0000 1.2 +++ /dev/null 1 Jan 1970 00:00:00 -0000 @@ -1,317 +0,0 @@
-/**
- * <a href="">ServiceMix: The open source ESB</a>
- *
- * Copyright 2005 RAJD Consultancy Ltd
- *
- * 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
- *
- * http://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.servicemix.jbi.management;
-import java.beans.PropertyDescriptor;
-import java.lang.reflect.InvocationTargetException;
-import java.util.Iterator;
-import java.util.LinkedHashMap;
-import java.util.Map;
-import javax.management.Attribute;
-import javax.management.AttributeList;
-import javax.management.AttributeNotFoundException;
-import javax.management.DynamicMBean;
-import javax.management.InvalidAttributeValueException;
-import javax.management.MBeanAttributeInfo;
-import javax.management.MBeanException;
-import javax.management.MBeanInfo;
-import javax.management.MBeanOperationInfo;
-import javax.management.MBeanRegistration;
-import javax.management.MBeanServer;
-import javax.management.ObjectName;
-import javax.management.ReflectionException;
-import org.apache.commons.beanutils.MethodUtils;
-import org.apache.commons.beanutils.PropertyUtilsBean;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
-
-/**
- * An MBean wrapper for an Existing Object
- *
- * @version $Revision: 1.2 $
- */
-public class BaseDynamicMBean implements DynamicMBean, MBeanRegistration {
- private final static Log log = LogFactory.getLog(BaseDynamicMBean.class);
- private Map cachedAttributes = new LinkedHashMap();//used to maintain insertion ordering
- private PropertyUtilsBean beanUtil = new PropertyUtilsBean();
- private MBeanAttributeInfo[] attributeInfos;
- private MBeanOperationInfo[] operationInfos;
- private MBeanInfo beanInfo;
- private Object theBean;
- //this values are set after registering with the MBeanServer//
- private ObjectName objectName;
- private MBeanServer beanServer;
-
- /**
- * Constructor
- *
- * @param object
- * @param description
- * @param attrs
- * @param ops
- * @throws ReflectionException
- */
- public BaseDynamicMBean(Object object, String description, MBeanAttributeInfo[] attrs, MBeanOperationInfo[] ops)
- throws ReflectionException {
- this.theBean = object;
- this.attributeInfos = attrs;
- this.operationInfos = ops;
- buildAttributes(this.theBean, this.attributeInfos);
- this.beanInfo = new MBeanInfo(this.theBean.getClass().getName(), description, attrs, null, ops, null);
- }
-
- /**
- * @return the MBeanINfo for this MBean
- */
- public MBeanInfo getMBeanInfo() {
- return beanInfo;
- }
-
- /**
- * Retrieve ObjectName of the MBean - set after registration
- *
- * @return the ObjectName of the MBean
- */
- public ObjectName getObjectName() {
- return objectName;
- }
-
- /**
- * Retrieve the MBeanServer - set after registration
- *
- * @return the beanServer
- */
- public MBeanServer getBeanServer() {
- return beanServer;
- }
-
- /**
- * Get the Value of an Attribute
- *
- * @param name
- * @return the value of the Attribute
- * @throws AttributeNotFoundException
- * @throws MBeanException
- * @throws ReflectionException
- */
- public Object getAttribute(String name) throws AttributeNotFoundException, MBeanException, ReflectionException {
- Object result = null;
- CachedAttribute ca = (CachedAttribute) cachedAttributes.get(name);
- if (ca != null) {
- try {
- Object value = beanUtil.getProperty(ca.getBean(), name);
- }
- catch (IllegalAccessException e) {
- throw new MBeanException(e);
- }
- catch (InvocationTargetException e) {
- throw new MBeanException(e);
- }
- catch (NoSuchMethodException e) {
- throw new MBeanException(e);
- }
- }
- else {
- throw new AttributeNotFoundException("Could not locate " + name);
- }
- return result;
- }
-
- /**
- * Set the Attribute
- *
- * @param attr
- * @throws AttributeNotFoundException
- * @throws InvalidAttributeValueException
- * @throws MBeanException
- * @throws ReflectionException
- */
- public void setAttribute(Attribute attr) throws AttributeNotFoundException, InvalidAttributeValueException,
- MBeanException, ReflectionException {
- String name = attr.getName();
- CachedAttribute ca = (CachedAttribute) cachedAttributes.get(name);
- if (ca != null) {
- try {
- ca.updateAttribute(beanUtil, attr);
- }
- catch (IllegalAccessException e) {
- throw new MBeanException(e);
- }
- catch (InvocationTargetException e) {
- throw new MBeanException(e);
- }
- catch (NoSuchMethodException e) {
- throw new MBeanException(e);
- }
- }
- else {
- throw new AttributeNotFoundException("Could not locate " + name);
- }
- }
-
- /**
- * @param attributes - array of Attribute names
- * @return AttributeList of matching Attributes
- */
- public AttributeList getAttributes(String[] attributes) {
- AttributeList result = null;
- if (attributes != null) {
- result = new AttributeList();
- for (int i = 0;i < attributes.length;i++) {
- CachedAttribute ca = (CachedAttribute) cachedAttributes.get(attributes[i]);
- result.add(ca.getAttribute());
- }
- }
- else {
- //Do this to maintain insertion ordering
- for (Iterator i = cachedAttributes.entrySet().iterator();i.hasNext();) {
- Map.Entry entry = (Map.Entry) i.next();
- CachedAttribute ca = (CachedAttribute) entry.getValue();
- result.add(ca.getAttribute());
- }
- }
- return result;
- }
-
- /**
- * Set values of Attributes
- *
- * @param attributes
- * @return the list of Attributes set with their new values
- */
- public AttributeList setAttributes(AttributeList attributes) {
- AttributeList result = new AttributeList();
- if (attributes != null) {
- for (int i = 0;i < attributes.size();i++) {
- Attribute attribute = (Attribute) attributes.get(i);
- try {
- setAttribute(attribute);
- }
- catch (AttributeNotFoundException e) {
- log.warn("Failed to setAttribute(" + attribute + ")", e);
- }
- catch (InvalidAttributeValueException e) {
- log.warn("Failed to setAttribute(" + attribute + ")", e);
- }
- catch (MBeanException e) {
- log.warn("Failed to setAttribute(" + attribute + ")", e);
- }
- catch (ReflectionException e) {
- log.warn("Failed to setAttribute(" + attribute + ")", e);
- }
- result.add(attribute);
- }
- }
- return result;
- }
-
- /**
- * Invoke an operation
- *
- * @param name
- * @param params
- * @param signature
- * @return result of invoking an operation
- * @throws MBeanException
- * @throws ReflectionException
- */
- public Object invoke(String name, Object[] params, String[] signature) throws MBeanException, ReflectionException {
- try {
- return MethodUtils.invokeMethod(theBean, name, params);
- }
- catch (NoSuchMethodException e) {
- throw new ReflectionException(e);
- }
- catch (IllegalAccessException e) {
- throw new ReflectionException(e);
- }
- catch (InvocationTargetException e) {
- throw new ReflectionException(e);
- }
- }
-
- /**
- * Called at registration
- *
- * @param mbs
- * @param on
- * @return the ObjectName
- * @throws Exception
- */
- public ObjectName preRegister(MBeanServer mbs, ObjectName on) throws Exception {
- this.beanServer = mbs;
- this.objectName = on;
- return on;
- }
-
- /**
- * Caled post registration
- *
- * @param done
- */
- public void postRegister(Boolean done) {
- }
-
- /**
- * Called before removal from the MBeanServer
- *
- * @throws Exception
- */
- public void preDeregister() throws Exception {
- }
-
- /**
- * Called after removal from the MBeanServer
- */
- public void postDeregister() {
- }
-
- /**
- * build internal Map of CachedAttributes
- *
- * @param obj
- * @param attrs
- * @throws ReflectionException
- */
- private void buildAttributes(Object obj, MBeanAttributeInfo[] attrs) throws ReflectionException {
- if (attrs != null) {
- for (int i = 0;i < attrs.length;i++) {
- try {
- String name = attrs[i].getName();
- PropertyDescriptor pd = beanUtil.getPropertyDescriptor(obj, name);
- Object value = beanUtil.getProperty(obj, name);
- Attribute attribute = new Attribute(name, value);
- CachedAttribute ca = new CachedAttribute(attribute);
- ca.setBean(obj);
- ca.setPropertyDescriptor(pd);
- cachedAttributes.put(name, ca);
- }
- catch (NoSuchMethodException e) {
- throw new ReflectionException(e);
- }
- catch (IllegalAccessException e) {
- throw new ReflectionException(e);
- }
- catch (InvocationTargetException e) {
- throw new ReflectionException(e);
- }
- }
- }
- }
-}
\ No newline at end of file
servicemix/base/src/test/java/org/servicemix/jbi/management
ManagementAttributesTest.java added at 1.1
diff -N ManagementAttributesTest.java --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ ManagementAttributesTest.java 19 Aug 2005 07:40:10 -0000 1.1 @@ -0,0 +1,84 @@
+/*
+ * Created on Jun 15, 2005
+ *
+ * To change the template for this generated file go to
+ * Window - Preferences - Java - Code Generation - Code and Comments
+ */
+
+package org.servicemix.jbi.management;
+import javax.jbi.management.LifeCycleMBean;
+import java.util.*;
+import javax.management.*;
+import javax.management.MBeanServerDelegateMBean;
+import javax.management.MBeanServerInvocationHandler;
+import javax.management.ObjectName;
+import javax.management.remote.JMXConnector;
+import javax.management.remote.JMXConnectorFactory;
+import javax.management.remote.JMXServiceURL;
+import junit.framework.TestCase;
+import org.servicemix.jbi.container.JBIContainer;
+import org.servicemix.jbi.nmr.Broker;
+
+/**
+ * ManagementContextTest
+ */
+public class ManagementAttributesTest extends TestCase {
+ JBIContainer container;
+
+ protected void setUp() throws Exception {
+ container = new JBIContainer();
+ container.setCreateMBeanServer(true);
+ container.init();
+ container.start();
+ }
+
+ protected void tearDown() throws Exception {
+ container.shutDown();
+ }
+
+ public void testRemote() throws Exception {
+ // The JMXConnectorServer protocol, in this case is RMI.
+ String serverProtocol = "rmi";
+ // The RMI server's host: this is actually ignored by JSR 160
+ // since this information is stored in the RMI stub.
+
+ // The host, port and path where the rmiregistry runs.
+ String namingHost = "localhost";
+ int namingPort = 1099;
+ String jndiPath = "/" + JBIContainer.DEFAULT_NAME + "JMX";
+ // The address of the connector server
+ JMXServiceURL url = "" JMXServiceURL("service:jmx:rmi:///jndi/rmi://"
+ + namingHost + ":" + namingPort + jndiPath);
+ // Connect a JSR 160 JMXConnector to the server side
+ JMXConnector connector = JMXConnectorFactory.connect(url);
+ // Retrieve an MBeanServerConnection that represent the MBeanServer the remote
+ // connector server is bound to
+ MBeanServerConnection connection = connector.getMBeanServerConnection();
+
+ System.out.println(connection.getMBeanCount());
+
+
+ Set set = connection.queryNames(new ObjectName(connection.getDefaultDomain() + ":*"), null);
+ for (Iterator iter = set.iterator(); iter.hasNext();) {
+ ObjectName name = (ObjectName)iter.next();
+ System.out.println(name.toString());
+ MBeanInfo info = connection.getMBeanInfo(name);
+ MBeanAttributeInfo[] mia = info.getAttributes();
+ String[] attrNames = new String[mia.length];
+ for (int i = 0; i < mia.length; i++) {
+ attrNames[i] = mia[i].getName();
+ System.out.println("attr " + mia[i].getName() + " " + mia[i].getType() + " " + connection.getAttribute(name,mia[i].getName()));
+ }
+
+ AttributeList attributeList = (AttributeList) connection.getAttributes(name,attrNames);
+ for (int i = 0; i < attributeList.size(); i++) {
+ Attribute attribute = (Attribute) attributeList.get(i);
+ System.out.println("bulk " + attribute.getName() + " " + attribute.getValue() + " " + attribute.toString());
+ }
+
+ }
+
+
+ }
+
+}
