Comprehensive collection of 28 ESLint rules that enforce Testing Library best practices across async patterns, query selection, DOM access, testing patterns, user interactions, assertions, and naming conventions.
All rules follow the standard ESLint rule module format with Testing Library-specific enhancements.
interface RuleModule {
meta: {
type: 'problem' | 'suggestion' | 'layout';
docs: {
description: string;
category: string;
recommended: boolean;
url: string;
};
fixable?: 'code' | 'whitespace';
schema: JSONSchema4 | JSONSchema4[];
messages: Record<string, string>;
};
create: (context: RuleContext) => RuleListener;
}Rules that enforce proper async/await patterns with Testing Library queries and utilities.
// Enforce awaiting async events
'testing-library/await-async-events': RuleModule;Ensures async events are properly awaited to prevent race conditions.
// Enforce awaiting async queries (findBy*, findAllBy*)
'testing-library/await-async-queries': RuleModule;Ensures findBy* and findAllBy* queries are awaited since they return promises.
// Enforce awaiting async utilities (waitFor, waitForElementToBeRemoved)
'testing-library/await-async-utils': RuleModule;Ensures async utilities like waitFor and waitForElementToBeRemoved are properly awaited.
// Disallow awaiting sync events
'testing-library/no-await-sync-events': RuleModule;Prevents unnecessary await on synchronous events like fireEvent calls.
// Disallow awaiting sync queries (getBy*, getAllBy*, queryBy*, queryAllBy*)
'testing-library/no-await-sync-queries': RuleModule;Prevents unnecessary await on synchronous queries that return elements immediately.
Rules that guide proper query method selection and usage patterns.
// Prefer findBy* queries over waitFor + getBy*
'testing-library/prefer-find-by': RuleModule;Encourages using findBy* queries instead of waitFor(() => getBy*()) patterns.
// Prefer queryBy* for asserting elements are not present
'testing-library/prefer-query-by-disappearance': RuleModule;Suggests using queryBy* queries when asserting elements are not in the document.
// Prefer Testing Library query matchers over manual querySelector
'testing-library/prefer-query-matchers': RuleModule;Encourages Testing Library queries over direct DOM querying methods.
// Prefer screen.getBy* over destructured queries
'testing-library/prefer-screen-queries': RuleModule;Promotes using screen queries instead of destructuring from render result.
// Prefer presence queries for existence checks
'testing-library/prefer-presence-queries': RuleModule;Suggests appropriate queries for checking element presence vs absence.
// Disallow the use of data-testid queries
'testing-library/no-test-id-queries': RuleModule;Discourages *ByTestId queries in favor of more accessible alternatives.
Rules that prevent direct DOM manipulation and encourage Testing Library patterns.
// Disallow the use of container methods
'testing-library/no-container': RuleModule;Prevents direct access to the container element from render results.
// Disallow direct node access methods
'testing-library/no-node-access': RuleModule;Discourages direct DOM node access methods like querySelector in tests.
// Disallow importing DOM Testing Library directly
'testing-library/no-dom-import': RuleModule;Prevents importing from @testing-library/dom when framework-specific packages should be used.
Rules that enforce good testing practices and patterns.
// Disallow debugging utilities in production code
'testing-library/no-debugging-utils': RuleModule;Prevents debug, logRoles, and other debugging utilities from reaching production.
// Disallow manual cleanup in tests
'testing-library/no-manual-cleanup': RuleModule;Discourages manual cleanup calls when automatic cleanup is available.
// Disallow render calls in lifecycle methods
'testing-library/no-render-in-lifecycle': RuleModule;Prevents rendering components in setup hooks like beforeEach.
// Disallow unnecessary act() calls
'testing-library/no-unnecessary-act': RuleModule;Identifies unnecessary act() wrappers when Testing Library handles them automatically.
// Disallow multiple assertions in waitFor
'testing-library/no-wait-for-multiple-assertions': RuleModule;Ensures waitFor contains only a single assertion for proper error messaging.
// Disallow side effects in waitFor
'testing-library/no-wait-for-side-effects': RuleModule;Prevents side effects like state updates within waitFor callbacks.
// Disallow snapshot assertions in waitFor
'testing-library/no-wait-for-snapshot': RuleModule;Prevents snapshot testing within waitFor which can cause flaky tests.
// Disallow global RegExp flags in queries
'testing-library/no-global-regexp-flag-in-query': RuleModule;Prevents global regex flags that can cause unexpected matching behavior.
Rules for proper event simulation and user interaction patterns.
// Prefer userEvent over fireEvent
'testing-library/prefer-user-event': RuleModule;Encourages userEvent over fireEvent for more realistic user interactions.
// Disallow promises in fireEvent calls
'testing-library/no-promise-in-fire-event': RuleModule;Prevents promise-returning functions in fireEvent calls which are synchronous.
Rules that guide proper assertion patterns with Testing Library.
// Prefer explicit assertions over implicit presence checks
'testing-library/prefer-explicit-assert': RuleModule;Encourages explicit assertions with matchers over implicit element existence checks.
// Prefer implicit assertions for simple presence checks
'testing-library/prefer-implicit-assert': RuleModule;Suggests implicit assertions for simple element presence when appropriate.
Rules that enforce consistent naming and convention patterns.
// Enforce consistent data-testid naming conventions
'testing-library/consistent-data-testid': RuleModule;Configuration Options:
interface ConsistentDataTestIdOptions {
testIdPattern?: string; // Regex pattern for valid test IDs
testIdAttribute?: string; // Custom test ID attribute name
}Enforces consistent naming patterns for test ID attributes.
// Enforce naming conventions for render results
'testing-library/render-result-naming-convention': RuleModule;Configuration Options:
interface RenderResultNamingOptions {
renderFunctionName?: string[]; // Valid render function names
allowedWrapperNames?: string[]; // Valid wrapper variable names
}Enforces consistent naming for render result destructuring and variables.
Rules can be configured individually with custom options and severity levels.
// Individual rule configuration
{
rules: {
// Error level
'testing-library/await-async-queries': 'error',
// Warning level
'testing-library/no-debugging-utils': 'warn',
// Disabled
'testing-library/no-test-id-queries': 'off',
// With options
'testing-library/consistent-data-testid': ['error', {
testIdPattern: '^[a-z]+(-[a-z]+)*$',
testIdAttribute: 'data-testid'
}],
'testing-library/render-result-naming-convention': ['warn', {
renderFunctionName: ['render', 'renderWithProviders'],
allowedWrapperNames: ['wrapper', 'container']
}]
}
}interface RuleContext<TMessageIds extends string = string, TOptions extends readonly unknown[] = unknown[]> {
id: string;
options: TOptions;
settings: Record<string, unknown>;
parserPath: string;
parserServices?: ParserServices;
getAncestors(): TSESTree.Node[];
getDeclaredVariables(node: TSESTree.Node): Variable[];
getFilename(): string;
getScope(): Scope.Scope;
getSourceCode(): SourceCode;
markVariableAsUsed(name: string): boolean;
report(descriptor: ReportDescriptor<TMessageIds>): void;
}
interface RuleListener {
[key: string]: (node: TSESTree.Node) => void;
}
interface ReportDescriptor<TMessageIds extends string> {
node: TSESTree.Node;
messageId: TMessageIds;
data?: Record<string, unknown>;
fix?: (fixer: RuleFixer) => FixCommand | FixCommand[] | null;
suggest?: SuggestionReportDescriptor<TMessageIds>[];
}