Test utilities for Yeoman generators providing a fluent API for setting up test environments and asserting generated content
The YeomanTest class provides utility functions for creating, mocking, and managing generators and test environments. It supports dummy generators, mocked interactions, environment configuration, and both functional and class-based testing approaches.
Create customized helper instances with specific configurations.
/**
* Create a customized YeomanTest instance with specific options
* @param options - Configuration options to apply to the helper instance
* @returns New YeomanTest instance with applied options
*/
function createHelpers(options: Partial<YeomanTest>): YeomanTest;
/**
* Default YeomanTest instance available as default export
*/
const defaultHelpers: YeomanTest;Usage Examples:
import { createHelpers } from "yeoman-test";
// Create helper with custom settings
const helpers = createHelpers({
settings: { tmpdir: false },
environmentOptions: { localConfigOnly: false },
generatorOptions: { skipInstall: true }
});
// Use custom helper
await helpers.run("my-generator");Create generator instances with dependencies and configuration for testing.
/**
* Create a generator instance with dependencies and options
* @param name - Generator name or constructor
* @param options - Configuration including dependencies and instantiation options
* @returns Promise resolving to generator instance
*/
async createGenerator<GeneratorType extends BaseGenerator = DefaultGeneratorApi>(
name: string | GetGeneratorConstructor<GeneratorType>,
options?: {
dependencies?: Dependency[];
localConfigOnly?: boolean;
} & InstantiateOptions<GeneratorType>
): Promise<GeneratorType>;
type Dependency = string | Parameters<DefaultEnvironmentApi['register']>;Usage Examples:
import helpers from "yeoman-test";
// Create generator with dependencies
const generator = await helpers.createGenerator("my-generator", {
dependencies: [
"./path/to/dep-generator",
["./other-generator", { namespace: "other:gen" }]
],
localConfigOnly: true,
generatorArgs: ["init"],
generatorOptions: { force: true }
});
// Use the generator instance
await generator.run();Create simple, customizable generators for testing scenarios.
/**
* Create a simple, dummy generator for testing
* @param Generator - Base generator class (defaults to yeoman-generator)
* @param contents - Object defining methods and properties for the dummy generator
* @returns Generator constructor that can be instantiated
*/
createDummyGenerator<GenParameter extends BaseGenerator = DefaultGeneratorApi>(
Generator?: GetGeneratorConstructor<GenParameter>,
contents?: Record<string, (...args: any[]) => void>
): new (...args: any[]) => GenParameter;Usage Examples:
import helpers from "yeoman-test";
// Basic dummy generator
const DummyGen = helpers.createDummyGenerator();
// Custom dummy generator with methods
const CustomDummyGen = helpers.createDummyGenerator(undefined, {
writing(this: any) {
this.fs.write("output.txt", "Hello World");
},
install(this: any) {
this.spawnCommand("npm", ["install"]);
}
});
// Use in tests
await helpers.run(CustomDummyGen)
.withSpawnMock();
result.assertFile("output.txt");Create fully mocked generators for testing generator composition.
/**
* Create a mocked generator with stubbed methods
* @param GeneratorClass - Base generator class to mock
* @returns Mocked generator constructor with stubbed methods
*/
createMockedGenerator(GeneratorClass?: any): ReturnType<typeof mock.fn>;Usage Examples:
import helpers from "yeoman-test";
// Create mocked generator
const MockedGen = helpers.createMockedGenerator();
// Use in test environment
const env = await helpers.createTestEnv();
env.register(MockedGen, { namespace: "mocked:gen" });
// Verify mock was called
expect(MockedGen.mock.callCount()).toBeGreaterThan(0);Legacy methods maintained for backward compatibility.
/**
* @deprecated Use inTmpDir from RunContext instead
* Create a function that will clean up the test directory
* @param dir - Path to the test directory
* @returns Mocha callback function
*/
setUpTestDirectory(dir: string): () => void;
/**
* @deprecated Use inTmpDir from RunContext instead
* Clean-up the test directory and cd into it
* @param dir - Path to the test directory
* @param cb - Callback executed after setting working directory
*/
testDirectory(dir: string, callback?: (error?: any) => unknown): void;
/**
* @deprecated Use withAnswers from RunContext instead
* Answer prompt questions for the passed-in generator
* @param generator - Yeoman generator or environment
* @param answers - Object mapping prompt names to answers
* @param options - Prompt options
*/
mockPrompt(
environmentOrGenerator: BaseGenerator | DefaultEnvironmentApi,
mockedAnswers?: PromptAnswers,
options?: DummyPromptOptions
): void;
/**
* @deprecated Use test cleanup methods instead
* Restore defaults prompts on a generator
* @param generator - Generator or environment instance
*/
restorePrompt(environmentOrGenerator: BaseGenerator | DefaultEnvironmentApi): void;
/**
* @deprecated Use withLocalConfig from RunContext instead
* Provide mocked values to the config
* @param generator - Yeoman generator instance
* @param localConfig - Configuration object
*/
mockLocalConfig(generator: BaseGenerator, localConfig: any): void;The YeomanTest class can be configured with default settings that apply to all test contexts created from that instance.
class YeomanTest {
/** Default settings for RunContext creation */
settings?: RunContextSettings;
/** Default environment options */
environmentOptions?: BaseEnvironmentOptions;
/** Default generator options */
generatorOptions?: BaseGeneratorOptions;
/** Default adapter options */
adapterOptions?: Omit<TestAdapterOptions, 'mockedAnswers'>;
}Usage Examples:
import { createHelpers } from "yeoman-test";
// Create configured helper instance
const helpers = createHelpers({
settings: {
tmpdir: true,
autoCleanup: true
},
environmentOptions: {
localConfigOnly: true,
skipCache: true
},
generatorOptions: {
skipInstall: true,
force: true
}
});
// All run contexts from this helper will use these defaults
await helpers.run("my-generator"); // Uses configured defaultsYeomanTest methods can be overridden for custom behavior:
/**
* Get RunContext constructor - can be overridden for custom context types
* @returns RunContext constructor function
*/
getRunContextType(): typeof RunContext;Usage Examples:
import { createHelpers, RunContext } from "yeoman-test";
// Custom RunContext with additional methods
class CustomRunContext extends RunContext {
withCustomFeature() {
// Add custom functionality
return this;
}
}
// Create helper with custom context type
const helpers = createHelpers({});
helpers.getRunContextType = () => CustomRunContext;
// Now all contexts will be CustomRunContext instances
const context = helpers.run("my-generator") as CustomRunContext;
context.withCustomFeature();// Create reusable generator factory
function createTestGenerator(options = {}) {
return helpers.createDummyGenerator(undefined, {
writing(this: any) {
this.fs.writeJSON("package.json", {
name: options.name || "test-app",
version: options.version || "1.0.0"
});
}
});
}
// Use in multiple tests
const TestGen = createTestGenerator({ name: "my-app" });
await helpers.run(TestGen);// Test generator that composes with others
await helpers.run("main-generator")
.withMockedGenerators([
"sub:component",
"sub:service",
"common:utils"
]);
// Verify composition behavior
result.assertGeneratorComposed("sub:component");
result.assertGeneratorComposedOnce("common:utils");
const composedGens = result.getComposedGenerators();
expect(composedGens).toHaveLength(2);// Run initial generator
await helpers.run("init-generator")
.withAnswers({ projectType: "library" });
// Run follow-up generator in same directory
await result.create("feature-generator")
.withAnswers({ featureName: "auth" })
.withLocalConfig({ initialized: true });
// Verify combined result
result.assertFile(["package.json", "src/auth.ts"]);Install with Tessl CLI
npx tessl i tessl/npm-yeoman-test