# test.govlab/pipeline/core/factories/plan.factory.test.ts

> 51 lines of code and 0 definitions.

Tree: Codebase Testing
Language: typescript
Canonical: https://banes-lab.com/anatomy/testing#file-testing-test-govlab-pipeline-core-factories-plan-factory-test-ts
Source text: https://banes-lab.com/source/testing/test.govlab/pipeline/core/factories/plan.factory.test.ts.txt

Listed in [test.govlab/pipeline/core/factories](https://banes-lab.com/api/source/testing/test.govlab/pipeline/core/factories.md), after [test.govlab/pipeline/core/factories/build.factory.test.ts](https://banes-lab.com/source/testing/test.govlab/pipeline/core/factories/build.factory.test.ts.md) and before [test.govlab/pipeline/core/factories/stage.factory.test.ts](https://banes-lab.com/source/testing/test.govlab/pipeline/core/factories/stage.factory.test.ts.md).

## Contained in

- [test.govlab/pipeline/core/factories](https://banes-lab.com/anatomy/testing/folder-testing-test-govlab-pipeline-core-factories.md)

## Source

```typescript
import { describe, expect, it } from "vitest";
import { MEMBERS } from "@govlab/pipeline/configuration/configs/package.config.ts";
import type { StageOptions } from "@govlab/pipeline/types/stage.types.ts";
import { stageLabels } from "@govlab/pipeline/core/converters/stage.converter.ts";
import { stagesFor } from "@govlab/pipeline/core/factories/plan.factory.ts";

const optionsFor = function optionsFor(...members: string[]): StageOptions {
    return { cleanCommentsIgnore: "", hexIgnore: "", qualityRoot: "", scope: new Set(members) };
};

describe("MEMBERS", () => {
    it("gives every member a distinct id", () => {
        const ids = MEMBERS.map((member) => member.id);
        expect(new Set(ids).size).toBe(ids.length);
    });
});

describe("stagesFor", () => {
    it("ranges a full run over the gated members only and skips no wide step", () => {
        const plan = stagesFor(optionsFor());
        const labels = stageLabels(plan);
        for (const member of MEMBERS) {
            expect(labels.some((label) => label.endsWith(member.dir.slice(member.dir.lastIndexOf("/") + 1)))).toBe(
                member.gated,
            );
        }
        expect(plan.skippedWide).toHaveLength(0);
    });

    it("narrows a scoped run to the named members and names every wide step it skipped", () => {
        const plan = stagesFor(optionsFor("pipeline"));
        const labels = stageLabels(plan);
        expect(labels).toContain("Typecheck govlab.pipeline");
        expect(labels).not.toContain("Knip");
        expect(plan.skippedWide).toContain("Knip");
        expect(plan.skippedWide).toContain("Validate documents");
    });

    it("drops a stage left with no steps", () => {
        const slugs = stagesFor(optionsFor("paths")).stages.map((stage) => stage.slug);
        expect(slugs).not.toContain("unused");
        expect(slugs).toContain("linting");
    });

    it("keeps the stage order the gate runs in", () => {
        expect(stagesFor(optionsFor()).stages.map((stage) => stage.slug)).toStrictEqual([
            "prepare",
            "unused",
            "auto-fix",
            "format",
            "linting",
            "testing",
            "build",
            "validation",
        ]);
    });
});
```
