You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

176 lines
6.3 KiB

require_relative '../../lib/carto/dbdirect/metadata_manager'
namespace :carto do
namespace :dbdirect do
def save_certs(username, name, id, arn, data, output_directory)
base_filename = "#{username}_#{name}"
key_filename = File.join(output_directory, "#{base_filename}.key")
crt_filename = File.join(output_directory, "#{base_filename}.crt")
ca_filename = File.join(output_directory, "server_ca.crt")
pk8_filename = File.join(output_directory, "#{base_filename}.key.pk8")
puts "Certificate #{name} generated for #{username}"
puts " id: #{id}"
puts " arn: #{arn}"
files = [
[:client_key, key_filename],
[:client_key_pk8, pk8_filename, 'b'],
[:client_crt, crt_filename],
[:server_ca, ca_filename]
]
files.each do |datum, filename, binary|
File.open(filename, "w#{binary}") do |file|
file.write data[datum]
end
puts "#{datum} written to #{filename}"
end
end
def ok_to_revoke?(cert)
STDOUT.puts "About to revoke certificate #{cert.name} for user #{cert.user.username}. Are you sure? (y/n)"
input = STDIN.gets.strip
input == 'y'
end
desc "Generate DB direct certificate"
task :generate_certificate, [:username, :name, :password, :validity] => :environment do |_t, args|
user = Carto::User.find_by_username(args.username)
raise "User #{args.username} not found" unless user
data, cert = Carto::DbdirectCertificate.generate(
user: user,
name: args.name,
passphrase: args.password,
validity_days: args.validity.blank? ? 365 : args.validity.to_i,
server_ca: true,
pk8: true
)
save_certs user.username, cert.name, cert.id, cert.arn, data, '.'
end
desc "Show DB direct user certificates"
task :user_certificates, [:username] => :environment do |_t, args|
user = Carto::User.find_by_username(args.username)
raise "User #{args.username} not found" unless user
user.dbdirect_certificates.each do |certificate|
puts "#{certificate.name}:"
puts " id: #{certificate.id}"
puts " expires: #{certificate.expiration}"
puts " arn: #{certificate.arn}"
end
end
desc "Show DB direct organization certificates"
task :organization_certificates, [:org] => :environment do |_t, args|
organization = Carto::Organization.find_by_id(args.org) || Carto::Organization.find_by_name(args.org)
raise "Couldn't find organization #{args.org.inspect}" unless organization.present?
organization.users.each do |user|
user.dbdirect_certificates.each do |certificate|
puts "#{certificate.name}:"
puts " username: #{user.username}"
puts " id: #{certificate.id}"
puts " expires: #{certificate.expiration}"
puts " arn: #{certificate.arn}"
end
end
end
desc "Revoke DB direct certificate"
task :revoke_certificate, [:id] => :environment do |_t, args|
cert = Carto::DbdirectCertificate.find(args.id)
raise "Certificate #{args.id} not found" unless cert
if ok_to_revoke?(cert)
puts "Revoking certificate #{cert.name} for user #{cert.user.username}"
puts " ARN: #{cert.arn}"
puts " Expiration was #{cert.expiration}"
cert.destroy!
puts "DESTROYED!!"
end
end
desc "Show organization ips"
task :get_organization_ips, [:org] => :environment do |_t, args|
organization = Carto::Organization.find_by_id(args.org) || Carto::Organization.find_by_name(args.org)
raise "Couldn't find organization #{args.org.inspect}" unless organization.present?
ips = organization.dbdirect_effective_ips
org_id = "#{organization.name} (#{organization.id})"
if ips.present?
puts "DBDirect IPs for organization #{org_id}:"
puts ips
else
puts "No IPs defined for organization #{org_id}"
end
end
desc "Show user ips"
task :get_user_ips, [:user_spec] => :environment do |_t, args|
user = Carto::User.find_by_id(args.user_spec) || Carto::User.find_by_username(args.user_spec)
raise "Couldn't find user #{args.user_spec.inspect}" unless user.present?
ips = user.dbdirect_effective_ips
user_id = "#{user.username} (#{user.id})"
if ips.present?
puts "DBDirect IPs for user #{user_id}:"
puts ips
else
puts "No IPs defined for user #{user_id}"
end
end
desc "Save orgnization ips (use ; to separate ips)"
task :set_organization_ips, [:org, :ips] => :environment do |_t, args|
organization = Carto::Organization.find_by_id(args.org) || Carto::Organization.find_by_name(args.org)
raise "Couldn't find organization #{args.org.inspect}" unless organization.present?
set_ips = args.ips.present? ? args.ips.split(';') : []
org_id = "#{organization.name} (#{organization.id})"
old_ips = organization.dbdirect_effective_ips
organization.dbdirect_effective_ips = set_ips
organization.reload
new_ips = organization.dbdirect_effective_ips
if old_ips.present?
puts "Previous DBDirect IPs for organization #{org_id}:"
puts old_ips
end
if new_ips.blank?
if old_ips.present?
puts "IPs deleted for organization #{org_id}:"
else
puts "No changes"
end
else
puts "New IPs for organization #{org_id}:"
puts new_ips
end
end
desc "Check database and redis metadata are in sync"
task :check_metadata_sync, [] => :environment do |_t, args|
config = Cartodb.get_config(:dbdirect, 'metadata_persist') || {}
raise "Config entries for dbdirect:metadata_persist are missing" unless config.any?
metadata_manager = Carto::Dbdirect::MetadataManager.new(config, $users_metadata)
Carto::User.find_each do |user|
database_ips = user.dbdirect_effective_ips.sort
metadata_ips = metadata_manager.get(user.username).sort
diff = database_ips - metadata_ips | metadata_ips - database_ips
if diff.any?
puts "#{user.username} not in sync:"
puts " > Database: #{database_ips.join(', ')}"
puts " > Metadata: #{metadata_ips.join(', ')}"
puts " > Diff: #{diff.join(', ')}"
puts ""
end
end
end
end
end