Add secrets-common for shared secrets
Add a shared secrets file used across all destinations. Useful for things Github tokens or registry passwords. The secrets are added to a new file called `secrets-common` to highlight they are shared, and to avoid acciedentally inheriting a secret from the `secrets` file to `secrets.destination`.
This commit is contained in:
@@ -1,19 +1,20 @@
|
|||||||
require "dotenv"
|
require "dotenv"
|
||||||
|
|
||||||
class Kamal::Secrets
|
class Kamal::Secrets
|
||||||
attr_reader :secrets_file
|
attr_reader :secrets_files
|
||||||
|
|
||||||
Kamal::Secrets::Dotenv::InlineCommandSubstitution.install!
|
Kamal::Secrets::Dotenv::InlineCommandSubstitution.install!
|
||||||
|
|
||||||
def initialize(destination: nil)
|
def initialize(destination: nil)
|
||||||
@secrets_file = [ *(".kamal/secrets.#{destination}" if destination), ".kamal/secrets" ].find { |f| File.exist?(f) }
|
@secrets_files = \
|
||||||
|
[ ".kamal/secrets-common", ".kamal/secrets#{(".#{destination}" if destination)}" ].select { |f| File.exist?(f) }
|
||||||
end
|
end
|
||||||
|
|
||||||
def [](key)
|
def [](key)
|
||||||
secrets.fetch(key)
|
secrets.fetch(key)
|
||||||
rescue KeyError
|
rescue KeyError
|
||||||
if secrets_file
|
if secrets_files
|
||||||
raise Kamal::ConfigurationError, "Secret '#{key}' not found in #{secrets_file}"
|
raise Kamal::ConfigurationError, "Secret '#{key}' not found in #{secrets_files.join(", ")}"
|
||||||
else
|
else
|
||||||
raise Kamal::ConfigurationError, "Secret '#{key}' not found, no secret files provided"
|
raise Kamal::ConfigurationError, "Secret '#{key}' not found, no secret files provided"
|
||||||
end
|
end
|
||||||
@@ -25,14 +26,8 @@ class Kamal::Secrets
|
|||||||
|
|
||||||
private
|
private
|
||||||
def secrets
|
def secrets
|
||||||
@secrets ||= parse_secrets
|
@secrets ||= secrets_files.inject({}) do |secrets, secrets_file|
|
||||||
end
|
secrets.merge!(::Dotenv.parse(secrets_file))
|
||||||
|
|
||||||
def parse_secrets
|
|
||||||
if secrets_file
|
|
||||||
::Dotenv.parse(secrets_file)
|
|
||||||
else
|
|
||||||
{}
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -1,5 +1,3 @@
|
|||||||
SECRET_TOKEN='1234 with "中文"'
|
|
||||||
SECRET_TAG='TAGME'
|
|
||||||
SECRETS=$(kamal secrets fetch --adapter test --account test INTERPOLATED_SECRET1 INTERPOLATED_SECRET2 INTERPOLATED_中文)
|
SECRETS=$(kamal secrets fetch --adapter test --account test INTERPOLATED_SECRET1 INTERPOLATED_SECRET2 INTERPOLATED_中文)
|
||||||
INTERPOLATED_SECRET1=$(kamal secrets extract INTERPOLATED_SECRET1 ${SECRETS})
|
INTERPOLATED_SECRET1=$(kamal secrets extract INTERPOLATED_SECRET1 ${SECRETS})
|
||||||
INTERPOLATED_SECRET2=$(kamal secrets extract INTERPOLATED_SECRET2 ${SECRETS})
|
INTERPOLATED_SECRET2=$(kamal secrets extract INTERPOLATED_SECRET2 ${SECRETS})
|
||||||
|
|||||||
@@ -0,0 +1,2 @@
|
|||||||
|
SECRET_TOKEN='1234 with "中文"'
|
||||||
|
SECRET_TAG='TAGME'
|
||||||
@@ -21,10 +21,14 @@ class SecretsTest < ActiveSupport::TestCase
|
|||||||
end
|
end
|
||||||
|
|
||||||
test "destinations" do
|
test "destinations" do
|
||||||
with_test_secrets("secrets.dest" => "SECRET=DEF", "secrets" => "SECRET=ABC") do
|
with_test_secrets("secrets.dest" => "SECRET=DEF", "secrets" => "SECRET=ABC", "secrets-common" => "SECRET=GHI\nSECRET2=JKL") do
|
||||||
assert_equal "ABC", Kamal::Secrets.new["SECRET"]
|
assert_equal "ABC", Kamal::Secrets.new["SECRET"]
|
||||||
assert_equal "DEF", Kamal::Secrets.new(destination: "dest")["SECRET"]
|
assert_equal "DEF", Kamal::Secrets.new(destination: "dest")["SECRET"]
|
||||||
assert_equal "ABC", Kamal::Secrets.new(destination: "nodest")["SECRET"]
|
assert_equal "GHI", Kamal::Secrets.new(destination: "nodest")["SECRET"]
|
||||||
|
|
||||||
|
assert_equal "JKL", Kamal::Secrets.new["SECRET2"]
|
||||||
|
assert_equal "JKL", Kamal::Secrets.new(destination: "dest")["SECRET2"]
|
||||||
|
assert_equal "JKL", Kamal::Secrets.new(destination: "nodest")["SECRET2"]
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
Reference in New Issue
Block a user