1 //----------------------------------------------------------------------
2 //
3 // PerfectJPattern: "Design patterns are good but components are better!"
4 // IDelegate.java Copyright (c) 2009 Giovanni Azua Garcia
5 // bravegag@hotmail.com
6 //
7 // This program is free software; you can redistribute it and/or
8 // modify it under the terms of the GNU General Public License
9 // as published by the Free Software Foundation; either version 3
10 // of the License, or (at your option) any later version.
11 //
12 // This program is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 // GNU General Public License for more details.
16 //
17 // You should have received a copy of the GNU General Public License
18 // along with this program; if not, see <http://www.gnu.org/licenses/>.
19 //
20 //----------------------------------------------------------------------
21 package org.perfectjpattern.core.api.extras.delegate;
22
23 /**
24 * <b>Delegates Design Pattern</b>: Allows multiple objects implementing
25 * methods with different names but compatible signatures to be used
26 * interchangeably. It will also work with or without a target interface
27 * to implement i.e. using <code>IDelegate</code>.
28 * <br/><br/>
29 * The <code>IDelegator</code> interface simplifies and generalizes the
30 * steps in creating an Adapter. Delegates are simple to use, and
31 * a single delegate instance may be reused multiple times.
32 * <br/><br/>
33 * <b>Responsibility</b>: Definition of "Delegator".
34 * <br/><br/>
35 * <b>Notes</b>: Base source code implemented by Steve Lewis and Wilhelm
36 * Fitzpatrick and adapted to fit PerfectJPattern componentization
37 * criteria and code conventions.
38 *
39 * <br/><br/>
40 * Example usage:
41 * <pre><code>
42 * //
43 * // Example class that defines two methods that match in signature
44 * //
45 * class Example
46 * {
47 * //--------------------------------------------------------------------
48 * public static void
49 * staticMethod(String aValue)
50 * {
51 * System.out.println(aValue);
52 * }
53 *
54 * //--------------------------------------------------------------------
55 * public void
56 * memberMethod(String aValue)
57 * {
58 * System.out.println(aValue);
59 * }
60 * }
61 *
62 * //
63 * // Defines a common interface with method printValue
64 * //
65 * interface IPrinter
66 * {
67 * //--------------------------------------------------------------------
68 * public void
69 * printValue(String aValue);
70 * }
71 *
72 * //
73 * // Create instance of example class
74 * //
75 * Example myInstance = new Example();
76 *
77 * //
78 * // Example using DynamicDelegator without well defined target interface
79 * //
80 * IDelegator<IDelegate> myDynamicDelegator = new DynamicDelegator(
81 * Void.TYPE, String.class);
82 *
83 * //
84 * // Build appropriate IDelegate references
85 * //
86 * IDelegate myDelegate1 = myDynamicDelegator.build(Example.class,
87 * "staticMethod");
88 * IDelegate myDelegate2 = myDynamicDelegator.build(myInstance,
89 * "memberMethod");
90 *
91 * //
92 * // Use the Delegate references to invoke the target methods.
93 * //
94 * myDelegate1.invoke("Value1");
95 * myDelegate2.invoke("Value2");
96 *
97 * //
98 * // Example using well defined target interface
99 * //
100 * IDelegator<IPrinter> myPrinterDelegator = new Delegator(
101 * IPrinter.class);
102 *
103 * //
104 * // Build appropriate IPrinter references
105 * //
106 * IPrinter myPrinter1 = myPrinterDelegator.build(Example.class,
107 * "staticMethod");
108 * IPrinter myPrinter2 = myPrinterDelegator.build(myInstance,
109 * "memberMethod");
110 *
111 * //
112 * // Use the IPrinter interface reference.
113 * //
114 * myPrinter1.printValue("Value1");
115 * myPrinter2.printValue("Value2");
116 * </code></pre>
117 *
118 * @see <a href="http://www.onjava.com/pub/a/onjava/2003/05/21/delegates.html">
119 * Article: A Java Programmer Looks at C-Sharp Delegates</a>
120 *
121 * @param <I> Type interface that this <code>IDelegator</code> builds.
122 *
123 * @author <a href="mailto:smlewis@lordjoe.com">Steve Lewis</a>
124 * @author <a href="mailto:wilhelmf@agileinformatics.com">Wilhelm
125 * Fitzpatrick</a>
126 * @author <a href="mailto:bravegag@hotmail.com">Giovanni Azua</a>
127 * @version $Revision: 1.0 $ $Date: Jun 24, 2007 11:58:59 AM $
128 */
129 @SuppressWarnings("unchecked")
130 public
131 interface IDelegator<I>
132 {
133 //------------------------------------------------------------------------
134 // public
135 //------------------------------------------------------------------------
136 /**
137 * Returns Dynamic Proxy that implements the target generic parameter
138 * interface. The implementing Dynamic Proxy executes the underlying
139 * method identified by Class type and Method name.
140 *
141 * @param aTarget non-null class with a bindable static method.
142 * @param aMethodName name of the static method.
143 * @return Dynamic proxy implementing the target generic interface.
144 * @throws UnsupportedOperationException No suitable method found.
145 * @throws IllegalArgumentException 'aTarget' must not be null.
146 * @throws IllegalArgumentException 'aMethodName' must not be null.
147 */
148 public I
149 build(Class aTarget, String aMethodName)
150 throws IllegalArgumentException, UnsupportedOperationException;
151
152 //------------------------------------------------------------------------
153 /**
154 * Returns Dynamic Proxy that implements the target generic parameter
155 * interface. The implementing Dynamic Proxy executes the underlying
156 * method identified by Object instance and Method name.
157 *
158 * @param aTarget non-null target with a bindable method.
159 * @param aMethodName name of the method.
160 * @return Dynamic proxy implementing the target generic interface.
161 * @throws UnsupportedOperationException No suitable method found.
162 * @throws IllegalArgumentException 'aTarget' must not be null.
163 * @throws IllegalArgumentException 'aMethodName' must not be null.
164 */
165 public I
166 build(Object aTarget, String aMethodName)
167 throws IllegalArgumentException, UnsupportedOperationException;
168 }