public InstanceSourcesScope(IReadOnlyDictionary <ITypeSymbol, InstanceSource> instanceSource, Compilation compilation) { _instanceSource = instanceSource; _containerScope = this; _task1Type = compilation.GetType(typeof(Task <>)); _valueTask1Type = compilation.GetType(typeof(ValueTask <>)); Depth = 0; }
private InstanceSourcesScope(InstanceSourcesScope containerScope, Dictionary <ITypeSymbol, DelegateParameter> delegateParameters, int depth) { _instanceSource = containerScope._instanceSource; _delegateParameters = delegateParameters; _containerScope = containerScope; _task1Type = containerScope._task1Type; _valueTask1Type = containerScope._valueTask1Type; Depth = depth; }
public static string GenerateContainerImplementations( INamedTypeSymbol container, InstanceSourcesScope containerScope, WellKnownTypes wellKnownTypes, Action <Diagnostic> reportDiagnostic, CancellationToken cancellationToken) => new ContainerGenerator( container, containerScope, wellKnownTypes, reportDiagnostic, cancellationToken).GenerateContainerImplementations();
private InstanceSourcesScope(InstanceSourcesScope containerScope, Dictionary <ITypeSymbol, DelegateParameter> delegateParameters, int depth) { _instanceSources = containerScope._instanceSources; _genericRegistrationsResolver = containerScope._genericRegistrationsResolver; _decoratorSources = containerScope._decoratorSources; _genericDecoratorsResolver = containerScope._genericDecoratorsResolver; _wellKnownTypes = containerScope._wellKnownTypes; _containerScope = containerScope; _delegateParameters = delegateParameters; Depth = depth; }
public InstanceSourcesScope( IReadOnlyDictionary <ITypeSymbol, InstanceSources> instanceSources, GenericRegistrationsResolver genericRegistrationsResolver, IReadOnlyDictionary <ITypeSymbol, ImmutableArray <DecoratorSource> > decoratorSources, GenericDecoratorsResolver genericDecoratorsResolver, WellKnownTypes wellKnownTypes) { _instanceSources = instanceSources; _genericRegistrationsResolver = genericRegistrationsResolver; _decoratorSources = decoratorSources; _genericDecoratorsResolver = genericDecoratorsResolver; _wellKnownTypes = wellKnownTypes; _containerScope = this; Depth = 0; }
public static bool HasCircularOrMissingDependencies(ITypeSymbol target, bool isAsync, InstanceSourcesScope containerScope, Action <Diagnostic> reportDiagnostic, Location location) { var currentlyVisiting = new HashSet <InstanceSource>(); var visited = new HashSet <InstanceSource>(); return(Visit( GetInstanceSourceOrReport(target, containerScope), containerScope, usedParams: null, isScopeAsync: isAsync)); InstanceSource?GetInstanceSourceOrReport(ITypeSymbol type, InstanceSourcesScope instanceSourcesScope) { if (!instanceSourcesScope.TryGetSource(type, out var instanceSource, out var ambiguous, out var sourcesNotMatchingConstraints)) { if (ambiguous) { reportDiagnostic(NoBestSourceForType(location, target, type)); } else { reportDiagnostic(NoSourceForType(location, target, type)); foreach (var sourceNotMatchingConstraints in sourcesNotMatchingConstraints) { reportDiagnostic(WarnFactoryMethodNotMatchingConstraint(location, target, type, sourceNotMatchingConstraints)); } } return(null); } return(instanceSource); } // returns true if has any errors that make resolution impossible bool Visit(InstanceSource?instanceSource, InstanceSourcesScope instanceSourcesScope, HashSet <IParameterSymbol>?usedParams, bool isScopeAsync) { if (instanceSource is null) { return(true); } var outerIsContainerScope = ReferenceEquals(instanceSourcesScope, containerScope); var innerIsContainerScope = outerIsContainerScope; if (outerIsContainerScope && visited.Contains(instanceSource)) { return(false); } if (!currentlyVisiting.Add(instanceSource)) { reportDiagnostic(CircularDependency(location, target, instanceSource.OfType)); return(true); } var result = false; instanceSourcesScope = instanceSourcesScope.Enter(instanceSource); innerIsContainerScope = ReferenceEquals(instanceSourcesScope, containerScope); if (innerIsContainerScope && visited.Contains(instanceSource)) { return(false); } if (currentlyVisiting.Count > MAX_DEPENDENCY_TREE_DEPTH) { reportDiagnostic(DependencyTreeTooDeep(location, target)); return(true); } switch (instanceSource) { case DelegateSource(var delegateType, var returnType, var delegateParameters, var isAsync) delegateSource: { foreach (var paramsWithType in delegateParameters.GroupBy(x => x.Type)) { if (paramsWithType.Count() > 1) { reportDiagnostic(DelegateHasMultipleParametersOfTheSameType(location, target, instanceSource.OfType, paramsWithType.Key)); result = true; } } var returnTypeSource = GetInstanceSourceOrReport(returnType, instanceSourcesScope); if (returnTypeSource is DelegateParameter { Parameter : var param }) { if (delegateParameters.Contains(param)) { reportDiagnostic(WarnDelegateReturnTypeProvidedBySameDelegate(location, target, instanceSource.OfType, returnType)); } else { reportDiagnostic(WarnDelegateReturnTypeProvidedByAnotherDelegate(location, target, instanceSource.OfType, returnType)); } }
public static bool HasCircularOrMissingDependencies(ITypeSymbol target, bool isAsync, InstanceSourcesScope containerScope, Action <Diagnostic> reportDiagnostic, Location location) { var currentlyVisiting = new HashSet <ITypeSymbol>(); var visited = new HashSet <ITypeSymbol>(); return(Visit( target, containerScope, usedParams: null, isScopeAsync: isAsync)); // returns true if it has errors bool Visit(ITypeSymbol node, InstanceSourcesScope instanceSourcesScope, HashSet <IParameterSymbol>?usedParams, bool isScopeAsync) { var outerIsContainerScope = ReferenceEquals(instanceSourcesScope, containerScope); var innerIsContainerScope = outerIsContainerScope; if (outerIsContainerScope && visited.Contains(node)) { return(false); } if (!currentlyVisiting.Add(node)) { reportDiagnostic(CircularDependency(location, target, node)); return(true); } var result = false; if (!instanceSourcesScope.TryGetSource(node, out var instanceSource)) { reportDiagnostic(NoSourceForType(location, target, node)); result = true; } else { instanceSourcesScope = instanceSourcesScope.Enter(instanceSource); innerIsContainerScope = ReferenceEquals(instanceSourcesScope, containerScope); if (innerIsContainerScope && visited.Contains(node)) { return(false); } switch (instanceSource) { case DelegateSource(var delegateType, var returnType, var delegateParameters, var isAsync) delegateSource: { foreach (var paramsWithType in delegateParameters.GroupBy(x => x.Type)) { if (paramsWithType.Count() > 1) { reportDiagnostic(DelegateHasMultipleParametersOfTheSameType(location, target, node, paramsWithType.Key)); result = true; } } if (instanceSourcesScope.TryGetSource(returnType, out var returnTypeSource)) { if (returnTypeSource is DelegateParameter { parameter : var param }) { if (delegateParameters.Contains(param)) { reportDiagnostic(DelegateReturnTypeProvidedBySameDelegate(location, target, node, returnType)); } else { reportDiagnostic(DelegateReturnTypeProvidedByAnotherDelegate(location, target, node, returnType)); } }