001 /**
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements. See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License. You may obtain a copy of the License at
008 *
009 * http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017 package org.apache.activemq.console.filter;
018
019 import javax.management.Attribute;
020 import javax.management.AttributeList;
021 import javax.management.InstanceNotFoundException;
022 import javax.management.IntrospectionException;
023 import javax.management.MBeanAttributeInfo;
024 import javax.management.MBeanServerConnection;
025 import javax.management.ObjectInstance;
026 import javax.management.ObjectName;
027 import javax.management.ReflectionException;
028 import java.io.IOException;
029 import java.util.ArrayList;
030 import java.util.Collection;
031 import java.util.Iterator;
032 import java.util.List;
033 import java.util.Set;
034
035 public class MBeansAttributeQueryFilter extends AbstractQueryFilter {
036 public static final String KEY_OBJECT_NAME_ATTRIBUTE = "Attribute:ObjectName:";
037
038 private MBeanServerConnection jmxConnection;
039 private Set attribView;
040
041 /**
042 * Create an mbean attributes query filter that is able to select specific
043 * mbean attributes based on the object name to get.
044 *
045 * @param jmxConnection - JMX connection to use.
046 * @param attribView - the attributes to extract
047 * @param next - the next query filter
048 */
049 public MBeansAttributeQueryFilter(MBeanServerConnection jmxConnection, Set attribView, MBeansObjectNameQueryFilter next) {
050 super(next);
051 this.jmxConnection = jmxConnection;
052 this.attribView = attribView;
053 }
054
055 /**
056 * Filter the query by retrieving the attributes specified, this will modify
057 * the collection to a list of AttributeList
058 *
059 * @param queries - query list
060 * @return List of AttributeList, which includes the ObjectName, which has a
061 * key of MBeansAttributeQueryFilter.KEY_OBJECT_NAME_ATTRIBUTE
062 * @throws Exception
063 */
064 public List query(List queries) throws Exception {
065 return getMBeanAttributesCollection(next.query(queries));
066 }
067
068 /**
069 * Retrieve the specified attributes of the mbean
070 *
071 * @param result - collection of ObjectInstances and/or ObjectNames
072 * @return List of AttributeList
073 * @throws IOException
074 * @throws ReflectionException
075 * @throws InstanceNotFoundException
076 * @throws NoSuchMethodException
077 */
078 protected List getMBeanAttributesCollection(Collection result) throws IOException, ReflectionException, InstanceNotFoundException, NoSuchMethodException, IntrospectionException {
079 List mbeansCollection = new ArrayList();
080
081 for (Iterator i = result.iterator(); i.hasNext();) {
082 Object mbean = i.next();
083 if (mbean instanceof ObjectInstance) {
084 try {
085 mbeansCollection.add(getMBeanAttributes(((ObjectInstance)mbean).getObjectName(), attribView));
086 } catch (InstanceNotFoundException ignore) {
087 // mbean could have been deleted in the meantime
088 }
089 } else if (mbean instanceof ObjectName) {
090 try {
091 mbeansCollection.add(getMBeanAttributes((ObjectName)mbean, attribView));
092 } catch (InstanceNotFoundException ignore) {
093 // mbean could have been deleted in the meantime
094 }
095 } else {
096 throw new NoSuchMethodException("Cannot get the mbean attributes for class: " + mbean.getClass().getName());
097 }
098 }
099
100 return mbeansCollection;
101 }
102
103 /**
104 * Retrieve the specified attributes of the mbean
105 *
106 * @param obj - mbean ObjectInstance
107 * @param attrView - list of attributes to retrieve
108 * @return AttributeList for the mbean
109 * @throws ReflectionException
110 * @throws InstanceNotFoundException
111 * @throws IOException
112 */
113 protected AttributeList getMBeanAttributes(ObjectInstance obj, Set attrView) throws ReflectionException, InstanceNotFoundException, IOException, IntrospectionException {
114 return getMBeanAttributes(obj.getObjectName(), attrView);
115 }
116
117 /**
118 * Retrieve the specified attributes of the mbean
119 *
120 * @param objName - mbean ObjectName
121 * @param attrView - list of attributes to retrieve
122 * @return AttributeList for the mbean
123 * @throws IOException
124 * @throws ReflectionException
125 * @throws InstanceNotFoundException
126 */
127 protected AttributeList getMBeanAttributes(ObjectName objName, Set attrView) throws IOException, ReflectionException, InstanceNotFoundException, IntrospectionException {
128 // If no attribute view specified, get all attributes
129 String[] attribs;
130 if (attrView == null || attrView.isEmpty()) {
131 MBeanAttributeInfo[] infos = jmxConnection.getMBeanInfo(objName).getAttributes();
132 attribs = new String[infos.length];
133
134 for (int i = 0; i < infos.length; i++) {
135 if (infos[i].isReadable()) {
136 attribs[i] = infos[i].getName();
137 }
138 }
139
140 // Get selected attributes
141 } else {
142
143 attribs = new String[attrView.size()];
144 int count = 0;
145 for (Iterator i = attrView.iterator(); i.hasNext();) {
146 attribs[count++] = (String)i.next();
147 }
148 }
149
150 AttributeList attribList = jmxConnection.getAttributes(objName, attribs);
151
152 attribList.add(0, new Attribute(KEY_OBJECT_NAME_ATTRIBUTE, objName));
153
154 return attribList;
155 }
156 }