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.plugin.report; 017 018import java.io.BufferedWriter; 019import java.io.File; 020import java.io.FileNotFoundException; 021import java.io.FileOutputStream; 022import java.io.OutputStreamWriter; 023import java.io.UnsupportedEncodingException; 024import org.opengion.hayabusa.common.HybsSystemException; 025import org.opengion.hayabusa.common.HybsSystem; 026import org.opengion.hayabusa.report.AbstractCSVPrintPointService; 027import org.opengion.fukurou.util.StringUtil; 028 029/** 030 * ユニリタ「Report & Form Warehouse」に対応したCSV形式でデータを作成します。 031 * 032 * CSVはシステムリソースRFW_CSV_OUTPUTDIRで指定した場所に[LISTID]_[GRPID]_[YKNO].csvで出力されます。 033 * 特殊な動作として、デーモングループに"BIG"の文字が入っている場合はCSV出力先ディレクトリ末尾に"_BIG"を付加します。 034 * 2つのフォルダは予め作成しておきます。 035 * 036 * PDF等の最終的な出力先、つまりCSVのコントロールヘッダのRDSetOutputFileNameはGE50で指定します。 037 * (Defaultのプラグインと出力が異なるので注意が必要です) 038 * 039 * データに関しては、全てダブルクウォートで囲って出力されます。 040 * ダブルクウォートそのものは二重化でエスケープします。 041 * ヘッダ、フッタが存在する場合、ボディ、ヘッダ、フッタの順番に連結して出力し、カラム名はヘッダはH_、フッタはF_を先頭に追加します。 042 * 043 * 044 * @og.group 帳票システム 045 * 046 * @version 5.9.0.0 047 * @author Masakazu Takahashi 048 * @since JDK6.0, 049 */ 050public class CSVPrintPointService_RFW extends AbstractCSVPrintPointService { 051 052 private static final String CR = System.getProperty("line.separator"); 053 private final StringBuilder strCSV = new StringBuilder(); // CSVはこれに吐く 054 055 private static final String csvEncode = HybsSystem.sys("REPORT_CSV_TEXT_ENCODE"); 056 057 private static final String RFW_CSV_OUTPUTDIR = HybsSystem.sys("RFW_CSV_OUTPUTDIR"); 058 059 /** 060 * 発行処理 061 * ファイル出力 062 * 063 * @og.rev 5.9.2.2 ファイル名に標準OrderBy同様にGRPIDを付ける。デーモングループに「BIG」が入っている場合は出力先変更 064 * 065 * @return 結果 [true:正常/false:異常] 066 */ 067 @Override 068 public boolean execute(){ 069 System.out.print( "CSV create ... " ); 070 BufferedWriter bw = null; 071 boolean flg = false; 072 073 try { 074 makeheader(); 075 makebody(); 076 077// bw = getWriter( RFW_CSV_OUTPUTDIR + File.separator + listid + "_" + ykno + ".csv" ,false,csvEncode); 078 // 汎用化も考えたが、予期せぬ出力があると困るのでBIG決め打ち。フォルダ存在しない場合はエラー 079 if( dmngrp != null && dmngrp.indexOf( "BIG" ) >= 0 ){ // 5.9.2.2 080 bw = getWriter( RFW_CSV_OUTPUTDIR + "_BIG" + File.separator + listid + "_" + grpid + "_" + ykno + ".csv" ,false,csvEncode); 081 } 082 else{ 083 bw = getWriter( RFW_CSV_OUTPUTDIR + File.separator + listid + "_" + grpid + "_" + ykno + ".csv" ,false,csvEncode); 084 } 085 bw.write( strCSV.toString() ); 086 bw.flush(); 087 bw.close(); 088 089 flg = true; 090 091// if( prgfile != null && prgfile.length() > 0){ 092// makeShellCommand(); 093// flg = programRun(); 094// } 095 096 } 097 catch ( Throwable ex ) { 098 errMsg.append( "CSV Print Request Execution Error. " ).append( CR ); 099 errMsg.append( "==============================" ).append( CR ); 100 errMsg.append( "SYSTEM_ID=[" ).append( systemId ).append( "] , " ); 101 errMsg.append( "YKNO=[" ).append( ykno ).append( "] , " ); 102 errMsg.append( ex.toString() ); 103 errMsg.append( CR ); 104// throw new RuntimeException( errMsg.toString() ); 105 throw new RuntimeException( errMsg.toString(), ex ); 106 } 107 return flg; 108 } 109 110 /** 111 * ヘッダの出力 112 * 113 * @og.rev 5.9.1.2 (2015/10/23) RDSetOutputPrinterの値をIDに変更 114 * @og.rev 5.9.3.0 (2015/12/04) option追加 115 */ 116 private void makeheader(){ 117 //ヘッダデータを出力する場合はここで指定する。 118 strCSV.append( "<rdstart>" ).append( CR ); 119 120 strCSV.append( "RDSetForm=\"" ).append(modelname).append("\"").append( CR ); 121 122 // PDFの場合 123 if( FGRUN_PDF.equals( fgrun ) ){ 124 strCSV.append( "RDSetOutputMode=PDF" ).append( CR ); 125 strCSV.append( "RDSetOutputFileName=\"" ).append( outdir ).append("\"").append( CR ); 126 } 127 // Excel 128 else if( FGRUN_EXCEL.equals(fgrun) ){ 129 strCSV.append( "RDSetOutputMode=XLS" ).append( CR ); 130 strCSV.append( "RDSetOutputFileName=\"" ).append( outdir ).append("\"").append( CR ); 131 } 132 // 印刷 133 else{ 134 strCSV.append( "RDSetOutputMode=SPOOL" ).append( CR ); 135 //strCSV.append( "RDSetOutputPrinter=\"" ).append(prtName).append( "\"" ).append( CR ); 136 // プリンタ名ではなく、プリンタIDを出力するように変更 137 strCSV.append( "RDSetOutputPrinter=\"" ).append(prtid).append( "\"" ).append( CR ); 138 } 139 140 if( option != null && option.length() > 0 ){ 141 strCSV.append( option ).append( CR ); // 5.9.3.0 (2015/12/04) 142 } 143 144 strCSV.append( "<rdend>" ).append( CR ); 145 146 //1行目にカラム名を出力します。クウォートで囲わない。 147 // メインテーブルはNULLではない 148 for( int clmNo=0; clmNo<table.getColumnCount(); clmNo++ ) { 149 // 先頭以外はカンマを付ける 150 if( clmNo > 0 ){ strCSV.append( "," ); } 151 strCSV.append( table.getColumnName( clmNo )); 152 } 153 if( tableH != null){ 154 for( int clmNo=0; clmNo<tableH.getColumnCount(); clmNo++ ) { 155 strCSV.append( "," ); 156 strCSV.append("H_").append( tableH.getColumnName( clmNo )); 157 } 158 } 159 if( tableF != null){ 160 for( int clmNo=0; clmNo<tableF.getColumnCount(); clmNo++ ) { 161 strCSV.append( "," ); 162 strCSV.append("F_").append( tableF.getColumnName( clmNo )); 163 } 164 } 165 strCSV.append( CR ); 166 } 167 168 169 170 /** 171 * 本体の出力を行います 172 * HTMLエスケープされている場合は戻します 173 */ 174 private void makebody(){ 175 176 for( int rowNo=0; rowNo<table.getRowCount(); rowNo++ ) { 177 // カラム単位の処理 178 for( int clmNo=0; clmNo<table.getColumnCount(); clmNo++ ) { 179 // 先頭以外はカンマを付ける 180 if( clmNo > 0 ){ strCSV.append( "," ); } 181 // 全てダブルクウォートで囲う 182 strCSV.append("\"").append( StringUtil.replace( StringUtil.getReplaceEscape( table.getValue( rowNo, clmNo )) ,"\"","\"\"" ) ).append("\""); 183 } 184 185 //ヘッダ、フッタは毎行に必ず付加します。 186 //例え複数行あったとしても先頭行のみ有効です 187 //ヘッダ 188 if( tableH != null){ 189 int rowNoH=0; 190 for( int clmNo=0; clmNo<tableH.getColumnCount(); clmNo++ ) { 191 // 必ずカンマを付ける 192 strCSV.append( "," ); 193 // 全てダブルクウォートで囲う 194 strCSV.append("\"").append( StringUtil.replace( StringUtil.getReplaceEscape( tableH.getValue( rowNoH, clmNo )) ,"\"","\"\"" ) ).append("\""); 195 } 196 } 197 198 //フッタ 199 if( tableF != null ){ 200 int rowNoF=0; 201 for( int clmNo=0; clmNo<tableF.getColumnCount(); clmNo++ ) { 202 // 必ずカンマを付ける 203 strCSV.append( "," ); 204 // 全てダブルクウォートで囲う 205 strCSV.append("\"").append( StringUtil.replace( StringUtil.getReplaceEscape( tableF.getValue( rowNoF, clmNo )) ,"\"","\"\"" ) ).append("\""); 206 } 207 } 208 209 strCSV.append( CR ); 210 } 211 } 212 213 214 /** 215 * ファイル書き込み用のライターを返します。 216 * 217 * @param fileName ファイル名 218 * @param append アベンドするか 219 * @param encode エンコード 220 * 221 * @return ライター 222 */ 223 private BufferedWriter getWriter( final String fileName, final boolean append, final String encode) { 224 File file = new File ( fileName ); 225 BufferedWriter bw; 226 227 try { 228 bw = new BufferedWriter( new OutputStreamWriter( new FileOutputStream( file, append ), encode ) ); 229 } 230 catch ( UnsupportedEncodingException ex ) { 231 errMsg.append( "[ERROR] Input File is written by Unsupported Encoding" ); 232 throw new HybsSystemException( ex ); 233 } 234 catch ( FileNotFoundException ex ) { 235 errMsg.append( "[ERROR] File not Found" ); 236 throw new HybsSystemException( ex ); 237 } 238 return bw; 239 } 240 241}