반응형
지난 포스트에 이어서 이 포스트에서는 XML 데이터를 출력하는 기능에 대해 정리하겠습니다.
1. 실행결과
2. 구현 방법
이 토이 프로젝트에서는 특정 테이블의 데이터를 XML로 그대로 옮기는 것 만을 생각했기에
1) DB 테이블의 데이터를 XML로 옮기는 기능을 구현한 추상 클래스를 만들었고,
2) Item테이블의 정보가 담긴 XML에서 Item객체로 , Item객체에서 Item의 정보가 담긴 XML로 변환하게 해주는 클래스를 1) 추상클래스를 상속하여 만들었습니다.
이 토이 프로젝트에서는 파싱에 관련된 기능은 없지만
구상하고 있는 토이프로젝트 중 대용량의 XML 파싱 기능이 필요한 경우가 있으므로 겸사겸사 SAX방식으로 XML를 파싱 하는 기능도 만들어 두었습니다.
※ 아래의 코드가 XML을 다루기 위한 추상 XML 유틸 클래스입니다.
package tools.utils;
/**
* XML 데이터를 지정한 클래스(데이터를 담기위한 클래스) 형식으로 파싱,
* 또는 지정한 클래스에 담긴 데이터를 XML형식으로 변환해주는 유틸클래스.
* 대용량 XML데이터를 처리하는데 있어 유리한 SAXBuilder를 사용했다.
* 이 코드를 사용하기 위해선 build.gradle에 아래의 의존성을 추가해주어야한다.
* // https://mvnrepository.com/artifact/org.jdom/jdom
* compile group: 'org.jdom', name: 'jdom', version: '2.0.2'
*
* @author lee-y
*
*/
public abstract class XmlUtil {
int count = 0;
/**
* xml 데이터를 받아오는 부분
*
* @param target : 파싱 대상 XML
* @param obj : 파싱한 데이터를 담기위한 클래스
* @return
*/
public Object parser(String target, Object obj) {
SAXBuilder builder = new SAXBuilder();
InputStream xmlInput = new ByteArrayInputStream(target.getBytes());
Document doc;
Element el;
try {
doc = builder.build(xmlInput, "UTF-8");
el = doc.getRootElement();
getObject(el, obj);
} catch (JDOMException e) { e.printStackTrace();
} catch (IOException e) { e.printStackTrace();
} catch (Exception e) { e.printStackTrace(); }
return obj;
}
/**
* XML데이터를 파싱하기 위한 메소드.
* 재귀적인 방식으로 동작하도록 설계함.
*
* @param el : String 형식의 XML데이터를 Element형식으로 변환한것.
* @param obj : 파싱한 데이터를 담기위한 클래스
*/
public void getObject(Element el, Object obj) {
count++;
int countInFirstRoop = 0;
List<?> childList = el.getChildren();
Iterator<?> childItr = childList.iterator();
while(childItr.hasNext()) {
countInFirstRoop++;
Element childEl = (Element)childItr.next();
String elName = new String(childEl.getName());
List<?> grandChildList = childEl.getChildren();
Iterator<?> grandChildItr = grandChildList.iterator();
if (grandChildItr.hasNext()) {
System.out.println("("+count+") ("+countInFirstRoop+") [ "+ elName + " ] has child");
getObject(childEl, obj);
} else {
List<?> contentList = childEl.getContent();
Iterator<?> contentItr = contentList.iterator();
if (contentItr.hasNext()) {
Content content = (Content) contentItr.next();
System.out.println("("+count+") ("+countInFirstRoop+") "+ elName + " : " + content.getValue());
if (!setData(elName, content.getValue(), obj)) {
System.err.println("Error ["+ elName+"], ["+content.getValue()+"]");
}
} else {
System.out.println("("+count+") ("+countInFirstRoop+") "+elName + " : Null value");
}
}
}
}
/**
* XML데이터를 파싱해서 데이터 클래스에 데이터를 담는 메소드.
*
* @param elName : XML태그명
* @param val : XML태그의 값
* @param model : 파싱한 데이터를 담기위한 클래스
* @return
*/
public abstract boolean setData(String elName, String val, Object obj);
/**
* 지정한 데이터 클래스에 담긴 데이터를 XML형식으로 변환해주는 기능.
*
* @param obj : XML로 변환하기 위한 데이터 클래스
* @return
*/
public abstract String makeXml(Object obj);
}
※ 아래의 코드가 추상 클래스를 상속한 Item만을 다루기 위한 XML 유틸 클래스입니다.
package tools.utils;
public class ItemXmlUtil extends XmlUtil {
/**
* XML데이터를 파싱해서 데이터 클래스에 데이터를 담는 메소드.
*
* @param elName : XML태그명
* @param val : XML태그의 값
* @param model : 파싱한 데이터를 담기위한 클래스
* @return
*/
@Override
public boolean setData(String elName, String val, Object obj) {
if (val == null) return false;
System.out.println("Element Name : ["+elName+"], Value : ["+val+"]");
// ----- Start 이 부분은 지정한 데이터 클래스에 맞게 재정의를 해줘야함. -----
Item model = (Item) obj;
if (elName.equals("itemId")) {
model.setItemId(Integer.parseInt(val));
} else if (elName.equals("itemName")) {
model.setItemName(val);
} else if (elName.equals("itemDescription")) {
model.setItemDescription(val);
} else if (elName.equals("makerCode")) {
model.setMakerCode(val);
} else if (elName.equals("price")) {
model.setPrice(Integer.parseInt(val));
} else if (elName.equals("saleStatus")) {
model.setSaleStatus(Integer.parseInt(val));
} else if (elName.equals("images")) {
model.getImages().add(val);
} else {
return false;
}
return true;
}
/**
* 지정한 데이터 클래스에 담긴 데이터를 XML형식으로 변환해주는 기능.
*
* @param obj : XML로 변환하기 위한 데이터 클래스
* @return
*/
@Override
public String makeXml(Object obj) {
if (obj == null) return "";
Item i = (Item)obj;
Element rootEl = new Element("item");
Document doc = new Document(rootEl);
doc.getRootElement().addContent(new Element("itemId").addContent(String.valueOf(i.getItemId())));
doc.getRootElement().addContent(new Element("itemName").addContent(i.getItemName()));
doc.getRootElement().addContent(new Element("itemDescription").addContent(i.getItemDescription()));
doc.getRootElement().addContent(new Element("makerCode").addContent(i.getMakerCode()));
doc.getRootElement().addContent(new Element("price").addContent(String.valueOf(i.getPrice())));
doc.getRootElement().addContent(new Element("saleStatus").addContent(String.valueOf(i.getSaleStatus())));
Element images = new Element("images");
for (String img : i.getImages()) {
images.addContent(new Element("image").addContent(img));
}
doc.getRootElement().addContent(images);
Format fm = Format.getPrettyFormat();
fm.setEncoding("UTF-8");
XMLOutputter output = new XMLOutputter(fm);
return output.outputString(doc);
}
/**
* 지정한 데이터 클래스에 담긴 데이터를 XML형식으로 변환해주는 기능.
*
* @param list : XML로 변환하기 위한 데이터 클래스의 리스트
* @return
*/
public String makeXmlList(List<Item> list) {
if (list == null) return "";
Element rootEl = new Element("items");
Document doc = new Document(rootEl);
for (Item i : list) {
Element item = new Element("item");
item.addContent(new Element("itemId").addContent(String.valueOf(i.getItemId())));
item.addContent(new Element("itemName").addContent(i.getItemName()));
item.addContent(new Element("itemDescription").addContent(i.getItemDescription()));
item.addContent(new Element("makerCode").addContent(i.getMakerCode()));
item.addContent(new Element("price").addContent(String.valueOf(i.getPrice())));
item.addContent(new Element("saleStatus").addContent(String.valueOf(i.getSaleStatus())));
Element images = new Element("images");
for (String img : i.getImages()) {
images.addContent(new Element("image").addContent(img));
}
item.addContent(images);
doc.getRootElement().addContent(item);
}
Format fm = Format.getPrettyFormat();
fm.setEncoding("UTF-8");
XMLOutputter output = new XMLOutputter(fm);
return output.outputString(doc);
}
}
※ 위의 유틸 클래스의 메서드를 ItemDataOutputXml.java에서 사용하여 Item객체를 XML 데이터로 변환하여 파일로 출력합니다.
package tools.dataoutput;
import tools.models.Item;
import tools.utils.ItemXmlUtil;
public class ItemDataOutputXml extends ItemDataOutput {
private ItemXmlUtil xmlUtil = new ItemXmlUtil();
public ItemDataOutputXml() {
super();
Properties prop = new Properties();
InputStream is = null;
try {
is = ItemDataOutput.class.getClassLoader().getResourceAsStream("config.dataoutput.properties");
prop.load(is);
super.OUTPUT_DIR = prop.getProperty("output.dir.dataoutput.xml");
super.OUTPUT_FILE_NAME = prop.getProperty("output.filename.dataoutput.xml");
super.EXTENTION = ".xml";
super.ENCODING_TYPE = prop.getProperty("encodingtype.dataoutput.xml");
} catch (Exception e) {
System.out.println("Properties load fail!!");
}
}
@Override
public void outputDataToFile(List<Item> list, int processNum) {
String outputFilePath = makeFileName(processNum);
try (BufferedWriter bw = Files.newBufferedWriter(
Paths.get(outputFilePath),
Charset.forName(ENCODING_TYPE),
StandardOpenOption.CREATE_NEW)) {
bw.write(xmlUtil.makeXmlList(list));
} catch (IOException e) {
e.printStackTrace();
} catch (NullPointerException e) {
e.printStackTrace();
}
}
}
반응형
'프로그래밍 > Java-토이프로젝트' 카테고리의 다른 글
서버 상태 확인 시각화 툴(vmstat,sar와 같은 명령어의 결과 차트화)-1【전체구조와 설계】 (0) | 2021.07.12 |
---|---|
데이터 출력(DB -> json,xml등) 프로그램-2【JSON출력】 (0) | 2021.05.23 |
데이터 출력(DB -> json,xml등) 프로그램-1【전체구조】 (0) | 2021.05.22 |
파일 인코딩 변환 프로그램 (0) | 2021.05.14 |
계산기 (계산식을 입력 받아 처리) (0) | 2021.05.09 |
댓글