/* * HJB4U is toolchain for creating a HyperJAXB front end for database users. * Copyright (C) 2010 NigelB * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ package hjb4u; import hjb4u.config.hjb4u.DBConf; import hjb4u.config.hjb4u.HJB4UConfiguration; import hjb4u.config.hjb4u.HJB4UConfigurationException; import com.sun.xml.bind.marshaller.NamespacePrefixMapper; import hjb4u.roundtrip.RoundTripInterface; import hjb4u.roundtrip.RoundTripProxy; import org.apache.log4j.Logger; import org.w3c.dom.Document; import org.w3c.dom.Element; import org.w3c.dom.Node; import org.w3c.dom.NodeList; import org.xml.sax.ErrorHandler; import org.xml.sax.SAXException; import org.xml.sax.SAXParseException; import javax.persistence.EntityManager; import javax.persistence.EntityManagerFactory; import javax.persistence.EntityTransaction; import javax.persistence.Persistence; import javax.xml.XMLConstants; import javax.xml.bind.*; import static javax.xml.bind.JAXBContext.newInstance; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; import javax.xml.transform.*; import javax.xml.transform.dom.DOMResult; import javax.xml.transform.dom.DOMSource; import javax.xml.transform.stream.StreamResult; import javax.xml.transform.stream.StreamSource; import javax.xml.validation.Schema; import javax.xml.validation.SchemaFactory; import javax.xml.validation.Validator; import java.io.*; import java.util.Arrays; import java.util.Comparator; import java.util.Properties; /** * <code>Main</code> * Date: May 20, 2009 * Time: 10:40:27 PM * * @author Nigel B */ public class Main { private JAXBContext jaxbContext; private Schema schema; private Marshaller vmarshaller; private Marshaller marshaller; private Unmarshaller unmarshaller; private EntityManagerFactory fac; private RoundTripInterface roundTrip = RoundTripProxy.createRoundTrip(); private HJB4UConfiguration settings = SettingsStore.getInstance().getSettings(); private Logger logger = Logger.getLogger(Main.class.getName()); public Main() throws SAXException, IOException, JAXBException { //Initialise JAXB. jaxbContext = newInstance(roundTrip.getContextPath()); marshaller = jaxbContext.createMarshaller(); vmarshaller = jaxbContext.createMarshaller(); unmarshaller = jaxbContext.createUnmarshaller(); schema = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI) .newSchema(this.getClass().getClassLoader().getResource(settings.getSchema())); vmarshaller.setSchema(schema); vmarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); vmarshaller.setProperty(Marshaller.JAXB_ENCODING, "UTF-8"); marshaller.setProperty(Marshaller.JAXB_ENCODING, "UTF-8"); NamespacePrefixMapper prefix = SettingsStore.getInstance().getNamespaceMapper(); marshaller.setProperty("com.sun.xml.bind.namespacePrefixMapper", prefix); vmarshaller.setProperty("com.sun.xml.bind.namespacePrefixMapper", prefix); unmarshaller.setSchema(schema); } private Properties getPersistance() throws HJB4UConfigurationException { Properties p = new Properties(); try { p = new Properties(); InputStream closer; p.load(closer = new FileInputStream( Util.joinPath(SettingsStore.getInstance().getConfDir(), "persistence.properties"))); closer.close(); } catch (IOException e) { logger.error("Failed to load persistance settings." + e, e); } boolean configError = true; String id = settings.getDatabase(); for (DBConf dbConf : settings.getDbs()) { if (dbConf.getUuid().equals(id)) { configError = false; logger.info("Using DB: " + dbConf); p.setProperty("hibernate.dialect", dbConf.getDialect()); p.setProperty("hibernate.connection.driver_class", dbConf.getDriver()); if (dbConf.getUsername() != null) { p.setProperty("hibernate.connection.username", dbConf.getUsername()); } if (dbConf.getPassword() != null) { p.setProperty("hibernate.connection.password", dbConf.getPassword()); } p.setProperty("hibernate.connection.url", dbConf.getUrl()); break; } } if (configError) { if (id == null) { throw new HJB4UConfigurationException("You haven't select a database configuration to use. It can be set the the Settings Dialog."); } else { throw new HJB4UConfigurationException("The database configuration selected is no longer available. Please select another in the Settings Dialog"); } } return p; } public void populateDatabase() throws HJB4UConfigurationException { Properties p = getPersistance(); p.setProperty("hibernate.hbm2ddl.auto", "create-drop"); fac = Persistence.createEntityManagerFactory(roundTrip.getPersistenceUnitName(), p); createEM().close(); } EntityManager createEM() throws HJB4UConfigurationException { Properties p = getPersistance(); fac = Persistence.createEntityManagerFactory(roundTrip.getPersistenceUnitName(), p); return fac.createEntityManager(p); } public void createXML(OutputStream out) throws TransformerException, JAXBException, ParserConfigurationException, IOException, ClassNotFoundException, HJB4UConfigurationException { String data = getData(); out.write(data.getBytes()); out.close(); if (settings.isValidate()) { test(data); } } /** * @param in - Input stream that provides the xml to be unmarsheled. * @throws JAXBException */ public void insertData(InputStream in) throws JAXBException, HJB4UConfigurationException { EntityManager emanager = createEM(); try { EntityTransaction t = emanager.getTransaction(); t.begin(); if (!settings.isValidate()) { unmarshaller.setSchema(null); } Object o = unmarshaller.unmarshal(in); if(o instanceof JAXBElement) { o = ((JAXBElement)o).getValue(); } emanager.persist(o); t.commit(); } finally { doClose(emanager); } } public void doClose(EntityManager emanager) { if (emanager != null) { emanager.close(); emanager = null; } } private String getData() throws JAXBException, ParserConfigurationException, TransformerException, ClassNotFoundException, HJB4UConfigurationException { EntityManager emanager = createEM(); try { DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); DocumentBuilder builder = factory.newDocumentBuilder(); Document doc = builder.newDocument(); Element n; Object loadedObject = emanager.find(Class.forName(settings.getRootElementType()), settings.getRootID()); marshaller.marshal(loadedObject, doc); // NodeList nl = n.getChildNodes(); // // for (int i = 0; i < nl.getLength(); i++) { // if (nl.item(i).getNodeType() == Node.ELEMENT_NODE) { //// removeHJID(nl.item(i), doc); // doc.appendChild(nl.item(i)); // } // } return getDomString(postProcess(doc, builder)); } finally { doClose(emanager); } } private Document postProcess(Document doc, DocumentBuilder builder) throws TransformerException { DOMSource domSource = new DOMSource(doc); TransformerFactory tf = TransformerFactory.newInstance(); Document result = doc; File[] transforms = new File(SettingsStore.getInstance().getXSLTDir()).listFiles(); Arrays.sort(transforms, new Comparator<File>() { public int compare(File o1, File o2) { return o1.getName().compareTo(o2.getName()); } }); for (File file : transforms) { logger.info(String.format("Transforming output with %s", file)); Transformer transformer = tf.newTransformer(new StreamSource(file)); result = builder.newDocument(); transformer.transform(domSource, new DOMResult(result)); domSource = new DOMSource(result); } return result; } private void removeHJID(Node n, Document doc) { Node cn; NodeList nl = n.getChildNodes(); Element e; int length = nl.getLength(); for (int i = 0; i < length; i++) { cn = nl.item(i); if (cn.getNodeType() == Node.ELEMENT_NODE) { removeHJID(cn, doc); } } if (n.getNodeType() == Node.ELEMENT_NODE) { e = (Element) n; e.removeAttribute("Hjid"); } } private String getDomString(Document doc) throws TransformerException { DOMSource domSource = new DOMSource(doc); TransformerFactory tf = TransformerFactory.newInstance(); Transformer transformer = tf.newTransformer(); // //transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes"); transformer.setOutputProperty(OutputKeys.METHOD, "xml"); transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8"); transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "4"); transformer.setOutputProperty(OutputKeys.INDENT, "yes"); transformer.setOutputProperty(OutputKeys.STANDALONE, "yes"); ByteArrayOutputStream bos = new ByteArrayOutputStream(); StreamResult sr = new StreamResult(bos); transformer.transform(domSource, sr); return bos.toString(); } private void test(String data) throws JAXBException { try { DocumentBuilder parser = DocumentBuilderFactory.newInstance().newDocumentBuilder(); Document document = parser.parse(new File("myXMLDocument.xml")); Validator validator = schema.newValidator(); validator.setErrorHandler(new ErrorHandler() { public void warning(SAXParseException exception) throws SAXException { logger.warn(exception, exception); } public void error(SAXParseException exception) throws SAXException { logger.error(exception, exception); } public void fatalError(SAXParseException exception) throws SAXException { logger.fatal(exception, exception); } }); validator.validate(new DOMSource(document)); } catch (IOException e) { logger.error(e, e); } catch (SAXException e) { logger.error(e, e); } catch (ParserConfigurationException e) { logger.error(e, e); } } }