in modules/core/src/main/java/org/apache/tuscany/sca/core/runtime/impl/EndpointReferenceBinderImpl.java [148:381]
public void bind(DomainRegistry domainRegistry,
EndpointReference endpointReference,
BuilderContext builderContext,
boolean runtime){
logger.fine("Binding " + endpointReference.toString());
Audit matchAudit = new Audit();
// This logic does post build autowire matching but isn't actually used at the moment
// as problems with dependencies mean we still do this during build
if (endpointReference.getStatus() == EndpointReference.Status.AUTOWIRE_PLACEHOLDER){
// do autowire matching
// will only be called at build time at the moment
Multiplicity multiplicity = endpointReference.getReference().getMultiplicity();
for (Endpoint endpoint : domainRegistry.getEndpoints()){
// if (endpoint is in the same composite as endpoint reference){
if ((multiplicity == Multiplicity.ZERO_ONE ||
multiplicity == Multiplicity.ONE_ONE) &&
(endpointReference.getReference().getEndpointReferences().size() > 1)) {
break;
}
// Prevent autowire connecting to self
if (endpointReference.getComponent() ==
endpoint.getComponent()) {
continue;
}
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
Endpoint autowireEndpoint = null;
for (EndpointReference epr : endpointReference.getReference().getEndpointReferences()){
if (epr.getTargetEndpoint() == endpoint){
autowireEndpoint = endpoint;
break;
}
}
if (autowireEndpoint == null){
// create new EPR for autowire
EndpointReference autowireEndpointRefrence = null;
try {
autowireEndpointRefrence = (EndpointReference)endpointReference.clone();
} catch (Exception ex){
// won't happen as clone is supported
}
autowireEndpointRefrence.setTargetEndpoint(endpoint);
autowireEndpointRefrence.setBinding(endpoint.getBinding());
autowireEndpointRefrence.setStatus(EndpointReference.Status.WIRED_TARGET_FOUND_AND_MATCHED);
endpointReference.getReference().getEndpointReferences().add(autowireEndpointRefrence);
}
}
// }
}
if (multiplicity == Multiplicity.ONE_N || multiplicity == Multiplicity.ONE_ONE) {
if (endpointReference.getReference().getEndpointReferences().size() == 1) {
Monitor.error(monitor,
this,
"endpoint-validation-messages",
"NoComponentReferenceTarget",
endpointReference.getReference().getName());
//throw new ServiceRuntimeException("Unable to bind " +
// monitor.getLastProblem().toString());
}
}
setSingleAutoWireTarget(endpointReference.getReference());
} else if ( endpointReference.getStatus() == EndpointReference.Status.WIRED_TARGET_FOUND_AND_MATCHED||
endpointReference.getStatus() == EndpointReference.Status.RESOLVED_BINDING ) {
// The endpoint reference is already resolved to either
// a service endpoint local to this composite or it has
// a remote binding. Just make sure the binding is built
build(endpointReference);
// still need to check that the callback endpoint is set correctly
if (hasCallback(endpointReference) &&
(endpointReference.getCallbackEndpoint() == null
|| endpointReference.getCallbackEndpoint().isUnresolved())) {
selectCallbackEndpoint(endpointReference,
endpointReference.getReference().getCallbackService(),
matchAudit,
builderContext,
runtime);
}
} else if (endpointReference.getStatus() == EndpointReference.Status.WIRED_TARGET_FOUND_READY_FOR_MATCHING ){
// The endpoint reference is already resolved to either
// a service endpoint but no binding was specified in the
// target URL and/or the policies have yet to be matched.
// Used when $self references are resolved
selectForwardEndpoint(endpointReference,
endpointReference.getTargetEndpoint().getService().getEndpoints(),
matchAudit,
builderContext,
runtime);
if (hasCallback(endpointReference)){
selectCallbackEndpoint(endpointReference,
endpointReference.getReference().getCallbackService(),
matchAudit,
builderContext,
runtime);
}
} else if (endpointReference.getStatus() == EndpointReference.Status.WIRED_TARGET_IN_BINDING_URI ||
endpointReference.getStatus() == EndpointReference.Status.WIRED_TARGET_NOT_FOUND ||
endpointReference.getStatus() == EndpointReference.Status.NOT_CONFIGURED){
// The reference is not yet matched to a service
// find the service in the endpoint registry
List<Endpoint> endpoints = domainRegistry.findEndpoint(endpointReference);
if (endpoints.size() > 0){
selectForwardEndpoint(endpointReference,
endpoints,
matchAudit,
builderContext,
runtime);
// 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
if (endpointReference.getStatus() == EndpointReference.Status.WIRED_TARGET_IN_BINDING_URI){
endpointReference.getTargetEndpoint().setBinding(endpointReference.getBinding());
endpointReference.setStatus(EndpointReference.Status.RESOLVED_BINDING);
} else {
processUnknownEndpoint(endpointReference, matchAudit);
if (!endpointReference.getStatus().equals(EndpointReference.Status.WIRED_TARGET_FOUND_AND_MATCHED)){
Monitor.error(monitor,
this,
"endpoint-validation-messages",
"NoEndpointsFound",
endpointReference.toString());
throw new ServiceRuntimeException(monitor.getMessageString(EndpointReferenceBinderImpl.class.getName(),
"endpoint-validation-messages",
"UnableToBind") +
" " +
monitor.getLastProblem().toString());
}
}
} else {
// it's build time so just give the UnknownEndpoint code a chance
// without regard for the result
processUnknownEndpoint(endpointReference, matchAudit);
}
}
logger.fine(matchAudit.toString());
if (endpointReference.getStatus() != EndpointReference.Status.WIRED_TARGET_FOUND_AND_MATCHED &&
endpointReference.getStatus() != EndpointReference.Status.RESOLVED_BINDING){
if (runtime){
Monitor.error(monitor,
this,
"endpoint-validation-messages",
"EndpointReferenceCantBeMatched",
endpointReference.toString(),
matchAudit);
throw new ServiceRuntimeException(monitor.getMessageString(EndpointReferenceBinderImpl.class.getName(),
"endpoint-validation-messages",
"UnableToBind") +
" " +
monitor.getLastProblem().toString());
} else {
Monitor.warning(monitor,
this,
"endpoint-validation-messages",
"ComponentReferenceTargetNotFound",
endpointReference.toString());
return;
}
}
// [rfeng] Setup the target endpoint if the reference uses an explicit binding
if (endpointReference.getTargetEndpoint().getBinding() == null) {
endpointReference.getTargetEndpoint().setBinding(endpointReference.getBinding());
}
// Now the endpoint reference is resolved check that the binding interfaces contract
// and the reference contract are compatible
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());
}
}
// TUSCANY-3783
// if the reference is an async reference and the binding doesn't support
// async natively fluff up the response service/endpoint
ReferenceBindingProvider referenceBindingProvider = ((RuntimeEndpointReference)endpointReference).getBindingProvider();
if ( referenceBindingProvider instanceof EndpointReferenceAsyncProvider &&
!((EndpointReferenceAsyncProvider)referenceBindingProvider).supportsNativeAsync() &&
endpointReference.isAsyncInvocation() &&
endpointReference.getCallbackEndpoint() == null) {
((RuntimeEndpointReference)endpointReference).createAsyncCallbackEndpoint();
}
// System.out.println("MATCH AUDIT:" + matchAudit.toString());
}