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.plugin.io;
017
018 import java.io.BufferedReader;
019 import java.io.FileInputStream;
020 import java.io.IOException;
021 import java.io.InputStream;
022 // import java.text.DateFormat;
023 import java.text.DecimalFormat;
024 import java.text.NumberFormat;
025 // import java.text.SimpleDateFormat;
026 // import java.util.Locale;
027 import java.util.List;
028 import java.util.ArrayList;
029
030 import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
031 import org.apache.poi.ss.usermodel.Cell;
032 import org.apache.poi.ss.usermodel.DateUtil;
033 import org.apache.poi.ss.usermodel.RichTextString;
034 import org.apache.poi.ss.usermodel.Row;
035 import org.apache.poi.ss.usermodel.Sheet;
036 import org.apache.poi.ss.usermodel.Workbook;
037 import org.apache.poi.ss.usermodel.WorkbookFactory;
038 import org.apache.poi.ss.usermodel.CreationHelper;
039 import org.apache.poi.ss.usermodel.FormulaEvaluator;
040 import org.opengion.fukurou.util.Closer;
041 import org.opengion.fukurou.util.StringUtil;
042 import org.opengion.fukurou.util.HybsDateUtil;
043 import org.opengion.hayabusa.common.HybsSystem;
044 import org.opengion.hayabusa.common.HybsSystemException;
045 import org.opengion.hayabusa.db.DBTableModelUtil;
046
047 /**
048 * POI による、EXCELバイナリファイルを読み取る実è£?‚¯ラスですã?
049 *
050 * ファイル名ã?シート名を指定して、データを読み取ることが可能ですã?
051 * 第ä¸?‚«ラãƒ?�Œ # で始まる行ã?、コメント行なので、読み飛ã?しますã?
052 * カラãƒ?��のæŒ?®š行で、カラãƒ?��ã�?null の場合ã?、その列ã?読み飛ã?しますã?
053 *
054 * 入力形式ã?、openXML形式にも対応してã�?�¾すã?
055 * ファイルのå†?®¹に応じてã€?xlsと.xlsxのどちらで読み取るかã?、å?部çš?�«
056 * 自動判定されますã?
057 *
058 * @og.rev 3.5.4.8 (2004/02/23) 新規作æ?
059 * @og.rev 4.3.6.7 (2009/05/22) ooxml形式対å¿?
060 * @og.group ファイル入åŠ?
061 *
062 * @version 4.0
063 * @author Kazuhiko Hasegawa
064 * @since JDK5.0,
065 */
066 public class TableReader_Excel extends TableReader_Default {
067 //* こã?プログラãƒ??VERSIONæ–?—å?を設定しますã? {@value} */
068 private static final String VERSION = "5.5.8.2 (2012/11/09)" ;
069
070 private String filename = null; // 3.5.4.3 (2004/01/05)
071 private String sheetName = null; // 3.5.4.2 (2003/12/15)
072 private String sheetNos = null; // 5.5.7.2 (2012/10/09)
073
074 private String constKeys = null; // 5.5.8.2 (2012/11/09) 固定å?となるカラãƒ?��(CSV形å¼?
075 private String constAdrs = null; // 5.5.8.2 (2012/11/09) 固定å?となるアドレス(è¡?åˆ?è¡?åˆ?・・・)
076 private String nullBreakClm = null; // 5.5.8.2 (2012/11/09) 取込み条件/Sheet BREAK条件
077
078 /**
079 * DBTableModel から å�?½¢式ã?ãƒ??タを作æ?して,BufferedReader より読み取りますã?
080 * コメンãƒ?空行を除きã?æœ??の行ã?、å¿?�šé ?›®名がå¿?¦�ですã?
081 * それ以降ã?、コメンãƒ?空行を除きã?ãƒ??タとして読み込んでã�?��ますã?
082 * こã?メソãƒ?ƒ‰は、EXCEL 読み込み時に使用しますã?
083 *
084 * @og.rev 4.0.0.0 (2006/09/31) 新規追åŠ?
085 * @og.rev 5.1.6.0 (2010/05/01) columns 処ç�?追åŠ?
086 * @og.rev 5.1.6.0 (2010/05/01) skipRowCountの追åŠ?
087 * @og.rev 5.1.8.0 (2010/07/01) Exception をきちっと記述(InvalidFormatException)
088 * @og.rev 5.2.1.0 (2010/10/01) setTableColumnValues メソãƒ?ƒ‰を経由して、テーブルにãƒ??タをセãƒ?ƒˆするã€?
089 * @og.rev 5.5.1.2 (2012/04/06) HeaderData ã‚?try の上にã�?�—、エラーメãƒ?‚»ージを取得できるようにするã€?
090 * @og.rev 5.5.7.2 (2012/10/09) sheetNos 追åŠ?�«よるè¤?•°シートã?マã?ジ読み取りサポã?ãƒ?
091 * @og.rev 5.5.8.2 (2012/11/09) HeaderData に ãƒ?ƒ�ãƒ?‚°フラグを渡しますã?
092 *
093 * @see #isExcel()
094 */
095 @Override
096 public void readDBTable() {
097 InputStream in = null;
098 HeaderData data = null; // 5.5.1.2 (2012/04/06)
099 try {
100 boolean isDebug = isDebug(); // 5.5.7.2 (2012/10/09) ãƒ?ƒ�ãƒ?‚°æƒ??
101
102 if( isDebug ) { System.out.println( " Filename=" + filename ) ; }
103
104 in = new FileInputStream(filename);
105
106 // POIFSFileSystem fs = new POIFSFileSystem(in);
107 // HSSFWorkbook wb = new HSSFWorkbook(fs);
108 // HSSFSheet sheet ;
109 Workbook wb = WorkbookFactory.create(in);
110 // Sheet sheet ;
111 Sheet[] sheets ; // 5.5.7.2 (2012/10/09) 配å?に変更
112
113 if( isDebug ) { wb = ExcelUtil.activeWorkbook( wb ); } // ãƒ?ƒ�ãƒ?‚°モード時には、エクセルのアクãƒ?‚£ブセル領域のみにシュリンクを行う
114
115 // 5.5.7.2 (2012/10/09) è¤?•°シートã?マã?ジ読み取りã€?sheetNos のæŒ?®šが優先されるã€?
116 if( sheetNos != null && sheetNos.length() > 0 ) {
117 String[] sheetList = StringUtil.csv2ArrayExt( sheetNos , wb.getNumberOfSheets()-1 ); // æœ?¤§シート番号は、シート数-1
118 sheets = new Sheet[sheetList.length];
119 for( int i=0; i<sheetList.length; i++ ) {
120 sheets[i] = wb.getSheetAt( Integer.parseInt( sheetList[i] ) );
121 }
122 }
123 else if( sheetName != null && sheetName.length() > 0 ) {
124 Sheet sheet = wb.getSheet( sheetName );
125 if( sheet == null ) {
126 String errMsg = "対応するシートが存在しませんã€?Sheet=[" + sheetName + "]" ;
127 throw new HybsSystemException( errMsg );
128 }
129 sheets = new Sheet[] { sheet };
130 }
131 else {
132 Sheet sheet = wb.getSheetAt(0);
133 sheets = new Sheet[] { sheet };
134 }
135
136 // if( sheetName == null || sheetName.length() == 0 ) {
137 // sheet = wb.getSheetAt(0);
138 // }
139 // else {
140 // sheet = wb.getSheet( sheetName );
141 // if( sheet == null ) {
142 // String errMsg = "対応するシートが存在しませんã€?Sheet=[" + sheetName + "]" ;
143 // throw new HybsSystemException( errMsg );
144 // }
145 // }
146
147 boolean nameNoSet = true;
148 table = DBTableModelUtil.newDBTable();
149
150 int numberOfRows = 0;
151 // HeaderData data = new HeaderData();
152 data = new HeaderData(); // 5.5.1.2 (2012/04/06)
153
154 data.setDebug( isDebug ); // 5.5.8.2 (2012/11/09)
155
156 // 5.1.6.0 (2010/05/01) columns 処ç�?
157 data.setUseNumber( isUseNumber() );
158
159 // 5.5.8.2 (2012/11/09) 固定å?となるカラãƒ?��(CSV形å¼?とアドレス(è¡?åˆ?è¡?åˆ?・・・)を設å®?
160 data.setSheetConstData( constKeys,constAdrs );
161
162 int nullBreakClmAdrs = -1; // 5.5.8.2 (2012/11/09) nullBreakClm の DBTableModel上ã?アドレスã€?1 は、未使用
163 if( data.setColumns( columns ) ) {
164 nameNoSet = false;
165 table.init( data.getColumnSize() );
166 setTableDBColumn( data.getNames() ) ;
167 nullBreakClmAdrs = table.getColumnNo( nullBreakClm, false ); // 5.5.8.2 (2012/11/09) カラãƒ?•ª号取得ã?存在しなければ -1 を返すã€?
168 }
169
170 int skip = getSkipRowCount(); // 5.1.6.0 (2010/05/01)
171 // 5.5.7.2 (2012/10/09) è¤?•°シートã?マã?ジ読み取りã€?
172 for( int i=0; i<sheets.length; i++ ) { // 5.5.7.2 (2012/10/09) シートé?列を処ç�?�—ますã?
173 Sheet sheet = sheets[i] ; // 5.5.7.2 (2012/10/09)
174
175 data.setSheetConstValues( sheet ); // 5.5.8.2 (2012/11/09) シート単位に固定カラãƒ??値をキャãƒ?‚·ュするã€?
176
177 int nFirstRow = sheet.getFirstRowNum();
178 if( nFirstRow < skip ) { nFirstRow = skip; } // 5.1.6.0 (2010/05/01)
179 int nLastRow = sheet.getLastRowNum();
180 if( isDebug ) { // 5.5.7.2 (2012/10/09) ãƒ?ƒ�ãƒ?‚°æƒ??
181 System.out.println( " Debug: 行é?番=" + numberOfRows + " : Sheet= " + sheet.getSheetName() + " , 開å§?" + nFirstRow + " , 終äº?" + nLastRow );
182 }
183 for( int nIndexRow = nFirstRow; nIndexRow <= nLastRow; nIndexRow++) {
184 // HSSFRow oRow = sheet.getRow(nIndexRow);
185 Row oRow = sheet.getRow(nIndexRow);
186 if( data.isSkip( oRow ) ) { continue; }
187 if( nameNoSet ) {
188 nameNoSet = false;
189 table.init( data.getColumnSize() );
190 setTableDBColumn( data.getNames() ) ;
191 nullBreakClmAdrs = table.getColumnNo( nullBreakClm, false ); // 5.5.8.2 (2012/11/09) カラãƒ?•ª号取得ã?存在しなければ -1 を返すã€?
192 }
193
194 if( numberOfRows < getMaxRowCount() ) {
195 String[] tblData = data.row2Array( oRow ); // 5.5.8.2 (2012/11/09) nullBreakClm の判定ã?ため、ä¸?—¦配å?に受けるã?
196 if( nullBreakClmAdrs >= 0 && ( tblData[nullBreakClmAdrs] == null || tblData[nullBreakClmAdrs].isEmpty() ) ) {
197 break; // nullBreakClm ã�?null の場合ã?、そのSheet処ç�?‚’中止するã€?
198 }
199 setTableColumnValues( tblData ); // 5.5.8.2 (2012/11/09)
200 // setTableColumnValues( data.row2Array( oRow ) ); // 5.2.1.0 (2010/10/01)
201 // table.addColumnValues( data.row2Array( oRow ) );
202 numberOfRows ++ ;
203 }
204 else {
205 table.setOverflow( true );
206 }
207 }
208
209 // æœ?¾Œまでã€?NAME が見つから無かったå?å�?
210 if( nameNoSet ) {
211 String errMsg = "æœ?¾Œまでã€?NAME が見つかりませんでしたã€?
212 + HybsSystem.CR
213 + "ファイルが空かã?もしくã?損傷してã�?‚‹可能性がありますã?"
214 + HybsSystem.CR ;
215 throw new HybsSystemException( errMsg );
216 }
217 }
218 }
219 // catch (Exception e) {
220 catch ( IOException ex ) {
221 String errMsg = "ファイル読込みエラー[" + filename + "]" ;
222 if( data != null ) { errMsg = errMsg + data.getLastCellMsg(); } // 5.5.1.2 (2012/04/06)
223 throw new HybsSystemException( errMsg,ex ); // 3.5.5.4 (2004/04/15) 引数の並びé ?¤‰更
224 }
225 // 5.1.8.0 (2010/07/01) Exception をきちっと記述
226 catch (InvalidFormatException ex) {
227 String errMsg = "ファイル形式エラー[" + filename + "]" ;
228 if( data != null ) { errMsg = errMsg + data.getLastCellMsg(); } // 5.5.1.2 (2012/04/06)
229 throw new HybsSystemException( errMsg,ex );
230 }
231 finally {
232 Closer.ioClose( in ); // 4.0.0 (2006/01/31) close 処ç�?™‚の IOException を無è¦?
233 }
234 }
235
236 /**
237 * DBTableModel から å�?½¢式ã?ãƒ??タを作æ?して,BufferedReader より読み取りますã?
238 * コメンãƒ?空行を除きã?æœ??の行ã?、å¿?�šé ?›®名がå¿?¦�ですã?
239 * それ以降ã?、コメンãƒ?空行を除きã?ãƒ??タとして読み込んでã�?��ますã?
240 *
241 * @og.rev 3.5.4.3 (2004/01/05) 引数に、BufferedReader を受け取る要に変更しますã?
242 * @og.rev 4.0.0.0 (2006/09/31) UnsupportedOperationException を発行しますã?
243 *
244 * @param reader å�?½¢式ã?ãƒ??タ(使用してã�?�¾せん)
245 */
246 @Override
247 public void readDBTable( final BufferedReader reader ) {
248 String errMsg = "こã?クラスでは実è£?�•れてã�?�¾せんã€?;
249 throw new UnsupportedOperationException( errMsg );
250 }
251
252 /**
253 * DBTableModelのãƒ??タとしてEXCELファイルを読み込ã‚?�¨きã?シート名を設定しますã?
254 * これにより、è¤?•°の形式ã?異なるデータをé?次読み込ã‚?�“とã‚??シートをæŒ?®šして
255 * 読み取ることが可能になりますã?
256 * sheetNos と sheetName が同時にæŒ?®šされた場合ã?、sheetNos が優先されますã?エラーにはならなã�??でご注意くã�?�•ã�??
257 * のでご注意くã�?�•ã�??
258 *
259 * @og.rev 3.5.4.2 (2003/12/15) 新規追åŠ?
260 *
261 * @param sheetName シート名
262 */
263 @Override
264 public void setSheetName( final String sheetName ) {
265 this.sheetName = sheetName;
266 }
267
268 /**
269 * EXCELファイルを読み込ã‚?�¨きã?シート番号を指定しまã�?初期値:0)ã€?
270 *
271 * EXCEL読み込み時にè¤?•°シートをマã?ジして取り込みますã?
272 * シート番号はã€? から始まる数字で表しますã?
273 * ヘッãƒ??は、最初ã?シートã?カラãƒ?½�置に合わせますã??ˆã?ãƒ?ƒ€ータイトルの自動認識ã?ありません。ï¼?
274 * よって、指定するシートã?、すべて同ä¸?ƒ¬イアウトでなã�?�¨取り込み時にカラãƒ??ずれが発生しますã?
275 *
276 * シート番号のæŒ?®šã?、カンマ区åˆ?‚Šで、è¤?•°æŒ?®šできますã?またã?N-M の様にハイフンで繋げることでã€?
277 * N 番から、M 番のシートç¯?›²をä¸?‹¬æŒ?®š可能ですã?またã?"*" による、å?シート指定が可能ですã?
278 * これらã?çµ?�¿合わせも可能ですã???0,1,3,5-8,10-* ??
279 * ただしã?"*" に関しては例外的に、ä¸?–‡字だけで、すべてのシートを表すか、N-* を最後にæŒ?®šするかの
280 * どちらかですã?途中にはã€?*" は、現れませんã€?
281 * シート番号はã€?‡�è¤?1,1,2,2)ã€??転(3,2,1) でのæŒ?®šが可能ですã?これは、そのæŒ?®šé?で、読み込まれますã?
282 * sheetNos と sheetName が同時にæŒ?®šされた場合ã?、sheetNos が優先されますã?エラーにはならなã�??でご注意くã�?�•ã�??
283 * こã?メソãƒ?ƒ‰は、isExcel() == true の場合ã?み利用されますã?
284 *
285 * 初期値はã€??ˆ第ä¸?‚·ートï¼?ですã?
286 *
287 * ※ こã?クラスでは実è£?�•れてã�?�¾せんã€?
288 *
289 * @og.rev 5.5.7.2 (2012/10/09) 新規追åŠ?
290 *
291 * @param sheetNos EXCELファイルのシート番号??から始まるï¼?
292 * @see #setSheetName( String )
293 */
294 @Override
295 public void setSheetNos( final String sheetNos ) {
296 this.sheetNos = sheetNos;
297 }
298
299 /**
300 * EXCELファイルを読み込ã‚?�¨きã?シート単位ã?固定å?を設定するためã?カラãƒ?��とアドレスを指定しますã?
301 * カラãƒ?��は、カンマ区åˆ?‚ŠでæŒ?®šしますã?
302 * 対応するアドレスをã?EXCEL上ã?è¡?列を?�から始まる整数でカンマ区åˆ?‚ŠでæŒ?®šしますã?
303 * これにより、シートã?ä¸?�‹æ‰?�«書かれてã�?‚‹æƒ??をã?DBTableModel のカラãƒ?�«固定å?として
304 * 設定することができますã?
305 * 例として、DB定義書で、テーブル名をシートã?全レコードに設定したい場合などに使ã�?�¾すã?
306 * こã?メソãƒ?ƒ‰は、isExcel() == true の場合ã?み利用されますã?
307 *
308 * @og.rev 5.5.8.2 (2012/11/09) 新規追åŠ?
309 *
310 * @param constKeys 固定å?となるカラãƒ?��(CSV形å¼?
311 * @param constAdrs 固定å?となるアドレス(è¡?åˆ?è¡?åˆ?・・・)
312 */
313 @Override
314 public void setSheetConstData( final String constKeys,final String constAdrs ) {
315 this.constKeys = constKeys;
316 this.constAdrs = constAdrs;
317 }
318
319 /**
320 * ここにæŒ?®šされたカラãƒ??に NULL が現れた時点で読み取りを中止しますã?
321 *
322 * これは、指定ã?カラãƒ??å¿??とã�?�†事を条件に、そのレコードだけを読み取る処ç�?‚’行いますã?
323 * è¤?•°Sheetの場合ã?、次のSheetを読みますã?
324 * 現時点では、Excel の場合ã?み有効ですã?
325 *
326 * @og.rev 5.5.8.2 (2012/11/09) 新規追åŠ?
327 *
328 * @param clm カラãƒ??
329 */
330 @Override
331 public void setNullBreakClm( final String clm ) {
332 nullBreakClm = clm;
333 }
334
335 /**
336 * こã?クラスがã?EXCEL対応機è?を持ってã�?‚‹かどã�?�‹を返しますã?
337 *
338 * EXCEL対応機è?とは、シート名のセãƒ?ƒˆ、読み込みå…?ƒ•ァイルの
339 * Fileオブジェクト取得などの、特殊機è?ですã?
340 * 本来は、インターフェースをå?けるべきとè€?�ˆますが、taglib クラス等ã?
341 * 関係があり、問ã�?�ˆわせによる条件åˆ?²�で対応しますã?
342 *
343 * @og.rev 3.5.4.3 (2004/01/05) 新規追åŠ?
344 *
345 * @return EXCEL対応機è?を持ってã�?‚‹かどã�?�‹(常にtrue)
346 */
347 @Override
348 public boolean isExcel() {
349 return true;
350 }
351
352 /**
353 * 読み取りå…?ƒ•ァイル名をセãƒ?ƒˆしますã?(DIR + Filename)
354 * これは、EXCEL追åŠ?©Ÿè?として実è£?�•れてã�?�¾すã?
355 *
356 * @og.rev 3.5.4.3 (2004/01/05) 新規作æ?
357 *
358 * @param filename 読み取りå…?ƒ•ァイルå�?
359 */
360 @Override
361 public void setFilename( final String filename ) {
362 this.filename = filename;
363 if( filename == null ) {
364 String errMsg = "ファイル名がæŒ?®šされてã�?�¾せんã€? ;
365 throw new HybsSystemException( errMsg );
366 }
367 }
368 }
369
370 /**
371 * EXCEL ネイãƒ?‚£ブã?ãƒ??タをå?ç�?�™ã‚?ローカルクラスですã?
372 * こã?クラスでは、コメント行ã?スキãƒ??判定ã?ヘッãƒ??部のカラãƒ?��取得ã?
373 * 行情報(Row)から、カラãƒ??配å?の取得などを行いますã?
374 *
375 * @og.rev 3.5.4.8 (2004/02/23) 新規追åŠ?
376 * @og.group ファイル入åŠ?
377 *
378 * @version 4.0
379 * @author 儲
380 * @since JDK5.0,
381 */
382 class HeaderData {
383 private String[] names ;
384 // private short[] index;
385 private int[] index; // 4.3.4.0 (2008/12/01) POI3.2対å¿?
386 private int columnSize = 0;
387 private boolean nameNoSet = true;
388 private boolean useNumber = true;
389 private boolean isDebug = false; // 5.5.8.2 (2012/11/09)
390
391 private String[] orgNames ; // 5.5.1.2 (2012/04/06) オリジナルのカラãƒ?��
392 private Cell lastCell = null; // 5.5.1.2 (2012/04/06) æœ?¾Œに実行してã�?‚‹セルを保持(エラー時に使用するã€?
393
394 // 5.5.8.2 (2012/11/09) 固定å?のカラãƒ?��、DBTableModelのアドレス、Sheetのè¡?列番号
395 private int cnstLen = 0; // 初期値=0 の場合ã?、固定å?を使わなã�?�¨ã�?�†事ã?
396 private String[] cnstKeys ;
397 private int[] cnstIndx ;
398 private int[] cnstRowNo;
399 private int[] cnstClmNo;
400 private String[] cnstVals ; // Sheet単位ã?固定å?のキャãƒ?‚·ュ(シートã?æœ??に値を取得して保持しておく)
401
402 /**
403 * ãƒ?ƒ�ãƒ?‚°æƒ??をã?出力するかどã�?�‹[true/false]を指定しまã�?初期値:false)ã€?
404 *
405 * 初期値は、false(出力しなã�? ですã?
406 *
407 * @og.rev 5.5.8.2 (2012/11/09) 新規作æ?
408 *
409 * @param isDebug ãƒ?ƒ�ãƒ?‚°æƒ?? [true:出力すã‚?false:出力しない]
410 */
411 void setDebug( final boolean isDebug ) {
412 this.isDebug = isDebug ;
413 }
414
415 /**
416 * 行番号æƒ??をã?使用してã�?‚‹かどã�?�‹[true/false]を指定しまã�?初期値:true)ã€?
417 *
418 * 初期値は、true(使用する) ですã?
419 *
420 * @og.rev 5.1.6.0 (2010/05/01) 新規作æ?
421 *
422 * @param useNumber 行番号æƒ?? [true:使用してã�?‚‹/false:してã�?�ªい]
423 */
424 void setUseNumber( final boolean useNumber ) {
425 this.useNumber = useNumber ;
426 }
427
428 /**
429 * 固定å?となるカラãƒ?��(CSV形å¼?と、constAdrs 固定å?となるアドレス(è¡?åˆ?è¡?åˆ?・・・)を設定しますã?
430 *
431 * @param constKeys 固定å?となるカラãƒ?��(CSV形å¼?
432 * @param constAdrs 固定å?となるアドレス(è¡?åˆ?è¡?åˆ?・・・)
433 *
434 * @og.rev 5.5.8.2 (2012/11/09) 新規追åŠ?
435 */
436 public void setSheetConstData( final String constKeys,final String constAdrs ) {
437 if( constKeys == null || constKeys.isEmpty() ) {
438 return ;
439 }
440
441 cnstKeys = constKeys.split( "," );
442 cnstLen = cnstKeys.length;
443 cnstIndx = new int[cnstLen];
444 cnstRowNo = new int[cnstLen];
445 cnstClmNo = new int[cnstLen];
446
447 String[] row_col = constAdrs.split( "," ) ;
448 cnstRowNo = new int[cnstLen];
449 cnstClmNo = new int[cnstLen];
450 for( int j=0; j<cnstLen; j++ ) {
451 cnstKeys[j] = cnstKeys[j].trim(); // 前後ã?不要なスペã?スを削除
452 String rowcol = row_col[j].trim(); // 前後ã?不要なスペã?スを削除
453
454 int sep = rowcol.indexOf( '-' );
455 cnstRowNo[j] = Integer.parseInt( rowcol.substring( 0,sep ) );
456 cnstClmNo[j] = Integer.parseInt( rowcol.substring( sep+1 ) );
457
458 if( isDebug ) {
459 System.out.println( " Debug: constKey=" + cnstKeys[j] + " : RowNo= " + cnstRowNo[j] + " , ClmNo=" + cnstClmNo[j] );
460 }
461 }
462 }
463
464 /**
465 * カラãƒ?��を外部からæŒ?®šしますã?
466 * カラãƒ?��がã?NULL でなければã€?¼ƒNAME より、こちらが優先されますã?
467 * カラãƒ?��はã€??番に、指定するå¿?¦�がありますã?
468 *
469 * @og.rev 5.1.6.0 (2010/05/01) 新規作æ?
470 * @og.rev 5.5.8.2 (2012/11/09) 固定å?取得用の cnstIndx の設定を行うã€?
471 *
472 * @param columns EXCELのカラãƒ??(CSV形å¼?
473 *
474 * @return true:処ç�?®Ÿ施/false:無処ç�?
475 */
476 boolean setColumns( final String columns ) {
477 if( columns != null && columns.length() > 0 ) {
478 names = StringUtil.csv2Array( columns );
479 columnSize = names.length ;
480 index = new int[columnSize];
481 int adrs = (useNumber) ? 1:0 ; // useNumber =true の場合ã?ã€?¼‘件目(No)は読み飛ã?すã?
482 // 5.5.8.2 (2012/11/09) 固定å?取得用の cnstIndx の設定を行うã€?
483 // for( int i=0; i<columnSize; i++ ) { index[i] = adrs++; }
484 for( int i=0; i<columnSize; i++ ) {
485 index[i] = adrs++;
486 for( int j=0; j<cnstLen; j++ ) {
487 if( names[i].equalsIgnoreCase( cnstKeys[j] ) ) {
488 cnstIndx[j] = index[i];
489 }
490 }
491 }
492 nameNoSet = false;
493
494 return true;
495 }
496 return false;
497 }
498
499 /**
500 * EXCEL ネイãƒ?‚£ブã?ãƒ??タをå?ç�?�™ã‚?ローカルクラスですã?
501 * こã?クラスでは、コメント行ã?スキãƒ??判定ã?ヘッãƒ??部のカラãƒ?��取得ã?
502 * 行情報(Row)から、カラãƒ??配å?の取得などを行いますã?
503 *
504 * @og.rev 4.3.4.0 (2008/12/01) POI3.2対å¿?
505 *
506 * @param oRow Row EXCELの行オブジェクãƒ?
507 *
508 * @return true:コメントè¡?false:通常è¡?
509 */
510 // boolean isSkip( HSSFRow oRow ) {
511 boolean isSkip( Row oRow ) {
512 if( oRow == null ) { return true; }
513
514 // short nFirstCell = oRow.getFirstCellNum();
515 int nFirstCell = oRow.getFirstCellNum();
516 // HSSFCell oCell = oRow.getCell(nFirstCell);
517 Cell oCell = oRow.getCell(nFirstCell);
518 String strText = getValue( oCell );
519 if( strText != null && strText.length() > 0 ) {
520 if( nameNoSet ) {
521 if( strText.equalsIgnoreCase( "#Name" ) ) {
522 makeNames( oRow );
523 nameNoSet = false;
524 return true;
525 }
526 else if( strText.charAt( 0 ) == '#' ) {
527 return true;
528 }
529 else {
530 String errMsg = "#NAME が見つかる前にãƒ??タが見つかりましたã€?
531 + HybsSystem.CR
532 + "可能性として、ファイルがã?ネイãƒ?‚£ブExcelでなã�?º‹がè€?�ˆられますã?"
533 + HybsSystem.CR ;
534 throw new HybsSystemException( errMsg );
535 }
536 }
537 else {
538 if( strText.charAt( 0 ) == '#' ) {
539 return true;
540 }
541 }
542 }
543
544 return nameNoSet ;
545 }
546
547 /**
548 * EXCEL ネイãƒ?‚£ブã?行情報(Row)からカラãƒ?��æƒ??を取得しますã?
549 *
550 * @og.rev 4.3.4.0 (2008/12/01) POI3.2対å¿?
551 * @og.rev 5.1.6.0 (2010/05/01) useNumber(行番号æƒ??をã?使用してã�?‚‹(true)/してã�?�ªã�?false)を指å®?
552 * @og.rev 5.1.6.0 (2010/05/01) useNumber(行番号æƒ??をã?使用してã�?‚‹(true)/してã�?�ªã�?false)を指å®?
553 * @og.rev 5.5.1.2 (2012/04/06) オリジナルのカラãƒ?��を取å¾?
554 * @og.rev 5.5.8.2 (2012/11/09) 固定å?取得用の cnstIndx の設定を行うã€?
555 *
556 * @param oRow Row EXCELの行オブジェクãƒ?
557 */
558 // private void makeNames( final HSSFRow oRow ) {
559 private void makeNames( final Row oRow ) {
560 // 先é?カラãƒ??ã€?NAME 属æ?行であるかどã�?�‹をã?useNumber で判定しておくã€?
561 short nFirstCell = (short)( (useNumber) ? 1:0 );
562 // short nFirstCell = oRow.getFirstCellNum();
563 short nLastCell = oRow.getLastCellNum();
564
565 orgNames = new String[nLastCell+1]; // 5.5.1.2 (2012/04/06) オリジナルのカラãƒ?��を取å¾?
566
567 int maxCnt = nLastCell - nFirstCell;
568 String[] names2 = new String[maxCnt];
569 // short[] index2 = new short[maxCnt];
570 int[] index2 = new int[maxCnt];
571
572 // 先é?カラãƒ??ã€?NAME 属æ?行であるã€?+ で、ä¸?�¤進めてã�?‚‹ã€?
573 // for( short nIndexCell = ++nFirstCell; nIndexCell <= nLastCell; nIndexCell++) {
574 // for( int nIndexCell = ++nFirstCell; nIndexCell <= nLastCell; nIndexCell++) {
575 // 先é?カラãƒ??ã€?NAME 属æ?行であるかどã�?�‹をã?useNumber で判定しておくã€?
576 for( int nIndexCell = nFirstCell; nIndexCell <= nLastCell; nIndexCell++) {
577 // HSSFCell oCell = oRow.getCell(nIndexCell);
578 Cell oCell = oRow.getCell(nIndexCell);
579 String strText = getValue( oCell );
580
581 orgNames[nIndexCell] = strText; // 5.5.1.2 (2012/04/06) オリジナルのカラãƒ?��を取å¾?
582
583 // #NAME 行が、ゼロæ–?—å?の場合ã?、読み飛ã?すã?
584 if( strText != null && strText.length() > 0 ) {
585 names2[columnSize] = strText;
586 index2[columnSize] = nIndexCell;
587 columnSize++;
588 }
589 }
590
591 // #NAME を使用しなã�??合:noæ¬?�Œ存在しなã�?‚±ース
592 if( maxCnt == columnSize ) {
593 names = names2;
594 index = index2;
595 }
596 else {
597 names = new String[columnSize];
598 // index = new short[columnSize];
599 index = new int[columnSize];
600 System.arraycopy(names2, 0, names, 0, columnSize);
601 System.arraycopy(index2, 0, index, 0, columnSize);
602 }
603
604 // 5.5.8.2 (2012/11/09) 固定å?取得用の cnstIndx の設定を行うã€?
605 if( cnstLen > 0 ) {
606 for( int i=0; i<columnSize; i++ ) {
607 for( int j=0; j<cnstLen; j++ ) {
608 if( names[i].equalsIgnoreCase( cnstKeys[j] ) ) {
609 cnstIndx[j] = index[i];
610 }
611 }
612 }
613 }
614 }
615
616 /**
617 * カラãƒ?��æƒ??を返しますã?
618 * ここでは、å?部配å?をそのまま返しますã?
619 *
620 * @return String[] カラãƒ??配å?æƒ??
621 */
622 String[] getNames() {
623 return names;
624 }
625
626 /**
627 * カラãƒ?‚µイズを返しますã?
628 *
629 * @return カラãƒ?‚µイズ
630 */
631 int getColumnSize() {
632 return columnSize;
633 }
634
635 /**
636 * Sheet単位ã?固定å?のキャãƒ?‚·ュ(シートã?æœ??に値を取得して保持しておく)を設定しますã?
637 * これは、シートチェンジのæœ??にä¸?º¦呼び出しておくことで、それ以降ã?列取得時に
638 * 固定å?を利用することで処ç�??度向上を目æŒ?�—ますã?
639 *
640 * @og.rev 5.5.8.2 (2012/11/09) 新規作æ?
641 *
642 * @param sheet Sheet EXCELのSheetオブジェクãƒ?
643 */
644 public void setSheetConstValues( final Sheet sheet ) {
645 cnstVals = new String[cnstLen];
646 for( int j=0; j<cnstLen; j++ ) {
647 Row oRow = sheet.getRow( cnstRowNo[j] );
648 Cell oCell = oRow.getCell( cnstClmNo[j] );
649 cnstVals[j] = getValue( oCell );
650
651 if( isDebug ) {
652 System.out.println( " Debug: Sheet=" + sheet.getSheetName() + " : RowNo= " + cnstRowNo[j] + " , ClmNo=" + cnstClmNo[j] + " , " + cnstKeys[j] + "=" + cnstVals[j] );
653 }
654 }
655 }
656
657 /**
658 * カラãƒ?��æƒ??を返しますã?
659 *
660 * @og.rev 5.5.8.2 (2012/11/09) 固定å?の設定を行うã€?
661 *
662 * @param oRow Row EXCELの行オブジェクãƒ?
663 *
664 * @return String[] カラãƒ??配å?æƒ??
665 */
666 // String[] row2Array( final HSSFRow oRow ) {
667 String[] row2Array( final Row oRow ) {
668 if( nameNoSet ) {
669 String errMsg = "#NAME が見つかる前にãƒ??タが見つかりましたã€?;
670 throw new HybsSystemException( errMsg );
671 }
672
673 String[] data = new String[columnSize];
674 for( int i=0;i<columnSize; i++ ) {
675 // HSSFCell oCell = oRow.getCell( index[i] );
676 Cell oCell = oRow.getCell( index[i] );
677 data[i] = getValue( oCell );
678 }
679
680 // 5.5.8.2 (2012/11/09) 固定å?の設定を行うã€?
681 for( int j=0; j<cnstLen; j++ ) {
682 data[cnstIndx[j]] = cnstVals[j];
683 }
684 return data;
685 }
686
687 /**
688 * セルオブジェクãƒ?Cell)から値を取りå?しますã?
689 *
690 * @og.rev 3.8.5.3 (2006/08/07) 取り出し方法を少し修正
691 * @og.rev 5.5.1.2 (2012/04/06) フォーマットセルを実行して、その結果をå?帰çš?�«処ç�?�™るã?
692 *
693 * @param oCell Cell EXCELのセルオブジェクãƒ?
694 *
695 * @return セルの値
696 */
697 // private String getValue( final Cell oCell ) {
698 private String getValue( final Cell oCell ) {
699 lastCell = oCell; // 5.5.1.2 (2012/04/06) 今から実行するセルを取得しておきますã?
700
701 if( oCell == null ) { return null; }
702
703 String strText = "";
704 // HSSFRichTextString richText;
705 RichTextString richText;
706 int nCellType = oCell.getCellType();
707 switch(nCellType) {
708 // case HSSFCell.CELL_TYPE_NUMERIC:
709 case Cell.CELL_TYPE_NUMERIC:
710 strText = getNumericTypeString( oCell );
711 break;
712 // case HSSFCell.CELL_TYPE_STRING:
713 case Cell.CELL_TYPE_STRING:
714 // POI3.0 strText = oCell.getStringCellValue();
715 richText = oCell.getRichStringCellValue();
716 if( richText != null ) {
717 strText = richText.getString();
718 }
719 break;
720 // case HSSFCell.CELL_TYPE_FORMULA:
721 case Cell.CELL_TYPE_FORMULA:
722 // POI3.0 strText = oCell.getStringCellValue();
723 // 5.5.1.2 (2012/04/06) フォーマットセルを実行して、その結果をå?帰çš?�«処ç�?�™るã?
724 Workbook wb = oCell.getSheet().getWorkbook();
725 CreationHelper crateHelper = wb.getCreationHelper();
726 FormulaEvaluator evaluator = crateHelper.createFormulaEvaluator();
727
728 try {
729 strText = getValue(evaluator.evaluateInCell(oCell));
730 }
731 catch ( Throwable th ) {
732 // String errMsg = "セルフォーマットが解析できませんã€?" + String.valueOf(oCell.getCellFormula()) + "]"
733 String errMsg = "セルフォーマットが解析できませんã€?" + oCell.getCellFormula() + "]"
734 + getLastCellMsg();
735 throw new HybsSystemException( errMsg,th );
736 }
737 break;
738
739 // richText = oCell.getRichStringCellValue();
740 // if( richText != null ) {
741 // strText = richText.getString();
742 // }
743 // else {
744 // strText = getNumericTypeString( oCell );
745 // }
746 // break;
747 // case HSSFCell.CELL_TYPE_BOOLEAN:
748 case Cell.CELL_TYPE_BOOLEAN:
749 strText = String.valueOf(oCell.getBooleanCellValue());
750 break;
751 // case HSSFCell.CELL_TYPE_BLANK :
752 // case HSSFCell.CELL_TYPE_ERROR:
753 case Cell.CELL_TYPE_BLANK :
754 case Cell.CELL_TYPE_ERROR:
755 break;
756 default :
757 break;
758 }
759 return strText.trim();
760 }
761
762 /**
763 * セル値が数字ã?場合に、数字か日付かを判断して、対応する文字å?を返しますã?
764 *
765 * @og.rev 3.8.5.3 (2006/08/07) 新規追åŠ?
766 * @og.rev 5.5.7.2 (2012/10/09) HybsDateUtil を利用するように修正しますã?
767 *
768 * @param oCell Cell
769 *
770 * @return 数字ã?場合ã?、文字å?に変換した結果をã?日付ã?場合ã?ã€?yyyyMMddHHmmss" 形式で返しますã?
771 */
772 // private String getNumericTypeString( final HSSFCell oCell ) {
773 private String getNumericTypeString( final Cell oCell ) {
774 final String strText ;
775
776 double dd = oCell.getNumericCellValue() ;
777 // if( HSSFDateUtil.isCellDateFormatted( oCell ) ) {
778 if( DateUtil.isCellDateFormatted( oCell ) ) {
779 strText = HybsDateUtil.getDate( DateUtil.getJavaDate( dd ).getTime() , "yyyyMMddHHmmss" ); // 5.5.7.2 (2012/10/09) HybsDateUtil を利用
780
781 // DateFormat dateFormat = new SimpleDateFormat( "yyyyMMddHHmmss",Locale.JAPAN );
782 // // strText = dateFormat.format( HSSFDateUtil.getJavaDate( dd ) );
783 // strText = dateFormat.format( DateUtil.getJavaDate( dd ) );
784 }
785 else {
786 NumberFormat numFormat = NumberFormat.getInstance();
787 if( numFormat instanceof DecimalFormat ) {
788 ((DecimalFormat)numFormat).applyPattern( "#.####" );
789 }
790 strText = numFormat.format( dd );
791 }
792 return strText ;
793 }
794
795 /**
796 * æœ?¾Œに実行してã�?‚‹セルæƒ??を返しますã?
797 *
798 * エラー発生時に、どのセルでエラーが発生したかのæƒ??を取得できるようにしますã?
799 *
800 * @og.rev 5.5.1.2 (2012/04/06) 新規追åŠ?
801 * @og.rev 5.5.8.2 (2012/11/09) エラーæƒ??に、シート名も追åŠ?
802 *
803 * @return æœ?¾Œに実行してã�?‚‹セルæƒ??のæ–?—å?
804 */
805 String getLastCellMsg() {
806 String lastMsg = null;
807
808 if( lastCell != null ) {
809 int rowNo = lastCell.getRowIndex();
810 int celNo = lastCell.getColumnIndex();
811 int no = lastCell.getColumnIndex();
812 String shtNm = lastCell.getSheet().getSheetName();
813
814
815 lastMsg = "Sheet=" + shtNm + ", Row=" + rowNo + ", Cel=" + celNo ;
816 if( orgNames != null && orgNames.length < no ) {
817 lastMsg = lastMsg + ", NAME=" + orgNames[no] ;
818 }
819 }
820 return lastMsg;
821 }
822 }