Skip to content

Commit

Permalink
Provide public SCP command line builder (Fixes \#951)
Browse files Browse the repository at this point in the history
Signed-off-by: Jeroen van Erp <jeroen@hierynomus.com>
  • Loading branch information
hierynomus committed Aug 20, 2024
1 parent 54376b7 commit 93046f3
Show file tree
Hide file tree
Showing 2 changed files with 33 additions and 21 deletions.
32 changes: 20 additions & 12 deletions src/main/java/net/schmizz/sshj/xfer/scp/SCPUploadClient.java
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import net.schmizz.sshj.xfer.LocalFileFilter;
import net.schmizz.sshj.xfer.LocalSourceFile;
import net.schmizz.sshj.xfer.TransferListener;
import net.schmizz.sshj.xfer.scp.ScpCommandLine.Arg;

import java.io.IOException;
import java.io.InputStream;
Expand All @@ -43,37 +44,44 @@ public synchronized int copy(LocalSourceFile sourceFile, String remotePath)
return copy(sourceFile, remotePath, ScpCommandLine.EscapeMode.SingleQuote);
}

public synchronized int copy (LocalSourceFile sourceFile, String remotePath, ScpCommandLine.EscapeMode escapeMode) throws IOException {
public synchronized int copy(LocalSourceFile sourceFile, String remotePath, ScpCommandLine.EscapeMode escapeMode)
throws IOException {
return copy(sourceFile, remotePath, escapeMode, true);
}

public synchronized int copy(LocalSourceFile sourceFile, String remotePath, ScpCommandLine.EscapeMode escapeMode, boolean preserveTimes)
throws IOException {
throws IOException {
ScpCommandLine commandLine = ScpCommandLine.with(ScpCommandLine.Arg.SINK)
.and(ScpCommandLine.Arg.RECURSIVE)
.and(ScpCommandLine.Arg.LIMIT, String.valueOf(bandwidthLimit), (bandwidthLimit > 0));
if (preserveTimes) {
commandLine.and(ScpCommandLine.Arg.PRESERVE_TIMES, sourceFile.providesAtimeMtime());
}
return copy(sourceFile, remotePath, escapeMode, commandLine);
}

public synchronized int copy(LocalSourceFile sourceFile, String remotePath, ScpCommandLine.EscapeMode escapeMode, ScpCommandLine commandLine)
throws IOException {
engine.cleanSlate();
try {
startCopy(sourceFile, remotePath, escapeMode, preserveTimes);
commandLine.withPath(remotePath, escapeMode);
startCopy(sourceFile, commandLine);
} finally {
engine.exit();
}
return engine.getExitStatus();
}


public void setUploadFilter(LocalFileFilter uploadFilter) {
this.uploadFilter = uploadFilter;
}

private void startCopy(LocalSourceFile sourceFile, String targetPath, ScpCommandLine.EscapeMode escapeMode, boolean preserveTimes)
private void startCopy(LocalSourceFile sourceFile, ScpCommandLine commandLine)
throws IOException {
ScpCommandLine commandLine = ScpCommandLine.with(ScpCommandLine.Arg.SINK)
.and(ScpCommandLine.Arg.RECURSIVE)
.and(ScpCommandLine.Arg.LIMIT, String.valueOf(bandwidthLimit), (bandwidthLimit > 0));
if (preserveTimes) {
commandLine.and(ScpCommandLine.Arg.PRESERVE_TIMES, sourceFile.providesAtimeMtime());
}
commandLine.withPath(targetPath, escapeMode);
engine.execSCPWith(commandLine);
engine.check("Start status OK");
process(engine.getTransferListener(), sourceFile, preserveTimes);
process(engine.getTransferListener(), sourceFile, commandLine.has(Arg.PRESERVE_TIMES));
}

private void process(TransferListener listener, LocalSourceFile f, boolean preserveTimes)
Expand Down
22 changes: 13 additions & 9 deletions src/main/java/net/schmizz/sshj/xfer/scp/ScpCommandLine.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ public class ScpCommandLine {
private static final String SCP_COMMAND = "scp";
private EscapeMode mode;

enum Arg {
public enum Arg {
SOURCE('f'),
SINK('t'),
RECURSIVE('r'),
Expand Down Expand Up @@ -77,19 +77,19 @@ String escapedPath(String path) {
ScpCommandLine() {
}

static ScpCommandLine with(Arg name) {
public static ScpCommandLine with(Arg name) {
return with(name, null, true);
}

static ScpCommandLine with(Arg name, String value) {
public static ScpCommandLine with(Arg name, String value) {
return with(name, value, true);
}

static ScpCommandLine with(Arg name, boolean accept) {
public static ScpCommandLine with(Arg name, boolean accept) {
return with(name, null, accept);
}

static ScpCommandLine with(Arg name, String value, boolean accept) {
public static ScpCommandLine with(Arg name, String value, boolean accept) {
ScpCommandLine commandLine = new ScpCommandLine();
commandLine.addArgument(name, value, accept);
return commandLine;
Expand All @@ -101,22 +101,22 @@ private void addArgument(Arg name, String value, boolean accept) {
}
}

ScpCommandLine and(Arg name) {
public ScpCommandLine and(Arg name) {
addArgument(name, null, true);
return this;
}

ScpCommandLine and(Arg name, String value) {
public ScpCommandLine and(Arg name, String value) {
addArgument(name, value, true);
return this;
}

ScpCommandLine and(Arg name, boolean accept) {
public ScpCommandLine and(Arg name, boolean accept) {
addArgument(name, null, accept);
return this;
}

ScpCommandLine and(Arg name, String value, boolean accept) {
public ScpCommandLine and(Arg name, String value, boolean accept) {
addArgument(name, value, accept);
return this;
}
Expand All @@ -127,6 +127,10 @@ ScpCommandLine withPath(String path, EscapeMode mode) {
return this;
}

boolean has(Arg arg) {
return arguments.containsKey(arg);
}

String toCommandLine() {
final StringBuilder cmd = new StringBuilder(SCP_COMMAND);
for (Arg arg : arguments.keySet()) {
Expand Down

0 comments on commit 93046f3

Please sign in to comment.