summaryrefslogtreecommitdiffstats
path: root/sca-java-2.x/trunk/modules/implementation-java-runtime/src
diff options
context:
space:
mode:
authorbdaniel <bdaniel@13f79535-47bb-0310-9956-ffa450edef68>2010-08-18 13:53:47 +0000
committerbdaniel <bdaniel@13f79535-47bb-0310-9956-ffa450edef68>2010-08-18 13:53:47 +0000
commit219ae1935ec10aeb4b5a1955183272cda9a3a574 (patch)
tree1065600edfbc333f7df2fe79239d065efc34517c /sca-java-2.x/trunk/modules/implementation-java-runtime/src
parenta91e13d3e237ea8dcd91a1eafaecf47203e50768 (diff)
TUSCANY-3652 Inject callbacks at service invocation
git-svn-id: http://svn.us.apache.org/repos/asf/tuscany@986678 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'sca-java-2.x/trunk/modules/implementation-java-runtime/src')
-rw-r--r--sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceFactory.java5
-rw-r--r--sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceWrapper.java10
-rw-r--r--sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaAsyncImplementationInvoker.java7
-rw-r--r--sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaComponentContextProvider.java23
-rw-r--r--sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationInvoker.java50
-rw-r--r--sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationProvider.java6
-rw-r--r--sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaInstanceFactoryProvider.java34
7 files changed, 112 insertions, 23 deletions
diff --git a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceFactory.java b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceFactory.java
index 209546ce2f..f5d9860130 100644
--- a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceFactory.java
+++ b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceFactory.java
@@ -36,15 +36,18 @@ public class ReflectiveInstanceFactory<T> implements InstanceFactory<T> {
private final Injector<T>[] injectors;
private final EventInvoker<T> initInvoker;
private final EventInvoker<T> destroyInvoker;
+ private final Injector<T>[] callbackInjectors;
public ReflectiveInstanceFactory(Constructor<T> ctr,
ObjectFactory<?>[] ctrArgs,
Injector<T>[] injectors,
+ Injector<T>[] callbackInjectors,
EventInvoker<T> initInvoker,
EventInvoker<T> destroyInvoker) {
this.ctr = ctr;
this.ctrArgs = ctrArgs;
this.injectors = injectors;
+ this.callbackInjectors = callbackInjectors;
this.initInvoker = initInvoker;
this.destroyInvoker = destroyInvoker;
}
@@ -88,6 +91,6 @@ public class ReflectiveInstanceFactory<T> implements InstanceFactory<T> {
}
}
- return new ReflectiveInstanceWrapper<T>(instance, initInvoker, destroyInvoker);
+ return new ReflectiveInstanceWrapper<T>(instance, initInvoker, destroyInvoker, callbackInjectors);
}
}
diff --git a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceWrapper.java b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceWrapper.java
index 7c96606cf6..a3ed16dde5 100644
--- a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceWrapper.java
+++ b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/context/ReflectiveInstanceWrapper.java
@@ -21,6 +21,7 @@ package org.apache.tuscany.sca.implementation.java.context;
import org.apache.tuscany.sca.core.factory.InstanceWrapper;
import org.apache.tuscany.sca.core.scope.TargetDestructionException;
import org.apache.tuscany.sca.core.scope.TargetInitializationException;
+import org.apache.tuscany.sca.implementation.java.injection.Injector;
import org.apache.tuscany.sca.implementation.java.invocation.EventInvoker;
/**
@@ -30,11 +31,13 @@ public class ReflectiveInstanceWrapper<T> implements InstanceWrapper<T> {
private final EventInvoker<T> initInvoker;
private final EventInvoker<T> destroyInvoker;
private final T instance;
+ private final Injector<T>[] callbackInjectors;
- public ReflectiveInstanceWrapper(T instance, EventInvoker<T> initInvoker, EventInvoker<T> destroyInvoker) {
+ public ReflectiveInstanceWrapper(T instance, EventInvoker<T> initInvoker, EventInvoker<T> destroyInvoker, Injector<T>[] callbackInjectors) {
this.instance = instance;
this.initInvoker = initInvoker;
this.destroyInvoker = destroyInvoker;
+ this.callbackInjectors = callbackInjectors;
}
public T getInstance() {
@@ -61,4 +64,9 @@ public class ReflectiveInstanceWrapper<T> implements InstanceWrapper<T> {
destroyInvoker.invokeEvent(instance);
}
}
+
+ public Injector<T>[] getCallbackInjectors() {
+ return this.callbackInjectors;
+ }
+
}
diff --git a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaAsyncImplementationInvoker.java b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaAsyncImplementationInvoker.java
index de810a0f02..97b7570faa 100644
--- a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaAsyncImplementationInvoker.java
+++ b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaAsyncImplementationInvoker.java
@@ -21,12 +21,12 @@ package org.apache.tuscany.sca.implementation.java.invocation;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
-import java.util.concurrent.TimeUnit;
import org.apache.tuscany.sca.core.factory.InstanceWrapper;
import org.apache.tuscany.sca.core.factory.ObjectCreationException;
import org.apache.tuscany.sca.core.invocation.AsyncResponseException;
import org.apache.tuscany.sca.interfacedef.DataType;
+import org.apache.tuscany.sca.interfacedef.InterfaceContract;
import org.apache.tuscany.sca.interfacedef.Operation;
import org.apache.tuscany.sca.interfacedef.java.JavaOperation;
import org.apache.tuscany.sca.invocation.Message;
@@ -41,8 +41,9 @@ import org.oasisopen.sca.ServiceRuntimeException;
*/
public class JavaAsyncImplementationInvoker extends JavaImplementationInvoker {
- public JavaAsyncImplementationInvoker(Operation operation, Method method, RuntimeComponent component) {
- super( operation, method, component);
+ public JavaAsyncImplementationInvoker(Operation operation, Method method, RuntimeComponent component,
+ InterfaceContract interfaceContract) {
+ super( operation, method, component, interfaceContract);
assert method != null : "Operation method cannot be null";
assert ((JavaOperation) operation).isAsyncServer() : "Operation must be async";
} // end constructor
diff --git a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaComponentContextProvider.java b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaComponentContextProvider.java
index ea9aec5238..1fa51315c3 100644
--- a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaComponentContextProvider.java
+++ b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaComponentContextProvider.java
@@ -52,10 +52,13 @@ import org.apache.tuscany.sca.core.scope.TargetResolutionException;
import org.apache.tuscany.sca.databinding.DataBindingExtensionPoint;
import org.apache.tuscany.sca.implementation.java.JavaConstructorImpl;
import org.apache.tuscany.sca.implementation.java.JavaElementImpl;
+import org.apache.tuscany.sca.implementation.java.JavaImplementation;
import org.apache.tuscany.sca.implementation.java.JavaResourceImpl;
+import org.apache.tuscany.sca.implementation.java.JavaScopeImpl;
import org.apache.tuscany.sca.implementation.java.context.InstanceFactory;
import org.apache.tuscany.sca.implementation.java.injection.JavaPropertyValueObjectFactory;
import org.apache.tuscany.sca.implementation.java.introspect.JavaIntrospectionHelper;
+import org.apache.tuscany.sca.interfacedef.InterfaceContract;
import org.apache.tuscany.sca.interfacedef.Operation;
import org.apache.tuscany.sca.interfacedef.java.JavaOperation;
import org.apache.tuscany.sca.interfacedef.java.impl.JavaInterfaceUtil;
@@ -76,6 +79,7 @@ public class JavaComponentContextProvider {
private JavaInstanceFactoryProvider<?> instanceFactoryProvider;
private ProxyFactory proxyFactory;
private InstanceFactory instanceFactory;
+ private JavaScopeImpl scope;
public JavaComponentContextProvider(RuntimeComponent component,
JavaInstanceFactoryProvider configuration,
@@ -93,6 +97,7 @@ public class JavaComponentContextProvider {
// }
this.component = component;
this.propertyValueFactory = (JavaPropertyValueObjectFactory) propertyValueObjectFactory;
+ this.scope = ((JavaImplementation)component.getImplementation()).getJavaScope();
}
InstanceWrapper<?> createInstanceWrapper() throws ObjectCreationException {
@@ -144,6 +149,16 @@ public class JavaComponentContextProvider {
}
void start() {
+ List<JavaElementImpl> callbackInjectionList = null;
+
+ // If the component implementation is stateless, we need to inject the callbacks on service invocation
+ // rather than doing it once at the component level.
+ if ( scope.equals(JavaScopeImpl.STATELESS)) {
+ callbackInjectionList = instanceFactoryProvider.getCallbackInjectionSites();
+ } else {
+ callbackInjectionList = instanceFactoryProvider.getInjectionSites();
+ }
+
if (!instanceFactoryProvider.getImplementation().getCallbackMembers().isEmpty()) {
Map<String, List<EndpointReference>> callbackWires = new HashMap<String, List<EndpointReference>>();
for (ComponentService service : component.getServices()) {
@@ -179,7 +194,7 @@ public class JavaComponentContextProvider {
factory = new CallbackWireObjectFactory(businessInterface, proxyFactory, wires);
}
if (!(element.getAnchor() instanceof Constructor)) {
- instanceFactoryProvider.getInjectionSites().add(element);
+ callbackInjectionList.add(element);
}
instanceFactoryProvider.setObjectFactory(element, factory);
}
@@ -288,15 +303,15 @@ public class JavaComponentContextProvider {
//cleanUpPolicyHandlers();
}
- Invoker createInvoker(Operation operation) throws NoSuchMethodException {
+ Invoker createInvoker(Operation operation, InterfaceContract interfaceContract) throws NoSuchMethodException {
Class<?> implClass = instanceFactoryProvider.getImplementationClass();
Method method = JavaInterfaceUtil.findMethod(implClass, operation);
if (operation instanceof JavaOperation &&
((JavaOperation) operation).isAsyncServer() ) {
- return new JavaAsyncImplementationInvoker(operation, method, component);
+ return new JavaAsyncImplementationInvoker(operation, method, component, interfaceContract);
} else {
- return new JavaImplementationInvoker(operation, method, component);
+ return new JavaImplementationInvoker(operation, method, component, interfaceContract);
} // end if
} // end
diff --git a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationInvoker.java b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationInvoker.java
index 4d54fbd46c..13fcfbf413 100644
--- a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationInvoker.java
+++ b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationInvoker.java
@@ -22,17 +22,23 @@ import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import org.apache.tuscany.sca.assembly.EndpointReference;
-import org.apache.tuscany.sca.core.factory.InstanceWrapper;
import org.apache.tuscany.sca.core.factory.ObjectCreationException;
+import org.apache.tuscany.sca.core.scope.Scope;
import org.apache.tuscany.sca.core.scope.ScopeContainer;
import org.apache.tuscany.sca.core.scope.ScopedRuntimeComponent;
import org.apache.tuscany.sca.implementation.java.JavaImplementation;
+import org.apache.tuscany.sca.implementation.java.context.ReflectiveInstanceWrapper;
+import org.apache.tuscany.sca.implementation.java.injection.Injector;
+import org.apache.tuscany.sca.implementation.java.introspect.JavaIntrospectionHelper;
import org.apache.tuscany.sca.interfacedef.DataType;
+import org.apache.tuscany.sca.interfacedef.InterfaceContract;
import org.apache.tuscany.sca.interfacedef.Operation;
+import org.apache.tuscany.sca.interfacedef.java.JavaInterface;
import org.apache.tuscany.sca.interfacedef.java.impl.JavaInterfaceUtil;
import org.apache.tuscany.sca.invocation.Invoker;
import org.apache.tuscany.sca.invocation.Message;
import org.apache.tuscany.sca.runtime.RuntimeComponent;
+import org.oasisopen.sca.ServiceReference;
import org.oasisopen.sca.ServiceRuntimeException;
/**
@@ -48,19 +54,22 @@ public class JavaImplementationInvoker implements Invoker {
@SuppressWarnings("unchecked")
protected final ScopeContainer scopeContainer;
+ private final InterfaceContract interfaze;
- public JavaImplementationInvoker(Operation operation, Method method, RuntimeComponent component) {
+ public JavaImplementationInvoker(Operation operation, Method method, RuntimeComponent component, InterfaceContract intf) {
assert method != null : "Operation method cannot be null";
this.method = method;
this.operation = operation;
this.scopeContainer = ((ScopedRuntimeComponent)component).getScopeContainer();
this.allowsPBR = ((JavaImplementation)component.getImplementation()).isAllowsPassByReference(method);
+ this.interfaze = intf;
}
- public JavaImplementationInvoker(Operation operation, RuntimeComponent component) {
+ public JavaImplementationInvoker(Operation operation, RuntimeComponent component, InterfaceContract intf) {
// used if the method can't be computed statically in advance
this.operation = operation;
this.scopeContainer = ((ScopedRuntimeComponent)component).getScopeContainer();
+ this.interfaze = intf;
}
@SuppressWarnings("unchecked")
@@ -83,8 +92,14 @@ public class JavaImplementationInvoker implements Invoker {
try {
// The following call might create a new conversation, as a result, the msg.getConversationID() might
// return a new value
- InstanceWrapper wrapper = scopeContainer.getWrapper(contextId);
-
+ ReflectiveInstanceWrapper wrapper = (ReflectiveInstanceWrapper) scopeContainer.getWrapper(contextId);
+
+ // If there is a callback interface and the implementation is stateless, we need to
+ // inject callbacks at invocation time. For Composite scope, this has already been done.
+ if (( interfaze.getCallbackInterface() != null ) && (scopeContainer.getScope().equals(Scope.STATELESS))){
+ injectCallbacks(wrapper, (JavaInterface)interfaze.getCallbackInterface());
+ }
+
Object instance = wrapper.getInstance();
// If the method couldn't be computed statically, or the instance being
@@ -149,4 +164,29 @@ public class JavaImplementationInvoker implements Invoker {
return msg;
}
+ private void injectCallbacks(ReflectiveInstanceWrapper wrapper,
+ JavaInterface callbackInterface) {
+
+ for (Injector injector : wrapper.getCallbackInjectors()) {
+ if (injector != null) {
+ try {
+ if (ServiceReference.class.isAssignableFrom(injector.getType())) {
+ Class<?> intf = JavaIntrospectionHelper.getBusinessInterface(injector.getType(), injector.getGenericType());
+ if ( intf.isAssignableFrom(callbackInterface.getJavaClass())) {
+ injector.inject(wrapper.getInstance());
+ }
+ } else if (injector.getType().isAssignableFrom(callbackInterface.getJavaClass())) {
+ injector.inject(wrapper.getInstance());
+ } else {
+ injector.injectNull(wrapper.getInstance());
+ }
+ } catch (Exception e) {
+ throw new ObjectCreationException("Exception invoking injector - " + e.getMessage(), e);
+ }
+ }
+ }
+
+ }
+
+
}
diff --git a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationProvider.java b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationProvider.java
index 3cee156d76..d7abd021f6 100644
--- a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationProvider.java
+++ b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaImplementationProvider.java
@@ -118,7 +118,7 @@ public class JavaImplementationProvider implements ScopedImplementationProvider
public Invoker createInvoker(RuntimeComponentService service, Operation operation) {
try {
- return componentContextProvider.createInvoker(operation);
+ return componentContextProvider.createInvoker(operation, service.getInterfaceContract());
} catch (NoSuchMethodException e) {
// It's possible that the instance being invoked is a user-specified
// callback object that isn't an instance of the component implementation
@@ -132,12 +132,12 @@ public class JavaImplementationProvider implements ScopedImplementationProvider
if (iface instanceof JavaInterface) {
try {
Method method = JavaInterfaceUtil.findMethod(((JavaInterface)iface).getJavaClass(), operation);
- return new JavaImplementationInvoker(operation, method, componentContextProvider.getComponent());
+ return new JavaImplementationInvoker(operation, method, componentContextProvider.getComponent(), service.getInterfaceContract());
} catch (NoSuchMethodException e1) {
throw new IllegalArgumentException(e1);
}
} else {
- return new JavaImplementationInvoker(operation, componentContextProvider.getComponent());
+ return new JavaImplementationInvoker(operation, componentContextProvider.getComponent(), service.getInterfaceContract());
}
}
}
diff --git a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaInstanceFactoryProvider.java b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaInstanceFactoryProvider.java
index 7fcfaad615..1f1f1eefdc 100644
--- a/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaInstanceFactoryProvider.java
+++ b/sca-java-2.x/trunk/modules/implementation-java-runtime/src/main/java/org/apache/tuscany/sca/implementation/java/invocation/JavaInstanceFactoryProvider.java
@@ -57,6 +57,7 @@ public class JavaInstanceFactoryProvider<T> implements InstanceFactoryProvider<T
private final EventInvoker<T> initInvoker;
private final EventInvoker<T> destroyInvoker;
private final Map<JavaElementImpl, Object> factories = new HashMap<JavaElementImpl, Object>();
+ private final List<JavaElementImpl> callbackInjectionSites;
public JavaInstanceFactoryProvider(JavaImplementation definition) {
this.definition = definition;
@@ -65,6 +66,7 @@ public class JavaInstanceFactoryProvider<T> implements InstanceFactoryProvider<T
this.destroyInvoker = definition.getDestroyMethod() == null ? null : new MethodEventInvoker<T>(definition
.getDestroyMethod());
injectionSites = new ArrayList<JavaElementImpl>();
+ callbackInjectionSites = new ArrayList<JavaElementImpl>();
}
ProxyFactory getProxyFactory() {
@@ -85,12 +87,15 @@ public class JavaInstanceFactoryProvider<T> implements InstanceFactoryProvider<T
@SuppressWarnings("unchecked")
public InstanceFactory<T> createFactory() {
ObjectFactory<?>[] initArgs = getConstructorArgs();
- Injector<T>[] injectors = getInjectors();
+ Injector<T>[] injectors = getInjectors(false);
+ Injector<T>[] callbackInjectors = getInjectors(true);
return new ReflectiveInstanceFactory<T>((Constructor<T>)definition.getConstructor().getConstructor(),
- initArgs, injectors, initInvoker, destroyInvoker);
+ initArgs, injectors, callbackInjectors, initInvoker, destroyInvoker);
}
- private ObjectFactory<?>[] getConstructorArgs() {
+
+
+ private ObjectFactory<?>[] getConstructorArgs() {
JavaConstructorImpl<?> constructor = definition.getConstructor();
ObjectFactory<?>[] initArgs = new ObjectFactory<?>[constructor.getParameters().length];
for (int i = 0; i < initArgs.length; i++) {
@@ -101,13 +106,21 @@ public class JavaInstanceFactoryProvider<T> implements InstanceFactoryProvider<T
return initArgs;
}
+
+
@SuppressWarnings("unchecked")
- private Injector<T>[] getInjectors() {
+ private Injector<T>[] getInjectors(boolean callback) {
+ List<JavaElementImpl> sites = null;
+ if ( callback )
+ sites = callbackInjectionSites;
+ else
+ sites = injectionSites;
+
// work around JDK1.5 issue with allocating generic arrays
- Injector<T>[] injectors = new Injector[injectionSites.size()];
+ Injector<T>[] injectors = new Injector[sites.size()];
int i = 0;
- for (JavaElementImpl element : injectionSites) {
+ for (JavaElementImpl element : sites) {
Object obj = factories.get(element);
if (obj != null) {
if (obj instanceof ObjectFactory) {
@@ -172,6 +185,13 @@ public class JavaInstanceFactoryProvider<T> implements InstanceFactoryProvider<T
return injectionSites;
}
+ /**
+ * @return the callbackInjectionSites
+ */
+ public List<JavaElementImpl> getCallbackInjectionSites() {
+ return callbackInjectionSites;
+ }
+
/**
* @return the factories
*/
@@ -179,4 +199,6 @@ public class JavaInstanceFactoryProvider<T> implements InstanceFactoryProvider<T
return factories;
}
+
+
}