forest_admin_datasource_customizer 1.0.0.pre.beta.61 → 1.0.0.pre.beta.63

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 01a3e9d078567da75ac00fbce2df8722f362800ac0e67108691755f8ea3908ea
4
- data.tar.gz: b7fb6555dcefb5e78f6fceba1afaca3459d73f52692be6492d6992a9875c3de8
3
+ metadata.gz: 2931a28a63603345c0a55e07c2a4519eab8550fc464d8efe04e41a715de800c9
4
+ data.tar.gz: ec4a9c635c12d3b274a4829a6f90e56dca336d4e53831c96652e987edc071755
5
5
  SHA512:
6
- metadata.gz: abfb2618846aebd32cacb55c85a074786e59e72596baefded111a7e1a801622ee9d5b7bc1ab19c3c74018a19e692fb600c9fa47043b146efb1c4fc438cff3b82
7
- data.tar.gz: ee3c04a82b7b8cc35ee009a935b26f06e014bfb95b6d34b8e82263c3433ba665619d59ad9795020c9399cd83d538758cef97aad01725f7a5701cffb1b0def061
6
+ metadata.gz: 5707661b9169c5bc653f0ab08279e3874419fc259e87df8e8b94481576f6f2ec392815c9b6d5ed320c70086cb158a30d436c67f3e94e6be6fd80134a58ac01b0
7
+ data.tar.gz: 2ef42a74baf4880a54cb7fcf4d36673cacab8d2a6745c32ffda12d3cf4ceb2b9b9d1d38e031f3046ac30e8682d3d3772733618d499dd7dc9a6634c92c2048b2a
@@ -134,6 +134,8 @@ module ForestAdminDatasourceCustomizer
134
134
  prefix, suffix = path.split(':')
135
135
  field = @child_collection.schema[:fields][prefix]
136
136
 
137
+ return value if field.type == 'PolymorphicManyToOne'
138
+
137
139
  if field.type != 'Column'
138
140
  foreign_collection = @datasource.get_collection(field.foreign_collection)
139
141
 
@@ -16,6 +16,15 @@ module ForestAdminDatasourceCustomizer
16
16
  index = path.index(':')
17
17
  return @computeds[path] if index.nil?
18
18
 
19
+ if schema[:fields][path[0, index]].type == 'PolymorphicManyToOne'
20
+ ForestAdminAgent::Facades::Container.logger.log(
21
+ 'Debug',
22
+ "Cannot compute field over polymorphic relation #{name}.#{path[0, index]}."
23
+ )
24
+
25
+ return @computeds[path]
26
+ end
27
+
19
28
  foreign_collection = schema[:fields][path[0, index]].foreign_collection
20
29
  association = @datasource.get_collection(foreign_collection)
21
30
 
@@ -27,6 +36,10 @@ module ForestAdminDatasourceCustomizer
27
36
 
28
37
  # Check that all dependencies exist and are columns
29
38
  computed.dependencies.each do |field|
39
+ if field.include?(':') && schema[:fields][field.partition(':')[0]].type == 'PolymorphicManyToOne'
40
+ raise ForestException,
41
+ "Dependencies over a polymorphic relations(#{self.name}.#{field.partition(":")[0]}) are forbidden"
42
+ end
30
43
  FieldValidator.validate(self, field)
31
44
  end
32
45
 
@@ -90,12 +103,14 @@ module ForestAdminDatasourceCustomizer
90
103
  if path.include?(':')
91
104
  prefix = path.split(':')[0]
92
105
  schema = collection.schema[:fields][prefix]
93
- association = collection.datasource.get_collection(schema.foreign_collection)
106
+ if schema.type != 'PolymorphicManyToOne'
107
+ association = collection.datasource.get_collection(schema.foreign_collection)
94
108
 
95
- return Projection.new([path])
96
- .unnest
97
- .replace { |sub_path| rewrite_field(association, sub_path) }
98
- .nest(prefix: prefix)
109
+ return Projection.new([path])
110
+ .unnest
111
+ .replace { |sub_path| rewrite_field(association, sub_path) }
112
+ .nest(prefix: prefix)
113
+ end
99
114
  end
100
115
 
101
116
  # Computed field that we own: recursively replace by dependencies
@@ -11,7 +11,8 @@ module ForestAdminDatasourceCustomizer
11
11
  schema = sub_schema.dup
12
12
  schema[:fields] = sub_schema[:fields].dup
13
13
 
14
- schema[:fields].map do |_name, field_schema|
14
+ schema[:fields].each do |name, field_schema|
15
+ field_schema = field_schema.dup
15
16
  if field_schema.type == 'Column'
16
17
  new_operators = Operators.all.select do |operator|
17
18
  ConditionTreeEquivalent.equivalent_tree?(operator, field_schema.filter_operators,
@@ -19,9 +20,9 @@ module ForestAdminDatasourceCustomizer
19
20
  end
20
21
 
21
22
  field_schema.filter_operators = new_operators
22
- else
23
- field_schema
24
23
  end
24
+
25
+ schema[:fields][name] = field_schema
25
26
  end
26
27
 
27
28
  schema
@@ -17,6 +17,13 @@ module ForestAdminDatasourceCustomizer
17
17
  child_collection, name
18
18
  )
19
19
 
20
+ @child_collection.schema[:fields].each do |field_name, field_schema|
21
+ next unless field_schema.type == 'PolymorphicManyToOne' &&
22
+ [field_schema.foreign_key, field_schema.foreign_key_type_field].include?(name)
23
+
24
+ raise ForestException, "Cannot remove field '#{self.name}.#{name}', because it's implied " \
25
+ "in a polymorphic relation '#{self.name}.#{field_name}'"
26
+ end
20
27
  if visible
21
28
  @blacklist.delete(name)
22
29
  else
@@ -37,14 +44,15 @@ module ForestAdminDatasourceCustomizer
37
44
 
38
45
  def refine_schema(child_schema)
39
46
  fields = {}
47
+ schema = child_schema.dup
40
48
 
41
- child_schema[:fields].each do |name, field|
49
+ schema[:fields].each do |name, field|
42
50
  fields[name] = field if published?(name)
43
51
  end
44
52
 
45
- child_schema[:fields] = fields
53
+ schema[:fields] = fields
46
54
 
47
- child_schema
55
+ schema
48
56
  end
49
57
 
50
58
  def published?(name)
@@ -33,6 +33,7 @@ module ForestAdminDatasourceCustomizer
33
33
 
34
34
  def remove_collection(collection_name)
35
35
  validate_collection_names([collection_name])
36
+ validate_is_removable(collection_name)
36
37
 
37
38
  # Delete the collection
38
39
  @blacklist << collection_name
@@ -48,6 +49,17 @@ module ForestAdminDatasourceCustomizer
48
49
 
49
50
  private
50
51
 
52
+ def validate_is_removable(collection_name)
53
+ collection = get_collection(collection_name)
54
+ collection.schema[:fields].each do |field_name, field_schema|
55
+ next unless field_schema.type == 'PolymorphicOneToOne' || field_schema.type == 'PolymorphicOneToMany'
56
+
57
+ inverse = ForestAdminDatasourceToolkit::Utils::Collection.get_inverse_relation(collection, field_name)
58
+
59
+ raise ForestException, "Cannot remove #{collection.name} because it's a potential target of polymorphic relation #{field_schema.foreign_collection}.#{inverse}"
60
+ end
61
+ end
62
+
51
63
  def validate_collection_names(names)
52
64
  names.each { |name| get_collection(name) }
53
65
  end
@@ -177,7 +177,7 @@ module ForestAdminDatasourceCustomizer
177
177
  prefix = field.split(':').first
178
178
  field_schema = schema[:fields][prefix]
179
179
 
180
- return [field] if field_schema.type == 'Column'
180
+ return [field] if field_schema.type == 'Column' || field_schema.type == 'PolymorphicManyToOne'
181
181
 
182
182
  relation = datasource.get_collection(field_schema.foreign_collection)
183
183
  result = []
@@ -55,6 +55,16 @@ module ForestAdminDatasourceCustomizer
55
55
  "Cannot rename a collection twice: #{@to_child_name[current_name]}->#{current_name}->#{new_name}"
56
56
  end
57
57
 
58
+ get_collection(current_name).schema[:fields].each do |field_name, field_schema|
59
+ next unless field_schema.type == 'PolymorphicOneToOne' || field_schema.type == 'PolymorphicOneToMany'
60
+
61
+ reverse_relation_name = Utils::Collection.get_inverse_relation(get_collection(current_name), field_name)
62
+
63
+ raise Exceptions::ForestException,
64
+ "Cannot rename collection #{current_name} because it's a target of a polymorphic relation " \
65
+ "'#{field_schema.foreign_collection}.#{reverse_relation_name}'"
66
+ end
67
+
58
68
  @from_child_name[current_name] = new_name
59
69
  @to_child_name[new_name] = current_name
60
70
 
@@ -13,7 +13,7 @@ module ForestAdminDatasourceCustomizer
13
13
  fields = {}
14
14
 
15
15
  sub_schema[:fields].each do |name, old_schema|
16
- if old_schema.type != 'Column'
16
+ if old_schema.type != 'Column' && old_schema.type != 'PolymorphicManyToOne'
17
17
  old_schema.foreign_collection = datasource.get_collection_name(old_schema.foreign_collection)
18
18
  if old_schema.type == 'ManyToMany'
19
19
  old_schema.through_collection = datasource.get_collection_name(old_schema.through_collection)
@@ -3,6 +3,7 @@ module ForestAdminDatasourceCustomizer
3
3
  module RenameField
4
4
  class RenameFieldCollectionDecorator < ForestAdminDatasourceToolkit::Decorators::CollectionDecorator
5
5
  include ForestAdminDatasourceToolkit::Decorators
6
+ include ForestAdminDatasourceToolkit::Exceptions
6
7
  include ForestAdminDatasourceToolkit::Components::Query::ConditionTree
7
8
 
8
9
  attr_accessor :from_child_collection, :to_child_collection
@@ -22,6 +23,14 @@ module ForestAdminDatasourceCustomizer
22
23
 
23
24
  ForestAdminDatasourceToolkit::Validations::FieldValidator.validate_name(name, new_name)
24
25
 
26
+ @child_collection.schema[:fields].each do |field_name, field_schema|
27
+ next unless field_schema.type == 'PolymorphicManyToOne' &&
28
+ [field_schema.foreign_key, field_schema.foreign_key_type_field].include?(current_name)
29
+
30
+ raise ForestException, "Cannot rename '#{name}.#{current_name}', because it's implied " \
31
+ "in a polymorphic relation '#{name}.#{field_name}'"
32
+ end
33
+
25
34
  # Revert previous renaming (avoids conflicts and need to recurse on @to_child_collection).
26
35
  if to_child_collection[current_name]
27
36
  child_name = to_child_collection[current_name]
@@ -41,6 +50,7 @@ module ForestAdminDatasourceCustomizer
41
50
 
42
51
  def refine_schema(sub_schema)
43
52
  fields = {}
53
+ schema = sub_schema.dup
44
54
 
45
55
  sub_schema[:fields].each do |old_name, old_schema|
46
56
  case old_schema.type
@@ -58,9 +68,9 @@ module ForestAdminDatasourceCustomizer
58
68
  fields[from_child_collection[old_name] || old_name] = old_schema
59
69
  end
60
70
 
61
- sub_schema[:fields] = fields
71
+ schema[:fields] = fields
62
72
 
63
- sub_schema
73
+ schema
64
74
  end
65
75
 
66
76
  def refine_filter(_caller, filter = nil)
@@ -89,7 +99,7 @@ module ForestAdminDatasourceCustomizer
89
99
  def list(caller, filter, projection)
90
100
  child_projection = projection.replace { |field| path_to_child_collection(field) }
91
101
  records = @child_collection.list(caller, filter, child_projection)
92
- return records if child_projection == projection
102
+ return records if child_projection.sort == projection.sort
93
103
 
94
104
  records.map { |record| record_from_child_collection(record) }
95
105
  end
@@ -134,9 +144,11 @@ module ForestAdminDatasourceCustomizer
134
144
  child_field = paths[0]
135
145
  relation_name = from_child_collection[child_field] || child_field
136
146
  relation_schema = schema[:fields][relation_name]
137
- relation = datasource.get_collection(relation_schema.foreign_collection)
147
+ if relation_schema.type != 'PolymorphicManyToOne'
148
+ relation = datasource.get_collection(relation_schema.foreign_collection)
138
149
 
139
- return "#{relation_name}:#{relation.path_from_child_collection(paths[1])}"
150
+ return "#{relation_name}:#{relation.path_from_child_collection(paths[1])}"
151
+ end
140
152
  end
141
153
 
142
154
  from_child_collection[path] ||= path
@@ -148,10 +160,12 @@ module ForestAdminDatasourceCustomizer
148
160
  paths = path.split(':')
149
161
  relation_name = paths[0]
150
162
  relation_schema = schema[:fields][relation_name]
151
- relation = datasource.get_collection(relation_schema.foreign_collection)
152
- child_field = to_child_collection[relation_name] || relation_name
163
+ if relation_schema.type != 'PolymorphicManyToOne'
164
+ relation = datasource.get_collection(relation_schema.foreign_collection)
165
+ child_field = to_child_collection[relation_name] || relation_name
153
166
 
154
- return "#{child_field}:#{relation.path_to_child_collection(paths[1])}"
167
+ return "#{child_field}:#{relation.path_to_child_collection(paths[1])}"
168
+ end
155
169
  end
156
170
 
157
171
  to_child_collection[path] ||= path
@@ -173,8 +187,8 @@ module ForestAdminDatasourceCustomizer
173
187
  field = from_child_collection[child_field] || child_field
174
188
  field_schema = schema[:fields][field]
175
189
 
176
- # Perform the mapping, recurse for relations
177
- if field_schema.type == 'Column' || value.nil?
190
+ # Perform the mapping, recurse for relation
191
+ if field_schema.type == 'Column' || field_schema.type == 'PolymorphicManyToOne' || value.nil?
178
192
  record[field] = value
179
193
  else
180
194
  relation = datasource.get_collection(field_schema.foreign_collection)
@@ -104,7 +104,17 @@ module ForestAdminDatasourceCustomizer
104
104
  collection.schema[:fields].each do |name, field|
105
105
  fields.push([name, field]) if field.type == 'Column'
106
106
 
107
- next unless extended && (field.type == 'ManyToOne' || field.type == 'OneToOne')
107
+ if field.type == 'PolymorphicManyToOne'
108
+ ForestAdminAgent::Facades::Container.logger.log(
109
+ 'Debug',
110
+ "We're not searching through #{self.name}.#{name} because it's a polymorphic relation. " \
111
+ "You can override the default search behavior with 'replace_search'. " \
112
+ 'See more: https://docs.forestadmin.com/developer-guide-agents-ruby/agent-customization/search'
113
+ )
114
+ end
115
+
116
+ next unless extended &&
117
+ (field.type == 'ManyToOne' || field.type == 'OneToOne' || field.type == 'PolymorphicOneToOne')
108
118
 
109
119
  related = collection.datasource.get_collection(field.foreign_collection)
110
120
 
@@ -72,10 +72,10 @@ module ForestAdminDatasourceCustomizer
72
72
  if field_schema&.type == 'Column'
73
73
  # We either call the customer handler or a default one that does nothing.
74
74
  handler = @handlers[key] || proc { |v| { key => v } }
75
- field_patch = if context.record[key] && handler.call(context.record[key], context)
75
+ field_patch = if context.record.key?(key) && handler.call(context.record[key], context)
76
76
  handler.call(context.record[key], context)
77
77
  else
78
- []
78
+ {}
79
79
  end
80
80
 
81
81
  if field_patch && !field_patch.is_a?(Hash)
@@ -84,10 +84,17 @@ module ForestAdminDatasourceCustomizer
84
84
 
85
85
  # Isolate change to our own value (which should not recurse) and the rest which should
86
86
  # trigger the other handlers.
87
- value = field_patch[key] || nil
87
+ if field_patch.key?(key)
88
+ value = field_patch[key]
89
+ is_value = true
90
+ else
91
+ value = nil
92
+ is_value = false
93
+ end
94
+
88
95
  new_patch = rewrite_patch(context.caller, context.action, field_patch.except(key), used + [key])
89
96
 
90
- value ? deep_merge({ key => value }, new_patch) : new_patch
97
+ is_value ? deep_merge({ key => value }, new_patch) : new_patch
91
98
  elsif field_schema&.type == 'ManyToOne' || field_schema&.type == 'OneToOne'
92
99
  # Delegate relations to the appropriate collection.
93
100
  relation = datasource.get_collection(field_schema.foreign_collection)
@@ -1,3 +1,3 @@
1
1
  module ForestAdminDatasourceCustomizer
2
- VERSION = "1.0.0-beta.61"
2
+ VERSION = "1.0.0-beta.63"
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: forest_admin_datasource_customizer
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.0.pre.beta.61
4
+ version: 1.0.0.pre.beta.63
5
5
  platform: ruby
6
6
  authors:
7
7
  - Matthieu
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: exe
11
11
  cert_chain: []
12
- date: 2024-07-26 00:00:00.000000000 Z
12
+ date: 2024-08-20 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: activesupport