-
Notifications
You must be signed in to change notification settings - Fork 730
Expand file tree
/
Copy pathMCPEXP001Suppressor.cs
More file actions
51 lines (46 loc) · 2.21 KB
/
Copy pathMCPEXP001Suppressor.cs
File metadata and controls
51 lines (46 loc) · 2.21 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.Diagnostics;
using System.Collections.Immutable;
namespace ModelContextProtocol.Analyzers;
/// <summary>
/// Suppresses MCPEXP001 diagnostics in source-generated code.
/// </summary>
/// <remarks>
/// <para>
/// The MCP SDK uses <c>object?</c> backing fields with <c>[JsonConverter(typeof(ExperimentalJsonConverter<T>))]</c>
/// to handle serialization of experimental types. When consumers define their own <c>JsonSerializerContext</c>,
/// the System.Text.Json source generator emits code referencing these converters with experimental type arguments,
/// which triggers MCPEXP001 diagnostics in the generated code.
/// </para>
/// <para>
/// This suppressor suppresses MCPEXP001 only in source-generated files (identified by <c>.g.cs</c> file extension),
/// so that hand-written user code that directly references experimental types still produces the diagnostic.
/// </para>
/// </remarks>
[DiagnosticAnalyzer(LanguageNames.CSharp)]
public sealed class MCPEXP001Suppressor : DiagnosticSuppressor
{
private static readonly SuppressionDescriptor SuppressInGeneratedCode = new(
id: "MCP_MCPEXP001_GENERATED",
suppressedDiagnosticId: "MCPEXP001",
justification: "MCPEXP001 is suppressed in source-generated code because the experimental type reference originates from the MCP SDK's backing field infrastructure, not from user code.");
/// <inheritdoc/>
public override ImmutableArray<SuppressionDescriptor> SupportedSuppressions =>
ImmutableArray.Create(SuppressInGeneratedCode);
/// <inheritdoc/>
public override void ReportSuppressions(SuppressionAnalysisContext context)
{
foreach (Diagnostic diagnostic in context.ReportedDiagnostics)
{
if (diagnostic.Id == "MCPEXP001" && IsInGeneratedCode(diagnostic))
{
context.ReportSuppression(Suppression.Create(SuppressInGeneratedCode, diagnostic));
}
}
}
private static bool IsInGeneratedCode(Diagnostic diagnostic)
{
string? filePath = diagnostic.Location.SourceTree?.FilePath;
return filePath is not null && filePath.EndsWith(".g.cs", StringComparison.OrdinalIgnoreCase);
}
}