HADOOP-9387. Fix DF so that it won't execute a shell command on Windows to compute the file system/mount point. Contributed by Ivan Mitic

git-svn-id: https://svn.apache.org/repos/asf/hadoop/common/trunk@1459642 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Tsz-wo Sze 2013-03-22 06:26:52 +00:00
parent 7ed618e324
commit 883601a1d6
3 changed files with 46 additions and 74 deletions

View File

@ -576,6 +576,9 @@ Release 2.0.5-beta - UNRELEASED
HADOOP-9299. kerberos name resolution is kicking in even when kerberos HADOOP-9299. kerberos name resolution is kicking in even when kerberos
is not configured (daryn) is not configured (daryn)
HADOOP-9387. Fix DF so that it won't execute a shell command on Windows
to compute the file system/mount point. (Ivan Mitic via szetszwo)
Release 2.0.4-alpha - UNRELEASED Release 2.0.4-alpha - UNRELEASED
INCOMPATIBLE CHANGES INCOMPATIBLE CHANGES

View File

@ -50,37 +50,6 @@ public class DF extends Shell {
private ArrayList<String> output; private ArrayList<String> output;
enum OSType {
OS_TYPE_UNIX("UNIX"),
OS_TYPE_WIN("Windows"),
OS_TYPE_SOLARIS("SunOS"),
OS_TYPE_MAC("Mac"),
OS_TYPE_AIX("AIX");
private String id;
OSType(String id) {
this.id = id;
}
public boolean match(String osStr) {
return osStr != null && osStr.indexOf(id) >= 0;
}
String getId() {
return id;
}
}
private static final String OS_NAME = System.getProperty("os.name");
private static final OSType OS_TYPE = getOSType(OS_NAME);
protected static OSType getOSType(String osName) {
for (OSType ost : EnumSet.allOf(OSType.class)) {
if (ost.match(osName)) {
return ost;
}
}
return OSType.OS_TYPE_UNIX;
}
public DF(File path, Configuration conf) throws IOException { public DF(File path, Configuration conf) throws IOException {
this(path, conf.getLong(CommonConfigurationKeys.FS_DF_INTERVAL_KEY, DF.DF_INTERVAL_DEFAULT)); this(path, conf.getLong(CommonConfigurationKeys.FS_DF_INTERVAL_KEY, DF.DF_INTERVAL_DEFAULT));
} }
@ -92,10 +61,6 @@ public class DF extends Shell {
this.output = new ArrayList<String>(); this.output = new ArrayList<String>();
} }
protected OSType getOSType() {
return OS_TYPE;
}
/// ACCESSORS /// ACCESSORS
/** @return the canonical path to the volume we're checking. */ /** @return the canonical path to the volume we're checking. */
@ -105,8 +70,13 @@ public class DF extends Shell {
/** @return a string indicating which filesystem volume we're checking. */ /** @return a string indicating which filesystem volume we're checking. */
public String getFilesystem() throws IOException { public String getFilesystem() throws IOException {
run(); if (Shell.WINDOWS) {
return filesystem; this.filesystem = dirFile.getCanonicalPath().substring(0, 2);
return this.filesystem;
} else {
run();
return filesystem;
}
} }
/** @return the capacity of the measured filesystem in bytes. */ /** @return the capacity of the measured filesystem in bytes. */
@ -138,16 +108,23 @@ public class DF extends Shell {
throw new FileNotFoundException("Specified path " + dirFile.getPath() throw new FileNotFoundException("Specified path " + dirFile.getPath()
+ "does not exist"); + "does not exist");
} }
run();
// Skip parsing if df was not successful if (Shell.WINDOWS) {
if (getExitCode() != 0) { // Assume a drive letter for a mount point
StringBuffer sb = new StringBuffer("df could not be run successfully: "); this.mount = dirFile.getCanonicalPath().substring(0, 2);
for (String line: output) { } else {
sb.append(line); run();
// Skip parsing if df was not successful
if (getExitCode() != 0) {
StringBuffer sb = new StringBuffer("df could not be run successfully: ");
for (String line: output) {
sb.append(line);
}
throw new IOException(sb.toString());
} }
throw new IOException(sb.toString()); parseOutput();
} }
parseOutput();
return mount; return mount;
} }
@ -163,24 +140,16 @@ public class DF extends Shell {
mount; mount;
} }
@Override
protected void run() throws IOException {
if (WINDOWS) {
try {
this.mount = dirFile.getCanonicalPath().substring(0,2);
} catch (IOException e) {
}
return;
}
super.run();
}
@Override @Override
protected String[] getExecString() { protected String[] getExecString() {
// ignoring the error since the exit code it enough // ignoring the error since the exit code it enough
return (WINDOWS)? new String[]{"cmd", "/c", "df -k " + dirPath + " 2>nul"}: if (Shell.WINDOWS){
new String[] {"bash","-c","exec 'df' '-k' '-P' '" + dirPath throw new AssertionError(
"DF.getExecString() should never be called on Windows");
} else {
return new String[] {"bash","-c","exec 'df' '-k' '-P' '" + dirPath
+ "' 2>/dev/null"}; + "' 2>/dev/null"};
}
} }
@Override @Override

View File

@ -36,15 +36,10 @@ import static org.junit.Assert.*;
public class TestDFVariations { public class TestDFVariations {
public static class XXDF extends DF { public static class XXDF extends DF {
private final String osName; public XXDF() throws IOException {
public XXDF(String osName) throws IOException {
super(new File(System.getProperty("test.build.data","/tmp")), 0L); super(new File(System.getProperty("test.build.data","/tmp")), 0L);
this.osName = osName;
}
@Override
public DF.OSType getOSType() {
return DF.getOSType(osName);
} }
@Override @Override
protected String[] getExecString() { protected String[] getExecString() {
return new String[] { "echo", "IGNORE\n", return new String[] { "echo", "IGNORE\n",
@ -53,13 +48,18 @@ public class TestDFVariations {
} }
@Test(timeout=5000) @Test(timeout=5000)
public void testOSParsing() throws Exception { public void testMountAndFileSystem() throws Exception {
for (DF.OSType ost : EnumSet.allOf(DF.OSType.class)) { XXDF df = new XXDF();
XXDF df = new XXDF(ost.getId()); String expectedMount =
assertEquals(ost.getId() + " mount", Shell.WINDOWS ? df.getDirPath().substring(0, 2) : "/foo/bar";
Shell.WINDOWS ? df.getDirPath().substring(0, 2) : "/foo/bar", String expectedFileSystem =
df.getMount()); Shell.WINDOWS ? df.getDirPath().substring(0, 2) : "/dev/sda3";
}
assertEquals("Invalid mount point",
expectedMount, df.getMount());
assertEquals("Invalid filesystem",
expectedFileSystem, df.getFilesystem());
} }
@Test(timeout=5000) @Test(timeout=5000)