From 47f6879e357c5f878e3e43164e243cd41e056df0 Mon Sep 17 00:00:00 2001 From: slaws Date: Tue, 13 Jul 2010 09:12:08 +0000 Subject: TUSCANY-3616 - Add code to check that that interface contracts a reference and reference binding and at service and service binding match. Motivated by BWS_2007. TO do this properly we have to test that the interfaces are described using the same IDL and if not convert to WSDL1.1 are required by the SCA specifications. There are a lot of changes here as doing this upset quite a few tests. Further work is required to look at the details of our WSDL generation process which looks a little suspect around wrapper namespaces. git-svn-id: http://svn.us.apache.org/repos/asf/tuscany@963624 13f79535-47bb-0310-9956-ffa450edef68 --- .../sca/builder/impl/ComponentBuilderImpl.java | 87 +++++++++++++++++++++- .../impl/CompositeComponentTypeBuilderImpl.java | 81 +++++++++++++++++++- 2 files changed, 163 insertions(+), 5 deletions(-) (limited to 'sca-java-2.x/trunk/modules/builder/src/main') diff --git a/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/ComponentBuilderImpl.java b/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/ComponentBuilderImpl.java index 32ebc71348..694ece2d6c 100644 --- a/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/ComponentBuilderImpl.java +++ b/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/ComponentBuilderImpl.java @@ -61,6 +61,7 @@ import org.apache.tuscany.sca.assembly.SCABindingFactory; import org.apache.tuscany.sca.assembly.Service; import org.apache.tuscany.sca.assembly.builder.BuilderContext; import org.apache.tuscany.sca.assembly.builder.BuilderExtensionPoint; +import org.apache.tuscany.sca.assembly.builder.ContractBuilder; import org.apache.tuscany.sca.assembly.builder.ImplementationBuilder; import org.apache.tuscany.sca.assembly.builder.Messages; import org.apache.tuscany.sca.assembly.xsd.Constants; @@ -75,9 +76,12 @@ import org.apache.tuscany.sca.definitions.Definitions; import org.apache.tuscany.sca.interfacedef.Compatibility; import org.apache.tuscany.sca.interfacedef.DataType; import org.apache.tuscany.sca.interfacedef.IncompatibleInterfaceContractException; +import org.apache.tuscany.sca.interfacedef.Interface; import org.apache.tuscany.sca.interfacedef.InterfaceContract; import org.apache.tuscany.sca.interfacedef.InterfaceContractMapper; import org.apache.tuscany.sca.interfacedef.impl.DataTypeImpl; +import org.apache.tuscany.sca.interfacedef.java.JavaInterface; +import org.apache.tuscany.sca.interfacedef.java.JavaInterfaceContract; import org.apache.tuscany.sca.interfacedef.util.XMLType; import org.apache.tuscany.sca.monitor.Monitor; import org.apache.tuscany.sca.policy.ExtensionType; @@ -106,6 +110,7 @@ public class ComponentBuilderImpl { private InterfaceContractMapper interfaceContractMapper; private BuilderExtensionPoint builders; private Mediator mediator; + private ContractBuilder contractBuilder; public ComponentBuilderImpl(ExtensionPointRegistry registry) { UtilityExtensionPoint utilities = registry.getExtensionPoint(UtilityExtensionPoint.class); @@ -120,6 +125,7 @@ public class ComponentBuilderImpl { policyBuilder = new ComponentPolicyBuilderImpl(registry); builders = registry.getExtensionPoint(BuilderExtensionPoint.class); mediator = new MediatorImpl(registry); + contractBuilder = builders.getContractBuilder(); } public void setComponentTypeBuilder(CompositeComponentTypeBuilderImpl componentTypeBuilder) { @@ -1297,7 +1303,8 @@ public class ComponentBuilderImpl { boolean isCompatible = true; String incompatibilityReason = ""; try{ - isCompatible = interfaceContractMapper.checkCompatibility(topInterfaceContract, bottomInterfaceContract, Compatibility.SUBSET, false, false); + isCompatible = checkSubsetCompatibility(topInterfaceContract, + bottomInterfaceContract); } catch (IncompatibleInterfaceContractException ex){ isCompatible = false; incompatibilityReason = ex.getMessage(); @@ -1311,6 +1318,24 @@ public class ComponentBuilderImpl { topContract.getName(), incompatibilityReason); } + + // TODO - there is an issue with the following code if the + // contracts of of different types. Need to use the + // normalized form + + // fix up the forward interface based on the promoted component + // Someone might have manually specified a callback interface but + // left out the forward interface + if (topInterfaceContract.getInterface() == null){ + topInterfaceContract.setInterface(bottomInterfaceContract.getInterface()); + } + + // fix up the callback interface based on the promoted component + // Someone might have manually specified a forward interface but + // left out the callback interface + if (topInterfaceContract.getCallbackInterface() == null){ + topInterfaceContract.setCallbackInterface(bottomInterfaceContract.getCallbackInterface()); + } } } @@ -1337,7 +1362,8 @@ public class ComponentBuilderImpl { boolean isCompatible = true; String incompatibilityReason = ""; try{ - isCompatible = interfaceContractMapper.checkCompatibility(bottomInterfaceContract, topInterfaceContract, Compatibility.SUBSET, false, false); + isCompatible = checkSubsetCompatibility(bottomInterfaceContract, + topInterfaceContract); } catch (IncompatibleInterfaceContractException ex){ isCompatible = false; incompatibilityReason = ex.getMessage(); @@ -1351,6 +1377,24 @@ public class ComponentBuilderImpl { topContract.getName(), incompatibilityReason); } + + // TODO - there is an issue with the following code if the + // contracts of of different types. Need to use the + // normalized form + + // fix up the forward interface based on the promoted component + // Someone might have manually specified a callback interface but + // left out the forward interface + if (topInterfaceContract.getInterface() == null){ + topInterfaceContract.setInterface(bottomInterfaceContract.getInterface()); + } + + // fix up the callback interface based on the promoted component + // Someone might have manually specified a forward interface but + // left out the callback interface + if (topInterfaceContract.getCallbackInterface() == null){ + topInterfaceContract.setCallbackInterface(bottomInterfaceContract.getCallbackInterface()); + } } } @@ -1418,6 +1462,43 @@ public class ComponentBuilderImpl { } else if (componentReference.getCallback().getBindings().isEmpty() && componentTypeReference.getCallback() != null) { componentReference.getCallback().getBindings().addAll(componentTypeReference.getCallback().getBindings()); } - } + } + + /** + * A local wrapper for the interace contract mapper as we need to normalize the + * interface contracts if appropriate and the mapper doesn't have the right + * dependencies to be able to do it. + * + * Sometimes the two interfaces can be presented using different IDLs, for example + * Java and WSDL. In this case interfaces are converted so that they are both WSDL1.1 interfaces + * and they are then compared. The generated WSDL is cached on the interface object for + * any subsequent matching + * + * @param contractA + * @param contractB + * @return true if the interface contracts match + */ + private boolean checkSubsetCompatibility(InterfaceContract contractA, InterfaceContract contractB) + throws IncompatibleInterfaceContractException { + + if (contractA.getClass() != contractB.getClass()) { + + if (contractA instanceof JavaInterfaceContract){ + contractBuilder.build(contractA, null); + contractA = ((JavaInterfaceContract)contractA).getNormalizedWSDLContract(); + } + + if (contractB instanceof JavaInterfaceContract){ + contractBuilder.build(contractB, null); + contractB = ((JavaInterfaceContract)contractB).getNormalizedWSDLContract(); + } + } + + return interfaceContractMapper.checkCompatibility(contractA, + contractB, + Compatibility.SUBSET, + false, + false); + } } diff --git a/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/CompositeComponentTypeBuilderImpl.java b/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/CompositeComponentTypeBuilderImpl.java index 2ea35ffb9b..1deec1b5e2 100644 --- a/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/CompositeComponentTypeBuilderImpl.java +++ b/sca-java-2.x/trunk/modules/builder/src/main/java/org/apache/tuscany/sca/builder/impl/CompositeComponentTypeBuilderImpl.java @@ -42,6 +42,7 @@ import org.apache.tuscany.sca.assembly.SCABindingFactory; import org.apache.tuscany.sca.assembly.Service; import org.apache.tuscany.sca.assembly.builder.BuilderContext; import org.apache.tuscany.sca.assembly.builder.BuilderExtensionPoint; +import org.apache.tuscany.sca.assembly.builder.ContractBuilder; import org.apache.tuscany.sca.assembly.builder.Messages; import org.apache.tuscany.sca.core.ExtensionPointRegistry; import org.apache.tuscany.sca.core.FactoryExtensionPoint; @@ -51,6 +52,7 @@ import org.apache.tuscany.sca.interfacedef.Compatibility; import org.apache.tuscany.sca.interfacedef.IncompatibleInterfaceContractException; import org.apache.tuscany.sca.interfacedef.InterfaceContract; import org.apache.tuscany.sca.interfacedef.InterfaceContractMapper; +import org.apache.tuscany.sca.interfacedef.java.JavaInterfaceContract; import org.apache.tuscany.sca.monitor.Monitor; import org.apache.tuscany.sca.policy.ExtensionType; import org.apache.tuscany.sca.policy.PolicySubject; @@ -73,6 +75,7 @@ public class CompositeComponentTypeBuilderImpl { private SCABindingFactory scaBindingFactory; private InterfaceContractMapper interfaceContractMapper; private BuilderExtensionPoint builders; + private ContractBuilder contractBuilder; public CompositeComponentTypeBuilderImpl(ExtensionPointRegistry registry) { UtilityExtensionPoint utilities = registry.getExtensionPoint(UtilityExtensionPoint.class); @@ -83,6 +86,7 @@ public class CompositeComponentTypeBuilderImpl { interfaceContractMapper = utilities.getUtility(InterfaceContractMapper.class); builders = registry.getExtensionPoint(BuilderExtensionPoint.class); + contractBuilder = builders.getContractBuilder(); } public void setComponentBuilder(ComponentBuilderImpl componentBuilder) { @@ -434,7 +438,7 @@ public class CompositeComponentTypeBuilderImpl { boolean isCompatible = true; String incompatibilityReason = ""; try{ - isCompatible = interfaceContractMapper.checkCompatibility(topInterfaceContract, bottomInterfaceContract, Compatibility.SUBSET, false, false); + isCompatible = checkSubsetCompatibility(topInterfaceContract, bottomInterfaceContract); } catch (IncompatibleInterfaceContractException ex){ isCompatible = false; incompatibilityReason = ex.getMessage(); @@ -447,6 +451,24 @@ public class CompositeComponentTypeBuilderImpl { topContract.getName(), incompatibilityReason); } + + // TODO - there is an issue with the following code if the + // contracts of of different types. Need to use the + // normalized form + + // fix up the forward interface based on the promoted component + // Someone might have manually specified a callback interface but + // left out the forward interface + if (topInterfaceContract.getInterface() == null){ + topInterfaceContract.setInterface(bottomInterfaceContract.getInterface()); + } + + // fix up the callback interface based on the promoted component + // Someone might have manually specified a forward interface but + // left out the callback interface + if (topInterfaceContract.getCallbackInterface() == null){ + topInterfaceContract.setCallbackInterface(bottomInterfaceContract.getCallbackInterface()); + } } } @@ -472,7 +494,7 @@ public class CompositeComponentTypeBuilderImpl { boolean isCompatible = true; String incompatibilityReason = ""; try{ - isCompatible = interfaceContractMapper.checkCompatibility(bottomInterfaceContract, topInterfaceContract, Compatibility.SUBSET, false, false); + isCompatible = checkSubsetCompatibility(bottomInterfaceContract, topInterfaceContract); } catch (IncompatibleInterfaceContractException ex){ isCompatible = false; incompatibilityReason = ex.getMessage(); @@ -485,6 +507,24 @@ public class CompositeComponentTypeBuilderImpl { topContract.getName(), incompatibilityReason); } + + // TODO - there is an issue with the following code if the + // contracts of of different types. Need to use the + // normalized form + + // fix up the forward interface based on the promoted component + // Someone might have manually specified a callback interface but + // left out the forward interface + if (topInterfaceContract.getInterface() == null){ + topInterfaceContract.setInterface(bottomInterfaceContract.getInterface()); + } + + // fix up the callback interface based on the promoted component + // Someone might have manually specified a forward interface but + // left out the callback interface + if (topInterfaceContract.getCallbackInterface() == null){ + topInterfaceContract.setCallbackInterface(bottomInterfaceContract.getCallbackInterface()); + } } } @@ -616,4 +656,41 @@ public class CompositeComponentTypeBuilderImpl { } } + /** + * A local wrapper for the interace contract mapper as we need to normalize the + * interface contracts if appropriate and the mapper doesn't have the right + * dependencies to be able to do it. + * + * Sometimes the two interfaces can be presented using different IDLs, for example + * Java and WSDL. In this case interfaces are converted so that they are both WSDL1.1 interfaces + * and they are then compared. The generated WSDL is cached on the interface object for + * any subsequent matching + * + * @param contractA + * @param contractB + * @return true if the interface contracts match + */ + private boolean checkSubsetCompatibility(InterfaceContract contractA, InterfaceContract contractB) + throws IncompatibleInterfaceContractException { + + if (contractA.getClass() != contractB.getClass()) { + + if (contractA instanceof JavaInterfaceContract){ + contractBuilder.build(contractA, null); + contractA = ((JavaInterfaceContract)contractA).getNormalizedWSDLContract(); + } + + if (contractB instanceof JavaInterfaceContract){ + contractBuilder.build(contractB, null); + contractB = ((JavaInterfaceContract)contractB).getNormalizedWSDLContract(); + } + } + + return interfaceContractMapper.checkCompatibility(contractA, + contractB, + Compatibility.SUBSET, + false, + false); + } + } //end class -- cgit v1.2.3