Package tk.eclipse.plugin.jspeditor.editors

Source Code of tk.eclipse.plugin.jspeditor.editors.TLDParser

package tk.eclipse.plugin.jspeditor.editors;

import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;

import org.apache.xerces.parsers.DOMParser;
import org.eclipse.jdt.core.IJavaProject;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.w3c.dom.Text;
import org.xml.sax.InputSource;

import tk.eclipse.plugin.htmleditor.HTMLPlugin;
import tk.eclipse.plugin.htmleditor.assist.AttributeInfo;
import tk.eclipse.plugin.htmleditor.assist.TagInfo;
import tk.eclipse.plugin.htmleditor.gefutils.IJarVisitor;
import tk.eclipse.plugin.htmleditor.gefutils.JarAcceptor;

/**
*
* @author Naoki Takezoe
* @since 2.0.4
*/
public class TLDParser {
 
  private IJavaProject project;
  private String uri = null;
  private String prefix = "";
  private ArrayList<TagInfo> result = new ArrayList<TagInfo>();

  /**
   * Use the specified prefix.
   *
   * @param the prefix
   */
  public TLDParser(IJavaProject project, String prefix){
    this.project = project;
    this.prefix = prefix;
  }
 
  /**
   * Use tld's <code>shortname</code> (or <code>short-name</code>) as prefix.
   */
  public TLDParser(IJavaProject project){
    this(project, null);
  }
 
  /**
   * Returns the <code>uri</code> which declared in the TLD.
   *
   * @return the <code>uri</code>
   */
  public String getUri(){
    return uri;
  }
 
  /**
   * Returns parsed <code>List</code> which contains <code>TagInfo</code>.
   *
   * @return <code>List</code> which contains <code>TagInfo</code>
   */
  public List<TagInfo> getResult(){
    return result;
  }

  public void parse(InputStream in) throws Exception {
    DOMParser parser = new DOMParser();
    parser.setEntityResolver(new TLDResolver());
    parser.parse(new InputSource(in));
    Document doc = parser.getDocument();
    Element element = doc.getDocumentElement();
   
    NodeList nodeList = element.getChildNodes();
    for(int i=0;i<nodeList.getLength();i++){
      Node node = nodeList.item(i);
      if(node instanceof Element){
        Element childElement = (Element)nodeList.item(i);
        String elementName = childElement.getNodeName();
        if(elementName.equals("tag")){
          result.add(parseTagElement(childElement));
        } else if(elementName.equals("uri")){
          uri = getChildText(childElement);
        } else if(elementName.equals("shortname") || elementName.equals("short-name")){
          if(prefix==null){
            prefix = getChildText(childElement);
          }
        } else if(elementName.equals("tag-file")){
          TagInfo tagInfo = parseTagFileElement(childElement);
          if(tagInfo!=null){
            result.add(tagInfo);
          }
        }
      }
    }
  }
 
  /**
   * Parses the tag element and returns <code>TagInfo</code> as result.
   *
   * @param tagFile the tag element
   * @return the <code>TagInfo</code> from the given tag
   */
  private TagInfo parseTagElement(Element tag){
    NodeList children = tag.getChildNodes();
   
    List<AttributeInfo> attributes = new ArrayList<AttributeInfo>();
    String name = null;
    String description = "";
    boolean hasBody = true;
   
    for(int j=0;j<children.getLength();j++){
      Node node = children.item(j);
      if(node instanceof Element){
        Element element = (Element)node;
        String elementName = element.getNodeName();
        if(elementName.equals("name")){
          name = prefix + ":" + getChildText(element);
        } else if(elementName.equals("bodycontent") || elementName.equals("body-content")){
          hasBody = !getChildText(element).equals("empty");
        } else if(elementName.equals("description")){
          description = wrap(getChildText(element));
        } else if(elementName.equals("attribute")){
          AttributeInfo attrInfo = parseAttributeElement(element);
          attributes.add(attrInfo);
        }
      }
    }
   
    TagInfo info = new TagInfo(name, hasBody);
    info.setDescription(description);
    for(int i=0;i<attributes.size();i++){
      info.addAttributeInfo(attributes.get(i));
    }

    return info;
  }
 
  private AttributeInfo parseAttributeElement(Element attr){
    NodeList children = attr.getChildNodes();
   
    String name = null;
    String description = "";
    boolean required = false;
   
    for(int i=0;i<children.getLength();i++){
      Node node = children.item(i);
      if(node instanceof Element){
        Element element = (Element)node;
        String elementName = element.getNodeName();
        if(elementName.equals("name")){
          name = getChildText(element);
        } else if(elementName.equals("description")){
          description = wrap(getChildText(element));
        } else if(elementName.equals("required")){
          if(getChildText(element).equals("true")){
            required = true;
          } else {
            required = false;
          }
        }
      }
    }
   
    AttributeInfo attrInfo = new AttributeInfo(name, true, AttributeInfo.NONE, required);
    attrInfo.setDescription(description);
    return attrInfo;
  }
 
  private static String getChildText(Element element){
    StringBuffer sb = new StringBuffer();
    NodeList children = element.getChildNodes();
    for(int i=0;i<children.getLength();i++){
      Node node = children.item(i);
      if(node instanceof Text){
        sb.append(node.getNodeValue());
      }
    }
    return sb.toString().trim().replaceAll("\\s+", " ");
  }
 
  private static String wrap(String text){
    StringBuffer sb = new StringBuffer();
    int word = 0;
    for(int i=0;i<text.length();i++){
      char c = text.charAt(i);
      if(word > 40){
        if(c==' ' || c== '\t'){
          sb.append('\n');
          word = 0;
          continue;
        }
      }
      sb.append(c);
      word++;
    }
    return sb.toString();
  }
 
  /**
   * Parses the tag-file element and returns <code>TagInfo</code> as result.
   *
   * @since 2.0.5
   * @param tagFile the tag-file element
   * @return the <code>TagInfo</code> from given tag file
   *   or <code>null</code> if given tag file does not found.
   */
  private TagInfo parseTagFileElement(Element tagFile) throws Exception {
    NodeList children = tagFile.getChildNodes();
   
    List<AttributeInfo> attributes = new ArrayList<AttributeInfo>();
    String name = null;
    String description = "";
    boolean hasBody = true;
   
    for(int j=0;j<children.getLength();j++){
      Node node = children.item(j);
      if(node instanceof Element){
        Element element = (Element)node;
        String elementName = element.getNodeName();
        if(elementName.equals("name")){
          name = prefix + ":" + getChildText(element);
        } else if(elementName.equals("description")){
          description = wrap(getChildText(element));
        } else if(elementName.equals("path") && project!=null){
          String path = getChildText(element);
          InputStream in = getTagFile(path);
          if(in != null){
            TagInfo tagInfo = TagFileParser.parseTagFile(null, null, in);
            for(int i=0;i<tagInfo.getAttributeInfo().length;i++){
              attributes.add(tagInfo.getAttributeInfo()[i]);
            }
          } else {
            return null;
          }
        }
      }
    }
   
    TagInfo info = new TagInfo(name, hasBody);
    info.setDescription(description);
    for(int i=0;i<attributes.size();i++){
      info.addAttributeInfo(attributes.get(i));
    }

    return info;
  }
 
  /**
   * TODO This method might have to be moved to the utility class.
   *
   * @since 2.0.5
   * @param path the path of the tag file
   *   <ul>
   *     <li>starts with &quot;/META-INF/tags&quot; : in the WAR file
   *     <li>starts with &quot;/WEB-INF/tags&quot; : in the JAR file
   *   </ul>
   * @return the <code>InputSream</code> of the given tag file or <code>null</code>.
   */
  private InputStream getTagFile(final String path){
    try {
      if(path.startsWith("/META-INF/tags")){
        // in JAR (or classpath?)
        return (InputStream)JarAcceptor.accept(project.getProject(),
            new IJarVisitor(){
          public Object visit(JarFile file, JarEntry entry) throws Exception {
            if(("/" + entry.getName()).equals(path)){
              return file.getInputStream(entry);
            }
            return null;
          }
        });
      }
     
      // in WAR
      File basedir = TLDInfo.getBaseDir(project.getProject()).getLocation().makeAbsolute().toFile();
      File file = new File(basedir, path);
      return new FileInputStream(file);
     
    } catch(Exception ex){
      HTMLPlugin.logException(ex);
      return null;
    }
  }
 
}
TOP

Related Classes of tk.eclipse.plugin.jspeditor.editors.TLDParser

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.