ServiceRegistration
Represents a service registration.
using Stashbox.Lifetime;
using Stashbox.Resolution;
using Stashbox.Utils.Data;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Threading;
namespace Stashbox.Registration
{
[System.Runtime.CompilerServices.NullableContext(1)]
[System.Runtime.CompilerServices.Nullable(0)]
[DebuggerDisplay("Name = {Name}, Lifetime = {Lifetime.Name}", Name = "{ImplementationType}")]
public class ServiceRegistration
{
private static int globalRegistrationId = -2147483648;
private static int globalRegistrationOrder = -2147483648;
public readonly int RegistrationId;
public readonly bool IsDecorator;
[System.Runtime.CompilerServices.Nullable(2)]
[DebuggerBrowsable(DebuggerBrowsableState.Never)]
internal Dictionary<RegistrationOption, object> Options;
[System.Runtime.CompilerServices.Nullable(2)]
[field: System.Runtime.CompilerServices.Nullable(2)]
public object Name {
[System.Runtime.CompilerServices.NullableContext(2)]
get;
[System.Runtime.CompilerServices.NullableContext(2)]
internal set;
}
public LifetimeDescriptor Lifetime { get; set; }
public int RegistrationOrder { get; set; }
public Type ImplementationType { get; set; }
[System.Runtime.CompilerServices.Nullable(2)]
public IReadOnlyDictionary<RegistrationOption, object> RegistrationOptions {
[System.Runtime.CompilerServices.NullableContext(2)]
get {
return Options;
}
}
internal ServiceRegistration(Type implementationType, [System.Runtime.CompilerServices.Nullable(2)] object name, LifetimeDescriptor lifetimeDescriptor, bool isDecorator, [System.Runtime.CompilerServices.Nullable(2)] Dictionary<RegistrationOption, object> options = null, int? registrationId = default(int?), int? order = default(int?))
{
ImplementationType = implementationType;
IsDecorator = isDecorator;
Name = name;
Lifetime = lifetimeDescriptor;
Options = options;
RegistrationId = (registrationId ?? ReserveRegistrationId());
RegistrationOrder = (order ?? ReserveRegistrationOrder());
}
internal void Replaces(ServiceRegistration serviceRegistration)
{
RegistrationOrder = serviceRegistration.RegistrationOrder;
}
internal bool IsFactory()
{
return Options.GetOrDefault(RegistrationOption.RegistrationTypeOptions) is FactoryOptions;
}
internal bool IsInstance()
{
return Options.GetOrDefault(RegistrationOption.RegistrationTypeOptions) is InstanceOptions;
}
internal static bool IsUsableForCurrentContext(TypeInformation typeInfo, ConditionOptions conditionOptions)
{
if (!HasParentTypeConditionAndMatch(typeInfo, conditionOptions) && !HasAttributeConditionAndMatch(typeInfo, conditionOptions))
return HasResolutionConditionAndMatch(typeInfo, conditionOptions);
return true;
}
private static bool HasParentTypeConditionAndMatch(TypeInformation typeInfo, ConditionOptions conditionOptions)
{
if (conditionOptions.TargetTypeConditions == null || !CheckTypeConditions(conditionOptions.TargetTypeConditions, typeInfo)) {
if (conditionOptions.TargetTypeInResolutionPathConditions != null)
return CheckInPathTypeConditions(conditionOptions.TargetTypeInResolutionPathConditions, typeInfo);
return false;
}
return true;
}
private static bool HasAttributeConditionAndMatch(TypeInformation typeInfo, ConditionOptions conditionOptions)
{
if (conditionOptions.AttributeConditions == null || typeInfo.CustomAttributes == null || !conditionOptions.AttributeConditions.Intersect(from attribute in typeInfo.CustomAttributes
select attribute.GetType()).Any()) {
if (conditionOptions.AttributeInResolutionPathConditions != null)
return CheckInPathAttributeConditions(conditionOptions.AttributeInResolutionPathConditions, typeInfo);
return false;
}
return true;
}
private static bool HasResolutionConditionAndMatch(TypeInformation typeInfo, ConditionOptions conditionOptions)
{
if (conditionOptions.ResolutionConditions == null)
return false;
int length = conditionOptions.ResolutionConditions.Length;
for (int i = 0; i < length; i++) {
if (conditionOptions.ResolutionConditions[i](typeInfo))
return true;
}
return false;
}
private static bool CheckInPathTypeConditions([System.Runtime.CompilerServices.Nullable(new byte[] {
1,
2,
1
})] ExpandableArray<object, Type> conditions, TypeInformation typeInformation)
{
TypeInformation typeInformation2 = typeInformation;
do {
if (CheckTypeConditions(conditions, typeInformation2))
return true;
typeInformation2 = typeInformation2.Parent;
} while (typeInformation2 != null);
return false;
}
private static bool CheckTypeConditions([System.Runtime.CompilerServices.Nullable(new byte[] {
1,
2,
1
})] ExpandableArray<object, Type> conditions, TypeInformation typeInformation)
{
if (typeInformation.ParentType == (Type)null)
return false;
int length = conditions.Length;
for (int i = 0; i < length; i++) {
if (<CheckTypeConditions>g__CheckSingleCondition|32_0(conditions[i], typeInformation))
return true;
}
return false;
}
private static bool CheckInPathAttributeConditions([System.Runtime.CompilerServices.Nullable(new byte[] {
1,
2,
1
})] ExpandableArray<object, Type> attributes, TypeInformation typeInformation)
{
TypeInformation typeInformation2 = typeInformation;
do {
if (CheckAttributeConditions(attributes, typeInformation2))
return true;
typeInformation2 = typeInformation2.Parent;
} while (typeInformation2 != null);
return false;
}
private static bool CheckAttributeConditions([System.Runtime.CompilerServices.Nullable(new byte[] {
1,
2,
1
})] ExpandableArray<object, Type> attributes, TypeInformation typeInformation)
{
if (typeInformation.CustomAttributes == null)
return false;
List<Type> list = (from attribute in typeInformation.CustomAttributes
select attribute.GetType()).ToList();
if (list.Count == 0)
return false;
int length = attributes.Length;
for (int i = 0; i < length; i++) {
ReadOnlyKeyValue<object, Type> readOnlyKeyValue = attributes[i];
if (readOnlyKeyValue.Key != null) {
if (typeInformation.Parent == null)
continue;
if (readOnlyKeyValue.Key.Equals(typeInformation.Parent.DependencyName) && list.Contains(readOnlyKeyValue.Value))
return true;
}
if (list.Contains(readOnlyKeyValue.Value))
return true;
}
return false;
}
private static int ReserveRegistrationId()
{
return Interlocked.Increment(ref globalRegistrationId);
}
private static int ReserveRegistrationOrder()
{
return Interlocked.Increment(ref globalRegistrationOrder);
}
}
}