diff --git a/common/source/java/ch/systemsx/cisd/common/highwatermark/RemoteFreeSpaceProvider.java b/common/source/java/ch/systemsx/cisd/common/highwatermark/RemoteFreeSpaceProvider.java index 9537323af00614d6eda4eab4db015524dbf05b10..ed8a57a57f1b96ccd4ae15007caab7d36239a982 100644 --- a/common/source/java/ch/systemsx/cisd/common/highwatermark/RemoteFreeSpaceProvider.java +++ b/common/source/java/ch/systemsx/cisd/common/highwatermark/RemoteFreeSpaceProvider.java @@ -18,7 +18,6 @@ package ch.systemsx.cisd.common.highwatermark; import java.io.File; import java.io.IOException; -import java.util.Arrays; import java.util.List; import org.apache.commons.lang.StringUtils; @@ -92,25 +91,43 @@ public final class RemoteFreeSpaceProvider implements IFreeSpaceProvider final String path = file.getPath(); assert StringUtils.isNotEmpty(path) : "Empty path."; final String dfCommand = String.format(DF_COMMAND_TEMPLATE, path); - final List<String> command = Arrays.asList(sshExecutable.getPath(), "-T", host, dfCommand); + final List<String> command = + ProcessExecutionHelper.createSshCommand(dfCommand, sshExecutable, host); final ProcessResult processResult = ProcessExecutionHelper.run(command, millisToWaitForCompletion, operationLog, machineLog); processResult.log(); final List<String> processOutput = processResult.getProcessOutput(); final String commandLine = StringUtils.join(processResult.getCommandLine(), SPACE); - if (processOutput.size() >= 2) + String spaceOutputKb = tryParseFreeSpaceOutput(processOutput); + if (spaceOutputKb == null) { - final String output = processOutput.get(1); + throw new IOException(String.format( + "Command line '%s' did not return info as expected. Response was '%s'", + commandLine, processOutput)); + } + return parseKbytes(spaceOutputKb, dfCommand); + } + + // NOTE sometimes the line with results breaks if the value in the column is longer then the + // header. So we cannot take the 3rd token from the second line, we have to count tokens in all + // the lines which appear + private static String tryParseFreeSpaceOutput(final List<String> outputLines) + { + int line = 1; + int seenTokens = 0; + while (line < outputLines.size()) + { + final String output = outputLines.get(line); final String[] split = StringUtils.split(output, SPACE); - if (split.length >= 4) + if (seenTokens + split.length >= 4) { // The column 'avail' (3th column) interests us. - return parseKbytes(split[3], commandLine); + return split[3 - seenTokens]; } + seenTokens += split.length; + line++; } - throw new IOException(String.format( - "Command line '%s' did not return info as expected. Response was '%s'", - commandLine, processOutput)); + return null; } } \ No newline at end of file diff --git a/common/source/java/ch/systemsx/cisd/common/process/ProcessExecutionHelper.java b/common/source/java/ch/systemsx/cisd/common/process/ProcessExecutionHelper.java index 3b4811a32c0473b5f0c1e1f95e4883c565956e37..86d6d774ce876050cff18a7a81ecc8b96212a454 100644 --- a/common/source/java/ch/systemsx/cisd/common/process/ProcessExecutionHelper.java +++ b/common/source/java/ch/systemsx/cisd/common/process/ProcessExecutionHelper.java @@ -17,9 +17,11 @@ package ch.systemsx.cisd.common.process; import java.io.BufferedReader; +import java.io.File; import java.io.IOException; import java.io.InputStreamReader; import java.util.ArrayList; +import java.util.Arrays; import java.util.List; import org.apache.commons.io.IOUtils; @@ -63,6 +65,15 @@ public final class ProcessExecutionHelper private final Logger machineLog; + public static List<String> createSshCommand(String command, File sshExecutable, String host) + { + ArrayList<String> wrappedCmd = new ArrayList<String>(); + List<String> sshCommand = Arrays.asList(sshExecutable.getPath(), "-T", host); + wrappedCmd.addAll(sshCommand); + wrappedCmd.add(command); + return wrappedCmd; + } + /** * Runs an Operating System process, specified by <var>cmd</var>. *