All skills
asyrafhussin avatar

/testing-best-practices

@575c801

Unit testing, integration testing, and test-driven development principles. Use when writing tests, reviewing test code, improving test coverage, or setting up testing strategy. Triggers on "write tests", "review tests", "testing best practices", or "TDD".

Use this Skill: https://skilld.dev/gh/asyrafhussin/agent-skills/testing-best-practices

This session only. Nothing lands on disk.

rulesiso-no-shared-state.md

≈928 tokens on demand. Your agent reads this file only when SKILL.md points to it.

No Shared Mutable State

Impact: CRITICAL (test predictability and flakiness prevention)

Avoid sharing mutable state between tests to prevent interference and flakiness. Shared mutable state is one of the most common causes of flaky tests. Use beforeEach to create fresh instances and reset any necessary state.

Incorrect

// ❌ Bad: Shared mutable state causes test interference
let counter = 0;
const cache: Map<string, User> = new Map();
const users: User[] = [];

describe('UserCache', () => {
  test('caches user on first access', () => {
    const user = { id: ++counter, name: 'Alice' };
    users.push(user);
    cache.set(user.id.toString(), user);

    expect(cache.get('1')).toEqual(user);
  });

  test('retrieves cached user', () => {
    // Relies on cache populated by previous test
    expect(cache.has('1')).toBe(true);
  });

  test('adds second user to cache', () => {
    const user = { id: ++counter, name: 'Bob' };
    users.push(user);
    cache.set(user.id.toString(), user);

    // This assertion depends on test execution order
    expect(users.length).toBe(2);
    expect(counter).toBe(2);
  });
});

// Global mock that persists between tests
jest.mock('./emailService', () => ({
  send: jest.fn()
}));

Problems:

  • Module-level variables are mutated across tests
  • Cache and array state depend on prior test execution
  • Counter values are only correct if tests run in a specific order
  • Global mocks retain call counts from previous tests

Correct

// ✅ Good: Each test has its own isolated state
describe('UserCache', () => {
  let cache: UserCache;
  let userIdCounter: number;

  beforeEach(() => {
    cache = new UserCache();
    userIdCounter = 0;
  });

  const createUser = (name: string): User => ({
    id: ++userIdCounter,
    name
  });

  test('caches user on first access', () => {
    const user = createUser('Alice');

    cache.set(user);

    expect(cache.get(user.id)).toEqual(user);
  });

  test('returns undefined for uncached user', () => {
    expect(cache.get(999)).toBeUndefined();
  });

  test('stores multiple users independently', () => {
    const alice = createUser('Alice');
    const bob = createUser('Bob');

    cache.set(alice);
    cache.set(bob);

    expect(cache.size()).toBe(2);
    expect(cache.get(alice.id)).toEqual(alice);
    expect(cache.get(bob.id)).toEqual(bob);
  });
});

describe('EmailNotificationService', () => {
  let emailService: jest.Mocked<EmailService>;
  let notificationService: NotificationService;

  beforeEach(() => {
    // Fresh mock for each test
    emailService = {
      send: jest.fn().mockResolvedValue(true)
    };
    notificationService = new NotificationService(emailService);
  });

  test('sends welcome email to new user', async () => {
    await notificationService.welcomeUser('alice@example.com');

    expect(emailService.send).toHaveBeenCalledTimes(1);
  });

  test('sends password reset email', async () => {
    await notificationService.sendPasswordReset('bob@example.com');

    // Not affected by previous test
    expect(emailService.send).toHaveBeenCalledTimes(1);
  });
});

Benefits:

  • Each test starts with a known, predictable state
  • One test cannot corrupt another test's data
  • Tests can run concurrently without conflicts
  • State is clearly defined within each test for easier debugging
  • Results are consistent whether running one test or the full suite

Reference: Jest Docs — Setup and Teardown

Source: SKILL.md on GitHub

No alerts16d5 checks · Risk SAFE
  • Gen Agent Trust Hub16d

    The skill provides comprehensive guidelines and best practices for unit testing, integration testing, and Test-Driven Development (TDD). It consists entirely of documentation and illustrative code examples using industry-standard tools like Jest and Vitest. No security risks or malicious patterns were detected.

  • Socket16d

    No alerts

  • Snyk16d

    Risk: LOW · No issues

  • Runlayer6mo

    29 files scanned · No issues

  • ZeroLeaks5mo

    Score: 93/100 · 2 sections analyzed

Signed by skilld at 575c801. This ties the file your Agent reads to that commit on GitHub. It does not review the instructions.

Last checked against GitHub last month.

Steadyupdated 7 months ago
metadata
{
  "author": "agent-skills",
  "version": "2.0.0"
}

README badge

README badge for asyrafhussin/agent-skills/testing-best-practices