UNPKG

vitest-stylelint-utils

Version:
164 lines (163 loc) 5.37 kB
// src/get-test-rule.ts import util from "node:util"; import stylelint from "stylelint"; var { lint } = stylelint; function getTestRule(options) { const { describe, expect, it } = options; return function testRule(schema) { describe(`${schema.ruleName}`, () => { const stylelintConfig = { plugins: options.plugins || schema.plugins, rules: { [schema.ruleName]: schema.config } }; setupTestCases({ name: "accept", cases: schema.accept, schema, comparisons(testCase) { return async function() { const stylelintOptions = { code: testCase.code, config: stylelintConfig, customSyntax: schema.customSyntax, codeFilename: schema.codeFilename }; const output = await lint(stylelintOptions); expect(output.results[0].warnings).toEqual([]); expect(output.results[0].parseErrors).toEqual([]); expect(output.results[0].invalidOptionWarnings).toEqual([]); if (!schema.fix) { return; } const outputAfterFix = await lint({ ...stylelintOptions, fix: true }); const fixedCode = getOutputCss(outputAfterFix); expect(fixedCode).toBe(testCase.code); }; }, describe, it }); setupTestCases({ name: "reject", cases: schema.reject, schema, comparisons(testCase) { return async function() { const stylelintOptions = { code: testCase.code, config: stylelintConfig, customSyntax: schema.customSyntax, codeFilename: schema.codeFilename }; const outputAfterLint = await lint(stylelintOptions); const actualWarnings = [ ...outputAfterLint.results[0].invalidOptionWarnings, ...outputAfterLint.results[0].warnings ]; expect(outputAfterLint.results[0]).toMatchObject({ parseErrors: [] }); expect(actualWarnings).toHaveLength( testCase.warnings ? testCase.warnings.length : 1 ); const warnings = testCase.warnings || [testCase]; warnings.forEach((warning, index) => { expect( warning.message, 'Expected "reject" test case to have a "message" property' ).toBeDefined(); const expectedWarning = { text: warning.message, line: warning.line, column: warning.column, endLine: warning.endLine, endColumn: warning.endColumn }; Object.entries(expectedWarning).forEach(([key, value]) => { if (value === void 0) { delete expectedWarning[key]; } }); expect(actualWarnings[index]).toMatchObject(expectedWarning); }); if (!schema.fix) { return; } if (schema.fix && !testCase.fixed && testCase.fixed !== "" && !testCase.unfixable) { throw new Error( "If using { fix: true } in test schema, all reject cases must have { fixed: .. }" ); } const outputAfterFix = await lint({ ...stylelintOptions, fix: true }); const fixedCode = getOutputCss(outputAfterFix); if (!testCase.unfixable) { expect(fixedCode).toBe(testCase.fixed); expect(fixedCode).not.toBe(testCase.code); } else { if (testCase.fixed) { expect(fixedCode).toBe(testCase.fixed); } expect(fixedCode).toBe(testCase.code); } const outputAfterLintOnFixedCode = await lint({ ...stylelintOptions, code: fixedCode, fix: testCase.unfixable }); expect(outputAfterLintOnFixedCode.results[0]).toMatchObject({ warnings: outputAfterFix.results[0].warnings, parseErrors: [] }); }; }, describe, it }); }); }; } function setupTestCases({ name, cases, schema, comparisons, describe, it }) { if (cases && cases.length) { const testGroup = schema.only ? describe.only : schema.skip ? describe.skip : describe; testGroup(`${name}`, () => { cases.forEach((testCase) => { if (testCase) { const spec = testCase.only ? it.only : testCase.skip ? it.skip : it; describe(`${util.inspect(schema.config)}`, () => { describe(`${util.inspect(testCase.code)}`, () => { spec( testCase.description || "no description", comparisons(testCase) ); }); }); } }); }); } } function getOutputCss(output) { const result = output.results[0]._postcssResult; if (result && result.root && result.opts) { return result.root.toString(result.opts.syntax); } throw new TypeError("Invalid result"); } export { getTestRule };