|
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information.
#nullable disable
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Microsoft.CodeAnalysis.CSharp;
using Microsoft.CodeAnalysis.CSharp.SignatureHelp;
using Microsoft.CodeAnalysis.Editor.UnitTests.SignatureHelp;
using Microsoft.CodeAnalysis.Test.Utilities;
using Roslyn.Test.Utilities;
using Xunit;
namespace Microsoft.CodeAnalysis.Editor.CSharp.UnitTests.SignatureHelp;
[Trait(Traits.Feature, Traits.Features.SignatureHelp)]
public class GenericNamePartiallyWrittenSignatureHelpProviderTests : AbstractCSharpSignatureHelpProviderTests
{
internal override Type GetSignatureHelpProviderType()
=> typeof(GenericNamePartiallyWrittenSignatureHelpProvider);
[Fact]
public async Task NestedGenericUnterminated()
{
var markup = """
class G<T> { };
class C
{
void Goo()
{
G<G<int>$$
}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("G<T>", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestAsync(markup, expectedOrderedItems);
}
[Fact]
public async Task NestedGenericUnterminatedWithAmbiguousShift()
{
var markup = """
class G<T> { };
class C
{
void Goo()
{
var x = G<G<G<int>>$$>
x = x;
}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("G<T>", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestAsync(markup, expectedOrderedItems);
}
[Fact]
public async Task NestedGenericUnterminatedWithAmbiguousUnsignedShift()
{
var markup = """
class G<T> { };
class C
{
void Goo()
{
var x = G<G<G<G<int>>>$$>
x = x;
}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("G<T>", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestAsync(markup, expectedOrderedItems);
}
[Fact, WorkItem("http://vstfdevdiv:8080/DevDiv2/DevDiv/_workitems/edit/544088")]
public async Task DeclaringGenericTypeWith1ParameterUnterminated()
{
var markup = """
class G<T> { };
class C
{
void Goo()
{
[|G<$$
|]}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("G<T>", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestAsync(markup, expectedOrderedItems);
}
[Fact]
public async Task CallingGenericAsyncMethod()
{
var markup = """
using System.Threading.Tasks;
class Program
{
void Main(string[] args)
{
Goo<$$
}
Task<int> Goo<T>()
{
return Goo<T>();
}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem($"({CSharpFeaturesResources.awaitable}) Task<int> Program.Goo<T>()", methodDocumentation: string.Empty, string.Empty, currentParameterIndex: 0)
};
// TODO: Enable the script case when we have support for extension methods in scripts
await TestAsync(markup, expectedOrderedItems, usePreviousCharAsTrigger: false, sourceCodeKind: Microsoft.CodeAnalysis.SourceCodeKind.Regular);
}
[Fact, WorkItem(7336, "DevDiv_Projects/Roslyn")]
public async Task EditorBrowsable_GenericMethod_BrowsableAlways()
{
var markup = """
class Program
{
void M()
{
new C().Goo<$$
}
}
""";
var referencedCode = """
public class C
{
[System.ComponentModel.EditorBrowsable(System.ComponentModel.EditorBrowsableState.Always)]
public void Goo<T>(T x)
{ }
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("void C.Goo<T>(T x)", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestSignatureHelpInEditorBrowsableContextsAsync(markup: markup,
referencedCode: referencedCode,
expectedOrderedItemsMetadataReference: expectedOrderedItems,
expectedOrderedItemsSameSolution: expectedOrderedItems,
sourceLanguage: LanguageNames.CSharp,
referencedLanguage: LanguageNames.CSharp);
}
[Fact, WorkItem(7336, "DevDiv_Projects/Roslyn")]
public async Task EditorBrowsable_GenericMethod_BrowsableNever()
{
var markup = """
class Program
{
void M()
{
new C().Goo<$$
}
}
""";
var referencedCode = """
public class C
{
[System.ComponentModel.EditorBrowsable(System.ComponentModel.EditorBrowsableState.Never)]
public void Goo<T>(T x)
{ }
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("void C.Goo<T>(T x)", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestSignatureHelpInEditorBrowsableContextsAsync(markup: markup,
referencedCode: referencedCode,
expectedOrderedItemsMetadataReference: new List<SignatureHelpTestItem>(),
expectedOrderedItemsSameSolution: expectedOrderedItems,
sourceLanguage: LanguageNames.CSharp,
referencedLanguage: LanguageNames.CSharp);
}
[Fact, WorkItem(7336, "DevDiv_Projects/Roslyn")]
public async Task EditorBrowsable_GenericMethod_BrowsableAdvanced()
{
var markup = """
class Program
{
void M()
{
new C().Goo<$$
}
}
""";
var referencedCode = """
public class C
{
[System.ComponentModel.EditorBrowsable(System.ComponentModel.EditorBrowsableState.Advanced)]
public void Goo<T>(T x)
{ }
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("void C.Goo<T>(T x)", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestSignatureHelpInEditorBrowsableContextsAsync(markup: markup,
referencedCode: referencedCode,
expectedOrderedItemsMetadataReference: expectedOrderedItems,
expectedOrderedItemsSameSolution: expectedOrderedItems,
sourceLanguage: LanguageNames.CSharp,
referencedLanguage: LanguageNames.CSharp,
hideAdvancedMembers: false);
await TestSignatureHelpInEditorBrowsableContextsAsync(markup: markup,
referencedCode: referencedCode,
expectedOrderedItemsMetadataReference: new List<SignatureHelpTestItem>(),
expectedOrderedItemsSameSolution: expectedOrderedItems,
sourceLanguage: LanguageNames.CSharp,
referencedLanguage: LanguageNames.CSharp,
hideAdvancedMembers: true);
}
[Fact, WorkItem(7336, "DevDiv_Projects/Roslyn")]
public async Task EditorBrowsable_GenericMethod_BrowsableMixed()
{
var markup = """
class Program
{
void M()
{
new C().Goo<$$
}
}
""";
var referencedCode = """
public class C
{
[System.ComponentModel.EditorBrowsable(System.ComponentModel.EditorBrowsableState.Always)]
public void Goo<T>(T x)
{ }
[System.ComponentModel.EditorBrowsable(System.ComponentModel.EditorBrowsableState.Never)]
public void Goo<T, U>(T x, U y)
{ }
}
""";
var expectedOrderedItemsMetadataReference = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("void C.Goo<T>(T x)", string.Empty, string.Empty, currentParameterIndex: 0)
};
var expectedOrderedItemsSameSolution = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("void C.Goo<T>(T x)", string.Empty, string.Empty, currentParameterIndex: 0),
new SignatureHelpTestItem("void C.Goo<T, U>(T x, U y)", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestSignatureHelpInEditorBrowsableContextsAsync(markup: markup,
referencedCode: referencedCode,
expectedOrderedItemsMetadataReference: expectedOrderedItemsMetadataReference,
expectedOrderedItemsSameSolution: expectedOrderedItemsSameSolution,
sourceLanguage: LanguageNames.CSharp,
referencedLanguage: LanguageNames.CSharp);
}
[Fact]
public async Task GenericExtensionMethod()
{
var markup = """
interface IGoo
{
void Bar<T>();
}
static class GooExtensions
{
public static void Bar<T1, T2>(this IGoo goo) { }
}
class Program
{
static void Main()
{
IGoo f = null;
f.[|Bar<$$
|]}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("void IGoo.Bar<T>()", currentParameterIndex: 0),
new SignatureHelpTestItem($"({CSharpFeaturesResources.extension}) void IGoo.Bar<T1, T2>()", currentParameterIndex: 0),
};
// Extension methods are supported in Interactive/Script (yet).
await TestAsync(markup, expectedOrderedItems, sourceCodeKind: SourceCodeKind.Regular);
}
[Fact, WorkItem("http://vstfdevdiv:8080/DevDiv2/DevDiv/_workitems/edit/544088")]
public async Task InvokingGenericMethodWith1ParameterUnterminated()
{
var markup = """
class C
{
/// <summary>
/// Method Goo
/// </summary>
/// <typeparam name="T">Method type parameter</typeparam>
void Goo<T>() { }
void Bar()
{
[|Goo<$$
|]}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("void C.Goo<T>()",
"Method Goo", "Method type parameter", currentParameterIndex: 0)
};
await TestAsync(markup, expectedOrderedItems);
}
[Fact]
public async Task TestInvocationOnTriggerBracket()
{
var markup = """
class G<S, T> { };
class C
{
void Goo()
{
[|G<$$
|]}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("G<S, T>", string.Empty, string.Empty, currentParameterIndex: 0)
};
await TestAsync(markup, expectedOrderedItems, usePreviousCharAsTrigger: true);
}
[Fact]
public async Task TestInvocationOnTriggerComma()
{
var markup = """
class G<S, T> { };
class C
{
void Goo()
{
[|G<int,$$
|]}
}
""";
var expectedOrderedItems = new List<SignatureHelpTestItem>
{
new SignatureHelpTestItem("G<S, T>", string.Empty, string.Empty, currentParameterIndex: 1)
};
await TestAsync(markup, expectedOrderedItems, usePreviousCharAsTrigger: true);
}
[Fact, WorkItem("http://vstfdevdiv:8080/DevDiv2/DevDiv/_workitems/edit/1067933")]
public async Task InvokedWithNoToken()
{
var markup = """
// goo<$$
""";
await TestAsync(markup);
}
}
|