Skip to content
Ian Johnson edited this page Jul 2, 2018 · 15 revisions

Below is a list of collections that can be imported and what class implements them

  • IList<T> - implemented using List<T>
  • ICollection<T> - implemented using List<T>
  • IEnumerable<T> - implemented using T[ ]
  • ReadOnlyCollection<T> - implemented using ReadOnlyCollection<T>
  • IReadOnlyList<T> - implemented using ReadOnlyCollection<T>
  • IReadOnlyCollection<T> - implemented using ReadOnlyCollection<T>
  • T[ ] - an array will be created with a length matching the number of imports returned
  • ImmutableList<T> - System.Collections.Immutable.* classes are supported
  • Custom Collections - any class that has a public constructor that takes IEnumerabe<T> or T[ ]

Filtering Exports

In certain situation is can be useful to import only certain exports and not others. To help address this usecase you can provide a filter to be applied when locating exports. Below is an example of importing classes that are attributed with CustomAttribute.

container.Configure(c => c.Export<SomeType>().
                           WithCtorCollectionParam<IReadOnlyCollection<ISomeDependency>,ISomeDependency>().
                           Consider(ExportsThat.HaveAttribute<CustomAttribute>>()));

Sorting Collections

Another common use case when working with collection is applying a sort order. By default exports are ordered by priority or if no priority is specified for any of the exports then by registration order. If this order doesn't work then you have the option of applying a sort order during importing. Below is an example of sorting a readonly collection by the Name property on ISomeDependency.

container.Configure(c => c.Export<SomeType>().
                           WithCtorCollectionParam<IReadOnlyCollection<ISomeDependency>,ISomeDependency>().
                           SortByProperty(x => x.Name));

Note: SortBy is provided so you can do more advanced sorting than just by property

Custom IEnumerable<T>

By default IEnumerable<T> is T[]. If you want to return something different for IEnumerable<T> you can implement IEnumerableCreator and provide it when constructing the container

var container = new DependencyInjectionContainer(
    c => c.Behaviors.CustomEnumerableCreator = new ReadOnlyCreator());

public class ReadOnlyCreator : IEnumerableCreator
{
  public IEnumerable<T> CreateEnumerable<T>(IExportLocatorScope scope, T[] array)
  {
    return new ReadOnlyCollection<T>(array);
  }
}

Clone this wiki locally