@@ -5,73 +5,98 @@ module VCAP::CloudController
5
5
class ServiceInstanceListFetcher < BaseListFetcher
6
6
class << self
7
7
def fetch ( message , omniscient : false , readable_spaces_dataset : nil , eager_loaded_associations : [ ] )
8
- dataset = ServiceInstance . dataset . eager ( eager_loaded_associations ) .
9
- join ( :spaces , id : Sequel [ :service_instances ] [ :space_id ] ) .
10
- left_join ( :service_instance_shares , service_instance_guid : Sequel [ :service_instances ] [ :guid ] )
11
-
12
- unless omniscient
13
- dataset = dataset . where do
14
- ( Sequel [ :spaces ] [ :guid ] =~ readable_spaces_dataset ) |
15
- ( Sequel [ :service_instance_shares ] [ :target_space_guid ] =~ readable_spaces_dataset )
16
- end
17
- end
8
+ dataset = ServiceInstance . dataset . select_all ( :service_instances )
9
+
10
+ if omniscient
11
+ dataset = filter ( dataset , message )
12
+ else
13
+ # Reduce query complexity by fetching instances and shared instances separately
14
+ instances = dataset . clone . join ( :spaces , id : :service_instances__space_id )
15
+ instances = instances . where ( Sequel [ :spaces ] [ :guid ] =~ readable_spaces_dataset )
16
+ instances = filter ( instances , message )
17
+
18
+ shared_instances = dataset . clone . join ( :service_instance_shares , service_instance_guid : :service_instances__guid )
19
+ shared_instances = shared_instances . where ( Sequel [ :service_instance_shares ] [ :target_space_guid ] =~ readable_spaces_dataset )
20
+ shared_instances = filter ( shared_instances , message )
18
21
19
- if message . requested? ( :service_plan_names ) || message . requested? ( :service_plan_guids )
20
- dataset = dataset . left_join ( :service_plans ,
21
- id : Sequel [ :service_instances ] [ :service_plan_id ] )
22
+ # UNION the two datasets
23
+ dataset = instances . union ( shared_instances , all : true , alias : :service_instances )
22
24
end
23
25
24
- filter ( dataset , message ) .
25
- select_all ( :service_instances ) .
26
- distinct
26
+ dataset = dataset . distinct ( :service_instances__id )
27
+ dataset . eager ( eager_loaded_associations )
27
28
end
28
29
29
30
private
30
31
31
32
def filter ( dataset , message )
32
- dataset = dataset . where ( service_instances__name : message . names ) if message . requested? ( :names )
33
-
34
- if message . requested? ( :type )
35
- dataset = case message . type
36
- when 'managed'
37
- dataset . where { ( Sequel [ :service_instances ] [ :is_gateway_service ] =~ true ) }
38
- when 'user-provided'
39
- dataset . where { ( Sequel [ :service_instances ] [ :is_gateway_service ] =~ false ) }
40
- end
41
- end
33
+ dataset = filter_names ( dataset , message ) if message . requested? ( :names )
34
+ dataset = filter_type ( dataset , message ) if message . requested? ( :type )
35
+ dataset = filter_organization_guids ( dataset , message ) if message . requested? ( :organization_guids )
36
+ dataset = filter_space_guids ( dataset , message ) if message . requested? ( :space_guids )
37
+ dataset = filter_service_plan_names ( dataset , message ) if message . requested? ( :service_plan_names )
38
+ dataset = filter_service_plan_guids ( dataset , message ) if message . requested? ( :service_plan_guids )
39
+ dataset = filter_label ( dataset , message ) if message . requested? ( :label_selector )
42
40
43
- if message . requested? ( :organization_guids )
44
- spaces_in_orgs = Space . dataset . select ( :spaces__guid ) .
45
- join ( :organizations , id : Sequel [ :spaces ] [ :organization_id ] ) .
46
- where ( Sequel [ :organizations ] [ :guid ] =~ message . organization_guids )
41
+ super ( message , dataset , ServiceInstance )
42
+ end
47
43
48
- dataset = dataset . where do
49
- ( Sequel [ :spaces ] [ :guid ] =~ spaces_in_orgs ) |
50
- ( Sequel [ :service_instance_shares ] [ :target_space_guid ] =~ spaces_in_orgs )
51
- end
52
- end
44
+ def filter_names ( dataset , message )
45
+ dataset . where ( service_instances__name : message . names )
46
+ end
53
47
54
- if message . requested? ( :space_guids )
55
- dataset = dataset . where do
56
- ( Sequel [ :spaces ] [ :guid ] =~ message . space_guids ) |
57
- ( Sequel [ :service_instance_shares ] [ :target_space_guid ] =~ message . space_guids )
58
- end
48
+ def filter_type ( dataset , message )
49
+ case message . type
50
+ when 'managed'
51
+ dataset . where ( Sequel [ :service_instances ] [ :is_gateway_service ] =~ true )
52
+ when 'user-provided'
53
+ dataset . where ( Sequel [ :service_instances ] [ :is_gateway_service ] =~ false )
54
+ else
55
+ dataset
59
56
end
57
+ end
60
58
61
- dataset = dataset . where { Sequel [ :service_plans ] [ :guid ] =~ message . service_plan_guids } if message . requested? ( :service_plan_guids )
59
+ def filter_organization_guids ( dataset , message )
60
+ dataset = dataset . join ( :spaces , id : :service_instances__space_id ) unless joined? ( dataset , :spaces )
61
+ dataset = dataset . left_join ( :service_instance_shares , service_instance_guid : :service_instances__guid ) unless joined? ( dataset , :service_instance_shares )
62
62
63
- dataset = dataset . where { Sequel [ :service_plans ] [ :name ] =~ message . service_plan_names } if message . requested? ( :service_plan_names )
63
+ spaces_in_orgs = Space . dataset . select ( :spaces__guid ) .
64
+ join ( :organizations , id : :spaces__organization_id ) .
65
+ where ( Sequel [ :organizations ] [ :guid ] =~ message . organization_guids )
64
66
65
- if message . requested? ( :label_selector )
66
- dataset = LabelSelectorQueryGenerator . add_selector_queries (
67
- label_klass : ServiceInstanceLabelModel ,
68
- resource_dataset : dataset ,
69
- requirements : message . requirements ,
70
- resource_klass : ServiceInstance
71
- )
72
- end
67
+ dataset . where ( ( Sequel [ :spaces ] [ :guid ] =~ spaces_in_orgs ) | ( Sequel [ :service_instance_shares ] [ :target_space_guid ] =~ spaces_in_orgs ) )
68
+ end
73
69
74
- super ( message , dataset , ServiceInstance )
70
+ def filter_space_guids ( dataset , message )
71
+ dataset = dataset . join ( :spaces , id : :service_instances__space_id ) unless joined? ( dataset , :spaces )
72
+ dataset = dataset . left_join ( :service_instance_shares , service_instance_guid : :service_instances__guid ) unless joined? ( dataset , :service_instance_shares )
73
+
74
+ dataset . where ( ( Sequel [ :spaces ] [ :guid ] =~ message . space_guids ) | ( Sequel [ :service_instance_shares ] [ :target_space_guid ] =~ message . space_guids ) )
75
+ end
76
+
77
+ def filter_service_plan_names ( dataset , message )
78
+ dataset = dataset . left_join ( :service_plans , id : :service_instances__service_plan_id ) unless joined? ( dataset , :service_plans )
79
+
80
+ dataset . where ( Sequel [ :service_plans ] [ :name ] =~ message . service_plan_names )
81
+ end
82
+
83
+ def filter_service_plan_guids ( dataset , message )
84
+ dataset = dataset . left_join ( :service_plans , id : :service_instances__service_plan_id ) unless joined? ( dataset , :service_plans )
85
+
86
+ dataset . where ( Sequel [ :service_plans ] [ :guid ] =~ message . service_plan_guids )
87
+ end
88
+
89
+ def filter_label ( dataset , message )
90
+ LabelSelectorQueryGenerator . add_selector_queries (
91
+ label_klass : ServiceInstanceLabelModel ,
92
+ resource_dataset : dataset ,
93
+ requirements : message . requirements ,
94
+ resource_klass : ServiceInstance
95
+ )
96
+ end
97
+
98
+ def joined? ( dataset , table )
99
+ dataset . opts [ :join ] &.any? { |j | j . table_expr == table }
75
100
end
76
101
end
77
102
end
0 commit comments