Agent skill

Test Anti Patterns

by runceel in runceel/ReactiveProperty

Quick pragmatic detection-focused review of .NET test code for anti-patterns that undermine reliability and diagnostic value.

MITAuto-check passedTesting & QA

Install Test Anti Patterns

skills CLI
$ npx skills add runceel/ReactiveProperty --skill test-anti-patterns -a claude-code

Project install by default; add -g for ~/.claude/skills/.

GitHub CLI
$ gh skill install runceel/ReactiveProperty test-anti-patterns --agent claude-code

Project scope by default; add --scope user for a personal install. Needs GitHub CLI 2.90.0 or later (public preview).

Manual copy
$ git clone --depth 1 https://github.com/runceel/ReactiveProperty.git skills-src && mkdir -p .claude/skills && cp -r skills-src/.agents/skills/test-anti-patterns .claude/skills/test-anti-patterns && rm -rf skills-src

Use ~/.claude/skills/ instead of .claude/skills for a personal install. The folder must contain SKILL.md.

Claude Code skills documentation · loads skills from .claude/skills/

Facts

Skill name
test-anti-patterns
GitHub stars
944
Token cost
~2.8k tokens
SKILL.md length
1,263 words
Files
1
Skills in repo
12
Repo updated
First seen
Licence
MIT

At a glance

Quick pragmatic detection-focused review of .NET test code for anti-patterns that undermine reliability and diagnostic value.

  • Works in 5 steps: Gather the test code → Scan for anti-patterns → Calibrate severity honestly → …
  • Asked to audit test quality
  • SKILL.md covers When to Use, When Not to Use, Inputs and Workflow, plus 2 more sections
  • Instructions only: no scripts, shell commands, URLs or credentials in SKILL.md

What it does

Test Anti Patterns is an agent skill from runceel/ReactiveProperty. Quick pragmatic detection-focused review of .NET test code for anti-patterns that undermine reliability and diagnostic value. Use when asked to audit test quality, investigate flaky or coupled tests, find duplication or magic values, or when tests pass but don't actually verify anything. Best for identifying and prioritizing issues in existing tests with severity-ranked findings and targeted remediation guidance. Catches assertion gaps, swallowed exceptions, always-true assertions, flakiness indicators, test…

Its SKILL.md is about 2.8k tokens, which your agent loads only when the skill is triggered. It is a single SKILL.md file with no bundled scripts.

It sits in Testing & QA, covering Unit testing and Failing and flaky tests. It works with .NET. The repository describes itself as: ReactiveProperty provides MVVM and asynchronous support features under Reactive Extensions. Target frameworks are .NET 6+, .NET Framework 4.7.2 and .NET Standard 2.0. The licence is MIT.

When your agent uses it

  • Asked to audit test quality
  • Investigate flaky
  • Find duplication
  • Tests pass but dont actually verify anything

Example prompts

  • “/test-anti-patterns”

Workflow steps

5 steps, taken from the step headings in SKILL.md.

  1. Gather the test code
  2. Scan for anti-patterns
  3. Calibrate severity honestly
  4. Report findings
  5. Prioritize recommendations

What it can do on your machine

Read from SKILL.md and the folder at commit e7e6474. It shows what the files ask for, not the result of running them.

  • Tool permissions

    Pre-approves nothing: there is no allowed-tools line, so your agent's usual permission prompts apply.

    From allowed-tools in the SKILL.md frontmatter.

  • Runs code

    No scripts in the folder and no shell commands in SKILL.md.

    From the folder's file list and the shell code blocks in SKILL.md.

  • Network

    No URLs in SKILL.md.

    From URLs in SKILL.md, links to its own repository left out.

  • Credentials

    Names no API keys, tokens, secrets or passwords.

    From names ending in _API_KEY, _TOKEN, _SECRET, _KEY or _PASSWORD in SKILL.md.

Context cost

Test Anti Patterns loads about 2.8k tokens when it runs. Until then it costs about 251 tokens; SKILL.md has 1,263 words of instructions outside code blocks.

Always · name and description, kept in context so the agent knows when to use it
~251
When it runs · the whole SKILL.md, loaded when a task matches
~2.8k

Estimates: characters ÷ 4, the usual rule of thumb; real counts depend on the model's tokenizer. Scripts and assets cost tokens only if the agent reads them.

Safety

Auto-check passed

The automated check found no risky patterns in SKILL.md.

Automated static check — not a guarantee. Review scripts before installing. It scans the text of SKILL.md for risky patterns (piping downloads into a shell, reading credential files, hidden Unicode, destructive commands); files beside SKILL.md are not scanned.

SKILL.md

The full file from runceel/ReactiveProperty at commit e7e6474, republished under its MIT licence (© runceel). 1,263 words, ~2,750 tokens.

Download SKILL.mdSave it as .claude/skills/test-anti-patterns/SKILL.md (or your agent's skills folder).
name
test-anti-patterns
description
Quick pragmatic detection-focused review of .NET test code for anti-patterns that undermine reliability and diagnostic value. Use when asked to audit test quality, investigate flaky or coupled tests, find duplication or magic values, or when tests pass but don't actually verify anything. Best for identifying and prioritizing issues in existing tests with severity-ranked findings and targeted remediation guidance. Catches assertion gaps, swallowed exceptions, always-true assertions, flakiness indicators, test coupling, over-mocking, naming issues, magic values, duplicate tests, and structural problems. Do NOT use for direct MSTest API rewrites or implementation-only fixes (for example swapped Assert.AreEqual argument order or converting `DynamicData` from `IEnumerable<object[]>` to `ValueTuple`) — use writing-mstest-tests instead. For a deep formal audit based on academic test smell taxonomy, use exp-test-smell-detection instead. Works with MSTest, xUnit, NUnit, and TUnit.
metadata.github-path
plugins/dotnet-test/skills/test-anti-patterns
metadata.github-pinned
v1.0.0
metadata.github-ref
refs/tags/v1.0.0
metadata.github-repo
https://github.com/dotnet/skills
metadata.github-tree-sha
2b9ee0e14e82d7c47681cf48171e650a21ba7532

Test Anti-Pattern Detection

Quick, pragmatic analysis of .NET test code for anti-patterns and quality issues that undermine test reliability, maintainability, and diagnostic value.

When to Use

  • User asks to review test quality or find test smells
  • User wants to know why tests are flaky or unreliable
  • User asks "are my tests good?" or "what's wrong with my tests?"
  • User requests a test audit or test code review
  • User wants to improve existing test code

When Not to Use

  • User wants to write new tests from scratch (use writing-mstest-tests)
  • User wants direct implementation fixes in MSTest code rather than a diagnostic review (use writing-mstest-tests)
  • User asks to fix swapped Assert.AreEqual argument order (use writing-mstest-tests)
  • User asks to convert DynamicData from IEnumerable<object[]> to ValueTuple (use writing-mstest-tests)
  • User wants to run or execute tests (use run-tests)
  • User wants to migrate between test frameworks or versions (use migration skills)
  • User wants to measure code coverage (out of scope)
  • User wants a deep formal test smell audit with academic taxonomy and extended catalog (use exp-test-smell-detection)

Inputs

InputRequiredDescription
Test codeYesOne or more test files or classes to analyze
Production codeNoThe code under test, for context on what tests should verify
Specific concernNoA focused area like "flakiness" or "naming" to narrow the review

Workflow

Step 1: Gather the test code

Read the test files the user wants reviewed. If the user points to a directory or project, scan for all test files using the framework-specific markers in the dotnet-test-frameworks skill (e.g., [TestClass], [Fact], [Test]).

If production code is available, read it too -- this is critical for detecting tests that are coupled to implementation details rather than behavior.

Step 2: Scan for anti-patterns

Check each test file against the anti-pattern catalog below. Report findings grouped by severity.

Critical -- Tests that give false confidence
Anti-PatternWhat to Look For
No assertionsTest methods that execute code but never assert anything. A passing test without assertions proves nothing.
Swallowed exceptionstry { ... } catch { } or catch (Exception) without rethrowing or asserting. Failures are silently hidden.
Assert in catch block onlytry { Act(); } catch (Exception ex) { Assert.Fail(ex.Message); } -- use Assert.ThrowsException or equivalent instead. The test passes when no exception is thrown even if the result is wrong.
Always-true assertionsAssert.IsTrue(true), Assert.AreEqual(x, x), or conditions that can never fail.
Commented-out assertionsAssertions that were disabled but the test still runs, giving the illusion of coverage.
High -- Tests likely to cause pain
Anti-PatternWhat to Look For
Flakiness indicatorsThread.Sleep(...), Task.Delay(...) for synchronization, DateTime.Now/DateTime.UtcNow without abstraction, Random without a seed, environment-dependent paths.
Test ordering dependencyStatic mutable fields modified across tests, [TestInitialize] that doesn't fully reset state, tests that fail when run individually but pass in suite (or vice versa).
Over-mockingMore mock setup lines than actual test logic. Verifying exact call sequences on mocks rather than outcomes. Mocking types the test owns. For a deep mock audit, use exp-mock-usage-analysis.
Implementation couplingTesting private methods via reflection, asserting on internal state, verifying exact method call counts on collaborators instead of observable behavior.
Broad exception assertionsAssert.ThrowsException<Exception>(...) instead of the specific exception type. Also: [ExpectedException(typeof(Exception))].
Medium -- Maintainability and clarity issues
Anti-PatternWhat to Look For
Poor namingTest names like Test1, TestMethod, names that don't describe the scenario or expected outcome. Good: Add_NegativeNumber_ThrowsArgumentException.
Magic valuesUnexplained numbers or strings in arrange/assert: Assert.AreEqual(42, result) -- what does 42 mean?
Duplicate testsThree or more test methods with near-identical bodies that differ only in a single input value. Should be data-driven ([DataRow], [Theory], [TestCase]). For a detailed duplication analysis, use exp-test-maintainability. Note: Two tests covering distinct boundary conditions (e.g., zero vs. negative) are NOT duplicates -- separate tests for different edge cases provide clearer failure diagnostics and are a valid practice.
Giant testsTest methods exceeding ~30 lines or testing multiple behaviors at once. Hard to diagnose when they fail.
Assertion messages that repeat the assertionAssert.AreEqual(expected, actual, "Expected and actual are not equal") adds no information. Messages should describe the business meaning.
Missing AAA separationArrange, Act, Assert phases are interleaved or indistinguishable.
Low -- Style and hygiene
Anti-PatternWhat to Look For
Unused test infrastructure[TestInitialize]/[SetUp] that does nothing, test helper methods that are never called.
IDisposable not disposedTest creates HttpClient, Stream, or other disposable objects without using or cleanup.
Console.WriteLine debuggingLeftover Console.WriteLine or Debug.WriteLine statements used during test development.
Inconsistent naming conventionMix of naming styles in the same test class (e.g., some use Method_Scenario_Expected, others use ShouldDoSomething).
Show full SKILL.md (524 more words)Show less
Step 3: Calibrate severity honestly

Before reporting, re-check each finding against these severity rules:

  • Critical/High: Only for issues that cause tests to give false confidence or be unreliable. A test that always passes regardless of correctness is Critical. Flaky shared state is High.
  • Medium: Only for issues that actively harm maintainability -- 5+ nearly-identical tests, truly meaningless names like Test1.
  • Low: Cosmetic naming mismatches, minor style preferences, assertion messages that could be better. When in doubt, rate Low.
  • Not an issue: Separate tests for distinct boundary conditions (zero vs. negative vs. null). Explicit per-test setup instead of [TestInitialize] (this improves isolation). Tests that are short and clear but could theoretically be consolidated.

IMPORTANT: If the tests are well-written, say so clearly up front. Do not inflate severity to justify the review. A review that finds zero Critical/High issues and only minor Low suggestions is a valid and valuable outcome. Lead with what the tests do well.

Step 4: Report findings

Present findings in this structure:

  1. Summary -- Total issues found, broken down by severity (Critical / High / Medium / Low). If tests are well-written, lead with that assessment.
  2. Critical and High findings -- List each with:
    • The anti-pattern name
    • The specific location (file, method name, line)
    • A brief explanation of why it's a problem
    • A concrete fix (show before/after code when helpful)
  3. Medium and Low findings -- Summarize in a table unless the user wants full detail
  4. Positive observations -- Call out things the tests do well (sealed class, specific exception types, data-driven tests, clear AAA structure, proper use of fakes, good naming). Don't only report negatives.
Step 5: Prioritize recommendations

If there are many findings, recommend which to fix first:

  1. Critical -- Fix immediately, these tests may be giving false confidence
  2. High -- Fix soon, these cause flakiness or maintenance burden
  3. Medium/Low -- Fix opportunistically during related edits

Validation

  • Every finding includes a specific location (not just a general warning)
  • Every Critical/High finding includes a concrete fix
  • Report covers all categories (assertions, isolation, naming, structure)
  • Positive observations are included alongside problems
  • Recommendations are prioritized by severity

Common Pitfalls

PitfallSolution
Reporting style issues as criticalNaming and formatting are Medium/Low, never Critical
Suggesting rewrites instead of targeted fixesShow minimal diffs -- change the assertion, not the whole test
Flagging intentional design choicesIf Thread.Sleep is in an integration test testing actual timing, that's not an anti-pattern. Consider context.
Inventing false positives on clean codeIf tests follow best practices, say so. A review finding "0 Critical, 0 High, 1 Low" is perfectly valid. Don't inflate findings to justify the review.
Flagging separate boundary tests as duplicatesTwo tests for zero and negative inputs test different edge cases. Only flag as duplicates when 3+ tests have truly identical bodies differing by a single value.
Rating cosmetic issues as MediumNaming mismatches (e.g., method name says ArgumentException but asserts ArgumentOutOfRangeException) are Low, not Medium -- the test still works correctly.
Ignoring the test frameworkxUnit uses [Fact]/[Theory], NUnit uses [Test]/[TestCase], MSTest uses [TestMethod]/[DataRow] -- use correct terminology
Missing the forest for the treesIf 80% of tests have no assertions, lead with that systemic issue rather than listing every instance

© runceel, MIT. Rendered from Markdown: HTML in the file is shown as text, images as links, and headings moved down two levels. Raw file

Files

Just SKILL.md in .agents/skills/test-anti-patterns of runceel/ReactiveProperty.

Open the folder on GitHubat commit e7e6474

Compare with similar skills

Test Anti Patterns next to the 5 skills that share the most tags, products or categories with it. Stars are the repository's; “used in” counts other GitHub owners with a copy.

Test Anti Patterns compared with similar skills
SkillStarsUsed inTokensAuto-checkLicenceRepo updated
Test Anti Patterns this skillrunceel/ReactiveProperty944—~2.8kAutomated safety check: PassMIT
MAUI Helix Unit Test Runnerdotnet/maui23k—~1.4kAutomated safety check: PassMIT
Run Testsmicrosoft/testfx1k—~4.2kAutomated safety check: PassMIT
Debug Playwright Prowquay/quay2.8k—~2.2kAutomated safety check: PassApache-2.0
CI FixFastLED/FastLED7.5k—~897Automated safety check: PassMIT
Quay Prow Triagequay/quay2.8k—~2.9kAutomated safety check: PassApache-2.0

Similar skills

  • Official

    Submits .NET MAUI unit tests to Helix queues from a local machine and monitors job status and per-work-item logs with PowerShell scripts.

    23k GitHub stars~1.4k tokensUpdated today
    Testing & QAAuto-check passed
  • Run Tests

    microsoft/testfx

    Official

    For dotnet test: figures out which test platform (VSTest vs Microsoft.Testing.Platform) a project uses from Directory.Build.props, global.json, and .csproj, then picks the matching command syntax.

    1k GitHub stars~4.2k tokensUpdated today
    Testing & QAAuto-check passed
  • Deep-dive diagnosis of a Playwright test failure already isolated to one Quay Prow/OpenShift CI run: downloads its GCS artifacts (results.json, JUnit, build/pod logs, Jaeger traces), classifies real…

    2.8k GitHub stars~2.2k tokensUpdated today
    Testing & QAAuto-check passed
  • CI Fix

    FastLED/FastLED

    Scan all CI builds and tests, find failures, fetch error logs, and fix the code.

    7.5k GitHub stars~897 tokensUpdated today
    Testing & QAAuto-check passed
  • Diagnose any Quay Prow job failure end to end: prowjob.json - top-level build log - JUnit - resolved failing step - Playwright results.json when the failing step is Playwright, continuing through…

    2.8k GitHub stars~2.9k tokensUpdated today
    Testing & QAAuto-check passed
  • Official

    Investigate and triage CI failures for dotnet/macios from Azure DevOps build URLs.

    2.9k GitHub stars~2.3k tokensUpdated today
    Testing & QAAuto-check passed

More from runceel/ReactiveProperty

All 12 skills in this repo
  • Msbuild Antipatterns

    runceel/ReactiveProperty

    Catalog of MSBuild anti-patterns with detection rules and fix recipes.

    944 GitHub stars~3.7k tokensUpdated 1 mo ago
    Auto-check passed
  • Binlog Failure Analysis

    runceel/ReactiveProperty

    Analyze MSBuild binary logs to diagnose build failures by replaying binlogs to searchable text logs.

    944 GitHub stars~1.1k tokensUpdated 1 mo ago
    Auto-check passed
  • Coverage Analysis

    runceel/ReactiveProperty

    Automated, project-wide code coverage and CRAP (Change Risk Anti-Patterns) score analysis for .NET projects with existing unit tests.

    944 GitHub stars~5.9k tokensUpdated 1 mo ago
    Auto-check: warnings
  • Development Workflow

    runceel/ReactiveProperty

    ReactiveProperty repository development policy. An agent skill from runceel/ReactiveProperty.

    944 GitHub stars~1.4k tokensUpdated 1 mo ago
    Auto-check passed
  • Dotnet10 Features

    runceel/ReactiveProperty

    Reference for the .NET 10 / C 14 features that are relevant to the ReactiveProperty repository.

    944 GitHub stars~2.7k tokensUpdated 1 mo ago
    Auto-check passed
  • Migrate Vstest To Mtp

    runceel/ReactiveProperty

    Migrates .NET test projects from VSTest to Microsoft.Testing.Platform (MTP).

    944 GitHub stars~4.3k tokensUpdated 1 mo ago
    Auto-check passed

Works with

Categories

Questions about Test Anti Patterns

What does Test Anti Patterns do?

Quick pragmatic detection-focused review of .NET test code for anti-patterns that undermine reliability and diagnostic value. Test Anti Patterns is an agent skill from runceel/ReactiveProperty.NET test code for anti-patterns that undermine reliability and diagnostic value.

When should I use Test Anti Patterns?

Test Anti Patterns fits situations like: asked to audit test quality; investigate flaky; find duplication; tests pass but dont actually verify anything.

How do I install Test Anti Patterns in Claude Code?

Run `npx skills add runceel/ReactiveProperty --skill test-anti-patterns -a claude-code`. Or copy the skill folder (.agents/skills/test-anti-patterns in runceel/ReactiveProperty) into .claude/skills/test-anti-patterns in your project. Claude Code loads it when a task matches its description.

How do I install Test Anti Patterns in Codex?

Run `npx skills add runceel/ReactiveProperty --skill test-anti-patterns -a codex`. Or copy the skill folder (.agents/skills/test-anti-patterns in runceel/ReactiveProperty) into .agents/skills/test-anti-patterns in your project. Codex loads it when a task matches its description.

Can I use Test Anti Patterns in Cursor, Gemini CLI or GitHub Copilot?

Cursor, Gemini CLI, GitHub Copilot and OpenCode also load SKILL.md folders. With the skills CLI, run `npx skills add runceel/ReactiveProperty --skill test-anti-patterns -a cursor` (or -a gemini-cli, github-copilot or opencode for the others). To copy it by hand, put the folder in .cursor/skills/test-anti-patterns, .gemini/skills/test-anti-patterns, .github/skills/test-anti-patterns and .opencode/skills/test-anti-patterns in your project.

What does Test Anti Patterns need to run?

SKILL.md names no scripts, command-line tools or credentials: Test Anti Patterns is instructions for the agent only.

Does Test Anti Patterns access the network?

SKILL.md contains no URLs. Any network use would come from the scripts or tools the agent runs. This is read from the text; nothing was executed.

Is Test Anti Patterns safe to install?

Our automated static check of SKILL.md found no risky patterns, such as piping downloads into a shell, reading credential files or hidden Unicode. It is not a guarantee. Review the folder before installing.

What licence does Test Anti Patterns use?

Test Anti Patterns is published under the MIT licence (the repository's licence). It allows redistribution, so the full SKILL.md is shown on this page.

How many tokens does Test Anti Patterns use?

About 2.8k tokens (SKILL.md is roughly 11k characters). Agents keep only the skill's name and description in context until a task matches; then they load SKILL.md in full.

What are the alternatives to Test Anti Patterns?

Skills that share tags, products or a category with Test Anti Patterns: MAUI Helix Unit Test Runner (dotnet/maui, 23k stars), Run Tests (microsoft/testfx, 1k stars), Debug Playwright Prow (quay/quay, 2.8k stars) and CI Fix (FastLED/FastLED, 7.5k stars). The comparison table on this page puts their stars, adoption, token cost, safety result and licence side by side.

Who maintains Test Anti Patterns?

runceel (a GitHub user) maintains it in runceel/ReactiveProperty, which has 944 GitHub stars. The repository holds 12 skills in this directory. The repository was last updated on August 31, 2026.

Source: runceel/ReactiveProperty on GitHub. Facts on this page come from the repository at the commit we read; the author's words are quoted as theirs.