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 }