用 Codex 或 Claude 帮你安装 复制这段 Prompt,粘贴到 Codex、Claude 或其他助手里,让它检查 Skill 页面并帮你完成安装。
直接命令不会经过审查 Prompt;运行前请先检查来源。
npx skills add https://github.com/rudironsoni/Ghost --skill dotnet-roslyn-analyzers命令会保持在同一行。复制前请横向滚动并检查完整内容。
想先保存到本地?可下载 SkillsMP 当前能够提供的文件。
Rulesync CLI tool documentation - unified AI rule file management for various AI coding tools
Publishes .NET artifacts from Azure DevOps. NuGet push, containers to ACR, pipeline artifacts.
Configures artifacts output layout. UseArtifactsOutput, ArtifactsPath, impact on CI and Docker.
基于 SOC 职业分类
正在显示 SKILL.md
| name | dotnet-roslyn-analyzers |
| description | Authors Roslyn analyzers. DiagnosticAnalyzer, CodeFixProvider, CodeRefactoring, multi-version. |
| allowed-tools | ["Read","Grep","Glob","Bash","Write","Edit"] |
Guidance for authoring custom Roslyn analyzers, code fix providers, code refactoring providers, and diagnostic suppressors. Covers project setup, DiagnosticDescriptor conventions, analysis context registration, code fix actions, code refactoring actions, multi-Roslyn-version targeting (3.8 through 4.14), testing with Microsoft.CodeAnalysis.Testing, NuGet packaging, and performance best practices.
For extended code examples (CodeRefactoringProvider implementation, multi-version project structure, test matrix configuration), see details.md in this skill directory.
Cross-references: [skill:dotnet-csharp-source-generators] for shared Roslyn packaging concepts and IIncrementalGenerator patterns, [skill:dotnet-add-analyzers] for consuming and configuring analyzers, [skill:dotnet-testing-strategy] for general test organization and framework selection, [skill:dotnet-csharp-coding-standards] for naming conventions applied to analyzer code.
Analyzer projects must target netstandard2.0. The compiler loads analyzers into various host processes (Visual Studio on .NET Framework/Mono, MSBuild on .NET Core, dotnet build CLI) -- targeting net8.0+ breaks compatibility with hosts that do not run on that runtime.
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<EnforceExtendedAnalyzerRules>true</EnforceExtendedAnalyzerRules>
<IsRoslynComponent>true</IsRoslynComponent>
<LangVersion>latest</LangVersion>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="4.12.0" PrivateAssets="all" />
<PackageReference Include="Microsoft.CodeAnalysis.Analyzers" Version="3.11.0" PrivateAssets="all" />
</ItemGroup>
</Project>
EnforceExtendedAnalyzerRules enables RS-series meta-diagnostics that catch common analyzer authoring mistakes.IsRoslynComponent enables IDE tooling support for the project.LangVersion>latest lets you write modern C# in the analyzer itself while still targeting netstandard2.0.PrivateAssets="all" to avoid shipping them as transitive dependencies.Every analyzer inherits from DiagnosticAnalyzer and must be decorated with [DiagnosticAnalyzer(LanguageNames.CSharp)].
[DiagnosticAnalyzer(LanguageNames.CSharp)]
public sealed class NoPublicFieldsAnalyzer : DiagnosticAnalyzer
{
public const string DiagnosticId = "MYLIB001";
private static readonly DiagnosticDescriptor Rule = new(
id: DiagnosticId,
title: "Public fields should be properties",
messageFormat: "Field '{0}' is public; use a property instead",
category: "Design",
defaultSeverity: DiagnosticSeverity.Warning,
isEnabledByDefault: true,
helpLinkUri: $"https://example.com/docs/rules/{DiagnosticId}");
public override ImmutableArray<DiagnosticDescriptor> SupportedDiagnostics { get; }
= ImmutableArray.Create(Rule);
public override void Initialize(AnalysisContext context)
{
context.EnableConcurrentExecution();
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.RegisterSymbolAction(AnalyzeField, SymbolKind.Field);
}
private static void AnalyzeField(SymbolAnalysisContext context)
{
var field = (IFieldSymbol)context.Symbol;
if (field.DeclaredAccessibility == Accessibility.Public
&& !field.IsConst && !field.IsReadOnly)
{
context.ReportDiagnostic(Diagnostic.Create(Rule, field.Locations[0], field.Name));
}
}
}
| Method | Granularity | Use When |
|---|---|---|
RegisterSyntaxNodeAction | Individual syntax nodes | Pattern matching on specific syntax |
RegisterSymbolAction | Declared symbols | Checking symbol-level properties |
RegisterOperationAction | IL-level operations | Analyzing semantic operations |
RegisterSyntaxTreeAction | Entire syntax tree | File-level checks |
RegisterCompilationStartAction | Compilation start | Accumulate state across compilation |
RegisterCompilationAction | Full compilation | One-shot analysis after all files |
| Pattern | Example | When |
|---|---|---|
PROJ### | MYLIB001 | Single-project analyzers |
AREA#### | PERF0001 | Category-scoped analyzers |
XX#### | MA0042 | Short-prefix convention |
Avoid prefixes reserved by the .NET platform: CA, CS, RS, IDE, IL, SYSLIB.
| Severity | Use When |
|---|---|
Error | Code will not work correctly at runtime |
Warning | Code works but violates best practices |
Info | Suggestion for improvement |
Hidden | IDE-only refactoring suggestion |
Default to Warning for most rules. Always provide a non-null helpLinkUri (RS1015 enforces this).
Code fix providers offer automated corrections for diagnostics. Key patterns:
CodeAction must have a unique equivalenceKey for FixAll support (RS1010, RS1011)createChangedDocument for single-file fixes, createChangedSolution for cross-file renamesWellKnownFixAllProviders.BatchFixer for batch-applicable fixesSee details.md for the complete CodeFixProvider implementation with property conversion.
Conditionally suppresses diagnostics from other analyzers when EditorConfig cannot express the suppression condition. Requires Roslyn 3.8+.
| Approach | Use When |
|---|---|
| EditorConfig severity override | Suppression applies unconditionally |
[SuppressMessage] attribute | Suppression applies to a specific location |
DiagnosticSuppressor | Suppression depends on code structure or patterns |
| Roslyn Version | Ships With | Key APIs Added |
|---|---|---|
| 3.8 | VS 16.8 / .NET 5 SDK | DiagnosticSuppressor |
| 4.2 | VS 17.2 / .NET 6 SDK | Improved incremental analysis |
| 4.4 | VS 17.4 / .NET 7 SDK | ForAttributeWithMetadataName |
| 4.8 | VS 17.8 / .NET 8 U1 | CollectionExpression support |
| 4.14 | VS 17.14 / .NET 10 SDK | Latest API surface |
Use conditional compilation constants (ROSLYN_X_Y_OR_GREATER) and version-specific NuGet paths (analyzers/dotnet/roslyn{version}/cs/). See details.md for the complete multi-version project structure.
Use Microsoft.CodeAnalysis.Testing for ergonomic analyzer testing:
using Verify = Microsoft.CodeAnalysis.CSharp.Testing.CSharpAnalyzerVerifier<
NoPublicFieldsAnalyzer,
Microsoft.CodeAnalysis.Testing.DefaultVerifier>;
public class NoPublicFieldsAnalyzerTests
{
[Fact]
public async Task PublicField_ReportsDiagnostic()
{
var test = """
public class MyClass
{
public int {|MYLIB001:Value|};
}
""";
await Verify.VerifyAnalyzerAsync(test);
}
}
| Markup | Meaning |
|---|---|
| `[ | text |
| `{ | DIAG_ID:text |
Analyzers ship as NuGet packages with assemblies in analyzers/dotnet/cs/, not lib/.
<PropertyGroup>
<IncludeBuildOutput>false</IncludeBuildOutput>
<DevelopmentDependency>true</DevelopmentDependency>
<SuppressDependenciesWhenPacking>true</SuppressDependenciesWhenPacking>
</PropertyGroup>
<ItemGroup>
<None Include="$(OutputPath)\$(AssemblyName).dll"
Pack="true"
PackagePath="analyzers/dotnet/cs" />
</ItemGroup>
RegisterCompilationStartAction, not per-node/symbol callbacksSupportedDiagnostics as ImmutableArray field, not expression-bodied propertycontext.EnableConcurrentExecution()SyntaxKind possibleCompilation.GetSemanticModel() -- use the SemanticModel from the analysis context (RS1030)| ID | Title | What It Catches |
|---|---|---|
| RS1001 | Missing DiagnosticAnalyzerAttribute | Analyzer class missing attribute |
| RS1008 | Avoid storing per-compilation data | Instance fields with compilation data |
| RS1010 | Create code actions with unique EquivalenceKey | Missing equivalence key |
| RS1015 | Provide non-null helpLinkUri | Empty help link |
| RS1016 | Code fix providers should provide FixAll support | Missing GetFixAllProvider() |
| RS1024 | Symbols should be compared for equality | Using == instead of SymbolEqualityComparer |
| RS1026 | Enable concurrent execution | Missing EnableConcurrentExecution() |
| RS1030 | Do not invoke Compilation.GetSemanticModel() | Using wrong semantic model source |
| RS1041 | Compiler extensions should target netstandard2.0 | Wrong target framework |