업무중 자바로 엑셀을 만드는 일이 많은데 그걸 따로 따로 만들기는 벅찬 일이다.
ArrayList<String[]> resultList = new ArrayList<String[]>();
ArrayList<String> userName = new ArrayList<String>();
// HttpServletResponse response = null;
// count 뽑아서 놓은것
List<List<Integer>> count = new ArrayList<List<Integer>>();
String start = "";
String end = "";
for (int i = 1; i < 13; i++) {
if (i < 10) {
start = year + "0" + i + "01000000";
end = year + "0" + i + "31999999";
} else {
start = year + i + "01000000";
end = year + i + "31999999";
}
count.add(admUserService.selectTotalResultCount(start, end));
}
// 유저들 id, 이름뽑아서 놓은 곳
List<AdmUserVO> admList = new ArrayList<AdmUserVO>();
admList = admUserService.selectAdmInfo();
/*
* HSSF 는 .xls 형식 XSSF 는 .xlsx 형식 서로 사용해야할 변수 정의가 다 다름
*/
XSSFWorkbook wb = new XSSFWorkbook();
// 워크시트 지정
XSSFSheet sheet = wb.createSheet("sheet1");
Row row = null;
Cell cell = null;
try {
int rowNum = 0;
// cellStyle 지정
CellStyle titleStyle = wb.createCellStyle();
CellStyle headStyle = wb.createCellStyle();
CellStyle dataStyle = wb.createCellStyle();
CellStyle etcStyle = wb.createCellStyle();
// font 지정
Font titleFont = wb.createFont();
Font headFont = wb.createFont();
Font etcFont = wb.createFont();
// font 세팅------
// 글씨체 , 폰트 크기 , 볼드체 사용 유무, 폰트색상
headFont.setFontName("ARIAL");
titleFont.setFontName("ARIAL");
etcFont.setFontName("ARIAL");
// 폰트 크기 설정
// 원하는 폰트 크기 x2 후 0을 붙여서 입력
titleFont.setFontHeight((short) 320);
headFont.setFontHeight((short) 200);
etcFont.setFontHeight((short) 200);
// 이탤릭 사용유무
titleFont.setBold(true);
headFont.setBold(true);
etcFont.setBold(true);
// 폰트색
titleFont.setColor(IndexedColors.BLUE.getIndex());
headFont.setColor(IndexedColors.BLACK.getIndex());
etcFont.setColor(IndexedColors.BLACK.getIndex());
// 일반 내용쪽 테두리
etcStyle.setBorderTop(BorderStyle.THIN);
etcStyle.setBorderBottom(BorderStyle.THIN);
etcStyle.setBorderLeft(BorderStyle.THIN);
etcStyle.setBorderRight(BorderStyle.THIN);
//폰트 지정해준거 세팅해준거
titleStyle.setFont(titleFont);
headStyle.setFont(headFont);
etcStyle.setFont(etcFont);
// 타이틀
headStyle.setBorderTop(BorderStyle.THIN);
headStyle.setBorderBottom(BorderStyle.THIN);
headStyle.setBorderLeft(BorderStyle.THIN);
headStyle.setBorderRight(BorderStyle.THIN);
headStyle.setFont(headFont);
// 배경색
((XSSFCellStyle)headStyle).setFillForegroundColor(new XSSFColor(new java.awt.Color(204, 255, 255),null));
headStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
// 열 넓이 조절
sheet.setColumnWidth(0, (sheet.getColumnWidth(1)) + (short) 4096);
// 셀 병합
// title
sheet.addMergedRegion(new CellRangeAddress(0, 0, 0, 13));// 첫행 , 마지막행, 첫 열 , 마지막 열
row = sheet.createRow(rowNum++); // 행 객체 추가
cell = row.createCell((short) 0); // 추가한 행에 셀 객체 추가
cell.setCellStyle(titleStyle); // 셀에 스타일 지정
cell.setCellValue(year + "년 총 발송량"); // 데이터 입력
// Header
row = sheet.createRow(rowNum++);
cell = row.createCell((short) 0);
cell.setCellStyle(headStyle);
cell.setCellValue("");
for (int i = 1; i < 13; i++) {
cell = row.createCell((short) i);
cell.setCellStyle(headStyle);
cell.setCellValue(i + "월");
}
cell = row.createCell((short) 13);
cell.setCellStyle(headStyle);
cell.setCellValue("TOTAL");
int rowNum2 = rowNum;
row = sheet.createRow(rowNum++);
EntityManager em = emf.createEntityManager();
try {
String jpql = "select r.idx from RsvListVO r where r.u_idx = ?1 and r.sdate >= ?2 and r.sdate <= ?3";
Map<Integer, Integer> totalMap = new HashMap<Integer, Integer>();
for (int i = 0; i < admList.size(); i++) {
row = sheet.createRow(rowNum++);
cell = row.createCell((short) 0);
cell.setCellStyle(headStyle);
cell.setCellValue(admList.get(i).getAdmuserid() + "(" + admList.get(i).getAdmusername() + ")");
for (int j = 1; j <= 13; j++) {
cell = row.createCell((short) j);
cell.setCellStyle(etcStyle);
List<Integer> total = null;
if (j <= 9) {
total = em.createQuery(jpql, Integer.class)
.setParameter(1, admList.get(i).getAdmuser_idx())
.setParameter(2, year + "0" + j + "01000000")
.setParameter(3, year + "0" + j + "31999999")
.getResultList();
}else if(j == 13) {
total = em.createQuery(jpql, Integer.class)
.setParameter(1, admList.get(i).getAdmuser_idx())
.setParameter(2, year +"0101000000")
.setParameter(3, year +"1231999999")
.getResultList();
totalMap.put(admList.get(i).getAdmuser_idx(), total.size());
}else{
total = em.createQuery(jpql, Integer.class)
.setParameter(1, admList.get(i).getAdmuser_idx())
.setParameter(2, year + j + "01000000")
.setParameter(3, year + j + "31999999")
.getResultList();
}
if (total.size() == 0 || total == null) {
cell.setCellValue("-");
} else {
cell.setCellValue(total.size());
}
}
}
row = sheet.createRow(rowNum2);
cell = row.createCell((short) 0);
cell.setCellStyle(headStyle);
cell.setCellValue("전체발송량");
for(int i= 1; i<13; i++) {
cell = row.createCell((short) i);
cell.setCellStyle(etcStyle);
int total = 0;
for(int j=0; j<admList.size(); j++) {
total += count.get(i-1).get(j);
}
cell.setCellValue(total);
}
int totalCnt = 0;
for(int i= 0; i<admList.size(); i++) {
cell = row.createCell((short) 13);
cell.setCellStyle(etcStyle);
totalCnt += totalMap.get(admList.get(i).getAdmuser_idx());
}
cell.setCellValue(totalCnt);
if(totalMap != null) {
totalMap.clear();
totalMap.entrySet();
}
} catch (Exception e) {
e.printStackTrace();
}finally {
em.close();
}
} catch (Exception e) {
e.printStackTrace();
} finally {
}
// 엑셀 출력
try {
res.setHeader("Content-Disposition", "attachment;filename=resultDownload.xlsx");
res.setContentType("ms-vnd/excel");
OutputStream out = new BufferedOutputStream(res.getOutputStream());
wb.write(out);
out.flush();
wb.close();
out.close();
} catch (Exception e) {
System.out.println(e.getMessage());
}
따로 따로 만들려면 이런식으로 여러개의 코드가 계속 계속 작성이 필요하기 때문이다....
그래서 이번에 스프링으로 작업을 하니깐 mybatis에 기능을 이용하기로 했다...
이름하여 ResultHandler 라는 기능을 결과가 1row 조회될때 그걸 가지고 와서 Excel에 넣어 줄 수 있도록 그럼 세팅을 또... 시작하자 참 자바는 기본 세팅할 때 많은 번거로움을 느낀다.
POI
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi</artifactId>
<version>4.1.2</version>
</dependency>
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>4.1.2</version>
</dependency>
poi는 4.1.2버전과 스프링프레임워크 4.0 기반으로 작성된 코드이다.