Repository: dotnet/roslyn
File: src/Compilers/CSharp/Test/Symbol/Symbols/GenericConstraintTests.cs (C#)

Code before:

interface ISetup<T> where T : new() { T Data { get; set; } }
interface Base { public abstract class Nest { } }
interface Base<N> : Base, ISetup<N> where N : Base<N>.Nest { }
""";

            var comp = CreateCompilation(src);
            comp.VerifyDiagnostics(
                // (5,11): error CS0310: 'N' must be a non-abstract type with a public parameterless constructor in order to use it as parameter 'T' in the generic type or method 'ISetup<T>'
                // interface Base<N> : Base, ISetup<N> where N : Base<N>.Nest { }
                Diagnostic(ErrorCode.ERR_NewConstraintNotSatisfied, "Base").WithArguments("ISetup<T>", "T", "N").WithLocation(5, 11)
                );

            var tree = comp.SyntaxTrees.Single();
            var model = comp.GetSemanticModel(tree);
            var nest = tree.GetRoot().DescendantNodes().OfType<IdentifierNameSyntax>().Where(i => i.Identifier.ValueText == "Nest").Single();
            Assert.Null(model.GetAliasInfo(nest));
            Assert.Equal("Base.Nest", model.GetTypeInfo(nest).Type.ToDisplayString());
        }

        [Fact, WorkItem("https://github.com/dotnet/roslyn/issues/78605")]
        public void TypeParameter_BaseType_ReturnsNull()
        {
            // This test verifies that ITypeSymbol.BaseType returns null for type parameters,
            // not the effective base class.
            var source = @"
abstract class Base
{
    public abstract void Method();
}

class Derived<T> where T : Base
{
}";
            var comp = CreateCompilation(source);
            comp.VerifyDiagnostics();

            var derivedType = comp.GetTypeByMetadataName("Derived`1");
            Assert.NotNull(derivedType);

            var typeParameter = derivedType.TypeParameters[0];
            Assert.NotNull(typeParameter);

            // Test the public API: ITypeSymbol.BaseType should return null for type parameters,
            // even though there is an effective base class (Base in this case).
            var publicTypeParameter = (ITypeParameterSymbol)typeParameter.GetPublicSymbol();
            Assert.Null(publicTypeParameter.BaseType);
        }
    }
}


Review comment (suggestion):
@copilot  use a raw string literal here.  Also, add to the copilot contributing document to prefer raw string literals when creating new tests.

Also, remove the comments here.  They're redundant.  #Closed

Code after:

interface ISetup<T> where T : new() { T Data { get; set; } }
interface Base { public abstract class Nest { } }
interface Base<N> : Base, ISetup<N> where N : Base<N>.Nest { }
""";

            var comp = CreateCompilation(src);
            comp.VerifyDiagnostics(
                // (5,11): error CS0310: 'N' must be a non-abstract type with a public parameterless constructor in order to use it as parameter 'T' in the generic type or method 'ISetup<T>'
                // interface Base<N> : Base, ISetup<N> where N : Base<N>.Nest { }
                Diagnostic(ErrorCode.ERR_NewConstraintNotSatisfied, "Base").WithArguments("ISetup<T>", "T", "N").WithLocation(5, 11)
                );

            var tree = comp.SyntaxTrees.Single();
            var model = comp.GetSemanticModel(tree);
            var nest = tree.GetRoot().DescendantNodes().OfType<IdentifierNameSyntax>().Where(i => i.Identifier.ValueText == "Nest").Single();
            Assert.Null(model.GetAliasInfo(nest));
            Assert.Equal("Base.Nest", model.GetTypeInfo(nest).Type.ToDisplayString());
        }

        [Fact, WorkItem("https://github.com/dotnet/roslyn/issues/41733")]
        public void TypeParameter_BaseType_ReturnsNull()
        {
            var source = """
                abstract class Base
                {
                    public abstract void Method();
                }

                class Derived<T> where T : Base
                {
                }
                """;
            var comp = CreateCompilation(source);
            comp.VerifyDiagnostics();

            var typeParameter = (ITypeParameterSymbol)comp.GetTypeByMetadataName("Derived`1").TypeParameters[0].GetPublicSymbol();
            Assert.Null(typeParameter.BaseType);
        }

        [Fact, WorkItem("https://github.com/dotnet/roslyn/issues/41733")]
        public void MethodTypeParameter_BaseType_ReturnsNull()
        {
            var source = """
                class C
                {
                    void M<T>() where T : class
                    {
                    }
                }
                """;