提交 aa2d668b 编写于 作者: M Matt Warren

change error flow

上级 e03fb568
Microsoft.CodeAnalysis.MSBuild.MSBuildWorkspace.Diagnostics.get -> System.Collections.Immutable.ImmutableList<Microsoft.CodeAnalysis.WorkspaceDiagnostic>
\ No newline at end of file
......@@ -23,8 +23,8 @@ internal partial class CSharpProjectFileLoader : ProjectFileLoader
{
private class CSharpProjectFile : ProjectFile
{
public CSharpProjectFile(CSharpProjectFileLoader loader, MSB.Evaluation.Project project, Exception loadException)
: base(loader, project, loadException)
public CSharpProjectFile(CSharpProjectFileLoader loader, MSB.Evaluation.Project project, string errorMessage)
: base(loader, project, errorMessage)
{
}
......@@ -98,7 +98,7 @@ private ProjectFileInfo CreateProjectFileInfo(CSharpCompilerInputs compilerInput
docs,
additionalDocs,
this.GetProjectReferences(buildInfo.Project),
buildInfo.Exception);
buildInfo.ErrorMessage);
}
else
{
......@@ -109,7 +109,7 @@ private ProjectFileInfo CreateProjectFileInfo(CSharpCompilerInputs compilerInput
documents: SpecializedCollections.EmptyEnumerable<DocumentFileInfo>(),
additionalDocuments: SpecializedCollections.EmptyEnumerable<DocumentFileInfo>(),
projectReferences: SpecializedCollections.EmptyEnumerable<ProjectFileReference>(),
buildException: buildInfo.Exception);
errorMessage: buildInfo.ErrorMessage);
}
}
......
......@@ -22,7 +22,7 @@ public override string Language
protected override ProjectFile CreateProjectFile(LoadedProjectInfo info)
{
return new CSharpProjectFile(this, info.Project, info.Exception);
return new CSharpProjectFile(this, info.Project, info.ErrorMessage);
}
}
}
......@@ -157,7 +157,7 @@ private void SetSolutionProperties(string solutionFilePath)
{
// projects get added to 'loadedProjects' as side-effect
// never prefer metadata when loading solution, all projects get loaded if they can.
var tmp = await GetOrLoadProjectAsync(projectAbsolutePath, loader, preferMetadata: false, reportBuildFailures: ReportMode.Log, loadedProjects: loadedProjects, cancellationToken: cancellationToken).ConfigureAwait(false);
var tmp = await GetOrLoadProjectAsync(projectAbsolutePath, loader, preferMetadata: false, loadedProjects: loadedProjects, cancellationToken: cancellationToken).ConfigureAwait(false);
}
}
}
......@@ -210,7 +210,7 @@ internal string GetAbsoluteSolutionPath(string path, string baseDirectory)
var loadedProjects = new LoadState(projectPathToProjectIdMap);
var id = await this.LoadProjectAsync(fullPath, loader, this.LoadMetadataForReferencedProjects, ReportMode.Log, loadedProjects, cancellationToken).ConfigureAwait(false);
var id = await this.LoadProjectAsync(fullPath, loader, this.LoadMetadataForReferencedProjects, loadedProjects, cancellationToken).ConfigureAwait(false);
var result = loadedProjects.Projects.Reverse().ToImmutableArray();
Debug.Assert(result[0].Id == id);
......@@ -304,18 +304,18 @@ public ProjectId GetOrCreateProjectId(string fullProjectPath)
}
}
private async Task<ProjectId> GetOrLoadProjectAsync(string projectFilePath, IProjectFileLoader loader, bool preferMetadata, ReportMode reportBuildFailures, LoadState loadedProjects, CancellationToken cancellationToken)
private async Task<ProjectId> GetOrLoadProjectAsync(string projectFilePath, IProjectFileLoader loader, bool preferMetadata, LoadState loadedProjects, CancellationToken cancellationToken)
{
var projectId = loadedProjects.GetProjectId(projectFilePath);
if (projectId == null)
{
projectId = await this.LoadProjectAsync(projectFilePath, loader, preferMetadata, reportBuildFailures, loadedProjects, cancellationToken).ConfigureAwait(false);
projectId = await this.LoadProjectAsync(projectFilePath, loader, preferMetadata, loadedProjects, cancellationToken).ConfigureAwait(false);
}
return projectId;
}
private async Task<ProjectId> LoadProjectAsync(string projectFilePath, IProjectFileLoader loader, bool preferMetadata, ReportMode reportBuildFailures, LoadState loadedProjects, CancellationToken cancellationToken)
private async Task<ProjectId> LoadProjectAsync(string projectFilePath, IProjectFileLoader loader, bool preferMetadata, LoadState loadedProjects, CancellationToken cancellationToken)
{
Debug.Assert(projectFilePath != null);
Debug.Assert(loader != null);
......@@ -324,19 +324,19 @@ private async Task<ProjectId> LoadProjectAsync(string projectFilePath, IProjectF
var projectName = Path.GetFileNameWithoutExtension(projectFilePath);
var projectFile = await loader.LoadProjectFileAsync(projectFilePath, _properties, cancellationToken).ConfigureAwait(false);
if (projectFile.LoadException != null)
if (projectFile.ErrorMessage != null)
{
ReportFailure(reportBuildFailures, string.Format(WorkspaceDesktopResources.Cannot_open_project_0_because_msbuild_failed_with_message_1, projectFilePath, projectFile.LoadException.Message));
ReportFailure(ReportMode.Log, GetMsbuildFailedMessage(projectFilePath, projectFile.ErrorMessage));
// if we failed during load there won't be any project file info, so bail early with empty project.
loadedProjects.Add(CreateEmptyProjectInfo(projectId, projectFilePath, loader.Language));
return projectId;
}
var projectFileInfo = await projectFile.GetProjectFileInfoAsync(cancellationToken).ConfigureAwait(false);
if (projectFileInfo.BuildException != null)
if (projectFileInfo.ErrorMessage != null)
{
ReportFailure(reportBuildFailures, string.Format(WorkspaceDesktopResources.Cannot_open_project_0_because_msbuild_failed_with_message_1, projectFilePath, projectFileInfo.BuildException.Message));
loadedProjects.Add(CreateEmptyProjectInfo(projectId, projectFilePath, loader.Language));
return projectId;
ReportFailure(ReportMode.Log, GetMsbuildFailedMessage(projectFilePath, projectFileInfo.ErrorMessage));
}
var projectDirectory = Path.GetDirectoryName(projectFilePath);
......@@ -464,6 +464,18 @@ private async Task<ProjectId> LoadProjectAsync(string projectFilePath, IProjectF
return projectId;
}
private static string GetMsbuildFailedMessage(string projectFilePath, string message)
{
if (string.IsNullOrWhiteSpace(message))
{
return string.Format(WorkspaceDesktopResources.Msbuild_failed_when_processing_the_file_0, projectFilePath);
}
else
{
return string.Format(WorkspaceDesktopResources.Msbuild_failed_when_processing_the_file_0_with_message_1, projectFilePath, message);
}
}
private static VersionStamp GetProjectVersion(string projectFilePath)
{
if (!string.IsNullOrEmpty(projectFilePath) && File.Exists(projectFilePath))
......@@ -604,7 +616,7 @@ private class ResolvedReferences
if (TryGetLoaderFromProjectPath(fullPath, reportMode, out loader))
{
// load the project
var projectId = await this.GetOrLoadProjectAsync(fullPath, loader, preferMetadata, ReportMode.Log, loadedProjects, cancellationToken).ConfigureAwait(false);
var projectId = await this.GetOrLoadProjectAsync(fullPath, loader, preferMetadata, loadedProjects, cancellationToken).ConfigureAwait(false);
// If that other project already has a reference on us, this will cause a circularity.
// This check doesn't need to be in the "already loaded" path above, since in any circularity this path
......
......@@ -30,6 +30,7 @@ public sealed class MSBuildWorkspace : Workspace
private readonly NonReentrantLock _serializationLock = new NonReentrantLock();
private MSBuildProjectLoader _loader;
private ImmutableList<WorkspaceDiagnostic> _diagnostics = ImmutableList<WorkspaceDiagnostic>.Empty;
private MSBuildWorkspace(
HostServices hostServices,
......@@ -96,6 +97,20 @@ public static MSBuildWorkspace Create(IDictionary<string, string> properties, Ho
get { return _loader.Properties; }
}
/// <summary>
/// Diagnostics logged while opening solutions, projects and documents.
/// </summary>
public ImmutableList<WorkspaceDiagnostic> Diagnostics
{
get { return _diagnostics; }
}
protected internal override void OnWorkspaceFailed(WorkspaceDiagnostic diagnostic)
{
ImmutableInterlocked.Update(ref _diagnostics, d => d.Add(diagnostic));
base.OnWorkspaceFailed(diagnostic);
}
/// <summary>
/// Determines if metadata from existing output assemblies is loaded instead of opening referenced projects.
/// If the referenced project is already opened, the metadata will not be loaded.
......
// Copyright (c) Microsoft. 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.IO;
using System.Linq;
using System.Threading;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.Text;
using Roslyn.Utilities;
using MSB = Microsoft.Build;
namespace Microsoft.CodeAnalysis.MSBuild
{
/// <summary>
/// Defines a list of build targets and operations to modify that list.
/// </summary>
internal class BuildTargets
{
private readonly MSB.Evaluation.Project _project;
private readonly List<string> _buildTargets;
public BuildTargets(MSB.Evaluation.Project project, params string[] targets)
{
_project = project;
_buildTargets = new List<string>();
_buildTargets.AddRange(targets);
}
public string[] Targets
{
get { return _buildTargets.ToArray(); }
}
/// <summary>
/// Remove the specified target from the build targets.
///
/// If the target is nested (a dependent target) of one of the build targets,
/// promote the siblings of the target to the formal list (in execution order.)
/// </summary>
public void Remove(string target)
{
// keep a set of targets already known to be in the build target list so we can keep
// from redundantly adding multiple of the same targets when we replace a target with
// its children
var knownTargets = new HashSet<string>();
for (int i = 0; i < _buildTargets.Count;)
{
var buildTarget = _buildTargets[i];
if (buildTarget == target)
{
// we found it!
_buildTargets.RemoveAt(i);
// it might exist multiple times
continue;
}
else if (DependsOn(buildTarget, target))
{
// replace this build target with its children and check again
_buildTargets.RemoveAt(i);
int loc = i;
foreach (var dependsOnTarget in GetTargetDependents(_project, buildTarget))
{
if (!knownTargets.Contains(dependsOnTarget))
{
_buildTargets.Insert(loc, dependsOnTarget);
loc++;
}
}
continue;
}
else
{
knownTargets.Add(buildTarget);
i++;
}
}
}
/// <summary>
/// Remove all targets after the specified target (and possibly also remove the specified target).
///
/// If a removed target is nested (a dependent target) of one of the build targets,
/// promote the siblings of the removed target to the formal list (in execution order).
/// </summary>
public void RemoveAfter(string target, bool includeTargetInRemoval)
{
// keep a set of targets already known to be in the build target list
// so we can keep from redundantly adding multiple of the same targets
// when we replace a target with its children
var knownTargets = new HashSet<string>();
bool found = false;
for (int i = 0; i < _buildTargets.Count;)
{
var buildTarget = _buildTargets[i];
if (found)
{
_buildTargets.RemoveAt(i);
continue;
}
else if (buildTarget == target)
{
// we found it!
found = true;
if (!includeTargetInRemoval)
{
i++;
}
}
else if (DependsOn(buildTarget, target))
{
// replace this build target with its children and check again
_buildTargets.RemoveAt(i);
int loc = i;
foreach (var dependsOnTarget in GetTargetDependents(_project, buildTarget))
{
if (!knownTargets.Contains(dependsOnTarget))
{
_buildTargets.Insert(loc, dependsOnTarget);
loc++;
}
}
continue;
}
else
{
knownTargets.Add(buildTarget);
i++;
}
}
}
private bool DependsOn(string target, string dependentTarget)
{
foreach (var dependsOnTarget in GetTargetDependents(_project, target))
{
if (dependsOnTarget == dependentTarget || DependsOn(dependsOnTarget, dependentTarget))
{
return true;
}
}
return false;
}
private static readonly char[] s_targetsSplitChars = new char[] { ';', '\r', '\n', '\t', ' ' };
private static IEnumerable<string> SplitTargets(string targets)
{
return targets.Split(s_targetsSplitChars, StringSplitOptions.RemoveEmptyEntries);
}
private static IEnumerable<string> GetTargetDependents(MSB.Evaluation.Project project, string targetName)
{
MSB.Execution.ProjectTargetInstance targetInstance;
if (project.Targets.TryGetValue(targetName, out targetInstance))
{
return SplitTargets(project.ExpandString(targetInstance.DependsOnTargets));
}
else
{
return SpecializedCollections.EmptyEnumerable<string>();
}
}
internal static IEnumerable<string> GetTopLevelTargets(MSB.Evaluation.Project project)
{
// start with set of all targets
HashSet<string> targets = new HashSet<string>(project.Targets.Keys);
// remove any target that another target depends on
foreach (var target in project.Targets.Keys)
{
var dependents = GetTargetDependents(project, target).ToList();
foreach (var depTarget in dependents)
{
targets.Remove(depTarget);
}
}
return targets;
}
}
}
......@@ -21,9 +21,10 @@ internal interface IProjectFile
string FilePath { get; }
/// <summary>
/// Exception thrown attempting to load the project.
/// The error message produced when a failure occurred attempting to access the project file.
/// If a failure occurred the projectd file info will be inaccessible.
/// </summary>
Exception LoadException { get; }
string ErrorMessage { get; }
/// <summary>
/// Gets the project file info asynchronously.
......
......@@ -19,13 +19,13 @@ internal abstract class ProjectFile : IProjectFile
{
private readonly ProjectFileLoader _loader;
private readonly MSB.Evaluation.Project _loadedProject;
private readonly Exception _loadException;
private readonly string _errorMessage;
public ProjectFile(ProjectFileLoader loader, MSB.Evaluation.Project loadedProject, Exception loadException)
public ProjectFile(ProjectFileLoader loader, MSB.Evaluation.Project loadedProject, string errorMessage)
{
_loader = loader;
_loadedProject = loadedProject;
_loadException = loadException;
_errorMessage = errorMessage;
}
~ProjectFile()
......@@ -45,9 +45,9 @@ public virtual string FilePath
get { return _loadedProject.FullPath; }
}
public Exception LoadException
public string ErrorMessage
{
get { return _loadException; }
get { return _errorMessage; }
}
public string GetPropertyValue(string name)
......@@ -62,24 +62,17 @@ public string GetPropertyValue(string name)
public struct BuildInfo
{
public readonly ProjectInstance Project;
public readonly Exception Exception;
public readonly string ErrorMessage;
public BuildInfo(ProjectInstance project, Exception exception)
public BuildInfo(ProjectInstance project, string errorMessage)
{
this.Project = project;
this.Exception = exception;
this.ErrorMessage = errorMessage;
}
}
protected async Task<BuildInfo> BuildAsync(string taskName, MSB.Framework.ITaskHost taskHost, CancellationToken cancellationToken)
{
// prepare for building
var buildTargets = new BuildTargets(_loadedProject, "Compile");
// don't execute anything after CoreCompile target, since we've
// already done everything we need to compute compiler inputs by then.
buildTargets.RemoveAfter("CoreCompile", includeTargetInRemoval: false);
// create a project instance to be executed by build engine.
// The executed project will hold the final model of the project after execution via msbuild.
var executedProject = _loadedProject.CreateProjectInstance();
......@@ -94,19 +87,19 @@ protected async Task<BuildInfo> BuildAsync(string taskName, MSB.Framework.ITaskH
// connect the host "callback" object with the host services, so we get called back with the exact inputs to the compiler task.
hostServices.RegisterHostObject(_loadedProject.FullPath, "CoreCompile", taskName, taskHost);
try
{
var buildParameters = new MSB.Execution.BuildParameters(_loadedProject.ProjectCollection);
var buildParameters = new MSB.Execution.BuildParameters(_loadedProject.ProjectCollection);
var buildRequestData = new MSB.Execution.BuildRequestData(executedProject, buildTargets.Targets, hostServices);
var buildRequestData = new MSB.Execution.BuildRequestData(executedProject, new string[] { "Compile" }, hostServices);
var result = await this.BuildAsync(buildParameters, buildRequestData, cancellationToken).ConfigureAwait(continueOnCapturedContext: false);
BuildResult result = await this.BuildAsync(buildParameters, buildRequestData, cancellationToken).ConfigureAwait(continueOnCapturedContext: false);
return new BuildInfo(executedProject, result.Exception);
if (result.OverallResult == BuildResultCode.Failure)
{
return new BuildInfo(executedProject, result.Exception?.Message ?? "");
}
catch (Exception e)
else
{
return new BuildInfo(project: null, exception: e);
return new BuildInfo(executedProject, null);
}
}
......
......@@ -43,9 +43,10 @@ internal sealed class ProjectFileInfo
public IReadOnlyList<ProjectFileReference> ProjectReferences { get; }
/// <summary>
/// An exception produced by the build system.
/// The error message produced when a failure occurred attempting to get the info.
/// If a failure occurred some or all of the information may be inaccurate or incomplete.
/// </summary>
public Exception BuildException { get; }
public string ErrorMessage { get; }
public ProjectFileInfo(
string outputPath,
......@@ -54,7 +55,7 @@ internal sealed class ProjectFileInfo
IEnumerable<DocumentFileInfo> documents,
IEnumerable<DocumentFileInfo> additionalDocuments,
IEnumerable<ProjectFileReference> projectReferences,
Exception buildException)
string errorMessage)
{
this.OutputFilePath = outputPath;
this.AssemblyName = assemblyName;
......@@ -62,7 +63,7 @@ internal sealed class ProjectFileInfo
this.Documents = documents.ToImmutableReadOnlyListOrEmpty();
this.AdditionalDocuments = additionalDocuments.ToImmutableArrayOrEmpty();
this.ProjectReferences = projectReferences.ToImmutableReadOnlyListOrEmpty();
this.BuildException = buildException;
this.ErrorMessage = errorMessage;
}
}
}
......@@ -42,12 +42,12 @@ public async Task<IProjectFile> LoadProjectFileAsync(string path, IDictionary<st
public struct LoadedProjectInfo
{
public readonly MSB.Evaluation.Project Project;
public readonly Exception Exception;
public readonly string ErrorMessage;
public LoadedProjectInfo(MSB.Evaluation.Project project, Exception exception)
public LoadedProjectInfo(MSB.Evaluation.Project project, string errorMessage)
{
this.Project = project;
this.Exception = exception;
this.ErrorMessage = errorMessage;
}
}
......@@ -69,11 +69,11 @@ private static async Task<LoadedProjectInfo> LoadProjectAsync(string path, IDict
return new LoadedProjectInfo(
new MSB.Evaluation.Project(xml, properties, toolsVersion: null, projectCollection: collection),
exception: null);
errorMessage: null);
}
catch (Exception e)
{
return new LoadedProjectInfo(project: null, exception: e);
return new LoadedProjectInfo(project: null, errorMessage: e.Message);
}
}
......
......@@ -35,13 +35,13 @@ internal VisualBasicProjectFileLoader()
protected override ProjectFile CreateProjectFile(LoadedProjectInfo info)
{
return new VisualBasicProjectFile(this, info.Project, info.Exception);
return new VisualBasicProjectFile(this, info.Project, info.ErrorMessage);
}
internal class VisualBasicProjectFile : ProjectFile
{
public VisualBasicProjectFile(VisualBasicProjectFileLoader loader, MSB.Evaluation.Project loadedProject, Exception loadException)
: base(loader, loadedProject, loadException)
public VisualBasicProjectFile(VisualBasicProjectFileLoader loader, MSB.Evaluation.Project loadedProject, string errorMessage)
: base(loader, loadedProject, errorMessage)
{
}
......@@ -89,7 +89,7 @@ private ProjectFileInfo CreateProjectFileInfo(VisualBasicProjectFileLoader.Visua
documents,
additionalDocuments,
projectRefeferences,
buildInfo.Exception);
buildInfo.ErrorMessage);
}
private IEnumerable<DocumentFileInfo> GetDocuments(IEnumerable<ITaskItem> sources, ProjectInstance executedProject)
......
......@@ -60,15 +60,6 @@ internal class WorkspaceDesktopResources {
}
}
/// <summary>
/// Looks up a localized string similar to Cannot open project &apos;{0}&apos; because msbuild failed with message: {1}.
/// </summary>
internal static string Cannot_open_project_0_because_msbuild_failed_with_message_1 {
get {
return ResourceManager.GetString("Cannot_open_project_0_because_msbuild_failed_with_message_1", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Invalid assembly name.
/// </summary>
......@@ -87,6 +78,24 @@ internal class WorkspaceDesktopResources {
}
}
/// <summary>
/// Looks up a localized string similar to Msbuild failed when processing the file &apos;{0}&apos;.
/// </summary>
internal static string Msbuild_failed_when_processing_the_file_0 {
get {
return ResourceManager.GetString("Msbuild_failed_when_processing_the_file_0", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Msbuild failed when processing the file &apos;{0}&apos; with message: {1}.
/// </summary>
internal static string Msbuild_failed_when_processing_the_file_0_with_message_1 {
get {
return ResourceManager.GetString("Msbuild_failed_when_processing_the_file_0_with_message_1", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to .
/// </summary>
......
......@@ -117,15 +117,18 @@
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<data name="Cannot_open_project_0_because_msbuild_failed_with_message_1" xml:space="preserve">
<value>Cannot open project '{0}' because msbuild failed with message: {1}</value>
</data>
<data name="Invalid_assembly_name" xml:space="preserve">
<value>Invalid assembly name</value>
</data>
<data name="Invalid_characters_in_assembly_name" xml:space="preserve">
<value>Invalid characters in assembly name</value>
</data>
<data name="Msbuild_failed_when_processing_the_file_0" xml:space="preserve">
<value>Msbuild failed when processing the file '{0}'</value>
</data>
<data name="Msbuild_failed_when_processing_the_file_0_with_message_1" xml:space="preserve">
<value>Msbuild failed when processing the file '{0}' with message: {1}</value>
</data>
<data name="String1" xml:space="preserve">
<value />
</data>
......
......@@ -111,7 +111,6 @@
<Compile Include="Workspace\MSBuild\CSharp\CSharpProjectFileLoader.CSharpProjectFile.cs" />
<Compile Include="Workspace\MSBuild\CSharp\CSharpProjectFileLoaderFactory.cs" />
<Compile Include="Workspace\MSBuild\MSBuildWorkspace.cs" />
<Compile Include="Workspace\MSBuild\ProjectFile\BuildTargets.cs" />
<Compile Include="Workspace\MSBuild\ProjectFile\DocumentFileInfo.cs" />
<Compile Include="Workspace\MSBuild\ProjectFile\IProjectFile.cs" />
<Compile Include="Workspace\MSBuild\ProjectFile\IProjectFileLoader.cs" />
......
......@@ -289,6 +289,11 @@
<SubType>Designer</SubType>
</EmbeddedResource>
</ItemGroup>
<ItemGroup>
<EmbeddedResource Include="TestFiles\CSharpProject_CSharpProject_MsbuildError.csproj">
<SubType>Designer</SubType>
</EmbeddedResource>
</ItemGroup>
<Import Project="..\..\..\build\Targets\Imports.targets" />
<Import Project="..\..\..\build\Targets\Roslyn.Toolsets.Xunit.targets" />
</Project>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. -->
<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProductVersion>8.0.30703</ProductVersion>
<SchemaVersion>2.0</SchemaVersion>
<ProjectGuid>{686DD036-86AA-443E-8A10-DDB43266A8C4}</ProjectGuid>
<OutputType>Library</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>CSharpProject</RootNamespace>
<AssemblyName>CSharpProject</AssemblyName>
<TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
<AssemblyOriginatorKeyFile>snKey.snk</AssemblyOriginatorKeyFile>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<Reference Include="Microsoft.CSharp" />
<Reference Include="System" />
<Reference Include="System.Core" />
</ItemGroup>
<ItemGroup>
<Compile Include="CSharpClass.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
</ItemGroup>
<PropertyGroup>
<CompileDependsOn>TestError;$(CompileDependsOn)</CompileDependsOn>
</PropertyGroup>
<Target Name="TestError" BeforeTargets="CoreCompile">
<Error Text="This is a test of the msbuild error system. This is only a test." />
</Target>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
</Project>
......@@ -1265,20 +1265,14 @@ public void TestOpenProject_WithUnrecognizedProjectReferenceFileExtension_BadMsb
Workspace.TestHookStandaloneProjectsDoNotHoldReferences = true;
var ws = MSBuildWorkspace.Create();
var diags = new List<WorkspaceDiagnostic>();
ws.WorkspaceFailed += (s, args) =>
{
diags.Add(args.Diagnostic);
};
ws.SkipUnrecognizedProjects = true;
var project = ws.OpenProjectAsync(GetSolutionFileName(@"VisualBasicProject\VisualBasicProject.vbproj")).Result;
Assert.Equal(1, project.Solution.ProjectIds.Count);
Assert.Equal(0, project.ProjectReferences.Count());
Assert.Equal(1, project.AllProjectReferences.Count());
Assert.Equal(1, diags.Count);
Assert.Equal(1, ws.Diagnostics.Count);
}
[Fact(Skip = "https://roslyn.codeplex.com/workitem/451"), Trait(Traits.Feature, Traits.Features.Workspace)]
......@@ -2923,17 +2917,10 @@ public async Task TestOpenProject_BadTaskImport()
.WithFile(@"CSharpProject\CSharpProject.csproj", GetResourceText(@"CSharpProject_CSharpProject_BadTasks.csproj")));
var ws = MSBuildWorkspace.Create();
string message = null;
ws.WorkspaceFailed += (sender, args) =>
{
message = args.Diagnostic.Message;
};
var proj = await ws.OpenProjectAsync(GetSolutionFileName(@"CSharpProject\CSharpProject.csproj"));
Assert.NotNull(message);
Assert.True(message.StartsWith("Cannot open"));
Assert.Equal(1, ws.Diagnostics.Count);
Assert.True(ws.Diagnostics[0].Message.StartsWith("Msbuild failed"));
Assert.Equal(0, proj.DocumentIds.Count);
}
......@@ -2945,22 +2932,28 @@ public async Task TestOpenSolution_BadTaskImport()
.WithFile(@"CSharpProject\CSharpProject.csproj", GetResourceText(@"CSharpProject_CSharpProject_BadTasks.csproj")));
var ws = MSBuildWorkspace.Create();
string message = null;
ws.WorkspaceFailed += (sender, args) =>
{
message = args.Diagnostic.Message;
};
var solution = await ws.OpenSolutionAsync(GetSolutionFileName(@"TestSolution.sln"));
Assert.NotNull(message);
Assert.True(message.StartsWith("Cannot open"));
Assert.Equal(1, ws.Diagnostics.Count);
Assert.True(ws.Diagnostics[0].Message.StartsWith("Msbuild failed"));
Assert.Equal(1, solution.ProjectIds.Count);
Assert.Equal(0, solution.Projects.First().DocumentIds.Count);
}
[Fact, Trait(Traits.Feature, Traits.Features.Workspace)]
public async Task TestOpenProject_MsbuildError()
{
CreateFiles(GetSimpleCSharpSolutionFiles()
.WithFile(@"CSharpProject\CSharpProject.csproj", GetResourceText(@"CSharpProject_CSharpProject_MsbuildError.csproj")));
var ws = MSBuildWorkspace.Create();
var proj = await ws.OpenProjectAsync(GetSolutionFileName(@"CSharpProject\CSharpProject.csproj"));
Assert.Equal(1, ws.Diagnostics.Count);
Assert.True(ws.Diagnostics[0].Message.StartsWith("Msbuild failed"));
}
[Fact, Trait(Traits.Feature, Traits.Features.Workspace)]
public void TestOpenProject_CommandLineArgsHaveNoErrors()
{
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册