Skip to content
This repository was archived by the owner on Dec 18, 2017. It is now read-only.

Commit

Permalink
Cleanup some of ApplicationHostContext and dependency management
Browse files Browse the repository at this point in the history
- Made DependencyWalker static and internal
- Pass project to GetAllExports and avoid walking the
graph twice for the same project
  • Loading branch information
davidfowl committed Aug 20, 2015
1 parent 40829cb commit a029ba0
Show file tree
Hide file tree
Showing 7 changed files with 60 additions and 51 deletions.
2 changes: 1 addition & 1 deletion src/Microsoft.Dnx.ApplicationHost/DefaultHost.cs
Original file line number Diff line number Diff line change
Expand Up @@ -154,7 +154,7 @@ private void Initialize(RuntimeOptions options, IServiceProvider hostServices, I
var hostEnvironment = (IApplicationEnvironment)hostServices.GetService(typeof(IApplicationEnvironment));
var applicationEnvironment = new ApplicationEnvironment(Project, _targetFramework, options.Configuration, hostEnvironment);

var compilationContext = new CompilationEngineContext(applicationEnvironment, loadContextAccessor.Default, new CompilationCache(), fileWatcher);
var compilationContext = new CompilationEngineContext(applicationEnvironment, loadContextAccessor.Default, new CompilationCache(), fileWatcher, new ProjectGraphProvider());

// Compilation services available only for runtime compilation
compilationContext.AddCompilationService(typeof(RuntimeOptions), options);
Expand Down
17 changes: 13 additions & 4 deletions src/Microsoft.Dnx.Compilation/CompilationEngineContext.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
using System;
using Microsoft.Dnx.Compilation;
using Microsoft.Dnx.Compilation.Caching;
using Microsoft.Dnx.Runtime;
using Microsoft.Dnx.Runtime.Common.DependencyInjection;
Expand All @@ -17,22 +16,32 @@ public class CompilationEngineContext

private readonly ServiceProvider _compilerServices = new ServiceProvider();

public CompilationEngineContext(IApplicationEnvironment applicationEnvironment,
IAssemblyLoadContext defaultLoadContext,
CompilationCache cache,
IProjectGraphProvider projectGraphProvider) :
this(applicationEnvironment, defaultLoadContext, cache, NoopWatcher.Instance, projectGraphProvider)
{

}

public CompilationEngineContext(IApplicationEnvironment applicationEnvironment,
IAssemblyLoadContext defaultLoadContext,
CompilationCache cache) :
this(applicationEnvironment, defaultLoadContext, cache, NoopWatcher.Instance)
this(applicationEnvironment, defaultLoadContext, cache, NoopWatcher.Instance, new ProjectGraphProvider())
{

}

public CompilationEngineContext(IApplicationEnvironment applicationEnvironment,
IAssemblyLoadContext defaultLoadContext,
CompilationCache cache,
IFileWatcher fileWatcher)
IFileWatcher fileWatcher,
IProjectGraphProvider projectGraphProvider)
{
ApplicationEnvironment = applicationEnvironment;
DefaultLoadContext = defaultLoadContext;
ProjectGraphProvider = new ProjectGraphProvider();
ProjectGraphProvider = projectGraphProvider;
CompilationCache = cache;
FileWatcher = fileWatcher;

Expand Down
34 changes: 22 additions & 12 deletions src/Microsoft.Dnx.Compilation/LibraryExporter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Runtime.Versioning;
using Microsoft.Dnx.Compilation.Caching;
using Microsoft.Dnx.Runtime;
using NuGet;
Expand Down Expand Up @@ -74,21 +73,21 @@ public LibraryExport GetAllExports(
string aspect,
Func<LibraryDescription, bool> libraryFilter)
{
var library = LibraryManager.GetLibraryDescription(name);
if (library == null)
var project = LibraryManager.GetLibraryDescription(name) as ProjectDescription;
if (project == null)
{
return null;
}
return GetAllExports(library, aspect, libraryFilter);
return GetAllExports(project, aspect, libraryFilter);
}

private LibraryExport GetAllExports(
LibraryDescription projectLibrary,
ProjectDescription project,
string aspect,
Func<LibraryDescription, bool> include)
{
var dependencyStopWatch = Stopwatch.StartNew();
Logger.TraceInformation($"[{nameof(LibraryExporter)}]: Resolving references for '{projectLibrary.Identity.Name}' {aspect}");
Logger.TraceInformation($"[{nameof(LibraryExporter)}]: Resolving references for '{project.Identity.Name}' {aspect}");

var references = new Dictionary<string, IMetadataReference>(StringComparer.OrdinalIgnoreCase);
var sourceReferences = new Dictionary<string, ISourceReference>(StringComparer.OrdinalIgnoreCase);
Expand All @@ -99,7 +98,7 @@ private LibraryExport GetAllExports(

var rootNode = new Node
{
Library = LibraryManager.GetLibraryDescription(projectLibrary.Identity.Name)
Library = project
};

queue.Enqueue(rootNode);
Expand All @@ -116,7 +115,18 @@ private LibraryExport GetAllExports(

if (include(node.Library))
{
var libraryExport = GetExport(node.Library, aspect: null);
LibraryExport libraryExport = null;

if (node.Library == project)
{
// We know it's a project so skip the lookup
libraryExport = ExportProject(project, aspect: null, exporter: this);
}
else
{
libraryExport = GetExport(node.Library, aspect: null);
}

if (libraryExport != null)
{
if (node.Parent == rootNode)
Expand Down Expand Up @@ -145,7 +155,7 @@ private LibraryExport GetAllExports(
}

dependencyStopWatch.Stop();
Logger.TraceInformation($"[{nameof(LibraryExporter)}]: Resolved {references.Count} references for '{projectLibrary.Identity.Name}' in {dependencyStopWatch.ElapsedMilliseconds}ms");
Logger.TraceInformation($"[{nameof(LibraryExporter)}]: Resolved {references.Count} references for '{project.Identity.Name}' in {dependencyStopWatch.ElapsedMilliseconds}ms");

return new LibraryExport(
references.Values.ToList(),
Expand Down Expand Up @@ -186,7 +196,7 @@ private LibraryExport GetExport(LibraryDescription library, string aspect)
}
else if (string.Equals(LibraryTypes.Project, library.Type, StringComparison.Ordinal))
{
return ExportProject((ProjectDescription)library, aspect);
return ExportProject((ProjectDescription)library, aspect, exporter: null);
}
else
{
Expand All @@ -210,7 +220,7 @@ private LibraryExport ExportPackage(PackageDescription package)
return new LibraryExport(references.Values.ToList(), sourceReferences);
}

private LibraryExport ExportProject(ProjectDescription project, string aspect)
private LibraryExport ExportProject(ProjectDescription project, string aspect, LibraryExporter exporter)
{
Logger.TraceInformation($"[{nameof(LibraryExporter)}]: {nameof(ExportProject)}({project.Identity.Name}, {aspect}, {project.Framework}, {_configuration})");

Expand Down Expand Up @@ -239,7 +249,7 @@ private LibraryExport ExportProject(ProjectDescription project, string aspect)
var compilerTypeInfo = project.Project.CompilerServices?.ProjectCompiler ?? Project.DefaultCompiler;

// Create the project exporter
var exporter = _compilationEngine.CreateProjectExporter(project.Project, project.Framework, _configuration);
exporter = exporter ?? _compilationEngine.CreateProjectExporter(project.Project, project.Framework, _configuration);

// Get the exports for the project dependencies
var projectDependenciesExport = new Lazy<LibraryExport>(() => exporter.GetAllDependencies(project.Identity.Name, aspect));
Expand Down
18 changes: 9 additions & 9 deletions src/Microsoft.Dnx.Runtime/ApplicationHostContext.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.

using System;
using System.Collections.Generic;
using System.IO;
using System.Runtime.Versioning;
using NuGet;

namespace Microsoft.Dnx.Runtime
{
Expand Down Expand Up @@ -44,7 +44,7 @@ public static void Initialize(ApplicationHostContext context)
var projectDependencyProvider = new ProjectReferenceDependencyProvider(projectResolver);
var unresolvedDependencyProvider = new UnresolvedDependencyProvider();

DependencyWalker dependencyWalker = null;
IList<IDependencyProvider> dependencyProviders = null;
LockFileLookup lockFileLookup = null;

if (context.Project == null)
Expand Down Expand Up @@ -82,31 +82,31 @@ public static void Initialize(ApplicationHostContext context)
lockFileLookup = new LockFileLookup(lockFile);
var packageDependencyProvider = new PackageDependencyProvider(context.PackagesDirectory, lockFileLookup);

dependencyWalker = new DependencyWalker(new IDependencyProvider[] {
dependencyProviders = new IDependencyProvider[] {
projectDependencyProvider,
packageDependencyProvider,
referenceAssemblyDependencyResolver,
gacDependencyResolver,
unresolvedDependencyProvider
});
};
}
}

if ((!validLockFile && !skipLockFileValidation) || !lockFileExists)
{
// We don't add NuGetDependencyProvider to DependencyWalker
// We don't add the PackageDependencyProvider to DependencyWalker
// It will leave all NuGet packages unresolved and give error message asking users to run "dnu restore"
dependencyWalker = new DependencyWalker(new IDependencyProvider[] {
dependencyProviders = new IDependencyProvider[] {
projectDependencyProvider,
referenceAssemblyDependencyResolver,
gacDependencyResolver,
unresolvedDependencyProvider
});
};
}

dependencyWalker.Walk(context.Project.Name, context.Project.Version, context.TargetFramework);
var libraries = DependencyWalker.Walk(dependencyProviders, context.Project.Name, context.Project.Version, context.TargetFramework);

context.LibraryManager = new LibraryManager(context.Project.ProjectFilePath, context.TargetFramework, dependencyWalker.Libraries);
context.LibraryManager = new LibraryManager(context.Project.ProjectFilePath, context.TargetFramework, libraries);

if (!validLockFile)
{
Expand Down
30 changes: 10 additions & 20 deletions src/Microsoft.Dnx.Runtime/DependencyManagement/DependencyWalker.cs
Original file line number Diff line number Diff line change
@@ -1,51 +1,41 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Runtime.Versioning;
using NuGet;

namespace Microsoft.Dnx.Runtime
{
public class DependencyWalker
internal static class DependencyWalker
{
private readonly IEnumerable<IDependencyProvider> _dependencyProviders;
private readonly List<LibraryDescription> _libraries = new List<LibraryDescription>();

public DependencyWalker(IEnumerable<IDependencyProvider> dependencyProviders)
public static IList<LibraryDescription> Walk(IList<IDependencyProvider> providers, string name, SemanticVersion version, FrameworkName targetFramework)
{
_dependencyProviders = dependencyProviders;
}
var libraries = new List<LibraryDescription>();

public IList<LibraryDescription> Libraries
{
get { return _libraries; }
}

public void Walk(string name, SemanticVersion version, FrameworkName targetFramework)
{
var sw = Stopwatch.StartNew();
Logger.TraceInformation("[{0}]: Walking dependency graph for '{1} {2}'.", GetType().Name, name, targetFramework);
Logger.TraceInformation($"[{nameof(DependencyWalker)}]: Walking dependency graph for '{name} {targetFramework}'.");

var context = new WalkContext();

var walkSw = Stopwatch.StartNew();

context.Walk(
_dependencyProviders,
providers,
name,
version,
targetFramework);

walkSw.Stop();
Logger.TraceInformation("[{0}]: Graph walk took {1}ms.", GetType().Name, walkSw.ElapsedMilliseconds);
Logger.TraceInformation($"[{nameof(DependencyWalker)}]: Graph walk took {walkSw.ElapsedMilliseconds}ms.");

context.Populate(targetFramework, Libraries);
context.Populate(targetFramework, libraries);

sw.Stop();
Logger.TraceInformation("[{0}]: Resolved dependencies for {1} in {2}ms", GetType().Name, name, sw.ElapsedMilliseconds);
Logger.TraceInformation($"$[{ nameof(DependencyWalker)}]: Resolved dependencies for {name} in { sw.ElapsedMilliseconds}ms");

return libraries;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ private IEnumerable<LibraryDependency> GetDependencies(LockFileTargetLibrary tar
}
}

public void Initialize(PackageDescription package)
private void Initialize(PackageDescription package)
{
string packagePath = ResolvePackagePath(package);

Expand Down Expand Up @@ -165,7 +165,7 @@ public static void ResolvePackageAssemblyPaths(LibraryManager libraryManager, Ac
var assemblyName = new AssemblyName(name);

string replacementPath;
if (Servicing.ServicingTable.TryGetReplacement(
if (ServicingTable.TryGetReplacement(
library.Identity.Name,
library.Identity.Version,
assemblyPath,
Expand Down
6 changes: 3 additions & 3 deletions src/Microsoft.Dnx.Runtime/DependencyManagement/WalkContext.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ public class WalkContext
private readonly IDictionary<string, Item> _usedItems = new Dictionary<string, Item>();

public void Walk(
IEnumerable<IDependencyProvider> dependencyResolvers,
IList<IDependencyProvider> dependencyResolvers,
string name,
SemanticVersion version,
FrameworkName frameworkName)
Expand All @@ -28,7 +28,7 @@ public void Walk(
}
};

var resolvers = dependencyResolvers as IDependencyProvider[] ?? dependencyResolvers.ToArray();
var resolvers = dependencyResolvers;
var resolvedItems = new Dictionary<LibraryRange, Item>();

var buildTreeSw = Stopwatch.StartNew();
Expand Down Expand Up @@ -209,7 +209,7 @@ public void Populate(FrameworkName frameworkName, IList<LibraryDescription> libr
{
var library = item.Description;
library.Dependencies = library.Dependencies.SelectMany(CorrectDependencyVersion).ToList();
library.Framework = library.Framework ?? frameworkName;
library.Framework = library.Framework ?? frameworkName;
libraries.Add(library);
}

Expand Down

0 comments on commit a029ba0

Please sign in to comment.