001/** 002 * Copyright 2013-2015 John Ericksen 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package org.asciidoctor.asciidoclet; 017 018import com.google.common.base.Optional; 019import com.google.common.io.Files; 020import com.sun.javadoc.*; 021 022import java.io.File; 023import java.io.IOException; 024import java.util.HashSet; 025import java.util.Set; 026import java.util.regex.Pattern; 027 028/** 029 * Iterates over the various elements of a RootDoc, handing off to the DocletRenderer to perform the rendering work. 030 * 031 * @author John Ericksen 032 */ 033public class DocletIterator { 034 035 private static final Pattern ASCIIDOC_FILE_PATTERN = Pattern.compile("(.*\\.(ad|adoc|txt|asciidoc))"); 036 037 private final DocletOptions docletOptions; 038 039 public DocletIterator(DocletOptions docletOptions) { 040 this.docletOptions = docletOptions; 041 } 042 043 /** 044 * Renders a RootDoc's contents. 045 * 046 * @param rootDoc 047 * @param renderer 048 */ 049 public boolean render(RootDoc rootDoc, DocletRenderer renderer) { 050 if (!processOverview(rootDoc, renderer)) { 051 return false; 052 } 053 Set<PackageDoc> packages = new HashSet<PackageDoc>(); 054 for (ClassDoc doc : rootDoc.classes()) { 055 packages.add(doc.containingPackage()); 056 renderClass(doc, renderer); 057 } 058 for (PackageDoc doc : packages) { 059 renderer.renderDoc(doc); 060 } 061 return true; 062 } 063 064 /** 065 * Renders an individual class. 066 * 067 * @param doc input 068 */ 069 private void renderClass(ClassDoc doc, DocletRenderer renderer) { 070 //handle the various parts of the Class doc 071 renderer.renderDoc(doc); 072 for (MemberDoc member : doc.fields()) { 073 renderer.renderDoc(member); 074 } 075 for (MemberDoc member : doc.constructors()) { 076 renderer.renderDoc(member); 077 } 078 for (MemberDoc member : doc.methods()) { 079 renderer.renderDoc(member); 080 } 081 for (MemberDoc member : doc.enumConstants()) { 082 renderer.renderDoc(member); 083 } 084 if (doc instanceof AnnotationTypeDoc) { 085 for (MemberDoc member : ((AnnotationTypeDoc)doc).elements()) { 086 renderer.renderDoc(member); 087 } 088 } 089 } 090 091 private boolean processOverview(RootDoc rootDoc, DocletRenderer renderer) { 092 Optional<File> overview = docletOptions.overview(); 093 if (overview.isPresent()) { 094 File overviewFile = overview.get(); 095 if (isAsciidocFile(overviewFile.getName())) { 096 try { 097 String overviewContent = Files.toString(overviewFile, docletOptions.encoding()); 098 rootDoc.setRawCommentText(overviewContent); 099 renderer.renderDoc(rootDoc); 100 } catch (IOException e) { 101 rootDoc.printError("Error reading overview file: " + e.getLocalizedMessage()); 102 return false; 103 } 104 } 105 else { 106 rootDoc.printNotice("Skipping non-AsciiDoc overview " + overviewFile + ", will be processed by standard Doclet."); 107 } 108 } 109 return true; 110 } 111 112 private static boolean isAsciidocFile(String name) { 113 return ASCIIDOC_FILE_PATTERN.matcher(name).matches(); 114 } 115}