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.camel.component.bean; 018 019 import java.lang.reflect.Proxy; 020 021 import org.apache.camel.Endpoint; 022 import org.apache.camel.Producer; 023 import org.apache.camel.util.ServiceHelper; 024 025 /** 026 * A helper class for creating proxies which delegate to Camel 027 * 028 * @version 029 */ 030 public final class ProxyHelper { 031 032 /** 033 * Utility classes should not have a public constructor. 034 */ 035 private ProxyHelper() { 036 } 037 038 /** 039 * Creates a Proxy which sends the exchange to the endpoint. 040 */ 041 @SuppressWarnings("unchecked") 042 public static <T> T createProxyObject(Endpoint endpoint, Producer producer, ClassLoader classLoader, Class<T>[] interfaces, MethodInfoCache methodCache) { 043 return (T) Proxy.newProxyInstance(classLoader, interfaces.clone(), new CamelInvocationHandler(endpoint, producer, methodCache)); 044 } 045 046 /** 047 * Creates a Proxy which sends the exchange to the endpoint. 048 */ 049 public static <T> T createProxy(Endpoint endpoint, ClassLoader cl, Class<T> interfaceClass, MethodInfoCache methodCache) throws Exception { 050 return createProxy(endpoint, cl, toArray(interfaceClass), methodCache); 051 } 052 053 /** 054 * Creates a Proxy which sends the exchange to the endpoint. 055 */ 056 public static <T> T createProxy(Endpoint endpoint, ClassLoader cl, Class<T>[] interfaceClasses, MethodInfoCache methodCache) throws Exception { 057 Producer producer = endpoint.createProducer(); 058 // ensure the producer is started 059 ServiceHelper.startService(producer); 060 return createProxyObject(endpoint, producer, cl, interfaceClasses, methodCache); 061 } 062 063 /** 064 * Creates a Proxy which sends the exchange to the endpoint. 065 */ 066 public static <T> T createProxy(Endpoint endpoint, ClassLoader cl, Class<T> interfaceClass) throws Exception { 067 return createProxy(endpoint, cl, toArray(interfaceClass)); 068 } 069 070 /** 071 * Creates a Proxy which sends the exchange to the endpoint. 072 */ 073 public static <T> T createProxy(Endpoint endpoint, ClassLoader cl, Class<T>... interfaceClasses) throws Exception { 074 return createProxy(endpoint, cl, interfaceClasses, createMethodInfoCache(endpoint)); 075 } 076 077 /** 078 * Creates a Proxy which sends the exchange to the endpoint. 079 */ 080 public static <T> T createProxy(Endpoint endpoint, Class<T> interfaceClass) throws Exception { 081 return createProxy(endpoint, toArray(interfaceClass)); 082 } 083 084 /** 085 * Creates a Proxy which sends the exchange to the endpoint. 086 */ 087 public static <T> T createProxy(Endpoint endpoint, Class<T>... interfaceClasses) throws Exception { 088 return createProxy(endpoint, getClassLoader(interfaceClasses), interfaceClasses); 089 } 090 091 /** 092 * Creates a Proxy which sends the exchange to the endpoint. 093 */ 094 public static <T> T createProxy(Endpoint endpoint, Producer producer, Class<T> interfaceClass) throws Exception { 095 return createProxy(endpoint, producer, toArray(interfaceClass)); 096 } 097 098 /** 099 * Creates a Proxy which sends the exchange to the endpoint. 100 */ 101 public static <T> T createProxy(Endpoint endpoint, Producer producer, Class<T>... interfaceClasses) throws Exception { 102 return createProxyObject(endpoint, producer, getClassLoader(interfaceClasses), interfaceClasses, createMethodInfoCache(endpoint)); 103 } 104 105 /** 106 * Returns the class loader of the first interface or throws {@link IllegalArgumentException} if there are no interfaces specified 107 */ 108 protected static ClassLoader getClassLoader(Class<?>... interfaces) { 109 if (interfaces == null || interfaces.length < 1) { 110 throw new IllegalArgumentException("You must provide at least 1 interface class."); 111 } 112 return interfaces[0].getClassLoader(); 113 } 114 115 protected static MethodInfoCache createMethodInfoCache(Endpoint endpoint) { 116 return new MethodInfoCache(endpoint.getCamelContext()); 117 } 118 119 @SuppressWarnings("unchecked") 120 private static <T> Class<T>[] toArray(Class<T> interfaceClass) { 121 // this method and it's usage is introduced to avoid compiler warnings 122 // about the generic Class arrays in the case we've got only one single 123 // Class to build a Proxy for 124 return new Class[] {interfaceClass}; 125 } 126 }