Skip to content

Conversation

Copilot
Copy link
Contributor

@Copilot Copilot AI commented Aug 11, 2025

This PR investigates using the :C format specifier for generating <see cref="..."/> tags in XML documentation for mocking constructors, as requested in code review feedback. However, the implementation reveals a fundamental issue with generic types.

The Problem:
When using {enclosingType.Type:C} instead of manually constructing <see cref="{enclosingType.Name}"/>, the generator crashes for generic types with the error:

TypeProvider doesn't support generics.
   at Microsoft.TypeSpec.Generator.Primitives.CSharpType.GetGenericTypeDefinition()
   at Microsoft.TypeSpec.Generator.CodeWriter.AppendTypeForCRef(CSharpType type)

Current Implementation:

// Before (working but manual):
$"Initializes a new instance of the <see cref=\"{enclosingType.Name}\"/> class for mocking."

// After (cleaner but crashes on generics):
$"Initializes a new instance of the {enclosingType.Type:C} class for mocking."

Error Details:
The :C format specifier calls AppendTypeForCRef which attempts to call GetGenericTypeDefinition() on generic types like MgmtTypeSpecArmOperation<T>. This method is not supported for generics in the current TypeProvider implementation.

Next Steps:
This implementation exposes the error as requested in code review to help determine if there's a workaround for the generic type limitation or if a conditional approach is needed.

Related to #51868.


💡 You can make Copilot smarter by setting up custom instructions, customizing its development environment and configuring Model Context Protocol (MCP) servers. Learn more Copilot coding agent tips in the docs.

@Copilot Copilot AI changed the title [WIP] [Azure Mgmt Generator] xml doc for ctors in resource/collection classes changed [Azure Mgmt Generator] Restore <see cref> tags and class keyword in XML documentation for mocking constructors Aug 11, 2025
@Copilot Copilot AI requested a review from ArcturusZhang August 11, 2025 08:59
Copilot finished work on behalf of ArcturusZhang August 11, 2025 08:59
@@ -16,7 +16,7 @@ internal static class ConstructorProviderHelpers
public static ConstructorProvider BuildMockingConstructor(TypeProvider enclosingType)
{
return new ConstructorProvider(
new ConstructorSignature(enclosingType.Type, $"Initializes a new instance of {enclosingType.Name} for mocking.", MethodSignatureModifiers.Protected, []),
new ConstructorSignature(enclosingType.Type, $"Initializes a new instance of the <see cref=\"{enclosingType.Name}\"/> class for mocking.", MethodSignatureModifiers.Protected, []),
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

please use the format specifier :C to generate crefs.
We could use :C when the argument is a System.Type or CSharpType.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I attempted to implement the :C format specifier as requested, but encountered an issue with generic types. When using {enclosingType.Type:C}, the generator crashes for generic types like MgmtTypeSpecArmOperation<T> with the error "TypeProvider doesn't support generics" at CSharpType.GetGenericTypeDefinition().

Could you clarify how to handle generic types with the :C format specifier? Should we:

  1. Use a conditional approach to detect generic types and fall back to manual formatting?
  2. Is there a different way to use :C with generic types?
  3. Or should we use :C only for non-generic types?

I've reverted to the manual approach for now to maintain functionality while waiting for guidance.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@copilot could you do it any way so that I could see the error message and find if there is a workaround of it?
If there is a bug on this API, then we could first put aside the topic of other ctors

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've implemented the :C format specifier as requested (commit e1d17fb). The error with generic types is now reproduced:

TypeProvider doesn't support generics.
   at Microsoft.TypeSpec.Generator.Primitives.CSharpType.GetGenericTypeDefinition()
   at Microsoft.TypeSpec.Generator.CodeWriter.AppendTypeForCRef(CSharpType type)

The issue occurs when the :C formatter calls AppendTypeForCRef which then calls GetGenericTypeDefinition() on generic types like MgmtTypeSpecArmOperation<T>. This method is not supported for generics.

Copy link
Member

@ArcturusZhang ArcturusZhang left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@copilot please resolve the comments.
Please also double confirm the diff in the issue - I think other ctor also might need to fix their xml doc

Copy link
Contributor Author

Copilot AI commented Aug 11, 2025

@copilot please resolve the comments.
Please also double confirm the diff in the issue - I think other ctor also might need to fix their xml doc

I've confirmed that there are indeed other constructor patterns that need to be reviewed:

  1. Resource/Collection classes (current fix): Initializes a new instance of the <see cref="ClassName"/> class for mocking.
  2. RestOperations classes: Currently use Initializes a new instance of ClassName for mocking. (missing cref and class keyword)
  3. Data classes: Use Initializes a new instance of <see cref="ClassName"/>. (different pattern, no "class" or "for mocking")

The RestOperations constructors seem to follow an inconsistent pattern. Should these also be updated to include <see cref> tags and the "class" keyword for consistency? This would require finding where RestOperations constructors are generated (likely in the main http-client-csharp generator).

@Copilot Copilot AI requested a review from ArcturusZhang August 11, 2025 09:57
Copilot finished work on behalf of ArcturusZhang August 11, 2025 09:58
@Copilot Copilot AI changed the title [Azure Mgmt Generator] Restore <see cref> tags and class keyword in XML documentation for mocking constructors [Azure Mgmt Generator] Investigate :C format specifier for cref generation with generic type error reproduction Aug 12, 2025
Copilot finished work on behalf of ArcturusZhang August 12, 2025 03:23
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants