app/models/services/service_credential_binding_view.rb
module VCAP
module CloudController
module ServiceCredentialBinding
module Types
SERVICE_KEY = 'key'.freeze
SERVICE_BINDING = 'app'.freeze
end
SERVICE_KEY_VIEW = Sequel::Model(:service_keys).select(
Sequel.as(:service_keys__id, :id),
Sequel.as(:service_keys__guid, :guid),
Sequel.as(Types::SERVICE_KEY, :type),
Sequel.as(:service_instances__space_id, :space_id),
Sequel.as(:service_keys__created_at, :created_at),
Sequel.as(:service_keys__updated_at, :updated_at),
Sequel.as(:service_keys__name, :name),
Sequel.as(:service_keys__credentials, :credentials),
Sequel.as(:service_keys__salt, :salt),
Sequel.as(:service_keys__encryption_key_label, :encryption_key_label),
Sequel.as(:service_keys__encryption_iterations, :encryption_iterations),
Sequel.as(:service_instances__guid, :service_instance_guid),
Sequel.as(:service_instances__name, :service_instance_name),
Sequel.as(nil, :app_guid),
Sequel.as(nil, :app_name),
Sequel.as(:service_keys__service_instance_id, :service_instance_id),
Sequel.as(nil, :syslog_drain_url),
Sequel.as(nil, :volume_mounts),
Sequel.as(nil, :volume_mounts_salt),
Sequel.as(:service_plans__name, :service_plan_name),
Sequel.as(:service_plans__guid, :service_plan_guid),
Sequel.as(:services__label, :service_offering_name),
Sequel.as(:services__guid, :service_offering_guid)
).join(
:service_instances, id: Sequel[:service_keys][:service_instance_id]
).left_join(
:service_plans, id: Sequel[:service_instances][:service_plan_id]
).left_join(
:services, id: Sequel[:service_plans][:service_id]
).freeze
SERVICE_BINDING_VIEW = Sequel::Model(:service_bindings).select(
Sequel.as(:service_bindings__id, :id),
Sequel.as(:service_bindings__guid, :guid),
Sequel.as(Types::SERVICE_BINDING, :type),
Sequel.as(:spaces__id, :space_id),
Sequel.as(:service_bindings__created_at, :created_at),
Sequel.as(:service_bindings__updated_at, :updated_at),
Sequel.as(:service_bindings__name, :name),
Sequel.as(:service_bindings__credentials, :credentials),
Sequel.as(:service_bindings__salt, :salt),
Sequel.as(:service_bindings__encryption_key_label, :encryption_key_label),
Sequel.as(:service_bindings__encryption_iterations, :encryption_iterations),
Sequel.as(:service_bindings__service_instance_guid, :service_instance_guid),
Sequel.as(:service_instances__name, :service_instance_name),
Sequel.as(:service_bindings__app_guid, :app_guid),
Sequel.as(:apps__name, :app_name),
Sequel.as(nil, :service_instance_id),
Sequel.as(:service_bindings__syslog_drain_url, :syslog_drain_url),
Sequel.as(:service_bindings__volume_mounts, :volume_mounts),
Sequel.as(:service_bindings__volume_mounts_salt, :volume_mounts_salt),
Sequel.as(:service_plans__name, :service_plan_name),
Sequel.as(:service_plans__guid, :service_plan_guid),
Sequel.as(:services__label, :service_offering_name),
Sequel.as(:services__guid, :service_offering_guid)
).join(
:apps, guid: Sequel[:service_bindings][:app_guid]
).join(
:service_instances, guid: Sequel[:service_bindings][:service_instance_guid]
).left_join(
:service_plans, id: Sequel[:service_instances][:service_plan_id]
).left_join(
:services, id: Sequel[:service_plans][:service_id]
).join(
:spaces, guid: Sequel[:apps][:space_guid]
).freeze
VIEW = [
SERVICE_KEY_VIEW,
SERVICE_BINDING_VIEW
].inject do |statement, sub_select|
statement.union(sub_select, all: true, from_self: false)
end.from_self.freeze
class View < Sequel::Model(VIEW)
plugin :single_table_inheritance,
:type,
model_map: {
'app' => 'VCAP::CloudController::ServiceBinding',
'key' => 'VCAP::CloudController::ServiceKey'
}
# Custom eager loading: https://github.com/jeremyevans/sequel/blob/master/doc/advanced_associations.rdoc#label-Custom+Eager+Loaders
many_to_one :service_instance_sti_eager_load,
dataset: -> { raise 'Must be used for eager loading' },
eager_loader_key: nil, # set up id_map ourselves
eager_loader: proc { |eo|
service_instance_id_to_keys = {}
service_instance_guid_to_bindings = {}
eo[:rows].each do |scb|
scb.associations[:service_instance] = nil
case scb # keys are joined by ID and bindings by GUID
when ServiceKey
service_instance_id_to_keys[scb.service_instance_id] ||= []
service_instance_id_to_keys[scb.service_instance_id] << scb
when ServiceBinding
service_instance_guid_to_bindings[scb.service_instance_guid] ||= []
service_instance_guid_to_bindings[scb.service_instance_guid] << scb
end
end
ds = ServiceInstance.where(id: service_instance_id_to_keys.keys).or(guid: service_instance_guid_to_bindings.keys)
ds = ds.eager(eo[:associations]) if eo[:associations]
ds = eo[:eager_block].call(ds) if eo[:eager_block]
ds.all do |service_instance|
service_instance_id_to_keys[service_instance.id]&.each { |binding| binding.associations[:service_instance] = service_instance }
service_instance_guid_to_bindings[service_instance.guid]&.each { |binding| binding.associations[:service_instance] = service_instance }
end
}
# Custom eager loading: https://github.com/jeremyevans/sequel/blob/master/doc/advanced_associations.rdoc#label-Custom+Eager+Loaders
one_to_many :labels_sti_eager_load,
dataset: -> { raise 'Must be used for eager loading' },
eager_loader_key: nil, # set up id_map ourselves
eager_loader: proc { |eo|
service_keys = {}
service_bindings = {}
eo[:rows].each do |scb|
scb.associations[:labels] = []
case scb
when ServiceKey
service_keys[scb.guid] = scb
when ServiceBinding
service_bindings[scb.guid] = scb
end
end
ServiceKeyLabelModel.where(resource_guid: service_keys.keys).all do |label|
service_keys[label.resource_guid].associations[:labels] << label if service_keys[label.resource_guid]
end
ServiceBindingLabelModel.where(resource_guid: service_bindings.keys).all do |label|
service_bindings[label.resource_guid].associations[:labels] << label if service_bindings[label.resource_guid]
end
}
# Custom eager loading: https://github.com/jeremyevans/sequel/blob/master/doc/advanced_associations.rdoc#label-Custom+Eager+Loaders
one_to_many :annotations_sti_eager_load,
dataset: -> { raise 'Must be used for eager loading' },
eager_loader_key: nil, # set up id_map ourselves
eager_loader: proc { |eo|
service_keys = {}
service_bindings = {}
eo[:rows].each do |scb|
scb.associations[:annotations] = []
case scb
when ServiceKey
service_keys[scb.guid] = scb
when ServiceBinding
service_bindings[scb.guid] = scb
end
end
ServiceKeyAnnotationModel.where(resource_guid: service_keys.keys).all do |annotation|
service_keys[annotation.resource_guid].associations[:annotations] << annotation if service_keys[annotation.resource_guid]
end
ServiceBindingAnnotationModel.where(resource_guid: service_bindings.keys).all do |annotation|
service_bindings[annotation.resource_guid].associations[:annotations] << annotation if service_bindings[annotation.resource_guid]
end
}
# Custom eager loading: https://github.com/jeremyevans/sequel/blob/master/doc/advanced_associations.rdoc#label-Custom+Eager+Loaders
one_to_many :operation_sti_eager_load,
dataset: -> { raise 'Must be used for eager loading' },
eager_loader_key: nil, # set up id_map ourselves
eager_loader: proc { |eo|
service_keys = {}
service_bindings = {}
eo[:rows].each do |scb|
case scb
when ServiceKey
scb.associations[:service_key_operation] = nil
service_keys[scb.id] = scb
when ServiceBinding
scb.associations[:service_binding_operation] = nil
service_bindings[scb.id] = scb
end
end
ServiceKeyOperation.where(service_key_id: service_keys.keys).all do |operation|
service_keys[operation.service_key_id].associations[:service_key_operation] = operation
end
ServiceBindingOperation.where(service_binding_id: service_bindings.keys).all do |operation|
service_bindings[operation.service_binding_id].associations[:service_binding_operation] = operation
end
}
end
end
module ServiceCredentialBindingLabels
SERVICE_KEY_LABELS_VIEW = Sequel::Model(:service_key_labels).select(
Sequel.as(:service_key_labels__guid, :guid),
Sequel.as(:service_key_labels__resource_guid, :resource_guid),
Sequel.as(:service_key_labels__key_prefix, :key_prefix),
Sequel.as(:service_key_labels__key_name, :key_name),
Sequel.as(:service_key_labels__value, :value),
Sequel.as(ServiceCredentialBinding::Types::SERVICE_KEY, :type)
)
SERVICE_BINDING_LABELS_VIEW = Sequel::Model(:service_binding_labels).select(
Sequel.as(:service_binding_labels__guid, :guid),
Sequel.as(:service_binding_labels__resource_guid, :resource_guid),
Sequel.as(:service_binding_labels__key_prefix, :key_prefix),
Sequel.as(:service_binding_labels__key_name, :key_name),
Sequel.as(:service_binding_labels__value, :value),
Sequel.as(ServiceCredentialBinding::Types::SERVICE_BINDING, :type)
)
VIEW = [
SERVICE_KEY_LABELS_VIEW,
SERVICE_BINDING_LABELS_VIEW
].inject do |statement, sub_select|
statement.union(sub_select, all: true)
end.freeze
class View < Sequel::Model(VIEW)
plugin :single_table_inheritance,
:type,
model_map: {
'app' => 'VCAP::CloudController::ServiceBindingLabels',
'key' => 'VCAP::CloudController::ServiceKeyLabels'
}
end
end
end
end