Merge branch 'main' into feat/custom-ssl
This commit is contained in:
4
.github/workflows/ci.yml
vendored
4
.github/workflows/ci.yml
vendored
@@ -26,16 +26,12 @@ jobs:
|
|||||||
fail-fast: false
|
fail-fast: false
|
||||||
matrix:
|
matrix:
|
||||||
ruby-version:
|
ruby-version:
|
||||||
- "3.1"
|
|
||||||
- "3.2"
|
- "3.2"
|
||||||
- "3.3"
|
- "3.3"
|
||||||
- "3.4"
|
- "3.4"
|
||||||
gemfile:
|
gemfile:
|
||||||
- Gemfile
|
- Gemfile
|
||||||
- gemfiles/rails_edge.gemfile
|
- gemfiles/rails_edge.gemfile
|
||||||
exclude:
|
|
||||||
- ruby-version: "3.1"
|
|
||||||
gemfile: gemfiles/rails_edge.gemfile
|
|
||||||
name: ${{ format('Tests (Ruby {0})', matrix.ruby-version) }}
|
name: ${{ format('Tests (Ruby {0})', matrix.ruby-version) }}
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
env:
|
env:
|
||||||
|
|||||||
@@ -1,13 +1,13 @@
|
|||||||
PATH
|
PATH
|
||||||
remote: .
|
remote: .
|
||||||
specs:
|
specs:
|
||||||
kamal (2.5.3)
|
kamal (2.6.1)
|
||||||
activesupport (>= 7.0)
|
activesupport (>= 7.0)
|
||||||
base64 (~> 0.2)
|
base64 (~> 0.2)
|
||||||
bcrypt_pbkdf (~> 1.0)
|
bcrypt_pbkdf (~> 1.0)
|
||||||
concurrent-ruby (~> 1.2)
|
concurrent-ruby (~> 1.2)
|
||||||
dotenv (~> 3.1)
|
dotenv (~> 3.1)
|
||||||
ed25519 (~> 1.2)
|
ed25519 (~> 1.4)
|
||||||
net-ssh (~> 7.3)
|
net-ssh (~> 7.3)
|
||||||
sshkit (>= 1.23.0, < 2.0)
|
sshkit (>= 1.23.0, < 2.0)
|
||||||
thor (~> 1.3)
|
thor (~> 1.3)
|
||||||
@@ -60,7 +60,7 @@ GEM
|
|||||||
reline (>= 0.3.8)
|
reline (>= 0.3.8)
|
||||||
dotenv (3.1.5)
|
dotenv (3.1.5)
|
||||||
drb (2.2.1)
|
drb (2.2.1)
|
||||||
ed25519 (1.3.0)
|
ed25519 (1.4.0)
|
||||||
erubi (1.13.0)
|
erubi (1.13.0)
|
||||||
i18n (1.14.6)
|
i18n (1.14.6)
|
||||||
concurrent-ruby (~> 1.0)
|
concurrent-ruby (~> 1.0)
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ Gem::Specification.new do |spec|
|
|||||||
spec.add_dependency "thor", "~> 1.3"
|
spec.add_dependency "thor", "~> 1.3"
|
||||||
spec.add_dependency "dotenv", "~> 3.1"
|
spec.add_dependency "dotenv", "~> 3.1"
|
||||||
spec.add_dependency "zeitwerk", ">= 2.6.18", "< 3.0"
|
spec.add_dependency "zeitwerk", ">= 2.6.18", "< 3.0"
|
||||||
spec.add_dependency "ed25519", "~> 1.2"
|
spec.add_dependency "ed25519", "~> 1.4"
|
||||||
spec.add_dependency "bcrypt_pbkdf", "~> 1.0"
|
spec.add_dependency "bcrypt_pbkdf", "~> 1.0"
|
||||||
spec.add_dependency "concurrent-ruby", "~> 1.2"
|
spec.add_dependency "concurrent-ruby", "~> 1.2"
|
||||||
spec.add_dependency "base64", "~> 0.2"
|
spec.add_dependency "base64", "~> 0.2"
|
||||||
|
|||||||
@@ -14,6 +14,10 @@ class Kamal::Cli::Build < Kamal::Cli::Base
|
|||||||
def push
|
def push
|
||||||
cli = self
|
cli = self
|
||||||
|
|
||||||
|
# Ensure pre-connect hooks run before the build, they may needed for a remote builder
|
||||||
|
# or the pre-build hooks.
|
||||||
|
pre_connect_if_required
|
||||||
|
|
||||||
ensure_docker_installed
|
ensure_docker_installed
|
||||||
login_to_registry_locally
|
login_to_registry_locally
|
||||||
|
|
||||||
|
|||||||
@@ -31,6 +31,8 @@ class Kamal::Cli::Proxy < Kamal::Cli::Base
|
|||||||
option :registry, type: :string, default: nil, desc: "Registry to use for the proxy image"
|
option :registry, type: :string, default: nil, desc: "Registry to use for the proxy image"
|
||||||
option :repository, type: :string, default: nil, desc: "Repository for the proxy image"
|
option :repository, type: :string, default: nil, desc: "Repository for the proxy image"
|
||||||
option :image_version, type: :string, default: nil, desc: "Version of the proxy to run"
|
option :image_version, type: :string, default: nil, desc: "Version of the proxy to run"
|
||||||
|
option :metrics_port, type: :numeric, default: nil, desc: "Port to report prometheus metrics on"
|
||||||
|
option :debug, type: :boolean, default: false, desc: "Whether to run the proxy in debug mode"
|
||||||
option :docker_options, type: :array, default: [], desc: "Docker options to pass to the proxy container", banner: "option=value option2=value2"
|
option :docker_options, type: :array, default: [], desc: "Docker options to pass to the proxy container", banner: "option=value option2=value2"
|
||||||
def boot_config(subcommand)
|
def boot_config(subcommand)
|
||||||
proxy_boot_config = KAMAL.config.proxy_boot
|
proxy_boot_config = KAMAL.config.proxy_boot
|
||||||
@@ -40,6 +42,7 @@ class Kamal::Cli::Proxy < Kamal::Cli::Base
|
|||||||
boot_options = [
|
boot_options = [
|
||||||
*(proxy_boot_config.publish_args(options[:http_port], options[:https_port], options[:publish_host_ip]) if options[:publish]),
|
*(proxy_boot_config.publish_args(options[:http_port], options[:https_port], options[:publish_host_ip]) if options[:publish]),
|
||||||
*(proxy_boot_config.logging_args(options[:log_max_size])),
|
*(proxy_boot_config.logging_args(options[:log_max_size])),
|
||||||
|
*("--expose=#{options[:metrics_port]}" if options[:metrics_port]),
|
||||||
*options[:docker_options].map { |option| "--#{option}" }
|
*options[:docker_options].map { |option| "--#{option}" }
|
||||||
]
|
]
|
||||||
|
|
||||||
@@ -51,6 +54,9 @@ class Kamal::Cli::Proxy < Kamal::Cli::Base
|
|||||||
|
|
||||||
image_version = options[:image_version]
|
image_version = options[:image_version]
|
||||||
|
|
||||||
|
run_command_options = { debug: options[:debug] || nil, "metrics-port": options[:metrics_port] }.compact
|
||||||
|
run_command = "kamal-proxy run #{Kamal::Utils.optionize(run_command_options).join(" ")}" if run_command_options.any?
|
||||||
|
|
||||||
on(KAMAL.proxy_hosts) do |host|
|
on(KAMAL.proxy_hosts) do |host|
|
||||||
execute(*KAMAL.proxy.ensure_proxy_directory)
|
execute(*KAMAL.proxy.ensure_proxy_directory)
|
||||||
if boot_options != proxy_boot_config.default_boot_options
|
if boot_options != proxy_boot_config.default_boot_options
|
||||||
@@ -70,6 +76,12 @@ class Kamal::Cli::Proxy < Kamal::Cli::Base
|
|||||||
else
|
else
|
||||||
execute *KAMAL.proxy.reset_image_version, raise_on_non_zero_exit: false
|
execute *KAMAL.proxy.reset_image_version, raise_on_non_zero_exit: false
|
||||||
end
|
end
|
||||||
|
|
||||||
|
if run_command
|
||||||
|
upload! StringIO.new(run_command), proxy_boot_config.run_command_file
|
||||||
|
else
|
||||||
|
execute *KAMAL.proxy.reset_run_command, raise_on_non_zero_exit: false
|
||||||
|
end
|
||||||
end
|
end
|
||||||
when "get"
|
when "get"
|
||||||
|
|
||||||
@@ -81,6 +93,7 @@ class Kamal::Cli::Proxy < Kamal::Cli::Base
|
|||||||
execute *KAMAL.proxy.reset_boot_options, raise_on_non_zero_exit: false
|
execute *KAMAL.proxy.reset_boot_options, raise_on_non_zero_exit: false
|
||||||
execute *KAMAL.proxy.reset_image, raise_on_non_zero_exit: false
|
execute *KAMAL.proxy.reset_image, raise_on_non_zero_exit: false
|
||||||
execute *KAMAL.proxy.reset_image_version, raise_on_non_zero_exit: false
|
execute *KAMAL.proxy.reset_image_version, raise_on_non_zero_exit: false
|
||||||
|
execute *KAMAL.proxy.reset_run_command, raise_on_non_zero_exit: false
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
raise ArgumentError, "Unknown boot_config subcommand #{subcommand}"
|
raise ArgumentError, "Unknown boot_config subcommand #{subcommand}"
|
||||||
@@ -107,18 +120,6 @@ class Kamal::Cli::Proxy < Kamal::Cli::Base
|
|||||||
execute *KAMAL.proxy.ensure_apps_config_directory
|
execute *KAMAL.proxy.ensure_apps_config_directory
|
||||||
|
|
||||||
execute *KAMAL.proxy.run
|
execute *KAMAL.proxy.run
|
||||||
|
|
||||||
KAMAL.roles_on(host).select(&:running_proxy?).each do |role|
|
|
||||||
app = KAMAL.app(role: role, host: host)
|
|
||||||
|
|
||||||
version = capture_with_info(*app.current_running_version, raise_on_non_zero_exit: false).strip
|
|
||||||
endpoint = capture_with_info(*app.container_id_for_version(version)).strip
|
|
||||||
|
|
||||||
if endpoint.present?
|
|
||||||
info "Deploying #{endpoint} for role `#{role}` on #{host}..."
|
|
||||||
execute *app.deploy(target: endpoint)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
run_hook "post-proxy-reboot", hosts: host_list
|
run_hook "post-proxy-reboot", hosts: host_list
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -7,7 +7,7 @@
|
|||||||
# KAMAL_PERFORMER
|
# KAMAL_PERFORMER
|
||||||
# KAMAL_VERSION
|
# KAMAL_VERSION
|
||||||
# KAMAL_HOSTS
|
# KAMAL_HOSTS
|
||||||
# KAMAL_ROLE (if set)
|
# KAMAL_ROLES (if set)
|
||||||
# KAMAL_DESTINATION (if set)
|
# KAMAL_DESTINATION (if set)
|
||||||
# KAMAL_RUNTIME
|
# KAMAL_RUNTIME
|
||||||
|
|
||||||
|
|||||||
@@ -13,7 +13,7 @@
|
|||||||
# KAMAL_PERFORMER
|
# KAMAL_PERFORMER
|
||||||
# KAMAL_VERSION
|
# KAMAL_VERSION
|
||||||
# KAMAL_HOSTS
|
# KAMAL_HOSTS
|
||||||
# KAMAL_ROLE (if set)
|
# KAMAL_ROLES (if set)
|
||||||
# KAMAL_DESTINATION (if set)
|
# KAMAL_DESTINATION (if set)
|
||||||
|
|
||||||
if [ -n "$(git status --porcelain)" ]; then
|
if [ -n "$(git status --porcelain)" ]; then
|
||||||
|
|||||||
@@ -9,7 +9,7 @@
|
|||||||
# KAMAL_PERFORMER
|
# KAMAL_PERFORMER
|
||||||
# KAMAL_VERSION
|
# KAMAL_VERSION
|
||||||
# KAMAL_HOSTS
|
# KAMAL_HOSTS
|
||||||
# KAMAL_ROLE (if set)
|
# KAMAL_ROLES (if set)
|
||||||
# KAMAL_DESTINATION (if set)
|
# KAMAL_DESTINATION (if set)
|
||||||
# KAMAL_RUNTIME
|
# KAMAL_RUNTIME
|
||||||
|
|
||||||
|
|||||||
@@ -13,7 +13,7 @@
|
|||||||
# KAMAL_HOSTS
|
# KAMAL_HOSTS
|
||||||
# KAMAL_COMMAND
|
# KAMAL_COMMAND
|
||||||
# KAMAL_SUBCOMMAND
|
# KAMAL_SUBCOMMAND
|
||||||
# KAMAL_ROLE (if set)
|
# KAMAL_ROLES (if set)
|
||||||
# KAMAL_DESTINATION (if set)
|
# KAMAL_DESTINATION (if set)
|
||||||
|
|
||||||
# Only check the build status for production deployments
|
# Only check the build status for production deployments
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ class Kamal::Commander::Specifics
|
|||||||
@primary_role = primary_or_first_role(roles_on(primary_host))
|
@primary_role = primary_or_first_role(roles_on(primary_host))
|
||||||
|
|
||||||
stable_sort!(roles) { |role| role == primary_role ? 0 : 1 }
|
stable_sort!(roles) { |role| role == primary_role ? 0 : 1 }
|
||||||
stable_sort!(hosts) { |host| roles_on(host).any? { |role| role == primary_role } ? 0 : 1 }
|
sort_primary_role_hosts_first!(hosts)
|
||||||
end
|
end
|
||||||
|
|
||||||
def roles_on(host)
|
def roles_on(host)
|
||||||
@@ -19,7 +19,7 @@ class Kamal::Commander::Specifics
|
|||||||
end
|
end
|
||||||
|
|
||||||
def app_hosts
|
def app_hosts
|
||||||
config.app_hosts & specified_hosts
|
@app_hosts ||= sort_primary_role_hosts_first!(config.app_hosts & specified_hosts)
|
||||||
end
|
end
|
||||||
|
|
||||||
def proxy_hosts
|
def proxy_hosts
|
||||||
@@ -55,4 +55,8 @@ class Kamal::Commander::Specifics
|
|||||||
specified_hosts
|
specified_hosts
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def sort_primary_role_hosts_first!(hosts)
|
||||||
|
stable_sort!(hosts) { |host| roles_on(host).any? { |role| role == primary_role } ? 0 : 1 }
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -70,7 +70,7 @@ class Kamal::Commands::Proxy < Kamal::Commands::Base
|
|||||||
end
|
end
|
||||||
|
|
||||||
def boot_config
|
def boot_config
|
||||||
[ :echo, "#{substitute(read_boot_options)} #{substitute(read_image)}:#{substitute(read_image_version)}" ]
|
[ :echo, "#{substitute(read_boot_options)} #{substitute(read_image)}:#{substitute(read_image_version)} #{substitute(read_run_command)}" ]
|
||||||
end
|
end
|
||||||
|
|
||||||
def read_boot_options
|
def read_boot_options
|
||||||
@@ -85,6 +85,10 @@ class Kamal::Commands::Proxy < Kamal::Commands::Base
|
|||||||
read_file(config.proxy_boot.image_version_file, default: Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION)
|
read_file(config.proxy_boot.image_version_file, default: Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def read_run_command
|
||||||
|
read_file(config.proxy_boot.run_command_file)
|
||||||
|
end
|
||||||
|
|
||||||
def reset_boot_options
|
def reset_boot_options
|
||||||
remove_file config.proxy_boot.options_file
|
remove_file config.proxy_boot.options_file
|
||||||
end
|
end
|
||||||
@@ -97,6 +101,10 @@ class Kamal::Commands::Proxy < Kamal::Commands::Base
|
|||||||
remove_file config.proxy_boot.image_version_file
|
remove_file config.proxy_boot.image_version_file
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def reset_run_command
|
||||||
|
remove_file config.proxy_boot.run_command_file
|
||||||
|
end
|
||||||
|
|
||||||
private
|
private
|
||||||
def container_name
|
def container_name
|
||||||
config.proxy_boot.container_name
|
config.proxy_boot.container_name
|
||||||
|
|||||||
@@ -63,7 +63,7 @@ class Kamal::Configuration
|
|||||||
@env = Env.new(config: @raw_config.env || {}, secrets: secrets)
|
@env = Env.new(config: @raw_config.env || {}, secrets: secrets)
|
||||||
|
|
||||||
@logging = Logging.new(logging_config: @raw_config.logging)
|
@logging = Logging.new(logging_config: @raw_config.logging)
|
||||||
@proxy = Proxy.new(config: self, proxy_config: @raw_config.key?(:proxy) ? @raw_config.proxy : {}, secrets: secrets)
|
@proxy = Proxy.new(config: self, proxy_config: @raw_config.proxy, secrets: secrets)
|
||||||
@proxy_boot = Proxy::Boot.new(config: self)
|
@proxy_boot = Proxy::Boot.new(config: self)
|
||||||
@ssh = Ssh.new(config: self)
|
@ssh = Ssh.new(config: self)
|
||||||
@sshkit = Sshkit.new(config: self)
|
@sshkit = Sshkit.new(config: self)
|
||||||
|
|||||||
@@ -32,7 +32,7 @@ class Kamal::Configuration::Accessory
|
|||||||
end
|
end
|
||||||
|
|
||||||
def hosts
|
def hosts
|
||||||
hosts_from_host || hosts_from_hosts || hosts_from_roles
|
hosts_from_host || hosts_from_hosts || hosts_from_roles || hosts_from_tags
|
||||||
end
|
end
|
||||||
|
|
||||||
def port
|
def port
|
||||||
@@ -202,11 +202,31 @@ class Kamal::Configuration::Accessory
|
|||||||
end
|
end
|
||||||
|
|
||||||
def hosts_from_roles
|
def hosts_from_roles
|
||||||
if accessory_config.key?("roles")
|
if accessory_config.key?("role")
|
||||||
|
config.role(accessory_config["role"])&.hosts
|
||||||
|
elsif accessory_config.key?("roles")
|
||||||
accessory_config["roles"].flat_map { |role| config.role(role)&.hosts }
|
accessory_config["roles"].flat_map { |role| config.role(role)&.hosts }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def hosts_from_tags
|
||||||
|
if accessory_config.key?("tag")
|
||||||
|
extract_hosts_from_config_with_tag(accessory_config["tag"])
|
||||||
|
elsif accessory_config.key?("tags")
|
||||||
|
accessory_config["tags"].flat_map { |tag| extract_hosts_from_config_with_tag(tag) }
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def extract_hosts_from_config_with_tag(tag)
|
||||||
|
if (servers_with_roles = config.raw_config.servers).is_a?(Hash)
|
||||||
|
servers_with_roles.flat_map do |role, servers_in_role|
|
||||||
|
servers_in_role.filter_map do |host|
|
||||||
|
host.keys.first if host.is_a?(Hash) && host.values.first.include?(tag)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
def network
|
def network
|
||||||
accessory_config["network"] || DEFAULT_NETWORK
|
accessory_config["network"] || DEFAULT_NETWORK
|
||||||
end
|
end
|
||||||
@@ -214,6 +234,8 @@ class Kamal::Configuration::Accessory
|
|||||||
def ensure_valid_roles
|
def ensure_valid_roles
|
||||||
if accessory_config["roles"] && (missing_roles = accessory_config["roles"] - config.roles.map(&:name)).any?
|
if accessory_config["roles"] && (missing_roles = accessory_config["roles"] - config.roles.map(&:name)).any?
|
||||||
raise Kamal::ConfigurationError, "accessories/#{name}: unknown roles #{missing_roles.join(", ")}"
|
raise Kamal::ConfigurationError, "accessories/#{name}: unknown roles #{missing_roles.join(", ")}"
|
||||||
|
elsif accessory_config["role"] && !config.role(accessory_config["role"])
|
||||||
|
raise Kamal::ConfigurationError, "accessories/#{name}: unknown role #{accessory_config["role"]}"
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -46,13 +46,18 @@ accessories:
|
|||||||
|
|
||||||
# Accessory hosts
|
# Accessory hosts
|
||||||
#
|
#
|
||||||
# Specify one of `host`, `hosts`, or `roles`:
|
# Specify one of `host`, `hosts`, `role`, `roles`, `tag` or `tags`:
|
||||||
host: mysql-db1
|
host: mysql-db1
|
||||||
hosts:
|
hosts:
|
||||||
- mysql-db1
|
- mysql-db1
|
||||||
- mysql-db2
|
- mysql-db2
|
||||||
|
role: mysql
|
||||||
roles:
|
roles:
|
||||||
- mysql
|
- mysql
|
||||||
|
tag: writer
|
||||||
|
tags:
|
||||||
|
- writer
|
||||||
|
- reader
|
||||||
|
|
||||||
# Custom command
|
# Custom command
|
||||||
#
|
#
|
||||||
|
|||||||
@@ -10,11 +10,6 @@
|
|||||||
# They are application-specific, so they are not shared when multiple applications
|
# They are application-specific, so they are not shared when multiple applications
|
||||||
# run on the same proxy.
|
# run on the same proxy.
|
||||||
#
|
#
|
||||||
# The proxy is enabled by default on the primary role but can be disabled by
|
|
||||||
# setting `proxy: false`.
|
|
||||||
#
|
|
||||||
# It is disabled by default on all other roles but can be enabled by setting
|
|
||||||
# `proxy: true` or providing a proxy configuration.
|
|
||||||
proxy:
|
proxy:
|
||||||
# Hosts
|
# Hosts
|
||||||
#
|
#
|
||||||
@@ -126,3 +121,30 @@ proxy:
|
|||||||
response_headers:
|
response_headers:
|
||||||
- X-Request-ID
|
- X-Request-ID
|
||||||
- X-Request-Start
|
- X-Request-Start
|
||||||
|
|
||||||
|
# Enabling/disabling the proxy on roles
|
||||||
|
#
|
||||||
|
# The proxy is enabled by default on the primary role but can be disabled by
|
||||||
|
# setting `proxy: false` in the primary role's configuration.
|
||||||
|
#
|
||||||
|
# ```yaml
|
||||||
|
# servers:
|
||||||
|
# web:
|
||||||
|
# hosts:
|
||||||
|
# - ...
|
||||||
|
# proxy: false
|
||||||
|
# ```
|
||||||
|
#
|
||||||
|
# It is disabled by default on all other roles but can be enabled by setting
|
||||||
|
# `proxy: true` or providing a proxy configuration for that role.
|
||||||
|
#
|
||||||
|
# ```yaml
|
||||||
|
# servers:
|
||||||
|
# web:
|
||||||
|
# hosts:
|
||||||
|
# - ...
|
||||||
|
# web2:
|
||||||
|
# hosts:
|
||||||
|
# - ...
|
||||||
|
# proxy: true
|
||||||
|
# ```
|
||||||
|
|||||||
@@ -11,6 +11,7 @@ class Kamal::Configuration::Proxy
|
|||||||
def initialize(config:, proxy_config:, secrets:, context: "proxy")
|
def initialize(config:, proxy_config:, secrets:, context: "proxy")
|
||||||
@config = config
|
@config = config
|
||||||
@proxy_config = proxy_config
|
@proxy_config = proxy_config
|
||||||
|
@proxy_config = {} if @proxy_config.nil?
|
||||||
@secrets = secrets
|
@secrets = secrets
|
||||||
validate! @proxy_config, with: Kamal::Configuration::Validator::Proxy, context: context
|
validate! @proxy_config, with: Kamal::Configuration::Validator::Proxy, context: context
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
class Kamal::Configuration::Proxy::Boot
|
class Kamal::Configuration::Proxy::Boot
|
||||||
MINIMUM_VERSION = "v0.8.7"
|
MINIMUM_VERSION = "v0.9.0"
|
||||||
DEFAULT_HTTP_PORT = 80
|
DEFAULT_HTTP_PORT = 80
|
||||||
DEFAULT_HTTPS_PORT = 443
|
DEFAULT_HTTPS_PORT = 443
|
||||||
DEFAULT_LOG_MAX_SIZE = "10m"
|
DEFAULT_LOG_MAX_SIZE = "10m"
|
||||||
@@ -66,6 +66,10 @@ class Kamal::Configuration::Proxy::Boot
|
|||||||
File.join host_directory, "image_version"
|
File.join host_directory, "image_version"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def run_command_file
|
||||||
|
File.join host_directory, "run_command"
|
||||||
|
end
|
||||||
|
|
||||||
def apps_directory
|
def apps_directory
|
||||||
File.join host_directory, "apps-config"
|
File.join host_directory, "apps-config"
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -2,8 +2,8 @@ class Kamal::Configuration::Validator::Accessory < Kamal::Configuration::Validat
|
|||||||
def validate!
|
def validate!
|
||||||
super
|
super
|
||||||
|
|
||||||
if (config.keys & [ "host", "hosts", "roles" ]).size != 1
|
if (config.keys & [ "host", "hosts", "role", "roles", "tag", "tags" ]).size != 1
|
||||||
error "specify one of `host`, `hosts` or `roles`"
|
error "specify one of `host`, `hosts`, `role`, `roles`, `tag` or `tags`"
|
||||||
end
|
end
|
||||||
|
|
||||||
validate_docker_options!(config["options"])
|
validate_docker_options!(config["options"])
|
||||||
|
|||||||
@@ -1,3 +1,3 @@
|
|||||||
module Kamal
|
module Kamal
|
||||||
VERSION = "2.5.3"
|
VERSION = "2.6.1"
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -21,6 +21,7 @@ class CliBuildTest < CliTestCase
|
|||||||
.returns("")
|
.returns("")
|
||||||
|
|
||||||
run_command("push", "--verbose").tap do |output|
|
run_command("push", "--verbose").tap do |output|
|
||||||
|
assert_hook_ran "pre-connect", output
|
||||||
assert_hook_ran "pre-build", output
|
assert_hook_ran "pre-build", output
|
||||||
assert_match /Cloning repo into build directory/, output
|
assert_match /Cloning repo into build directory/, output
|
||||||
assert_match /git -C #{Dir.tmpdir}\/kamal-clones\/app-#{pwd_sha} clone #{Dir.pwd}/, output
|
assert_match /git -C #{Dir.tmpdir}\/kamal-clones\/app-#{pwd_sha} clone #{Dir.pwd}/, output
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ class CliProxyTest < CliTestCase
|
|||||||
run_command("boot").tap do |output|
|
run_command("boot").tap do |output|
|
||||||
assert_match "docker login", output
|
assert_match "docker login", output
|
||||||
assert_match "mkdir -p .kamal/proxy/apps-config", output
|
assert_match "mkdir -p .kamal/proxy/apps-config", output
|
||||||
assert_match "echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy", output
|
assert_match "echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -19,7 +19,7 @@ class CliProxyTest < CliTestCase
|
|||||||
exception = assert_raises do
|
exception = assert_raises do
|
||||||
run_command("boot").tap do |output|
|
run_command("boot").tap do |output|
|
||||||
assert_match "docker login", output
|
assert_match "docker login", output
|
||||||
assert_match "echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy", output
|
assert_match "echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -37,49 +37,27 @@ class CliProxyTest < CliTestCase
|
|||||||
|
|
||||||
run_command("boot").tap do |output|
|
run_command("boot").tap do |output|
|
||||||
assert_match "docker login", output
|
assert_match "docker login", output
|
||||||
assert_match "docker container start kamal-proxy || echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy", output
|
assert_match "docker container start kamal-proxy || echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy", output
|
||||||
end
|
end
|
||||||
ensure
|
ensure
|
||||||
Thread.report_on_exception = false
|
Thread.report_on_exception = false
|
||||||
end
|
end
|
||||||
|
|
||||||
test "reboot" do
|
test "reboot" do
|
||||||
SSHKit::Backend::Abstract.any_instance.expects(:capture_with_info)
|
|
||||||
.with(:docker, :container, :ls, "--all", "--filter", "name=^app-web-123$", "--quiet")
|
|
||||||
.returns("abcdefabcdef")
|
|
||||||
.at_least_once
|
|
||||||
|
|
||||||
SSHKit::Backend::Abstract.any_instance.expects(:capture_with_info)
|
|
||||||
.with { |*args| args[0..1] == [ :sh, "-c" ] }
|
|
||||||
.returns("123")
|
|
||||||
.at_least_once
|
|
||||||
|
|
||||||
run_command("reboot", "-y").tap do |output|
|
run_command("reboot", "-y").tap do |output|
|
||||||
assert_match "docker container stop kamal-proxy on 1.1.1.1", output
|
assert_match "docker container stop kamal-proxy on 1.1.1.1", output
|
||||||
assert_match "docker container prune --force --filter label=org.opencontainers.image.title=kamal-proxy on 1.1.1.1", output
|
assert_match "docker container prune --force --filter label=org.opencontainers.image.title=kamal-proxy on 1.1.1.1", output
|
||||||
assert_match "mkdir -p .kamal/proxy/apps-config on 1.1.1.1", output
|
assert_match "mkdir -p .kamal/proxy/apps-config on 1.1.1.1", output
|
||||||
assert_match "echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy --volume $(pwd)/.kamal/proxy/apps-config:/home/kamal-proxy/.apps-config on 1.1.1.1", output
|
assert_match "echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy --volume $(pwd)/.kamal/proxy/apps-config:/home/kamal-proxy/.apps-config on 1.1.1.1", output
|
||||||
assert_match "docker exec kamal-proxy kamal-proxy deploy app-web --target=\"abcdefabcdef:80\" --deploy-timeout=\"6s\" --drain-timeout=\"30s\" --buffer-requests --buffer-responses --log-request-header=\"Cache-Control\" --log-request-header=\"Last-Modified\" --log-request-header=\"User-Agent\" on 1.1.1.1", output
|
|
||||||
|
|
||||||
assert_match "docker container stop kamal-proxy on 1.1.1.2", output
|
assert_match "docker container stop kamal-proxy on 1.1.1.2", output
|
||||||
assert_match "docker container prune --force --filter label=org.opencontainers.image.title=kamal-proxy on 1.1.1.2", output
|
assert_match "docker container prune --force --filter label=org.opencontainers.image.title=kamal-proxy on 1.1.1.2", output
|
||||||
assert_match "mkdir -p .kamal/proxy/apps-config on 1.1.1.1", output
|
assert_match "mkdir -p .kamal/proxy/apps-config on 1.1.1.1", output
|
||||||
assert_match "echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy --volume $(pwd)/.kamal/proxy/apps-config:/home/kamal-proxy/.apps-config on 1.1.1.2", output
|
assert_match "echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy --volume $(pwd)/.kamal/proxy/apps-config:/home/kamal-proxy/.apps-config on 1.1.1.2", output
|
||||||
assert_match "docker exec kamal-proxy kamal-proxy deploy app-web --target=\"abcdefabcdef:80\" --deploy-timeout=\"6s\" --drain-timeout=\"30s\" --buffer-requests --buffer-responses --log-request-header=\"Cache-Control\" --log-request-header=\"Last-Modified\" --log-request-header=\"User-Agent\" on 1.1.1.2", output
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
test "reboot --rolling" do
|
test "reboot --rolling" do
|
||||||
SSHKit::Backend::Abstract.any_instance.expects(:capture_with_info)
|
|
||||||
.with(:docker, :container, :ls, "--all", "--filter", "name=^app-web-123$", "--quiet")
|
|
||||||
.returns("abcdefabcdef")
|
|
||||||
.at_least_once
|
|
||||||
|
|
||||||
SSHKit::Backend::Abstract.any_instance.expects(:capture_with_info)
|
|
||||||
.with { |*args| args[0..1] == [ :sh, "-c" ] }
|
|
||||||
.returns("123")
|
|
||||||
.at_least_once
|
|
||||||
|
|
||||||
run_command("reboot", "--rolling", "-y").tap do |output|
|
run_command("reboot", "--rolling", "-y").tap do |output|
|
||||||
assert_match "Running docker container prune --force --filter label=org.opencontainers.image.title=kamal-proxy on 1.1.1.1", output
|
assert_match "Running docker container prune --force --filter label=org.opencontainers.image.title=kamal-proxy on 1.1.1.1", output
|
||||||
end
|
end
|
||||||
@@ -199,7 +177,7 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "/usr/bin/env mkdir -p .kamal", output
|
assert_match "/usr/bin/env mkdir -p .kamal", output
|
||||||
assert_match "docker network create kamal", output
|
assert_match "docker network create kamal", output
|
||||||
assert_match "docker login -u [REDACTED] -p [REDACTED]", output
|
assert_match "docker login -u [REDACTED] -p [REDACTED]", output
|
||||||
assert_match "docker container start kamal-proxy || echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy", output
|
assert_match "docker container start kamal-proxy || echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy", output
|
||||||
assert_match "/usr/bin/env mkdir -p .kamal", output
|
assert_match "/usr/bin/env mkdir -p .kamal", output
|
||||||
assert_match %r{docker rename app-web-latest app-web-latest_replaced_.*}, output
|
assert_match %r{docker rename app-web-latest app-web-latest_replaced_.*}, output
|
||||||
assert_match "/usr/bin/env mkdir -p .kamal/apps/app/env/roles", output
|
assert_match "/usr/bin/env mkdir -p .kamal/apps/app/env/roles", output
|
||||||
@@ -243,7 +221,9 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "Running /usr/bin/env mkdir -p .kamal/proxy on #{host}", output
|
assert_match "Running /usr/bin/env mkdir -p .kamal/proxy on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/options on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output end
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/run_command on #{host}", output
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -254,6 +234,7 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "Uploading \"--log-opt max-size=10m\" to .kamal/proxy/options on #{host}", output
|
assert_match "Uploading \"--log-opt max-size=10m\" to .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/run_command on #{host}", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -265,6 +246,7 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "Uploading \"--publish 80:80 --publish 443:443 --log-opt max-size=100m\" to .kamal/proxy/options on #{host}", output
|
assert_match "Uploading \"--publish 80:80 --publish 443:443 --log-opt max-size=100m\" to .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/run_command on #{host}", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -276,6 +258,7 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "Uploading \"--publish 80:80 --publish 443:443\" to .kamal/proxy/options on #{host}", output
|
assert_match "Uploading \"--publish 80:80 --publish 443:443\" to .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/run_command on #{host}", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -322,6 +305,7 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "Uploading \"--publish 80:80 --publish 443:443 --log-opt max-size=10m --label=foo=bar --add_host=thishost:thathost\" to .kamal/proxy/options on #{host}", output
|
assert_match "Uploading \"--publish 80:80 --publish 443:443 --log-opt max-size=10m --label=foo=bar --add_host=thishost:thathost\" to .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/run_command on #{host}", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -333,6 +317,7 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/options on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Uploading \"myreg/basecamp/kamal-proxy\" to .kamal/proxy/image on #{host}", output
|
assert_match "Uploading \"myreg/basecamp/kamal-proxy\" to .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/run_command on #{host}", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -344,6 +329,7 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/options on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Uploading \"myrepo/kamal-proxy\" to .kamal/proxy/image on #{host}", output
|
assert_match "Uploading \"myrepo/kamal-proxy\" to .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/run_command on #{host}", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -355,23 +341,37 @@ class CliProxyTest < CliTestCase
|
|||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/options on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Uploading \"0.9.9\" to .kamal/proxy/image_version on #{host}", output
|
assert_match "Uploading \"0.9.9\" to .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/run_command on #{host}", output
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
test "boot_config set run_command" do
|
||||||
|
run_command("boot_config", "set", "--metrics_port", "9000", "--debug", "true").tap do |output|
|
||||||
|
%w[ 1.1.1.1 1.1.1.2 ].each do |host|
|
||||||
|
assert_match "Running /usr/bin/env mkdir -p .kamal/proxy on #{host}", output
|
||||||
|
assert_match "Uploading \"--publish 80:80 --publish 443:443 --log-opt max-size=10m --expose=9000\" to .kamal/proxy/options on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image on #{host}", output
|
||||||
|
assert_match "Running /usr/bin/env rm .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Uploading \"kamal-proxy run --debug --metrics-port \\\"9000\\\"\" to .kamal/proxy/run_command on #{host}", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
test "boot_config set all" do
|
test "boot_config set all" do
|
||||||
run_command("boot_config", "set", "--docker_options", "label=foo=bar", "--registry", "myreg", "--repository", "myrepo", "--image_version", "0.9.9").tap do |output|
|
run_command("boot_config", "set", "--docker_options", "label=foo=bar", "--registry", "myreg", "--repository", "myrepo", "--image_version", "0.9.9", "--metrics_port", "9000", "--debug", "true").tap do |output|
|
||||||
%w[ 1.1.1.1 1.1.1.2 ].each do |host|
|
%w[ 1.1.1.1 1.1.1.2 ].each do |host|
|
||||||
assert_match "Uploading \"--publish 80:80 --publish 443:443 --log-opt max-size=10m --label=foo=bar\" to .kamal/proxy/options on #{host}", output
|
assert_match "Uploading \"--publish 80:80 --publish 443:443 --log-opt max-size=10m --expose=9000 --label=foo=bar\" to .kamal/proxy/options on #{host}", output
|
||||||
assert_match "Uploading \"myreg/myrepo/kamal-proxy\" to .kamal/proxy/image on #{host}", output
|
assert_match "Uploading \"myreg/myrepo/kamal-proxy\" to .kamal/proxy/image on #{host}", output
|
||||||
assert_match "Uploading \"0.9.9\" to .kamal/proxy/image_version on #{host}", output
|
assert_match "Uploading \"0.9.9\" to .kamal/proxy/image_version on #{host}", output
|
||||||
|
assert_match "Uploading \"kamal-proxy run --debug --metrics-port \\\"9000\\\"\" to .kamal/proxy/run_command on #{host}", output
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
test "boot_config get" do
|
test "boot_config get" do
|
||||||
SSHKit::Backend::Abstract.any_instance.expects(:capture_with_info)
|
SSHKit::Backend::Abstract.any_instance.expects(:capture_with_info)
|
||||||
.with(:echo, "$(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"v0.8.7\")")
|
.with(:echo, "$(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\")")
|
||||||
.returns("--publish 80:80 --publish 8443:443 --label=foo=bar basecamp/kamal-proxy:v1.0.0")
|
.returns("--publish 80:80 --publish 8443:443 --label=foo=bar basecamp/kamal-proxy:v1.0.0")
|
||||||
.twice
|
.twice
|
||||||
|
|
||||||
|
|||||||
@@ -149,6 +149,12 @@ class CommanderTest < ActiveSupport::TestCase
|
|||||||
assert_equal [], @kamal.accessory_hosts
|
assert_equal [], @kamal.accessory_hosts
|
||||||
end
|
end
|
||||||
|
|
||||||
|
test "primary role hosts are first" do
|
||||||
|
configure_with(:deploy_with_roles_workers_primary)
|
||||||
|
assert_equal [ "1.1.1.1", "1.1.1.2", "1.1.1.3", "1.1.1.4" ], @kamal.hosts
|
||||||
|
assert_equal [ "1.1.1.1", "1.1.1.2", "1.1.1.3", "1.1.1.4" ], @kamal.app_hosts
|
||||||
|
end
|
||||||
|
|
||||||
private
|
private
|
||||||
def configure_with(variant)
|
def configure_with(variant)
|
||||||
@kamal = Kamal::Commander.new.tap do |kamal|
|
@kamal = Kamal::Commander.new.tap do |kamal|
|
||||||
|
|||||||
@@ -15,7 +15,7 @@ class CommandsProxyTest < ActiveSupport::TestCase
|
|||||||
|
|
||||||
test "run" do
|
test "run" do
|
||||||
assert_equal \
|
assert_equal \
|
||||||
"echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy --volume $(pwd)/.kamal/proxy/apps-config:/home/kamal-proxy/.apps-config",
|
"echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy --volume $(pwd)/.kamal/proxy/apps-config:/home/kamal-proxy/.apps-config",
|
||||||
new_command.run.join(" ")
|
new_command.run.join(" ")
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -23,7 +23,7 @@ class CommandsProxyTest < ActiveSupport::TestCase
|
|||||||
@config.delete(:proxy)
|
@config.delete(:proxy)
|
||||||
|
|
||||||
assert_equal \
|
assert_equal \
|
||||||
"echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy --volume $(pwd)/.kamal/proxy/apps-config:/home/kamal-proxy/.apps-config",
|
"echo $(cat .kamal/proxy/options 2> /dev/null || echo \"--publish 80:80 --publish 443:443 --log-opt max-size=10m\") $(cat .kamal/proxy/image 2> /dev/null || echo \"basecamp/kamal-proxy\"):$(cat .kamal/proxy/image_version 2> /dev/null || echo \"#{Kamal::Configuration::Proxy::Boot::MINIMUM_VERSION}\") $(cat .kamal/proxy/run_command 2> /dev/null || echo \"\") | xargs docker run --name kamal-proxy --network kamal --detach --restart unless-stopped --volume kamal-proxy-config:/home/kamal-proxy/.config/kamal-proxy --volume $(pwd)/.kamal/proxy/apps-config:/home/kamal-proxy/.apps-config",
|
||||||
new_command.run.join(" ")
|
new_command.run.join(" ")
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -129,6 +129,12 @@ class CommandsProxyTest < ActiveSupport::TestCase
|
|||||||
new_command.read_image_version.join(" ")
|
new_command.read_image_version.join(" ")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
test "read_run_command" do
|
||||||
|
assert_equal \
|
||||||
|
"cat .kamal/proxy/run_command 2> /dev/null || echo \"\"",
|
||||||
|
new_command.read_run_command.join(" ")
|
||||||
|
end
|
||||||
|
|
||||||
test "reset_boot_options" do
|
test "reset_boot_options" do
|
||||||
assert_equal \
|
assert_equal \
|
||||||
"rm .kamal/proxy/options",
|
"rm .kamal/proxy/options",
|
||||||
@@ -153,6 +159,12 @@ class CommandsProxyTest < ActiveSupport::TestCase
|
|||||||
new_command.ensure_apps_config_directory.join(" ")
|
new_command.ensure_apps_config_directory.join(" ")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
test "reset_run_command" do
|
||||||
|
assert_equal \
|
||||||
|
"rm .kamal/proxy/run_command",
|
||||||
|
new_command.reset_run_command.join(" ")
|
||||||
|
end
|
||||||
|
|
||||||
private
|
private
|
||||||
def new_command
|
def new_command
|
||||||
Kamal::Commands::Proxy.new(Kamal::Configuration.new(@config, version: "123"))
|
Kamal::Commands::Proxy.new(Kamal::Configuration.new(@config, version: "123"))
|
||||||
|
|||||||
@@ -7,8 +7,8 @@ class ConfigurationAccessoryTest < ActiveSupport::TestCase
|
|||||||
image: "dhh/app",
|
image: "dhh/app",
|
||||||
registry: { "username" => "dhh", "password" => "secret" },
|
registry: { "username" => "dhh", "password" => "secret" },
|
||||||
servers: {
|
servers: {
|
||||||
"web" => [ "1.1.1.1", "1.1.1.2" ],
|
"web" => [ { "1.1.1.1" => "writer" }, { "1.1.1.2" => "reader" } ],
|
||||||
"workers" => [ "1.1.1.3", "1.1.1.4" ]
|
"workers" => [ { "1.1.1.3" => "writer" }, "1.1.1.4" ]
|
||||||
},
|
},
|
||||||
builder: { "arch" => "amd64" },
|
builder: { "arch" => "amd64" },
|
||||||
env: { "REDIS_URL" => "redis://x/y" },
|
env: { "REDIS_URL" => "redis://x/y" },
|
||||||
@@ -55,7 +55,7 @@ class ConfigurationAccessoryTest < ActiveSupport::TestCase
|
|||||||
"service" => "custom-monitoring",
|
"service" => "custom-monitoring",
|
||||||
"image" => "monitoring:latest",
|
"image" => "monitoring:latest",
|
||||||
"registry" => { "server" => "other.registry", "username" => "user", "password" => "pw" },
|
"registry" => { "server" => "other.registry", "username" => "user", "password" => "pw" },
|
||||||
"roles" => [ "web" ],
|
"role" => "web",
|
||||||
"port" => "4321:4321",
|
"port" => "4321:4321",
|
||||||
"labels" => {
|
"labels" => {
|
||||||
"cache" => "true"
|
"cache" => "true"
|
||||||
@@ -70,6 +70,14 @@ class ConfigurationAccessoryTest < ActiveSupport::TestCase
|
|||||||
"proxy" => {
|
"proxy" => {
|
||||||
"host" => "monitoring.example.com"
|
"host" => "monitoring.example.com"
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
"proxy" => {
|
||||||
|
"image" => "proxy:latest",
|
||||||
|
"tags" => [ "writer", "reader" ]
|
||||||
|
},
|
||||||
|
"logger" => {
|
||||||
|
"image" => "logger:latest",
|
||||||
|
"tag" => "writer"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -107,6 +115,8 @@ class ConfigurationAccessoryTest < ActiveSupport::TestCase
|
|||||||
assert_equal [ "1.1.1.5" ], @config.accessory(:mysql).hosts
|
assert_equal [ "1.1.1.5" ], @config.accessory(:mysql).hosts
|
||||||
assert_equal [ "1.1.1.6", "1.1.1.7" ], @config.accessory(:redis).hosts
|
assert_equal [ "1.1.1.6", "1.1.1.7" ], @config.accessory(:redis).hosts
|
||||||
assert_equal [ "1.1.1.1", "1.1.1.2" ], @config.accessory(:monitoring).hosts
|
assert_equal [ "1.1.1.1", "1.1.1.2" ], @config.accessory(:monitoring).hosts
|
||||||
|
assert_equal [ "1.1.1.1", "1.1.1.3", "1.1.1.2" ], @config.accessory(:proxy).hosts
|
||||||
|
assert_equal [ "1.1.1.1", "1.1.1.3" ], @config.accessory(:logger).hosts
|
||||||
end
|
end
|
||||||
|
|
||||||
test "missing host" do
|
test "missing host" do
|
||||||
@@ -117,14 +127,14 @@ class ConfigurationAccessoryTest < ActiveSupport::TestCase
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
test "setting host, hosts and roles" do
|
test "setting host, hosts, roles and tags" do
|
||||||
@deploy[:accessories]["mysql"]["hosts"] = [ "mysql-db1" ]
|
@deploy[:accessories]["mysql"]["hosts"] = [ "mysql-db1" ]
|
||||||
@deploy[:accessories]["mysql"]["roles"] = [ "db" ]
|
@deploy[:accessories]["mysql"]["roles"] = [ "db" ]
|
||||||
|
|
||||||
exception = assert_raises(Kamal::ConfigurationError) do
|
exception = assert_raises(Kamal::ConfigurationError) do
|
||||||
Kamal::Configuration.new(@deploy)
|
Kamal::Configuration.new(@deploy)
|
||||||
end
|
end
|
||||||
assert_equal "accessories/mysql: specify one of `host`, `hosts` or `roles`", exception.message
|
assert_equal "accessories/mysql: specify one of `host`, `hosts`, `role`, `roles`, `tag` or `tags`", exception.message
|
||||||
end
|
end
|
||||||
|
|
||||||
test "all hosts" do
|
test "all hosts" do
|
||||||
|
|||||||
19
test/fixtures/deploy_with_roles_workers_primary.yml
vendored
Normal file
19
test/fixtures/deploy_with_roles_workers_primary.yml
vendored
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
service: app
|
||||||
|
image: dhh/app
|
||||||
|
servers:
|
||||||
|
workers:
|
||||||
|
- 1.1.1.1
|
||||||
|
- 1.1.1.2
|
||||||
|
web:
|
||||||
|
- 1.1.1.3
|
||||||
|
- 1.1.1.4
|
||||||
|
env:
|
||||||
|
REDIS_URL: redis://x/y
|
||||||
|
registry:
|
||||||
|
server: registry.digitalocean.com
|
||||||
|
username: user
|
||||||
|
password: pw
|
||||||
|
builder:
|
||||||
|
arch: amd64
|
||||||
|
deploy_timeout: 1
|
||||||
|
primary_role: workers
|
||||||
@@ -0,0 +1,4 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
set -e
|
||||||
|
|
||||||
|
kamal proxy boot_config set --registry registry:4443
|
||||||
@@ -20,7 +20,7 @@ push_image_to_registry_4443() {
|
|||||||
install_kamal
|
install_kamal
|
||||||
push_image_to_registry_4443 nginx 1-alpine-slim
|
push_image_to_registry_4443 nginx 1-alpine-slim
|
||||||
push_image_to_registry_4443 busybox 1.36.0
|
push_image_to_registry_4443 busybox 1.36.0
|
||||||
push_image_to_registry_4443 basecamp/kamal-proxy v0.8.7
|
push_image_to_registry_4443 basecamp/kamal-proxy v0.9.0
|
||||||
|
|
||||||
# .ssh is on a shared volume that persists between runs. Clean it up as the
|
# .ssh is on a shared volume that persists between runs. Clean it up as the
|
||||||
# churn of temporary vm IPs can eventually create conflicts.
|
# churn of temporary vm IPs can eventually create conflicts.
|
||||||
|
|||||||
Reference in New Issue
Block a user