1/* 2 * Licensed to the Apache Software Foundation (ASF) under one or more 3 * contributor license agreements. See the NOTICE file distributed with 4 * this work for additional information regarding copyright ownership. 5 * The ASF licenses this file to You under the Apache License, Version 2.0 6 * (the "License"); you may not use this file except in compliance with 7 * the License. You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 */ 17 18package tests.api.java.lang.reflect; 19 20import java.lang.reflect.InvocationHandler; 21import java.lang.reflect.Method; 22import java.lang.reflect.Proxy; 23import java.lang.reflect.UndeclaredThrowableException; 24 25import tests.support.Support_Proxy_I1; 26import tests.support.Support_Proxy_I2; 27import tests.support.Support_Proxy_ParentException; 28import tests.support.Support_Proxy_SubException; 29 30public class ProxyTest extends junit.framework.TestCase { 31 32 /* 33 * When multiple interfaces define the same method, the list of thrown 34 * exceptions are those which can be mapped to another exception in the 35 * other method: 36 * 37 * String foo(String s) throws SubException, LinkageError; 38 * 39 * UndeclaredThrowableException wrappers any checked exception which is not 40 * in the merged list. So ParentException would be wrapped, BUT LinkageError 41 * would not be since its not an Error/RuntimeException. 42 * 43 * interface I1 { String foo(String s) throws ParentException, LinkageError; } 44 * interface I2 { String foo(String s) throws SubException, Error; } 45 */ 46 47 interface Broken1 { 48 public float method(float _number0, float _number1); 49 } 50 51 class Broken1Invoke implements InvocationHandler { 52 public Object invoke(Object proxy, Method method, Object[] args) 53 throws Throwable { 54 return args[1]; 55 } 56 } 57 58 class ProxyCoonstructorTest extends Proxy { 59 protected ProxyCoonstructorTest(InvocationHandler h) { 60 super(h); 61 } 62 } 63 64 /** 65 * java.lang.reflect.Proxy#getProxyClass(java.lang.ClassLoader, 66 * java.lang.Class[]) 67 */ 68 public void test_getProxyClassLjava_lang_ClassLoader$Ljava_lang_Class() { 69 Class proxy = Proxy.getProxyClass(Support_Proxy_I1.class 70 .getClassLoader(), new Class[] { Support_Proxy_I1.class }); 71 72 assertTrue("Did not create a Proxy subclass ", 73 proxy.getSuperclass() == Proxy.class); 74 assertTrue("Does not believe its a Proxy class ", Proxy 75 .isProxyClass(proxy)); 76 77 assertTrue("Does not believe it's a Proxy class ", Proxy 78 .isProxyClass(Proxy.getProxyClass(null, 79 new Class[] { Comparable.class }))); 80 81 try { 82 Proxy.getProxyClass(Support_Proxy_I1.class.getClassLoader(), 83 (Class<?>[]) null); 84 fail("NPE expected"); 85 } catch (NullPointerException expected) { 86 } 87 88 try { 89 Proxy.getProxyClass(Support_Proxy_I1.class.getClassLoader(), 90 new Class<?>[] {Support_Proxy_I1.class, null}); 91 fail("NPE expected"); 92 } catch (NullPointerException expected) { 93 } 94 } 95 96 /** 97 * java.lang.reflect.Proxy#Proxy(java.lang.reflect.InvocationHandler) 98 */ 99 public void test_ProxyLjava_lang_reflect_InvocationHandler() { 100 assertNotNull(new ProxyCoonstructorTest(new InvocationHandler() { 101 public Object invoke(Object proxy, Method method, Object[] args) 102 throws Throwable { 103 return null; 104 } 105 })); 106 } 107 108 109 110 /** 111 * java.lang.reflect.Proxy#newProxyInstance(java.lang.ClassLoader, 112 * java.lang.Class[], java.lang.reflect.InvocationHandler) 113 */ 114 public void test_newProxyInstanceLjava_lang_ClassLoader$Ljava_lang_ClassLjava_lang_reflect_InvocationHandler() { 115 Object p = Proxy.newProxyInstance(Support_Proxy_I1.class 116 .getClassLoader(), new Class[] { Support_Proxy_I1.class, 117 Support_Proxy_I2.class }, new InvocationHandler() { 118 public Object invoke(Object proxy, Method method, Object[] args) 119 throws Throwable { 120 if (method.getName().equals("equals")) 121 return new Boolean(proxy == args[0]); 122 if (method.getName().equals("array")) 123 return new int[] { (int) ((long[]) args[0])[1], -1 }; 124 if (method.getName().equals("string")) { 125 if ("".equals(args[0])) 126 throw new Support_Proxy_SubException(); 127 if ("clone".equals(args[0])) 128 throw new Support_Proxy_ParentException(); 129 if ("error".equals(args[0])) 130 throw new ArrayStoreException(); 131 if ("any".equals(args[0])) 132 throw new IllegalAccessException(); 133 } 134 return null; 135 } 136 }); 137 138 Support_Proxy_I1 proxy = (Support_Proxy_I1) p; 139 assertTrue("Failed identity test ", proxy.equals(proxy)); 140 assertTrue("Failed not equals test ", !proxy.equals("")); 141 int[] result = (int[]) proxy.array(new long[] { 100L, -200L }); 142 assertEquals("Failed primitive type conversion test ", -200, result[0]); 143 144 boolean worked = false; 145 try { 146 proxy.string(""); 147 } catch (Support_Proxy_SubException e) { 148 worked = true; 149 } catch (Support_Proxy_ParentException e) { // is never thrown 150 } 151 assertTrue("Problem converting exception ", worked); 152 153 worked = false; 154 try { 155 proxy.string("clone"); 156 } catch (Support_Proxy_ParentException e) { // is never thrown 157 } catch (UndeclaredThrowableException e) { 158 worked = true; 159 } 160 assertTrue("Problem converting exception ", worked); 161 162 worked = false; 163 try { 164 proxy.string("error"); 165 } catch (Support_Proxy_ParentException e) { // is never thrown 166 } catch (UndeclaredThrowableException e) { 167 } catch (RuntimeException e) { 168 worked = e.getClass() == ArrayStoreException.class; 169 } 170 assertTrue("Problem converting exception ", worked); 171 172 worked = false; 173 try { 174 proxy.string("any"); 175 } catch (Support_Proxy_ParentException e) { // is never thrown 176 } catch (UndeclaredThrowableException e) { 177 worked = true; 178 } 179 assertTrue("Problem converting exception ", worked); 180 181 Broken1 proxyObject = null; 182 try { 183 proxyObject = (Broken1) Proxy.newProxyInstance(Broken1.class 184 .getClassLoader(), new Class[] { Broken1.class }, 185 new Broken1Invoke()); 186 } catch (Throwable e) { 187 fail("Failed to create proxy for class: " + Broken1.class + " - " 188 + e); 189 } 190 float brokenResult = proxyObject.method(2.1f, 5.8f); 191 assertTrue("Invalid invoke result", brokenResult == 5.8f); 192 } 193 194 /** 195 * java.lang.reflect.Proxy#isProxyClass(java.lang.Class) 196 */ 197 public void test_isProxyClassLjava_lang_Class() { 198 Class proxy = Proxy.getProxyClass(Support_Proxy_I1.class 199 .getClassLoader(), new Class[] { Support_Proxy_I1.class }); 200 201 class Fake extends Proxy { 202 Fake() { 203 super(null); 204 } 205 } 206 207 Proxy fake = new Proxy(new InvocationHandler() { 208 public Object invoke(Object proxy, Method method, Object[] args) 209 throws Throwable { 210 return null; 211 } 212 }) { 213 }; 214 215 assertTrue("Does not believe its a Proxy class ", Proxy 216 .isProxyClass(proxy)); 217 assertTrue("Proxy subclasses do not count ", !Proxy 218 .isProxyClass(Fake.class)); 219 assertTrue("Is not a runtime generated Proxy class ", !Proxy 220 .isProxyClass(fake.getClass())); 221 boolean thrown = false; 222 try{ 223 Proxy.isProxyClass(null); 224 } catch (NullPointerException ex){ 225 thrown = true; 226 } 227 assertTrue("NPE not thrown.", thrown); 228 } 229 230 /** 231 * java.lang.reflect.Proxy#getInvocationHandler(java.lang.Object) 232 */ 233 public void test_getInvocationHandlerLjava_lang_Object() { 234 InvocationHandler handler = new InvocationHandler() { 235 public Object invoke(Object proxy, Method method, Object[] args) 236 throws Throwable { 237 return null; 238 } 239 }; 240 241 Object p = Proxy.newProxyInstance(Support_Proxy_I1.class 242 .getClassLoader(), new Class[] { Support_Proxy_I1.class }, 243 handler); 244 245 assertTrue("Did not return invocation handler ", Proxy 246 .getInvocationHandler(p) == handler); 247 boolean aborted = false; 248 try { 249 Proxy.getInvocationHandler(""); 250 } catch (IllegalArgumentException e) { 251 aborted = true; 252 } 253 assertTrue("Did not detect non proxy object ", aborted); 254 } 255 256 //Regression Test for HARMONY-2355 257 public void test_newProxyInstance_withCompatibleReturnTypes() { 258 Object o = Proxy 259 .newProxyInstance(this.getClass().getClassLoader(), 260 new Class[] { ITestReturnObject.class, 261 ITestReturnString.class }, 262 new TestProxyHandler(new TestProxyImpl())); 263 assertNotNull(o); 264 } 265 266 public void test_newProxyInstance_withNonCompatibleReturnTypes() { 267 try { 268 Proxy.newProxyInstance(this.getClass().getClassLoader(), 269 new Class[] { ITestReturnInteger.class, 270 ITestReturnString.class }, new TestProxyHandler( 271 new TestProxyImpl())); 272 fail("should throw IllegalArgumentException"); 273 } catch (IllegalArgumentException e) { 274 // expected 275 } 276 277 } 278 279 public static interface ITestReturnObject { 280 Object f(); 281 } 282 283 public static interface ITestReturnString { 284 String f(); 285 } 286 287 public static interface ITestReturnInteger { 288 Integer f(); 289 } 290 291 public static class TestProxyImpl implements ITestReturnObject, 292 ITestReturnString { 293 public String f() { 294 // do nothing 295 return null; 296 } 297 } 298 299 public static class TestProxyHandler implements InvocationHandler { 300 private Object proxied; 301 302 public TestProxyHandler(Object object) { 303 proxied = object; 304 } 305 306 public Object invoke(Object object, Method method, Object[] args) 307 throws Throwable { 308 // do nothing 309 return method.invoke(proxied, args); 310 } 311 312 } 313 314 protected void setUp() { 315 } 316 317 protected void tearDown() { 318 } 319} 320