Index: .classpath =================================================================== --- .classpath (revision 18778) +++ .classpath (working copy) @@ -4,7 +4,6 @@ - @@ -57,11 +56,24 @@ - - - - - + + + + + + + + + + + + + + + + + + Index: src/java/org/hibernate/tool/hbm2x/AbstractExporter.java =================================================================== --- src/java/org/hibernate/tool/hbm2x/AbstractExporter.java (revision 16604) +++ src/java/org/hibernate/tool/hbm2x/AbstractExporter.java (working copy) @@ -30,6 +30,7 @@ private TemplateHelper vh; private Properties properties = new Properties(); private ArtifactCollector collector = new ArtifactCollector(); + private String mergeMethod = MERGE; private Iterator iterator; @@ -254,4 +255,12 @@ public Cfg2JavaTool getCfg2JavaTool() { return c2j; } + + public void setMergeMethod(String mergeMethod){ + this.mergeMethod = mergeMethod; + } + + public String getMergeMethod(){ + return this.mergeMethod; + } } Index: src/java/org/hibernate/tool/hbm2x/DocExporter.java =================================================================== --- src/java/org/hibernate/tool/hbm2x/DocExporter.java (revision 16604) +++ src/java/org/hibernate/tool/hbm2x/DocExporter.java (working copy) @@ -610,7 +610,7 @@ protected void processTemplate(Map parameters, String templateName, File outputFile) { - TemplateProducer producer = new TemplateProducer(getTemplateHelper(), getArtifactCollector() ); + TemplateProducer producer = new TemplateProducer(getTemplateHelper(), getArtifactCollector(), getMergeMethod() ); producer.produce(parameters, templateName, outputFile, templateName); } Index: src/java/org/hibernate/tool/hbm2x/Exporter.java =================================================================== --- src/java/org/hibernate/tool/hbm2x/Exporter.java (revision 16604) +++ src/java/org/hibernate/tool/hbm2x/Exporter.java (working copy) @@ -13,6 +13,10 @@ * */ public interface Exporter { + + public static final String OVERWRITE = "overwrite"; + public static final String SKIP = "skip"; + public static final String MERGE = "merge"; /** * @param cfg An Hibernate {@link org.hibernate.Configuration} or subclass instance that defines the hibernate meta model to be exported. @@ -60,4 +64,8 @@ */ public void start(); + public void setMergeMethod(String mergeMethod); + + public String getMergeMethod(); + } Index: src/java/org/hibernate/tool/hbm2x/GenericExporter.java =================================================================== --- src/java/org/hibernate/tool/hbm2x/GenericExporter.java (revision 16604) +++ src/java/org/hibernate/tool/hbm2x/GenericExporter.java (working copy) @@ -27,7 +27,7 @@ modelIterators.put( "configuration", new ModelIterator() { void process(GenericExporter ge) { - TemplateProducer producer = new TemplateProducer(ge.getTemplateHelper(),ge.getArtifactCollector()); + TemplateProducer producer = new TemplateProducer(ge.getTemplateHelper(),ge.getArtifactCollector(), ge.getMergeMethod()); producer.produce(new HashMap(), ge.getTemplateName(), new File(ge.getOutputDirectory(),ge.filePattern), ge.templateName, "Configuration"); } @@ -138,7 +138,7 @@ } protected void exportPOJO(Map additionalContext, POJOClass element) { - TemplateProducer producer = new TemplateProducer(getTemplateHelper(),getArtifactCollector()); + TemplateProducer producer = new TemplateProducer(getTemplateHelper(),getArtifactCollector(), getMergeMethod()); additionalContext.put("pojo", element); additionalContext.put("clazz", element.getDecoratedObject()); String filename = resolveFilename( element ); Index: src/java/org/hibernate/tool/hbm2x/HibernateMappingExporter.java =================================================================== --- src/java/org/hibernate/tool/hbm2x/HibernateMappingExporter.java (revision 16604) +++ src/java/org/hibernate/tool/hbm2x/HibernateMappingExporter.java (working copy) @@ -38,7 +38,7 @@ Cfg2HbmTool c2h = getCfg2HbmTool(); Configuration cfg = getConfiguration(); if(c2h.isImportData(cfg) && (c2h.isNamedQueries(cfg)) && (c2h.isNamedSQLQueries(cfg)) && (c2h.isFilterDefinitions(cfg))) { - TemplateProducer producer = new TemplateProducer(getTemplateHelper(),getArtifactCollector()); + TemplateProducer producer = new TemplateProducer(getTemplateHelper(),getArtifactCollector(), getMergeMethod()); producer.produce(new HashMap(), "hbm/generalhbm.hbm.ftl", new File(getOutputDirectory(),"GeneralHbmSettings.hbm.xml"), getTemplateName(), "General Settings"); } } Index: src/java/org/hibernate/tool/hbm2x/SourceMerger.java =================================================================== --- src/java/org/hibernate/tool/hbm2x/SourceMerger.java (revision 0) +++ src/java/org/hibernate/tool/hbm2x/SourceMerger.java (revision 0) @@ -0,0 +1,89 @@ +package org.hibernate.tool.hbm2x; +import java.io.ByteArrayInputStream; +import java.io.File; +import java.io.FileInputStream; +import java.io.FileWriter; +import java.io.IOException; +import java.io.InputStream; + +import org.apache.log4j.Logger; +import org.eclipse.emf.codegen.merge.java.JControlModel; +import org.eclipse.emf.codegen.merge.java.JMerger; +import org.eclipse.emf.codegen.merge.java.facade.JCompilationUnit; +import org.eclipse.emf.codegen.merge.java.facade.jdom.JDOMFacadeHelper; +import org.eclipse.emf.codegen.merge.java.facade.jdom.JDOMJCompilationUnit; + +public class SourceMerger { + + protected static final Logger log = Logger.getLogger(SourceMerger.class); + + private JControlModel jControlModel; + + /** + * Does the merge operation and returns the new content. + */ + protected String merge(File targetFile, String newContent) { + try { + final String newSource; + if (targetFile.exists()) { + log.debug("Current source exists, use JMerge"); + final JControlModel jControlModel = getJControlModel(); + final JMerger jMerger = new JMerger(jControlModel); + + jMerger.setFixInterfaceBrace(jControlModel.getFacadeHelper().fixInterfaceBrace()); + jMerger.setTargetCompilationUnit(jMerger.createCompilationUnitForInputStream(getStringInputStream(newContent))); + jMerger.setSourceCompilationUnit(jMerger.createCompilationUnitForInputStream( + loadFileContent(targetFile))); + + jMerger.merge(); + newSource = jMerger.getTargetCompilationUnitContents(); + + jControlModel.getFacadeHelper().reset(); + + return newSource; + } else { + log.debug("Current source does not exist, create one"); + targetFile.createNewFile(); + FileWriter fw = new FileWriter(targetFile); + fw.write(newContent); + fw.flush(); + return newContent; + } + } catch (Exception e) { + throw new RuntimeException("Exception while merging and saving source file " + targetFile, e); + } + } + + public InputStream getStringInputStream(String s){ + return new ByteArrayInputStream(s.getBytes()); + } + + public InputStream loadFileContent(File file) throws IOException{ + return new FileInputStream(file); + } + + /** @return the jMerge control model */ + private JControlModel getJControlModel() { + if (jControlModel == null) { + jControlModel = new JControlModel(); + jControlModel.initialize(new MyJDomFacadeHelper(), this.getClass().getResource("merge.xml") + .toExternalForm()); + } + return jControlModel; + } + + // override method to prevent NPE (see https://bugs.eclipse.org/bugs/show_bug.cgi?id=308069) + class MyJDomFacadeHelper extends JDOMFacadeHelper { + @SuppressWarnings("deprecation") + @Override + public JCompilationUnit createCompilationUnit(String name, + String contents) { + JDOMJCompilationUnit compilationUnit = (JDOMJCompilationUnit) convertToNode(getJDOMFactory() + .createCompilationUnit(contents, name)); + compilationUnit.setOriginalContent(contents); + + return compilationUnit; + } + } + +} Index: src/java/org/hibernate/tool/hbm2x/TemplateProducer.java =================================================================== --- src/java/org/hibernate/tool/hbm2x/TemplateProducer.java (revision 16604) +++ src/java/org/hibernate/tool/hbm2x/TemplateProducer.java (working copy) @@ -17,13 +17,24 @@ private static final Log log = LogFactory.getLog(TemplateProducer.class); private final TemplateHelper th; private ArtifactCollector ac; + private String mergeMethod; + private SourceMerger merger; - public TemplateProducer(TemplateHelper th, ArtifactCollector ac) { + /*public TemplateProducer(TemplateHelper th, ArtifactCollector ac) { + this(th, ac, Exporter.OVERWRITE); + }*/ + + public TemplateProducer(TemplateHelper th, ArtifactCollector ac, String mergeMethod) { this.th = th; this.ac = ac; + this.mergeMethod = mergeMethod; } public void produce(Map additionalContext, String templateName, File destination, String identifier, String fileType, String rootContext) { + if (Exporter.SKIP.equalsIgnoreCase(mergeMethod) && destination.exists()){ + log.warn("Skipped creation for file " + destination + " as the file already exists."); + return; + } String tempResult = produceToString( additionalContext, templateName, rootContext ); @@ -31,6 +42,12 @@ log.warn("Generated output is empty. Skipped creation for file " + destination); return; } + if ("java".equals(fileType) && Exporter.MERGE.equalsIgnoreCase(mergeMethod) && destination.exists()){ + log.debug("Merging " + identifier + " with " + destination.getAbsolutePath() ); + if (merger == null) merger = new SourceMerger(); + tempResult = merger.merge(destination, tempResult); + } + FileWriter fileWriter = null; try { Index: src/java/org/hibernate/tool/hbm2x/merge.xml =================================================================== --- src/java/org/hibernate/tool/hbm2x/merge.xml (revision 0) +++ src/java/org/hibernate/tool/hbm2x/merge.xml (revision 0) @@ -0,0 +1,63 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + +