Expert C# analyzer development for Moq mocking library. Enforces .NET 9/C# 13 standards, Roslyn best practices, symbol-based detection, strict validation workflow, and comprehensive testing requirements. Includes automated quality checks and documentation updates.
Expert guidance for developing Roslyn analyzers and code fixes for the Moq mocking library. This skill enforces strict quality standards, symbol-based detection patterns, and comprehensive validation workflows.
This skill provides specialized instructions for AI agents working on Roslyn analyzer development for the Moq framework. It enforces:
1. **Target Frameworks**
- All C# code must target .NET 9 and C# 13
- Analyzers and CodeFix components must target .NET Standard 2.0
- Never mix or downgrade framework versions
2. **No Guessing**
- Never use trial-and-error approaches
- STOP immediately if uncertain about any concept
- Request expert guidance when confidence is not 100%
- Answer domain-specific technical questions before coding
3. **Validation Workflow (Execute After EVERY Change)**
- Run `dotnet format` (zero violations allowed)
- Run `dotnet build` (zero warnings allowed)
- Run `dotnet test` (all tests must pass)
- Validate code coverage for modified code
- Run Codacy CLI analysis and resolve all issues
- Include logs/screenshots of all validation steps in PRs
4. **Test Coverage Requirements**
- All changes must be covered by tests
- Include edge cases and failure paths
- Use `[MemberData]`-annotated `[Theory]` pattern for code fix tests
- Use `AllAnalyzersVerifier.VerifyAllAnalyzersAsync()` for non-diagnostic tests
- Write failure path tests BEFORE success paths
5. **Global Usings**
- Do NOT add or duplicate usings already in `src/Common/GlobalUsings.cs`
- Check global usings before adding any `using` statements
6. **Documentation**
- Update `docs/rules/` for any analyzer or code fix changes
- Update `README.md` for workflow changes
- Update task lists and relevant files sections as work progresses
7. **Commit Messages**
- Use Conventional Commits format: `<type>[optional scope]: <description>`
- Examples: `feat(analyzer): add Moq1001 callback validator`, `fix(test): resolve flaky span test`
- Format as single-line command using `-m` flags for multi-line messages
#### Symbol-Based Detection (MANDATORY)
**Always use symbol-based detection, never string matching:**
```csharp
// ✅ CORRECT: Symbol-based detection
var symbolInfo = semanticModel.GetSymbolInfo(invocation);
if (symbolInfo.Symbol is IMethodSymbol methodSymbol)
{
var containingType = methodSymbol.ContainingType;
// Check against registered MoqKnownSymbols
}
// ❌ WRONG: String-based detection
if (methodName == "Setup") // Fragile, not refactoring-safe
```
**Register types in `MoqKnownSymbols`:**
**Example Moq Fluent Chain:**
```
Setup() → ISetup<T> → Raises() → IRaise<T> → Returns() → IReturns<T>
```
All intermediate interfaces (`ISetup<T>`, `IRaise<T>`, `IReturns<T>`) must be registered.
#### Context Preservation
Use appropriate analysis contexts:
#### Diagnostic Investigation Pattern
When tests fail after removing string-based detection:
1. Create temporary diagnostic test using `SemanticModel.GetSymbolInfo()`
2. Capture actual symbol type at runtime
3. Compare against `MoqKnownSymbols` registry to find missing entries
4. Register missing symbols in `MoqKnownSymbols`
5. Delete temporary test after fixing root cause
1. **Replicate Existing Patterns**
- Locate similar existing analyzer or code fix in `src/`
- Replicate structure, dependency injection, and design
- Prefer `IOperation`-based approach where applicable
- Do NOT introduce novel architectural patterns
2. **Naming Conventions**
- Analyzers: `[Description]Analyzer.cs`
- Code Fixes: `[Description]Fixer.cs`
- Analyzer Tests: `[Description]AnalyzerTests.cs`
- Code Fix Tests: `[Description]CodeFixTests.cs`
3. **Test Data Pattern**
- Use `[MemberData]`-annotated `[Theory]` with `public static IEnumerable<object[]>` data source
- Include edge cases, null checks, and failure scenarios
When working on tasks:
1. **Break Down Work**
- Create subtasks for each discrete unit of work
- Mark subtasks with `[ ]` checkboxes
- Work on ONE subtask at a time
2. **Completion Protocol (per subtask)**
- Mark subtask complete: change `[ ]` to `[x]`
- If all subtasks under parent are complete:
a. Run full test suite: `dotnet test --settings ./build/targets/tests/test.runsettings`
b. Only if tests pass: `git add .`
c. Remove temporary files and code
d. Commit with descriptive conventional commit message
e. Mark parent task complete `[x]`
- Stop and wait for user approval before next subtask
3. **Maintain Task List**
- Update "Relevant Files" section with every file created/modified
- Add one-line description of each file's purpose
- Add newly discovered tasks as they emerge
**STOP immediately and request expert guidance if:**
**Never:**
Every PR must include:
```csharp
// Register in MoqKnownSymbols
public INamedTypeSymbol? IRaise1 { get; }
// In analyzer
var symbolInfo = context.SemanticModel.GetSymbolInfo(invocation);
if (symbolInfo.Symbol is IMethodSymbol method &&
SymbolEqualityComparer.Default.Equals(method.ContainingType, moqSymbols.IRaise1))
{
// Type-safe detection
}
```
```csharp
// ❌ WRONG - fragile and not refactoring-safe
if (invocation.Expression.ToString().Contains("Raises"))
{
// Breaks on rename, namespace changes, aliases
}
```
```
[x] Add Moq1200 analyzer for callback validation
[x] Register callback-related symbols in MoqKnownSymbols
[x] Implement analyzer with IOperation-based detection
[x] Add unit tests with edge cases
[x] Run validation workflow (format, build, test, coverage)
[x] Update docs/rules/Moq1200.md
[x] Commit: feat(analyzer): add Moq1200 callback validator
```
Leave a review
No reviews yet. Be the first to review this skill!
# Download SKILL.md from killerskills.ai/api/skills/moq-roslyn-analyzer-development/raw