GFlisch / Arc4u.Guidance.Doc

Other
5 stars 1 forks source link

The collection types of the nswag Generator should not be 'ObservableCollection' for interfaces #85

Open GFlexi opened 1 year ago

GFlexi commented 1 year ago

The generated interface.nswag uses 'ObservableCollection' for :

"codeGenerators": {
    "openApiToCSharpClient": {
      "responseArrayType": "System.Collections.ObjectModel.ObservableCollection",     
      "arrayType": "System.Collections.ObjectModel.ObservableCollection",
      "arrayBaseType": "System.Collections.ObjectModel.ObservableCollection"
}

The primary use of an interface sdk is necessarly a Front End, so it does not make sense to use ObservableCollection there. Moreover, there no streaming is used, so no observable collection will be emitted.

In my humble opinion, being cross-platform is far more important, so my preference goes for the simplest type possible : ( I never found a way to use 'Array', so I defaulted to IEnumerable )

"codeGenerators": {
    "openApiToCSharpClient": {
      "responseArrayType": "System.Collections.Generic.IEnumerable",     
      "arrayType": "System.Collections.Generic.IEnumerable",
      "arrayBaseType": "System.Collections.Generic.IEnumerable"
}
maxime-poulain commented 1 year ago

I agree with you @GFlexi about not using ObservableCollection for deserialization of collections.

ObservableCollection emits events when its content changes. It is just less performant. This is useful for frontend that needs support for dual binding. Therefore if a developer needs an ObservableCollection he should be responsible for having one.

Under the hood an ObservableCollection is a Collection which uses internally a List<T>.

Going with a List or an Array would be the best choice actually.

If messages/dtos/objects that transit must be considered as immutable then an Array is the preferred choice.

Otherwise a List is good too.

Some references in NET 6.0: https://github.com/dotnet/runtime/blob/release/6.0/src/libraries/System.ObjectModel/src/System/Collections/ObjectModel/ObservableCollection.cs https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Collections/ObjectModel/Collection.cs

I'd say that introducing this extension method could help.

public static class EnumerableExtensions
{
    public static ObservableCollection<T> ToObservableCollection<T>(this IEnumerable<T> source)
    {
        return new ObservableCollection<T>(source);
    }
}

Note that the code above should not be part of non frontend project/code.