@@ -157,123 +157,171 @@ defmodule Astarte.Cases.Device do
157157 end
158158
159159 defp interfaces_for_update do
160+ interface_specs = [
161+ { :individual_datastream_device ,
162+ fn acc -> new_interfaces ( individual_datastream_device ( ) , acc ) end } ,
163+ { :individual_datastream_server ,
164+ fn acc -> new_interfaces ( individual_datastream_server ( ) , acc ) end } ,
165+ { :object_datastream_device , fn acc -> new_interfaces ( object_datastream_device ( ) , acc ) end } ,
166+ { :object_datastream_server , fn acc -> new_interfaces ( object_datastream_server ( ) , acc ) end } ,
167+ { :properties_device , fn acc -> new_interfaces ( properties_device ( ) , acc ) end } ,
168+ { :properties_server , fn acc -> new_interfaces ( properties_server ( ) , acc ) end } ,
169+ { :fallible_interfaces , fn acc -> new_interfaces ( fallible_interfaces ( ) , acc ) end } ,
170+ { :individual_downsampable , fn acc -> new_interfaces ( individual_downsampable ( ) , acc ) end } ,
171+ { :object_downsampable , fn acc -> new_interfaces ( object_downsampable ( ) , acc ) end } ,
172+ { :properties_server_allow_unset ,
173+ fn acc -> new_interfaces ( properties_server_allow_unset ( ) , acc ) end } ,
174+ { :properties_server_without_unset ,
175+ fn acc -> new_interfaces ( properties_server_without_unset ( ) , acc ) end } ,
176+ { :explicit_timestamps , fn acc -> new_interfaces ( explicit_timestamps ( ) , acc ) end } ,
177+ { :other_interfaces , fn acc -> new_interfaces ( other_interfaces ( ) , acc ) end }
178+ ]
179+
180+ { all_interfaces , named_interfaces } =
181+ Enum . reduce ( interface_specs , { [ ] , % { } } , fn { name , gen_fn } , { acc_interfaces , named } ->
182+ new_ifaces = gen_fn . ( acc_interfaces )
183+ updated_interfaces = Enum . concat ( acc_interfaces , new_ifaces )
184+ updated_named = Map . put ( named , name , new_ifaces )
185+ { updated_interfaces , updated_named }
186+ end )
187+
160188 interfaces =
161189 % {
162- individual_datastream_device: individual_datastream_device ( ) ,
163- individual_datastream_server: individual_datastream_server ( ) ,
164- object_datastream_device: object_datastream_device ( ) ,
165- object_datastream_server: object_datastream_server ( ) ,
166- properties_device: properties_device ( ) ,
167- properties_server: properties_server ( ) ,
168- fallible_interfaces: fallible_interfaces ( ) ,
169- individual_downsampable: individual_downsampable ( ) ,
170- object_downsampable: object_downsampable ( ) ,
171- properties_server_allow_unset: properties_server_allow_unset ( ) ,
172- properties_server_without_unset: properties_server_without_unset ( ) ,
173- explicit_timestamps: explicit_timestamps ( ) ,
174- other_interfaces: other_interfaces ( )
190+ individual_datastream_device: named_interfaces . individual_datastream_device ,
191+ individual_datastream_server: named_interfaces . individual_datastream_server ,
192+ object_datastream_device: named_interfaces . object_datastream_device ,
193+ object_datastream_server: named_interfaces . object_datastream_server ,
194+ properties_device: named_interfaces . properties_device ,
195+ properties_server: named_interfaces . properties_server ,
196+ fallible_interfaces: named_interfaces . fallible_interfaces ,
197+ individual_downsampable: named_interfaces . individual_downsampable ,
198+ object_downsampable: named_interfaces . object_downsampable ,
199+ properties_server_allow_unset: named_interfaces . properties_server_allow_unset ,
200+ properties_server_without_unset: named_interfaces . properties_server_without_unset ,
201+ explicit_timestamps: named_interfaces . explicit_timestamps ,
202+ other_interfaces: named_interfaces . other_interfaces
175203 }
176204
177205 % {
178- interfaces: interfaces |> Map . values ( ) |> Enum . concat ( ) ,
206+ interfaces: all_interfaces ,
179207 downsampable_individual_interfaces: interfaces . individual_downsampable ,
180208 downsampable_object_interfaces: interfaces . object_downsampable ,
181209 explicit_timestamp_interfaces: interfaces . explicit_timestamps
182210 }
183211 end
184212
213+ defp new_interfaces ( interface_gen , previous_interfaces ) do
214+ installed_interfaces = previous_interfaces |> Enum . map ( & { & 1 . name , & 1 . major_version } )
215+
216+ installed_normalized_interfaces =
217+ previous_interfaces |> Enum . map ( & normalize_name ( & 1 . name ) )
218+
219+ interface_gen =
220+ interface_gen
221+ |> filter ( fn interface ->
222+ name_and_major = { interface . name , interface . major_version }
223+ normalized_name = normalize_name ( interface . name )
224+
225+ name_and_major not in installed_interfaces and
226+ normalized_name not in installed_normalized_interfaces
227+ end )
228+
229+ interface_gen
230+ |> list_of ( min_length: 1 )
231+ |> Enum . at ( 0 )
232+ |> cleanup_duplicates ( )
233+ end
234+
235+ defp cleanup_duplicates ( interfaces ) do
236+ interfaces
237+ |> Enum . reduce ( [ ] , fn new_interface , acc_interfaces ->
238+ prev = acc_interfaces |> Enum . map ( & { & 1 . name , & 1 . major_version } )
239+ prev_normalized = acc_interfaces |> Enum . map ( & normalize_name ( & 1 . name ) )
240+ name_and_major = { new_interface . name , new_interface . major_version }
241+ normalized_name = normalize_name ( new_interface . name )
242+
243+ if name_and_major not in prev and normalized_name not in prev_normalized do
244+ [ new_interface | acc_interfaces ]
245+ else
246+ acc_interfaces
247+ end
248+ end )
249+ |> Enum . reverse ( )
250+ end
251+
252+ defp normalize_name ( interface_name ) do
253+ interface_name
254+ |> String . replace ( "-" , "" )
255+ |> String . replace ( "." , "" )
256+ |> String . downcase ( )
257+ end
258+
185259 defp individual_datastream_device do
186260 [ ownership: :device , aggregation: :individual , type: :datastream ]
187261 |> InterfaceGenerator . interface ( )
188- |> list_of ( min_length: 1 )
189- |> Enum . at ( 0 )
190262 end
191263
192264 defp individual_datastream_server do
193265 [ ownership: :server , aggregation: :individual , type: :datastream ]
194266 |> InterfaceGenerator . interface ( )
195- |> list_of ( min_length: 1 )
196- |> Enum . at ( 0 )
197267 end
198268
199269 defp object_datastream_device do
200270 [ ownership: :device , aggregation: :object , type: :datastream ]
201271 |> InterfaceGenerator . interface ( )
202- |> list_of ( min_length: 1 )
203- |> Enum . at ( 0 )
204272 end
205273
206274 defp object_datastream_server do
207275 [ ownership: :server , aggregation: :object , type: :datastream ]
208276 |> InterfaceGenerator . interface ( )
209- |> list_of ( min_length: 1 )
210- |> Enum . at ( 0 )
211277 end
212278
213279 defp properties_device do
214280 [ ownership: :device , type: :properties ]
215281 |> InterfaceGenerator . interface ( )
216- |> list_of ( min_length: 1 )
217- |> Enum . at ( 0 )
218282 end
219283
220284 defp properties_server do
221285 [ ownership: :server , type: :properties ]
222286 |> InterfaceGenerator . interface ( )
223- |> list_of ( min_length: 1 )
224- |> Enum . at ( 0 )
225287 end
226288
227289 defp properties_server_allow_unset do
228290 [ ownership: :server , type: :properties ]
229291 |> InterfaceGenerator . interface ( )
230- |> list_of ( min_length: 1 )
231- |> Enum . at ( 0 )
232- |> customize_mappings ( allow_unset: true )
292+ |> map ( & customize_mappings ( & 1 , allow_unset: true ) )
233293 end
234294
235295 defp properties_server_without_unset do
236296 [ ownership: :server , type: :properties ]
237297 |> InterfaceGenerator . interface ( )
238- |> list_of ( min_length: 1 )
239- |> Enum . at ( 0 )
240- |> customize_mappings ( allow_unset: false )
298+ |> map ( & customize_mappings ( & 1 , allow_unset: false ) )
241299 end
242300
243301 defp fallible_interfaces do
244302 [ ownership: :server ]
245303 |> InterfaceGenerator . interface ( )
246- |> list_of ( min_length: 1 )
247- |> Enum . at ( 0 )
248- |> customize_mappings ( value_type: Enum . random ( fallible_value_types ( ) ) )
304+ |> map ( & customize_mappings ( & 1 , value_type: Enum . random ( fallible_value_types ( ) ) ) )
249305 end
250306
251307 defp individual_downsampable do
252308 [ aggregation: :individual ]
253309 |> InterfaceGenerator . interface ( )
254- |> list_of ( min_length: 1 )
255- |> Enum . at ( 0 )
256- |> customize_mappings ( value_type: Enum . random ( downsampable_value_types ( ) ) )
310+ |> map ( & customize_mappings ( & 1 , value_type: Enum . random ( downsampable_value_types ( ) ) ) )
257311 end
258312
259313 defp object_downsampable do
260314 [ type: :datastream , aggregation: :object ]
261315 |> InterfaceGenerator . interface ( )
262- |> list_of ( min_length: 1 )
263- |> Enum . at ( 0 )
264- |> customize_mappings ( value_type: Enum . random ( downsampable_value_types ( ) ) )
316+ |> map ( & customize_mappings ( & 1 , value_type: Enum . random ( downsampable_value_types ( ) ) ) )
265317 end
266318
267319 defp explicit_timestamps do
268320 [ ownership: :server , type: :datastream , explicit_timestamp: true ]
269321 |> InterfaceGenerator . interface ( )
270- |> list_of ( min_length: 1 )
271- |> Enum . at ( 0 )
272322 end
273323
274324 defp other_interfaces do
275325 InterfaceGenerator . interface ( )
276- |> list_of ( )
277- |> Enum . at ( 0 )
278326 end
279327end
0 commit comments