0N/A/*
2362N/A * Copyright (c) 2003, Oracle and/or its affiliates. All rights reserved.
0N/A * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
0N/A *
0N/A * This code is free software; you can redistribute it and/or modify it
0N/A * under the terms of the GNU General Public License version 2 only, as
0N/A * published by the Free Software Foundation.
0N/A *
0N/A * This code is distributed in the hope that it will be useful, but WITHOUT
0N/A * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
0N/A * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
0N/A * version 2 for more details (a copy is included in the LICENSE file that
0N/A * accompanied this code).
0N/A *
0N/A * You should have received a copy of the GNU General Public License version
0N/A * 2 along with this work; if not, write to the Free Software Foundation,
0N/A * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
0N/A *
2362N/A * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
2362N/A * or visit www.oracle.com if you need additional information or have any
2362N/A * questions.
0N/A */
0N/A
0N/A/*
0N/A * @test
0N/A * @bug 4950756
0N/A * @summary Test that RequiredModelMBean.invoke will not invoke methods
0N/A * from the RequiredModelMBean class itself if they are not in the
0N/A * ModelMBeanInfo
0N/A * @author Eamonn McManus
0N/A * @run clean RequiredModelMBeanMethodTest
0N/A * @run build RequiredModelMBeanMethodTest
0N/A * @run main RequiredModelMBeanMethodTest
0N/A */
0N/A
0N/Aimport java.lang.reflect.*;
0N/Aimport javax.management.*;
0N/Aimport javax.management.modelmbean.*;
0N/A
0N/A/*
0N/A * We do the same test with a number of different operations:
0N/A *
0N/A * - A plain operation that is directed to the managed resource in the
0N/A * usual way. We give it some parameters so we can test that the
0N/A * class loading logic for signature parameters is reasonable.
0N/A *
0N/A * - An operation (removeNotificationListener) that is directed to the
0N/A * RequiredModelMBean itself. We use this particular operation because
0N/A * it will throw an exception, which allows us to check that it did in
0N/A * fact execute.
0N/A *
0N/A * - An operation (load()) that has the same signature as a
0N/A * RequiredModelMBean operation but is directed to the resource
0N/A * because of a "class" field in the descriptor.
0N/A *
0N/A * - An operation (store()) that has the same signature as a
0N/A * RequiredModelMBean operation but is directed to the resource
0N/A * because of a "targetObject" field in the descriptor.
0N/A *
0N/A * In each case we check that the operation does not work if it is not
0N/A * in the ModelMBeanInfo, and does work if it is.
0N/A */
0N/Apublic class RequiredModelMBeanMethodTest {
0N/A public static void main(String[] args) throws Exception {
0N/A boolean ok = true;
0N/A MBeanServer mbs = MBeanServerFactory.createMBeanServer();
0N/A
0N/A Descriptor tralalaDescriptor =
0N/A new DescriptorSupport(new String[] {
0N/A "name=tralala",
0N/A "descriptorType=operation",
0N/A "role=operation",
0N/A "targetType=ObjectReference",
0N/A });
0N/A Method tralalaMethod =
0N/A Resource.class.getMethod("tralala",
0N/A new Class[] {int.class, Resource.class});
0N/A ModelMBeanOperationInfo tralalaInfo =
0N/A new ModelMBeanOperationInfo("tralala descr", tralalaMethod,
0N/A tralalaDescriptor);
0N/A
0N/A Method remACNLMethod =
0N/A RequiredModelMBean.class.getMethod("removeAttributeChangeNotificationListener",
0N/A new Class[] {
0N/A NotificationListener.class,
0N/A String.class
0N/A });
0N/A ModelMBeanOperationInfo remACNLInfo =
0N/A new ModelMBeanOperationInfo("remACNL descr", remACNLMethod);
0N/A
0N/A Descriptor loadDescriptor =
0N/A new DescriptorSupport(new String[] {
0N/A "name=load",
0N/A "descriptorType=operation",
0N/A "role=operation",
0N/A "targetType=ObjectReference",
0N/A "class=" + Resource.class.getName(),
0N/A });
0N/A ModelMBeanOperationInfo loadInfo =
0N/A new ModelMBeanOperationInfo("load", "load descr",
0N/A new MBeanParameterInfo[0],
0N/A "void", ModelMBeanOperationInfo.ACTION,
0N/A loadDescriptor);
0N/A
0N/A Descriptor storeDescriptor =
0N/A new DescriptorSupport(new String[] {
0N/A "name=store",
0N/A "descriptorType=operation",
0N/A "role=operation",
0N/A "targetType=ObjectReference",
0N/A });
0N/A storeDescriptor.setField("targetObject", resource);
0N/A ModelMBeanOperationInfo storeInfo =
0N/A new ModelMBeanOperationInfo("store", "store descr",
0N/A new MBeanParameterInfo[0],
0N/A "void", ModelMBeanOperationInfo.ACTION,
0N/A storeDescriptor);
0N/A
0N/A ModelMBeanInfo emptyMMBI =
0N/A new ModelMBeanInfoSupport(Resource.class.getName(),
0N/A "empty descr",
0N/A null, null, null, null);
0N/A ModelMBean emptyMMB = new RequiredModelMBean(emptyMMBI);
0N/A emptyMMB.setManagedResource(resource, "ObjectReference");
0N/A ObjectName emptyMMBName = new ObjectName("test:type=Empty");
0N/A mbs.registerMBean(emptyMMB, emptyMMBName);
0N/A
0N/A System.out.println("Testing that we cannot call methods not in the " +
0N/A "ModelMBeanInfo");
0N/A try {
0N/A boolean thisok = test(mbs, emptyMMBName, false);
0N/A if (thisok)
0N/A System.out.println("...OK");
0N/A else
0N/A ok = false;
0N/A } catch (Exception e) {
0N/A System.out.println("TEST FAILED: Caught exception:");
0N/A e.printStackTrace(System.out);
0N/A ok = false;
0N/A }
0N/A
0N/A ModelMBeanOperationInfo[] opInfos = {
0N/A tralalaInfo, remACNLInfo, loadInfo, storeInfo,
0N/A };
0N/A ModelMBeanInfo fullMMBI =
0N/A new ModelMBeanInfoSupport(Resource.class.getName(),
0N/A "full descr",
0N/A null, null, opInfos, null);
0N/A ModelMBean fullMMB = new RequiredModelMBean(fullMMBI);
0N/A fullMMB.setManagedResource(resource, "ObjectReference");
0N/A ObjectName fullMMBName = new ObjectName("test:type=Full");
0N/A mbs.registerMBean(fullMMB, fullMMBName);
0N/A
0N/A
0N/A System.out.println();
0N/A System.out.println("Testing that we can call methods in the " +
0N/A "ModelMBeanInfo");
0N/A System.out.println(" and that \"class\" or \"targetObject\" in " +
0N/A "descriptor directs methods to resource");
0N/A try {
0N/A boolean thisok = test(mbs, fullMMBName, true);
0N/A if (thisok)
0N/A System.out.println("...OK");
0N/A else
0N/A ok = false;
0N/A } catch (Exception e) {
0N/A System.out.println("TEST FAILED: Caught exception:");
0N/A e.printStackTrace(System.out);
0N/A ok = false;
0N/A }
0N/A
0N/A if (ok) {
0N/A if (!resource.loadCalled || !resource.storeCalled) {
0N/A System.out.println("TEST FAILED: not called:" +
0N/A (resource.loadCalled ? "" : " load") +
0N/A (resource.storeCalled ? "" : " store"));
0N/A ok = false;
0N/A }
0N/A }
0N/A
0N/A // Test the invoke("class.method") form
0N/A if (ok) {
0N/A System.out.println("Testing invoke(\"class.method\")");
0N/A resource.loadCalled = false;
0N/A mbs.invoke(fullMMBName, Resource.class.getName() + ".load",
0N/A null, null);
0N/A if (!resource.loadCalled) {
0N/A System.out.println("TEST FAILED: load not called");
0N/A ok = false;
0N/A }
0N/A try {
0N/A mbs.invoke(fullMMBName,
0N/A RequiredModelMBean.class.getName() +
0N/A ".removeAttributeChangeNotificationListener",
0N/A new Object[] {boringListener, null},
0N/A new String[] {
0N/A NotificationListener.class.getName(),
0N/A String.class.getName(),
0N/A });
0N/A System.out.println("TEST FAILED: removeNotificationListener" +
0N/A " returned successfully but " +
0N/A "should not have");
0N/A ok = false;
0N/A } catch (MBeanException e) {
0N/A final Exception target = e.getTargetException();
0N/A if (target instanceof ListenerNotFoundException) {
0N/A // OK: there is no such listener
0N/A } else
0N/A throw e;
0N/A }
0N/A }
0N/A
0N/A if (ok)
0N/A System.out.println("Test passed");
0N/A else {
0N/A System.out.println("TEST FAILED");
0N/A System.exit(1);
0N/A }
0N/A }
0N/A
0N/A private static boolean test(MBeanServer mbs, ObjectName name,
0N/A boolean shouldWork)
0N/A throws Exception {
0N/A
0N/A boolean ok = true;
0N/A
0N/A final String[] names = {
0N/A "tralala",
0N/A "removeAttributeChangeNotificationListener",
0N/A "load",
0N/A "store",
0N/A };
0N/A
0N/A for (int i = 0; i < 4; i++) {
0N/A boolean thisok = true;
0N/A try {
0N/A switch (i) {
0N/A case 0:
0N/A String tralala = (String)
0N/A mbs.invoke(name, names[i],
0N/A new Object[] {new Integer(5), resource},
0N/A new String[] {"int",
0N/A Resource.class.getName()});
0N/A if (!"tralala".equals(tralala)) {
0N/A System.out.println("TEST FAILED: tralala returned: " +
0N/A tralala);
0N/A thisok = false;
0N/A }
0N/A break;
0N/A case 1:
0N/A try {
0N/A mbs.invoke(name,
0N/A names[i],
0N/A new Object[] {boringListener, null},
0N/A new String[] {
0N/A NotificationListener.class.getName(),
0N/A String.class.getName(),
0N/A });
0N/A System.out.println("TEST FAILED: " + names[i] +
0N/A " returned successfully but " +
0N/A "should not have");
0N/A thisok = false;
0N/A } catch (MBeanException e) {
0N/A final Exception target = e.getTargetException();
0N/A if (target instanceof ListenerNotFoundException) {
0N/A // OK: there is no such listener
0N/A } else
0N/A throw e;
0N/A }
0N/A break;
0N/A case 2:
0N/A case 3:
0N/A mbs.invoke(name,
0N/A names[i],
0N/A new Object[0],
0N/A new String[0]);
0N/A break;
0N/A default:
0N/A throw new AssertionError();
0N/A }
0N/A
0N/A thisok = shouldWork;
0N/A if (!shouldWork) {
0N/A System.out.println("TEST FAILED: " + names[i] +
0N/A " worked but should not");
0N/A }
0N/A } catch (MBeanException e) {
0N/A if (shouldWork) {
0N/A System.out.println("TEST FAILED: " + names[i] + ": " + e);
0N/A e.printStackTrace(System.out);
0N/A thisok = false;
0N/A } else {
0N/A Exception target = e.getTargetException();
0N/A if (!(target instanceof ServiceNotFoundException)) {
0N/A System.out.println("TEST FAILED: " + names[i] +
0N/A ": wrong exception: " + target);
0N/A thisok = false;
0N/A }
0N/A }
0N/A } catch (Exception e) {
0N/A System.out.println("TEST FAILED: " + names[i] + ": " + e);
0N/A e.printStackTrace(System.out);
0N/A thisok = false;
0N/A }
0N/A
0N/A if (thisok)
0N/A System.out.println("OK: " + names[i]);
0N/A else
0N/A ok = false;
0N/A }
0N/A
0N/A return ok;
0N/A }
0N/A
0N/A public static class Resource {
0N/A public String tralala(int x, Resource y) {
0N/A if (x != 5 || y != this)
0N/A return "wrong params: " + x + " " + y;
0N/A return "tralala";
0N/A }
0N/A
0N/A public void load() {
0N/A loadCalled = true;
0N/A }
0N/A
0N/A public void store() {
0N/A storeCalled = true;
0N/A }
0N/A
0N/A boolean loadCalled, storeCalled;
0N/A }
0N/A
0N/A private static Resource resource = new Resource();
0N/A
0N/A private static NotificationListener boringListener =
0N/A new NotificationListener() {
0N/A public void handleNotification(Notification n, Object h) {
0N/A }
0N/A };
0N/A}