Skip to content

Commit

Permalink
Merge tag 'v1.7.3' into skip-shell-option-if-nil
Browse files Browse the repository at this point in the history
  • Loading branch information
xiaohui-zhangxh committed Jul 12, 2024
2 parents c7b3f68 + 9a1379b commit 3dc5659
Show file tree
Hide file tree
Showing 121 changed files with 3,648 additions and 1,169 deletions.
12 changes: 9 additions & 3 deletions Gemfile.lock
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
PATH
remote: .
specs:
kamal (1.4.0)
kamal (1.7.3)
activesupport (>= 7.0)
base64 (~> 0.2)
bcrypt_pbkdf (~> 1.0)
concurrent-ruby (~> 1.2)
dotenv (~> 2.8)
ed25519 (~> 1.2)
net-ssh (~> 7.0)
sshkit (~> 1.21)
sshkit (>= 1.22.2, < 2.0)
thor (~> 1.2)
x25519 (~> 1.0, >= 1.0.10)
zeitwerk (~> 2.5)

GEM
Expand Down Expand Up @@ -75,6 +76,8 @@ GEM
mutex_m (0.2.0)
net-scp (4.0.0)
net-ssh (>= 2.6.5, < 8.0.0)
net-sftp (4.0.0)
net-ssh (>= 5.0.0, < 8.0.0)
net-ssh (7.2.1)
nokogiri (1.16.0-arm64-darwin)
racc (~> 1.4)
Expand Down Expand Up @@ -151,16 +154,19 @@ GEM
rubocop-rails
ruby-progressbar (1.13.0)
ruby2_keywords (0.0.5)
sshkit (1.21.7)
sshkit (1.22.2)
base64
mutex_m
net-scp (>= 1.1.2)
net-sftp (>= 2.1.2)
net-ssh (>= 2.8.0)
stringio (3.1.0)
thor (1.3.0)
tzinfo (2.0.6)
concurrent-ruby (~> 1.0)
unicode-display_width (2.5.0)
webrick (1.8.1)
x25519 (1.0.10)
zeitwerk (2.6.12)

PLATFORMS
Expand Down
134 changes: 134 additions & 0 deletions bin/docs
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
#!/usr/bin/env ruby
require "stringio"

def usage
puts "Usage: #{$0} <kamal_site_repo>"
exit 1
end

usage if ARGV.size != 1

kamal_site_repo = ARGV[0]

if !File.directory?(kamal_site_repo)
puts "Error: #{kamal_site_repo} is not a directory"
exit 1
end

DOCS = {
"accessory" => "Accessories",
"boot" => "Booting",
"builder" => "Builders",
"configuration" => "Configuration overview",
"env" => "Environment variables",
"healthcheck" => "Healthchecks",
"logging" => "Logging",
"registry" => "Docker Registry",
"role" => "Roles",
"servers" => "Servers",
"ssh" => "SSH",
"sshkit" => "SSHKit",
"traefik" => "Traefik"
}

class DocWriter
attr_reader :from_file, :to_file, :key, :heading, :body, :output, :in_yaml

def initialize(from_file, to_dir)
@from_file = from_file
@key = File.basename(from_file, ".yml")
@to_file = File.join(to_dir, "#{linkify(DOCS[key])}.md")
@body = File.readlines(from_file)
@heading = body.shift.chomp("\n")
@output = nil
end

def write
puts "Writing #{to_file}"
generate_markdown
File.write(to_file, output.string)
end

private
def generate_markdown
@output = StringIO.new

generate_header

place = :in_section

loop do
line = body.shift&.chomp("\n")
break if line.nil?

case place
when :new_section, :in_section
if line.empty?
output.puts
place = :new_section
elsif line =~ /^ *#/
generate_line(line, place: place)
place = :in_section
else
output.puts "```yaml"
output.print line
place = :in_yaml
end
when :in_yaml
if line =~ /^ *#/
output.puts "```"
generate_line(line, place: :new_section)
place = :in_section
else
output.puts
output.print line
end
end
end

output.puts "\n```" if place == :in_yaml
end

def generate_header
output.puts "---"
output.puts "title: #{heading[2..-1]}"
output.puts "---"
output.puts
output.puts heading
output.puts
end

def generate_line(line, place: :in_section)
line = line.gsub(/^ *#\s?/, "")

if line =~ /(.*)kamal docs ([a-z]*)(.*)/
line = "#{$1}[#{DOCS[$2]}](../#{linkify(DOCS[$2])})#{$3}"
end

if line =~ /(.*)https:\/\/kamal-deploy.org([a-z\/-]*)(.*)/
line = "#{$1}[#{titlify($2.split("/").last)}](#{$2})#{$3}"
end

if place == :new_section
output.puts "## [#{line}](##{linkify(line)})"
else
output.puts line
end
end

def linkify(text)
text.downcase.gsub(" ", "-")
end

def titlify(text)
text.capitalize.gsub("-", " ")
end
end

from_dir = File.join(File.dirname(__FILE__), "../lib/kamal/configuration/docs")
to_dir = File.join(kamal_site_repo, "docs/configuration")
Dir.glob("#{from_dir}/*") do |from_file|
key = File.basename(from_file, ".yml")

DocWriter.new(from_file, to_dir).write
end
3 changes: 2 additions & 1 deletion kamal.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,13 @@ Gem::Specification.new do |spec|
spec.executables = %w[ kamal ]

spec.add_dependency "activesupport", ">= 7.0"
spec.add_dependency "sshkit", "~> 1.21"
spec.add_dependency "sshkit", ">= 1.22.2", "< 2.0"
spec.add_dependency "net-ssh", "~> 7.0"
spec.add_dependency "thor", "~> 1.2"
spec.add_dependency "dotenv", "~> 2.8"
spec.add_dependency "zeitwerk", "~> 2.5"
spec.add_dependency "ed25519", "~> 1.2"
spec.add_dependency "x25519", "~> 1.0", ">= 1.0.10"
spec.add_dependency "bcrypt_pbkdf", "~> 1.0"
spec.add_dependency "concurrent-ruby", "~> 1.2"
spec.add_dependency "base64", "~> 0.2"
Expand Down
2 changes: 2 additions & 0 deletions lib/kamal.rb
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
module Kamal
class ConfigurationError < StandardError; end
end

require "active_support"
require "zeitwerk"
require "yaml"

loader = Zeitwerk::Loader.for_gem
loader.ignore(File.join(__dir__, "kamal", "sshkit_with_ext.rb"))
Expand Down
2 changes: 1 addition & 1 deletion lib/kamal/cli.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
module Kamal::Cli
class LockError < StandardError; end
class HookError < StandardError; end
class LockError < StandardError; end
end

# SSHKit uses instance eval, so we need a global const for ergonomics
Expand Down
57 changes: 32 additions & 25 deletions lib/kamal/cli/accessory.rb
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
class Kamal::Cli::Accessory < Kamal::Cli::Base
desc "boot [NAME]", "Boot new accessory service on host (use NAME=all to boot all accessories)"
def boot(name, login: true)
mutating do
with_lock do
if name == "all"
KAMAL.accessory_names.each { |accessory_name| boot(accessory_name) }
else
Expand All @@ -21,7 +21,7 @@ def boot(name, login: true)

desc "upload [NAME]", "Upload accessory files to host", hide: true
def upload(name)
mutating do
with_lock do
with_accessory(name) do |accessory, hosts|
on(hosts) do
accessory.files.each do |(local, remote)|
Expand All @@ -38,7 +38,7 @@ def upload(name)

desc "directories [NAME]", "Create accessory directories on host", hide: true
def directories(name)
mutating do
with_lock do
with_accessory(name) do |accessory, hosts|
on(hosts) do
accessory.directories.keys.each do |host_path|
Expand All @@ -51,7 +51,7 @@ def directories(name)

desc "reboot [NAME]", "Reboot existing accessory on host (stop container, remove container, start new container; use NAME=all to boot all accessories)"
def reboot(name)
mutating do
with_lock do
if name == "all"
KAMAL.accessory_names.each { |accessory_name| reboot(accessory_name) }
else
Expand All @@ -70,7 +70,7 @@ def reboot(name)

desc "start [NAME]", "Start existing accessory container on host"
def start(name)
mutating do
with_lock do
with_accessory(name) do |accessory, hosts|
on(hosts) do
execute *KAMAL.auditor.record("Started #{name} accessory"), verbosity: :debug
Expand All @@ -82,7 +82,7 @@ def start(name)

desc "stop [NAME]", "Stop existing accessory container on host"
def stop(name)
mutating do
with_lock do
with_accessory(name) do |accessory, hosts|
on(hosts) do
execute *KAMAL.auditor.record("Stopped #{name} accessory"), verbosity: :debug
Expand All @@ -94,7 +94,7 @@ def stop(name)

desc "restart [NAME]", "Restart existing accessory container on host"
def restart(name)
mutating do
with_lock do
with_accessory(name) do
stop(name)
start(name)
Expand All @@ -107,8 +107,9 @@ def details(name)
if name == "all"
KAMAL.accessory_names.each { |accessory_name| details(accessory_name) }
else
type = "Accessory #{name}"
with_accessory(name) do |accessory, hosts|
on(hosts) { puts capture_with_info(*accessory.info) }
on(hosts) { puts_by_host host, capture_with_info(*accessory.info), type: type }
end
end
end
Expand Down Expand Up @@ -148,23 +149,25 @@ def exec(name, cmd)
option :since, aliases: "-s", desc: "Show logs since timestamp (e.g. 2013-01-02T13:23:37Z) or relative (e.g. 42m for 42 minutes)"
option :lines, type: :numeric, aliases: "-n", desc: "Number of log lines to pull from each server"
option :grep, aliases: "-g", desc: "Show lines with grep match only (use this to fetch specific requests by id)"
option :grep_options, aliases: "-o", desc: "Additional options supplied to grep"
option :follow, aliases: "-f", desc: "Follow logs on primary server (or specific host set by --hosts)"
def logs(name)
with_accessory(name) do |accessory, hosts|
grep = options[:grep]
grep_options = options[:grep_options]

if options[:follow]
run_locally do
info "Following logs on #{hosts}..."
info accessory.follow_logs(grep: grep)
exec accessory.follow_logs(grep: grep)
info accessory.follow_logs(grep: grep, grep_options: grep_options)
exec accessory.follow_logs(grep: grep, grep_options: grep_options)
end
else
since = options[:since]
lines = options[:lines].presence || ((since || grep) ? nil : 100) # Default to 100 lines if since or grep isn't set

on(hosts) do
puts capture_with_info(*accessory.logs(since: since, lines: lines, grep: grep))
puts capture_with_info(*accessory.logs(since: since, lines: lines, grep: grep, grep_options: grep_options))
end
end
end
Expand All @@ -173,25 +176,20 @@ def logs(name)
desc "remove [NAME]", "Remove accessory container, image and data directory from host (use NAME=all to remove all accessories)"
option :confirmed, aliases: "-y", type: :boolean, default: false, desc: "Proceed without confirmation question"
def remove(name)
mutating do
if name == "all"
KAMAL.accessory_names.each { |accessory_name| remove(accessory_name) }
else
confirming "This will remove all containers, images and data directories for #{name}. Are you sure?" do
with_accessory(name) do
stop(name)
remove_container(name)
remove_image(name)
remove_service_directory(name)
end
confirming "This will remove all containers, images and data directories for #{name}. Are you sure?" do
with_lock do
if name == "all"
KAMAL.accessory_names.each { |accessory_name| remove_accessory(accessory_name) }
else
remove_accessory(name)
end
end
end
end

desc "remove_container [NAME]", "Remove accessory container from host", hide: true
def remove_container(name)
mutating do
with_lock do
with_accessory(name) do |accessory, hosts|
on(hosts) do
execute *KAMAL.auditor.record("Remove #{name} accessory container"), verbosity: :debug
Expand All @@ -203,7 +201,7 @@ def remove_container(name)

desc "remove_image [NAME]", "Remove accessory image from host", hide: true
def remove_image(name)
mutating do
with_lock do
with_accessory(name) do |accessory, hosts|
on(hosts) do
execute *KAMAL.auditor.record("Removed #{name} accessory image"), verbosity: :debug
Expand All @@ -215,7 +213,7 @@ def remove_image(name)

desc "remove_service_directory [NAME]", "Remove accessory directory used for uploaded files and data directories from host", hide: true
def remove_service_directory(name)
mutating do
with_lock do
with_accessory(name) do |accessory, hosts|
on(hosts) do
execute *accessory.remove_service_directory
Expand Down Expand Up @@ -249,4 +247,13 @@ def accessory_hosts(accessory)
accessory.hosts
end
end

def remove_accessory(name)
with_accessory(name) do
stop(name)
remove_container(name)
remove_image(name)
remove_service_directory(name)
end
end
end
Loading

0 comments on commit 3dc5659

Please sign in to comment.