diff --git a/build/Packages.props b/build/Packages.props index f7de2c33ed..fb0d45ebf3 100644 --- a/build/Packages.props +++ b/build/Packages.props @@ -2,7 +2,8 @@ - 2.0.3 + 0.1.0 + 0.1.0 1.1.0 1.1.0 1.1.0 @@ -25,7 +26,7 @@ 1.1.0 1.1.0 1.1.0 - 1.1.0 + 2.0.0 1.1.0 1.1.0 1.1.0 diff --git a/src/OmniSharp.Script/OmniSharp.Script.csproj b/src/OmniSharp.Script/OmniSharp.Script.csproj index 96752b03e0..098c34c0c8 100644 --- a/src/OmniSharp.Script/OmniSharp.Script.csproj +++ b/src/OmniSharp.Script/OmniSharp.Script.csproj @@ -12,7 +12,8 @@ - + + diff --git a/src/OmniSharp.Script/ScriptHelper.cs b/src/OmniSharp.Script/ScriptHelper.cs index 4f29ed66b2..31443bfdb9 100644 --- a/src/OmniSharp.Script/ScriptHelper.cs +++ b/src/OmniSharp.Script/ScriptHelper.cs @@ -1,7 +1,7 @@ using System; using System.Collections.Generic; using System.Reflection; -using Dotnet.Script.NuGetMetadataResolver; +using Dotnet.Script.DependencyModel.NuGet; using Microsoft.CodeAnalysis; using Microsoft.CodeAnalysis.CSharp; using Microsoft.CodeAnalysis.Scripting; diff --git a/src/OmniSharp.Script/ScriptProjectSystem.cs b/src/OmniSharp.Script/ScriptProjectSystem.cs index 0d70c952ee..0ec17b630e 100644 --- a/src/OmniSharp.Script/ScriptProjectSystem.cs +++ b/src/OmniSharp.Script/ScriptProjectSystem.cs @@ -5,15 +5,14 @@ using System.Linq; using System.Reflection; using System.Threading.Tasks; -using Dotnet.Script.NuGetMetadataResolver; using Microsoft.CodeAnalysis; -using Microsoft.CodeAnalysis.CSharp; -using Microsoft.DotNet.ProjectModel; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyModel; using Microsoft.Extensions.Logging; using OmniSharp.Models.WorkspaceInformation; using OmniSharp.Services; +using Dotnet.Script.DependencyModel.Compilation; +using LogLevel = Dotnet.Script.DependencyModel.Logging.LogLevel; namespace OmniSharp.Script { @@ -31,8 +30,7 @@ public class ScriptProjectSystem : IProjectSystem private readonly IOmniSharpEnvironment _env; private readonly ILogger _logger; - private readonly IScriptProjectProvider _scriptProjectProvider; - private static readonly Lazy _targetFrameWork = new Lazy(ResolveTargetFramework); + private readonly CompilationDependencyResolver _compilationDependencyResolver; [ImportingConstructor] public ScriptProjectSystem(OmniSharpWorkspace workspace, IOmniSharpEnvironment env, ILoggerFactory loggerFactory, @@ -43,7 +41,24 @@ public ScriptProjectSystem(OmniSharpWorkspace workspace, IOmniSharpEnvironment e _env = env; _logger = loggerFactory.CreateLogger(); _projects = new Dictionary(); - _scriptProjectProvider = ScriptProjectProvider.Create(loggerFactory); + + _compilationDependencyResolver = new CompilationDependencyResolver(type => + { + // Prefix with "OmniSharp" so that we make it through the log filter. + var categoryName = $"OmniSharp.Script.{type.FullName}"; + var dependencyResolverLogger = loggerFactory.CreateLogger(categoryName); + return ((level, message) => + { + if (level == LogLevel.Debug) + { + dependencyResolverLogger.LogDebug(message); + } + if (level == LogLevel.Info) + { + dependencyResolverLogger.LogInformation(message); + } + }); + }); } public string Key => "Script"; @@ -73,45 +88,31 @@ public void Initalize(IConfiguration configuration) // explicitly include System.ValueTuple inheritedCompileLibraries.AddRange(DependencyContext.Default.CompileLibraries.Where(x => x.Name.ToLowerInvariant().StartsWith("system.valuetuple"))); - - var runtimeContexts = File.Exists(Path.Combine(_env.TargetDirectory, "project.json")) ? ProjectContext.CreateContextForEachTarget(_env.TargetDirectory) : null; + if (!bool.TryParse(configuration["enableScriptNuGetReferences"], out var enableScriptNuGetReferences)) { enableScriptNuGetReferences = false; } - if (enableScriptNuGetReferences && (runtimeContexts == null || runtimeContexts.Any() == false)) - { - runtimeContexts = TryCreateRuntimeContextsFromScriptFiles(); - } - - var runtimeContext = runtimeContexts?.FirstOrDefault(); var commonReferences = new HashSet(); - // if we have no context, then we also have no dependencies + var compilationDependencies = TryGetCompilationDependencies(enableScriptNuGetReferences); + + // if we have no compilation dependencies // we will assume desktop framework // and add default CLR references // same applies for having a context that is not a .NET Core app - AddDefaultClrMetadataReferences(runtimeContext, commonReferences); - if (runtimeContext == null) + if (!compilationDependencies.Any()) { - _logger.LogInformation("Unable to find project context for CSX files. Will default to non-context usage (Destkop CLR scripts)."); + _logger.LogInformation("Unable to find dependency context for CSX files. Will default to non-context usage (Destkop CLR scripts)."); + AddDefaultClrMetadataReferences(commonReferences); } - // otherwise we will grab dependencies for the script from the runtime context else { - // assume the first one - _logger.LogInformation($"Found script runtime context '{runtimeContext.TargetFramework.Framework}' for '{runtimeContext.ProjectFile.ProjectFilePath}'."); - - var projectExporter = runtimeContext.CreateExporter("Release"); - var projectDependencies = projectExporter.GetDependencies(); - - // let's inject all compilation assemblies needed - var compilationAssemblies = projectDependencies.SelectMany(x => x.CompilationAssemblies); - foreach (var compilationAssembly in compilationAssemblies) + foreach (var compilationAssembly in compilationDependencies) { - _logger.LogDebug("Discovered script compilation assembly reference: " + compilationAssembly.ResolvedPath); - AddMetadataReference(commonReferences, compilationAssembly.ResolvedPath); + _logger.LogDebug("Discovered script compilation assembly reference: " + compilationAssembly); + AddMetadataReference(commonReferences, compilationAssembly); } } @@ -144,30 +145,40 @@ public void Initalize(IConfiguration configuration) } } - private void AddDefaultClrMetadataReferences(ProjectContext projectContext, HashSet commonReferences) + private string[] TryGetCompilationDependencies(bool enableScriptNuGetReferences) { - if (projectContext == null || projectContext.TargetFramework?.Framework != ".NETCoreApp") + try { - var assemblies = new[] - { - typeof(object).GetTypeInfo().Assembly, - typeof(Enumerable).GetTypeInfo().Assembly, - typeof(Stack<>).GetTypeInfo().Assembly, - typeof(Lazy<,>).GetTypeInfo().Assembly, - FromName("System.Runtime"), - FromName("mscorlib") - }; - - var references = assemblies - .Where(a => a != null) - .Select(a => a.Location) - .Distinct() - .Select(l => _metadataFileReferenceCache.GetMetadataReference(l)); - - foreach (var reference in references) - { - commonReferences.Add(reference); - } + return _compilationDependencyResolver.GetDependencies(_env.TargetDirectory, enableScriptNuGetReferences).ToArray(); + } + catch (Exception e) + { + _logger.LogError("Failed to resolve compilation dependencies", e); + return Array.Empty(); + } + } + + private void AddDefaultClrMetadataReferences(HashSet commonReferences) + { + var assemblies = new[] + { + typeof(object).GetTypeInfo().Assembly, + typeof(Enumerable).GetTypeInfo().Assembly, + typeof(Stack<>).GetTypeInfo().Assembly, + typeof(Lazy<,>).GetTypeInfo().Assembly, + FromName("System.Runtime"), + FromName("mscorlib") + }; + + var references = assemblies + .Where(a => a != null) + .Select(a => a.Location) + .Distinct() + .Select(l => _metadataFileReferenceCache.GetMetadataReference(l)); + + foreach (var reference in references) + { + commonReferences.Add(reference); } Assembly FromName(string assemblyName) @@ -183,21 +194,6 @@ Assembly FromName(string assemblyName) } } - private IEnumerable TryCreateRuntimeContextsFromScriptFiles() - { - _logger.LogInformation($"Attempting to create runtime context from script files. Default target framework {_targetFrameWork.Value}"); - try - { - var scriptProjectInfo = _scriptProjectProvider.CreateProject(_env.TargetDirectory, _targetFrameWork.Value); - return ProjectContext.CreateContextForEachTarget(Path.GetDirectoryName(scriptProjectInfo.PathToProjectJson)); - } - catch (Exception exception) - { - _logger.LogError(exception, "Unable to create runtime context from script files."); - } - return null; - } - private void AddMetadataReference(ISet referenceCollection, string fileReference) { if (!File.Exists(fileReference)) @@ -260,13 +256,5 @@ Task IProjectSystem.GetWorkspaceModelAsync(WorkspaceInformationRequest r } return Task.FromResult(new ScriptContextModelCollection(scriptContextModels)); } - - private static string ResolveTargetFramework() - { - return Assembly.GetEntryAssembly().GetCustomAttributes() - .OfType() - .Select(x => x.FrameworkName) - .FirstOrDefault(); - } } -} \ No newline at end of file +} diff --git a/tests/app.config b/tests/app.config index c67d67cb96..e45e38ad21 100644 --- a/tests/app.config +++ b/tests/app.config @@ -37,11 +37,11 @@ - + - +