Skip to content

Latest commit

 

History

History
200 lines (169 loc) · 4.07 KB

File metadata and controls

200 lines (169 loc) · 4.07 KB

Func with arguments

Demonstrates how to use Func with arguments for dynamic creation of instances with runtime parameters.

using Shouldly;
using Pure.DI;
using System.Collections.Immutable;

DI.Setup(nameof(Composition))
    .Bind().As(Lifetime.Singleton).To<Clock>()
    .Bind().To<Person>()
    .Bind().To<Team>()

    // Composition root
    .Root<ITeam>("Team");

var composition = new Composition();
var team = composition.Team;

team.Members.Length.ShouldBe(3);

team.Members[0].Id.ShouldBe(10);
team.Members[0].Name.ShouldBe("Nik");

team.Members[1].Id.ShouldBe(20);
team.Members[1].Name.ShouldBe("Mike");

team.Members[2].Id.ShouldBe(30);
team.Members[2].Name.ShouldBe("Jake");

interface IClock
{
    DateTimeOffset Now { get; }
}

class Clock : IClock
{
    public DateTimeOffset Now => DateTimeOffset.Now;
}

interface IPerson
{
    int Id { get; }

    string Name { get; }
}

class Person(string name, IClock clock, int id)
    : IPerson
{
    public int Id => id;

    public string Name => name;
}

interface ITeam
{
    ImmutableArray<IPerson> Members { get; }
}

class Team(Func<int, string, IPerson> personFactory) : ITeam
{
    public ImmutableArray<IPerson> Members { get; } =
    [
        personFactory(10, "Nik"),
        personFactory(20, "Mike"),
        personFactory(30, "Jake")
    ];
}
Running this code sample locally
dotnet --list-sdk
  • Create a net10.0 (or later) console application
dotnet new console -n Sample
dotnet add package Pure.DI
dotnet add package Shouldly
  • Copy the example code into the Program.cs file

You are ready to run the example 🚀

dotnet run

Note

Func with arguments provides flexibility for scenarios where you need to pass runtime parameters during instance creation.

The following partial class will be generated:

partial class Composition
{
#if NET9_0_OR_GREATER
  private readonly Lock _lock = new Lock();
#else
  private readonly Object _lock = new Object();
#endif

  private Clock? _singletonClock62;

  public ITeam Team
  {
    [MethodImpl(MethodImplOptions.AggressiveInlining)]
    get
    {
      Func<int, string, IPerson> perBlockFunc404;
      Func<int, string, IPerson> localFactory2 = new Func<int, string, IPerson>((int localArg11, string localArg2) =>
      {
        lock (_lock)
        {
          int overriddenInt32 = localArg11;
          string overriddenString2 = localArg2;
          if (_singletonClock62 is null)
            lock (_lock)
              if (_singletonClock62 is null)
              {
                _singletonClock62 = new Clock();
              }

          return new Person(overriddenString2, _singletonClock62, overriddenInt32);
        }
      });
      perBlockFunc404 = localFactory2;
      return new Team(perBlockFunc404);
    }
  }
}

Class diagram:

---
 config:
  maxTextSize: 2147483647
  maxEdges: 2147483647
  class:
   hideEmptyMembersBox: true
---
classDiagram
	Person --|> IPerson
	Team --|> ITeam
	Composition ..> Team : ITeam Team
	Person o-- "Singleton" Clock : IClock
	Person *--  Int32 : Int32
	Person *--  String : String
	Team o-- "PerBlock" FuncᐸInt32ˏStringˏIPersonᐳ : FuncᐸInt32ˏStringˏIPersonᐳ
	FuncᐸInt32ˏStringˏIPersonᐳ *--  Person : IPerson
	namespace Pure.DI.UsageTests.BCL.FuncWithArgumentsScenario {
		class Clock {
			<<class>>
		}
		class Composition {
		<<partial>>
		+ITeam Team
		}
		class IPerson {
			<<interface>>
		}
		class ITeam {
			<<interface>>
		}
		class Person {
				<<class>>
			+Person(String name, IClock clock, Int32 id)
		}
		class Team {
				<<class>>
			+Team(FuncᐸInt32ˏStringˏIPersonᐳ personFactory)
		}
	}
	namespace System {
		class FuncᐸInt32ˏStringˏIPersonᐳ {
				<<delegate>>
		}
		class Int32 {
			<<struct>>
		}
		class String {
			<<class>>
		}
	}
Loading