/// <summary>
        /// Register a type by constructor (represented by the expression <paramref name="newExpr"/>).
        /// </summary>
        /// <typeparam name="TObject"></typeparam>
        /// <param name="targets"></param>
        /// <param name="newExpr">A lambda expression whose <see cref="LambdaExpression.Body"/> is a <see cref="NewExpression"/>
        /// which identifies the constructor that is to be used to create the instance of <typeparamref name="TObject"/>.  An exception
        /// will be thrown if the lambda does not follow this pattern.</param>
        /// <param name="configureMemberBinding">A callback which configures a custom member binding via the
        /// <see cref="IMemberBindingBehaviourBuilder{TInstance}"/> interface.  A new builder will be created and passed to this
        /// callback.</param>
        /// <remarks>Note that you can achieve a similar result by simply registering an expression which
        /// represents a call to a type's constructor.
        ///
        /// **Generic constructors**
        /// If you wish to register an open generic type by constructor through the use of an expression, then you
        /// need to use the <see cref="RegisterGenericConstructor{TObject}(ITargetContainer, Expression{Func{TObject}}, IMemberBindingBehaviour)"/>
        /// overload.</remarks>
        public static void RegisterConstructor <TObject>(
            this ITargetContainer targets,
            Expression <Func <TObject> > newExpr,
            Action <IMemberBindingBehaviourBuilder <TObject> > configureMemberBinding)
        {
            if (targets == null)
            {
                throw new ArgumentNullException(nameof(targets));
            }

            if (configureMemberBinding == null)
            {
                throw new ArgumentNullException(nameof(configureMemberBinding));
            }

            var ctor = Extract.Constructor(newExpr ?? throw new ArgumentNullException(nameof(newExpr)));

            if (ctor == null)
            {
                throw new ArgumentException($"The expression ${newExpr} does not represent a NewExpression", nameof(newExpr));
            }

            var behaviour = MemberBindingBehaviour.For <TObject>();

            configureMemberBinding(behaviour);
            targets.Register(Target.ForConstructor(ctor, behaviour.BuildBehaviour()));
        }
예제 #2
0
        /// <summary>
        /// Creates a <see cref="ConstructorTarget"/> for the type <typeparamref name="T"/> with
        /// an <see cref="IMemberBindingBehaviour"/> built from an <see cref="IMemberBindingBehaviourBuilder{TInstance}"/>
        /// that's configured by the <paramref name="configureMemberBinding"/> callback.
        /// </summary>
        /// <typeparam name="T">The type of object to be created by the target</typeparam>
        /// <param name="configureMemberBinding">Will be called with a new instance of
        /// <see cref="IMemberBindingBehaviourBuilder{TInstance}"/> for you to configure any
        /// member bindings you wish to add to the target.</param>
        /// <returns>A new target for the type <typeparamref name="T"/></returns>
        public static ITarget ForType <T>(Action <IMemberBindingBehaviourBuilder <T> > configureMemberBinding)
        {
            var builder = MemberBindingBehaviour.For <T>();

            configureMemberBinding?.Invoke(builder);
            return(ForType <T>(builder.BuildBehaviour()));
        }
        /// <summary>
        /// Same as the <see cref="RegisterType{TObject}(ITargetContainer, Action{IMemberBindingBehaviourBuilder{TObject}})"/> method, except this
        /// creates a registration for <typeparamref name="TService"/> that will be implemented by instances of the type <typeparamref name="TObject"/>,
        /// created via constructor injection.
        /// </summary>
        /// <typeparam name="TObject"></typeparam>
        /// <typeparam name="TService"></typeparam>
        /// <param name="targets">The target container on which the registration is to be performed.</param>
        /// <param name="configureMemberBinding">A callback that will be invoked with a new <see cref="IMemberBindingBehaviourBuilder{TInstance}"/>
        /// object that you can use to configure a custom member binding behaviour for the type <typeparamref name="TObject"/>.  The
        /// <see cref="IMemberBindingBehaviourBuilder{TInstance}.BuildBehaviour"/> method will be called after executing your callback to
        /// obtain the final <see cref="IMemberBindingBehaviour"/>.</param>
        public static void RegisterType <TObject, TService>(this ITargetContainer targets, Action <IMemberBindingBehaviourBuilder <TObject> > configureMemberBinding)
            where TObject : TService
        {
            var factory = MemberBindingBehaviour.For <TObject>();

            configureMemberBinding?.Invoke(factory);
            targets.RegisterType <TObject, TService>(factory.BuildBehaviour());
        }
예제 #4
0
        /// <summary>
        /// Same as <see cref="ForType{T}(object, IMemberBindingBehaviour)"/> except this lets you build a custom <see cref="IMemberBindingBehaviour"/>
        /// using the fluent API offered by the <see cref="IMemberBindingBehaviourBuilder{TInstance}"/> interface.
        /// </summary>
        /// <typeparam name="T">The type whose constructor is to be bound by the created target.</typeparam>
        /// <param name="namedArgs">Optional.  An objeect whose publicly readable members which are of the type
        /// <see cref="ITarget"/> (or a type which implements it) are to be bound to the type's constructor by name
        /// and <see cref="ITarget.DeclaredType"/>.</param>
        /// <param name="configureMemberBinding">Will be called with a new instance of
        /// <see cref="IMemberBindingBehaviourBuilder{TInstance}"/> for you to configure any
        /// member bindings you wish to add to the target.</param>
        /// <returns>A new target for the type <typeparamref name="T"/></returns>
        public static ITarget ForType <T>(
            object namedArgs,
            Action <IMemberBindingBehaviourBuilder <T> > configureMemberBinding)
        {
            var builder = MemberBindingBehaviour.For <T>();

            configureMemberBinding?.Invoke(builder);
            return(ForType(typeof(T), namedArgs, builder.BuildBehaviour()));
        }
예제 #5
0
        /// <summary>
        /// Same as <see cref="ForType{T}(IDictionary{string, ITarget}, IMemberBindingBehaviour)"/> except this allows you to
        /// build a custom member binding behaviour using the fluent API exposed by the <see cref="IMemberBindingBehaviourBuilder{TInstance}"/>
        /// interface
        /// </summary>
        /// <typeparam name="T">The type whose constructor is to be bound by the target.</typeparam>
        /// <param name="namedArgs">Can be null. A dictionary of targets that are to be bound to the type's
        /// constructor by name and <see cref="ITarget.DeclaredType"/>.
        ///
        /// If <typeparamref name="T"/> is a generic type definition, then
        /// this parameter must be null, or an <see cref="ArgumentException"/> will be thrown.</param>
        /// <param name="configureMemberBinding">Will be called with a new instance of
        /// <see cref="IMemberBindingBehaviourBuilder{TInstance}"/> for you to configure any
        /// member bindings you wish to add to the target.</param>
        /// <returns>A new target for the type <typeparamref name="T"/></returns>
        public static ITarget ForType <T>(
            IDictionary <string, ITarget> namedArgs,
            Action <IMemberBindingBehaviourBuilder <T> > configureMemberBinding)
        {
            var builder = MemberBindingBehaviour.For <T>();

            configureMemberBinding?.Invoke(builder);
            return(ForType <T>(namedArgs, builder.BuildBehaviour()));
        }