-
Notifications
You must be signed in to change notification settings - Fork 125
/
Copy path20180606155924_move_ansible_container_secrets_into_database.rb
120 lines (101 loc) · 3.57 KB
/
20180606155924_move_ansible_container_secrets_into_database.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
class MoveAnsibleContainerSecretsIntoDatabase < ActiveRecord::Migration[5.0]
TOKEN_FILE = "/run/secrets/kubernetes.io/serviceaccount/token".freeze
CA_CERT_FILE = "/run/secrets/kubernetes.io/serviceaccount/ca.crt".freeze
SECRET_NAME = "ansible-secrets".freeze
class MiqDatabase < ActiveRecord::Base; end
class Authentication < ActiveRecord::Base
self.inheritance_column = :_type_disabled
end
def up
return unless containerized?
update_authentications
end
private
def token_file
if Rails.env.test? && ENV['TOKEN_FILE']
ENV['TOKEN_FILE']
else
TOKEN_FILE
end
end
def ca_cert_file
if Rails.env.test? && ENV['CA_CERT_FILE']
ENV['CA_CERT_FILE']
else
CA_CERT_FILE
end
end
def containerized?
File.exist?(token_file) && File.exist?(ca_cert_file)
end
def update_authentications
secret_key, rabbit_password, admin_password, database_password = get_secret_data
return unless secret_key.present? && rabbit_password.present? && admin_password.present?
db_args = {
:resource_id => MiqDatabase.first.id,
:resource_type => "MiqDatabase"
}
secret_key_find_args = db_args.merge(
:name => "Ansible Secret Key",
:authtype => "ansible_secret_key",
:type => "AuthToken"
)
rabbitmq_auth_find_args = db_args.merge(
:name => "Ansible Rabbitmq Authentication",
:authtype => "ansible_rabbitmq_auth",
:userid => "ansible",
:type => "AuthUseridPassword"
)
admin_auth_find_args = db_args.merge(
:name => "Ansible Admin Authentication",
:authtype => "ansible_admin_password",
:userid => "admin",
:type => "AuthUseridPassword"
)
database_auth_find_args = db_args.merge(
:name => "Ansible Database Authentication",
:authtype => "ansible_database_password",
:userid => ApplicationRecord.configurations.configs_for(:env_name => Rails.env, :name => "primary").configuration_hash["username"],
:type => "AuthUseridPassword"
)
update_or_create_authentication!(secret_key_find_args, :auth_key => secret_key)
update_or_create_authentication!(rabbitmq_auth_find_args, :password => rabbit_password)
update_or_create_authentication!(admin_auth_find_args, :password => admin_password)
update_or_create_authentication!(database_auth_find_args, :password => database_password)
end
def get_secret_data
require 'open-uri'
require 'json'
kube_data = secret_uri.open(request_params) do |f|
JSON.parse(f.read)["data"]
end
decoded_data = kube_data.transform_values { |v| Base64.decode64(v) }
[
decoded_data["secret-key"],
decoded_data["rabbit-password"],
decoded_data["admin-password"],
ApplicationRecord.configurations.configs_for(:env_name => Rails.env, :name => "primary").configuration_hash["password"]
].map { |v| ManageIQ::Password.encrypt(v) }
rescue OpenURI::HTTPError
nil
end
def update_or_create_authentication!(find_args, update_args)
auth = Authentication.find_or_initialize_by(find_args)
auth.update!(update_args)
end
def request_params
{
'Accept' => "application/json",
'Authorization' => "Bearer #{File.read(token_file)}",
:ssl_ca_cert => ca_cert_file,
:ssl_verify_mode => OpenSSL::SSL::VERIFY_PEER
}
end
def secret_uri
URI::HTTPS.build(
:host => ENV["KUBERNETES_SERVICE_HOST"],
:port => ENV["KUBERNETES_SERVICE_PORT"],
:path => "/api/v1/namespaces/#{ENV["MY_POD_NAMESPACE"]}/secrets/#{SECRET_NAME}"
)
end
end