Skip to content

Commit 423ace2

Browse files
authored
Merge pull request #1746 from dkan75/support-run-over-ssh-with-ssh-config
Add support ssh-config to run-over-ssh
2 parents 46c00ff + 922be73 commit 423ace2

File tree

2 files changed

+54
-1
lines changed

2 files changed

+54
-1
lines changed

lib/kamal/commands/base.rb

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ def initialize(config)
1111
end
1212

1313
def run_over_ssh(*command, host:)
14-
"ssh#{ssh_proxy_args}#{ssh_keys_args} -t #{config.ssh.user}@#{host} -p #{config.ssh.port} '#{command.join(" ").gsub("'", "'\\\\''")}'"
14+
"ssh#{ssh_config_args}#{ssh_proxy_args}#{ssh_keys_args} -t #{config.ssh.user}@#{host} -p #{config.ssh.port} '#{command.join(" ").gsub("'", "'\\\\''")}'"
1515
end
1616

1717
def container_id_for(container_name:, only_running: false)
@@ -100,6 +100,19 @@ def tags(**details)
100100
Kamal::Tags.from_config(config, **details)
101101
end
102102

103+
def ssh_config_args
104+
case config.ssh.config
105+
when Array
106+
config.ssh.config.map { |file| " -F #{file}" }.join
107+
when String
108+
" -F #{config.ssh.config}"
109+
when true
110+
"" # Use default SSH config
111+
when false
112+
" -F /dev/null" # Ignore SSH config
113+
end
114+
end
115+
103116
def ssh_proxy_args
104117
case config.ssh.proxy
105118
when Net::SSH::Proxy::Jump

test/commands/app_test.rb

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -236,6 +236,26 @@ class CommandsAppTest < ActiveSupport::TestCase
236236
new_command.follow_logs(host: "app-1", timestamps: false, lines: 123, grep: "Completed")
237237
end
238238

239+
test "follow logs with ssh keys" do
240+
@config[:ssh] = { "keys" => [ "path_to_key.pem" ] }
241+
assert_equal \
242+
"ssh -i path_to_key.pem -t root@app-1 -p 22 'sh -c '\\''docker ps --latest --quiet --filter label=service=app --filter label=destination= --filter label=role=web --filter status=running --filter status=restarting --filter ancestor=$(docker image ls --filter reference=dhh/app:latest --format '\\''\\'\\'''\\''{{.ID}}'\\''\\'\\'''\\'') ; docker ps --latest --quiet --filter label=service=app --filter label=destination= --filter label=role=web --filter status=running --filter status=restarting'\\'' | head -1 | xargs docker logs --timestamps --follow 2>&1'",
243+
new_command.follow_logs(host: "app-1")
244+
end
245+
246+
test "follow logs with ssh proxy_command" do
247+
@config[:ssh] = { "proxy_command" => "ssh -W %h:%p user@proxy-server" }
248+
assert_equal \
249+
"ssh -o ProxyCommand='ssh -W %h:%p user@proxy-server' -t root@app-1 -p 22 'sh -c '\\''docker ps --latest --quiet --filter label=service=app --filter label=destination= --filter label=role=web --filter status=running --filter status=restarting --filter ancestor=$(docker image ls --filter reference=dhh/app:latest --format '\\''\\'\\'''\\''{{.ID}}'\\''\\'\\'''\\'') ; docker ps --latest --quiet --filter label=service=app --filter label=destination= --filter label=role=web --filter status=running --filter status=restarting'\\'' | head -1 | xargs docker logs --timestamps --follow 2>&1'",
250+
new_command.follow_logs(host: "app-1")
251+
end
252+
253+
test "follow logs with ssh config file" do
254+
@config[:ssh] = { "config" => "~/.ssh/custom_config" }
255+
assert_equal \
256+
"ssh -F ~/.ssh/custom_config -t root@app-1 -p 22 'sh -c '\\''docker ps --latest --quiet --filter label=service=app --filter label=destination= --filter label=role=web --filter status=running --filter status=restarting --filter ancestor=$(docker image ls --filter reference=dhh/app:latest --format '\\''\\'\\'''\\''{{.ID}}'\\''\\'\\'''\\'') ; docker ps --latest --quiet --filter label=service=app --filter label=destination= --filter label=role=web --filter status=running --filter status=restarting'\\'' | head -1 | xargs docker logs --timestamps --follow 2>&1'",
257+
new_command.follow_logs(host: "app-1")
258+
end
239259

240260
test "execute in new container" do
241261
assert_match \
@@ -364,6 +384,26 @@ class CommandsAppTest < ActiveSupport::TestCase
364384
assert_equal "ssh -o ProxyCommand='ssh -W %h:%p user@proxy-server' -t root@1.1.1.1 -p 22 'ls'", new_command.run_over_ssh("ls", host: "1.1.1.1")
365385
end
366386

387+
test "run over ssh with config file" do
388+
@config[:ssh] = { "config" => "~/.ssh/custom_config" }
389+
assert_equal "ssh -F ~/.ssh/custom_config -t root@1.1.1.1 -p 22 'ls'", new_command.run_over_ssh("ls", host: "1.1.1.1")
390+
end
391+
392+
test "run over ssh with multiple config files" do
393+
@config[:ssh] = { "config" => [ "~/.ssh/config1", "~/.ssh/config2" ] }
394+
assert_equal "ssh -F ~/.ssh/config1 -F ~/.ssh/config2 -t root@1.1.1.1 -p 22 'ls'", new_command.run_over_ssh("ls", host: "1.1.1.1")
395+
end
396+
397+
test "run over ssh with config false" do
398+
@config[:ssh] = { "config" => false }
399+
assert_equal "ssh -F /dev/null -t root@1.1.1.1 -p 22 'ls'", new_command.run_over_ssh("ls", host: "1.1.1.1")
400+
end
401+
402+
test "run over ssh with config true" do
403+
@config[:ssh] = { "config" => true }
404+
assert_equal "ssh -t root@1.1.1.1 -p 22 'ls'", new_command.run_over_ssh("ls", host: "1.1.1.1")
405+
end
406+
367407
test "current_running_container_id" do
368408
assert_equal \
369409
"sh -c 'docker ps --latest --quiet --filter label=service=app --filter label=destination= --filter label=role=web --filter status=running --filter status=restarting --filter ancestor=$(docker image ls --filter reference=dhh/app:latest --format '\\''{{.ID}}'\\'') ; docker ps --latest --quiet --filter label=service=app --filter label=destination= --filter label=role=web --filter status=running --filter status=restarting' | head -1",

0 commit comments

Comments
 (0)