Package org.codehaus.enunciate.contract.jaxb

Source Code of org.codehaus.enunciate.contract.jaxb.AccessorFilter

/*
* Copyright 2006-2008 Web Cohesion
*
* Licensed 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.codehaus.enunciate.contract.jaxb;

import com.sun.mirror.declaration.*;
import com.sun.mirror.type.AnnotationType;
import net.sf.jelly.apt.decorations.declaration.DecoratedMethodDeclaration;
import net.sf.jelly.apt.decorations.declaration.PropertyDeclaration;

import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlTransient;
import java.util.Collection;

/**
* Filter for potential accessors.
*
* @author Ryan Heaton
*/
public class AccessorFilter {

  private final XmlAccessType accessType;

  public AccessorFilter(XmlAccessType accessType) {
    this.accessType = accessType;

    if (accessType == null) {
      throw new IllegalArgumentException("An access type must be specified.");
    }
  }

  /**
   * The access type for this filter.
   *
   * @return The access type for this filter.
   */
  public XmlAccessType getAccessType() {
    return accessType;
  }

  /**
   * Whether to accept the given member declaration as an accessor.
   *
   * @param declaration The declaration to filter.
   * @return Whether to accept the given member declaration as an accessor.
   */
  public boolean accept(MemberDeclaration declaration) {
    if (isXmlTransient(declaration)) {
      return false;
    }

    if (declaration instanceof PropertyDeclaration) {
      PropertyDeclaration property = ((PropertyDeclaration) declaration);

      if ("".equals(property.getPropertyName())) {
        return false;
      }

      for (String annotationName : property.getAnnotations().keySet()) {
        if (annotationName.startsWith("javax.xml.bind.annotation")) {
          //if the property has an explicit annotation, we'll include it.
          return true;
        }
      }

      DecoratedMethodDeclaration getter = property.getGetter();
      if (getter == null) {
        //needs a getter.
        return false;
      }

      DecoratedMethodDeclaration setter = property.getSetter();
      if (setter == null) {
        //needs a setter.
        return false;
      }

      if (!getter.getModifiers().contains(Modifier.PUBLIC)) {
        //we only have to worry about public methods ("properties" are only defined by public accessor methods).
        return false;
      }

      if (!setter.getModifiers().contains(Modifier.PUBLIC)) {
        //we only have to worry about public methods ("properties" are only defined by public accessor methods).
        return false;
      }

      return (((accessType != XmlAccessType.NONE) && (accessType != XmlAccessType.FIELD)) || (explicitlyDeclaredAccessor(declaration)));
    }
    else if (declaration instanceof FieldDeclaration) {
      if (declaration.getModifiers().contains(Modifier.STATIC) || declaration.getModifiers().contains(Modifier.TRANSIENT)) {
        return false;
      }

      if ((accessType == XmlAccessType.NONE) || (accessType == XmlAccessType.PROPERTY)) {
        return explicitlyDeclaredAccessor(declaration);
      }

      if (accessType == XmlAccessType.PUBLIC_MEMBER) {
        return (declaration.getModifiers().contains(Modifier.PUBLIC) || (explicitlyDeclaredAccessor(declaration)));
      }

      //the accessType is FIELD.  Include it.
      return true;
    }

    return false;
  }

  /**
   * Whether the specified member declaration is explicitly declared to be an accessor.
   *
   * @param declaration The declaration to check whether it is explicitly declared to be an accessor.
   * @return Whether the specified member declaration is explicitly declared to be an accessor.
   */
  protected boolean explicitlyDeclaredAccessor(MemberDeclaration declaration) {
    Collection<AnnotationMirror> annotationMirrors = declaration.getAnnotationMirrors();
    for (AnnotationMirror annotationMirror : annotationMirrors) {
      AnnotationType annotationType = annotationMirror.getAnnotationType();
      if (annotationType != null) {
        AnnotationTypeDeclaration annotationDeclaration = annotationType.getDeclaration();
        if ((annotationDeclaration != null) && (annotationDeclaration.getQualifiedName().startsWith(XmlElement.class.getPackage().getName()))) {
          //if it's annotated with anything in javax.xml.bind.annotation, (exception XmlTransient) we'll consider it to be "explicitly annotated."
          return !annotationDeclaration.getQualifiedName().equals(XmlTransient.class.getName());
        }
      }
    }

    return false;
  }

  /**
   * Whether a declaration is xml transient.
   *
   * @param declaration The declaration on which to determine xml transience.
   * @return Whether a declaration is xml transient.
   */
  protected boolean isXmlTransient(Declaration declaration) {
    return (declaration.getAnnotation(XmlTransient.class) != null);
  }
}
TOP

Related Classes of org.codehaus.enunciate.contract.jaxb.AccessorFilter

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.