Hello here is the source of an example how we (my friend and Apple-Fan Michael and myself) did do it some months ago last year. The purpose was to collect log4j configuration from various locations into one file.
The idea is to include the dtd and the xsl script in the jar, to be automatically used, when nothing else is configured. If I understand the original problem correctly, this is more or less want you want. As you can see in the source, we adapted it from Cameron Taggart at the time. Change the package name (or whatever else...) and the import of the AbstractFileScannerMojo (also included). If it is of any value, please let me know any results of your work. Hope this helps Wolfgang ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ package WHATEVER.maven.util; /* * Licensed to the Apache Software Foundation (ASF) under one * or more contributor license agreements. See the NOTICE file * distributed with this work for additional information * regarding copyright ownership. The ASF licenses this file * to you under the Apache License, Version 2.0 (the * "License"); you may not use this file except in compliance * with the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, * software distributed under the License is distributed on an * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY * KIND, either express or implied. See the License for the * specific language governing permissions and limitations * under the License. */ import WHATEVER.maven.util.AbstractFileScannerMojo; import org.apache.maven.plugin.MojoExecutionException; import org.xml.sax.EntityResolver; import org.xml.sax.InputSource; import org.xml.sax.SAXException; import org.xml.sax.XMLReader; import javax.xml.parsers.ParserConfigurationException; import javax.xml.parsers.SAXParserFactory; import javax.xml.transform.Source; import javax.xml.transform.Transformer; import javax.xml.transform.TransformerException; import javax.xml.transform.TransformerFactory; import javax.xml.transform.URIResolver; import javax.xml.transform.sax.SAXSource; import javax.xml.transform.stream.StreamResult; import javax.xml.transform.stream.StreamSource; import java.io.*; /** * Transforms XML source files using an XSL style sheet. * * @goal collect * @phase process-sources * @author Cameron Taggart/Wolfgang Schrecker * * copied from JalopyMojo, then modified */ public class CollectLog4jConfig extends AbstractFileScannerMojo { /** * Location of the log4j.dtd. * * @parameter default-value="/org/apache/log4j/xml/log4j.dtd" */ private String log4jdtd; /** * The XSL stylesheet to use. * * @parameter default-value="${project.resources}/log4jcollect.xsl" */ private File xslFile; /** * The destination directory to write the XML file(s). * * @parameter expression="${project.build.outputDirectory}" * @required */ private File destDir; /** * The destination filename to write the XML file(s). * * @parameter expression="log4j.xml" */ private String destFilename; /** * Three modes are anticipated "Dryrun", "delete", and "generate"/"enable" * * @parameter expression="${mode}" * @parameter default-value="tryrun" */ private String mode; /** * The list of files to be used should (NOT = false) be (true) overwritten * * @parameter default-value=true */ private Boolean overwrite; /** * * @parameter default-value=false */ private Boolean strict; /** * * @parameter default-value=true */ private Boolean deletefilelist; // ----------------------------------------------------------- public void execute() throws MojoExecutionException { getLog().info("executing: " + this.getClass().getName() + "!"); try { super.execute(); // do some input validation if (!srcDir.exists()) { if( strict ) throw new MojoExecutionException( "CLC(strict): Source directory does not exist: " + srcDir); getLog().error( "CLC: Source directory does not exist: " + srcDir); return; } if (!destDir.exists()) { destDir.mkdirs(); } File destFile = new File(destDir.getCanonicalFile(), destFilename); File master = new File(destDir.getCanonicalFile(), "filelist.xml"); if ("FILELIST".compareToIgnoreCase(mode) == 0 || !master.exists() || overwrite) { getLog().debug("CLC: srcExcludes -> " + srcExcludes + " !"); String[] xmlFiles = getIncludedFiles(srcDir, srcIncludes, srcExcludes); getLog().info("CLC: # of XML files: " + xmlFiles.length); FileWriter masterWriter = new FileWriter(master); StringBuilder masterSB = new StringBuilder(); exhibitXMLHeader( masterSB ); exhibitXML( masterSB ); exhibitLog4jHeader( masterSB ); masterSB.append("\t<filelist>\n"); for (int i = 0; i < xmlFiles.length; i++) { getLog().debug( "CLC: file -> " + xmlFiles[i] + "!"); File log4j = new File(srcDir + "/" + xmlFiles[i]); getLog().debug( "CLC: ---- -> " + log4j.toURI() + "!"); masterSB.append("\t\t<doc filename=\"" + log4j.toURI() + "\" />\n"); } masterSB.append("\t</filelist>\n"); exhibitLog4jFooter( masterSB ); masterWriter.append(masterSB.toString()); masterWriter.close(); getLog().info( "CLC: new filelist -> " + master.getCanonicalPath()); } if ( "GENERATE".compareToIgnoreCase(mode) == 0 || "ENABLE".compareToIgnoreCase(mode) == 0) { getLog().debug("CLC: <log4jdtd> -> " + log4jdtd); TransformerFactory transformerFactory = TransformerFactory.newInstance(); transformerFactory.setURIResolver( /* this (anonymous) URIResolver needs it's own EntityResolver */ new URIResolver() { public Source resolve(String href, String base) throws TransformerException { try { SAXParserFactory saxParserFactory = SAXParserFactory.newInstance(); saxParserFactory.setValidating(false); saxParserFactory.setNamespaceAware(true); XMLReader xmlReader = saxParserFactory.newSAXParser().getXMLReader(); xmlReader.setEntityResolver( /* this (anonymous) class resolves always to the classpath entity 'log4j.dtd' */ new EntityResolver() { public InputSource resolveEntity(String publicId, String systemId) throws SAXException, IOException { getLog().debug("CLC: SAXParserFactory(publicId) -> " + publicId); getLog().debug("CLC: SAXParserFactory(systemId) -> " + systemId); if( systemId.contains("log4j.dtd") ) return new InputSource(this.getClass().getResourceAsStream(log4jdtd)); else { getLog().warn("CLC: SAXParserFactory(systemId) -> " + systemId); return null; } } } /*end of EntityResolver */ ); // setEntitiyResolver /* the SAXSource utilizes this (above) XMLReader and the InputSource returned */ SAXSource saxSource = new SAXSource(xmlReader, new InputSource(href)); return saxSource; } catch (SAXException e) { e.printStackTrace(); throw new TransformerException("CLC: SAXException -> " + e); } catch (ParserConfigurationException e) { e.printStackTrace(); throw new TransformerException("CLC: ParserConfigurationExceptio -> " + e); } } } /*end of URIResolver */ ); // setUriResolver Transformer transformer; // LATE input validation if (!xslFile.exists()) { if( strict ) throw new MojoExecutionException( "CLC(strict): XSL file does not exist: " + xslFile); getLog().info("CLC: XSL file does not exist: " + xslFile); getLog().info("CLC: ... taking '/log4jcollect.xsl' from classpath "); transformer = transformerFactory.newTransformer( new StreamSource( this.getClass().getResourceAsStream("/log4jcollect.xsl") ) ); } else transformer = transformerFactory.newTransformer(new StreamSource(xslFile)); getLog().info( "CLC: transform, srcFile: " + master.getAbsolutePath() + ", destFile: " + destFile); transformer.transform( new StreamSource(master) , new StreamResult( destFile ) ); if( deletefilelist ) { getLog().info( "CLC: " + master.getAbsolutePath() + " deleted !"); master.delete(); } } else { getLog().info(mode + "? possible values for <mode> are :"); getLog().info(" ENABLE,GENERATE,FILELIST !"); throw new MojoExecutionException( "CLC: <mode> value NOT applicable !"); } } catch (Exception e) { //e.printStackTrace(); if( strict ) throw new MojoExecutionException("CLC: exception " + e); else getLog().error("CLC: exception " + e); } getLog().info("finished: " + this.getClass().getName() + "!"); } } ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ package WHATEVER.maven.util; import java.io.File; import org.apache.maven.plugin.AbstractMojo; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugin.MojoFailureException; import org.apache.maven.project.MavenProject; import org.codehaus.plexus.util.DirectoryScanner; import org.codehaus.plexus.util.StringUtils; import java.util.*; /* * * Copyright (c) 2009, Wolfgang Schrecker * * Permission is hereby granted, free of charge, to any person obtaining a copy of * this software and associated documentation files (the "Software"), to deal in * the Software without restriction, including without limitation the rights to * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies * of the Software, and to permit persons to whom the Software is furnished to do * so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in all * copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE * SOFTWARE. */ public abstract class AbstractFileScannerMojo extends AbstractMojo { /** * The directory containing the file(s). All filenames * are relative to this location * * @parameter expression="${project.build.sourceDirectory}" * @required */ public File srcDir; /** * Pattern to describe the file(s) to be selected. * This is a comma- or space-separated list of patterns of files. * * @parameter default-value="**\/*" */ public String srcIncludes; /** * Pattern to describe the file(s) to be excluded. * This is a comma- or space-separated list of patterns of files. * * @parameter default-value="**\/target\/**\/*" */ public String srcExcludes; /** * list of files to be used, when defined ordering is required * * @parameter */ public String filelist; /** * Maven Project instance * * @parameter expression="${project}" * @required */ protected MavenProject project; /** * */ protected String fileList[]; //////////////////////////////////////////////////////////////////// protected GregorianCalendar cal; protected String today; public void execute() throws MojoExecutionException, MojoFailureException { if( filelist != null && filelist.length() > 0 ) { getLog().debug( "FS: filelist != null -> " + filelist + "!"); fileList = getIncludedFiles( srcDir, filelist ); } else if ( srcIncludes != null ) { getLog().debug( "FS: srcIncludes != null " ); fileList = getIncludedFiles( srcDir, srcIncludes, srcExcludes ); } else getLog().error( "FS: filelist != null && srcIncludes != null ??????" ); filelist = null; } public String[] getIncludedFiles( File directory, String fileliste ) { StringTokenizer tok = new StringTokenizer( fileliste, ", \r\t\n"); List<String> l = new ArrayList<String>(); while( tok.hasMoreTokens()) { String filename = tok.nextToken().trim(); if( filename != null && filename.length() > 1) { getLog().debug( "FS: filename -> "+ filename + "!" ); l.add(filename); } } int i = 0; String files[] = new String[l.size()]; Iterator iter =l.iterator(); while (iter.hasNext() ) { files[i] = (String) iter.next(); getLog().debug( "FS: files["+i+"] -> "+ files[i] + "!" ); i++; } return files; } public String[] getIncludedFiles(MavenProject project) { java.util.List list = project.getModules(); getLog().info( "FS: # of modules -> "+ list.size() + "!" ); int i = 0; String modules[] = new String[list.size()]; Iterator iter =list.iterator(); while (iter.hasNext() ) { modules[i] = (String) iter.next(); getLog().info( "FS: modules["+i+"] -> "+ modules[i] + "!" ); i++; } return modules; } public String[] getIncludedFiles( File directory, String includes, String excludes ) { DirectoryScanner scanner = new DirectoryScanner(); scanner.setBasedir( directory ); scanner.setIncludes( StringUtils.split( includes, "," ) ); if ( excludes != null ) { scanner.setExcludes( StringUtils.split( excludes, "," ) ); } scanner.scan(); String[] filesToFormat = scanner.getIncludedFiles(); return filesToFormat; } protected void exhibitXMLHeader(StringBuilder s) { s.append("<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n"); } protected void exhibitLog4jHeader(StringBuilder s) { //s.append("<!DOCTYPE log4j:configuration SYSTEM \"log4j.dtd\">\n"); s.append("<log4j:configuration xmlns:log4j=\"http://jakarta.apache.org/log4j/\" debug=\"false\">\n"); } protected void exhibitLog4jFooter(StringBuilder s) { s.append("</log4j:configuration>\n"); } protected void exhibitParam( StringBuilder s, String name, String value, String offset ) { s.append(offset+"<param name=\""+name+"\" value=\""+value+"\" >\n"); } protected void exhibitXML(StringBuilder s) { cal = new GregorianCalendar(); today = (cal.get(Calendar.YEAR))+"/" +(cal.get(Calendar.MONTH)+1)+"/" +cal.get(Calendar.DATE)+" " +cal.get(Calendar.HOUR_OF_DAY)+":" +cal.get(Calendar.MINUTE)+":" +cal.get(Calendar.SECOND); s.append("\n<!-- Generated by MAVEN plugin @ "+ today + " -->\n"); s.append("<!--\n-->"); } } ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ -------------------------------------------------- Atos Worldline Processing GmbH Hahnstrasse 25 60528 Frankfurt/Main Germany Phone: +49 69/6657-1176 Fax : mailto: [email protected] http://www.atosworldline.com Geschäftsführer: Erik Munk Koefoed Aufsichtsratsvorsitzender: Didier Dhennin Sitz der Gesellschaft: Frankfurt/Main Handelsregister: Frankfurt/Main HRB 40 417 * * * * * * * * L E G A L D I S C L A I M E R * * * * * * * * This e-mail is destined for the above mentioned recipient. In case you received this e-mail by accident, we would appreciate it if you could contact the sender and delete all copies stored on your computer. Please be aware that the security and confidentiality of electronic data transmitted by e-mail is not completely guaranteed and that data may be seen, copied, downloaded or changed by third persons during transmission. Atos Origin accepts no liability for the security and confidentiality of data and documents sent by e-mail. Please make sure that all important messages will be confirmed in writing by means of a telefax or a letter. * * * * * * * * L E G A L D I S C L A I M E R * * * * * * * * --------------------------------------------------------------------- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
