Home | History | Annotate | Download | only in doclet
      1 /*
      2  * Copyright (C) 2009 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package signature.converter.doclet;
     18 
     19 import java.io.File;
     20 import java.io.FileWriter;
     21 import java.io.IOException;
     22 import java.io.PrintWriter;
     23 import java.io.StringWriter;
     24 import java.lang.reflect.Constructor;
     25 import java.util.HashSet;
     26 import java.util.Set;
     27 
     28 import signature.converter.Visibility;
     29 import signature.converter.doclet.DocletToSigConverter;
     30 import signature.converter.util.CompilationUnit;
     31 import signature.model.IApi;
     32 import signature.model.util.ModelUtil;
     33 
     34 import com.sun.javadoc.RootDoc;
     35 import com.sun.tools.javac.util.Context;
     36 import com.sun.tools.javac.util.ListBuffer;
     37 import com.sun.tools.javac.util.Options;
     38 import com.sun.tools.javadoc.JavadocTool;
     39 import com.sun.tools.javadoc.Messager;
     40 import com.sun.tools.javadoc.ModifierFilter;
     41 import com.sun.tools.javadoc.RootDocImpl;
     42 
     43 public class DocletTestConverter extends signature.converter.util.AbstractTestSourceConverter {
     44 
     45     static String sourcepath;
     46     static String separator;
     47 
     48     static {
     49         separator = System.getProperty("file.separator");
     50 
     51         sourcepath = System.getProperty("java.io.tmpdir");
     52         sourcepath = sourcepath + separator + "cts" + separator;
     53         System.out.println(">> "+sourcepath);
     54     }
     55 
     56     public IApi convert(Visibility visibility, Set<CompilationUnit> units) throws IOException {
     57         try {
     58             Set<String> packages = new HashSet<String>();
     59             for(CompilationUnit u : units){
     60                 putSource(u);
     61                 String p = ModelUtil.getPackageName(u.getName());
     62                 assert p.length() > 0 : "default package not supported by doclets";
     63                 packages.add(p);
     64             }
     65 
     66             RootDoc root = getRootDoc(visibility, packages);
     67 
     68             DocletToSigConverter converter = new DocletToSigConverter();
     69 
     70             IApi api = converter.convertDocletRoot("Doclet Test", root, visibility, packages);
     71             return api;
     72         }
     73         finally {
     74             removeSources();
     75         }
     76     }
     77 
     78     public static void putSource(CompilationUnit source) throws IOException {
     79         String directory = sourcepath;
     80         String filename = source.getName();    // a.b.C
     81         int pos = filename.indexOf(".");
     82         while(pos > 0) {
     83             directory = directory + filename.substring(0, pos) + separator;
     84             filename = filename.substring(pos+1);
     85             pos = filename.indexOf(".");
     86         }
     87 
     88         File file = new File(directory, filename + ".java");
     89         File parent = file.getParentFile();
     90         parent.mkdirs();
     91 
     92         FileWriter wr = new FileWriter(file);
     93         wr.write(source.getSource());
     94         wr.close();
     95     }
     96 
     97     private static void removeSources() {
     98         File file = new File(sourcepath);
     99         removeFile(file);
    100     }
    101 
    102     private static void removeFile(File file){
    103         if(file.isDirectory()){
    104             for(File f : file.listFiles()) removeFile(f);
    105         }
    106         file.delete();
    107     }
    108 
    109     private static RootDoc getRootDoc(Visibility visibility, java.util.Set<String> packages) throws IOException  {
    110         long accessModifier = 0;
    111         if(visibility == Visibility.PUBLIC){
    112             accessModifier =
    113                 com.sun.tools.javac.code.Flags.PUBLIC;    // 0x1
    114         }
    115         if(visibility == Visibility.PROTECTED){
    116             accessModifier =
    117                 com.sun.tools.javac.code.Flags.PUBLIC    // 0x1
    118                 | com.sun.tools.javac.code.Flags.PROTECTED;    // 0x4
    119         }
    120         if(visibility == Visibility.PACKAGE){
    121             accessModifier =
    122                 com.sun.tools.javac.code.Flags.PUBLIC    // 0x1
    123                 | com.sun.tools.javac.code.Flags.PROTECTED    // 0x4
    124                 | com.sun.tools.javadoc.ModifierFilter.PACKAGE; // 0x80000000
    125         }
    126         if(visibility == Visibility.PRIVATE){
    127             accessModifier =
    128                 com.sun.tools.javac.code.Flags.PUBLIC    // 0x1
    129                 | com.sun.tools.javac.code.Flags.PROTECTED    // 0x4
    130                 | com.sun.tools.javadoc.ModifierFilter.PACKAGE // 0x80000000
    131                 | com.sun.tools.javac.code.Flags.PRIVATE;    // 0x2
    132         }
    133 
    134         ModifierFilter showAccess = new ModifierFilter(accessModifier);
    135         boolean breakiterator = false;
    136         boolean quiet = false;
    137         boolean legacy = false;
    138         boolean docClasses = false;
    139 
    140         String docLocale = "";
    141         String encoding = null;
    142         ListBuffer<String> javaNames = new ListBuffer<String>();
    143         for(String p : packages)
    144             javaNames.append(p);
    145 
    146         ListBuffer<String[]> options = new ListBuffer<String[]>();
    147 
    148 
    149 //        String sourcepath = "//D:/Documents/Projects/08_CTS/signature-tools/signature-tools/test/";
    150         options.append(new String[]{"-sourcepath", sourcepath});
    151 
    152         ListBuffer<String> subPackages = new ListBuffer<String>();
    153         ListBuffer<String> excludedPackages = new ListBuffer<String>();
    154 
    155         Context context = new Context();
    156         Options compOpts = Options.instance(context);
    157         compOpts.put("-sourcepath", sourcepath);
    158 
    159         Constructor<Messager> c;
    160         try {
    161 //            c = Messager.class.getDeclaredConstructor(Context.class, String.class);
    162 //            c.setAccessible(true);
    163 //            c.newInstance(context, "SigTest");
    164             c = Messager.class.getDeclaredConstructor(Context.class, String.class, PrintWriter.class, PrintWriter.class, PrintWriter.class);
    165             c.setAccessible(true);
    166             PrintWriter err = new PrintWriter(new StringWriter());
    167             PrintWriter warn = new PrintWriter(new StringWriter());
    168             PrintWriter notice = new PrintWriter(new StringWriter());
    169             c.newInstance(context, "SigTest", err, warn, notice);
    170         } catch (Exception e) {
    171             throw new RuntimeException(e);
    172         }
    173 
    174         JavadocTool comp = JavadocTool.make0(context);
    175         RootDocImpl root = comp.getRootDocImpl(docLocale, encoding, showAccess,
    176                 javaNames.toList(), options.toList(), breakiterator,
    177                 subPackages.toList(), excludedPackages.toList(), docClasses,
    178                 legacy, quiet);
    179         return root;
    180     }
    181 
    182 }
    183