diff --git a/packages/generate-loader/README.md b/packages/generate-loader/README.md index 8f23e52343c..8d719e8062a 100644 --- a/packages/generate-loader/README.md +++ b/packages/generate-loader/README.md @@ -27,7 +27,13 @@ generateLoader(); ### CLI (via `webpack-cli`) ```bash -npx webpack-cli generate-loader +npx webpack-cli loader +``` + +> Optionally specify a path for generating the loader template. + +```bash +npx webpack-cli loader [path] ``` [downloads]: https://img.shields.io/npm/dm/@webpack-cli/generate-loader.svg diff --git a/packages/generate-loader/src/index.ts b/packages/generate-loader/src/index.ts index ee7a7a6fa63..599d39abf6d 100644 --- a/packages/generate-loader/src/index.ts +++ b/packages/generate-loader/src/index.ts @@ -9,8 +9,9 @@ const { logger } = utils; * @returns {void} */ -export default function loaderCreator(): void { - const env = yeoman.createEnv(); +export default function loaderCreator(...args: string[]): void { + const generationPath = args[0]; + const env = yeoman.createEnv([], { cwd: generationPath }); const generatorName = 'webpack-loader-generator'; env.registerStub(loaderGenerator, generatorName); diff --git a/test/loader/loader.test.js b/test/loader/loader.test.js index 239e69247d2..bf1638a239d 100644 --- a/test/loader/loader.test.js +++ b/test/loader/loader.test.js @@ -1,6 +1,6 @@ 'use strict'; -const { existsSync } = require('fs'); +const { existsSync, mkdirSync } = require('fs'); const { join, resolve } = require('path'); const rimraf = require('rimraf'); const stripAnsi = require('strip-ansi'); @@ -10,13 +10,16 @@ const firstPrompt = '? Loader name (my-loader)'; const ENTER = '\x0D'; const loaderName = 'test-loader'; const loaderPath = join(__dirname, loaderName); +const genPath = join(__dirname, 'test-assets'); +const customLoaderPath = join(genPath, loaderName); describe('loader command', () => { - beforeAll(() => { + beforeEach(() => { rimraf.sync(loaderPath); + rimraf.sync(genPath); }); - it('Should ask the loader name when invoked', () => { + it('should ask the loader name when invoked', () => { const { stdout, stderr } = run(__dirname, ['loader'], false); expect(stdout).toBeTruthy(); expect(stderr).toBeFalsy(); @@ -33,19 +36,74 @@ describe('loader command', () => { return; } - // check if the output directory exists with the appropriate loader name - expect(existsSync(join(__dirname, loaderName))).toBeTruthy(); + // Check if the output directory exists with the appropriate loader name + expect(existsSync(loaderPath)).toBeTruthy(); // All test files are scaffolded const files = ['package.json', 'examples', 'src', 'test', 'src/index.js', 'examples/simple/webpack.config.js']; files.forEach((file) => { - expect(existsSync(join(__dirname, `${loaderName}/${file}`))).toBeTruthy(); + expect(existsSync(loaderPath, file)).toBeTruthy(); }); - //check if the the generated plugin works successfully + // Check if the the generated loader works successfully const path = resolve(__dirname, './test-loader/examples/simple/'); ({ stdout } = run(path, [], false)); expect(stdout).toContain('test-loader'); }); + + it('should scaffold loader template in the specified path', async () => { + let { stdout } = await runPromptWithAnswers(__dirname, ['loader', 'test-assets'], [`${loaderName}${ENTER}`]); + + expect(stripAnsi(stdout)).toContain(firstPrompt); + + // Skip test in case installation fails + if (!existsSync(resolve(customLoaderPath, './yarn.lock'))) { + return; + } + + // Check if the output directory exists with the appropriate loader name + expect(existsSync(customLoaderPath)).toBeTruthy(); + + // All test files are scaffolded + const files = ['package.json', 'examples', 'src', 'test', 'src/index.js', 'examples/simple/webpack.config.js']; + + files.forEach((file) => { + expect(existsSync(customLoaderPath, file)).toBeTruthy(); + }); + + // Check if the the generated loader works successfully + const path = resolve(customLoaderPath, './examples/simple/'); + ({ stdout } = run(path, [], false)); + expect(stdout).toContain('test-loader'); + }); + + it('should scaffold loader template in the current directory', async () => { + // Create test-assets directory + mkdirSync(genPath); + + let { stdout } = await runPromptWithAnswers(genPath, ['loader', './'], [`${loaderName}${ENTER}`]); + + expect(stripAnsi(stdout)).toContain(firstPrompt); + + // Skip test in case installation fails + if (!existsSync(resolve(customLoaderPath, './yarn.lock'))) { + return; + } + + // Check if the output directory exists with the appropriate loader name + expect(existsSync(customLoaderPath)).toBeTruthy(); + + // All test files are scaffolded + const files = ['package.json', 'examples', 'src', 'test', 'src/index.js', 'examples/simple/webpack.config.js']; + + files.forEach((file) => { + expect(existsSync(customLoaderPath, file)).toBeTruthy(); + }); + + // Check if the the generated loader works successfully + const path = resolve(customLoaderPath, './examples/simple/'); + ({ stdout } = run(path, [], false)); + expect(stdout).toContain('test-loader'); + }); });