venerdì 23 ottobre 2015

ODI 12c - Groovy come creare un file csv leggendo da un file excel

Supponiamo di avere un file excel, per poterlo leggere con ODI occorre installare i drivers ODBC e poi procedere all'esecuzione dei normali KM di caricamento,
Se siamo però su macchine con Sistema Operativo MS, l'operazione è gratuita nel caso di macchine Linux/Unix occorre installare dei drivers ODBC e configurarli. Per evitare di installare e configurare questi drivers si può pensare di scrivere una classe java ed inserirla come script Groovy che effettui la lettura del file excel e generi a valle un file csv per ogni sheet. Per poter fare questo occorre utilizzare le classi java Apache POI che possono essere scaricate al seguente link.
Di seguito un esempio di lettura file excel e relativa scrittura csv.

...
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.ss.usermodel.WorkbookFactory;
...

public class xlsToCsv{

       /** Please change these Parameters 
     * @throws Exception *************/

public static void main(String [] args) throws Exception {

...

 if (directory.isFile() &&(directory.getAbsolutePath().contains(".xls")||directory.getAbsolutePath().contains(".xlsx"))) {
                    ...
                                              
         try {
              name = "";
              FileInputStream file = new FileInputStream(new File(directory.getAbsolutePath()));                      
          if(directory.getName().contains(".xlsx"))
    name = directory.getName().replaceAll(".xlsx", ".csv");
        else
name = directory.getName().replaceAll(".xls", ".csv");                    
                      
                filex = new File(name);
                       
            if (!filex.exists()) {
       filex.createNewFile();
     }
                      
                     ...
                       
             Workbook workbook = null;
             Sheet sheet = null;
             Iterator<Row> rowIterator = null;
             //Get the workbook instance for XLS file 
             workbook = WorkbookFactory.create(file);                    
             //Get first sheet from the workbook
             sheet = workbook.getSheetAt(0);
             rowIterator = sheet.iterator();                      
             //Iterate through each rows from first sheet
                        
                  while(rowIterator.hasNext()) {
                       
                   Row row = rowIterator.next();
                   if(row.getRowNum()!=0){
                   //For each row, iterate through each columns
                   Iterator<Cell> cellIterator = row.cellIterator();
                   String concat = "";
                       while(cellIterator.hasNext()) {                              
                    Cell cell = cellIterator.next();
                    String str = "";
                    switch(cell.getCellType()) {
                     case Cell.CELL_TYPE_BOOLEAN:
                         str = (String.valueOf(cell.getBooleanCellValue()));
                    break;
                     case Cell.CELL_TYPE_NUMERIC:
                         str = (String.valueOf(cell.getNumericCellValue()));
                     break;
                     case Cell.CELL_TYPE_STRING:
                          str = (String.valueOf(cell.getStringCellValue()));
                              break;
                     }
                               
                  if(str.contains("|")){
                           throw new Exception("file "+directory.getAbsolutePath()+" non valido");
                     }
                        concat = concat + str;
                        concat=concat+("|");
                              
                   }
                                        
                      concat = concat.substring(0,concat.length()-1)+"\n";
                      outputStream.write(concat.getBytes());
                   }
                  }
                     outputStream.flush();
                     outputStream.close();
                     file.close();                                                   
                    } catch (FileNotFoundException e) {
                    e.printStackTrace();       
                    } catch (IOException e) {
                       e.printStackTrace();
                    }
...
                   } // if file
                   
...                   
}
}


Alla fine dovremmo avere per ogni sheet un file csv delimitato da "|" nel caso in cui questo valore non è presente nelle stringhe di testo.