@@ -56,7 +56,9 @@ package org.apache.tools.ant.taskdefs;
import org.apache.tools.ant.*;
import org.apache.tools.ant.*;
import org.apache.tools.ant.types.*;
import org.apache.tools.ant.types.*;
import org.apache.tools.ant.util.*;
import java.util.Hashtable;
import java.util.Vector;
import java.util.Vector;
import java.io.File;
import java.io.File;
import java.io.IOException;
import java.io.IOException;
@@ -74,6 +76,15 @@ public class ExecuteOn extends ExecTask {
protected String type = "file";
protected String type = "file";
protected Commandline.Marker srcFilePos = null;
protected Commandline.Marker srcFilePos = null;
private boolean skipEmpty = false;
private boolean skipEmpty = false;
protected Commandline.Marker targetFilePos = null;
protected Mapper mapperElement = null;
protected FileNameMapper mapper = null;
protected File destDir = null;
/**
* Has <srcfile> been specified before <targetfile>
*/
protected boolean srcIsFirst = true;
/**
/**
* Adds a set of files (nested fileset attribute).
* Adds a set of files (nested fileset attribute).
@@ -103,6 +114,13 @@ public class ExecuteOn extends ExecTask {
skipEmpty = skip;
skipEmpty = skip;
}
}
/**
* Set the destination directory.
*/
public void setDest(File destDir) {
this.destDir = destDir;
}
/**
/**
* Marker that indicates where the name of the source file should
* Marker that indicates where the name of the source file should
* be put on the command line.
* be put on the command line.
@@ -116,18 +134,62 @@ public class ExecuteOn extends ExecTask {
return srcFilePos;
return srcFilePos;
}
}
/**
* Marker that indicates where the name of the target file should
* be put on the command line.
*/
public Commandline.Marker createTargetfile() {
if (targetFilePos != null) {
throw new BuildException(taskType + " doesn\'t support multiple targetfile elements.",
location);
}
targetFilePos = cmdl.createMarker();
srcIsFirst = (srcFilePos != null);
return targetFilePos;
}
/**
* Defines the FileNameMapper to use (nested mapper element).
*/
public Mapper createMapper() throws BuildException {
if (mapperElement != null) {
throw new BuildException("Cannot define more than one mapper",
location);
}
mapperElement = new Mapper(project);
return mapperElement;
}
protected void checkConfiguration() {
protected void checkConfiguration() {
if ("execon".equals(taskName)) {
log("!! execon is deprecated. Use apply instead. !!");
}
super.checkConfiguration();
super.checkConfiguration();
if (filesets.size() == 0) {
if (filesets.size() == 0) {
throw new BuildException("no filesets specified", location);
throw new BuildException("no filesets specified", location);
}
}
if (targetFilePos != null || mapperElement != null
|| destDir != null) {
if (mapperElement == null) {
throw new BuildException("no mapper specified", location);
}
if (mapperElement == null) {
throw new BuildException("no dest attribute specified",
location);
}
mapper = mapperElement.getImplementation();
}
}
}
protected void runExec(Execute exe) throws BuildException {
protected void runExec(Execute exe) throws BuildException {
try {
try {
Vector fileNames = new Vector();
Vector baseDirs = new Vector();
for (int i=0; i<filesets.size(); i++) {
for (int i=0; i<filesets.size(); i++) {
Vector v = new Vector();
FileSet fs = (FileSet) filesets.elementAt(i);
FileSet fs = (FileSet) filesets.elementAt(i);
File base = fs.getDir(project);
File base = fs.getDir(project);
DirectoryScanner ds = fs.getDirectoryScanner(project);
DirectoryScanner ds = fs.getDirectoryScanner(project);
@@ -135,36 +197,28 @@ public class ExecuteOn extends ExecTask {
if (!"dir".equals(type)) {
if (!"dir".equals(type)) {
String[] s = getFiles(base, ds);
String[] s = getFiles(base, ds);
for (int j=0; j<s.length; j++) {
for (int j=0; j<s.length; j++) {
v.addElement(s[j]);
fileNames.addElement(s[j]);
baseDirs.addElement(base);
}
}
}
}
if (!"file".equals(type)) {
if (!"file".equals(type)) {
String[] s = getDirs(base, ds);;
String[] s = getDirs(base, ds);;
for (int j=0; j<s.length; j++) {
for (int j=0; j<s.length; j++) {
v.addElement(s[j]);
fileNames.addElement(s[j]);
baseDirs.addElement(base);
}
}
}
}
if (v .size() == 0 && skipEmpty) {
if (fileNames .size() == 0 && skipEmpty) {
log("Skipping fileset for directory "
log("Skipping fileset for directory "
+ base + ". It is empty.", Project.MSG_INFO);
+ base + ". It is empty.", Project.MSG_INFO);
continue;
continue;
}
}
String[] s = new String[v.size()];
v.copyInto(s);
int err = -1;
if (parallel) {
String[] command = getCommandline(s, base);
log("Executing " + Commandline.toString(command),
Project.MSG_VERBOSE);
exe.setCommandline(command);
runExecute(exe);
} else {
if (!parallel) {
String[] s = new String[fileNames.size()];
fileNames.copyInto(s);
for (int j=0; j<s.length; j++) {
for (int j=0; j<s.length; j++) {
String[] command = getCommandline(s[j], base);
String[] command = getCommandline(s[j], base);
log("Executing " + Commandline.toString(command),
log("Executing " + Commandline.toString(command),
@@ -172,9 +226,23 @@ public class ExecuteOn extends ExecTask {
exe.setCommandline(command);
exe.setCommandline(command);
runExecute(exe);
runExecute(exe);
}
}
fileNames.removeAllElements();
baseDirs.removeAllElements();
}
}
}
}
if (parallel) {
String[] s = new String[fileNames.size()];
fileNames.copyInto(s);
File[] b = new File[baseDirs.size()];
baseDirs.copyInto(b);
String[] command = getCommandline(s, b);
log("Executing " + Commandline.toString(command),
Project.MSG_VERBOSE);
exe.setCommandline(command);
runExecute(exe);
}
} catch (IOException e) {
} catch (IOException e) {
throw new BuildException("Execute failed: " + e, e, location);
throw new BuildException("Execute failed: " + e, e, location);
} finally {
} finally {
@@ -189,22 +257,87 @@ public class ExecuteOn extends ExecTask {
* @param srcFiles The filenames to add to the commandline
* @param srcFiles The filenames to add to the commandline
* @param baseDir filenames are relative to this dir
* @param baseDir filenames are relative to this dir
*/
*/
protected String[] getCommandline(String[] srcFiles, File baseDir) {
protected String[] getCommandline(String[] srcFiles, File[] baseDirs) {
Vector targets = new Vector();
if (targetFilePos != null) {
Hashtable addedFiles = new Hashtable();
for (int i=0; i<srcFiles.length; i++) {
String[] subTargets = mapper.mapFileName(srcFiles[i]);
if (subTargets != null) {
for (int j=0; j<subTargets.length; j++) {
String name = (new File(destDir, subTargets[j])).getAbsolutePath();
if (!addedFiles.contains(name)) {
targets.addElement(name);
addedFiles.put(name, name);
}
}
}
}
}
String[] targetFiles = new String[targets.size()];
targets.copyInto(targetFiles);
String[] orig = cmdl.getCommandline();
String[] orig = cmdl.getCommandline();
String[] result = new String[orig.length+srcFiles.length];
String[] result = new String[orig.length+srcFiles.length+targetFiles.length ];
int index = orig.length;
int srcI ndex = orig.length;
if (srcFilePos != null) {
if (srcFilePos != null) {
index = srcFilePos.getPosition();
srcI ndex = srcFilePos.getPosition();
}
}
System.arraycopy(orig, 0, result, 0, index);
if (targetFilePos != null) {
int targetIndex = targetFilePos.getPosition();
if (srcIndex < targetIndex
|| (srcIndex == targetIndex && srcIsFirst)) {
// 0 --> srcIndex
System.arraycopy(orig, 0, result, 0, srcIndex);
// srcIndex --> targetIndex
System.arraycopy(orig, srcIndex, result,
srcIndex + srcFiles.length,
targetIndex - srcIndex);
// targets are already absolute file names
System.arraycopy(targetFiles, 0, result,
targetIndex + srcFiles.length,
targetFiles.length);
// targetIndex --> end
System.arraycopy(orig, targetIndex, result,
targetIndex + srcFiles.length + targetFiles.length,
orig.length - targetIndex);
} else {
// 0 --> targetIndex
System.arraycopy(orig, 0, result, 0, targetIndex);
// targets are already absolute file names
System.arraycopy(targetFiles, 0, result,
targetIndex,
targetFiles.length);
// targetIndex --> srcIndex
System.arraycopy(orig, targetIndex, result,
targetIndex + targetFiles.length,
srcIndex - targetIndex);
// srcIndex --> end
System.arraycopy(orig, srcIndex, result,
srcIndex + srcFiles.length + targetFiles.length,
orig.length - srcIndex);
srcIndex += targetFiles.length;
}
} else { // no targetFilePos
System.arraycopy(orig, 0, result, 0, srcIndex);
}
// fill in source file names
for (int i=0; i < srcFiles.length; i++) {
for (int i=0; i < srcFiles.length; i++) {
result[index+i] = (new File(baseDir, srcFiles[i])).getAbsolutePath();
result[srcIndex+i] =
(new File(baseDirs[i], srcFiles[i])).getAbsolutePath();
}
}
System.arraycopy(orig, index, result, index+srcFiles.length,
orig.length-index);
return result;
return result;
}
}
@@ -215,23 +348,35 @@ public class ExecuteOn extends ExecTask {
* @param baseDir filename is relative to this dir
* @param baseDir filename is relative to this dir
*/
*/
protected String[] getCommandline(String srcFile, File baseDir) {
protected String[] getCommandline(String srcFile, File baseDir) {
return getCommandline(new String[] {srcFile}, baseDir);
return getCommandline(new String[] {srcFile}, new File[] { baseDir} );
}
}
/**
/**
* Return the list of files from this DirectoryScanner that should
* Return the list of files from this DirectoryScanner that should
* be included on the command line.
* be included on the command line.
*/
*/
protected String[] getFiles(File basedir, DirectoryScanner ds) {
return ds.getIncludedFiles();
protected String[] getFiles(File baseDir, DirectoryScanner ds) {
if (mapper != null) {
SourceFileScanner sfs = new SourceFileScanner(this);
return sfs.restrict(ds.getIncludedFiles(), baseDir, destDir,
mapper);
} else {
return ds.getIncludedFiles();
}
}
}
/**
/**
* Return the list of Directories from this DirectoryScanner that
* Return the list of Directories from this DirectoryScanner that
* should be included on the command line.
* should be included on the command line.
*/
*/
protected String[] getDirs(File basedir, DirectoryScanner ds) {
return ds.getIncludedDirectories();
protected String[] getDirs(File baseDir, DirectoryScanner ds) {
if (mapper != null) {
SourceFileScanner sfs = new SourceFileScanner(this);
return sfs.restrict(ds.getIncludedDirectories(), baseDir, destDir,
mapper);
} else {
return ds.getIncludedDirectories();
}
}
}
/**
/**