bard 1.9.6 → 2.0.0.beta
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/ci.yml +0 -5
- data/MIGRATION_GUIDE.md +9 -24
- data/README.md +6 -14
- data/README.rdoc +15 -0
- data/Rakefile +1 -3
- data/features/bard_check.feature +94 -0
- data/features/bard_deploy.feature +18 -0
- data/features/bard_pull.feature +112 -0
- data/features/bard_push.feature +112 -0
- data/features/podman_testcontainers.feature +16 -0
- data/features/step_definitions/check_steps.rb +47 -0
- data/features/step_definitions/git_steps.rb +73 -0
- data/features/step_definitions/global_steps.rb +56 -0
- data/features/step_definitions/podman_steps.rb +23 -0
- data/features/step_definitions/rails_steps.rb +44 -0
- data/features/step_definitions/submodule_steps.rb +110 -0
- data/features/support/env.rb +39 -14
- data/features/support/grit_ext.rb +13 -0
- data/features/support/io.rb +32 -0
- data/features/support/podman.rb +153 -0
- data/lib/bard/ci/github_actions.rb +2 -1
- data/lib/bard/ci/jenkins.rb +11 -82
- data/lib/bard/ci/local.rb +6 -6
- data/lib/bard/ci/runner.rb +1 -35
- data/lib/bard/ci.rb +23 -11
- data/lib/bard/cli/ci.rb +38 -45
- data/lib/bard/cli/deploy.rb +9 -40
- data/lib/bard/cli/hurt.rb +15 -10
- data/lib/bard/cli/install.rb +12 -7
- data/lib/bard/cli/open.rb +16 -12
- data/lib/bard/cli/ping.rb +14 -8
- data/lib/bard/cli/provision.rb +1 -1
- data/lib/bard/cli/run.rb +3 -5
- data/lib/bard/cli/stage.rb +1 -9
- data/lib/bard/cli/vim.rb +10 -5
- data/lib/bard/cli.rb +11 -13
- data/lib/bard/command.rb +13 -33
- data/lib/bard/config.rb +14 -10
- data/lib/bard/copy.rb +33 -12
- data/lib/bard/deploy_strategy/github_pages.rb +2 -10
- data/lib/bard/deploy_strategy.rb +0 -3
- data/lib/bard/github.rb +4 -2
- data/lib/bard/provision/apt.rb +1 -1
- data/lib/bard/provision/logrotation.rb +1 -1
- data/lib/bard/provision/mysql.rb +2 -2
- data/lib/bard/provision/passenger.rb +2 -2
- data/lib/bard/provision/repo.rb +2 -2
- data/lib/bard/provision/ssh.rb +2 -9
- data/lib/bard/provision/swapfile.rb +1 -3
- data/lib/bard/server.rb +3 -46
- data/lib/bard/ssh_server.rb +2 -9
- data/lib/bard/target.rb +16 -67
- data/lib/bard/version.rb +1 -1
- data/spec/acceptance/docker/Dockerfile +1 -2
- data/spec/bard/ci/github_actions_spec.rb +13 -116
- data/spec/bard/cli/ci_spec.rb +8 -34
- data/spec/bard/cli/deploy_spec.rb +8 -46
- data/spec/bard/cli/hurt_spec.rb +2 -2
- data/spec/bard/cli/install_spec.rb +4 -4
- data/spec/bard/cli/open_spec.rb +8 -10
- data/spec/bard/cli/ping_spec.rb +5 -5
- data/spec/bard/cli/run_spec.rb +1 -20
- data/spec/bard/cli/stage_spec.rb +0 -20
- data/spec/bard/cli/vim_spec.rb +5 -5
- data/spec/bard/command_spec.rb +1 -3
- data/spec/bard/config_spec.rb +0 -28
- data/spec/bard/copy_spec.rb +3 -3
- data/spec/bard/github_spec.rb +1 -1
- data/spec/bard/provision/apt_spec.rb +1 -1
- data/spec/bard/provision/logrotation_spec.rb +1 -1
- data/spec/bard/provision/passenger_spec.rb +1 -1
- data/spec/bard/provision/repo_spec.rb +1 -1
- data/spec/bard/provision/ssh_spec.rb +4 -17
- data/spec/bard/provision/swapfile_spec.rb +1 -2
- data/spec/bard/ssh_server_spec.rb +8 -12
- data/spec/bard/target_spec.rb +5 -9
- data/spec/spec_helper.rb +1 -6
- metadata +31 -41
- data/CLAUDE.md +0 -76
- data/PLUGINS.md +0 -114
- data/cucumber.yml +0 -1
- data/features/ci.feature +0 -62
- data/features/data.feature +0 -12
- data/features/deploy.feature +0 -13
- data/features/deploy_git_workflow.feature +0 -88
- data/features/run.feature +0 -13
- data/features/step_definitions/bard_steps.rb +0 -135
- data/features/support/bard-coverage +0 -16
- data/features/support/test_server.rb +0 -216
- data/lib/bard/deprecation.rb +0 -19
- data/lib/bard/plugin.rb +0 -100
- data/lib/bard/plugins/backup.rb +0 -19
- data/lib/bard/plugins/github_pages.rb +0 -34
- data/lib/bard/plugins/hurt.rb +0 -5
- data/lib/bard/plugins/install.rb +0 -5
- data/lib/bard/plugins/jenkins.rb +0 -6
- data/lib/bard/plugins/new.rb +0 -5
- data/lib/bard/plugins/ping.rb +0 -6
- data/lib/bard/plugins/provision.rb +0 -5
- data/lib/bard/plugins/vim.rb +0 -5
- data/lib/bard/secrets.rb +0 -10
- data/spec/bard/ci/jenkins_spec.rb +0 -139
- data/spec/bard/ci/runner_spec.rb +0 -61
- data/spec/bard/deprecation_spec.rb +0 -281
- data/spec/bard/plugin_spec.rb +0 -79
data/lib/bard/config.rb
CHANGED
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
require "bard/server"
|
|
2
2
|
require "bard/target"
|
|
3
|
-
require "bard/deprecation"
|
|
4
3
|
|
|
5
4
|
module Bard
|
|
6
5
|
class Config
|
|
@@ -44,21 +43,14 @@ module Bard
|
|
|
44
43
|
|
|
45
44
|
# Old v1.x API - creates Server instances
|
|
46
45
|
def server(key, &block)
|
|
47
|
-
Deprecation.warn "`server` is deprecated; use `target` instead (will be removed in v2.0)"
|
|
48
46
|
key = key.to_sym
|
|
49
47
|
@servers[key] = Server.define(project_name, key, &block)
|
|
50
48
|
end
|
|
51
49
|
|
|
52
|
-
def remove_target(key)
|
|
53
|
-
@servers.delete(key.to_sym)
|
|
54
|
-
end
|
|
55
|
-
|
|
56
50
|
# New v2.0 API - creates Target instances
|
|
57
51
|
def target(key, &block)
|
|
58
52
|
key = key.to_sym
|
|
59
|
-
|
|
60
|
-
@servers[key] = Target.new(key, self)
|
|
61
|
-
end
|
|
53
|
+
@servers[key] ||= Target.new(key, self)
|
|
62
54
|
@servers[key].instance_eval(&block) if block
|
|
63
55
|
@servers[key]
|
|
64
56
|
end
|
|
@@ -137,7 +129,19 @@ module Bard
|
|
|
137
129
|
return nil if @ci_system == false
|
|
138
130
|
|
|
139
131
|
require "bard/ci"
|
|
140
|
-
|
|
132
|
+
|
|
133
|
+
# Use the existing CI class which handles auto-detection
|
|
134
|
+
case @ci_system
|
|
135
|
+
when :local
|
|
136
|
+
CI.new(project_name, branch, local: true)
|
|
137
|
+
when :github_actions, :jenkins, nil
|
|
138
|
+
# CI class auto-detects between github_actions and jenkins
|
|
139
|
+
CI.new(project_name, branch)
|
|
140
|
+
when false
|
|
141
|
+
nil
|
|
142
|
+
else
|
|
143
|
+
CI.new(project_name, branch)
|
|
144
|
+
end
|
|
141
145
|
end
|
|
142
146
|
|
|
143
147
|
private
|
data/lib/bard/copy.rb
CHANGED
|
@@ -29,16 +29,10 @@ module Bard
|
|
|
29
29
|
|
|
30
30
|
ssh_key = ssh_server.ssh_key ? "-i #{ssh_server.ssh_key}" : ""
|
|
31
31
|
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
# scp uses -P for port (uppercase, unlike ssh's -p)
|
|
35
|
-
port = ssh_server.port
|
|
36
|
-
port_opt = port && port.to_s != "22" ? "-P #{port}" : ""
|
|
37
|
-
|
|
38
|
-
from_and_to = [path, target_or_server.scp_uri(path).to_s]
|
|
32
|
+
from_and_to = [path, target_or_server.scp_uri(path)]
|
|
39
33
|
from_and_to.reverse! if direction == :from
|
|
40
34
|
|
|
41
|
-
command = ["scp",
|
|
35
|
+
command = ["scp", gateway, ssh_key, *from_and_to].join(" ")
|
|
42
36
|
Bard::Command.run! command, verbose: verbose
|
|
43
37
|
end
|
|
44
38
|
|
|
@@ -65,7 +59,18 @@ module Bard
|
|
|
65
59
|
# Support both new Target (with server attribute) and old Server
|
|
66
60
|
ssh_server = target_or_server.respond_to?(:server) ? target_or_server.server : target_or_server
|
|
67
61
|
|
|
68
|
-
ssh_uri
|
|
62
|
+
# Get ssh_uri - it might be a URI object (old Server), string (new SSHServer), or mock
|
|
63
|
+
ssh_uri_value = ssh_server.respond_to?(:ssh_uri) ? ssh_server.ssh_uri : nil
|
|
64
|
+
if ssh_uri_value.respond_to?(:port)
|
|
65
|
+
# Already a URI-like object (old Server or mock)
|
|
66
|
+
ssh_uri = ssh_uri_value
|
|
67
|
+
elsif ssh_uri_value.is_a?(String)
|
|
68
|
+
# String from new SSHServer
|
|
69
|
+
ssh_uri = URI("ssh://#{ssh_uri_value}")
|
|
70
|
+
else
|
|
71
|
+
# Fallback
|
|
72
|
+
ssh_uri = ssh_uri_value
|
|
73
|
+
end
|
|
69
74
|
|
|
70
75
|
gateway = ssh_server.gateway ? "-oProxyCommand=\"ssh #{ssh_server.gateway} -W %h:%p\"" : ""
|
|
71
76
|
|
|
@@ -86,13 +91,29 @@ module Bard
|
|
|
86
91
|
|
|
87
92
|
raise NotImplementedError if from_server.gateway || to_server.gateway || from_server.ssh_key || to_server.ssh_key
|
|
88
93
|
|
|
89
|
-
|
|
90
|
-
|
|
94
|
+
# Get ssh_uri - it might be a URI object (old Server), string (new SSHServer), or mock
|
|
95
|
+
from_uri_value = from_server.respond_to?(:ssh_uri) ? from_server.ssh_uri : nil
|
|
96
|
+
if from_uri_value.respond_to?(:port)
|
|
97
|
+
from_uri = from_uri_value
|
|
98
|
+
elsif from_uri_value.is_a?(String)
|
|
99
|
+
from_uri = URI("ssh://#{from_uri_value}")
|
|
100
|
+
else
|
|
101
|
+
from_uri = from_uri_value
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
to_uri_value = to_server.respond_to?(:ssh_uri) ? to_server.ssh_uri : nil
|
|
105
|
+
if to_uri_value.respond_to?(:port)
|
|
106
|
+
to_uri = to_uri_value
|
|
107
|
+
elsif to_uri_value.is_a?(String)
|
|
108
|
+
to_uri = URI("ssh://#{to_uri_value}")
|
|
109
|
+
else
|
|
110
|
+
to_uri = to_uri_value
|
|
111
|
+
end
|
|
91
112
|
|
|
92
113
|
from_str = "-p#{from_uri.port || 22} #{from_uri.user}@#{from_uri.host}"
|
|
93
114
|
to_str = to.rsync_uri(path).sub(%r(/[^/]+$), '/')
|
|
94
115
|
|
|
95
|
-
command = %(ssh -A #{from_str} 'rsync -e \"ssh -A -p#{to_uri.port || 22} -o StrictHostKeyChecking=no
|
|
116
|
+
command = %(ssh -A #{from_str} 'rsync -e \"ssh -A -p#{to_uri.port || 22} -o StrictHostKeyChecking=no\" --delete --info=progress2 -az #{from.path}/#{path} #{to_str}')
|
|
96
117
|
Bard::Command.run! command, verbose: verbose
|
|
97
118
|
end
|
|
98
119
|
end
|
|
@@ -8,7 +8,7 @@ module Bard
|
|
|
8
8
|
class GithubPages < DeployStrategy
|
|
9
9
|
def initialize(target, url = nil, **options)
|
|
10
10
|
super(target)
|
|
11
|
-
@url = url
|
|
11
|
+
@url = url
|
|
12
12
|
@options = options
|
|
13
13
|
|
|
14
14
|
# Auto-configure ping URL if provided
|
|
@@ -65,15 +65,7 @@ module Bard
|
|
|
65
65
|
ensure
|
|
66
66
|
# cleanup
|
|
67
67
|
run! <<~SH
|
|
68
|
-
|
|
69
|
-
if [ -n "$PID" ]; then
|
|
70
|
-
kill $PID 2>/dev/null
|
|
71
|
-
for i in 1 2 3 4 5; do
|
|
72
|
-
kill -0 $PID 2>/dev/null || break
|
|
73
|
-
sleep 1
|
|
74
|
-
done
|
|
75
|
-
kill -9 $PID 2>/dev/null || true
|
|
76
|
-
fi
|
|
68
|
+
cat tmp/pids/server.pid | xargs -I {} kill {}
|
|
77
69
|
rm -rf public/assets
|
|
78
70
|
SH
|
|
79
71
|
end
|
data/lib/bard/deploy_strategy.rb
CHANGED
data/lib/bard/github.rb
CHANGED
|
@@ -3,7 +3,6 @@ require "json"
|
|
|
3
3
|
require "base64"
|
|
4
4
|
require "rbnacl"
|
|
5
5
|
require "bard/ci/retryable"
|
|
6
|
-
require "bard/secrets"
|
|
7
6
|
|
|
8
7
|
module Bard
|
|
9
8
|
class Github < Struct.new(:project_name)
|
|
@@ -108,7 +107,10 @@ module Bard
|
|
|
108
107
|
private
|
|
109
108
|
|
|
110
109
|
def api_key
|
|
111
|
-
@api_key ||=
|
|
110
|
+
@api_key ||= begin
|
|
111
|
+
raw = `git ls-remote -t git@github.com:botandrosedesign/secrets`
|
|
112
|
+
raw[/github-apikey\|(.+)$/, 1]
|
|
113
|
+
end
|
|
112
114
|
end
|
|
113
115
|
|
|
114
116
|
def request path, &block
|
data/lib/bard/provision/apt.rb
CHANGED
|
@@ -7,7 +7,7 @@ class Bard::Provision::Apt < Bard::Provision
|
|
|
7
7
|
%(echo "\\$nrconf{restart} = \\"a\\";" | sudo tee /etc/needrestart/conf.d/90-autorestart.conf),
|
|
8
8
|
"sudo apt-get update -y",
|
|
9
9
|
"sudo apt-get upgrade -y",
|
|
10
|
-
"sudo apt-get install -y curl
|
|
10
|
+
"sudo apt-get install -y curl",
|
|
11
11
|
].join("; "), home: true
|
|
12
12
|
|
|
13
13
|
puts " ✓"
|
|
@@ -5,7 +5,7 @@ class Bard::Provision::LogRotation < Bard::Provision
|
|
|
5
5
|
print "Log Rotation:"
|
|
6
6
|
|
|
7
7
|
provision_server.run! <<~SH, quiet: true
|
|
8
|
-
file=/etc/logrotate.d/#{
|
|
8
|
+
file=/etc/logrotate.d/#{server.project_name}
|
|
9
9
|
if [ ! -f $file ]; then
|
|
10
10
|
sudo tee $file > /dev/null <<EOF
|
|
11
11
|
$(pwd)/log/*.log {
|
data/lib/bard/provision/mysql.rb
CHANGED
|
@@ -7,8 +7,8 @@ class Bard::Provision::MySQL < Bard::Provision
|
|
|
7
7
|
print " Installing,"
|
|
8
8
|
provision_server.run! [
|
|
9
9
|
"sudo apt-get install -y mysql-server",
|
|
10
|
-
%
|
|
11
|
-
%
|
|
10
|
+
%(sudo mysql -uroot -e "ALTER USER \\"'\\"root\\"'\\"@\\"'\\"localhost\\"'\\" IDENTIFIED WITH mysql_native_password BY \\"'\\"\\"'\\", \\"'\\"root\\"'\\"@\\"'\\"localhost\\"'\\" PASSWORD EXPIRE NEVER; FLUSH PRIVILEGES;"),
|
|
11
|
+
%(mysql -uroot -e "UPDATE mysql.user SET password_lifetime = NULL WHERE user = \\"'\\"root\\"'\\" AND host = \\"'\\"localhost\\"'\\";"),
|
|
12
12
|
].join("; "), home: true
|
|
13
13
|
end
|
|
14
14
|
|
|
@@ -9,7 +9,7 @@ class Bard::Provision::Passenger < Bard::Provision
|
|
|
9
9
|
%(grep -qxF "RAILS_ENV=production" /etc/environment || echo "RAILS_ENV=production" | sudo tee -a /etc/environment),
|
|
10
10
|
%(grep -qxF "EDITOR=vim" /etc/environment || echo "EDITOR=vim" | sudo tee -a /etc/environment),
|
|
11
11
|
"sudo apt-get install -y vim dirmngr gnupg apt-transport-https ca-certificates",
|
|
12
|
-
"curl https://oss-binaries.phusionpassenger.com/auto-software-signing-gpg-key
|
|
12
|
+
"curl https://oss-binaries.phusionpassenger.com/auto-software-signing-gpg-key.txt | gpg --dearmor | sudo tee /etc/apt/trusted.gpg.d/phusion.gpg >/dev/null",
|
|
13
13
|
%(echo "deb https://oss-binaries.phusionpassenger.com/apt/passenger jammy main" | sudo tee /etc/apt/sources.list.d/passenger.list),
|
|
14
14
|
"sudo apt-get update -y",
|
|
15
15
|
"sudo apt-get install -y nginx libnginx-mod-http-passenger",
|
|
@@ -30,7 +30,7 @@ class Bard::Provision::Passenger < Bard::Provision
|
|
|
30
30
|
end
|
|
31
31
|
|
|
32
32
|
def app_configured?
|
|
33
|
-
provision_server.run "[ -f /etc/nginx/sites-enabled/#{
|
|
33
|
+
provision_server.run "[ -f /etc/nginx/sites-enabled/#{server.project_name} ]", quiet: true
|
|
34
34
|
end
|
|
35
35
|
end
|
|
36
36
|
|
data/lib/bard/provision/repo.rb
CHANGED
|
@@ -16,7 +16,7 @@ class Bard::Provision::Repo < Bard::Provision
|
|
|
16
16
|
print " Add public key to GitHub repo deploy keys,"
|
|
17
17
|
title = "#{server.ssh_uri.user}@#{server.ssh_uri.host}"
|
|
18
18
|
key = provision_server.run "cat ~/.ssh/id_rsa.pub", home: true
|
|
19
|
-
Bard::Github.new(
|
|
19
|
+
Bard::Github.new(server.project_name).add_deploy_key title:, key:
|
|
20
20
|
end
|
|
21
21
|
print " Cloning repo,"
|
|
22
22
|
provision_server.run! "git clone git@github.com:botandrosedesign/#{project_name}", home: true
|
|
@@ -50,7 +50,7 @@ class Bard::Provision::Repo < Bard::Provision
|
|
|
50
50
|
end
|
|
51
51
|
|
|
52
52
|
def project_name
|
|
53
|
-
|
|
53
|
+
server.project_name
|
|
54
54
|
end
|
|
55
55
|
|
|
56
56
|
def on_latest_master?
|
data/lib/bard/provision/ssh.rb
CHANGED
|
@@ -19,14 +19,7 @@ class Bard::Provision::SSH < Bard::Provision
|
|
|
19
19
|
add_ssh_known_host!(provision_server.ssh_uri)
|
|
20
20
|
end
|
|
21
21
|
print " Reconfiguring port to #{target_port},"
|
|
22
|
-
provision_server.run! %(echo "Port #{target_port}" | sudo tee /etc/ssh/sshd_config.d/port_#{target_port}.conf
|
|
23
|
-
5.times do
|
|
24
|
-
sleep 1
|
|
25
|
-
break if ssh_available?(provision_server.ssh_uri, port: target_port)
|
|
26
|
-
end
|
|
27
|
-
if !ssh_available?(provision_server.ssh_uri, port: target_port)
|
|
28
|
-
raise "reconfigured SSH to port #{target_port} but it's not responding — check firewall and sshd_config Include directive"
|
|
29
|
-
end
|
|
22
|
+
provision_server.run! %(echo "Port #{target_port}" | sudo tee /etc/ssh/sshd_config.d/port_#{target_port}.conf; sudo service ssh restart), home: true
|
|
30
23
|
end
|
|
31
24
|
|
|
32
25
|
if !ssh_known_host?(provision_server.ssh_uri)
|
|
@@ -72,7 +65,7 @@ class Bard::Provision::SSH < Bard::Provision
|
|
|
72
65
|
|
|
73
66
|
def disable_password_auth!
|
|
74
67
|
provision_server.run!(
|
|
75
|
-
%q{echo "PasswordAuthentication no" | sudo tee /etc/ssh/sshd_config.d/disable_password_auth.conf
|
|
68
|
+
%q{echo "PasswordAuthentication no" | sudo tee /etc/ssh/sshd_config.d/disable_password_auth.conf; sudo service ssh restart},
|
|
76
69
|
home: true
|
|
77
70
|
)
|
|
78
71
|
end
|
|
@@ -4,7 +4,7 @@ class Bard::Provision::Swapfile < Bard::Provision
|
|
|
4
4
|
def call
|
|
5
5
|
print "Swapfile:"
|
|
6
6
|
|
|
7
|
-
provision_server.run! <<~SH
|
|
7
|
+
provision_server.run! <<~SH
|
|
8
8
|
if [ ! -f /swapfile ]; then
|
|
9
9
|
sudo fallocate -l $(grep MemTotal /proc/meminfo | awk '{print $2}')K /swapfile
|
|
10
10
|
fi
|
|
@@ -14,8 +14,6 @@ class Bard::Provision::Swapfile < Bard::Provision
|
|
|
14
14
|
grep -q '/swapfile none swap sw 0 0' /etc/fstab || echo '/swapfile none swap sw 0 0' | sudo tee -a /etc/fstab
|
|
15
15
|
SH
|
|
16
16
|
|
|
17
|
-
provision_server.run! "sudo swapon --show | grep -q /swapfile", home: true
|
|
18
|
-
|
|
19
17
|
puts " ✓"
|
|
20
18
|
end
|
|
21
19
|
end
|
data/lib/bard/server.rb
CHANGED
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
require "uri"
|
|
2
2
|
require "bard/command"
|
|
3
3
|
require "bard/copy"
|
|
4
|
-
require "bard/deprecation"
|
|
5
4
|
|
|
6
5
|
module Bard
|
|
7
6
|
class Server < Struct.new(:project_name, :key, :ssh, :path, :ping, :gateway, :ssh_key, :env, :github_pages)
|
|
@@ -25,24 +24,7 @@ module Bard
|
|
|
25
24
|
end
|
|
26
25
|
end
|
|
27
26
|
|
|
28
|
-
|
|
29
|
-
fields.each do |field|
|
|
30
|
-
define_method field do |*args|
|
|
31
|
-
if args.length == 1
|
|
32
|
-
Deprecation.warn message
|
|
33
|
-
send :"#{field}=", args.first
|
|
34
|
-
elsif args.length == 0
|
|
35
|
-
super()
|
|
36
|
-
else
|
|
37
|
-
raise ArgumentError
|
|
38
|
-
end
|
|
39
|
-
end
|
|
40
|
-
end
|
|
41
|
-
end
|
|
42
|
-
|
|
43
|
-
setting :ssh, :ping, :github_pages
|
|
44
|
-
setting_with_deprecation :gateway, :ssh_key, :env,
|
|
45
|
-
message: "Separate SSH options are deprecated; pass as keyword arguments to `ssh` instead, e.g., `ssh \"user@host\", path: \"/app\"` (will be removed in v2.0)"
|
|
27
|
+
setting :ssh, :path, :ping, :gateway, :ssh_key, :env, :github_pages
|
|
46
28
|
|
|
47
29
|
def ping(*args)
|
|
48
30
|
if args.length == 0
|
|
@@ -68,7 +50,6 @@ module Bard
|
|
|
68
50
|
|
|
69
51
|
def path(*args)
|
|
70
52
|
if args.length == 1
|
|
71
|
-
Deprecation.warn "Separate SSH options are deprecated; pass as keyword arguments to `ssh` instead, e.g., `ssh \"user@host\", path: \"/app\"` (will be removed in v2.0)"
|
|
72
53
|
self.path = args.first
|
|
73
54
|
elsif args.length == 0
|
|
74
55
|
super() || project_name
|
|
@@ -77,34 +58,11 @@ module Bard
|
|
|
77
58
|
end
|
|
78
59
|
end
|
|
79
60
|
|
|
80
|
-
def strategy(name)
|
|
81
|
-
Deprecation.warn "`strategy` is deprecated; use the strategy method directly, e.g., `jets \"url\"` instead of `strategy :jets` (will be removed in v2.0)"
|
|
82
|
-
@strategy = name
|
|
83
|
-
end
|
|
84
|
-
|
|
85
|
-
def option(key, value)
|
|
86
|
-
Deprecation.warn "`option` is deprecated; pass options as keyword arguments to the strategy method, e.g., `jets \"url\", run_tests: true` (will be removed in v2.0)"
|
|
87
|
-
@options ||= {}
|
|
88
|
-
@options[key] = value
|
|
89
|
-
end
|
|
90
|
-
|
|
91
|
-
def strategy_name
|
|
92
|
-
@strategy
|
|
93
|
-
end
|
|
94
|
-
|
|
95
|
-
def strategy_options
|
|
96
|
-
@options || {}
|
|
97
|
-
end
|
|
98
|
-
|
|
99
61
|
def ssh_uri which=:ssh
|
|
100
62
|
value = send(which)
|
|
101
63
|
URI("ssh://#{value}")
|
|
102
64
|
end
|
|
103
65
|
|
|
104
|
-
def port
|
|
105
|
-
ssh_uri.port || 22
|
|
106
|
-
end
|
|
107
|
-
|
|
108
66
|
def scp_uri file_path=nil
|
|
109
67
|
ssh_uri.dup.tap do |uri|
|
|
110
68
|
uri.scheme = "scp"
|
|
@@ -135,9 +93,8 @@ module Bard
|
|
|
135
93
|
key
|
|
136
94
|
end
|
|
137
95
|
|
|
138
|
-
def run! command, home: false, verbose: false, quiet: false
|
|
139
|
-
|
|
140
|
-
result if capture
|
|
96
|
+
def run! command, home: false, verbose: false, quiet: false
|
|
97
|
+
Bard::Command.run! command, on: self, home:, verbose:, quiet:
|
|
141
98
|
end
|
|
142
99
|
|
|
143
100
|
def run command, home: false, verbose: false, quiet: false
|
data/lib/bard/ssh_server.rb
CHANGED
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
require "uri"
|
|
2
|
-
require "shellwords"
|
|
3
2
|
require "bard/command"
|
|
4
3
|
|
|
5
4
|
module Bard
|
|
@@ -24,19 +23,13 @@ module Bard
|
|
|
24
23
|
end
|
|
25
24
|
|
|
26
25
|
def ssh_uri
|
|
27
|
-
|
|
26
|
+
"#{user}@#{host}:#{port}"
|
|
28
27
|
end
|
|
29
28
|
|
|
30
29
|
def hostname
|
|
31
30
|
host
|
|
32
31
|
end
|
|
33
32
|
|
|
34
|
-
def to_s
|
|
35
|
-
str = "#{user}@#{host}"
|
|
36
|
-
str += ":#{port}" if port && port != "22"
|
|
37
|
-
str
|
|
38
|
-
end
|
|
39
|
-
|
|
40
33
|
def connection_string
|
|
41
34
|
"#{user}@#{host}"
|
|
42
35
|
end
|
|
@@ -100,7 +93,7 @@ module Bard
|
|
|
100
93
|
remote_cmd += "cd #{path} && " if path
|
|
101
94
|
remote_cmd += command
|
|
102
95
|
|
|
103
|
-
cmd += " #{
|
|
96
|
+
cmd += " '#{remote_cmd}'"
|
|
104
97
|
cmd
|
|
105
98
|
end
|
|
106
99
|
end
|
data/lib/bard/target.rb
CHANGED
|
@@ -2,12 +2,11 @@ require "uri"
|
|
|
2
2
|
require "bard/command"
|
|
3
3
|
require "bard/copy"
|
|
4
4
|
require "bard/deploy_strategy"
|
|
5
|
-
require "bard/deprecation"
|
|
6
5
|
|
|
7
6
|
module Bard
|
|
8
7
|
class Target
|
|
9
|
-
attr_reader :key, :config
|
|
10
|
-
attr_accessor :server
|
|
8
|
+
attr_reader :key, :config, :path
|
|
9
|
+
attr_accessor :server, :gateway, :ssh_key, :env
|
|
11
10
|
|
|
12
11
|
def initialize(key, config)
|
|
13
12
|
@key = key
|
|
@@ -68,7 +67,7 @@ module Bard
|
|
|
68
67
|
|
|
69
68
|
# Auto-configure ping from hostname
|
|
70
69
|
hostname = @server.hostname
|
|
71
|
-
ping(
|
|
70
|
+
ping(hostname) if hostname
|
|
72
71
|
end
|
|
73
72
|
end
|
|
74
73
|
|
|
@@ -79,46 +78,17 @@ module Bard
|
|
|
79
78
|
# Path configuration
|
|
80
79
|
def path(new_path = nil)
|
|
81
80
|
if new_path
|
|
82
|
-
Deprecation.warn "Separate `path` call is deprecated; pass as keyword argument to `ssh` instead, e.g., `ssh \"user@host\", path: \"#{new_path}\"` (will be removed in v2.0)"
|
|
83
81
|
@path = new_path
|
|
84
82
|
else
|
|
85
83
|
@path || config.project_name
|
|
86
84
|
end
|
|
87
85
|
end
|
|
88
86
|
|
|
89
|
-
# Deprecated separate setter methods - use ssh(..., option: value) instead
|
|
90
|
-
def gateway(value = nil)
|
|
91
|
-
if value
|
|
92
|
-
Deprecation.warn "Separate `gateway` call is deprecated; pass as keyword argument to `ssh` instead, e.g., `ssh \"user@host\", gateway: \"#{value}\"` (will be removed in v2.0)"
|
|
93
|
-
@gateway = value
|
|
94
|
-
else
|
|
95
|
-
@gateway
|
|
96
|
-
end
|
|
97
|
-
end
|
|
98
|
-
|
|
99
|
-
def ssh_key(value = nil)
|
|
100
|
-
if value
|
|
101
|
-
Deprecation.warn "Separate `ssh_key` call is deprecated; pass as keyword argument to `ssh` instead, e.g., `ssh \"user@host\", ssh_key: \"#{value}\"` (will be removed in v2.0)"
|
|
102
|
-
@ssh_key = value
|
|
103
|
-
else
|
|
104
|
-
@ssh_key
|
|
105
|
-
end
|
|
106
|
-
end
|
|
107
|
-
|
|
108
|
-
def env(value = nil)
|
|
109
|
-
if value
|
|
110
|
-
Deprecation.warn "Separate `env` call is deprecated; pass as keyword argument to `ssh` instead, e.g., `ssh \"user@host\", env: \"#{value}\"` (will be removed in v2.0)"
|
|
111
|
-
@env = value
|
|
112
|
-
else
|
|
113
|
-
@env
|
|
114
|
-
end
|
|
115
|
-
end
|
|
116
|
-
|
|
117
87
|
# Ping configuration
|
|
118
88
|
def ping(*urls)
|
|
119
89
|
if urls.empty?
|
|
120
|
-
# Getter
|
|
121
|
-
@ping_urls
|
|
90
|
+
# Getter
|
|
91
|
+
@ping_urls
|
|
122
92
|
elsif urls.first == false
|
|
123
93
|
# Disable ping
|
|
124
94
|
@ping_urls = []
|
|
@@ -164,18 +134,6 @@ module Bard
|
|
|
164
134
|
end
|
|
165
135
|
end
|
|
166
136
|
|
|
167
|
-
# Deprecated strategy configuration methods
|
|
168
|
-
def strategy(name)
|
|
169
|
-
Deprecation.warn "`strategy` is deprecated; use the strategy method directly, e.g., `#{name} \"url\"` instead of `strategy :#{name}` (will be removed in v2.0)"
|
|
170
|
-
@deploy_strategy = name
|
|
171
|
-
end
|
|
172
|
-
|
|
173
|
-
def option(key, value)
|
|
174
|
-
Deprecation.warn "`option` is deprecated; pass options as keyword arguments to the strategy method, e.g., `jets \"url\", #{key}: #{value.inspect}` (will be removed in v2.0)"
|
|
175
|
-
@strategy_options_hash[@deploy_strategy] ||= {}
|
|
176
|
-
@strategy_options_hash[@deploy_strategy][key] = value
|
|
177
|
-
end
|
|
178
|
-
|
|
179
137
|
def strategy_options(strategy_name)
|
|
180
138
|
@strategy_options_hash[strategy_name] || {}
|
|
181
139
|
end
|
|
@@ -217,44 +175,44 @@ module Bard
|
|
|
217
175
|
end
|
|
218
176
|
|
|
219
177
|
# Remote command execution
|
|
220
|
-
def run!(command, home: false, verbose: false, quiet: false
|
|
178
|
+
def run!(command, home: false, verbose: false, quiet: false)
|
|
221
179
|
require_capability!(:ssh)
|
|
222
|
-
|
|
223
|
-
result if capture
|
|
180
|
+
Command.run!(command, on: server, home: home, verbose: verbose, quiet: quiet)
|
|
224
181
|
end
|
|
225
182
|
|
|
226
183
|
def run(command, home: false, verbose: false, quiet: false)
|
|
227
184
|
require_capability!(:ssh)
|
|
228
|
-
Command.run(command, on:
|
|
185
|
+
Command.run(command, on: server, home: home, verbose: verbose, quiet: quiet)
|
|
229
186
|
end
|
|
230
187
|
|
|
231
188
|
def exec!(command, home: false)
|
|
232
189
|
require_capability!(:ssh)
|
|
233
|
-
Command.exec!(command, on:
|
|
190
|
+
Command.exec!(command, on: server, home: home)
|
|
234
191
|
end
|
|
235
192
|
|
|
236
193
|
# File transfer
|
|
237
194
|
def copy_file(path, to:, verbose: false)
|
|
238
195
|
require_capability!(:ssh)
|
|
239
|
-
to.require_capability!(:ssh)
|
|
196
|
+
to.require_capability!(:ssh)
|
|
240
197
|
Copy.file(path, from: self, to: to, verbose: verbose)
|
|
241
198
|
end
|
|
242
199
|
|
|
243
200
|
def copy_dir(path, to:, verbose: false)
|
|
244
201
|
require_capability!(:ssh)
|
|
245
|
-
to.require_capability!(:ssh)
|
|
202
|
+
to.require_capability!(:ssh)
|
|
246
203
|
Copy.dir(path, from: self, to: to, verbose: verbose)
|
|
247
204
|
end
|
|
248
205
|
|
|
249
206
|
# URI methods for compatibility
|
|
250
207
|
def scp_uri(file_path = nil)
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
208
|
+
uri = URI("scp://#{ssh_uri}")
|
|
209
|
+
uri.path = "/#{path}"
|
|
210
|
+
uri.path += "/#{file_path}" if file_path
|
|
211
|
+
uri
|
|
254
212
|
end
|
|
255
213
|
|
|
256
214
|
def rsync_uri(file_path = nil)
|
|
257
|
-
uri = ssh_uri
|
|
215
|
+
uri = URI("ssh://#{ssh_uri}")
|
|
258
216
|
str = "#{uri.user}@#{uri.host}"
|
|
259
217
|
str += ":#{path}"
|
|
260
218
|
str += "/#{file_path}" if file_path
|
|
@@ -277,14 +235,5 @@ module Bard
|
|
|
277
235
|
end
|
|
278
236
|
end
|
|
279
237
|
end
|
|
280
|
-
|
|
281
|
-
private
|
|
282
|
-
|
|
283
|
-
def normalize_ping(value)
|
|
284
|
-
return nil if value == false || value.nil?
|
|
285
|
-
normalized = value.to_s
|
|
286
|
-
normalized = "https://#{normalized}" unless normalized.start_with?("http")
|
|
287
|
-
normalized
|
|
288
|
-
end
|
|
289
238
|
end
|
|
290
239
|
end
|
data/lib/bard/version.rb
CHANGED
|
@@ -3,11 +3,10 @@ FROM ubuntu:22.04
|
|
|
3
3
|
# Prevent interactive prompts
|
|
4
4
|
ENV DEBIAN_FRONTEND=noninteractive
|
|
5
5
|
|
|
6
|
-
# Install SSH server
|
|
6
|
+
# Install SSH server and basic tools
|
|
7
7
|
RUN apt-get update && \
|
|
8
8
|
apt-get install -y \
|
|
9
9
|
openssh-server \
|
|
10
|
-
git \
|
|
11
10
|
sudo \
|
|
12
11
|
&& rm -rf /var/lib/apt/lists/*
|
|
13
12
|
|