Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Exclude stderr from parsing on decryption success #647

Merged
merged 1 commit into from
Nov 29, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
## next

*Bug Fixes*
- Fix a bug causing secret generation from ejson to fail when decryption succeeded but a warning was also emitted. [#647](https://github.com/Shopify/krane/pull/647)

# 1.0.0

We've renamed the gem and cli to Krane.
Expand Down
11 changes: 7 additions & 4 deletions lib/krane/ejson_secret_provisioner.rb
Original file line number Diff line number Diff line change
Expand Up @@ -134,10 +134,13 @@ def with_decrypted_ejson
end

def decrypt_ejson(key_dir)
# ejson seems to dump both errors and output to STDOUT
out_err, st = Open3.capture2e("EJSON_KEYDIR=#{key_dir} ejson decrypt #{@ejson_file}")
raise EjsonSecretError, out_err unless st.success?
JSON.parse(out_err)
out, err, st = Open3.capture3("EJSON_KEYDIR=#{key_dir} ejson decrypt #{@ejson_file}")
unless st.success?
# older ejson versions dump some errors to STDOUT
msg = err.presence || out
raise EjsonSecretError, msg
end
JSON.parse(out)
rescue JSON::ParserError
raise EjsonSecretError, "Failed to parse decrypted ejson"
end
Expand Down
31 changes: 31 additions & 0 deletions test/unit/krane/ejson_secret_provisioner_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,37 @@ def test_run_with_bad_private_key_in_cloud_keys
end
end

def test_decryption_failure_with_error_on_stdout_reports_error
# ejson < 1.2 prints errors on stdout
Open3.expects(:capture3).with(regexp_matches(/ejson decrypt/))
.returns(["Some error from ejson", "", stub(success?: false)])
msg = "Generation of Kubernetes secrets from ejson failed: Some error from ejson"
assert_raises_message(Krane::EjsonSecretError, msg) do
build_provisioner(fixture_path('ejson-cloud')).resources
end
end

def test_decryption_successful_but_warning_on_stderr_does_not_confuse_us
valid_response = {
"_public_key" => fixture_public_key,
"kubernetes_secrets" =>
{
"test" => {
"_type" => "Opaque",
"data" => { "test" => "true" },
},
},
}.to_json

Open3.expects(:capture3).with(regexp_matches(/ejson decrypt/))
.returns([valid_response, "Permissions warning!", stub(success?: true)])
stub_server_dry_run_version_request
stub_server_dry_run_validation_request

resources = build_provisioner(fixture_path('ejson-cloud')).resources
refute_empty(resources)
end

def test_no_ejson_keys_secret_provided
assert_raises_message(Krane::EjsonSecretError,
/Generation of Kubernetes secrets from ejson failed: Secret ejson-keys not provided, cannot decrypt secrets/) do
Expand Down