Moved to delegate factory for resolver

This commit is contained in:
Eugene Sadovoi 2018-12-24 21:53:21 -05:00
Родитель cf55bd92ea
Коммит d10edf57cc
13 изменённых файлов: 286 добавлений и 403 удалений

Просмотреть файл

@ -1,5 +1,6 @@
using System;
using System.Diagnostics;
using System.Linq.Expressions;
using System.Reflection;
using System.Security;
using Unity.Policy;
@ -24,8 +25,58 @@ namespace Unity.Builder
#endregion
#region IResolveContext
public IUnityContainer Container => Lifetime?.Container;
public Type Type { get; set; }
public string Name => RegistrationName;
public object Resolve(Type type, string name) => Resolve(type, name,
(InternalRegistration)((UnityContainer)Container).GetRegistration(type, name));
#endregion
#region IPolicyList
public object Get(Type type, string name, Type policyInterface)
{
return list.Get(type, name, policyInterface) ??
(type != RegistrationType || name != RegistrationName
? ((UnityContainer)Container).GetPolicy(type, name, policyInterface)
: Registration.Get(policyInterface));
}
public void Set(Type type, string name, Type policyInterface, object policy)
{
list.Set(type, name, policyInterface, policy);
}
public void Clear(Type type, string name, Type policyInterface)
{
list.Clear(type, name, policyInterface);
}
#endregion
#region Registration
public Type RegistrationType { get; set; }
public string RegistrationName { get; set; }
public IPolicySet Registration { get; set; }
#endregion
#region Public Members
public object Existing { get; set; }
public ILifetimeContainer Lifetime;
public SynchronizedLifetimeManager RequiresRecovery;
@ -34,17 +85,12 @@ namespace Unity.Builder
public Type DeclaringType { get; private set; }
public ParameterExpression Variable;
#endregion
#region ResolveContext
public IUnityContainer Container => Lifetime?.Container;
public object Existing { get; set; }
public object Resolve(Type type, string name) => Resolve(type, name,
(InternalRegistration)((UnityContainer)Container).GetRegistration(type, name));
#region Public Methods
public object Resolve(Type type, string name, InternalRegistration registration)
{
@ -64,6 +110,63 @@ namespace Unity.Builder
return registration.BuildChain.ExecuteReThrowingPlan(ref context);
}
public object Resolve(ParameterInfo parameter, string name, object value)
{
var context = this;
// Process overrides if any
if (null != Overrides)
{
// Check if this parameter is overridden
for (var index = Overrides.Length - 1; index >= 0; --index)
{
var resolverOverride = Overrides[index];
// If matches with current parameter
if (resolverOverride is IEquatable<ParameterInfo> comparer && comparer.Equals(parameter))
{
// Check if itself is a value
if (resolverOverride is IResolve resolverPolicy)
{
return resolverPolicy.Resolve(ref context);
}
// Try to create value
var resolveDelegate = resolverOverride.GetResolver<BuilderContext>(parameter.ParameterType);
if (null != resolveDelegate)
{
return resolveDelegate(ref context);
}
}
}
}
// Resolve from injectors
// TODO: Optimize via overrides
switch (value)
{
case ResolveDelegate<BuilderContext> resolver:
return resolver(ref context);
case IResolve policy:
return policy.Resolve(ref context);
case IResolverFactory factory:
var method = factory.GetResolver<BuilderContext>(Type);
return method?.Invoke(ref context);
case Type type: // TODO: Requires evaluation
if (typeof(Type) == parameter.ParameterType) return type;
break;
case object obj:
return obj;
}
// Resolve from container
return Resolve(parameter.ParameterType, name);
}
public object Resolve(FieldInfo field, string name, object value)
{
var context = this;
@ -174,101 +277,6 @@ namespace Unity.Builder
return Resolve(property.PropertyType, name);
}
public object Resolve(ParameterInfo parameter, string name, object value)
{
var context = this;
// Process overrides if any
if (null != Overrides)
{
// Check if this parameter is overridden
for (var index = Overrides.Length - 1; index >= 0; --index)
{
var resolverOverride = Overrides[index];
// If matches with current parameter
if (resolverOverride is IEquatable<ParameterInfo> comparer && comparer.Equals(parameter))
{
// Check if itself is a value
if (resolverOverride is IResolve resolverPolicy)
{
return resolverPolicy.Resolve(ref context);
}
// Try to create value
var resolveDelegate = resolverOverride.GetResolver<BuilderContext>(parameter.ParameterType);
if (null != resolveDelegate)
{
return resolveDelegate(ref context);
}
}
}
}
// Resolve from injectors
// TODO: Optimize via overrides
switch (value)
{
case ResolveDelegate<BuilderContext> resolver:
return resolver(ref context);
case IResolve policy:
return policy.Resolve(ref context);
case IResolverFactory factory:
var method = factory.GetResolver<BuilderContext>(Type);
return method?.Invoke(ref context);
case Type type: // TODO: Requires evaluation
if (typeof(Type) == parameter.ParameterType) return type;
break;
case object obj:
return obj;
}
// Resolve from container
return Resolve(parameter.ParameterType, name);
}
#endregion
#region Registration
public Type RegistrationType { get; set; }
public string RegistrationName { get; set; }
public IPolicySet Registration { get; set; }
#endregion
#region Build
public Type Type { get; set; }
public string Name => RegistrationName;
public object Get(Type type, string name, Type policyInterface)
{
return list.Get(type, name, policyInterface) ??
(type != RegistrationType || name != RegistrationName
? ((UnityContainer)Container).GetPolicy(type, name, policyInterface)
: Registration.Get(policyInterface));
}
public void Set(Type type, string name, Type policyInterface, object policy)
{
list.Set(type, name, policyInterface, policy);
}
public void Clear(Type type, string name, Type policyInterface)
{
list.Clear(type, name, policyInterface);
}
#endregion
}
}

Просмотреть файл

@ -1,8 +1,10 @@
using System.Collections.Generic;
using System.Diagnostics.CodeAnalysis;
using System;
using System.Linq;
using System.Linq.Expressions;
using System.Reflection;
using Unity.Container.Lifetime;
using Unity.Resolution;
using Unity.ResolverPolicy;
@ -11,6 +13,45 @@ namespace Unity.Builder.Expressions
[SuppressMessage("ReSharper", "StaticMemberInGenericType")]
public class BuilderContextExpression : IResolveContextExpression<BuilderContext>
{
#region Fields
private static ConstructorInfo _perResolveInfo = typeof(InternalPerResolveLifetimeManager)
.GetTypeInfo().DeclaredConstructors.First();
private static readonly MethodInfo _resolveField =
typeof(BuilderContext).GetTypeInfo()
.GetDeclaredMethods(nameof(BuilderContext.Resolve))
.First(m =>
{
var parameters = m.GetParameters();
return 2 <= parameters.Length &&
typeof(FieldInfo) == parameters[0].ParameterType;
});
private static readonly MethodInfo _resolveProperty =
typeof(BuilderContext).GetTypeInfo()
.GetDeclaredMethods(nameof(BuilderContext.Resolve))
.First(m =>
{
var parameters = m.GetParameters();
return 2 <= parameters.Length &&
typeof(PropertyInfo) == parameters[0].ParameterType;
});
private static readonly MethodInfo _resolveParameter =
typeof(BuilderContext).GetTypeInfo()
.GetDeclaredMethods(nameof(BuilderContext.Resolve))
.First(m =>
{
var parameters = m.GetParameters();
return 2 <= parameters.Length &&
typeof(ParameterInfo) == parameters[0].ParameterType;
});
#endregion
#region Constructor
static BuilderContextExpression()
@ -33,6 +74,36 @@ namespace Unity.Builder.Expressions
#region Methods
public static Expression Resolve(FieldInfo field, string name, object value = null)
{
return Expression.Convert(
Expression.Call(Context, _resolveField,
Expression.Constant(field, typeof(FieldInfo)),
Expression.Constant(name, typeof(string)),
Expression.Constant(value, typeof(object))),
field.FieldType);
}
public static Expression Resolve(PropertyInfo property, string name, object value = null)
{
return Expression.Convert(
Expression.Call(Context, _resolveProperty,
Expression.Constant(property, typeof(PropertyInfo)),
Expression.Constant(name, typeof(string)),
Expression.Constant(value, typeof(object))),
property.PropertyType);
}
public static Expression Resolve(ParameterInfo parameter, string name, object value = null)
{
return Expression.Convert(
Expression.Call(Context, _resolveParameter,
Expression.Constant(parameter, typeof(ParameterInfo)),
Expression.Constant(name, typeof(string)),
Expression.Constant(value, typeof(object))),
parameter.ParameterType);
}
public static IEnumerable<Expression> GetParameters(MethodBase methodBase)
{
foreach (var parameter in methodBase.GetParameters())
@ -68,6 +139,12 @@ namespace Unity.Builder.Expressions
}
}
public static Expression SetPerBuildSingleton(ref BuilderContext context)
{
return Set(context.RegistrationType, context.RegistrationName, typeof(LifetimeManager),
Expression.New(_perResolveInfo, context.Variable));
}
#endregion
}
}

Просмотреть файл

@ -1,37 +0,0 @@
using System;
using Unity.Builder;
using Unity.Policy;
using Unity.Resolution;
namespace Unity.ObjectBuilder.BuildPlan.DynamicMethod
{
public class DynamicMethodBuildPlan : IBuildPlanPolicy, IResolve
{
private readonly Delegate _buildMethod;
/// <summary>
///
/// </summary>
/// <param name="buildMethod"></param>
public DynamicMethodBuildPlan(Delegate buildMethod)
{
_buildMethod = buildMethod;
}
/// <summary>
///
/// </summary>
/// <param name="context"></param>
public void BuildUp(ref BuilderContext context)
{
context.Existing = ((ResolveDelegate<BuilderContext>)_buildMethod).Invoke(ref context);
}
public object Resolve<TContext>(ref TContext context)
where TContext : IResolveContext
{
return ((ResolveDelegate<TContext>)_buildMethod).Invoke(ref context);
}
}
}

Просмотреть файл

@ -1,55 +0,0 @@
using System;
using Unity.Builder;
using Unity.Policy;
using Unity.Storage;
namespace Unity.ObjectBuilder.BuildPlan.DynamicMethod
{
/// <summary>
/// An <see cref="IBuildPlanCreatorPolicy"/> implementation
/// that constructs a build plan via dynamic IL emission.
/// </summary>
public class DynamicMethodBuildPlanCreatorPolicy : IBuildPlanCreatorPolicy
{
private BuilderStrategy[] _strategies;
/// <summary>
/// Construct a <see cref="DynamicMethodBuildPlanCreatorPolicy"/> that
/// uses the given strategy chain to construct the build plan.
/// </summary>
/// <param name="strategies">The strategy chain.</param>
public DynamicMethodBuildPlanCreatorPolicy(StagedStrategyChain<BuilderStrategy, BuilderStage> strategies)
{
strategies.Invalidated += (s, e) => _strategies = strategies.ToArray();
_strategies = strategies.ToArray();
}
/// <summary>
/// Construct a build plan.
/// </summary>
/// <param name="context">The current build context.</param>
/// <param name="type"></param>
/// <param name="name"></param>
/// <returns>The created build plan.</returns>
public IBuildPlanPolicy CreatePlan(ref BuilderContext context, Type type, string name)
{
var generatorContext = new DynamicBuildPlanGenerationContext(type);
var planContext = new BuilderContext
{
Existing = generatorContext,
Lifetime = context.Lifetime,
RegistrationType = context.RegistrationType,
RegistrationName = context.RegistrationName,
Registration = context.Registration,
Type = context.Type,
list = context.list
};
var plan = _strategies.ExecutePlan(ref planContext);
return new DynamicMethodBuildPlan(generatorContext.GetBuildMethod());
}
}
}

Просмотреть файл

@ -3,10 +3,7 @@ using Unity.Builder;
namespace Unity.Policy
{
/// <summary>
/// A policy that can create and return an <see cref="IBuildPlanPolicy"/>
/// for the given build key.
/// </summary>
[Obsolete("This interface has been replaced with Unity.Policy.ResolveDelegateFactory delegate", true)]
public interface IBuildPlanCreatorPolicy
{
/// <summary>

Просмотреть файл

@ -2,15 +2,14 @@
using System.Reflection;
using Unity.Builder;
using Unity.Container.Lifetime;
using Unity.ObjectBuilder.BuildPlan.DynamicMethod;
namespace Unity.Policy.BuildPlanCreator
{
/// <summary>
/// An <see cref="IBuildPlanCreatorPolicy"/> implementation
/// An <see cref="IResolveDelegateFactory"/> implementation
/// that constructs a build plan for creating <see cref="Lazy{T}"/> objects.
/// </summary>
public class GenericLazyBuildPlanCreatorPolicy : IBuildPlanCreatorPolicy
public class GenericLazyBuildPlanCreatorPolicy
{
#region Fields
@ -21,14 +20,14 @@ namespace Unity.Policy.BuildPlanCreator
#endregion
#region IBuildPlanCreatorPolicy
#region IResolveDelegateFactory
public IBuildPlanPolicy CreatePlan(ref BuilderContext context, Type type, string name)
public static ResolveDelegate<BuilderContext> GetResolver(ref BuilderContext context)
{
var itemType = context.Type.GetTypeInfo().GenericTypeArguments[0];
var lazyMethod = BuildResolveLazyMethod.MakeGenericMethod(itemType);
return new DynamicMethodBuildPlan(lazyMethod.CreateDelegate(typeof(ResolveDelegate<BuilderContext>)));
return (ResolveDelegate<BuilderContext>)lazyMethod.CreateDelegate(typeof(ResolveDelegate<BuilderContext>));
}
#endregion

Просмотреть файл

@ -0,0 +1,11 @@
using Unity.Builder;
namespace Unity.Policy
{
public delegate ResolveDelegate<BuilderContext> ResolveDelegateFactory(ref BuilderContext context);
public interface IResolveDelegateFactory
{
ResolveDelegate<BuilderContext> GetResolver(ref BuilderContext context);
}
}

Просмотреть файл

@ -42,28 +42,39 @@ namespace Unity.Strategies
var resolver = context.Registration.Get<ResolveDelegate<BuilderContext>>();
if (null == resolver)
{
// Legacy support
// TODO: Verify and optimize getting default
var plan = context.Registration.Get<IBuildPlanPolicy>() ??
var plan = context.Registration.Get<IBuildPlanPolicy>() ??
(IBuildPlanPolicy)(
context.Get(context.Type, string.Empty, typeof(IBuildPlanPolicy)) ??
GetGeneric(ref context, typeof(IBuildPlanPolicy),
context.RegistrationType, context.RegistrationName));
GetGeneric(ref context, typeof(IBuildPlanPolicy), context.RegistrationType, context.RegistrationName));
if (plan == null || plan is OverriddenBuildPlanMarkerPolicy)
if (plan == null)
{
var planCreator = context.Registration.Get<IBuildPlanCreatorPolicy>() ??
CheckIfOpenGeneric(context.RegistrationType, context.Registration) ??
Get_Policy<IBuildPlanCreatorPolicy>(ref context, context.Type, context.Name);
if (planCreator != null)
// Check if can create
#if NETCOREAPP1_0 || NETSTANDARD1_0
if (!(context.Registration is ContainerRegistration) && context.RegistrationType.GetTypeInfo().IsGenericTypeDefinition)
#else
if (!(context.Registration is ContainerRegistration) && context.RegistrationType.IsGenericTypeDefinition)
#endif
{
plan = planCreator.CreatePlan(ref context, context.Type, context.Name);
throw new ArgumentException(string.Format(CultureInfo.CurrentCulture,
Constants.CannotResolveOpenGenericType, context.RegistrationType.FullName));
}
if (plan is IResolve policy)
context.Registration.Set(typeof(ResolveDelegate<BuilderContext>), (ResolveDelegate<BuilderContext>)policy.Resolve);
else
context.Registration.Set(typeof(IBuildPlanPolicy), plan);
// Create plan
var factory = context.Registration.Get<ResolveDelegateFactory>() ??
Get_Policy<ResolveDelegateFactory>(ref context, context.Type, context.Name);
if (null != factory)
{
resolver = factory(ref context);
context.Registration.Set(typeof(ResolveDelegate<BuilderContext>), resolver);
context.Existing = resolver(ref context);
return;
}
else
throw new ResolutionFailedException(context.Type, context.Name, "Failed to find Build Plan Creator Policy");
@ -105,22 +116,6 @@ namespace Unity.Strategies
return null;
}
protected static IBuildPlanCreatorPolicy CheckIfOpenGeneric(Type type, IPolicySet namedType)
{
if (namedType is InternalRegistration registration && !(namedType is ContainerRegistration) &&
#if NETCOREAPP1_0 || NETSTANDARD1_0
type.GetTypeInfo().IsGenericTypeDefinition)
#else
type.IsGenericTypeDefinition)
#endif
{
throw new ArgumentException(string.Format(CultureInfo.CurrentCulture,
Constants.CannotResolveOpenGenericType, type.FullName));
}
return null;
}
#endregion
}
}

Просмотреть файл

@ -10,7 +10,6 @@ using Unity.Builder.Strategies;
using Unity.Container.Lifetime;
using Unity.Events;
using Unity.Extension;
using Unity.ObjectBuilder.BuildPlan.DynamicMethod;
using Unity.Policy;
using Unity.Policy.BuildPlanCreator;
using Unity.Registration;
@ -133,7 +132,7 @@ namespace Unity
Set(null, null, GetDefaultPolicies());
Set(typeof(Func<>), string.Empty, typeof(LifetimeManager), new PerResolveLifetimeManager());
Set(typeof(Func<>), string.Empty, typeof(IBuildPlanPolicy), new DeferredResolveCreatorPolicy());
Set(typeof(Lazy<>), string.Empty, typeof(IBuildPlanCreatorPolicy), new GenericLazyBuildPlanCreatorPolicy());
Set(typeof(Lazy<>), string.Empty, typeof(ResolveDelegateFactory), (ResolveDelegateFactory)GenericLazyBuildPlanCreatorPolicy.GetResolver);
// Register this instance
((IUnityContainer)this).RegisterInstance(typeof(IUnityContainer), null, this, new ContainerLifetimeManager());
@ -187,7 +186,7 @@ namespace Unity
{
var defaults = new InternalRegistration(null, null);
defaults.Set(typeof(IBuildPlanCreatorPolicy), new DynamicMethodBuildPlanCreatorPolicy(_buildPlanStrategies));
defaults.Set(typeof(ResolveDelegateFactory), (ResolveDelegateFactory)GetResolver);
defaults.Set(typeof(IConstructorSelectorPolicy), new DefaultUnityConstructorSelector());
defaults.Set(typeof(IFieldSelectorPolicy), new DefaultUnityFieldsSelector());
defaults.Set(typeof(IPropertySelectorPolicy), new DefaultUnityPropertiesSelector());

Просмотреть файл

@ -5,6 +5,7 @@ using System.Reflection;
using System.Text;
using Unity.Builder;
using Unity.Exceptions;
using Unity.Policy;
using Unity.Registration;
using Unity.Storage;
@ -157,6 +158,55 @@ namespace Unity
#endregion
#region Build Plan
private ResolveDelegate<BuilderContext> GetResolver(ref BuilderContext context)
{
var generatorContext = new ObjectBuilder.BuildPlan.DynamicMethod.DynamicBuildPlanGenerationContext(context.Type);
var planContext = new BuilderContext
{
Existing = generatorContext,
Lifetime = context.Lifetime,
RegistrationType = context.RegistrationType,
RegistrationName = context.RegistrationName,
Registration = context.Registration,
Type = context.Type,
list = context.list
};
var plan = _buildPlanStrategies.ToArray().ExecutePlan(ref planContext);
return generatorContext.GetBuildMethod();
}
//private ResolveDelegate<BuilderContext> GetResolver(ref BuilderContext context)
//{
// context.Variable = Expression.Variable(context.Type, "instance");
// var expressions = new List<Expression>();
// foreach (var strategy in _buildPlanStrategies.ToArray())
// {
// //foreach (var step in strategy.BuildUp(ref context))
// // expressions.Add(step);
// }
// expressions.Add(Expression.Convert(context.Variable, typeof(object)));
// var lambda = Expression.Lambda<ResolveDelegate<BuilderContext>>(
// Expression.Block(new ParameterExpression[] { context.Variable }, expressions),
// BuilderContextExpression.Context);
// return lambda.Compile();
//}
#endregion
#region Exceptions
public static string CreateMessage(Type typeRequested, string nameRequested, Exception innerException,

Просмотреть файл

@ -1,7 +1,6 @@
using BenchmarkDotNet.Configs;
using BenchmarkDotNet.Jobs;
using BenchmarkDotNet.Validators;
using System.Linq;
namespace Runner.Setup
{
@ -9,11 +8,12 @@ namespace Runner.Setup
{
public BenchmarkConfiguration()
{
Add(JitOptimizationsValidator.DontFailOnError); // ALLOW NON-OPTIMIZED DLLS
Add(Job.Default
.WithUnrollFactor(1)
.WithInvocationCount(50000));
.WithInvocationCount(1));
Add(JitOptimizationsValidator.DontFailOnError); // ALLOW NON-OPTIMIZED DLLS
}
}
}

Просмотреть файл

@ -22,6 +22,7 @@ namespace Runner.Tests
_container.RegisterType<IService, Service>("1");
_container.RegisterType<IService, Service>("2");
_container.Resolve<object>();
_container.Resolve<Poco>();
_container.Resolve<IService>();
_container.Resolve<IService>("1");

Просмотреть файл

@ -1,162 +0,0 @@
using Microsoft.VisualStudio.TestTools.UnitTesting;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Reflection;
using Unity.Builder;
using Unity.Policy;
using Unity.Resolution;
using Unity.ResolverPolicy;
namespace Unity.Tests.v5
{
[TestClass]
public class ExpressionFixture
{
public IUnityContainer _container;
public MockContext _context = new MockContext();
[TestInitialize]
public void Setup()
{
_container = new UnityContainer();
_context.Existing = null;
_context.Type = typeof(Service);
}
[TestMethod]
public void CreateNewExpression()
{
ref var context = ref _context;
var fieldInfo = context.Type.GetField(nameof(Service.Field));
var propInfo = context.Type.GetProperty(nameof(Service.Property));
var varExpr = Expression.Variable(context.Type, "instance");
var fieldExpr = Expression.Field(varExpr, fieldInfo);
var propExpr = Expression.Property(varExpr, propInfo);
var blockExpr = Expression.Block(new ParameterExpression[] { varExpr }, new Expression[]
{
Expression.IfThenElse(Expression.NotEqual( Expression.Constant(null), BuilderContextExpression.Existing),
Expression.Assign( varExpr, Expression.Convert(BuilderContextExpression.Existing, context.Type)),
Expression.Assign( varExpr, Expression.New(typeof(Service)))),
Expression.Assign(fieldExpr, BuilderContextExpression.Resolve(fieldInfo, null, null)),
Expression.Assign(propExpr, BuilderContextExpression.Resolve(propInfo, null, null)),
varExpr
});
var lambda = Expression.Lambda<ResolveDelegate<MockContext>>(blockExpr, BuilderContextExpression.Context);
var plan = lambda.Compile();
var instance = (Service)plan(ref context);
Assert.IsNotNull(instance);
Assert.AreEqual(instance.Field, Service.First);
Assert.AreEqual(instance.Property, Service.Other);
}
[TestMethod]
public void BaselineTest()
{
ResolveDelegate<BuilderContext> plan = (ref BuilderContext context) =>
{
Service instance;
if (null == context.Existing)
{
instance = new Service();
}
else
{
instance = (Service)context.Existing;
}
instance.Field = Service.First;
instance.Property = Service.Other;
return instance;
};
var result = new Service();
result.Field = Service.First;
result.Property = Service.Other;
Assert.IsNotNull(result);
Assert.AreEqual(result.Field, Service.First);
Assert.AreEqual(result.Property, Service.Other);
}
public interface IService { }
public class Service : IService
{
public static string First = "name";
public static string Other = "other";
public string Field;
public string Property { get; set; }
}
public class BuilderContextExpression : IResolveContextExpression<MockContext>
{
public static readonly MemberExpression Existing =
Expression.MakeMemberAccess(Context, typeof(MockContext).GetTypeInfo()
.GetDeclaredProperty(nameof(MockContext.Existing)));
}
public struct MockContext : IResolveContext
{
#region ResolveContext
public IUnityContainer Container => null;
public object Existing { get; set; }
public object Resolve(Type type, string name)
{
throw new NotImplementedException();
}
public object Resolve(FieldInfo field, string name, object value) => Service.First;
public object Resolve(PropertyInfo property, string name, object value) => Service.Other;
public object Resolve(ParameterInfo parameter, string name, object value)
{
throw new NotImplementedException();
}
#endregion
#region Build
public Type Type { get; set; }
public string Name { get; set; }
public object Get(Type type, string name, Type policyInterface)
{
throw new NotImplementedException();
}
public void Set(Type type, string name, Type policyInterface, object policy)
{
throw new NotImplementedException();
}
public void Clear(Type type, string name, Type policyInterface)
{
throw new NotImplementedException();
}
#endregion
}
}
}