package com.vst.snippets;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import org.hibernate.HibernateException;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.w3c.dom.Document;
import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xml.sax.SAXException;
import com.vst.model.ext.GeoCity;
import com.vst.model.ext.GeoClassificator;
import com.vst.model.ext.GeoCountry;
import com.vst.model.ext.GeoMacroRegion;
import com.vst.model.ext.GeoProvince;
public class LoadGeoClassificatorUtil {
private SessionFactory sessionFactory;
private Session sess;
private RTreeItem root;
public static String toTranslit(String name) {
if (name == null) {
return null;
}
if (name.length() > 0) {
name = name.trim();
name = name.replace(' ', '_');
name = name.replace(',', '_');
name = name.replace('\\', '_');
name = name.replace('/', '_');
name = name.replace('.', '_');
name = name.replaceAll("__", "_");
name = StringUtils.toTranslit(name);
}
return name;
}
class RTreeItem {
GeoClassificator item;
List<RTreeItem> children;
public RTreeItem() {
item = new GeoClassificator();
children = new ArrayList<RTreeItem>();
}
public RTreeItem(int code) {
if (code == 0) {
item = new GeoCountry();
} else if (code == 1){
item = new GeoMacroRegion();
} else if (code == 2){
item = new GeoProvince();
} else if (code == 3){
item = new GeoCity();
}else{
item = new GeoClassificator();
}
children = new ArrayList<RTreeItem>();
}
}
public LoadGeoClassificatorUtil() {
}
public LoadGeoClassificatorUtil(SessionFactory sessionFactory) {
this.sessionFactory = sessionFactory;
}
public Session getSession() throws HibernateException {
if (sess == null){
sess = sessionFactory.openSession();
}
return sess;
}
public void loadGeoRegions() throws SAXException, IOException {
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
InputStream in = LoadGeoClassificatorUtil.class.getResourceAsStream("georegions.xml");
try {
// Using factory get an instance of document builder
DocumentBuilder db = dbf.newDocumentBuilder();
// parse using builder to get DOM representation of the XML file
Document dom = db.parse(in);
doLoadFromDom(dom);
} catch (ParserConfigurationException pce) {
pce.printStackTrace();
} catch (SAXException se) {
se.printStackTrace();
} catch (IOException ioe) {
ioe.printStackTrace();
}
}
private void doLoadFromDom(Document dom) {
root = new RTreeItem();
root.item.setHierarchyLevel(0);
root.item.setRegionName("vstdomain");
root.item.setLatinName("vstdomain");
root.item.setLeafSign(0);
root.item.setParent(null);
root.item.setRegionCode("000");
scanDocument(root, dom.getDocumentElement());
doSaveModel(root);
System.out.println("done!!");
}
private void doSaveModel(RTreeItem root2) {
getSession();
saveModel(root2);
sess.close();
}
private void saveModel(RTreeItem ritem) {
sess.beginTransaction();
sess.save(ritem.item);
//sess.evict(ritem.item);
sess.getTransaction().commit();
for(RTreeItem child : ritem.children){
saveModel(child);
}
}
private RTreeItem getRegionTagCode(Node pNode) {
int rcode = -1;
RTreeItem res = null;
if (pNode.getNodeName().equalsIgnoreCase("country")) {
rcode=0;
} else if (pNode.getNodeName().equalsIgnoreCase("macrostate")) {
rcode=1;
} else if (pNode.getNodeName().equalsIgnoreCase("state")) {
rcode=2;
} else if (pNode.getNodeName().equalsIgnoreCase("city")) {
rcode=3;
}
if (rcode != -1){
res = new RTreeItem(rcode);
}
return res;
}
private String getAttrVal(Node pNode, String name) {
NamedNodeMap attrs = pNode.getAttributes();
Node attr = attrs.getNamedItem(name);
return attr == null ? null : attr.getNodeValue();
}
private void scanDocument(RTreeItem parent, Node node) {
NodeList childs = node.getChildNodes();
for (int i = 0; i < childs.getLength() - 1; i++) {
Node child = childs.item(i);
if ((child.getNodeType() == Node.ELEMENT_NODE) || (child
.getNodeType() == Node.DOCUMENT_NODE)){
RTreeItem r = getRegionTagCode(child);
if (r != null) {
GeoClassificator rparent = parent.item;
r.item.setParent(rparent);
r.item.setHierarchyLevel(parent.item.getHierarchyLevel() + 1);
while (rparent != null) {
r.item.addAncestor(rparent);
rparent = rparent.getParent();
}
String name = getAttrVal(child,"name");
r.item.setRegionName(name);
r.item.setLatinName(toTranslit(name));
parent.children.add(r);
}
scanDocument(r != null ? r : parent, child);
}
}
}
public static void main(String[] args) throws SAXException, IOException {
//BasicConfigurator.configure();
ApplicationContext context = new ClassPathXmlApplicationContext(
new String[]{"com/vst/snippets/snippetsContext-hibernate.xml"});
SessionFactory cfg = (SessionFactory)
context.getBean("sessionFactory");
LoadGeoClassificatorUtil util = new LoadGeoClassificatorUtil(cfg);
util.loadGeoRegions();
}
}