提交 887cfef4 编写于 作者: C CyrusNajmabadi

Make the assembly code action into pure data.

上级 a58003f7
// 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.Collections.Immutable;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.CodeAnalysis.CodeActions;
using Microsoft.CodeAnalysis.Host;
using Microsoft.CodeAnalysis.Tags;
using Microsoft.CodeAnalysis.Text;
using Roslyn.Utilities;
namespace Microsoft.CodeAnalysis.CodeFixes.AddImport
{
internal abstract partial class AbstractAddImportCodeFixProvider<TSimpleNameSyntax>
{
private partial class AssemblyReference
{
private class AssemblyReferenceCodeAction : CodeAction
{
private readonly AssemblyReference _reference;
private readonly string _title;
private readonly Document _document;
private readonly ImmutableArray<TextChange> _textChanges;
public override string Title => _title;
public override ImmutableArray<string> Tags => WellKnownTagArrays.AddReference;
private readonly Lazy<string> _lazyResolvedPath;
public AssemblyReferenceCodeAction(
AssemblyReference reference,
Document document,
ImmutableArray<TextChange> textChanges)
{
_reference = reference;
_document = document;
_textChanges = textChanges;
_title = $"{reference.provider.GetDescription(reference.SearchResult.NameParts)} ({string.Format(FeaturesResources.from_0, reference._referenceAssemblyWithType.AssemblyName)})";
_lazyResolvedPath = new Lazy<string>(ResolvePath);
}
// Adding a reference is always low priority.
internal override CodeActionPriority Priority => CodeActionPriority.Low;
private string ResolvePath()
{
var assemblyResolverService = _document.Project.Solution.Workspace.Services.GetService<IFrameworkAssemblyPathResolver>();
var packageWithType = _reference._referenceAssemblyWithType;
var fullyQualifiedName = string.Join(".", packageWithType.ContainingNamespaceNames.Concat(packageWithType.TypeName));
var assemblyPath = assemblyResolverService?.ResolveAssemblyPath(
_document.Project.Id, packageWithType.AssemblyName, fullyQualifiedName);
return assemblyPath;
}
internal override bool PerformFinalApplicabilityCheck => true;
internal override bool IsApplicable(Workspace workspace)
{
return !string.IsNullOrWhiteSpace(_lazyResolvedPath.Value);
}
protected override async Task<IEnumerable<CodeActionOperation>> ComputeOperationsAsync(CancellationToken cancellationToken)
{
var service = _document.Project.Solution.Workspace.Services.GetService<IMetadataService>();
var resolvedPath = _lazyResolvedPath.Value;
var reference = service.GetReference(resolvedPath, MetadataReferenceProperties.Assembly);
var oldText = await _document.GetTextAsync(cancellationToken).ConfigureAwait(false);
var newText = oldText.WithChanges(_textChanges);
var newDocument = _document.WithText(newText);
// Now add the actual assembly reference.
var newProject = newDocument.Project;
newProject = newProject.WithMetadataReferences(
newProject.MetadataReferences.Concat(reference));
var operation = new ApplyChangesOperation(newProject.Solution);
return SpecializedCollections.SingletonEnumerable<CodeActionOperation>(operation);
}
}
}
}
}
\ No newline at end of file
// 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.Collections.Immutable;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.CodeAnalysis.CodeActions;
using Microsoft.CodeAnalysis.Host;
using Microsoft.CodeAnalysis.SymbolSearch;
using Microsoft.CodeAnalysis.Tags;
using Microsoft.CodeAnalysis.Text;
using Roslyn.Utilities;
namespace Microsoft.CodeAnalysis.CodeFixes.AddImport
{
internal abstract partial class AbstractAddImportCodeFixProvider<TSimpleNameSyntax>
{
private class AssemblyReferenceCodeAction : CodeAction
{
private readonly ReferenceAssemblyWithTypeResult _referenceAssemblyWithType;
private readonly string _title;
private readonly Document _document;
private readonly ImmutableArray<TextChange> _textChanges;
public override string Title => _title;
public override ImmutableArray<string> Tags => WellKnownTagArrays.AddReference;
private readonly Lazy<string> _lazyResolvedPath;
public AssemblyReferenceCodeAction(
string title,
ReferenceAssemblyWithTypeResult referenceAssemblyWithType,
Document document,
ImmutableArray<TextChange> textChanges)
{
_referenceAssemblyWithType = referenceAssemblyWithType;
_document = document;
_textChanges = textChanges;
_title = title;
_lazyResolvedPath = new Lazy<string>(ResolvePath);
}
// Adding a reference is always low priority.
internal override CodeActionPriority Priority => CodeActionPriority.Low;
private string ResolvePath()
{
var assemblyResolverService = _document.Project.Solution.Workspace.Services.GetService<IFrameworkAssemblyPathResolver>();
var fullyQualifiedName = string.Join(
".", _referenceAssemblyWithType.ContainingNamespaceNames.Concat(_referenceAssemblyWithType.TypeName));
var assemblyPath = assemblyResolverService?.ResolveAssemblyPath(
_document.Project.Id, _referenceAssemblyWithType.AssemblyName, fullyQualifiedName);
return assemblyPath;
}
internal override bool PerformFinalApplicabilityCheck
=> true;
internal override bool IsApplicable(Workspace workspace)
=> !string.IsNullOrWhiteSpace(_lazyResolvedPath.Value);
protected override async Task<IEnumerable<CodeActionOperation>> ComputeOperationsAsync(CancellationToken cancellationToken)
{
var service = _document.Project.Solution.Workspace.Services.GetService<IMetadataService>();
var resolvedPath = _lazyResolvedPath.Value;
var reference = service.GetReference(resolvedPath, MetadataReferenceProperties.Assembly);
var oldText = await _document.GetTextAsync(cancellationToken).ConfigureAwait(false);
var newText = oldText.WithChanges(_textChanges);
var newDocument = _document.WithText(newText);
// Now add the actual assembly reference.
var newProject = newDocument.Project;
newProject = newProject.WithMetadataReferences(
newProject.MetadataReferences.Concat(reference));
var operation = new ApplyChangesOperation(newProject.Solution);
return SpecializedCollections.SingletonEnumerable<CodeActionOperation>(operation);
}
}
}
}
\ No newline at end of file
......@@ -29,7 +29,9 @@ private partial class AssemblyReference : Reference
var textChanges = await GetTextChangesAsync(
document, node, placeSystemNamespaceFirst, cancellationToken).ConfigureAwait(false);
return new AssemblyReferenceCodeAction(this, document, textChanges);
var title = $"{this.provider.GetDescription(this.SearchResult.NameParts)} ({string.Format(FeaturesResources.from_0, _referenceAssemblyWithType.AssemblyName)})";
return new AssemblyReferenceCodeAction(title, _referenceAssemblyWithType, document, textChanges);
}
public override bool Equals(object obj)
......
......@@ -99,7 +99,7 @@
<Compile Include="..\..\..\Compilers\Shared\DesktopShim.cs">
<Link>Shared\Utilities\DesktopShim.cs</Link>
</Compile>
<Compile Include="AddImport\CodeActions\AssemblyReference.AssemblyReferenceCodeAction.cs" />
<Compile Include="AddImport\CodeActions\AssemblyReferenceCodeAction.cs" />
<Compile Include="AddImport\SearchScopes\AllSymbolsProjectSearchScope.cs" />
<Compile Include="AddImport\SearchScopes\MetadataSymbolsSearchScope.cs" />
<Compile Include="AddImport\SearchScopes\ProjectSearchScope.cs" />
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册