Overview Package Class Use Source Tree Index Deprecated About
GNU Classpath (0.95)
Frames | No Frames

Source for javax.management.openmbean.CompositeDataInvocationHandler

 1:  /* CompositeDataInvocationHandler.java - Pseudo-accessors for CompositeData.
 2:  Copyright (C) 2007 Free Software Foundation
 3: 
 4: This file is part of GNU Classpath.
 5: 
 6: GNU Classpath is free software; you can redistribute it and/or modify
 7: it under the terms of the GNU General Public License as published by
 8: the Free Software Foundation; either version 2, or (at your option)
 9: any later version.
 10: 
 11: GNU Classpath is distributed in the hope that it will be useful, but
 12: WITHOUT ANY WARRANTY; without even the implied warranty of
 13: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 14: General Public License for more details.
 15: 
 16: You should have received a copy of the GNU General Public License
 17: along with GNU Classpath; see the file COPYING. If not, write to the
 18: Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
 19: 02110-1301 USA.
 20: 
 21: Linking this library statically or dynamically with other modules is
 22: making a combined work based on this library. Thus, the terms and
 23: conditions of the GNU General Public License cover the whole
 24: combination.
 25: 
 26: As a special exception, the copyright holders of this library give you
 27: permission to link this library with independent modules to produce an
 28: executable, regardless of the license terms of these independent
 29: modules, and to copy and distribute the resulting executable under
 30: terms of your choice, provided that you also meet, for each linked
 31: independent module, the terms and conditions of the license of that
 32: module. An independent module is a module which is not derived from
 33: or based on this library. If you modify this library, you may extend
 34: this exception to your version of the library, but you are not
 35: obligated to do so. If you do not wish to do so, delete this
 36: exception statement from your version. */
 37: 
 38:  package javax.management.openmbean;
 39: 
 40:  import java.lang.reflect.InvocationHandler;
 41:  import java.lang.reflect.Method;
 42:  import java.lang.reflect.Proxy;
 43: 
 44:  /**
 45:  * <p>
 46:  * Provides an {@link java.lang.reflect.InvocationHandler} which
 47:  * implements a series of accessor methods (those beginning with
 48:  * {@code "get"} or {@code "is"}) using the content of a
 49:  * {@link CompositeData} object. An instance of {@link CompositeData}
 50:  * consists of a series of key-value mappings. This handler assumes
 51:  * these keys to be the names of attributes, and thus provides
 52:  * accessor methods by returning the associated value. 
 53:  * </p>
 54:  * <p>
 55:  * As an example, consider the following interface:
 56:  * </p>
 57:  * <pre>
 58:  * public interface Person
 59:  * {
 60:  * public String getName();
 61:  * public Date getBirthday();
 62:  * }
 63:  * </pre>
 64:  * <p>
 65:  * This specifies two accessor methods for retrieving the attributes,
 66:  * {@code name} and {@code birthday}. An implementation of this interface
 67:  * can be provided by creating an instance of this class, using a
 68:  * {@link CompositeData} object with appropriate key-value mappings
 69:  * (e.g. "name" => "Fred", "birthday" => 30/06/1974), and then passing
 70:  * that to {@link java.lang.reflect.Proxy#newProxyInstance} along with
 71:  * the interface itself. The invocation handler implements the methods
 72:  * by calling {@link CompositeData#get(String)} with the appropriate key.
 73:  * </p>
 74:  * <p>
 75:  * The attribute name is derived by taking the remainder of the method
 76:  * name following {@code "get"}. If the first letter of this substring
 77:  * is uppercase, then two attempts are made to retrieve the attribute
 78:  * from the {@link CompositeData} instance: one using the original substring,
 79:  * and one with the first letter changed to its lower-case equivalent.
 80:  * If the first letter is lowercase, only the exact substring is used.
 81:  * </p>
 82:  * <p>
 83:  * An {@link Object#equals(Object)} implementation is provided. This returns
 84:  * true if the argument is a proxy with a {@link CompositeDataInvocationHandler}
 85:  * using an equivalent {@link CompositeData} instance. {@link Object#hashCode()}
 86:  * is also defined so as to match this implementation and give equivalent instances
 87:  * the same hashcode.
 88:  * </p>
 89:  *
 90:  * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
 91:  * @since 1.6
 92:  */
 93:  public class CompositeDataInvocationHandler
 94:  implements InvocationHandler
 95: {
 96: 
 97:  /**
 98:  * The {@link CompositeData} providing the key-value mappings.
 99:  */
 100:  private CompositeData data;
 101: 
 102:  /**
 103:  * Constructs a new {@link CompositeDataInvocationHandler}
 104:  * with the specified {@link CompositeData} instance.
 105:  *
 106:  * @param data the {@link CompositeData} instance to use.
 107:  * @throws IllegalArgumentException if {@code data} is {@code null}.
 108:  */
 109:  public CompositeDataInvocationHandler(CompositeData data)
 110:  {
 111:  if (data == null)
 112:  throw new IllegalArgumentException("The CompositeData instance " +
 113:  "must be non-null.");
 114:  this.data = data;
 115:  }
 116: 
 117:  /**
 118:  * Returns the {@link CompositeData} instance which provides
 119:  * the key-value mappings for this instance. This is never
 120:  * {@code null}.
 121:  *
 122:  * @return the {@link CompositeData} instance.
 123:  */
 124:  public CompositeData getCompositeData()
 125:  {
 126:  return data;
 127:  }
 128: 
 129:  /**
 130:  * Called by the proxy class whenever a method is called. The
 131:  * handler only deals with accessor methods (beginning with
 132:  * {@code "get"} or {@code "is"}), {@code equals}, and
 133:  * {@code "hashCode"}. Accessor methods are implemented by
 134:  * returning the appropriate value from the {@link CompositeData}
 135:  * instance, while {@code equals} and {@code hashCode} allow
 136:  * two proxies with a {@link CompositeDataInvocationHandler} using
 137:  * the same {@link CompositeData} instance to be classified
 138:  * as equivalent.
 139:  *
 140:  * @param proxy the proxy on which the method was called.
 141:  * @param method the method which was called.
 142:  * @param args the arguments supplied to the method.
 143:  * @return the return value from the method.
 144:  * @throws Throwable if an exception is thrown in the process.
 145:  */
 146:  public Object invoke(Object proxy, Method method, Object[] args)
 147:  throws Throwable
 148:  {
 149:  String mName = method.getName();
 150:  if (mName.equals("equals"))
 151:  {
 152:  if (args[0] instanceof Proxy)
 153:  {
 154:  InvocationHandler h = Proxy.getInvocationHandler(args[0]);
 155:  if (h instanceof CompositeDataInvocationHandler)
 156:  return data.equals(((CompositeDataInvocationHandler)
 157:  h).getCompositeData());
 158:  }
 159:  return false;
 160:  }
 161:  if (mName.equals("hashCode"))
 162:  {
 163:  return data.hashCode();
 164:  }
 165:  String attrib = null;
 166:  if (mName.startsWith("get"))
 167:  attrib = mName.substring(3);
 168:  else if (mName.startsWith("is"))
 169:  attrib = mName.substring(2);
 170:  if (attrib == null)
 171:  throw new NoSuchMethodException(mName + " is not an accessor.");
 172:  if (!data.containsKey(attrib))
 173:  {
 174:  if (Character.isLowerCase(attrib.charAt(0)))
 175:  throw new NoSuchMethodException("The attribute " +
 176:  attrib + " is not available " +
 177:  "in the given CompositeData " +
 178:  "object");
 179:  attrib = Character.toLowerCase(attrib.charAt(0))
 180:  + attrib.substring(1);
 181:  if (!data.containsKey(attrib))
 182:  throw new NoSuchMethodException("The attribute " +
 183:  attrib + " is not available " +
 184:  "in the given CompositeData " +
 185:  "object");
 186:  }
 187:  return data.get(attrib);
 188:  }
 189: 
 190: }
Overview Package Class Use Source Tree Index Deprecated About
GNU Classpath (0.95)

AltStyle によって変換されたページ (->オリジナル) /