001    /*
002     * Copyright (c) 2009 The openGion Project.
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,
013     * either express or implied. See the License for the specific language
014     * governing permissions and limitations under the License.
015     */
016    package org.opengion.fukurou.taglet;
017    
018    import org.opengion.fukurou.util.LogWriter;
019    
020    import com.sun.javadoc.RootDoc;
021    import com.sun.javadoc.ClassDoc;
022    import com.sun.javadoc.Type;
023    import com.sun.javadoc.Tag;
024    import java.util.Map;
025    import java.util.HashMap;
026    import java.io.IOException;
027    
028    /**
029     * ソースコメントから?属???を取り??Doclet クラスです?
030     *
031     * @version  4.0
032     * @author   Kazuhiko Hasegawa
033     * @since    JDK5.0,
034     */
035    public final class DocletPlugin {
036            private static Map<String,AttKeySet> map = new HashMap<String,AttKeySet>();
037    
038            private static final String OG_FOR_SMPL  = "og.formSample";
039            private static final String ENCODE = "UTF-8";
040    
041            /**
042             * すべて?staticメソ?なので、コンストラクタを呼び出さなくしておきます?
043             *
044             */
045            private DocletPlugin() {}
046    
047            /**
048             * Doclet のエントリポイントメソ?です?
049             *
050             * @param root ドキュメントルートオブジェク?
051             *
052             * @return 正常実行時 true
053             */
054            public static boolean start( final RootDoc root ) {
055                    String version = DocletUtil.getOption( "-version" , root.options() );
056                    String file    = DocletUtil.getOption( "-outfile" , root.options() );
057    
058                    mapInit();
059    
060                    DocletTagWriter writer = null;
061                    try {
062                            writer = new DocletTagWriter( file,ENCODE );
063    
064                            writer.printTag( "<?xml version=\"1.0\" encoding=\"", ENCODE, "\" ?>" );
065                            writer.printTag( "<javadoc>" );
066                            writer.printTag( "  <version>",version,"</version>" );
067                            writer.printTag( "  <description></description>" );
068                            writeContents( root.classes(),writer );
069                            writer.printTag( "</javadoc>" );
070                    }
071                    catch( IOException ex ) {
072                            LogWriter.log( ex );
073                    }
074                    finally {
075                            if( writer != null ) { writer.close(); }
076                    }
077                    return true;
078            }
079    
080            /**
081             * ClassDoc 配?よりコン??作?します?
082             * インターフェースも???対象とします?
083             *
084             * @og.rev 5.5.4.1 (2012/07/06) コメント???でなく?Tag配?として処?せる?
085             *
086             * @param classes       ClassDoc配?
087             * @param writer        DocletTagWriterオブジェク?
088             */
089            private static void writeContents( final ClassDoc[] classes,final DocletTagWriter writer ) {
090                    for(int i=0; i< classes.length; i++) {
091                            ClassDoc classDoc      = classes[i] ;
092                            if( ! classDoc.isPublic() ) { continue; }
093    
094                            AttKeySet attSet = getAttGroupName( classDoc ) ;
095    
096                            if( attSet == null ) { continue; }              // map に登録されて???
097    
098                            String attKey   = attSet.getAttKey( classDoc.name() );
099    
100                            if( attKey == null ) { continue; }              // 対象クラス名が、??しな??
101    
102                            String attClass = classDoc.qualifiedName() ;    // Class Full Name
103                            Tag[]  desc     = classDoc.firstSentenceTags();
104    //                      String cmnt     = DocletUtil.htmlFilter( classDoc.commentText() );                      // 5.5.4.1 (2012/07/06)
105                            Tag[]  cmnt     = classDoc.inlineTags();                                                                        // 5.5.4.1 (2012/07/06)
106                            Tag[] smplTags  = classDoc.tags(OG_FOR_SMPL);
107    
108                            writer.printTag( "<classDoc>" );
109                            writer.printTag( "  <attClass>"           ,attClass                               ,"</attClass>"            );
110                            writer.printTag( "  <seq>"                        ,attSet.getSeq()                ,"</seq>"                 );
111                            writer.printTag( "  <attKey>"             ,attKey                                 ,"</attKey>"              );
112                            writer.printTag( "  <valueName>"  ,attSet.getValueName()  ,"</valueName>"           );
113                            writer.printTag( "  <description>"        ,desc                                   ,"</description>" );
114                            writer.printTag( "  <contents>"           ,cmnt                                   ,"</contents>"            );
115                            writer.printTag( "  <formSample>" ,smplTags                               ,"</formSample>"  );
116    
117                            writer.printTag( "</classDoc>" );
118                    }
119            }
120    
121            /**
122             * 処?る属?クラスのMapを?期化します?
123             * ?できるのは、親クラスか?直接のインターフェースです?
124             *
125             * @og.rev 4.3.5.0 (2008/02/01) daemonパッケージ追?
126             * @og.rev 5.5.3.5 (2012/06/21) ChartWriter 削除、TransferExec,TransferRead 追?
127             * @og.rev 5.6.3.3 (2013/04/19) DBTableReport,CalendarData,DBConstValue,JspParserFilter,ConnectIF 追?
128             *
129             */
130            private static void mapInit() {
131                    map.put( "org.opengion.hayabusa.db.Query"                               , new AttKeySet( "Query"                        ,0, "queryType"         ));
132                    map.put( "org.opengion.hayabusa.db.CellRenderer"                , new AttKeySet( "Renderer"                     ,1, "renderer"          ));
133                    map.put( "org.opengion.hayabusa.db.CellEditor"                  , new AttKeySet( "Editor"                       ,2, "editor"            ));
134                    map.put( "org.opengion.hayabusa.db.DBType"                              , new AttKeySet( "DBType"                       ,3, "dbType"            ));
135                    map.put( "org.opengion.hayabusa.db.TableFilter"                 , new AttKeySet( "TableFilter"          ,4, "tableFilter"       ));
136                    map.put( "org.opengion.hayabusa.db.Selection"                   , new AttKeySet( "Selection"            ,5, "selection"         ));
137                    map.put( "org.opengion.hayabusa.html.ViewForm"                  , new AttKeySet( "ViewForm"                     ,6, "viewFormType"      ));
138                    map.put( "org.opengion.hayabusa.io.TableWriter"                 , new AttKeySet( "TableWriter"          ,7, "writerClass"       ));
139                    map.put( "org.opengion.hayabusa.io.TableReader"                 , new AttKeySet( "TableReader"          ,8, "readerClass"       ));
140    //              map.put( "org.opengion.hayabusa.io.ChartWriter"                 , new AttKeySet( "ChartWriter"          ,9, "chartClass"        ));             // 5.5.3.5 (2012/06/21)
141                    map.put( "org.opengion.hayabusa.resource.CalendarQuery" , new AttKeySet( "CalendarQuery"        ,10, "calDB"            ));
142                    map.put( "org.opengion.fukurou.process.HybsProcess"             , new AttKeySet( "Process"                      ,11, "process"          ));
143                    map.put( "org.opengion.fukurou.transfer.TransferExec"   , new AttKeySet( "TransferExec"         ,12, "kbExec"           ));             // 5.5.3.5 (2012/06/21)
144                    map.put( "org.opengion.fukurou.transfer.TransferRead"   , new AttKeySet( "TransferRead"         ,13, "kbRead"           ));             // 5.5.3.5 (2012/06/21)
145                    map.put( "org.opengion.fukurou.util.HybsTimerTask"              , new AttKeySet( "Daemon"                       ,14, "daemon"           ));             // 4.3.4.4 (2009/01/01)
146    
147                    map.put( "org.opengion.hayabusa.report.DBTableReport"   , new AttKeySet( "DBTableReport"        ,15, "tableReport"      ));             // 5.6.3.3 (2013/04/19)
148                    map.put( "org.opengion.hayabusa.resource.CalendarData"  , new AttKeySet( "CalendarData"         ,16, "calData"          ));             // 5.6.3.3 (2013/04/19)
149                    map.put( "org.opengion.hayabusa.db.DBConstValue"                , new AttKeySet( "DBConstValue"         ,17, "cnstVal"          ));             // 5.6.3.3 (2013/04/19)
150                    map.put( "org.opengion.fukurou.xml.JspParserFilter"             , new AttKeySet( "JspCreate"            ,18, "jspParser"        ));             // 5.6.3.3 (2013/04/19)
151                    map.put( "org.opengion.fukurou.util.ConnectIF   "               , new AttKeySet( "ConnectIF"            ,19, "connIF"           ));             // 5.6.3.3 (2013/04/19)
152            }
153    
154            /**
155             * ?? ClassDoc が?処?る属?クラスのMapに含まれて?場合?
156             * そ? AttKeySet クラスのオブジェクトを返します?
157             * 存在しな??合?null を返します?
158             *
159             * @param       classDoc ClassDocオブジェク?
160             *
161             * @return      ClassDocに対応す?AttKeySetオブジェク?
162             */
163            private static AttKeySet getAttGroupName( final ClassDoc classDoc ) {
164                    if( classDoc == null ) { return null; }
165    
166                    String classFullName = classDoc.qualifiedName() ;
167                    AttKeySet attKey = map.get( classFullName );
168                    if( attKey == null ) {
169                            Type type = classDoc.superclassType();  // 親クラスタイ?
170                            if( type != null ) {
171                                    attKey = getAttGroupName( type.asClassDoc() );  // 親クラス
172                            }
173    
174                            if( attKey == null ) {
175                                    Type[] itface = classDoc.interfaceTypes();              // 直近インターフェース
176                                    for( int i=0; i<itface.length; i++ ) {
177                                            attKey = getAttGroupName( itface[i].asClassDoc() );
178                                            if( attKey != null ) { break; }
179                                    }
180                            }
181                    }
182                    return attKey;
183            }
184    
185            /**
186             * カスタ?プションを使用するドックレ?の??メソ? optionLength(String) です?
187             *
188             * ドックレ?に認識させる?スタ?プションに?optionLength がその
189             * オプションを構?する要?(ト?クン) の数を返さなければなりません?
190             * こ?カスタ?プションでは?-tag オプションそ?も?と
191             * そ?値の 2 つの要?構?される?で、作?するドックレ?の
192             * optionLengthメソ?は?-tag オプションに対して 2 を返さなくては
193             * なりません。また?認識できな?プションに対しては? を返します?
194             *
195             * @param option オプション??
196             *
197             * @return 要?(ト?クン) の数
198             */
199            public static int optionLength( final String option ) {
200                    if(option.equalsIgnoreCase("-version")) {
201                            return 2;
202                    }
203                    else if(option.equalsIgnoreCase("-outfile")) {
204                            return 2;
205                    }
206                    return 0;
207            }
208    }