diff options
18 files changed, 461 insertions, 129 deletions
diff --git a/sca-java-2.x/trunk/modules/assembly/src/main/java/org/apache/tuscany/sca/assembly/impl/EndpointReferenceImpl.java b/sca-java-2.x/trunk/modules/assembly/src/main/java/org/apache/tuscany/sca/assembly/impl/EndpointReferenceImpl.java index d5ba25f04b..96af9373cd 100644 --- a/sca-java-2.x/trunk/modules/assembly/src/main/java/org/apache/tuscany/sca/assembly/impl/EndpointReferenceImpl.java +++ b/sca-java-2.x/trunk/modules/assembly/src/main/java/org/apache/tuscany/sca/assembly/impl/EndpointReferenceImpl.java @@ -232,6 +232,12 @@ public class EndpointReferenceImpl implements EndpointReference { } public boolean isAsyncInvocation() { + if (reference.getName().endsWith("_asyncCallback")){ + // this is a response reference at the service component so don't create a + // response service. The response service will be at the reference component + return false; + } + for(Intent intent : getRequiredIntents()){ if (intent.getName().getLocalPart().equals("asyncInvocation")){ return true; diff --git a/sca-java-2.x/trunk/modules/binding-corba-runtime/src/test/java/org/apache/tuscany/sca/binding/corba/testing/service/mocks/TestRuntimeWire.java b/sca-java-2.x/trunk/modules/binding-corba-runtime/src/test/java/org/apache/tuscany/sca/binding/corba/testing/service/mocks/TestRuntimeWire.java index 2896114775..d109b74e34 100644 --- a/sca-java-2.x/trunk/modules/binding-corba-runtime/src/test/java/org/apache/tuscany/sca/binding/corba/testing/service/mocks/TestRuntimeWire.java +++ b/sca-java-2.x/trunk/modules/binding-corba-runtime/src/test/java/org/apache/tuscany/sca/binding/corba/testing/service/mocks/TestRuntimeWire.java @@ -204,7 +204,10 @@ public class TestRuntimeWire implements RuntimeEndpoint { // TODO Auto-generated method stub return null; } - + + public void invokeAsync(Operation operation, Message msg) { + return; + } public void unbind() { // TODO Auto-generated method stub diff --git a/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/EndpointReferenceBuilderImpl.java b/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/EndpointReferenceBuilderImpl.java index 7af1451f68..9daaad8737 100644 --- a/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/EndpointReferenceBuilderImpl.java +++ b/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/EndpointReferenceBuilderImpl.java @@ -58,9 +58,6 @@ public class EndpointReferenceBuilderImpl { private AssemblyFactory assemblyFactory; private InterfaceContractMapper interfaceContractMapper; - - // causes dependency between builders and core - //private EndpointReferenceBinder endpointReferenceBinder; public EndpointReferenceBuilderImpl(ExtensionPointRegistry registry) { UtilityExtensionPoint utilities = registry.getExtensionPoint(UtilityExtensionPoint.class); @@ -68,9 +65,6 @@ public class EndpointReferenceBuilderImpl { FactoryExtensionPoint modelFactories = registry.getExtensionPoint(FactoryExtensionPoint.class); assemblyFactory = modelFactories.getFactory(AssemblyFactory.class); - - // causes dependency between builders and core - //endpointReferenceBinder = registry.getExtensionPoint(EndpointReferenceBinder.class); } /** @@ -88,20 +82,6 @@ public class EndpointReferenceBuilderImpl { // left until this stage, after all endpoints have been created, // to to catch more complex cases caused by reference promotion validateComponentReferences(composite, context.getMonitor()); - - // TODO - move the following buld time matching code - // to somewhere else because of - // the dependency between builders and core - - // create temporary local registry for all available local endpoints - //EndpointRegistry registry = new EndpointRegistryImpl(); - - // populate the registry with all the endpoints that are present in the model - //populateLocalRegistry(composite, registry, context); - - // match all local services against the endpoint references - // we've just created - //matchEndpointReferences(composite, registry, context); return composite; } @@ -270,7 +250,7 @@ public class EndpointReferenceBuilderImpl { // non-targetted, i.e. no URI, binding.sca in order to control the // intended QoS of the wire when matching takes place. If any other // bindings are specified then the test later on will complain about - // mixing targts with bindings + // mixing targets with bindings if (reference.getBindings().size() == 1){ Binding binding = reference.getBindings().get(0); if ((binding instanceof SCABinding) && (binding.getURI() == null)){ @@ -327,7 +307,7 @@ public class EndpointReferenceBuilderImpl { } } catch (Exception ex){ // do nothing and go to the next bit of code - // which assumes that the URI is an SCA usi + // which assumes that the URI is an SCA URI } // The user has put something in the binding uri but we don't know if it's @@ -832,52 +812,6 @@ public class EndpointReferenceBuilderImpl { } } } - } - - //========================================================================= - // methods below related to build time matching which is currently disabled -/* - private void populateLocalRegistry(Composite composite, EndpointRegistry registry, BuilderContext context){ - for (Component component : composite.getComponents()) { - // recurse for composite implementations - Implementation implementation = component.getImplementation(); - if (implementation instanceof Composite) { - populateLocalRegistry((Composite)implementation, registry, context); - } - - for (ComponentService service : component.getServices()) { - for (Endpoint endpoint : service.getEndpoints()){ - registry.addEndpoint(endpoint); - } - } - - - for (ComponentReference reference : component.getReferences()) { - for (EndpointReference epr : reference.getEndpointReferences()){ - registry.addEndpointReference(epr); - } - } - - // remove all autowire place holders so they don't cause wires to be created - // have to pass in reference as we don't have access to the registry in - // the builders - for (EndpointReference epr : registry.getEndpointReferences()){ - if (epr.getStatus() == EndpointReference.Status.AUTOWIRE_PLACEHOLDER){ - epr.getReference().getEndpointReferences().remove(epr); - } - } - } - } - - private void matchEndpointReferences(Composite composite, EndpointRegistry registry, BuilderContext context){ - - // look at all the endpoint references and try to match them to - // endpoints - for (EndpointReference endpointReference : registry.getEndpointReferences()){ - endpointReferenceBinder.bindBuildTime(registry, endpointReference); - } - } -*/ - + } }
\ No newline at end of file diff --git a/sca-java-2.x/trunk/modules/core-spi/META-INF/MANIFEST.MF b/sca-java-2.x/trunk/modules/core-spi/META-INF/MANIFEST.MF index 1ae10356d5..baae06d53a 100644 --- a/sca-java-2.x/trunk/modules/core-spi/META-INF/MANIFEST.MF +++ b/sca-java-2.x/trunk/modules/core-spi/META-INF/MANIFEST.MF @@ -31,6 +31,7 @@ Bundle-ManifestVersion: 2 Bundle-License: http://www.apache.org/licenses/LICENSE-2.0.txt
Bundle-Description: Apache Tuscany SCA Core SPI
Import-Package: org.apache.tuscany.sca.assembly;version="2.0.0",
+ org.apache.tuscany.sca.assembly.builder;version="2.0.0",
org.apache.tuscany.sca.context;version="2.0.0",
org.apache.tuscany.sca.core;version="2.0.0",
org.apache.tuscany.sca.definitions;version="2.0.0",
diff --git a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/invocation/InvokerAsync.java b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/invocation/InvokerAsync.java new file mode 100644 index 0000000000..624e8fdab4 --- /dev/null +++ b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/invocation/InvokerAsync.java @@ -0,0 +1,39 @@ +/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.tuscany.sca.invocation;
+
+/**
+ * TUSCANY-3786 - Possibly temporary interface to describe an
+ * async invocation. Need to make it work end to
+ * end before committing to this.
+ *
+ * Asynchronous mediation associated with a client- or target- side wire.
+ *
+ */
+public interface InvokerAsync {
+
+ /**
+ * Process an asynchronous wire
+ *
+ * @param msg The request Message for the wire
+ *
+ */
+ void invokeAsync(Message msg);
+
+}
diff --git a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/BaseEndpointRegistry.java b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/BaseEndpointRegistry.java index 0b6b93edc0..65c1f8815b 100644 --- a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/BaseEndpointRegistry.java +++ b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/BaseEndpointRegistry.java @@ -60,6 +60,7 @@ public abstract class BaseEndpointRegistry implements EndpointRegistry, LifeCycl public void addEndpointReference(EndpointReference endpointReference) { endpointreferences.add(endpointReference); + ((RuntimeEndpointReference)endpointReference).bind(registry, this); logger.fine("Add endpoint reference - " + endpointReference); } diff --git a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/EndpointReferenceBinder.java b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/EndpointReferenceBinder.java index b2ce3f5b7b..60f8a5c5a0 100644 --- a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/EndpointReferenceBinder.java +++ b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/EndpointReferenceBinder.java @@ -20,6 +20,7 @@ package org.apache.tuscany.sca.runtime; import org.apache.tuscany.sca.assembly.EndpointReference; +import org.apache.tuscany.sca.assembly.builder.BuilderContext; /** * A utility responsible for resolving the endpoint reference against a matching endpoint published @@ -32,7 +33,7 @@ public interface EndpointReferenceBinder { * @param endpointReference * @return */ - void bindBuildTime(EndpointRegistry endpointRegistry, EndpointReference endpointReference); + void bindBuildTime(EndpointRegistry endpointRegistry, EndpointReference endpointReference, BuilderContext builderContext); /** diff --git a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/Invocable.java b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/Invocable.java index 2df1761aec..31260f1afa 100644 --- a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/Invocable.java +++ b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/Invocable.java @@ -128,6 +128,15 @@ public interface Invocable { * @throws InvocationTargetException */ Message invoke(Operation operation, Message msg); + + /** + * Asynchronously invoke an operation with a context message + * @param operation The operation + * @param msg The request message + * @return The ticket that can be used to identify this invocation + * @throws InvocationTargetException + */ + void invokeAsync(Operation operation, Message msg); /** * Get a list of policy providers diff --git a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/RuntimeEndpointReference.java b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/RuntimeEndpointReference.java index 42e7328c0a..81ef1acd9e 100644 --- a/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/RuntimeEndpointReference.java +++ b/sca-java-2.x/trunk/modules/core-spi/src/main/java/org/apache/tuscany/sca/runtime/RuntimeEndpointReference.java @@ -77,4 +77,12 @@ public interface RuntimeEndpointReference extends EndpointReference, Invocable, * @return */ public InterfaceContract getGeneratedWSDLContract(InterfaceContract interfaceContract); + + /** + * Create the endpoint which will be the target of and asynchronous response to a + * message sent through this reference. We have the code here as this can't be done + * in the builders in the same was as callbacks are because we don't know the details + * of the endpoint until the endpoint reference has been resolved. + */ + public void createAsyncCallbackEndpoint(); } diff --git a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/assembly/impl/RuntimeEndpointImpl.java b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/assembly/impl/RuntimeEndpointImpl.java index 4cae8d0085..31738c3a5d 100644 --- a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/assembly/impl/RuntimeEndpointImpl.java +++ b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/assembly/impl/RuntimeEndpointImpl.java @@ -182,7 +182,7 @@ public class RuntimeEndpointImpl extends EndpointImpl implements RuntimeEndpoint new ExtensibleWireProcessor(registry.getExtensionPoint(RuntimeWireProcessorExtensionPoint.class)); this.messageFactory = registry.getExtensionPoint(FactoryExtensionPoint.class).getFactory(MessageFactory.class); - this.invoker = new RuntimeInvoker(this.messageFactory, this); + this.invoker = new RuntimeInvoker(registry, this); this.phaseManager = utilities.getUtility(PhaseManager.class); this.serializer = utilities.getUtility(EndpointSerializer.class); @@ -285,6 +285,11 @@ public class RuntimeEndpointImpl extends EndpointImpl implements RuntimeEndpoint public Message invoke(Operation operation, Message msg) { return invoker.invoke(operation, msg); } + + public void invokeAsync(Operation operation, Message msg) { + msg.setOperation(operation); + invoker.invokeAsync(msg); + } /** * Navigate the component/componentType inheritence chain to find the leaf contract @@ -647,7 +652,7 @@ public class RuntimeEndpointImpl extends EndpointImpl implements RuntimeEndpoint @Override public Object clone() throws CloneNotSupportedException { RuntimeEndpointImpl copy = (RuntimeEndpointImpl)super.clone(); - copy.invoker = new RuntimeInvoker(copy.messageFactory, copy); + copy.invoker = new RuntimeInvoker(registry, copy); return copy; } diff --git a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/assembly/impl/RuntimeEndpointReferenceImpl.java b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/assembly/impl/RuntimeEndpointReferenceImpl.java index 36480f3435..b18af33a39 100644 --- a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/assembly/impl/RuntimeEndpointReferenceImpl.java +++ b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/assembly/impl/RuntimeEndpointReferenceImpl.java @@ -31,18 +31,24 @@ import java.util.List; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; +import org.apache.tuscany.sca.assembly.AssemblyFactory; +import org.apache.tuscany.sca.assembly.Binding; import org.apache.tuscany.sca.assembly.ComponentReference; import org.apache.tuscany.sca.assembly.ComponentService; import org.apache.tuscany.sca.assembly.CompositeReference; import org.apache.tuscany.sca.assembly.CompositeService; import org.apache.tuscany.sca.assembly.Contract; import org.apache.tuscany.sca.assembly.EndpointReference; +import org.apache.tuscany.sca.assembly.builder.BindingBuilder; +import org.apache.tuscany.sca.assembly.builder.BuilderContext; import org.apache.tuscany.sca.assembly.builder.BuilderExtensionPoint; import org.apache.tuscany.sca.assembly.impl.EndpointReferenceImpl; import org.apache.tuscany.sca.context.CompositeContext; import org.apache.tuscany.sca.core.ExtensionPointRegistry; import org.apache.tuscany.sca.core.FactoryExtensionPoint; import org.apache.tuscany.sca.core.UtilityExtensionPoint; +import org.apache.tuscany.sca.core.assembly.RuntimeAssemblyFactory; +import org.apache.tuscany.sca.core.invocation.AsyncResponseHandler; import org.apache.tuscany.sca.core.invocation.ExtensibleWireProcessor; import org.apache.tuscany.sca.core.invocation.NonBlockingInterceptor; import org.apache.tuscany.sca.core.invocation.RuntimeInvoker; @@ -51,8 +57,10 @@ import org.apache.tuscany.sca.core.invocation.impl.PhaseManager; import org.apache.tuscany.sca.interfacedef.Compatibility; import org.apache.tuscany.sca.interfacedef.InterfaceContract; import org.apache.tuscany.sca.interfacedef.InterfaceContractMapper; +import org.apache.tuscany.sca.interfacedef.InvalidInterfaceException; import org.apache.tuscany.sca.interfacedef.Operation; import org.apache.tuscany.sca.interfacedef.java.JavaInterfaceContract; +import org.apache.tuscany.sca.interfacedef.java.JavaInterfaceFactory; import org.apache.tuscany.sca.invocation.Interceptor; import org.apache.tuscany.sca.invocation.InvocationChain; import org.apache.tuscany.sca.invocation.Invoker; @@ -68,7 +76,9 @@ import org.apache.tuscany.sca.provider.ReferenceBindingProvider; import org.apache.tuscany.sca.runtime.EndpointReferenceBinder; import org.apache.tuscany.sca.runtime.EndpointRegistry; import org.apache.tuscany.sca.runtime.EndpointSerializer; +import org.apache.tuscany.sca.runtime.RuntimeComponent; import org.apache.tuscany.sca.runtime.RuntimeComponentReference; +import org.apache.tuscany.sca.runtime.RuntimeEndpoint; import org.apache.tuscany.sca.runtime.RuntimeEndpointReference; import org.apache.tuscany.sca.runtime.RuntimeWireProcessor; import org.apache.tuscany.sca.runtime.RuntimeWireProcessorExtensionPoint; @@ -169,7 +179,7 @@ public class RuntimeEndpointReferenceImpl extends EndpointReferenceImpl implemen new ExtensibleWireProcessor(registry.getExtensionPoint(RuntimeWireProcessorExtensionPoint.class)); this.messageFactory = registry.getExtensionPoint(FactoryExtensionPoint.class).getFactory(MessageFactory.class); - this.invoker = new RuntimeInvoker(this.messageFactory, this); + this.invoker = new RuntimeInvoker(registry, this); this.phaseManager = utilities.getUtility(PhaseManager.class); this.serializer = utilities.getUtility(EndpointSerializer.class); @@ -227,6 +237,11 @@ public class RuntimeEndpointReferenceImpl extends EndpointReferenceImpl implemen public Message invoke(Operation operation, Message msg) { return invoker.invoke(operation, msg); } + + public void invokeAsync(Operation operation, Message msg) { + msg.setOperation(operation); + invoker.invokeAsync(msg); + } /** * Navigate the component/componentType inheritence chain to find the leaf contract @@ -472,7 +487,7 @@ public class RuntimeEndpointReferenceImpl extends EndpointReferenceImpl implemen @Override public Object clone() throws CloneNotSupportedException { RuntimeEndpointReferenceImpl copy = (RuntimeEndpointReferenceImpl)super.clone(); - copy.invoker = new RuntimeInvoker(copy.messageFactory, copy); + copy.invoker = new RuntimeInvoker(registry, copy); return copy; } @@ -615,5 +630,65 @@ public class RuntimeEndpointReferenceImpl extends EndpointReferenceImpl implemen } return interfaceContract.getNormalizedWSDLContract(); - } + } + + public void createAsyncCallbackEndpoint(){ + CompositeContext compositeContext = getCompositeContext(); + FactoryExtensionPoint modelFactories = registry.getExtensionPoint(FactoryExtensionPoint.class); + RuntimeAssemblyFactory assemblyFactory = (RuntimeAssemblyFactory)modelFactories.getFactory(AssemblyFactory.class); + + RuntimeEndpoint endpoint = (RuntimeEndpoint)assemblyFactory.createEndpoint(); + endpoint.bind(compositeContext); + endpoint.setComponent(getComponent()); + + // Create pseudo-service + ComponentService service = assemblyFactory.createComponentService(); + JavaInterfaceFactory javaInterfaceFactory = + (JavaInterfaceFactory)modelFactories.getFactory(JavaInterfaceFactory.class); + JavaInterfaceContract interfaceContract = javaInterfaceFactory.createJavaInterfaceContract(); + try { + interfaceContract.setInterface(javaInterfaceFactory.createJavaInterface(AsyncResponseHandler.class)); + } catch (InvalidInterfaceException e1) { + // Nothing to do here - will not happen + } // end try + + service.setInterfaceContract(interfaceContract); + String serviceName = getReference().getName() + "_asyncCallback"; + service.setName(serviceName); + service.getEndpoints().add(endpoint); + service.setForCallback(true); + endpoint.setService(service); + + // Set pseudo-service onto the component + getComponent().getServices().add(service); + + // Create a binding + // Mike had to go via the XML but I don't remember why + Binding binding = null; + try { + binding = (Binding)getBinding().clone(); + } catch (Exception ex){ + // + } + String callbackURI = "/" + component.getName() + "/" + service.getName(); + binding.setURI(callbackURI); + + BuilderExtensionPoint builders = registry.getExtensionPoint(BuilderExtensionPoint.class); + BindingBuilder builder = builders.getBindingBuilder(binding.getType()); + if (builder != null) { + org.apache.tuscany.sca.assembly.builder.BuilderContext builderContext = new BuilderContext(registry); + builder.build(component, service, binding, builderContext, true); + } // end if + + endpoint.setBinding(binding); + + // Need to establish policies here (binding has some...) + endpoint.getRequiredIntents().addAll(getRequiredIntents()); + endpoint.getPolicySets().addAll(getPolicySets()); + String epURI = getComponent().getName() + "#service-binding(" + serviceName + "/" + serviceName + ")"; + endpoint.setURI(epURI); + endpoint.setUnresolved(false); + + setCallbackEndpoint(endpoint); + } } diff --git a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/invocation/Constants.java b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/invocation/Constants.java new file mode 100644 index 0000000000..3e2a71027d --- /dev/null +++ b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/invocation/Constants.java @@ -0,0 +1,30 @@ +/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.tuscany.sca.core.invocation;
+
+/**
+ * Constants used during invocation in the runtime
+ *
+
+ */
+public interface Constants {
+ String MESSAGE_ID = "MESSAGE_ID";
+
+}
diff --git a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/invocation/RuntimeInvoker.java b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/invocation/RuntimeInvoker.java index 0751fd631b..b5e3eec282 100644 --- a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/invocation/RuntimeInvoker.java +++ b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/invocation/RuntimeInvoker.java @@ -20,28 +20,45 @@ package org.apache.tuscany.sca.core.invocation; import java.lang.reflect.InvocationTargetException; +import java.util.UUID; +import java.util.concurrent.ExecutorService; import org.apache.tuscany.sca.assembly.Endpoint; import org.apache.tuscany.sca.assembly.EndpointReference; import org.apache.tuscany.sca.context.ThreadMessageContext; +import org.apache.tuscany.sca.core.ExtensionPointRegistry; +import org.apache.tuscany.sca.core.FactoryExtensionPoint; +import org.apache.tuscany.sca.core.UtilityExtensionPoint; import org.apache.tuscany.sca.interfacedef.Operation; import org.apache.tuscany.sca.invocation.InvocationChain; import org.apache.tuscany.sca.invocation.Invoker; +import org.apache.tuscany.sca.invocation.InvokerAsync; import org.apache.tuscany.sca.invocation.Message; import org.apache.tuscany.sca.invocation.MessageFactory; import org.apache.tuscany.sca.runtime.Invocable; +import org.apache.tuscany.sca.runtime.RuntimeEndpointReference; +import org.apache.tuscany.sca.work.WorkScheduler; /** * Invoker for a endpoint or endpoint reference * @version $Rev$ $Date$ */ -public class RuntimeInvoker implements Invoker { +public class RuntimeInvoker implements Invoker, InvokerAsync { + protected ExtensionPointRegistry registry; protected MessageFactory messageFactory; protected Invocable invocable; + + // Run async service invocations using a ThreadPoolExecutor + private ExecutorService theExecutor; - public RuntimeInvoker(MessageFactory messageFactory, Invocable invocable) { - this.messageFactory = messageFactory; + public RuntimeInvoker(ExtensionPointRegistry registry, Invocable invocable) { + this.registry = registry; + this.messageFactory = registry.getExtensionPoint(FactoryExtensionPoint.class).getFactory(MessageFactory.class); this.invocable = invocable; + + UtilityExtensionPoint utilities = registry.getExtensionPoint(UtilityExtensionPoint.class); + WorkScheduler scheduler = utilities.getUtility(WorkScheduler.class); + theExecutor = scheduler.getExecutorService(); } public Message invokeBinding(Message msg) { @@ -93,5 +110,42 @@ public class RuntimeInvoker implements Invoker { ThreadMessageContext.setMessageContext(msgContext); } } + + public void invokeAsync(Message msg) { + if (invocable instanceof Endpoint) { + msg.setTo((Endpoint)invocable); + } else if (invocable instanceof EndpointReference) { + RuntimeEndpointReference epr = (RuntimeEndpointReference)invocable; + if (epr.isOutOfDate()) { + epr.rebuild(); + } + msg.setFrom((EndpointReference)invocable); + } + + Operation operation = msg.getOperation(); + InvocationChain chain = invocable.getInvocationChain(operation); + + if (chain == null) { + throw new IllegalArgumentException("No matching operation is found: " + operation.getName()); + } + + // create an async message ID if there isn't one there already + if (!msg.getHeaders().containsKey(Constants.MESSAGE_ID)){ + msg.getHeaders().put(Constants.MESSAGE_ID, UUID.randomUUID().toString());UUID.randomUUID().toString(); + } + + // Perform the async invocation + InvokerAsync headInvoker = (InvokerAsync)chain.getHeadInvoker(); + + Message msgContext = ThreadMessageContext.setMessageContext(msg); + try { + // TODO - is this the way we'll pass async messages down the chain? + headInvoker.invokeAsync(msg); + } finally { + ThreadMessageContext.setMessageContext(msgContext); + } + + return; + } } diff --git a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/runtime/impl/EndpointReferenceBinderImpl.java b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/runtime/impl/EndpointReferenceBinderImpl.java index 905fed4e01..ffe48005ea 100644 --- a/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/runtime/impl/EndpointReferenceBinderImpl.java +++ b/sca-java-2.x/trunk/modules/core/src/main/java/org/apache/tuscany/sca/core/runtime/impl/EndpointReferenceBinderImpl.java @@ -107,8 +107,9 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { * @param endpointReference */ public void bindBuildTime(EndpointRegistry endpointRegistry, - EndpointReference endpointReference) { - bind(endpointRegistry, endpointReference, false); + EndpointReference endpointReference, + BuilderContext builderContext) { + bind(endpointRegistry, endpointReference, builderContext, false); } /** @@ -120,7 +121,7 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { */ public void bindRunTime(EndpointRegistry endpointRegistry, EndpointReference endpointReference) { - bind(endpointRegistry, endpointReference, true); + bind(endpointRegistry, endpointReference, null, true); } /** @@ -132,6 +133,7 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { */ public void bind(EndpointRegistry endpointRegistry, EndpointReference endpointReference, + BuilderContext builderContext, boolean runtime){ logger.fine("Binding " + endpointReference.toString()); @@ -159,7 +161,7 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { continue; } - if (haveMatchingPolicy(endpointReference, endpoint, matchAudit) && + if (haveMatchingPolicy(endpointReference, endpoint, matchAudit, builderContext) && haveMatchingInterfaceContracts(endpointReference, endpoint, matchAudit)){ // matching service so find if this reference already has // an endpoint reference for this endpoint @@ -216,7 +218,9 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { || endpointReference.getCallbackEndpoint().isUnresolved())) { selectCallbackEndpoint(endpointReference, endpointReference.getReference().getCallbackService(), - matchAudit); + matchAudit, + builderContext, + runtime); } } else if (endpointReference.getStatus() == EndpointReference.Status.WIRED_TARGET_FOUND_READY_FOR_MATCHING ){ // The endpoint reference is already resolved to either @@ -226,12 +230,15 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { selectForwardEndpoint(endpointReference, endpointReference.getTargetEndpoint().getService().getEndpoints(), - matchAudit); + matchAudit, + builderContext); if (hasCallback(endpointReference)){ selectCallbackEndpoint(endpointReference, endpointReference.getReference().getCallbackService(), - matchAudit); + matchAudit, + builderContext, + runtime); } } else if (endpointReference.getStatus() == EndpointReference.Status.WIRED_TARGET_IN_BINDING_URI || endpointReference.getStatus() == EndpointReference.Status.WIRED_TARGET_NOT_FOUND || @@ -241,10 +248,23 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { // find the service in the endpoint registry List<Endpoint> endpoints = endpointRegistry.findEndpoint(endpointReference); - if ((endpoints.size() == 0) && - (runtime == true) ) { - - // tweak to test if this could be a resolve binding. This is the back end of the test + if (endpoints.size() > 0){ + selectForwardEndpoint(endpointReference, + endpoints, + matchAudit, + builderContext); + + // If the reference was matched try to match the callback + if (endpointReference.getStatus().equals(EndpointReference.Status.WIRED_TARGET_FOUND_AND_MATCHED) && + hasCallback(endpointReference)){ + selectCallbackEndpoint(endpointReference, + endpointReference.getReference().getCallbackService(), + matchAudit, + builderContext, + runtime); + } + } else if (runtime) { + // tweak to test if this could be a resolved binding. This is the back end of the test // in the builder that pulls the URI out of the binding if there are no targets // on the reference. have to wait until here to see if the binding uri matches any // available services. If not we assume here that it's a resolved binding @@ -260,16 +280,6 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { throw new ServiceRuntimeException("Unable to bind " + monitor.getLastProblem().toString()); } - } - - selectForwardEndpoint(endpointReference, - endpoints, - matchAudit); - - if (hasCallback(endpointReference)){ - selectCallbackEndpoint(endpointReference, - endpointReference.getReference().getCallbackService(), - matchAudit); } } @@ -285,21 +295,46 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { "EndpointReferenceCantBeMatched", endpointReference.toString(), matchAudit); + throw new ServiceRuntimeException("Unable to bind " + + monitor.getLastProblem().toString()); } else { Monitor.warning(monitor, this, "endpoint-validation-messages", "ComponentReferenceTargetNotFound", endpointReference.toString()); + return; } - throw new ServiceRuntimeException("Unable to bind " + - monitor.getLastProblem().toString()); + } // Now the endpoint reference is resolved check that the binding interfaces contract // and the reference contract are compatible - ((RuntimeEndpointReference)endpointReference).validateReferenceInterfaceCompatibility(); + try { + ((RuntimeEndpointReference)endpointReference).validateReferenceInterfaceCompatibility(); + } catch (ServiceRuntimeException ex) { + // don't re-throw this exception at build time just record the + // error. If it's thrown here is messes up the order in which + // build time errors are reported and that in turn messes + // up the output of the compliance tests. + if (runtime){ + throw ex; + } else { + Monitor.error(monitor, + this, + "endpoint-validation-messages", + "EndpointReferenceCantBeMatched", + endpointReference.toString(), + ex.getMessage()); + } + } + + // if the reference is an async reference fluff up the + // response service/endpoint + if (endpointReference.isAsyncInvocation()){ + ((RuntimeEndpointReference)endpointReference).createAsyncCallbackEndpoint(); + } // System.out.println("MATCH AUDIT:" + matchAudit.toString()); } @@ -323,7 +358,7 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { * @param endpointReference * @param endpoints */ - private void selectForwardEndpoint(EndpointReference endpointReference, List<Endpoint> endpoints, Audit matchAudit) { + private void selectForwardEndpoint(EndpointReference endpointReference, List<Endpoint> endpoints, Audit matchAudit, BuilderContext builderContext) { Endpoint matchedEndpoint = null; @@ -337,7 +372,7 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { } else { // find the first endpoint that matches this endpoint reference for (Endpoint endpoint : endpoints){ - if (haveMatchingPolicy(endpointReference, endpoint, matchAudit) && + if (haveMatchingPolicy(endpointReference, endpoint, matchAudit, builderContext) && haveMatchingInterfaceContracts(endpointReference, endpoint, matchAudit)){ matchedEndpoint = endpoint; break; @@ -374,7 +409,7 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { * @param endpointReference * @param endpoints */ - private void selectCallbackEndpoint(EndpointReference endpointReference, ComponentService callbackService, Audit matchAudit) { + private void selectCallbackEndpoint(EndpointReference endpointReference, ComponentService callbackService, Audit matchAudit, BuilderContext builderContext, boolean runtime) { // find the first callback endpoint that matches a callback endpoint reference // at the service @@ -382,7 +417,7 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { match: for ( EndpointReference callbackEndpointReference : endpointReference.getTargetEndpoint().getCallbackEndpointReferences()){ for (Endpoint endpoint : callbackService.getEndpoints()){ - if (haveMatchingPolicy(callbackEndpointReference, endpoint, matchAudit) && + if (haveMatchingPolicy(callbackEndpointReference, endpoint, matchAudit, builderContext) && haveMatchingInterfaceContracts(callbackEndpointReference, endpoint, matchAudit)){ callbackEndpoint = (RuntimeEndpoint)endpoint; break match; @@ -435,13 +470,18 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { // build it build(callbackEndpoint); - // activate it - compositeActivator.activate(((RuntimeEndpointReferenceImpl)endpointReference).getCompositeContext(), - callbackEndpoint); - - // start it - compositeActivator.start(((RuntimeEndpointReferenceImpl)endpointReference).getCompositeContext(), - callbackEndpoint); + // Only activate the callback endpoint if the bind is being done at runtime + // and hence everthing else is running. If we don't activate here then the + // endpoint will be activate at the same time as all the other endpoints + if (runtime) { + // activate it + compositeActivator.activate(((RuntimeEndpointReferenceImpl)endpointReference).getCompositeContext(), + callbackEndpoint); + + // start it + compositeActivator.start(((RuntimeEndpointReferenceImpl)endpointReference).getCompositeContext(), + callbackEndpoint); + } } endpointReference.setCallbackEndpoint(callbackEndpoint); @@ -477,7 +517,7 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { * - Perform policy specific match * */ - private boolean haveMatchingPolicy(EndpointReference endpointReference, Endpoint endpoint, Audit matchAudit){ + private boolean haveMatchingPolicy(EndpointReference endpointReference, Endpoint endpoint, Audit matchAudit, BuilderContext builderContext){ matchAudit.append("Match policy of " + endpointReference.toString() + " to " + endpoint.toString() + " "); List<PolicySet> referencePolicySets = new ArrayList<PolicySet>(); @@ -568,12 +608,17 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { // Failing this the intent is unresolved and the reference and // service don't match - - // TODO - seems that we should do this loop on a binding by binding basis // rather than each time we do matching BindingType bindingType = null; - Definitions systemDefinitions = ((RuntimeEndpoint)endpoint).getCompositeContext().getSystemDefinitions(); + + Definitions systemDefinitions = null; + if (builderContext != null){ + systemDefinitions = builderContext.getDefinitions(); + } else { + systemDefinitions = ((RuntimeEndpoint)endpoint).getCompositeContext().getSystemDefinitions(); + } + for (BindingType loopBindingType : systemDefinitions.getBindingTypes()){ if (loopBindingType.getType().equals(binding.getType())){ bindingType = loopBindingType; @@ -707,8 +752,9 @@ public class EndpointReferenceBinderImpl implements EndpointReferenceBinder { endpointReference.getPolicySets().addAll(referencePolicySets); if (builder != null) { - // TODO - where to get builder context from? - BuilderContext builderContext = new BuilderContext(monitor); + if (builderContext == null){ + builderContext = new BuilderContext(monitor); + } match = builder.build(endpointReference, endpoint, builderContext); } diff --git a/sca-java-2.x/trunk/modules/core/src/main/resources/endpoint-validation-messages.properties b/sca-java-2.x/trunk/modules/core/src/main/resources/endpoint-validation-messages.properties index 6e12d11d68..75f635fb1a 100644 --- a/sca-java-2.x/trunk/modules/core/src/main/resources/endpoint-validation-messages.properties +++ b/sca-java-2.x/trunk/modules/core/src/main/resources/endpoint-validation-messages.properties @@ -20,4 +20,4 @@ # NoEndpointsFound = No endpoints found in the domain that match the reference {0} EndpointReferenceCantBeMatched = = Unable to match the endpoint reference {0} with the policy of the service to which it refers, matching process was {1} -ComponentReferenceTargetNotFound = Component reference target not found, it might be a remote service running elsewhere in the SCA Domain: {1} +ComponentReferenceTargetNotFound = Component reference target not found at deployment time, it might be a remote service elsewhere in the SCA Domain so we'll try and resolve it again at runtime: {1} diff --git a/sca-java-2.x/trunk/modules/deployment/META-INF/MANIFEST.MF b/sca-java-2.x/trunk/modules/deployment/META-INF/MANIFEST.MF index 58d085ce87..65f35c59b0 100644 --- a/sca-java-2.x/trunk/modules/deployment/META-INF/MANIFEST.MF +++ b/sca-java-2.x/trunk/modules/deployment/META-INF/MANIFEST.MF @@ -45,6 +45,7 @@ Import-Package: javax.xml.namespace, org.apache.tuscany.sca.deployment;version="2.0.0",
org.apache.tuscany.sca.monitor;version="2.0.0",
org.apache.tuscany.sca.xsd;version="2.0.0",
+ org.apache.tuscany.sca.runtime;version="2.0.0",
org.oasisopen.sca.annotation;version="2.0.0";resolution:=optional
Bundle-SymbolicName: org.apache.tuscany.sca.deployment
Bundle-DocURL: http://www.apache.org/
diff --git a/sca-java-2.x/trunk/modules/deployment/pom.xml b/sca-java-2.x/trunk/modules/deployment/pom.xml index 68205135a2..31e380eaea 100644 --- a/sca-java-2.x/trunk/modules/deployment/pom.xml +++ b/sca-java-2.x/trunk/modules/deployment/pom.xml @@ -37,24 +37,30 @@ <artifactId>tuscany-assembly</artifactId> <version>2.0-SNAPSHOT</version> </dependency> + + <dependency> + <groupId>org.apache.tuscany.sca</groupId> + <artifactId>tuscany-assembly-xml</artifactId> + <version>2.0-SNAPSHOT</version> + </dependency> - <dependency> + <dependency> <groupId>org.apache.tuscany.sca</groupId> - <artifactId>tuscany-contribution</artifactId> + <artifactId>tuscany-assembly-xsd</artifactId> <version>2.0-SNAPSHOT</version> </dependency> <dependency> <groupId>org.apache.tuscany.sca</groupId> - <artifactId>tuscany-assembly-xml</artifactId> + <artifactId>tuscany-contribution</artifactId> <version>2.0-SNAPSHOT</version> - </dependency> + </dependency> - <dependency> + <dependency> <groupId>org.apache.tuscany.sca</groupId> - <artifactId>tuscany-assembly-xsd</artifactId> + <artifactId>tuscany-core</artifactId> <version>2.0-SNAPSHOT</version> - </dependency> + </dependency> <dependency> <groupId>org.apache.tuscany.sca</groupId> diff --git a/sca-java-2.x/trunk/modules/deployment/src/main/java/org/apache/tuscany/sca/deployment/impl/DeployerImpl.java b/sca-java-2.x/trunk/modules/deployment/src/main/java/org/apache/tuscany/sca/deployment/impl/DeployerImpl.java index cf94c5a8b7..c3e680bd4d 100644 --- a/sca-java-2.x/trunk/modules/deployment/src/main/java/org/apache/tuscany/sca/deployment/impl/DeployerImpl.java +++ b/sca-java-2.x/trunk/modules/deployment/src/main/java/org/apache/tuscany/sca/deployment/impl/DeployerImpl.java @@ -24,6 +24,7 @@ import java.io.Writer; import java.net.URI; import java.net.URL; import java.util.ArrayList; +import java.util.Collection; import java.util.Collections; import java.util.HashSet; import java.util.List; @@ -38,7 +39,13 @@ import javax.xml.stream.XMLStreamWriter; import org.apache.tuscany.sca.assembly.AssemblyFactory; import org.apache.tuscany.sca.assembly.Base; +import org.apache.tuscany.sca.assembly.Component; +import org.apache.tuscany.sca.assembly.ComponentReference; +import org.apache.tuscany.sca.assembly.ComponentService; import org.apache.tuscany.sca.assembly.Composite; +import org.apache.tuscany.sca.assembly.Endpoint; +import org.apache.tuscany.sca.assembly.EndpointReference; +import org.apache.tuscany.sca.assembly.Implementation; import org.apache.tuscany.sca.assembly.builder.BuilderContext; import org.apache.tuscany.sca.assembly.builder.BuilderExtensionPoint; import org.apache.tuscany.sca.assembly.builder.CompositeBuilder; @@ -72,6 +79,7 @@ import org.apache.tuscany.sca.core.ExtensionPointRegistry; import org.apache.tuscany.sca.core.FactoryExtensionPoint; import org.apache.tuscany.sca.core.ModuleActivatorExtensionPoint; import org.apache.tuscany.sca.core.UtilityExtensionPoint; +import org.apache.tuscany.sca.core.assembly.impl.EndpointRegistryImpl; import org.apache.tuscany.sca.definitions.Definitions; import org.apache.tuscany.sca.definitions.DefinitionsFactory; import org.apache.tuscany.sca.definitions.util.DefinitionsUtil; @@ -79,6 +87,9 @@ import org.apache.tuscany.sca.definitions.xml.DefinitionsExtensionPoint; import org.apache.tuscany.sca.deployment.Deployer; import org.apache.tuscany.sca.monitor.Monitor; import org.apache.tuscany.sca.monitor.MonitorFactory; +import org.apache.tuscany.sca.runtime.BaseEndpointRegistry; +import org.apache.tuscany.sca.runtime.EndpointReferenceBinder; +import org.apache.tuscany.sca.runtime.EndpointRegistry; import org.apache.tuscany.sca.xsd.XSDFactory; import org.apache.tuscany.sca.xsd.XSDefinition; @@ -103,6 +114,7 @@ public class DeployerImpl implements Deployer { protected ExtensibleURLArtifactProcessor artifactProcessor; protected ExtensibleStAXArtifactProcessor staxProcessor; protected ValidationSchemaExtensionPoint validationSchema; + protected EndpointReferenceBinder endpointReferenceBinder; protected MonitorFactory monitorFactory; @@ -310,11 +322,13 @@ public class DeployerImpl implements Deployer { // get the validation schema validationSchema = registry.getExtensionPoint(ValidationSchemaExtensionPoint.class); + + // Get the reference binder + endpointReferenceBinder = registry.getExtensionPoint(EndpointReferenceBinder.class); loadSystemContribution(new ProcessorContext(monitorFactory.createMonitor())); inited = true; - } protected void loadSystemContribution(ProcessorContext context) { @@ -546,6 +560,9 @@ public class DeployerImpl implements Deployer { BuilderContext builderContext = new BuilderContext(systemDefinitions, bindingMap, monitor); compositeBuilder.build(domainComposite, builderContext); // analyzeProblems(monitor); + + // do build time reference binding + buildTimeReferenceBind(domainComposite, builderContext); return domainComposite; } @@ -717,5 +734,101 @@ public class DeployerImpl implements Deployer { init(); return systemDefinitions; } + + // The following operations gives references a chance to bind to + // services at deployment time. + + private void buildTimeReferenceBind(Composite domainComposite, BuilderContext context){ + // create temporary local registry for all available local endpoints + EndpointRegistry endpointRegistry = new LocalEndpointRegistry(registry); + + // populate the registry with all the endpoints that are present in the model + populateLocalRegistry(domainComposite, endpointRegistry, context); + + // match all local services against the endpoint references + // we've just created + matchEndpointReferences(domainComposite, endpointRegistry, context); + } + + private void populateLocalRegistry(Composite composite, EndpointRegistry registry, BuilderContext context){ + for (Component component : composite.getComponents()) { + // recurse for composite implementations + Implementation implementation = component.getImplementation(); + if (implementation instanceof Composite) { + populateLocalRegistry((Composite)implementation, registry, context); + } + + // add all endpoints to the local registry + for (ComponentService service : component.getServices()) { + for (Endpoint endpoint : service.getEndpoints()){ + registry.addEndpoint(endpoint); + } + } + + // add endpoint references that we want to match to the registry + for (ComponentReference reference : component.getReferences()) { + for (EndpointReference epr : reference.getEndpointReferences()){ + if (epr.getStatus().equals(EndpointReference.Status.WIRED_TARGET_NOT_FOUND)|| + epr.getStatus().equals(EndpointReference.Status.WIRED_TARGET_IN_BINDING_URI)){ + registry.addEndpointReference(epr); + } + } + } + } + } + + private void matchEndpointReferences(Composite composite, EndpointRegistry registry, BuilderContext builderContext){ + + // look at all the endpoint references and try to match them to + // endpoints + for (EndpointReference endpointReference : registry.getEndpointReferences()){ + endpointReferenceBinder.bindBuildTime(registry, endpointReference, builderContext); + } + } + + // A minimal endpoint registry implementation used to store the Endpoints/EndpointReferences + // for build time local reference resolution. We don't rely on the endpoint registry + // factory here as we specifically just want to do simple local resolution + class LocalEndpointRegistry extends BaseEndpointRegistry { + + private List<Endpoint> endpoints = new ArrayList<Endpoint>(); + + public LocalEndpointRegistry(ExtensionPointRegistry registry){ + super(registry, null, "", ""); + } + + public void addEndpoint(Endpoint endpoint) { + endpoints.add(endpoint); + endpointAdded(endpoint); + } + + public void removeEndpoint(Endpoint endpoint) { + } + + public Collection<Endpoint> getEndpoints() { + return endpoints; + } + + public Endpoint getEndpoint(String uri) { + return null; + } + + public List<Endpoint> findEndpoint(String uri) { + List<Endpoint> foundEndpoints = new ArrayList<Endpoint>(); + for (Endpoint endpoint : endpoints) { + if (endpoint.matches(uri)) { + foundEndpoints.add(endpoint); + logger.fine("Found endpoint with matching service - " + endpoint); + } + // else the service name doesn't match + } + return foundEndpoints; + } + + public void start() { + } + public void stop() { + } + } } |