blob: 1575a265124527cca56887513d617a5316c12ebf [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2009 Shane Clarke.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Shane Clarke - initial API and implementation
*******************************************************************************/
package org.eclipse.jst.ws.internal.jaxws.core.annotations.validation;
import static org.eclipse.jst.ws.internal.jaxws.core.utils.JAXWSUtils.VALUE;
import java.util.Collection;
import javax.activation.DataSource;
import javax.xml.soap.SOAPMessage;
import javax.xml.transform.Source;
import javax.xml.ws.BindingType;
import javax.xml.ws.ServiceMode;
import javax.xml.ws.WebServiceProvider;
import javax.xml.ws.Service.Mode;
import javax.xml.ws.http.HTTPBinding;
import javax.xml.ws.soap.SOAPBinding;
import org.eclipse.jst.ws.annotations.core.processor.AbstractAnnotationProcessor;
import org.eclipse.jst.ws.annotations.core.utils.AnnotationUtils;
import org.eclipse.jst.ws.internal.jaxws.core.JAXWSCoreMessages;
import com.sun.mirror.declaration.AnnotationMirror;
import com.sun.mirror.declaration.AnnotationTypeDeclaration;
import com.sun.mirror.declaration.ClassDeclaration;
import com.sun.mirror.declaration.ConstructorDeclaration;
import com.sun.mirror.declaration.Declaration;
import com.sun.mirror.declaration.InterfaceDeclaration;
import com.sun.mirror.declaration.Modifier;
import com.sun.mirror.type.InterfaceType;
import com.sun.mirror.type.TypeMirror;
public class WebServiceProviderRules extends AbstractAnnotationProcessor {
@Override
public void process() {
AnnotationTypeDeclaration annotationDeclaration = (AnnotationTypeDeclaration) environment
.getTypeDeclaration(WebServiceProvider.class.getName());
Collection<Declaration> annotatedTypes = environment.getDeclarationsAnnotatedWith(annotationDeclaration);
for (Declaration declaration : annotatedTypes) {
if (declaration instanceof ClassDeclaration) {
checkForDefaultConstructor((ClassDeclaration)declaration);
checkForProviderInterface((ClassDeclaration)declaration);
}
}
}
private void checkForProviderInterface(ClassDeclaration classDeclaration) {
Collection<InterfaceType> interfaces = classDeclaration.getSuperinterfaces();
boolean implementsTypedProvider = false;
if (interfaces.size() > 0) {
for (InterfaceType interfaceType : interfaces) {
Collection<TypeMirror> typeParameters = interfaceType.getActualTypeArguments();
if (typeParameters.size() > 0) {
for (TypeMirror typeMirror : typeParameters) {
if (typeMirror instanceof ClassDeclaration) {
ClassDeclaration classDecl = (ClassDeclaration) typeMirror;
if (classDecl.getQualifiedName().equals(SOAPMessage.class.getCanonicalName())) {
checkSOAPMessageRequirements(classDeclaration);
implementsTypedProvider = true;
break;
}
Collection<InterfaceType> implementedInterfaces = classDecl.getSuperinterfaces();
for (InterfaceType implementedInterface : implementedInterfaces) {
InterfaceDeclaration interfaceDecl = implementedInterface.getDeclaration();
if (interfaceDecl != null) {
if (interfaceDecl.getQualifiedName().equals(Source.class.getCanonicalName())) {
implementsTypedProvider = true;
break;
}
if (interfaceDecl.getQualifiedName().equals(DataSource.class.getCanonicalName())) {
checkDataSourceRequirements(classDeclaration);
implementsTypedProvider = true;
break;
}
}
}
}
if (typeMirror instanceof InterfaceDeclaration) {
InterfaceDeclaration interfaceDecl = (InterfaceDeclaration) typeMirror;
if (interfaceDecl.getQualifiedName().equals(Source.class.getCanonicalName())) {
implementsTypedProvider = true;
break;
}
if (interfaceDecl.getQualifiedName().equals(DataSource.class.getCanonicalName())) {
checkDataSourceRequirements(classDeclaration);
implementsTypedProvider = true;
break;
}
}
}
}
}
}
if (!implementsTypedProvider) {
AnnotationMirror webServiceProvider = AnnotationUtils.getAnnotation(classDeclaration,
WebServiceProvider.class);
printFixableError(webServiceProvider.getPosition(),
JAXWSCoreMessages.WEBSERVICEPROVIDER_IMPLEMENT_TYPED_PROVIDER_INTERFACE);
}
}
private void checkSOAPMessageRequirements(ClassDeclaration classDeclaration) {
if (!isSOAPBinding(classDeclaration)) {
printError(classDeclaration.getPosition(), JAXWSCoreMessages.WEBSERVICEPROVIDER_SOAPMESSAGE_SOAPBINDING);
}
if (!isMessageMode(classDeclaration)) {
printError(classDeclaration.getPosition(), JAXWSCoreMessages.WEBSERVICEPROVIDER_SOAPMESSAGE_MESSAGE_MODE);
}
}
private void checkDataSourceRequirements(ClassDeclaration classDeclaration) {
if (!isHTTPBinding(classDeclaration)) {
printError(classDeclaration.getPosition(), JAXWSCoreMessages.WEBSERVICEPROVIDER_DATASOURCE_HTTPBINDING);
}
if (!isMessageMode(classDeclaration)) {
printError(classDeclaration.getPosition(), JAXWSCoreMessages.WEBSERVICEPROVIDER_DATASOURCE_MESSAGE_MODE);
}
}
private boolean isSOAPBinding(ClassDeclaration classDeclaration) {
String bindingType = getBindingTypeValue(classDeclaration);
if (bindingType.equals(SOAPBinding.SOAP11HTTP_BINDING)
|| bindingType.equals(SOAPBinding.SOAP12HTTP_BINDING)
|| bindingType.equals(SOAPBinding.SOAP11HTTP_MTOM_BINDING)
|| bindingType.equals(SOAPBinding.SOAP12HTTP_MTOM_BINDING)) {
return true;
}
return false;
}
private boolean isHTTPBinding(ClassDeclaration classDeclaration) {
String bindingType = getBindingTypeValue(classDeclaration);
if (bindingType.equals(HTTPBinding.HTTP_BINDING)) {
return true;
}
return false;
}
private String getBindingTypeValue(ClassDeclaration classDeclaration) {
AnnotationMirror bindingType = AnnotationUtils.getAnnotation(classDeclaration, BindingType.class);
if (bindingType != null) {
String value = AnnotationUtils.getStringValue(bindingType, VALUE);
if (value != null) {
return value;
}
}
return SOAPBinding.SOAP11HTTP_BINDING;
}
private boolean isMessageMode(ClassDeclaration classDeclaration) {
return getServiceMode(classDeclaration).equals(Mode.MESSAGE.name());
}
private boolean isPayloadMode(ClassDeclaration classDeclaration) {
return getServiceMode(classDeclaration).equals(Mode.PAYLOAD.name());
}
private String getServiceMode(ClassDeclaration classDeclaration) {
AnnotationMirror serviceMode = AnnotationUtils.getAnnotation(classDeclaration, ServiceMode.class);
if (serviceMode != null) {
String value = AnnotationUtils.getStringValue(serviceMode, VALUE);
if (value != null) {
return value;
}
}
return Mode.PAYLOAD.toString();
}
private void checkForDefaultConstructor(ClassDeclaration classDeclaration) {
boolean hasDefaultConstructor = false;
Collection<ConstructorDeclaration> constructors = classDeclaration.getConstructors();
if (constructors.size() == 0) {
hasDefaultConstructor = true;
} else {
for (ConstructorDeclaration constructorDeclaration : constructors) {
if (constructorDeclaration.getModifiers().contains(Modifier.PUBLIC) &&
constructorDeclaration.getParameters().size() == 0) {
hasDefaultConstructor = true;
break;
}
}
}
if (!hasDefaultConstructor) {
AnnotationMirror webServiceProvider = AnnotationUtils.getAnnotation(classDeclaration, WebServiceProvider.class);
printFixableError(webServiceProvider.getPosition(),
JAXWSCoreMessages.WEBSERVICEPROVIDER_DEFAULT_PUBLIC_CONSTRUCTOR);
}
}
}