advanced21 min

Tagging, Test Selection, Parallelism, and Isolation

Designing a tagging scheme that lets a suite be sliced into meaningful subsets on demand, and what genuine test isolation requires to make safe, correct parallel execution possible.

What you'll learn

  • Design a tagging scheme that lets a suite be selectively run by concern (smoke, regression, a feature area) without duplicating test files
  • Explain what genuine test isolation requires, beyond simply not sharing obvious global state
  • Explain why parallel execution amplifies the cost of a test-isolation bug that might otherwise go unnoticed

Prerequisites

Explanation

No real test suite is executed in this lesson's exercises -- they model tag-based selection and isolation-risk decisions as data, using genuine JavaScript/TypeScript execution.

A useful tagging scheme lets one shared test suite be sliced into meaningful, run-on-demand subsets by concern — a fast @smoke subset for a pre-merge check, a broader @regression subset for a nightly run, or a @checkout subset scoped to one feature area for a targeted investigation — without maintaining separate, duplicated test files for each purpose. The same underlying test can carry multiple tags at once (a checkout test can be both @smoke and @checkout), and a genuinely useful scheme keeps tags meaningful and non-overlapping in purpose — a handful of well-defined, consistently applied tags is far more useful long-term than dozens of ad-hoc, inconsistently used ones that no one remembers the exact meaning of.

Test isolation means one test's execution cannot affect another test's outcome, regardless of execution order or whether they run in parallel — and this requires more discipline than simply "don't use a literal global variable." A test that creates a user with a hardcoded email, or that queries "the first item in a list" instead of a specifically-identified item it created itself, or that depends on a previous test having already run and left the system in a particular state, is not genuinely isolated, even though it may never touch an explicit shared variable — this course's earlier lessons on unique test data (Lesson 3) and fixture-scoped setup (Lesson 4) are, in large part, specifically in service of achieving real isolation.

Parallel execution doesn't create isolation bugs — it amplifies ones that already existed. A genuine isolation bug (two tests colliding on the same hardcoded data, or one test depending on another's leftover state) might pass reliably when a suite happens to run tests sequentially, in a fixed, familiar order, purely by accident — and then fail intermittently, confusingly, and non-deterministically the moment the exact same suite runs in parallel or in a different order, since the accidental ordering that was silently hiding the bug is no longer guaranteed. This is precisely why isolation should be designed in from the start, not treated as a problem to solve only once parallel execution is introduced.

Example

Modeling filtering tests by tag and detecting a non-isolated test relying on shared, order-dependent state, as data.

function testsMatchingTag(tests, tag) {
  return tests.filter((t) => t.tags.includes(tag));
}
const suite = [
  { name: "login works", tags: ["smoke", "auth"] },
  { name: "checkout completes", tags: ["smoke", "checkout"] },
  { name: "detailed refund flow", tags: ["regression", "checkout"] },
];
console.log(testsMatchingTag(suite, "smoke").length);    // 2 -- a fast, targeted subset
console.log(testsMatchingTag(suite, "checkout").length); // 2 -- a feature-scoped subset, independent of the smoke/regression split

function isGenuinelyIsolated(usesUniqueOwnData, dependsOnPriorTestState) {
  return usesUniqueOwnData && !dependsOnPriorTestState;
}
console.log(isGenuinelyIsolated(true, false));  // true -- creates and uses its own uniquely identified data
console.log(isGenuinelyIsolated(false, true));  // false -- a real isolation bug, likely to surface only under parallel/reordered execution

Try it yourself

Call testsMatchingTag with 'regression', and confirm it correctly returns only the one regression-tagged test.

Code editor. Press Escape then Tab to leave the editor if keyboard focus becomes trapped. Press Control+Shift+M inside the editor to toggle Tab-key focus trapping.

Loading editor…

Guided exercise

Guided exercise

This models selecting tests matching ALL of several tags (an intersection, not just any match) only -- no real suite runs. Write testsMatchingAllTags(tests, requiredTags), returning tests whose tags array includes EVERY tag in requiredTags.

Checks: correctly finds a test matching an intersection of two required tags · correctly matches multiple tests for a single required tag · correctly returns none for an impossible tag combination

Code editor. Press Escape then Tab to leave the editor if keyboard focus becomes trapped. Press Control+Shift+M inside the editor to toggle Tab-key focus trapping.

Loading editor…

Stuck? Get a hint.

Independent exercise

Independent exercise

This models detecting a genuine isolation risk only -- no real test suite runs. Write isolationRisk(usesHardcodedIdentifier, readsFirstMatchingRecord, dependsOnExecutionOrder): return the array of risk names (in this exact order) among 'hardcoded-identifier-collision', 'ambiguous-record-selection', 'order-dependency' that apply, based on the three boolean inputs respectively.

Checks: correctly identifies a single, specific isolation risk · correctly identifies no risk for a genuinely isolated test · correctly identifies all three risks together, in the specified order

Code editor. Press Escape then Tab to leave the editor if keyboard focus becomes trapped. Press Control+Shift+M inside the editor to toggle Tab-key focus trapping.

Loading editor…

Stuck? Get a hint.

Common mistakes

  • Using dozens of ad-hoc, inconsistently applied tags with no shared, understood meaning -- this makes tag-based selection unreliable, since no one can be confident what a given tag actually guarantees about the tests carrying it.
  • Assuming a test is isolated simply because it doesn't use an explicit global variable -- hardcoded shared data, reading 'the first matching record' instead of a specifically-created one, and depending on a previous test's leftover state are all real isolation bugs that don't involve a literal global.
  • Only discovering an isolation bug once parallel execution is introduced, and treating it as a new, parallelism-specific problem -- the bug existed before parallelism; parallel execution just removed the accidental ordering that had been hiding it.

Knowledge check

Knowledge check

1. What makes a tagging scheme genuinely useful for test selection, as opposed to a source of confusion?
2. Why can a test be genuinely NOT isolated even if it never touches an explicit global variable?
3. Why does parallel execution tend to expose isolation bugs that a sequential run didn't reveal?

Takeaway

Design a small, consistent, well-understood tagging scheme so a suite can be selectively run by concern without duplicating test files. Pursue genuine test isolation deliberately -- unique, self-created data and independence from execution order -- since parallel execution amplifies, rather than causes, any isolation bug that already exists.

Summary

A useful tagging scheme is small, consistent, and meaningful, letting a shared suite be sliced into subsets (smoke, regression, a feature area) on demand. Genuine test isolation requires more than avoiding explicit global variables -- hardcoded shared data, ambiguous record selection, and order-dependency are all real isolation bugs. Parallel execution amplifies a pre-existing isolation bug by removing the accidental sequential ordering that had been hiding it, rather than introducing a new category of bug.

References

Your notes

Notes save automatically.

Finished this lesson?

Mark it complete to track your progress and schedule a future review.