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 */
016package org.opengion.fukurou.taglet;
017
018import com.sun.javadoc.Tag;
019
020import org.opengion.fukurou.util.FileUtil;
021import org.opengion.fukurou.util.StringUtil;
022import static org.opengion.fukurou.system.HybsConst.CR;                         // 6.1.0.0 (2014/12/26) refactoring
023
024import java.io.File;
025import java.io.PrintWriter;
026import java.io.IOException;
027
028/**
029 * Tag 情報を出力する PrintWriter 相当クラスです。
030 *
031 * @version  4.0
032 * @author   Kazuhiko Hasegawa
033 * @since    JDK5.0,
034 */
035@SuppressWarnings(value={"deprecation","removal"})                      // Ver7.0.0.0 , 7.2.2.0 (2020/03/27)
036public final class DocletTagWriter {
037        private final PrintWriter outFile ;
038        private final boolean rtn2br ;                  // 改行コードを <br>に置換するかどうか
039
040        private static final String ENCODE = "UTF-8" ;
041
042        /** HTML上のブレーク  &lt;br&gt; + CR  */
043        public static final String BR = "&lt;br&gt;" + CR ;
044
045        /**
046         * Doclet のエントリポイントメソッドです。
047         *
048         * 初期エンコードで出力します。
049         *
050         * @param file  出力ファイル名
051         * @throws IOException なんらかのエラーが発生した場合。
052         */
053        public DocletTagWriter( final String file ) throws IOException {
054                this( file,ENCODE,false );
055        }
056
057        /**
058         * Doclet のエントリポイントメソッドです。
059         *
060         * @param file          出力ファイル名
061         * @param encode        エンコード
062         * @throws IOException なんらかのエラーが発生した場合。
063         */
064        public DocletTagWriter( final String file,final String encode ) throws IOException {
065                this( file,encode,false );
066        }
067
068        /**
069         * Doclet のエントリポイントメソッドです。
070         *
071         * @param file          出力ファイル名
072         * @param encode        エンコード
073         * @param r2b           改行コードをBRタグに置換するかどうか [true:置換する/false:置換しない]
074         * @throws IOException なんらかのエラーが発生した場合。
075         */
076        public DocletTagWriter( final String file,final String encode,final boolean r2b ) throws IOException {
077                outFile = FileUtil.getPrintWriter( new File( file ),encode );
078                rtn2br = r2b;
079        }
080
081        /**
082         * 出力ファイルをクロースします。
083         *
084         */
085        public void close() {
086                outFile.close();
087        }
088
089        /**
090         * 可変長の文字列引数を取り、文字列を出力します。
091         * 文字列の最後に改行が入ります。
092         *
093         * @param str String...
094         */
095        public void printTag( final String... str ) {
096                for( int i=0; i<str.length; i++ ) {
097                        if( rtn2br ) { outFile.print( str[i].replaceAll( CR,BR ) ); }
098                        else             { outFile.print( str[i] ); }
099                }
100                outFile.println();
101        }
102
103        /**
104         * タグ配列を受け取り、タグ出力します。
105         *
106         * 従来は、Tagが、1つの場合と配列の場合で改行出力を分けていましたが、改行しないことにします。
107         *
108         * @og.rev 5.5.4.1 (2012/07/06) {&#064;og.value package.class#field} の処理 対応
109         * @og.rev 5.5.4.1 (2012/07/06) DocletUtil.htmlFilter → StringUtil.htmlFilter に変更
110         * @og.rev 5.5.4.2 (2012/07/13) タグ出力の最後に改行を入れておきます。
111         * @og.rev 5.5.5.6 (2012/08/31) @og.tag などに @og.value が含まれている場合の処理を追加
112         * @og.rev 5.5.5.6 (2012/08/31) @og.tag などに @og.value が含まれている場合の処理を追加
113         * @og.rev 5.6.3.3 (2013/04/19) @og.tag などに @og.doc03Link が含まれている場合の処理を追加
114         * @og.rev 5.7.1.1 (2013/12/13) 一旦文字列に入れて、rtn2br の判定処理を行います。
115         * @og.rev 6.1.0.0 (2014/12/26) デバッグ対応の try … catch 追加。処理は最後まで行う。
116         *
117         * @param tag タグ配列(可変長引数)
118         */
119        public void printTag( final Tag... tag ) {
120                for( int i=0; i<tag.length; i++ ) {
121                        final Tag nowTag = tag[i];                                                                      // 6.1.0.0 (2014/12/26) デバッグ対応
122                        try {
123                                final String tagName = nowTag.name();
124                                String data = "";
125                                // {@og.value package.class#field} の処理を行います。
126                                if( "@og.value".equalsIgnoreCase( tagName ) ) {
127                                        data = DocletUtil.valueTag( nowTag );
128                                }
129                                // 5.6.3.3 (2013/04/19) {@og.doc03Link ・・・} の処理を行います。
130                                else if( "@og.doc03Link".equalsIgnoreCase( tagName ) ) {
131                                        data = DocletUtil.doc03LinkTag( nowTag );
132                                }
133                                // 5.5.5.6 (2012/08/31) @og.tag などに @og.value が含まれている場合の処理を追加
134                                // 6.1.0.0 (2014/12/26) refactoring : Avoid if(x != y) ..; else ..;
135                                else if( "Text".equalsIgnoreCase( tagName ) ) {
136                                        data = StringUtil.htmlFilter( nowTag.text() ).trim();           // 5.5.4.1 (2012/07/06) DocletUtil → StringUtil に変更
137                                }
138                                else {
139                                        printTag( nowTag.inlineTags() );
140                                }
141        //                      else if( ! "Text".equalsIgnoreCase( tagName ) ) {
142        //                              printTag( nowTag.inlineTags() );
143        //                      }
144        //                      else {
145        //                              data = StringUtil.htmlFilter( nowTag.text() ).trim();           // 5.5.4.1 (2012/07/06) DocletUtil → StringUtil に変更
146        //                      }
147
148                                if( rtn2br ) {
149                                        outFile.print( data.replaceAll( CR,BR ) );
150                                }
151                                else {
152                                        outFile.print( data );
153                                }
154                        }
155                        catch( final Throwable th ) {
156                                final String errMsg = "処理エラー:位置="
157                                                                        + nowTag.position()                             + CR
158                                                                        + th.getMessage()                               + CR
159                                                                        + tag[i] ;
160                                System.err.println( errMsg );
161                        }
162                }
163        }
164
165        /**
166         * 文字列引数を 2つと、タグ配列を受け取り、タグ出力します。
167         *
168         * @param str1  第一文字列
169         * @param tag   タグ配列
170         * @param str3  第三文字列
171         */
172        public void printTag( final String str1,final Tag[] tag, final String str3 ) {
173                outFile.print( str1 );
174                printTag( tag );
175                outFile.println( str3 );
176        }
177
178        /**
179         * タグ配列を受け取り、タグ出力します。
180         * 複数のタグを出力する場合に、CSV形式で連結します。
181         *
182         * @og.rev 5.5.4.1 (2012/07/06) DocletUtil.htmlFilter → StringUtil.htmlFilter に変更
183         *
184         * @param tag タグ配列(可変長引数)
185         */
186        public void printCSVTag( final Tag... tag ) {
187                for( int i=0; i<tag.length; i++ ) {
188                        final String data = StringUtil.htmlFilter( tag[i].text() );             // 5.5.4.1 (2012/07/06) DocletUtil → StringUtil に変更
189                        if( i > 0 ) { outFile.print( "," ); }
190                        outFile.print( data );
191                }
192        }
193
194        /**
195         * タグ配列を受け取り、タグ出力します。
196         * ここでは、タグ毎にタグの名称と内容を出力し、改行を行います。
197         * 特殊処理:ここでは、og.rev タグは取り込みません。
198         *
199         * @og.rev 5.5.4.1 (2012/07/06) DocletUtil.htmlFilter → StringUtil.htmlFilter に変更
200         *
201         * @param tag タグ配列(可変長引数)
202         */
203        public void printTagsInfo( final Tag... tag ) {
204                for( int i=0; i<tag.length; i++ ) {
205                        final String tagName = tag[i].name();
206                        if( "@og.rev".equalsIgnoreCase( tagName ) ) {
207                                continue;
208                        }
209                        outFile.print( tagName );
210                        outFile.print( " " );
211                        outFile.print( StringUtil.htmlFilter( tag[i].text() ) );                // 5.5.4.1 (2012/07/06) DocletUtil → StringUtil に変更
212                        if( rtn2br ) { outFile.print( BR ); }
213                        else             { outFile.println(); }
214                }
215        }
216
217        /**
218         * 文字列引数を 2つと、タグ配列を受け取り、先頭一文字のタグ出力します。
219         *
220         * @param str1  第一文字列
221         * @param tag   タグ配列
222         * @param str3  第三文字列
223         */
224        public void printChar( final String str1,final Tag[] tag, final String str3 ) {
225                outFile.print( str1 );
226                if( tag.length > 0 ) {
227                        final String str = tag[0].text();
228                        if( str != null && str.length() > 0 ) {
229                                outFile.print( str.charAt(0) );
230                        }
231                }
232                outFile.println( str3 );
233        }
234}