diff --git a/.github/ISSUE_TEMPLATE/BUG_REPORT.yml b/.github/ISSUE_TEMPLATE/BUG_REPORT.yml index 67670dc8fd..7e1df48553 100644 --- a/.github/ISSUE_TEMPLATE/BUG_REPORT.yml +++ b/.github/ISSUE_TEMPLATE/BUG_REPORT.yml @@ -1,7 +1,7 @@ -name: '🐛 Bug Report' +name: "🐛 Bug Report" description: Create a new ticket for a bug. -title: 'fix: ' -labels: ['bug'] +title: "fix: <title>" +labels: ["bug"] body: - type: markdown attributes: @@ -10,7 +10,7 @@ body: - type: textarea id: steps-to-reproduce attributes: - label: 'Steps to Reproduce' + label: "Steps to Reproduce" description: Provide a link to a live example, or an unambiguous set of steps to reproduce this bug. Include code to reproduce, if relevant value: | 1. First step @@ -21,14 +21,14 @@ body: - type: textarea id: current-behavior attributes: - label: 'Current Behavior' + label: "Current Behavior" description: Tell us what happens instead of the expected behavior validations: required: false - type: textarea id: expected-behavior attributes: - label: 'Expected Behavior' + label: "Expected Behavior" description: Tell us what should happen placeholder: Short and explicit description of your incident... validations: @@ -36,7 +36,7 @@ body: - type: checkboxes id: affected-packages attributes: - label: 'Affected packages' + label: "Affected packages" options: - label: cli - label: core @@ -45,14 +45,14 @@ body: - type: textarea id: possible-solution attributes: - label: 'Possible Solution' + label: "Possible Solution" description: Not obligatory, but suggest a fix/reason for the bug, or ideas how to implement the addition or change validations: required: false - type: textarea id: context attributes: - label: 'Context' + label: "Context" description: | How has this issue affected you? What are you trying to accomplish? Providing context helps us come up with a solution that is most useful in the real world @@ -61,21 +61,21 @@ body: - type: input id: commitlint-version attributes: - label: 'commitlint --version' - placeholder: '@commitlint/cli@x.x.x' + label: "commitlint --version" + placeholder: "@commitlint/cli@x.x.x" validations: required: true - type: input id: git-version attributes: - label: 'git --version' + label: "git --version" placeholder: vx.x.x validations: required: true - type: input id: node-version attributes: - label: 'node --version' + label: "node --version" placeholder: vx.x.x validations: required: true diff --git a/.github/ISSUE_TEMPLATE/FEATURE_REQUEST.yml b/.github/ISSUE_TEMPLATE/FEATURE_REQUEST.yml index bf4e9609df..063dd15fe4 100644 --- a/.github/ISSUE_TEMPLATE/FEATURE_REQUEST.yml +++ b/.github/ISSUE_TEMPLATE/FEATURE_REQUEST.yml @@ -1,7 +1,7 @@ -name: '✨ Feature Request' +name: "✨ Feature Request" description: Create a new ticket for a new feature request -title: 'feat: <title>' -labels: ['feature'] +title: "feat: <title>" +labels: ["feature"] body: - type: markdown attributes: @@ -10,7 +10,7 @@ body: - type: textarea id: expected-behavior attributes: - label: 'Expected Behavior' + label: "Expected Behavior" description: Tell us how it should work placeholder: Short and explicit description of your request... validations: @@ -18,14 +18,14 @@ body: - type: textarea id: current-behavior attributes: - label: 'Current Behavior' + label: "Current Behavior" description: Explain the difference from current behavior validations: required: false - type: checkboxes id: affected-packages attributes: - label: 'Affected packages' + label: "Affected packages" options: - label: cli - label: core @@ -34,14 +34,14 @@ body: - type: textarea id: possible-solution attributes: - label: 'Possible Solution' + label: "Possible Solution" description: Ideas how to implement the addition or change validations: required: false - type: textarea id: context attributes: - label: 'Context' + label: "Context" description: | How has this issue affected you? What are you trying to accomplish? Providing context helps us come up with a solution that is most useful in the real world diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml index 234d2ac6f6..6ca2a6a64b 100644 --- a/.github/workflows/CI.yml +++ b/.github/workflows/CI.yml @@ -3,7 +3,7 @@ name: CI on: push: branches: - - '**' + - "**" pull_request: types: [opened, synchronize] @@ -11,7 +11,7 @@ on: # to execute once a day (more info see https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#schedule ) schedule: - - cron: '0 0 * * *' + - cron: "0 0 * * *" jobs: build: @@ -62,7 +62,7 @@ jobs: name: NodeJS installed from stock Ubuntu-LTS packages (not external sources) runs-on: ubuntu-24.04 container: - image: 'ubuntu:24.04' + image: "ubuntu:24.04" steps: - uses: actions/checkout@v4 diff --git a/.github/workflows/container-build.yml b/.github/workflows/container-build.yml index 4465d2f52a..398cc419c3 100644 --- a/.github/workflows/container-build.yml +++ b/.github/workflows/container-build.yml @@ -2,12 +2,12 @@ name: container build on: push: tags: - - '**' + - "**" schedule: - - cron: '0 0 * * *' + - cron: "0 0 * * *" pull_request: paths: - - 'Dockerfile.ci' + - "Dockerfile.ci" jobs: container-build: if: github.repository == 'conventional-changelog/commitlint' diff --git a/@alias/commitlint-config-angular/index.js b/@alias/commitlint-config-angular/index.js index 772977fc4c..0598f27f73 100644 --- a/@alias/commitlint-config-angular/index.js +++ b/@alias/commitlint-config-angular/index.js @@ -1 +1 @@ -export {default} from '@commitlint/config-angular'; +export { default } from "@commitlint/config-angular"; diff --git a/@alias/commitlint-config-lerna-scopes/index.js b/@alias/commitlint-config-lerna-scopes/index.js index 0cfd98ac94..000c9673ee 100644 --- a/@alias/commitlint-config-lerna-scopes/index.js +++ b/@alias/commitlint-config-lerna-scopes/index.js @@ -1 +1 @@ -export {default} from '@commitlint/config-lerna-scopes'; +export { default } from "@commitlint/config-lerna-scopes"; diff --git a/@alias/commitlint-config-nx-scopes/index.js b/@alias/commitlint-config-nx-scopes/index.js index 3e6a1de683..2ba02e27da 100644 --- a/@alias/commitlint-config-nx-scopes/index.js +++ b/@alias/commitlint-config-nx-scopes/index.js @@ -1 +1 @@ -export {default} from '@commitlint/config-nx-scopes'; +export { default } from "@commitlint/config-nx-scopes"; diff --git a/@alias/commitlint-config-patternplate/index.js b/@alias/commitlint-config-patternplate/index.js index 085cdbe448..d95944f6eb 100644 --- a/@alias/commitlint-config-patternplate/index.js +++ b/@alias/commitlint-config-patternplate/index.js @@ -1 +1 @@ -export {default} from '@commitlint/config-patternplate'; +export { default } from "@commitlint/config-patternplate"; diff --git a/@alias/commitlint/cli.js b/@alias/commitlint/cli.js index 3a54821b24..4b917c9cf5 100755 --- a/@alias/commitlint/cli.js +++ b/@alias/commitlint/cli.js @@ -1,2 +1,2 @@ #!/usr/bin/env node -import '@commitlint/cli/cli.js'; +import "@commitlint/cli/cli.js"; diff --git a/@alias/commitlint/cli.test.js b/@alias/commitlint/cli.test.js index 5f0674233b..ff28c511b3 100644 --- a/@alias/commitlint/cli.test.js +++ b/@alias/commitlint/cli.test.js @@ -1,16 +1,16 @@ -import {test, expect} from 'vitest'; -import {createRequire} from 'node:module'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { test, expect } from "vitest"; +import { createRequire } from "node:module"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {x} from 'tinyexec'; -import {fix} from '@commitlint/test'; +import { x } from "tinyexec"; +import { fix } from "@commitlint/test"; const require = createRequire(import.meta.url); -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -const bin = require.resolve('./cli.js'); +const bin = require.resolve("./cli.js"); function cli(args, options, input) { const result = x(bin, args, { @@ -28,15 +28,15 @@ function cli(args, options, input) { const fixBootstrap = (fixture) => fix.bootstrap(fixture, __dirname); -test('should reprint input from stdin', async () => { - const cwd = await fixBootstrap('fixtures/default'); - const actual = await cli([], {cwd}, 'foo: bar'); - expect(actual.stdout).toContain('foo: bar'); +test("should reprint input from stdin", async () => { + const cwd = await fixBootstrap("fixtures/default"); + const actual = await cli([], { cwd }, "foo: bar"); + expect(actual.stdout).toContain("foo: bar"); }); -test('should produce success output with --verbose flag', async () => { - const cwd = await fixBootstrap('fixtures/default'); - const actual = await cli(['--verbose'], {cwd}, 'type: bar'); - expect(actual.stdout).toContain('0 problems, 0 warnings'); - expect(actual.stderr).toEqual(''); +test("should produce success output with --verbose flag", async () => { + const cwd = await fixBootstrap("fixtures/default"); + const actual = await cli(["--verbose"], { cwd }, "type: bar"); + expect(actual.stdout).toContain("0 problems, 0 warnings"); + expect(actual.stderr).toEqual(""); }); diff --git a/@commitlint/cli/cli.js b/@commitlint/cli/cli.js index 1bda77159f..940e27804b 100755 --- a/@commitlint/cli/cli.js +++ b/@commitlint/cli/cli.js @@ -1,2 +1,2 @@ #!/usr/bin/env node -import './lib/cli.js'; +import "./lib/cli.js"; diff --git a/@commitlint/cli/src/cli-error.ts b/@commitlint/cli/src/cli-error.ts index 69db5917bc..8b21ae31ee 100644 --- a/@commitlint/cli/src/cli-error.ts +++ b/@commitlint/cli/src/cli-error.ts @@ -15,7 +15,7 @@ export class CliError extends Error { constructor( message: string, type: string, - error_code = ExitCode.CommitlintErrorDefault + error_code = ExitCode.CommitlintErrorDefault, ) { super(message); diff --git a/@commitlint/cli/src/cli.test.ts b/@commitlint/cli/src/cli.test.ts index 235e5f8849..d65a5e57ab 100644 --- a/@commitlint/cli/src/cli.test.ts +++ b/@commitlint/cli/src/cli.test.ts @@ -1,18 +1,18 @@ -import {describe, test, expect} from 'vitest'; -import {createRequire} from 'node:module'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; -import {fix, git} from '@commitlint/test'; -import fs from 'fs-extra'; -import merge from 'lodash.merge'; -import {x} from 'tinyexec'; -import {ExitCode} from './cli-error.js'; +import { describe, test, expect } from "vitest"; +import { createRequire } from "node:module"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; +import { fix, git } from "@commitlint/test"; +import fs from "fs-extra"; +import merge from "lodash.merge"; +import { x } from "tinyexec"; +import { ExitCode } from "./cli-error.js"; const require = createRequire(import.meta.url); -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -const bin = require.resolve('../cli.js'); +const bin = require.resolve("../cli.js"); interface TestOptions { cwd: string; @@ -20,7 +20,7 @@ interface TestOptions { } const cli = (args: string[], options: TestOptions) => { - return (input = '') => { + return (input = "") => { const result = x(bin, args, { nodeOptions: { cwd: options.cwd, @@ -38,542 +38,551 @@ const cli = (args: string[], options: TestOptions) => { const gitBootstrap = (fixture: string) => git.bootstrap(fixture, __dirname); const fixBootstrap = (fixture: string) => fix.bootstrap(fixture, __dirname); -test('should throw when called without [input]', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli([], {cwd})(); +test("should throw when called without [input]", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli([], { cwd })(); await result; expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should reprint input from stdin', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli([], {cwd})('foo: bar'); +test("should reprint input from stdin", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli([], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toContain('foo: bar'); + expect(output.stdout.trim()).toContain("foo: bar"); }); -test('should produce success output with --verbose flag', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli(['--verbose'], {cwd})('type: bar'); +test("should produce success output with --verbose flag", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli(["--verbose"], { cwd })("type: bar"); const output = await result; - expect(output.stdout.trim()).toContain('0 problems, 0 warnings'); - expect(output.stderr).toEqual(''); + expect(output.stdout.trim()).toContain("0 problems, 0 warnings"); + expect(output.stderr).toEqual(""); }); -test('should produce last commit and success output with --verbose flag', async () => { - const cwd = await gitBootstrap('fixtures/simple'); - await x('git', ['add', 'commitlint.config.js'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', '"test: this should work"'], { - nodeOptions: {cwd}, +test("should produce last commit and success output with --verbose flag", async () => { + const cwd = await gitBootstrap("fixtures/simple"); + await x("git", ["add", "commitlint.config.js"], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", '"test: this should work"'], { + nodeOptions: { cwd }, }); - const result = cli(['--last', '--verbose'], {cwd})(); + const result = cli(["--last", "--verbose"], { cwd })(); const output = await result; - expect(output.stdout.trim()).toContain('0 problems, 0 warnings'); - expect(output.stdout.trim()).toContain('test: this should work'); - expect(output.stderr).toEqual(''); + expect(output.stdout.trim()).toContain("0 problems, 0 warnings"); + expect(output.stdout.trim()).toContain("test: this should work"); + expect(output.stderr).toEqual(""); }); -test('regression test for running with --last flag', async () => { - const cwd = await gitBootstrap('fixtures/last-flag-regression'); - await x('git', ['add', 'commitlint.config.js'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', '"test: this should work"'], { - nodeOptions: {cwd}, +test("regression test for running with --last flag", async () => { + const cwd = await gitBootstrap("fixtures/last-flag-regression"); + await x("git", ["add", "commitlint.config.js"], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", '"test: this should work"'], { + nodeOptions: { cwd }, }); - const result = cli(['--last', '--verbose'], {cwd})(); + const result = cli(["--last", "--verbose"], { cwd })(); const output = await result; - expect(output.stdout.trim()).toContain('0 problems, 0 warnings'); - expect(output.stdout.trim()).toContain('test: this should work'); - expect(output.stderr).toEqual(''); + expect(output.stdout.trim()).toContain("0 problems, 0 warnings"); + expect(output.stdout.trim()).toContain("test: this should work"); + expect(output.stderr).toEqual(""); }); -test('should produce no output with --quiet flag', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli(['--quiet'], {cwd})('foo: bar'); +test("should produce no output with --quiet flag", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli(["--quiet"], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toEqual(''); - expect(output.stderr).toEqual(''); + expect(output.stdout.trim()).toEqual(""); + expect(output.stderr).toEqual(""); }); -test('should produce no output with -q flag', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli(['-q'], {cwd})('foo: bar'); +test("should produce no output with -q flag", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli(["-q"], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toEqual(''); - expect(output.stderr).toEqual(''); + expect(output.stdout.trim()).toEqual(""); + expect(output.stderr).toEqual(""); }); -test('should produce help for empty config', async () => { - const cwd = await gitBootstrap('fixtures/empty'); - const result = cli([], {cwd})('foo: bar'); +test("should produce help for empty config", async () => { + const cwd = await gitBootstrap("fixtures/empty"); + const result = cli([], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toContain('Please add rules'); + expect(output.stdout.trim()).toContain("Please add rules"); expect(result.exitCode).toBe(ExitCode.CommitlintInvalidArgument); }); -test('should produce help for problems', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli([], {cwd})('foo: bar'); +test("should produce help for problems", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli([], { cwd })("foo: bar"); const output = await result; expect(output.stdout.trim()).toContain( - 'Get help: https://github.com/conventional-changelog/commitlint/#what-is-commitlint' + "Get help: https://github.com/conventional-changelog/commitlint/#what-is-commitlint", ); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should produce help for problems with correct helpurl', async () => { - const cwd = await gitBootstrap('fixtures/default'); +test("should produce help for problems with correct helpurl", async () => { + const cwd = await gitBootstrap("fixtures/default"); const result = cli( - ['-H https://github.com/conventional-changelog/commitlint/#testhelpurl'], - {cwd} - )('foo: bar'); + ["-H https://github.com/conventional-changelog/commitlint/#testhelpurl"], + { cwd }, + )("foo: bar"); const output = await result; expect(output.stdout.trim()).toContain( - 'Get help: https://github.com/conventional-changelog/commitlint/#testhelpurl' + "Get help: https://github.com/conventional-changelog/commitlint/#testhelpurl", ); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should fail for input from stdin without rules', async () => { - const cwd = await gitBootstrap('fixtures/empty'); - const result = cli([], {cwd})('foo: bar'); +test("should fail for input from stdin without rules", async () => { + const cwd = await gitBootstrap("fixtures/empty"); + const result = cli([], { cwd })("foo: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintInvalidArgument); }); -test('should succeed for input from stdin with rules', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli([], {cwd})('type: bar'); +test("should succeed for input from stdin with rules", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli([], { cwd })("type: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should fail for input from stdin with rule from rc', async () => { - const cwd = await gitBootstrap('fixtures/simple'); - const result = cli([], {cwd})('foo: bar'); +test("should fail for input from stdin with rule from rc", async () => { + const cwd = await gitBootstrap("fixtures/simple"); + const result = cli([], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toContain('type must not be one of [foo]'); + expect(output.stdout.trim()).toContain("type must not be one of [foo]"); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should work with --config option', async () => { - const file = 'config/commitlint.config.js'; - const cwd = await gitBootstrap('fixtures/specify-config-file'); - const result = cli(['--config', file], {cwd})('foo: bar'); +test("should work with --config option", async () => { + const file = "config/commitlint.config.js"; + const cwd = await gitBootstrap("fixtures/specify-config-file"); + const result = cli(["--config", file], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toContain('type must not be one of [foo]'); + expect(output.stdout.trim()).toContain("type must not be one of [foo]"); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should fail for input from stdin with rule from js', async () => { - const cwd = await gitBootstrap('fixtures/extends-root'); - const result = cli(['--extends', './extended'], {cwd})('foo: bar'); +test("should fail for input from stdin with rule from js", async () => { + const cwd = await gitBootstrap("fixtures/extends-root"); + const result = cli(["--extends", "./extended"], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toContain('type must not be one of [foo]'); + expect(output.stdout.trim()).toContain("type must not be one of [foo]"); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should output help URL defined in config file', async () => { - const cwd = await gitBootstrap('fixtures/help-url'); - const result = cli([], {cwd})('foo: bar'); +test("should output help URL defined in config file", async () => { + const cwd = await gitBootstrap("fixtures/help-url"); + const result = cli([], { cwd })("foo: bar"); const output = await result; expect(output.stdout.trim()).toContain( - 'Get help: https://www.example.com/foo' + "Get help: https://www.example.com/foo", ); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should produce no error output with --quiet flag', async () => { - const cwd = await gitBootstrap('fixtures/simple'); - const result = cli(['--quiet'], {cwd})('foo: bar'); +test("should produce no error output with --quiet flag", async () => { + const cwd = await gitBootstrap("fixtures/simple"); + const result = cli(["--quiet"], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toEqual(''); - expect(output.stderr).toEqual(''); + expect(output.stdout.trim()).toEqual(""); + expect(output.stderr).toEqual(""); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should produce no error output with -q flag', async () => { - const cwd = await gitBootstrap('fixtures/simple'); - const result = cli(['-q'], {cwd})('foo: bar'); +test("should produce no error output with -q flag", async () => { + const cwd = await gitBootstrap("fixtures/simple"); + const result = cli(["-q"], { cwd })("foo: bar"); const output = await result; - expect(output.stdout.trim()).toEqual(''); - expect(output.stderr).toEqual(''); + expect(output.stdout.trim()).toEqual(""); + expect(output.stderr).toEqual(""); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should work with husky commitmsg hook and git commit', async () => { - const cwd = await gitBootstrap('fixtures/husky/integration'); - await writePkg({husky: {hooks: {'commit-msg': `'${bin}' -e`}}}, {cwd}); +test("should work with husky commitmsg hook and git commit", async () => { + const cwd = await gitBootstrap("fixtures/husky/integration"); + await writePkg( + { husky: { hooks: { "commit-msg": `'${bin}' -e` } } }, + { cwd }, + ); // await x('npm', ['install'], { nodeOptions: {cwd}}); // npm install is failing on windows machines - await x('git', ['add', 'package.json'], {nodeOptions: {cwd}}); - const commit = await x('git', ['commit', '-m', '"test: this should work"'], { - nodeOptions: {cwd}, + await x("git", ["add", "package.json"], { nodeOptions: { cwd } }); + const commit = await x("git", ["commit", "-m", '"test: this should work"'], { + nodeOptions: { cwd }, }); expect(commit).toBeTruthy(); }); -test('should work with husky commitmsg hook in sub packages', async () => { - const upper = await gitBootstrap('fixtures/husky'); - const cwd = path.join(upper, 'integration'); - await writePkg({husky: {hooks: {'commit-msg': `'${bin}' -e`}}}, {cwd: upper}); +test("should work with husky commitmsg hook in sub packages", async () => { + const upper = await gitBootstrap("fixtures/husky"); + const cwd = path.join(upper, "integration"); + await writePkg( + { husky: { hooks: { "commit-msg": `'${bin}' -e` } } }, + { cwd: upper }, + ); // await x('npm', ['install'], { nodeOptions: {cwd}}); // npm install is failing on windows machines - await x('git', ['add', 'package.json'], {nodeOptions: {cwd}}); - const commit = await x('git', ['commit', '-m', '"test: this should work"'], { - nodeOptions: {cwd}, + await x("git", ["add", "package.json"], { nodeOptions: { cwd } }); + const commit = await x("git", ["commit", "-m", '"test: this should work"'], { + nodeOptions: { cwd }, }); expect(commit).toBeTruthy(); }); -test('should work with husky via commitlint -e $GIT_PARAMS', async () => { - const cwd = await gitBootstrap('fixtures/husky/integration'); +test("should work with husky via commitlint -e $GIT_PARAMS", async () => { + const cwd = await gitBootstrap("fixtures/husky/integration"); await writePkg( - {husky: {hooks: {'commit-msg': `'${bin}' -e $GIT_PARAMS`}}}, - {cwd} + { husky: { hooks: { "commit-msg": `'${bin}' -e $GIT_PARAMS` } } }, + { cwd }, ); // await x('npm', ['install'], { nodeOptions: {cwd}}); // npm install is failing on windows machines - await x('git', ['add', 'package.json'], {nodeOptions: {cwd}}); - const commit = await x('git', ['commit', '-m', '"test: this should work"'], { - nodeOptions: {cwd}, + await x("git", ["add", "package.json"], { nodeOptions: { cwd } }); + const commit = await x("git", ["commit", "-m", '"test: this should work"'], { + nodeOptions: { cwd }, }); expect(commit).toBeTruthy(); }); -test('should work with husky via commitlint -e %GIT_PARAMS%', async () => { - const cwd = await gitBootstrap('fixtures/husky/integration'); +test("should work with husky via commitlint -e %GIT_PARAMS%", async () => { + const cwd = await gitBootstrap("fixtures/husky/integration"); await writePkg( - {husky: {hooks: {'commit-msg': `'${bin}' -e %GIT_PARAMS%`}}}, - {cwd} + { husky: { hooks: { "commit-msg": `'${bin}' -e %GIT_PARAMS%` } } }, + { cwd }, ); // await x('npm', ['install'], { nodeOptions: {cwd}}); // npm install is failing on windows machines - await x('git', ['add', 'package.json'], {nodeOptions: {cwd}}); - const commit = await x('git', ['commit', '-m', '"test: this should work"'], { - nodeOptions: {cwd}, + await x("git", ["add", "package.json"], { nodeOptions: { cwd } }); + const commit = await x("git", ["commit", "-m", '"test: this should work"'], { + nodeOptions: { cwd }, }); expect(commit).toBeTruthy(); }); -test('should work with husky via commitlint -e $HUSKY_GIT_PARAMS', async () => { - const cwd = await gitBootstrap('fixtures/husky/integration'); +test("should work with husky via commitlint -e $HUSKY_GIT_PARAMS", async () => { + const cwd = await gitBootstrap("fixtures/husky/integration"); await writePkg( - {husky: {hooks: {'commit-msg': `'${bin}' -e $HUSKY_GIT_PARAMS`}}}, - {cwd} + { husky: { hooks: { "commit-msg": `'${bin}' -e $HUSKY_GIT_PARAMS` } } }, + { cwd }, ); // await x('npm', ['install'], { nodeOptions: {cwd}}); // npm install is failing on windows machines - await x('git', ['add', 'package.json'], {nodeOptions: {cwd}}); - const commit = await x('git', ['commit', '-m', '"test: this should work"'], { - nodeOptions: {cwd}, + await x("git", ["add", "package.json"], { nodeOptions: { cwd } }); + const commit = await x("git", ["commit", "-m", '"test: this should work"'], { + nodeOptions: { cwd }, }); expect(commit).toBeTruthy(); }); -test('should work with husky via commitlint -e %HUSKY_GIT_PARAMS%', async () => { - const cwd = await gitBootstrap('fixtures/husky/integration'); +test("should work with husky via commitlint -e %HUSKY_GIT_PARAMS%", async () => { + const cwd = await gitBootstrap("fixtures/husky/integration"); await writePkg( - {husky: {hooks: {'commit-msg': `'${bin}' -e %HUSKY_GIT_PARAMS%`}}}, - {cwd} + { husky: { hooks: { "commit-msg": `'${bin}' -e %HUSKY_GIT_PARAMS%` } } }, + { cwd }, ); // await x('npm', ['install'], { nodeOptions: {cwd}}); // npm install is failing on windows machines - await x('git', ['add', 'package.json'], {nodeOptions: {cwd}}); - const commit = await x('git', ['commit', '-m', '"test: this should work"'], { - nodeOptions: {cwd}, + await x("git", ["add", "package.json"], { nodeOptions: { cwd } }); + const commit = await x("git", ["commit", "-m", '"test: this should work"'], { + nodeOptions: { cwd }, }); expect(commit).toBeTruthy(); }); -test('should allow reading of environment variables for edit file, succeeding if valid', async () => { - const cwd = await gitBootstrap('fixtures/simple'); - await fs.writeFile(path.join(cwd, 'commit-msg-file'), 'foo'); - const result = cli(['--env', 'variable'], { +test("should allow reading of environment variables for edit file, succeeding if valid", async () => { + const cwd = await gitBootstrap("fixtures/simple"); + await fs.writeFile(path.join(cwd, "commit-msg-file"), "foo"); + const result = cli(["--env", "variable"], { cwd, - env: {variable: 'commit-msg-file'}, + env: { variable: "commit-msg-file" }, })(); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should allow reading of environment variables for edit file, failing if invalid', async () => { - const cwd = await gitBootstrap('fixtures/simple'); +test("should allow reading of environment variables for edit file, failing if invalid", async () => { + const cwd = await gitBootstrap("fixtures/simple"); await fs.writeFile( - path.join(cwd, 'commit-msg-file'), - 'foo: bar\n\nFoo bar bizz buzz.\n\nCloses #123.' + path.join(cwd, "commit-msg-file"), + "foo: bar\n\nFoo bar bizz buzz.\n\nCloses #123.", ); - const result = cli(['--env', 'variable'], { + const result = cli(["--env", "variable"], { cwd, - env: {variable: 'commit-msg-file'}, + env: { variable: "commit-msg-file" }, })(); await result; expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should pick up parser preset and fail accordingly', async () => { - const cwd = await gitBootstrap('fixtures/parser-preset'); - const result = cli(['--parser-preset', './parser-preset'], {cwd})( - 'type(scope): subject' +test("should pick up parser preset and fail accordingly", async () => { + const cwd = await gitBootstrap("fixtures/parser-preset"); + const result = cli(["--parser-preset", "./parser-preset"], { cwd })( + "type(scope): subject", ); const output = await result; - expect(output.stdout.trim()).toContain('may not be empty'); + expect(output.stdout.trim()).toContain("may not be empty"); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should pick up parser preset and succeed accordingly', async () => { - const cwd = await gitBootstrap('fixtures/parser-preset'); - const result = cli(['--parser-preset', './parser-preset'], {cwd})( - '----type(scope): subject' +test("should pick up parser preset and succeed accordingly", async () => { + const cwd = await gitBootstrap("fixtures/parser-preset"); + const result = cli(["--parser-preset", "./parser-preset"], { cwd })( + "----type(scope): subject", ); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should pick up config from outside git repo and fail accordingly', async () => { - const outer = await fixBootstrap('fixtures/outer-scope'); - const cwd = await git.init(path.join(outer, 'inner-scope')); +test("should pick up config from outside git repo and fail accordingly", async () => { + const outer = await fixBootstrap("fixtures/outer-scope"); + const cwd = await git.init(path.join(outer, "inner-scope")); - const result = cli([], {cwd})('inner: bar'); + const result = cli([], { cwd })("inner: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should pick up config from outside git repo and succeed accordingly', async () => { - const outer = await fixBootstrap('fixtures/outer-scope'); - const cwd = await git.init(path.join(outer, 'inner-scope')); +test("should pick up config from outside git repo and succeed accordingly", async () => { + const outer = await fixBootstrap("fixtures/outer-scope"); + const cwd = await git.init(path.join(outer, "inner-scope")); - const result = cli([], {cwd})('outer: bar'); + const result = cli([], { cwd })("outer: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should pick up config from inside git repo with precedence and succeed accordingly', async () => { - const outer = await fixBootstrap('fixtures/inner-scope'); - const cwd = await git.init(path.join(outer, 'inner-scope')); +test("should pick up config from inside git repo with precedence and succeed accordingly", async () => { + const outer = await fixBootstrap("fixtures/inner-scope"); + const cwd = await git.init(path.join(outer, "inner-scope")); - const result = cli([], {cwd})('inner: bar'); + const result = cli([], { cwd })("inner: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should pick up config from inside git repo with precedence and fail accordingly', async () => { - const outer = await fixBootstrap('fixtures/inner-scope'); - const cwd = await git.init(path.join(outer, 'inner-scope')); +test("should pick up config from inside git repo with precedence and fail accordingly", async () => { + const outer = await fixBootstrap("fixtures/inner-scope"); + const cwd = await git.init(path.join(outer, "inner-scope")); - const result = cli([], {cwd})('outer: bar'); + const result = cli([], { cwd })("outer: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should handle --amend with signoff', async () => { - const cwd = await gitBootstrap('fixtures/signoff'); - await writePkg({husky: {hooks: {'commit-msg': `'${bin}' -e`}}}, {cwd}); +test("should handle --amend with signoff", async () => { + const cwd = await gitBootstrap("fixtures/signoff"); + await writePkg( + { husky: { hooks: { "commit-msg": `'${bin}' -e` } } }, + { cwd }, + ); // await x('npm', ['install'], { nodeOptions: {cwd}}); // npm install is failing on windows machines - await x('git', ['add', 'package.json'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', '"test: this should work"', '--signoff'], { - nodeOptions: {cwd}, + await x("git", ["add", "package.json"], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", '"test: this should work"', "--signoff"], { + nodeOptions: { cwd }, }); - const commit = await x('git', ['commit', '--amend', '--no-edit'], { - nodeOptions: {cwd}, + const commit = await x("git", ["commit", "--amend", "--no-edit"], { + nodeOptions: { cwd }, }); expect(commit).toBeTruthy(); }, 10000); -test('it uses parserOpts.commentChar when not using edit mode', async () => { - const cwd = await gitBootstrap('fixtures/comment-char'); - const input = 'header: foo\n$body\n'; +test("it uses parserOpts.commentChar when not using edit mode", async () => { + const cwd = await gitBootstrap("fixtures/comment-char"); + const input = "header: foo\n$body\n"; - const result = cli([], {cwd})(input); + const result = cli([], { cwd })(input); const output = await result; - expect(output.stdout.trim()).toContain('[body-empty]'); + expect(output.stdout.trim()).toContain("[body-empty]"); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); test("it doesn't use parserOpts.commentChar when using edit mode", async () => { - const cwd = await gitBootstrap('fixtures/comment-char'); + const cwd = await gitBootstrap("fixtures/comment-char"); await fs.writeFile( - path.join(cwd, '.git', 'COMMIT_EDITMSG'), - 'header: foo\n\n$body\n' + path.join(cwd, ".git", "COMMIT_EDITMSG"), + "header: foo\n\n$body\n", ); - const result = cli(['--edit', '.git/COMMIT_EDITMSG'], {cwd})(); + const result = cli(["--edit", ".git/COMMIT_EDITMSG"], { cwd })(); const output = await result; - expect(output.stdout.trim()).not.toContain('[body-empty]'); + expect(output.stdout.trim()).not.toContain("[body-empty]"); expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('it uses core.commentChar git config when using edit mode', async () => { - const cwd = await gitBootstrap('fixtures/comment-char'); - await x('git', ['config', '--local', 'core.commentChar', '$'], { - nodeOptions: {cwd}, +test("it uses core.commentChar git config when using edit mode", async () => { + const cwd = await gitBootstrap("fixtures/comment-char"); + await x("git", ["config", "--local", "core.commentChar", "$"], { + nodeOptions: { cwd }, }); await fs.writeFile( - path.join(cwd, '.git', 'COMMIT_EDITMSG'), - 'header: foo\n\n$body\n' + path.join(cwd, ".git", "COMMIT_EDITMSG"), + "header: foo\n\n$body\n", ); - const result = cli(['--edit', '.git/COMMIT_EDITMSG'], {cwd})(); + const result = cli(["--edit", ".git/COMMIT_EDITMSG"], { cwd })(); const output = await result; - expect(output.stdout.trim()).toContain('[body-empty]'); + expect(output.stdout.trim()).toContain("[body-empty]"); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('it falls back to # for core.commentChar when using edit mode', async () => { - const cwd = await gitBootstrap('fixtures/comment-char'); +test("it falls back to # for core.commentChar when using edit mode", async () => { + const cwd = await gitBootstrap("fixtures/comment-char"); await fs.writeFile( - path.join(cwd, '.git', 'COMMIT_EDITMSG'), - 'header: foo\n\n#body\n' + path.join(cwd, ".git", "COMMIT_EDITMSG"), + "header: foo\n\n#body\n", ); - const result = cli(['--edit', '.git/COMMIT_EDITMSG'], {cwd})(); + const result = cli(["--edit", ".git/COMMIT_EDITMSG"], { cwd })(); const output = await result; - expect(output.stdout.trim()).toContain('[body-empty]'); - expect(output.stderr).toEqual(''); + expect(output.stdout.trim()).toContain("[body-empty]"); + expect(output.stderr).toEqual(""); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should handle linting with issue prefixes', async () => { - const cwd = await gitBootstrap('fixtures/issue-prefixes'); - const result = cli([], {cwd})('foobar REF-1'); +test("should handle linting with issue prefixes", async () => { + const cwd = await gitBootstrap("fixtures/issue-prefixes"); + const result = cli([], { cwd })("foobar REF-1"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }, 10000); -test('should print full commit message when input from stdin fails', async () => { - const cwd = await gitBootstrap('fixtures/simple'); - const input = 'foo: bar\n\nFoo bar bizz buzz.\n\nCloses #123.'; +test("should print full commit message when input from stdin fails", async () => { + const cwd = await gitBootstrap("fixtures/simple"); + const input = "foo: bar\n\nFoo bar bizz buzz.\n\nCloses #123."; // output text in plain text so we can compare it - const result = cli(['--color=false'], {cwd})(input); + const result = cli(["--color=false"], { cwd })(input); const output = await result; expect(output.stdout.trim()).toContain(input); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should not print commit message fully or partially when input succeeds', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const message = 'type: bar\n\nFoo bar bizz buzz.\n\nCloses #123.'; +test("should not print commit message fully or partially when input succeeds", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const message = "type: bar\n\nFoo bar bizz buzz.\n\nCloses #123."; // output text in plain text so we can compare it - const result = cli(['--color=false'], {cwd})(message); + const result = cli(["--color=false"], { cwd })(message); const output = await result; expect(output.stdout.trim()).not.toContain(message); - expect(output.stdout.trim()).not.toContain(message.split('\n')[0]); + expect(output.stdout.trim()).not.toContain(message.split("\n")[0]); expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should fail for invalid formatters from configuration', async () => { - const cwd = await gitBootstrap('fixtures/custom-formatter'); - const result = cli([], {cwd})('foo: bar'); +test("should fail for invalid formatters from configuration", async () => { + const cwd = await gitBootstrap("fixtures/custom-formatter"); + const result = cli([], { cwd })("foo: bar"); const output = await result; expect(output.stderr).toContain( - 'Using format custom-formatter, but cannot find the module' + "Using format custom-formatter, but cannot find the module", ); - expect(output.stdout.trim()).toEqual(''); + expect(output.stdout.trim()).toEqual(""); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should skip linting if message matches ignores config', async () => { - const cwd = await gitBootstrap('fixtures/ignores'); - const result = cli([], {cwd})('WIP'); +test("should skip linting if message matches ignores config", async () => { + const cwd = await gitBootstrap("fixtures/ignores"); + const result = cli([], { cwd })("WIP"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should not skip linting if message does not match ignores config', async () => { - const cwd = await gitBootstrap('fixtures/ignores'); - const result = cli([], {cwd})('foo'); +test("should not skip linting if message does not match ignores config", async () => { + const cwd = await gitBootstrap("fixtures/ignores"); + const result = cli([], { cwd })("foo"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should not skip linting if defaultIgnores is false', async () => { - const cwd = await gitBootstrap('fixtures/default-ignores-false'); - const result = cli([], {cwd})('fixup! foo: bar'); +test("should not skip linting if defaultIgnores is false", async () => { + const cwd = await gitBootstrap("fixtures/default-ignores-false"); + const result = cli([], { cwd })("fixup! foo: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should skip linting if defaultIgnores is true', async () => { - const cwd = await gitBootstrap('fixtures/default-ignores-true'); - const result = cli([], {cwd})('fixup! foo: bar'); +test("should skip linting if defaultIgnores is true", async () => { + const cwd = await gitBootstrap("fixtures/default-ignores-true"); + const result = cli([], { cwd })("fixup! foo: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should skip linting if defaultIgnores is unset', async () => { - const cwd = await gitBootstrap('fixtures/default-ignores-unset'); - const result = cli([], {cwd})('fixup! foo: bar'); +test("should skip linting if defaultIgnores is unset", async () => { + const cwd = await gitBootstrap("fixtures/default-ignores-unset"); + const result = cli([], { cwd })("fixup! foo: bar"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should fail for invalid formatters from flags', async () => { - const cwd = await gitBootstrap('fixtures/custom-formatter'); - const result = cli(['--format', 'through-flag'], {cwd})('foo: bar'); +test("should fail for invalid formatters from flags", async () => { + const cwd = await gitBootstrap("fixtures/custom-formatter"); + const result = cli(["--format", "through-flag"], { cwd })("foo: bar"); const output = await result; expect(output.stderr).toContain( - 'Using format through-flag, but cannot find the module' + "Using format through-flag, but cannot find the module", ); - expect(output.stdout.trim()).toEqual(''); + expect(output.stdout.trim()).toEqual(""); expect(result.exitCode).toBe(ExitCode.CommitlintErrorDefault); }); -test('should work with absolute formatter path', async () => { +test("should work with absolute formatter path", async () => { const formatterPath = path.resolve( __dirname, - '../fixtures/custom-formatter/formatters/custom.js' + "../fixtures/custom-formatter/formatters/custom.js", ); - const cwd = await gitBootstrap('fixtures/custom-formatter'); - const result = cli(['--format', formatterPath], {cwd})( - 'test: this should work' + const cwd = await gitBootstrap("fixtures/custom-formatter"); + const result = cli(["--format", formatterPath], { cwd })( + "test: this should work", ); const output = await result; - expect(output.stdout.trim()).toContain('custom-formatter-ok'); + expect(output.stdout.trim()).toContain("custom-formatter-ok"); expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should work with relative formatter path', async () => { +test("should work with relative formatter path", async () => { const cwd = path.resolve( - await gitBootstrap('fixtures/custom-formatter'), - './formatters' + await gitBootstrap("fixtures/custom-formatter"), + "./formatters", ); - const result = cli(['--format', './custom.js'], {cwd})( - 'test: this should work' + const result = cli(["--format", "./custom.js"], { cwd })( + "test: this should work", ); const output = await result; - expect(output.stdout.trim()).toContain('custom-formatter-ok'); + expect(output.stdout.trim()).toContain("custom-formatter-ok"); expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('strict: should exit with 3 on error', async () => { - const cwd = await gitBootstrap('fixtures/warning'); - const result = cli(['--strict'], {cwd})('foo: abcdef'); +test("strict: should exit with 3 on error", async () => { + const cwd = await gitBootstrap("fixtures/warning"); + const result = cli(["--strict"], { cwd })("foo: abcdef"); await result; expect(result.exitCode).toBe(ExitCode.CommitLintError); }); -test('strict: should exit with 2 on warning', async () => { - const cwd = await gitBootstrap('fixtures/warning'); - const result = cli(['--strict'], {cwd})('feat: abcdef'); +test("strict: should exit with 2 on warning", async () => { + const cwd = await gitBootstrap("fixtures/warning"); + const result = cli(["--strict"], { cwd })("feat: abcdef"); await result; expect(result.exitCode).toBe(ExitCode.CommitLintWarning); }); -test('strict: should exit with 0 on success', async () => { - const cwd = await gitBootstrap('fixtures/warning'); - const result = cli(['--strict'], {cwd})('feat: abc'); +test("strict: should exit with 0 on success", async () => { + const cwd = await gitBootstrap("fixtures/warning"); + const result = cli(["--strict"], { cwd })("feat: abc"); await result; expect(result.exitCode).toBe(ExitCode.CommitlintDefault); }); -test('should print help', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli(['--help'], {cwd})(); +test("should print help", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli(["--help"], { cwd })(); const output = await result; - const version = require('../package.json').version; - const stdout = output.stdout.trim().replace(`@${version}`, '@dev'); + const version = require("../package.json").version; + const stdout = output.stdout.trim().replace(`@${version}`, "@dev"); expect(stdout).toMatchInlineSnapshot(` "@commitlint/cli@dev - Lint your commit messages @@ -604,23 +613,23 @@ test('should print help', async () => { `); }); -test('should print version', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli(['--version'], {cwd})(); +test("should print version", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli(["--version"], { cwd })(); const output = await result; - expect(output.stdout.trim()).toMatch('@commitlint/cli@'); + expect(output.stdout.trim()).toMatch("@commitlint/cli@"); }); -describe('should print config', () => { - test('should print config when flag is present but without value', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli(['--print-config', 'text', '--no-color'], {cwd})(); +describe("should print config", () => { + test("should print config when flag is present but without value", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli(["--print-config", "text", "--no-color"], { cwd })(); const output = await result; const stdout = output.stdout .trim() - .replace(/^{[^\n]/g, '{\n ') - .replace(/[^\n]}$/g, '\n}') - .replace(/(helpUrl:)\n[ ]+/, '$1 '); + .replace(/^{[^\n]/g, "{\n ") + .replace(/[^\n]}$/g, "\n}") + .replace(/(helpUrl:)\n[ ]+/, "$1 "); expect(stdout).toMatchInlineSnapshot(` "{ extends: [], @@ -636,15 +645,15 @@ describe('should print config', () => { `); }); - test('should print config when flag has `text` value', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli(['--print-config=text', '--no-color'], {cwd})(); + test("should print config when flag has `text` value", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli(["--print-config=text", "--no-color"], { cwd })(); const output = await result; const stdout = output.stdout .trim() - .replace(/^{[^\n]/g, '{\n ') - .replace(/[^\n]}$/g, '\n}') - .replace(/(helpUrl:)\n[ ]+/, '$1 '); + .replace(/^{[^\n]/g, "{\n ") + .replace(/[^\n]}$/g, "\n}") + .replace(/(helpUrl:)\n[ ]+/, "$1 "); expect(stdout).toMatchInlineSnapshot(` "{ extends: [], @@ -660,19 +669,19 @@ describe('should print config', () => { `); }); - test('should print config when flag has `json` value', async () => { - const cwd = await gitBootstrap('fixtures/default'); - const result = cli(['--print-config=json', '--no-color'], {cwd})(); + test("should print config when flag has `json` value", async () => { + const cwd = await gitBootstrap("fixtures/default"); + const result = cli(["--print-config=json", "--no-color"], { cwd })(); const output = await result; expect(output.stdout.trim()).toMatchInlineSnapshot( - `"{"extends":[],"formatter":"@commitlint/format","plugins":{},"rules":{"type-enum":[2,"never",["foo"]]},"helpUrl":"https://github.com/conventional-changelog/commitlint/#what-is-commitlint","prompt":{}}"` + `"{"extends":[],"formatter":"@commitlint/format","plugins":{},"rules":{"type-enum":[2,"never",["foo"]]},"helpUrl":"https://github.com/conventional-changelog/commitlint/#what-is-commitlint","prompt":{}}"`, ); }); }); async function writePkg(payload: unknown, options: TestOptions) { - const pkgPath = path.join(options.cwd, 'package.json'); - const pkg = JSON.parse(await fs.readFile(pkgPath, 'utf-8')); + const pkgPath = path.join(options.cwd, "package.json"); + const pkg = JSON.parse(await fs.readFile(pkgPath, "utf-8")); const result = merge(pkg, payload); - await fs.writeFile(pkgPath, JSON.stringify(result, null, ' ')); + await fs.writeFile(pkgPath, JSON.stringify(result, null, " ")); } diff --git a/@commitlint/cli/src/cli.ts b/@commitlint/cli/src/cli.ts index bce45db4e3..50cfed53f9 100644 --- a/@commitlint/cli/src/cli.ts +++ b/@commitlint/cli/src/cli.ts @@ -1,11 +1,11 @@ -import {createRequire} from 'node:module'; -import path from 'node:path'; -import {fileURLToPath, pathToFileURL} from 'node:url'; -import util from 'node:util'; - -import lint from '@commitlint/lint'; -import load, {resolveFromSilent, resolveGlobalSilent} from '@commitlint/load'; -import read from '@commitlint/read'; +import { createRequire } from "node:module"; +import path from "node:path"; +import { fileURLToPath, pathToFileURL } from "node:url"; +import util from "node:util"; + +import lint from "@commitlint/lint"; +import load, { resolveFromSilent, resolveGlobalSilent } from "@commitlint/load"; +import read from "@commitlint/read"; import type { Formatter, LintOptions, @@ -13,150 +13,150 @@ import type { ParserPreset, QualifiedConfig, UserConfig, -} from '@commitlint/types'; -import type {Options} from 'conventional-commits-parser'; -import {x} from 'tinyexec'; -import yargs, {type Arguments} from 'yargs'; +} from "@commitlint/types"; +import type { Options } from "conventional-commits-parser"; +import { x } from "tinyexec"; +import yargs, { type Arguments } from "yargs"; -import {CliFlags} from './types.js'; +import { CliFlags } from "./types.js"; -import {CliError, ExitCode} from './cli-error.js'; +import { CliError, ExitCode } from "./cli-error.js"; const require = createRequire(import.meta.url); -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); const dynamicImport = async <T>(id: string): Promise<T> => { const imported = await import( path.isAbsolute(id) ? pathToFileURL(id).toString() : id ); - return ('default' in imported && imported.default) || imported; + return ("default" in imported && imported.default) || imported; }; -const pkg: typeof import('../package.json') = require('../package.json'); +const pkg: typeof import("../package.json") = require("../package.json"); -const gitDefaultCommentChar = '#'; +const gitDefaultCommentChar = "#"; const cli = yargs(process.argv.slice(2)) .options({ color: { - alias: 'c', + alias: "c", default: true, - description: 'toggle colored output', - type: 'boolean', + description: "toggle colored output", + type: "boolean", }, config: { - alias: 'g', + alias: "g", description: - 'path to the config file; result code 9 if config is missing', - type: 'string', + "path to the config file; result code 9 if config is missing", + type: "string", }, - 'print-config': { - choices: ['', 'text', 'json'], - description: 'print resolved config', - type: 'string', + "print-config": { + choices: ["", "text", "json"], + description: "print resolved config", + type: "string", }, cwd: { - alias: 'd', + alias: "d", default: process.cwd(), - defaultDescription: '(Working Directory)', - description: 'directory to execute in', - type: 'string', + defaultDescription: "(Working Directory)", + description: "directory to execute in", + type: "string", }, edit: { - alias: 'e', + alias: "e", description: - 'read last commit message from the specified file or fallbacks to ./.git/COMMIT_EDITMSG', - type: 'string', + "read last commit message from the specified file or fallbacks to ./.git/COMMIT_EDITMSG", + type: "string", }, env: { - alias: 'E', + alias: "E", description: - 'check message in the file at path given by environment variable value', - type: 'string', + "check message in the file at path given by environment variable value", + type: "string", }, extends: { - alias: 'x', - description: 'array of shareable configurations to extend', - type: 'array', + alias: "x", + description: "array of shareable configurations to extend", + type: "array", }, - 'help-url': { - alias: 'H', - type: 'string', - description: 'help url in error message', + "help-url": { + alias: "H", + type: "string", + description: "help url in error message", }, from: { - alias: 'f', + alias: "f", description: - 'lower end of the commit range to lint; applies if edit=false', - type: 'string', + "lower end of the commit range to lint; applies if edit=false", + type: "string", }, - 'from-last-tag': { + "from-last-tag": { description: - 'uses the last tag as the lower end of the commit range to lint; applies if edit=false and from is not set', - type: 'boolean', + "uses the last tag as the lower end of the commit range to lint; applies if edit=false and from is not set", + type: "boolean", }, - 'git-log-args': { + "git-log-args": { description: "additional git log arguments as space separated string, example '--first-parent --cherry-pick'", - type: 'string', + type: "string", }, last: { - alias: 'l', - description: 'just analyze the last commit; applies if edit=false', - type: 'boolean', + alias: "l", + description: "just analyze the last commit; applies if edit=false", + type: "boolean", }, format: { - alias: 'o', - description: 'output format of the results', - type: 'string', + alias: "o", + description: "output format of the results", + type: "string", }, - 'parser-preset': { - alias: 'p', + "parser-preset": { + alias: "p", description: - 'configuration preset to use for conventional-commits-parser', - type: 'string', + "configuration preset to use for conventional-commits-parser", + type: "string", }, quiet: { - alias: 'q', + alias: "q", default: false, - description: 'toggle console output', - type: 'boolean', + description: "toggle console output", + type: "boolean", }, to: { - alias: 't', + alias: "t", description: - 'upper end of the commit range to lint; applies if edit=false', - type: 'string', + "upper end of the commit range to lint; applies if edit=false", + type: "string", }, verbose: { - alias: 'V', - type: 'boolean', - description: 'enable verbose output for reports without problems', + alias: "V", + type: "boolean", + description: "enable verbose output for reports without problems", }, strict: { - alias: 's', - type: 'boolean', + alias: "s", + type: "boolean", description: - 'enable strict mode; result code 2 for warnings, 3 for errors', + "enable strict mode; result code 2 for warnings, 3 for errors", }, }) .version( - 'version', - 'display version information', - `${pkg.name}@${pkg.version}` + "version", + "display version information", + `${pkg.name}@${pkg.version}`, ) - .alias('v', 'version') - .help('help') - .alias('h', 'help') + .alias("v", "version") + .help("help") + .alias("h", "help") .config( - 'options', - 'path to a JSON file or Common.js module containing CLI options', - require + "options", + "path to a JSON file or Common.js module containing CLI options", + require, ) .usage(`${pkg.name}@${pkg.version} - ${pkg.description}\n`) .usage( - `[input] reads from stdin if --edit, --env, --from and --to are omitted` + `[input] reads from stdin if --edit, --env, --from and --to are omitted`, ) .strict(); @@ -176,13 +176,13 @@ main(cli.argv).catch((err) => { }); async function stdin() { - let result = ''; + let result = ""; if (process.stdin.isTTY) { return result; } - process.stdin.setEncoding('utf8'); + process.stdin.setEncoding("utf8"); for await (const chunk of process.stdin) { result += chunk; @@ -198,30 +198,30 @@ type MainArgsPromise = Promise<MainArgsObject>; type MainArgs = MainArgsObject | MainArgsPromise; async function resolveArgs(args: MainArgs): Promise<MainArgsObject> { - return typeof args.then === 'function' ? await args : args; + return typeof args.then === "function" ? await args : args; } async function main(args: MainArgs): Promise<void> { const options = await resolveArgs(args); - if (typeof options.edit === 'undefined') { + if (typeof options.edit === "undefined") { options.edit = false; } const raw = options._; const flags = normalizeFlags(options); - if (typeof options['print-config'] === 'string') { + if (typeof options["print-config"] === "string") { const loaded = await load(getSeed(flags), { cwd: flags.cwd, file: flags.config, }); - switch (options['print-config']) { - case 'json': + switch (options["print-config"]) { + case "json": console.log(JSON.stringify(loaded)); return; - case 'text': + case "text": default: console.log(util.inspect(loaded, false, null, options.color)); return; @@ -231,14 +231,14 @@ async function main(args: MainArgs): Promise<void> { const fromStdin = checkFromStdin(raw, flags); if ( - Object.hasOwn(flags, 'last') && - (Object.hasOwn(flags, 'from') || Object.hasOwn(flags, 'to') || flags.edit) + Object.hasOwn(flags, "last") && + (Object.hasOwn(flags, "from") || Object.hasOwn(flags, "to") || flags.edit) ) { const err = new CliError( - 'Please use the --last flag alone. The --last flag should not be used with --to or --from or --edit.', - pkg.name + "Please use the --last flag alone. The --last flag should not be used with --to or --from or --edit.", + pkg.name, ); - cli.showHelp('log'); + cli.showHelp("log"); console.log(err.message); throw err; } @@ -248,24 +248,24 @@ async function main(args: MainArgs): Promise<void> { : read({ to: flags.to, from: flags.from, - fromLastTag: flags['from-last-tag'], + fromLastTag: flags["from-last-tag"], last: flags.last, edit: flags.edit, cwd: flags.cwd, - gitLogArgs: flags['git-log-args'], - })); + gitLogArgs: flags["git-log-args"], + })); const messages = (Array.isArray(input) ? input : [input]) - .filter((message) => typeof message === 'string') - .filter((message) => message.trim() !== '') + .filter((message) => typeof message === "string") + .filter((message) => message.trim() !== "") .filter(Boolean); if (messages.length === 0 && !checkFromRepository(flags)) { const err = new CliError( - '[input] is required: supply via stdin, or --env or --edit or --last or --from and --to', - pkg.name + "[input] is required: supply via stdin, or --env or --edit or --last or --from and --to", + pkg.name, ); - cli.showHelp('log'); + cli.showHelp("log"); console.log(err.message); throw err; } @@ -275,7 +275,7 @@ async function main(args: MainArgs): Promise<void> { file: flags.config, }); const parserOpts = selectParserOpts(loaded.parserPreset); - const opts: LintOptions & {parserOpts: Options} = { + const opts: LintOptions & { parserOpts: Options } = { parserOpts: {}, plugins: {}, ignores: [], @@ -298,13 +298,13 @@ async function main(args: MainArgs): Promise<void> { // If reading from `.git/COMMIT_EDIT_MSG`, strip comments using // core.commentChar from git configuration, falling back to '#'. if (flags.edit) { - const result = x('git', ['config', 'core.commentChar']); + const result = x("git", ["config", "core.commentChar"]); const output = await result; if (result.exitCode && result.exitCode > 1) { console.warn( - 'Could not determine core.commentChar git configuration', - output.stderr + "Could not determine core.commentChar git configuration", + output.stderr, ); opts.parserOpts.commentChar = gitDefaultCommentChar; } else { @@ -314,12 +314,12 @@ async function main(args: MainArgs): Promise<void> { } const results = await Promise.all( - messages.map((message) => lint(message, loaded.rules, opts)) + messages.map((message) => lint(message, loaded.rules, opts)), ); let isRulesEmpty = false; if (Object.keys(loaded.rules).length === 0) { - let input = ''; + let input = ""; if (results.length !== 0) { input = results[0].input; @@ -331,12 +331,12 @@ async function main(args: MainArgs): Promise<void> { { level: 2, valid: false, - name: 'empty-rules', + name: "empty-rules", message: [ - 'Please add rules to your `commitlint.config.js`', - ' - Getting started guide: https://commitlint.js.org/guides/getting-started', - ' - Example config: https://github.com/conventional-changelog/commitlint/blob/master/%40commitlint/config-conventional/src/index.ts', - ].join('\n'), + "Please add rules to your `commitlint.config.js`", + " - Getting started guide: https://commitlint.js.org/guides/getting-started", + " - Example config: https://github.com/conventional-changelog/commitlint/blob/master/%40commitlint/config-conventional/src/index.ts", + ].join("\n"), }, ], warnings: [], @@ -365,10 +365,10 @@ async function main(args: MainArgs): Promise<void> { errorCount: 0, warningCount: 0, results: [], - } + }, ); - const helpUrl = flags['help-url']?.trim() || loaded.helpUrl; + const helpUrl = flags["help-url"]?.trim() || loaded.helpUrl; const output = format(report, { color: flags.color, @@ -376,7 +376,7 @@ async function main(args: MainArgs): Promise<void> { helpUrl, }); - if (!flags.quiet && output !== '') { + if (!flags.quiet && output !== "") { console.log(output); } @@ -410,10 +410,10 @@ function checkFromEdit(flags: CliFlags): boolean { function checkFromHistory(flags: CliFlags): boolean { return ( - typeof flags.from === 'string' || - typeof flags['from-last-tag'] === 'boolean' || - typeof flags.to === 'string' || - typeof flags.last === 'boolean' + typeof flags.from === "string" || + typeof flags["from-last-tag"] === "boolean" || + typeof flags.to === "string" || + typeof flags.last === "boolean" ); } @@ -429,18 +429,18 @@ function getEditValue(flags: CliFlags) { if (flags.env) { if (!(flags.env in process.env)) { throw new Error( - `Received '${flags.env}' as value for -E | --env, but environment variable '${flags.env}' is not available globally` + `Received '${flags.env}' as value for -E | --env, but environment variable '${flags.env}' is not available globally`, ); } return process.env[flags.env]; } - const {edit} = flags; + const { edit } = flags; // If the edit flag is set but empty (i.e '-e') we default // to .git/COMMIT_EDITMSG - if (edit === '') { + if (edit === "") { return true; } - if (typeof edit === 'boolean') { + if (typeof edit === "boolean") { return edit; } // The recommended method to specify -e with husky was `commitlint -e $HUSKY_GIT_PARAMS` @@ -448,22 +448,22 @@ function getEditValue(flags: CliFlags) { // use a different syntax // See https://github.com/conventional-changelog/commitlint/issues/103 for details // This has been superceded by the `-E GIT_PARAMS` / `-E HUSKY_GIT_PARAMS` - const isGitParams = edit === '$GIT_PARAMS' || edit === '%GIT_PARAMS%'; + const isGitParams = edit === "$GIT_PARAMS" || edit === "%GIT_PARAMS%"; const isHuskyParams = - edit === '$HUSKY_GIT_PARAMS' || edit === '%HUSKY_GIT_PARAMS%'; + edit === "$HUSKY_GIT_PARAMS" || edit === "%HUSKY_GIT_PARAMS%"; if (isGitParams || isHuskyParams) { console.warn(`Using environment variable syntax (${edit}) in -e |\ --edit is deprecated. Use '{-E|--env} HUSKY_GIT_PARAMS instead'`); - if (isGitParams && 'GIT_PARAMS' in process.env) { + if (isGitParams && "GIT_PARAMS" in process.env) { return process.env.GIT_PARAMS; } - if ('HUSKY_GIT_PARAMS' in process.env) { + if ("HUSKY_GIT_PARAMS" in process.env) { return process.env.HUSKY_GIT_PARAMS; } throw new Error( - `Received ${edit} as value for -e | --edit, but GIT_PARAMS or HUSKY_GIT_PARAMS are not available globally.` + `Received ${edit} as value for -e | --edit, but GIT_PARAMS or HUSKY_GIT_PARAMS are not available globally.`, ); } return edit; @@ -471,19 +471,19 @@ function getEditValue(flags: CliFlags) { function getSeed(flags: CliFlags): UserConfig { const n = (flags.extends || []).filter( - (i): i is string => typeof i === 'string' + (i): i is string => typeof i === "string", ); return n.length > 0 - ? {extends: n, parserPreset: flags['parser-preset']} - : {parserPreset: flags['parser-preset']}; + ? { extends: n, parserPreset: flags["parser-preset"] } + : { parserPreset: flags["parser-preset"] }; } function selectParserOpts(parserPreset: ParserPreset | undefined) { - if (typeof parserPreset !== 'object') { + if (typeof parserPreset !== "object") { return undefined; } - if (typeof parserPreset.parserOpts !== 'object') { + if (typeof parserPreset.parserOpts !== "object") { return undefined; } @@ -492,9 +492,9 @@ function selectParserOpts(parserPreset: ParserPreset | undefined) { function loadFormatter( config: QualifiedConfig, - flags: CliFlags + flags: CliFlags, ): Promise<Formatter> { - const moduleName = flags.format || config.formatter || '@commitlint/format'; + const moduleName = flags.format || config.formatter || "@commitlint/format"; const modulePath = resolveFromSilent(moduleName, __dirname) || resolveFromSilent(moduleName, flags.cwd) || @@ -508,7 +508,7 @@ function loadFormatter( } // Catch unhandled rejections globally -process.on('unhandledRejection', (reason, promise) => { - console.log('Unhandled Rejection at: Promise ', promise, ' reason: ', reason); +process.on("unhandledRejection", (reason, promise) => { + console.log("Unhandled Rejection at: Promise ", promise, " reason: ", reason); throw reason; }); diff --git a/@commitlint/cli/src/types.ts b/@commitlint/cli/src/types.ts index c9b3a1b8ef..cbc9a8956a 100644 --- a/@commitlint/cli/src/types.ts +++ b/@commitlint/cli/src/types.ts @@ -6,19 +6,19 @@ export interface CliFlags { env?: string; extends?: (string | number)[]; help?: boolean; - 'help-url'?: string; + "help-url"?: string; from?: string; - 'from-last-tag'?: boolean; - 'git-log-args'?: string; + "from-last-tag"?: boolean; + "git-log-args"?: string; last?: boolean; format?: string; - 'parser-preset'?: string; + "parser-preset"?: string; quiet: boolean; to?: string; version?: boolean; verbose?: boolean; /** @type {'' | 'text' | 'json'} */ - 'print-config'?: string; + "print-config"?: string; strict?: boolean; _: (string | number)[]; $0: string; diff --git a/@commitlint/config-angular-type-enum/README.md b/@commitlint/config-angular-type-enum/README.md index 6ffd9dd17e..09df8aa8de 100644 --- a/@commitlint/config-angular-type-enum/README.md +++ b/@commitlint/config-angular-type-enum/README.md @@ -23,7 +23,7 @@ echo "build: bar" | commitlint # passes ```js // commitlint.config.js -const types = require('@commitlint/config-angular-type-enum'); +const types = require("@commitlint/config-angular-type-enum"); // Use as rule creating errors for non-allowed types module.exports = { @@ -35,7 +35,7 @@ module.exports = { // Warn for non-allowed types module.exports = { rules: { - 'type-enum': [1, 'always', types.values()], + "type-enum": [1, "always", types.values()], }, }; ``` diff --git a/@commitlint/config-angular-type-enum/index.js b/@commitlint/config-angular-type-enum/index.js index 485701638c..658d6259d2 100644 --- a/@commitlint/config-angular-type-enum/index.js +++ b/@commitlint/config-angular-type-enum/index.js @@ -1,19 +1,19 @@ const types = [ - 'build', - 'ci', - 'docs', - 'feat', - 'fix', - 'perf', - 'refactor', - 'revert', - 'style', - 'test', + "build", + "ci", + "docs", + "feat", + "fix", + "perf", + "refactor", + "revert", + "style", + "test", ]; export default { rules: { - 'type-enum': [2, 'always', types], + "type-enum": [2, "always", types], }, value: () => types, }; diff --git a/@commitlint/config-angular/index.js b/@commitlint/config-angular/index.js index c433e75baf..81848fb82c 100644 --- a/@commitlint/config-angular/index.js +++ b/@commitlint/config-angular/index.js @@ -1,22 +1,24 @@ -import typeEnum from '@commitlint/config-angular-type-enum'; +import typeEnum from "@commitlint/config-angular-type-enum"; export default { - parserPreset: {parserOpts: {headerPattern: /^(\w*)(?:\((.*)\))?!?: (.*)$/}}, + parserPreset: { + parserOpts: { headerPattern: /^(\w*)(?:\((.*)\))?!?: (.*)$/ }, + }, rules: { - 'subject-exclamation-mark': [2, 'never'], - 'body-leading-blank': [1, 'always'], - 'footer-leading-blank': [1, 'always'], - 'header-max-length': [2, 'always', 72], - 'scope-case': [2, 'always', 'lower-case'], - 'subject-case': [ + "subject-exclamation-mark": [2, "never"], + "body-leading-blank": [1, "always"], + "footer-leading-blank": [1, "always"], + "header-max-length": [2, "always", 72], + "scope-case": [2, "always", "lower-case"], + "subject-case": [ 2, - 'never', - ['sentence-case', 'start-case', 'pascal-case', 'upper-case'], + "never", + ["sentence-case", "start-case", "pascal-case", "upper-case"], ], - 'subject-empty': [2, 'never'], - 'subject-full-stop': [2, 'never', '.'], - 'type-case': [2, 'always', 'lower-case'], - 'type-empty': [2, 'never'], - 'type-enum': typeEnum.rules['type-enum'], + "subject-empty": [2, "never"], + "subject-full-stop": [2, "never", "."], + "type-case": [2, "always", "lower-case"], + "type-empty": [2, "never"], + "type-enum": typeEnum.rules["type-enum"], }, }; diff --git a/@commitlint/config-angular/index.test.js b/@commitlint/config-angular/index.test.js index 662c233cb3..d76a84c585 100644 --- a/@commitlint/config-angular/index.test.js +++ b/@commitlint/config-angular/index.test.js @@ -1,108 +1,108 @@ -import {test, expect} from 'vitest'; -import lint from '@commitlint/lint'; +import { test, expect } from "vitest"; +import lint from "@commitlint/lint"; -import config from './index.js'; +import config from "./index.js"; -const {rules, parserPreset} = config; +const { rules, parserPreset } = config; const lintMessage = async (message) => { const parserOpts = parserPreset.parserOpts; - const m = message.replace(/^\s+/, '').trim(); - const result = await lint(m, rules, {parserOpts}); + const m = message.replace(/^\s+/, "").trim(); + const result = await lint(m, rules, { parserOpts }); if (result.errors.length > 1) { throw new Error( - 'Commit test should only have one error message to validate against' + "Commit test should only have one error message to validate against", ); } if (result.warnings.length > 1) { throw new Error( - 'Commit test should only have one warning message to validate against' + "Commit test should only have one warning message to validate against", ); } return result; }; -test('a valid commit message', async () => { - const result = await lintMessage('test: a valid angular commit'); +test("a valid commit message", async () => { + const result = await lintMessage("test: a valid angular commit"); expect(result.valid).toBe(true); expect(result.errors).toStrictEqual([]); expect(result.warnings).toStrictEqual([]); }); -test('a valid message with a scope', async () => { +test("a valid message with a scope", async () => { const result = await lintMessage( - 'test(scope): a valid angular commit with a scope' + "test(scope): a valid angular commit with a scope", ); expect(result.valid).toBe(true); expect(result.errors).toStrictEqual([]); expect(result.warnings).toStrictEqual([]); }); -test('a valid multi line commit', async () => { +test("a valid multi line commit", async () => { const result = await lintMessage( `test(scope): a valid angular commit with a scope - Some content in the body` + Some content in the body`, ); expect(result.valid).toBe(true); expect(result.errors).toStrictEqual([]); expect(result.warnings).toStrictEqual([]); }); -test('a leading blank line after header', async () => { +test("a leading blank line after header", async () => { const result = await lintMessage( `test(scope): a valid angular commit with a scope - Some content in the body` + Some content in the body`, ); expect(result.valid).toBe(true); expect(result.errors).toStrictEqual([]); - expect(result.warnings[0].message).toBe('body must have leading blank line'); + expect(result.warnings[0].message).toBe("body must have leading blank line"); }); -test('an invalid scope', async () => { +test("an invalid scope", async () => { const result = await lintMessage(`no: no is not an invalid commit type`); expect(result.valid).toBe(false); expect(result.errors[0].message).toBe( - 'type must be one of [build, ci, docs, feat, fix, perf, refactor, revert, style, test]' + "type must be one of [build, ci, docs, feat, fix, perf, refactor, revert, style, test]", ); expect(result.warnings).toStrictEqual([]); }); -test('a long header', async () => { +test("a long header", async () => { const result = await lintMessage( - `test: that its an error when there is ia realllllllllllllllllllllly long header` + `test: that its an error when there is ia realllllllllllllllllllllly long header`, ); expect(result.valid).toBe(false); expect(result.errors[0].message).toBe( - 'header must not be longer than 72 characters, current length is 79' + "header must not be longer than 72 characters, current length is 79", ); expect(result.warnings).toStrictEqual([]); }); -test('message header with ! in it', async () => { +test("message header with ! in it", async () => { const result = await lintMessage(`test!: with a breaking change in the type`); expect(result.valid).toBe(false); expect(result.errors[0].message).toBe( - 'subject must not have an exclamation mark in the subject to identify a breaking change' + "subject must not have an exclamation mark in the subject to identify a breaking change", ); expect(result.warnings).toStrictEqual([]); }); -test('message header with ! in it and a scope', async () => { +test("message header with ! in it and a scope", async () => { const result = await lintMessage( - `test(scope)!: with a breaking change in the type` + `test(scope)!: with a breaking change in the type`, ); expect(result.valid).toBe(false); expect(result.errors[0].message).toBe( - 'subject must not have an exclamation mark in the subject to identify a breaking change' + "subject must not have an exclamation mark in the subject to identify a breaking change", ); expect(result.warnings).toStrictEqual([]); }); diff --git a/@commitlint/config-conventional/src/index.test.ts b/@commitlint/config-conventional/src/index.test.ts index a44fe8c59a..3603fe74f6 100644 --- a/@commitlint/config-conventional/src/index.test.ts +++ b/@commitlint/config-conventional/src/index.test.ts @@ -1,53 +1,53 @@ -import {test, expect} from 'vitest'; -import path from 'node:path'; -import {pathToFileURL} from 'node:url'; +import { test, expect } from "vitest"; +import path from "node:path"; +import { pathToFileURL } from "node:url"; -import lint from '@commitlint/lint'; +import lint from "@commitlint/lint"; -import config from './index.js'; +import config from "./index.js"; -const {rules, parserPreset} = config; +const { rules, parserPreset } = config; const dynamicImport = async (id: string) => { const imported = await import( path.isAbsolute(id) ? pathToFileURL(id).toString() : id ); - return ('default' in imported && imported.default) || imported; + return ("default" in imported && imported.default) || imported; }; const commitLint = async (message: string) => { const preset = await (await dynamicImport(parserPreset))(); - return lint(message, rules, {...preset}); + return lint(message, rules, { ...preset }); }; const messages = { - invalidTypeEnum: 'foo: some message', - invalidTypeCase: 'FIX: some message', - invalidTypeEmpty: ': some message', + invalidTypeEnum: "foo: some message", + invalidTypeCase: "FIX: some message", + invalidTypeEmpty: ": some message", invalidSubjectCases: [ - 'fix(scope): Some message', - 'fix(scope): Some Message', - 'fix(scope): SomeMessage', - 'fix(scope): SOMEMESSAGE', + "fix(scope): Some message", + "fix(scope): Some Message", + "fix(scope): SomeMessage", + "fix(scope): SOMEMESSAGE", ], - invalidSubjectEmpty: 'fix:', - invalidSubjectFullStop: 'fix: some message.', + invalidSubjectEmpty: "fix:", + invalidSubjectFullStop: "fix: some message.", invalidHeaderMaxLength: - 'fix: some message that is way too long and breaks the line max-length by several characters since the max is 100', + "fix: some message that is way too long and breaks the line max-length by several characters since the max is 100", warningFooterLeadingBlank: - 'fix: some message\n\nbody\nBREAKING CHANGE: It will be significant', + "fix: some message\n\nbody\nBREAKING CHANGE: It will be significant", invalidFooterMaxLineLength: 'fix: some message\n\nbody\n\nBREAKING CHANGE: footer with multiple lines\nhas a message that is way too long and will break the line rule "line-max-length" by several characters', - warningBodyLeadingBlank: 'fix: some message\nbody', + warningBodyLeadingBlank: "fix: some message\nbody", invalidBodyMaxLineLength: 'fix: some message\n\nbody with multiple lines\nhas a message that is way too long and will break the line rule "line-max-length" by several characters', validMessages: [ - 'fix: some message', - 'fix(scope): some message', - 'fix(scope): some Message', - 'fix(scope): some message\n\nBREAKING CHANGE: it will be significant!', - 'fix(scope): some message\n\nbody', - 'fix(scope)!: some message\n\nbody', + "fix: some message", + "fix(scope): some message", + "fix(scope): some Message", + "fix(scope): some message\n\nBREAKING CHANGE: it will be significant!", + "fix(scope): some message\n\nbody", + "fix(scope)!: some message\n\nbody", ], }; @@ -55,58 +55,58 @@ const errors = { typeEnum: { level: 2, message: - 'type must be one of [build, chore, ci, docs, feat, fix, perf, refactor, revert, style, test]', - name: 'type-enum', + "type must be one of [build, chore, ci, docs, feat, fix, perf, refactor, revert, style, test]", + name: "type-enum", valid: false, }, typeCase: { level: 2, - message: 'type must be lower-case', - name: 'type-case', + message: "type must be lower-case", + name: "type-case", valid: false, }, typeEmpty: { level: 2, - message: 'type may not be empty', - name: 'type-empty', + message: "type may not be empty", + name: "type-empty", valid: false, }, subjectCase: { level: 2, message: - 'subject must not be sentence-case, start-case, pascal-case, upper-case', - name: 'subject-case', + "subject must not be sentence-case, start-case, pascal-case, upper-case", + name: "subject-case", valid: false, }, subjectEmpty: { level: 2, - message: 'subject may not be empty', - name: 'subject-empty', + message: "subject may not be empty", + name: "subject-empty", valid: false, }, subjectFullStop: { level: 2, - message: 'subject may not end with full stop', - name: 'subject-full-stop', + message: "subject may not end with full stop", + name: "subject-full-stop", valid: false, }, headerMaxLength: { level: 2, message: - 'header must not be longer than 100 characters, current length is 112', - name: 'header-max-length', + "header must not be longer than 100 characters, current length is 112", + name: "header-max-length", valid: false, }, footerMaxLineLength: { level: 2, message: "footer's lines must not be longer than 100 characters", - name: 'footer-max-line-length', + name: "footer-max-line-length", valid: false, }, bodyMaxLineLength: { level: 2, message: "body's lines must not be longer than 100 characters", - name: 'body-max-line-length', + name: "body-max-line-length", valid: false, }, }; @@ -114,42 +114,44 @@ const errors = { const warnings = { footerLeadingBlank: { level: 1, - message: 'footer must have leading blank line', - name: 'footer-leading-blank', + message: "footer must have leading blank line", + name: "footer-leading-blank", valid: false, }, bodyLeadingBlank: { level: 1, - message: 'body must have leading blank line', - name: 'body-leading-blank', + message: "body must have leading blank line", + name: "body-leading-blank", valid: false, }, }; -test('type-enum', async () => { +test("type-enum", async () => { const result = await commitLint(messages.invalidTypeEnum); expect(result.valid).toBe(false); expect(result.errors).toEqual([errors.typeEnum]); }); -test('type-case', async () => { +test("type-case", async () => { const result = await commitLint(messages.invalidTypeCase); expect(result.valid).toBe(false); expect(result.errors).toEqual([errors.typeCase, errors.typeEnum]); }); -test('type-empty', async () => { +test("type-empty", async () => { const result = await commitLint(messages.invalidTypeEmpty); expect(result.valid).toBe(false); expect(result.errors).toEqual([errors.typeEmpty]); }); -test('subject-case', async () => { +test("subject-case", async () => { const invalidInputs = await Promise.all( - messages.invalidSubjectCases.map((invalidInput) => commitLint(invalidInput)) + messages.invalidSubjectCases.map((invalidInput) => + commitLint(invalidInput), + ), ); invalidInputs.forEach((result) => { @@ -158,58 +160,58 @@ test('subject-case', async () => { }); }); -test('subject-empty', async () => { +test("subject-empty", async () => { const result = await commitLint(messages.invalidSubjectEmpty); expect(result.valid).toBe(false); expect(result.errors).toEqual([errors.subjectEmpty, errors.typeEmpty]); }); -test('subject-full-stop', async () => { +test("subject-full-stop", async () => { const result = await commitLint(messages.invalidSubjectFullStop); expect(result.valid).toBe(false); expect(result.errors).toEqual([errors.subjectFullStop]); }); -test('header-max-length', async () => { +test("header-max-length", async () => { const result = await commitLint(messages.invalidHeaderMaxLength); expect(result.valid).toBe(false); expect(result.errors).toEqual([errors.headerMaxLength]); }); -test('footer-leading-blank', async () => { +test("footer-leading-blank", async () => { const result = await commitLint(messages.warningFooterLeadingBlank); expect(result.valid).toBe(true); expect(result.warnings).toEqual([warnings.footerLeadingBlank]); }); -test('footer-max-line-length', async () => { +test("footer-max-line-length", async () => { const result = await commitLint(messages.invalidFooterMaxLineLength); expect(result.valid).toBe(false); expect(result.errors).toEqual([errors.footerMaxLineLength]); }); -test('body-leading-blank', async () => { +test("body-leading-blank", async () => { const result = await commitLint(messages.warningBodyLeadingBlank); expect(result.valid).toBe(true); expect(result.warnings).toEqual([warnings.bodyLeadingBlank]); }); -test('body-max-line-length', async () => { +test("body-max-line-length", async () => { const result = await commitLint(messages.invalidBodyMaxLineLength); expect(result.valid).toBe(false); expect(result.errors).toEqual([errors.bodyMaxLineLength]); }); -test('valid messages', async () => { +test("valid messages", async () => { const validInputs = await Promise.all( - messages.validMessages.map((input) => commitLint(input)) + messages.validMessages.map((input) => commitLint(input)), ); validInputs.forEach((result) => { diff --git a/@commitlint/config-conventional/src/index.ts b/@commitlint/config-conventional/src/index.ts index f07f233f0e..09ee1c9a67 100644 --- a/@commitlint/config-conventional/src/index.ts +++ b/@commitlint/config-conventional/src/index.ts @@ -2,45 +2,45 @@ import { RuleConfigCondition, RuleConfigSeverity, TargetCaseType, -} from '@commitlint/types'; +} from "@commitlint/types"; export default { - parserPreset: 'conventional-changelog-conventionalcommits', + parserPreset: "conventional-changelog-conventionalcommits", rules: { - 'body-leading-blank': [RuleConfigSeverity.Warning, 'always'] as const, - 'body-max-line-length': [RuleConfigSeverity.Error, 'always', 100] as const, - 'footer-leading-blank': [RuleConfigSeverity.Warning, 'always'] as const, - 'footer-max-line-length': [ + "body-leading-blank": [RuleConfigSeverity.Warning, "always"] as const, + "body-max-line-length": [RuleConfigSeverity.Error, "always", 100] as const, + "footer-leading-blank": [RuleConfigSeverity.Warning, "always"] as const, + "footer-max-line-length": [ RuleConfigSeverity.Error, - 'always', + "always", 100, ] as const, - 'header-max-length': [RuleConfigSeverity.Error, 'always', 100] as const, - 'header-trim': [RuleConfigSeverity.Error, 'always'] as const, - 'subject-case': [ + "header-max-length": [RuleConfigSeverity.Error, "always", 100] as const, + "header-trim": [RuleConfigSeverity.Error, "always"] as const, + "subject-case": [ RuleConfigSeverity.Error, - 'never', - ['sentence-case', 'start-case', 'pascal-case', 'upper-case'], + "never", + ["sentence-case", "start-case", "pascal-case", "upper-case"], ] as [RuleConfigSeverity, RuleConfigCondition, TargetCaseType[]], - 'subject-empty': [RuleConfigSeverity.Error, 'never'] as const, - 'subject-full-stop': [RuleConfigSeverity.Error, 'never', '.'] as const, - 'type-case': [RuleConfigSeverity.Error, 'always', 'lower-case'] as const, - 'type-empty': [RuleConfigSeverity.Error, 'never'] as const, - 'type-enum': [ + "subject-empty": [RuleConfigSeverity.Error, "never"] as const, + "subject-full-stop": [RuleConfigSeverity.Error, "never", "."] as const, + "type-case": [RuleConfigSeverity.Error, "always", "lower-case"] as const, + "type-empty": [RuleConfigSeverity.Error, "never"] as const, + "type-enum": [ RuleConfigSeverity.Error, - 'always', + "always", [ - 'build', - 'chore', - 'ci', - 'docs', - 'feat', - 'fix', - 'perf', - 'refactor', - 'revert', - 'style', - 'test', + "build", + "chore", + "ci", + "docs", + "feat", + "fix", + "perf", + "refactor", + "revert", + "style", + "test", ], ] as [RuleConfigSeverity, RuleConfigCondition, string[]], }, @@ -50,93 +50,93 @@ export default { description: "Select the type of change that you're committing", enum: { feat: { - description: 'A new feature', - title: 'Features', - emoji: '✨', + description: "A new feature", + title: "Features", + emoji: "✨", }, fix: { - description: 'A bug fix', - title: 'Bug Fixes', - emoji: '🐛', + description: "A bug fix", + title: "Bug Fixes", + emoji: "🐛", }, docs: { - description: 'Documentation only changes', - title: 'Documentation', - emoji: '📚', + description: "Documentation only changes", + title: "Documentation", + emoji: "📚", }, style: { description: - 'Changes that do not affect the meaning of the code (white-space, formatting, missing semi-colons, etc)', - title: 'Styles', - emoji: '💎', + "Changes that do not affect the meaning of the code (white-space, formatting, missing semi-colons, etc)", + title: "Styles", + emoji: "💎", }, refactor: { description: - 'A code change that neither fixes a bug nor adds a feature', - title: 'Code Refactoring', - emoji: '📦', + "A code change that neither fixes a bug nor adds a feature", + title: "Code Refactoring", + emoji: "📦", }, perf: { - description: 'A code change that improves performance', - title: 'Performance Improvements', - emoji: '🚀', + description: "A code change that improves performance", + title: "Performance Improvements", + emoji: "🚀", }, test: { - description: 'Adding missing tests or correcting existing tests', - title: 'Tests', - emoji: '🚨', + description: "Adding missing tests or correcting existing tests", + title: "Tests", + emoji: "🚨", }, build: { description: - 'Changes that affect the build system or external dependencies (example scopes: gulp, broccoli, npm)', - title: 'Builds', - emoji: '🛠', + "Changes that affect the build system or external dependencies (example scopes: gulp, broccoli, npm)", + title: "Builds", + emoji: "🛠", }, ci: { description: - 'Changes to our CI configuration files and scripts (example scopes: Travis, Circle, BrowserStack, SauceLabs)', - title: 'Continuous Integrations', - emoji: '⚙️', + "Changes to our CI configuration files and scripts (example scopes: Travis, Circle, BrowserStack, SauceLabs)", + title: "Continuous Integrations", + emoji: "⚙️", }, chore: { description: "Other changes that don't modify src or test files", - title: 'Chores', - emoji: '♻️', + title: "Chores", + emoji: "♻️", }, revert: { - description: 'Reverts a previous commit', - title: 'Reverts', - emoji: '🗑', + description: "Reverts a previous commit", + title: "Reverts", + emoji: "🗑", }, }, }, scope: { description: - 'What is the scope of this change (e.g. component or file name)', + "What is the scope of this change (e.g. component or file name)", }, subject: { description: - 'Write a short, imperative tense description of the change', + "Write a short, imperative tense description of the change", }, body: { - description: 'Provide a longer description of the change', + description: "Provide a longer description of the change", }, isBreaking: { - description: 'Are there any breaking changes?', + description: "Are there any breaking changes?", }, breakingBody: { description: - 'A BREAKING CHANGE commit requires a body. Please enter a longer description of the commit itself', + "A BREAKING CHANGE commit requires a body. Please enter a longer description of the commit itself", }, breaking: { - description: 'Describe the breaking changes', + description: "Describe the breaking changes", }, isIssueAffected: { - description: 'Does this change affect any open issues?', + description: "Does this change affect any open issues?", }, issuesBody: { description: - 'If issues are closed, the commit requires a body. Please enter a longer description of the commit itself', + "If issues are closed, the commit requires a body. Please enter a longer description of the commit itself", }, issues: { description: 'Add issue references (e.g. "fix #123", "re #123".)', diff --git a/@commitlint/config-lerna-scopes/index.js b/@commitlint/config-lerna-scopes/index.js index accda8d8f2..a24642b5ae 100644 --- a/@commitlint/config-lerna-scopes/index.js +++ b/@commitlint/config-lerna-scopes/index.js @@ -1,13 +1,13 @@ -import path from 'node:path'; -import fs from 'node:fs/promises'; -import fg from 'fast-glob'; -import configWorkspaceScopes from '@commitlint/config-workspace-scopes'; +import path from "node:path"; +import fs from "node:fs/promises"; +import fg from "fast-glob"; +import configWorkspaceScopes from "@commitlint/config-workspace-scopes"; export default { - utils: {getProjects}, + utils: { getProjects }, rules: { - 'scope-enum': (ctx) => - getProjects(ctx).then((packages) => [2, 'always', packages]), + "scope-enum": (ctx) => + getProjects(ctx).then((packages) => [2, "always", packages]), }, }; @@ -20,7 +20,7 @@ export default { function normalizePatterns(patterns) { const normalizedPatterns = []; for (const pattern of patterns) { - normalizedPatterns.push(pattern.replace(/\/?$/, '/package.json')); + normalizedPatterns.push(pattern.replace(/\/?$/, "/package.json")); } return normalizedPatterns; } @@ -31,8 +31,8 @@ function normalizePatterns(patterns) { * @returns A list of parsed package.json files as objects */ async function findPackages(cwd) { - const json = await fs.readFile(path.join(cwd, 'lerna.json'), { - encoding: 'utf-8', + const json = await fs.readFile(path.join(cwd, "lerna.json"), { + encoding: "utf-8", }); const packages = JSON.parse(json)?.packages || []; @@ -43,13 +43,13 @@ async function findPackages(cwd) { const patterns = normalizePatterns(packages); const entries = await fg(patterns, { cwd, - ignore: ['**/node_modules/**', '**/bower_components/**'], + ignore: ["**/node_modules/**", "**/bower_components/**"], }); const pkgJsons = await Promise.all( Array.from(new Set(entries.map((entry) => path.join(cwd, entry)))).map( - (pkgPath) => fs.readFile(pkgPath, {encoding: 'utf-8'}) - ) + (pkgPath) => fs.readFile(pkgPath, { encoding: "utf-8" }), + ), ); return pkgJsons.map((pkgJson) => JSON.parse(pkgJson) || {}); @@ -70,7 +70,7 @@ async function getProjects(context) { `It seems that you are using npm/yarn workspaces instead of lernas "packages" declaration.`, `Support for workspaces will be removed in a future major version of this package.`, `Please make sure to transition to "@commitlint/config-workspace-scopes" in the near future.`, - ].join('\n') + ].join("\n"), ); return workspacePackages; } @@ -81,7 +81,7 @@ async function getProjects(context) { .reduce((pkgNames, pkg) => { const name = pkg.name; if (name) { - pkgNames.push(name.charAt(0) === '@' ? name.split('/')[1] : name); + pkgNames.push(name.charAt(0) === "@" ? name.split("/")[1] : name); } return pkgNames; }, []) diff --git a/@commitlint/config-lerna-scopes/index.test.js b/@commitlint/config-lerna-scopes/index.test.js index 2ed89fcb9e..3de602d281 100644 --- a/@commitlint/config-lerna-scopes/index.test.js +++ b/@commitlint/config-lerna-scopes/index.test.js @@ -1,119 +1,119 @@ -import {test, expect, vi} from 'vitest'; -import path from 'path'; -import {fileURLToPath} from 'url'; +import { test, expect, vi } from "vitest"; +import path from "path"; +import { fileURLToPath } from "url"; -import {npm} from '@commitlint/test'; +import { npm } from "@commitlint/test"; -import config from './index.js'; +import config from "./index.js"; -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -test('exports rules key', () => { - expect(config).toHaveProperty('rules'); +test("exports rules key", () => { + expect(config).toHaveProperty("rules"); }); -test('rules hold object', () => { +test("rules hold object", () => { expect(config).toMatchObject({ rules: expect.any(Object), }); }); -test('rules contain scope-enum', () => { +test("rules contain scope-enum", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.anything(), + "scope-enum": expect.anything(), }, }); }); -test('scope-enum is function', () => { +test("scope-enum is function", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.any(Function), + "scope-enum": expect.any(Function), }, }); }); -test('scope-enum does not throw for missing context', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum does not throw for missing context", async () => { + const { "scope-enum": fn } = config.rules; await expect(fn()).resolves.toBeTruthy(); }); -test('scope-enum has expected severity', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected severity", async () => { + const { "scope-enum": fn } = config.rules; const [severity] = await fn(); expect(severity).toBe(2); }); -test('scope-enum has expected modifier', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected modifier", async () => { + const { "scope-enum": fn } = config.rules; const [, modifier] = await fn(); - expect(modifier).toBe('always'); + expect(modifier).toBe("always"); }); -test('returns empty value for empty lerna repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/empty', __dirname); - const [, , value] = await fn({cwd}); +test("returns empty value for empty lerna repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/empty", __dirname); + const [, , value] = await fn({ cwd }); expect(value).toEqual([]); }); -test('returns all packages for nested lerna packages repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/nested', __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['nested-a', 'nested-b', 'nested-c']); +test("returns all packages for nested lerna packages repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/nested", __dirname); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["nested-a", "nested-b", "nested-c"]); }); -test('returns expected value for basic lerna repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/basic', __dirname); +test("returns expected value for basic lerna repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/basic", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['basic-a', 'basic-b']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["basic-a", "basic-b"]); }); -test('returns expected value for lerna repository containing modules', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/modules', __dirname); +test("returns expected value for lerna repository containing modules", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/modules", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['modules-a']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["modules-a"]); }); -test('returns expected value for scoped lerna repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/scoped', __dirname); +test("returns expected value for scoped lerna repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/scoped", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['scoped-a', 'scoped-b']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["scoped-a", "scoped-b"]); }); -test('work with no declared packages', async () => { - const {'scope-enum': fn} = config.rules; +test("work with no declared packages", async () => { + const { "scope-enum": fn } = config.rules; const cwd = await npm.bootstrap( - 'fixtures/no-packages-declaration', - __dirname + "fixtures/no-packages-declaration", + __dirname, ); - const [, , value] = await fn({cwd}); + const [, , value] = await fn({ cwd }); expect(value).toEqual([]); }); -test('inform the user about the transition to config-workspace-scopes if the project is using native workspaces', async () => { - const {'scope-enum': fn} = config.rules; +test("inform the user about the transition to config-workspace-scopes if the project is using native workspaces", async () => { + const { "scope-enum": fn } = config.rules; const cwd = await npm.bootstrap( - 'fixtures/transition-to-workspace-scopes', - __dirname + "fixtures/transition-to-workspace-scopes", + __dirname, ); - const consoleWarnSpy = vi.spyOn(console, 'warn'); + const consoleWarnSpy = vi.spyOn(console, "warn"); - const [, , value] = await fn({cwd}); + const [, , value] = await fn({ cwd }); expect(consoleWarnSpy).toHaveBeenCalledWith( - expect.stringContaining(`It seems that you are using npm/yarn workspaces`) + expect.stringContaining(`It seems that you are using npm/yarn workspaces`), ); - expect(value).toEqual(['workspace-package']); + expect(value).toEqual(["workspace-package"]); }); diff --git a/@commitlint/config-nx-scopes/index.js b/@commitlint/config-nx-scopes/index.js index 5251f49492..25debbeba3 100644 --- a/@commitlint/config-nx-scopes/index.js +++ b/@commitlint/config-nx-scopes/index.js @@ -1,12 +1,12 @@ -import {RuleConfigSeverity} from '@commitlint/types'; -import {getProjects as getNXProjects} from 'nx/src/generators/utils/project-configuration.js'; -import {FsTree} from 'nx/src/generators/tree.js'; +import { RuleConfigSeverity } from "@commitlint/types"; +import { getProjects as getNXProjects } from "nx/src/generators/utils/project-configuration.js"; +import { FsTree } from "nx/src/generators/tree.js"; export default { - utils: {getProjects}, + utils: { getProjects }, rules: { - 'scope-enum': (ctx) => - Promise.resolve([RuleConfigSeverity.Error, 'always', getProjects(ctx)]), + "scope-enum": (ctx) => + Promise.resolve([RuleConfigSeverity.Error, "always", getProjects(ctx)]), }, }; @@ -28,8 +28,8 @@ function getProjects(context, selector = () => true) { name: project.name, projectType: project.projectType, tags: project.tags, - }) + }), ) .map((project) => project.name) - .map((name) => (name.charAt(0) === '@' ? name.split('/')[1] : name)); + .map((name) => (name.charAt(0) === "@" ? name.split("/")[1] : name)); } diff --git a/@commitlint/config-nx-scopes/index.test.js b/@commitlint/config-nx-scopes/index.test.js index 22a525f145..1a6f863ef3 100644 --- a/@commitlint/config-nx-scopes/index.test.js +++ b/@commitlint/config-nx-scopes/index.test.js @@ -1,91 +1,91 @@ -import {test, expect} from 'vitest'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { test, expect } from "vitest"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {npm} from '@commitlint/test'; +import { npm } from "@commitlint/test"; -import config from './index.js'; +import config from "./index.js"; -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -test('exports rules key', () => { - expect(config).toHaveProperty('rules'); +test("exports rules key", () => { + expect(config).toHaveProperty("rules"); }); -test('rules hold object', () => { +test("rules hold object", () => { expect(config).toMatchObject({ rules: expect.any(Object), }); }); -test('rules contain scope-enum', () => { +test("rules contain scope-enum", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.anything(), + "scope-enum": expect.anything(), }, }); }); -test('scope-enum is function', () => { +test("scope-enum is function", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.any(Function), + "scope-enum": expect.any(Function), }, }); }); -test('scope-enum does not throw for missing context', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum does not throw for missing context", async () => { + const { "scope-enum": fn } = config.rules; await expect(fn()).resolves.toBeTruthy(); }); -test('scope-enum has expected severity', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected severity", async () => { + const { "scope-enum": fn } = config.rules; const [severity] = await fn(); expect(severity).toBe(2); }); -test('scope-enum has expected modifier', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected modifier", async () => { + const { "scope-enum": fn } = config.rules; const [, modifier] = await fn(); - expect(modifier).toBe('always'); + expect(modifier).toBe("always"); }); -test('returns empty value for empty nx repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/empty', __dirname); - const [, , value] = await fn({cwd}); +test("returns empty value for empty nx repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/empty", __dirname); + const [, , value] = await fn({ cwd }); expect(value).toEqual([]); }); -test('returns expected value for basic nx repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/basic', __dirname); +test("returns expected value for basic nx repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/basic", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['a', 'b']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["a", "b"]); }); -test('expect correct result from Nx 14', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/nx14', __dirname); +test("expect correct result from Nx 14", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/nx14", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['c', 'd']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["c", "d"]); }); -test('expect correct result from Nx 15', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/nx15', __dirname); +test("expect correct result from Nx 15", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/nx15", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['e', 'f']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["e", "f"]); }); -test('expect correct result from Nx 17', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/nx17', __dirname); +test("expect correct result from Nx 17", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/nx17", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['g', 'h']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["g", "h"]); }); diff --git a/@commitlint/config-nx-scopes/readme.md b/@commitlint/config-nx-scopes/readme.md index 454a28b1e0..2890f85872 100644 --- a/@commitlint/config-nx-scopes/readme.md +++ b/@commitlint/config-nx-scopes/readme.md @@ -24,20 +24,20 @@ In your .commitlintrc.js file: async function getConfig() { const { default: { - utils: {getProjects}, + utils: { getProjects }, }, - } = await import('@commitlint/config-nx-scopes'); + } = await import("@commitlint/config-nx-scopes"); return { rules: { - 'scope-enum': async (ctx) => [ + "scope-enum": async (ctx) => [ 2, - 'always', + "always", [ ...(await getProjects( ctx, - ({name, projectType}) => - !name.includes('e2e') && projectType == 'application' + ({ name, projectType }) => + !name.includes("e2e") && projectType == "application", )), ], ], @@ -57,19 +57,19 @@ In your .commitlintrc.js file: async function getConfig() { const { default: { - utils: {getProjects}, + utils: { getProjects }, }, - } = await import('@commitlint/config-nx-scopes'); + } = await import("@commitlint/config-nx-scopes"); return { rules: { - 'scope-enum': async (ctx) => [ + "scope-enum": async (ctx) => [ 2, - 'always', + "always", [ ...(await getProjects( ctx, - ({tags}) => !tags.includes('stage:end-of-life') + ({ tags }) => !tags.includes("stage:end-of-life"), )), ], ], diff --git a/@commitlint/config-patternplate/index.js b/@commitlint/config-patternplate/index.js index b732bf932a..240efb9655 100644 --- a/@commitlint/config-patternplate/index.js +++ b/@commitlint/config-patternplate/index.js @@ -1,24 +1,24 @@ -import path from 'node:path'; +import path from "node:path"; -import configAngular from '@commitlint/config-angular'; -import {glob} from 'glob'; -import merge from 'lodash.merge'; +import configAngular from "@commitlint/config-angular"; +import { glob } from "glob"; +import merge from "lodash.merge"; function pathToId(root, filePath) { const relativePath = path.relative(root, filePath); - return path.dirname(relativePath).split(path.sep).join('/'); + return path.dirname(relativePath).split(path.sep).join("/"); } async function getPatternIDs() { - const root = path.resolve(process.cwd(), './patterns'); - const pattern = path.resolve(root, '**/pattern.json'); + const root = path.resolve(process.cwd(), "./patterns"); + const pattern = path.resolve(root, "**/pattern.json"); const files = glob(pattern); return files.map((result) => pathToId(root, result)); } export default merge(configAngular, { rules: { - 'scope-enum': () => - getPatternIDs().then((ids) => [2, 'always', ids.concat(['system'])]), + "scope-enum": () => + getPatternIDs().then((ids) => [2, "always", ids.concat(["system"])]), }, }); diff --git a/@commitlint/config-pnpm-scopes/index.js b/@commitlint/config-pnpm-scopes/index.js index 6119f3789f..eb93cce86e 100644 --- a/@commitlint/config-pnpm-scopes/index.js +++ b/@commitlint/config-pnpm-scopes/index.js @@ -1,20 +1,20 @@ -import path from 'node:path'; +import path from "node:path"; -import fg from 'fast-glob'; -import readYamlFile from 'read-yaml-file'; -import {readExactProjectManifest} from '@pnpm/read-project-manifest'; +import fg from "fast-glob"; +import readYamlFile from "read-yaml-file"; +import { readExactProjectManifest } from "@pnpm/read-project-manifest"; export default { - utils: {getProjects}, + utils: { getProjects }, rules: { - 'scope-enum': (ctx) => - getProjects(ctx).then((packages) => [2, 'always', packages]), + "scope-enum": (ctx) => + getProjects(ctx).then((packages) => [2, "always", packages]), }, }; function requirePackagesManifest(dir) { - return readYamlFile(path.join(dir, 'pnpm-workspace.yaml')).catch((err) => { - if (err.code === 'ENOENT') { + return readYamlFile(path.join(dir, "pnpm-workspace.yaml")).catch((err) => { + if (err.code === "ENOENT") { return null; } @@ -25,9 +25,9 @@ function requirePackagesManifest(dir) { function normalizePatterns(patterns) { const normalizedPatterns = []; for (const pattern of patterns) { - normalizedPatterns.push(pattern.replace(/\/?$/, '/package.json')); - normalizedPatterns.push(pattern.replace(/\/?$/, '/package.json5')); - normalizedPatterns.push(pattern.replace(/\/?$/, '/package.yaml')); + normalizedPatterns.push(pattern.replace(/\/?$/, "/package.json")); + normalizedPatterns.push(pattern.replace(/\/?$/, "/package.json5")); + normalizedPatterns.push(pattern.replace(/\/?$/, "/package.yaml")); } return normalizedPatterns; } @@ -36,22 +36,22 @@ function findWorkspacePackages(cwd) { return requirePackagesManifest(cwd) .then((manifest) => { const patterns = normalizePatterns( - (manifest && manifest.packages) || ['**'] + (manifest && manifest.packages) || ["**"], ); const opts = { cwd, - ignore: ['**/node_modules/**', '**/bower_components/**'], + ignore: ["**/node_modules/**", "**/bower_components/**"], }; return fg(patterns, opts); }) .then((entries) => { const paths = Array.from( - new Set(entries.map((entry) => path.join(cwd, entry))) + new Set(entries.map((entry) => path.join(cwd, entry))), ); return Promise.all( - paths.map((manifestPath) => readExactProjectManifest(manifestPath)) + paths.map((manifestPath) => readExactProjectManifest(manifestPath)), ); }) .then((manifests) => { @@ -69,7 +69,7 @@ function getProjects(context) { const name = project.name; if (name) { - projects.push(name.charAt(0) === '@' ? name.split('/')[1] : name); + projects.push(name.charAt(0) === "@" ? name.split("/")[1] : name); } return projects; diff --git a/@commitlint/config-pnpm-scopes/index.test.js b/@commitlint/config-pnpm-scopes/index.test.js index 26644ec6fe..5b28bf7d1e 100644 --- a/@commitlint/config-pnpm-scopes/index.test.js +++ b/@commitlint/config-pnpm-scopes/index.test.js @@ -1,76 +1,76 @@ -import {test, expect} from 'vitest'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { test, expect } from "vitest"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {npm} from '@commitlint/test'; +import { npm } from "@commitlint/test"; -import config from './index.js'; +import config from "./index.js"; -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -test('exports rules key', () => { - expect(config).toHaveProperty('rules'); +test("exports rules key", () => { + expect(config).toHaveProperty("rules"); }); -test('rules hold object', () => { +test("rules hold object", () => { expect(config).toMatchObject({ rules: expect.any(Object), }); }); -test('rules contain scope-enum', () => { +test("rules contain scope-enum", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.anything(), + "scope-enum": expect.anything(), }, }); }); -test('scope-enum is function', () => { +test("scope-enum is function", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.any(Function), + "scope-enum": expect.any(Function), }, }); }); -test('scope-enum does not throw for missing context', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum does not throw for missing context", async () => { + const { "scope-enum": fn } = config.rules; await expect(fn()).resolves.toBeTruthy(); }); -test('scope-enum has expected severity', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected severity", async () => { + const { "scope-enum": fn } = config.rules; const [severity] = await fn(); expect(severity).toBe(2); }); -test('scope-enum has expected modifier', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected modifier", async () => { + const { "scope-enum": fn } = config.rules; const [, modifier] = await fn(); - expect(modifier).toBe('always'); + expect(modifier).toBe("always"); }); -test('returns empty value for empty pnpm repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/empty', __dirname); - const [, , value] = await fn({cwd}); +test("returns empty value for empty pnpm repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/empty", __dirname); + const [, , value] = await fn({ cwd }); expect(value).toEqual([]); }); -test('returns expected value for basic pnpm repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/basic', __dirname); +test("returns expected value for basic pnpm repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/basic", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['a', 'b']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["a", "b"]); }); -test('returns expected value for scoped pnpm repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/scoped', __dirname); +test("returns expected value for scoped pnpm repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/scoped", __dirname); - const [, , value] = await fn({cwd}); + const [, , value] = await fn({ cwd }); - expect(value).toEqual(['a', 'b']); + expect(value).toEqual(["a", "b"]); }); diff --git a/@commitlint/config-rush-scopes/index.js b/@commitlint/config-rush-scopes/index.js index f20d64b4b1..07fc2e1d07 100644 --- a/@commitlint/config-rush-scopes/index.js +++ b/@commitlint/config-rush-scopes/index.js @@ -1,13 +1,13 @@ -import Path from 'node:path'; -import fs from 'fs/promises'; +import Path from "node:path"; +import fs from "fs/promises"; -import jsonc from 'jsonc'; +import jsonc from "jsonc"; export default { - utils: {getPackages}, + utils: { getPackages }, rules: { - 'scope-enum': (ctx) => - getPackages(ctx).then((packages) => [2, 'always', packages]), + "scope-enum": (ctx) => + getPackages(ctx).then((packages) => [2, "always", packages]), }, }; @@ -18,15 +18,15 @@ function getPackages(context) { const cwd = ctx.cwd || process.cwd(); return fs - .readFile(Path.join(cwd, 'rush.json'), {encoding: 'utf8'}) + .readFile(Path.join(cwd, "rush.json"), { encoding: "utf8" }) .then((content) => jsonc.parse(content)) - .then(({projects}) => projects) + .then(({ projects }) => projects) .catch(() => []); }) .then((packages) => { return packages .map((pkg) => pkg.packageName) .filter(Boolean) - .map((name) => (name.charAt(0) === '@' ? name.split('/')[1] : name)); + .map((name) => (name.charAt(0) === "@" ? name.split("/")[1] : name)); }); } diff --git a/@commitlint/config-rush-scopes/index.test.js b/@commitlint/config-rush-scopes/index.test.js index 84b2e04bea..a5ce89033e 100644 --- a/@commitlint/config-rush-scopes/index.test.js +++ b/@commitlint/config-rush-scopes/index.test.js @@ -1,76 +1,76 @@ -import {test, expect} from 'vitest'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { test, expect } from "vitest"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {npm} from '@commitlint/test'; +import { npm } from "@commitlint/test"; -import config from './index.js'; +import config from "./index.js"; -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -test('exports rules key', () => { - expect(config).toHaveProperty('rules'); +test("exports rules key", () => { + expect(config).toHaveProperty("rules"); }); -test('rules hold object', () => { +test("rules hold object", () => { expect(config).toMatchObject({ rules: expect.any(Object), }); }); -test('rules contain scope-enum', () => { +test("rules contain scope-enum", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.anything(), + "scope-enum": expect.anything(), }, }); }); -test('scope-enum is function', () => { +test("scope-enum is function", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.any(Function), + "scope-enum": expect.any(Function), }, }); }); -test('scope-enum does not throw for missing context', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum does not throw for missing context", async () => { + const { "scope-enum": fn } = config.rules; await expect(fn()).resolves.toBeTruthy(); }); -test('scope-enum has expected severity', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected severity", async () => { + const { "scope-enum": fn } = config.rules; const [severity] = await fn(); expect(severity).toBe(2); }); -test('scope-enum has expected modifier', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected modifier", async () => { + const { "scope-enum": fn } = config.rules; const [, modifier] = await fn(); - expect(modifier).toBe('always'); + expect(modifier).toBe("always"); }); -test('returns empty value for empty rush repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/empty', __dirname); - const [, , value] = await fn({cwd}); +test("returns empty value for empty rush repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/empty", __dirname); + const [, , value] = await fn({ cwd }); expect(value).toEqual([]); }); -test('returns expected value for basic rush repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/basic', __dirname); +test("returns expected value for basic rush repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/basic", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['a', 'b']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["a", "b"]); }); -test('returns expected value for scoped lerna repository', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/scoped', __dirname); +test("returns expected value for scoped lerna repository", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/scoped", __dirname); - const [, , value] = await fn({cwd}); + const [, , value] = await fn({ cwd }); - expect(value).toEqual(['a', 'b']); + expect(value).toEqual(["a", "b"]); }); diff --git a/@commitlint/config-validator/src/commitlint.schema.json b/@commitlint/config-validator/src/commitlint.schema.json index 12998f4f49..2c6d2075a9 100644 --- a/@commitlint/config-validator/src/commitlint.schema.json +++ b/@commitlint/config-validator/src/commitlint.schema.json @@ -39,25 +39,25 @@ "oneOf": [ { "type": "array", - "items": {"type": "string"} + "items": { "type": "string" } }, - {"type": "string"} + { "type": "string" } ] }, "parserPreset": { "description": "Resolveable id to conventional-changelog parser preset to import and use", "oneOf": [ - {"type": "string"}, + { "type": "string" }, { "type": "object", "properties": { - "name": {"type": "string"}, - "path": {"type": "string"}, + "name": { "type": "string" }, + "path": { "type": "string" }, "parserOpts": {} }, "additionalProperties": true }, - {"typeof": "function"} + { "typeof": "function" } ] }, "helpUrl": { @@ -71,15 +71,15 @@ "rules": { "description": "Rules to check against", "type": "object", - "propertyNames": {"type": "string"}, - "additionalProperties": {"$ref": "#/definitions/rule"} + "propertyNames": { "type": "string" }, + "additionalProperties": { "$ref": "#/definitions/rule" } }, "plugins": { "description": "Resolveable ids of commitlint plugins from node_modules", "type": "array", "items": { "anyOf": [ - {"type": "string"}, + { "type": "string" }, { "type": "object", "required": ["rules"], @@ -94,7 +94,7 @@ }, "ignores": { "type": "array", - "items": {"typeof": "function"}, + "items": { "typeof": "function" }, "description": "Additional commits to ignore, defined by ignore matchers" }, "defaultIgnores": { diff --git a/@commitlint/config-validator/src/formatErrors.ts b/@commitlint/config-validator/src/formatErrors.ts index 3ca61d39a9..1021c92eb8 100644 --- a/@commitlint/config-validator/src/formatErrors.ts +++ b/@commitlint/config-validator/src/formatErrors.ts @@ -1,4 +1,4 @@ -import type {ErrorObject} from 'ajv'; +import type { ErrorObject } from "ajv"; /** * Formats an array of schema validation errors. @@ -10,8 +10,8 @@ export function formatErrors(errors: ErrorObject[]): string { return errors .map((error) => { if ( - error.keyword === 'additionalProperties' && - 'additionalProperty' in error.params + error.keyword === "additionalProperties" && + "additionalProperty" in error.params ) { const formattedPropertyPath = error.instancePath.length ? `${error.instancePath.slice(1)}.${error.params.additionalProperty}` @@ -19,7 +19,7 @@ export function formatErrors(errors: ErrorObject[]): string { return `Unexpected top-level property "${formattedPropertyPath}"`; } - if (error.keyword === 'type') { + if (error.keyword === "type") { const formattedField = error.instancePath.slice(1); if (!formattedField) { return `Config has the wrong type - ${error.message}`; @@ -27,19 +27,19 @@ export function formatErrors(errors: ErrorObject[]): string { return `Property "${formattedField}" has the wrong type - ${error.message}`; } const field = - (error.instancePath[0] === '.' + (error.instancePath[0] === "." ? error.instancePath.slice(1) - : error.instancePath) || 'Config'; - if (error.keyword === 'typeof') { + : error.instancePath) || "Config"; + if (error.keyword === "typeof") { return `"${field}" should be a ${error.schema}. Value: ${JSON.stringify( - error.data + error.data, )}`; } return `"${field}" ${error.message}. Value: ${JSON.stringify( - error.data + error.data, )}`; }) .map((message) => `\t- ${message}.\n`) - .join(''); + .join(""); } diff --git a/@commitlint/config-validator/src/validate.test.ts b/@commitlint/config-validator/src/validate.test.ts index f8e61e069c..1a3c402c4b 100644 --- a/@commitlint/config-validator/src/validate.test.ts +++ b/@commitlint/config-validator/src/validate.test.ts @@ -1,75 +1,75 @@ -import {describe, test, expect} from 'vitest'; -import {RuleConfigSeverity, UserConfig} from '@commitlint/types'; +import { describe, test, expect } from "vitest"; +import { RuleConfigSeverity, UserConfig } from "@commitlint/types"; -import {validateConfig} from './validate.js'; +import { validateConfig } from "./validate.js"; const validSchemas: Record<string, UserConfig> = { empty: {}, - withEmptyExtends: {extends: []}, - withStringExtends: {extends: 'test'}, - withSingleExtends: {extends: ['test']}, - withMultipleExtends: {extends: ['test', 'test2']}, - withFormatter: {formatter: ''}, - withHelpUrl: {helpUrl: ''}, + withEmptyExtends: { extends: [] }, + withStringExtends: { extends: "test" }, + withSingleExtends: { extends: ["test"] }, + withMultipleExtends: { extends: ["test", "test2"] }, + withFormatter: { formatter: "" }, + withHelpUrl: { helpUrl: "" }, withRules: { rules: { a: [RuleConfigSeverity.Disabled], - b: [RuleConfigSeverity.Warning, 'never'], - c: [RuleConfigSeverity.Error, 'never', true], + b: [RuleConfigSeverity.Warning, "never"], + c: [RuleConfigSeverity.Error, "never", true], }, }, - withParserPresetString: {parserPreset: 'test'}, - withParserPresetObject: {parserPreset: {}}, - withParserPresetObject2: {parserPreset: {name: 'string', path: 'string'}}, + withParserPresetString: { parserPreset: "test" }, + withParserPresetObject: { parserPreset: {} }, + withParserPresetObject2: { parserPreset: { name: "string", path: "string" } }, withParserPresetObjectPromise: { - parserPreset: Promise.resolve({name: 'string'}), + parserPreset: Promise.resolve({ name: "string" }), }, - withParserPresetOpts: {parserPreset: {parserOpts: {test: 1}}}, + withParserPresetOpts: { parserPreset: { parserOpts: { test: 1 } } }, withParserPresetOptsPromise: { - parserPreset: {parserOpts: Promise.resolve({test: 1})}, + parserPreset: { parserOpts: Promise.resolve({ test: 1 }) }, }, - withEmptyIgnores: {ignores: []}, - withIgnores: {ignores: [() => true]}, - withDefaultIgnoresTrue: {defaultIgnores: true}, - withDefaultIgnoresFalse: {defaultIgnores: false}, - withEmptyPlugins: {plugins: []}, - withPluginsAsString: {plugins: ['test']}, - withPluginsAsObject: {plugins: [{rules: {}}]}, - shouldSkipAllowAdditionalProperties: {foo: 1}, + withEmptyIgnores: { ignores: [] }, + withIgnores: { ignores: [() => true] }, + withDefaultIgnoresTrue: { defaultIgnores: true }, + withDefaultIgnoresFalse: { defaultIgnores: false }, + withEmptyPlugins: { plugins: [] }, + withPluginsAsString: { plugins: ["test"] }, + withPluginsAsObject: { plugins: [{ rules: {} }] }, + shouldSkipAllowAdditionalProperties: { foo: 1 }, }; const invalidSchemas: Record<string, any> = { whenConfigIsNotObject: [], - whenConfigIsNotObject2: '', - extendsAsObject: {extends: {test: 1}}, - extendsWithFunction: {extends: [() => true]}, - formatterAsObject: {formatter: {}}, - helpUrlAsArray: {helpUrl: []}, - rulesAsArray: {rules: ['a']}, - rules1: {rules: {a: [3]}}, - rules2: {rules: {b: [1, 'test', 2, 2]}}, - rules3: {rules: {c: []}}, - rules4: {rules: {d: [[], [], []]}}, - rules5: {rules: {e: {}}}, - parserPreset: {parserPreset: []}, - ignoresFunction: {ignores: () => true}, - ignoresNotFunction: {ignores: [1]}, - defaultIgnoresNotBoolean: {defaultIgnores: 'true'}, - pluginsNotArray: {plugins: 'test'}, - withPluginsAsObject: {plugins: [{}]}, - helpUrlNotString: {helpUrl: {}}, + whenConfigIsNotObject2: "", + extendsAsObject: { extends: { test: 1 } }, + extendsWithFunction: { extends: [() => true] }, + formatterAsObject: { formatter: {} }, + helpUrlAsArray: { helpUrl: [] }, + rulesAsArray: { rules: ["a"] }, + rules1: { rules: { a: [3] } }, + rules2: { rules: { b: [1, "test", 2, 2] } }, + rules3: { rules: { c: [] } }, + rules4: { rules: { d: [[], [], []] } }, + rules5: { rules: { e: {} } }, + parserPreset: { parserPreset: [] }, + ignoresFunction: { ignores: () => true }, + ignoresNotFunction: { ignores: [1] }, + defaultIgnoresNotBoolean: { defaultIgnores: "true" }, + pluginsNotArray: { plugins: "test" }, + withPluginsAsObject: { plugins: [{}] }, + helpUrlNotString: { helpUrl: {} }, }; -describe('validation should pass for', () => { - test.each(Object.entries(validSchemas))('%s', (file, config) => { +describe("validation should pass for", () => { + test.each(Object.entries(validSchemas))("%s", (file, config) => { expect(() => validateConfig(`${file}.js`, config)).not.toThrow(); }); }); -describe('validation should fail for', () => { - test.each(Object.entries(invalidSchemas))('%s', (file, config) => { +describe("validation should fail for", () => { + test.each(Object.entries(invalidSchemas))("%s", (file, config) => { expect(() => - validateConfig(`${file}.js`, config) + validateConfig(`${file}.js`, config), ).toThrowErrorMatchingSnapshot(); }); }); diff --git a/@commitlint/config-validator/src/validate.ts b/@commitlint/config-validator/src/validate.ts index 5eec2704cc..d4c28a2c7a 100644 --- a/@commitlint/config-validator/src/validate.ts +++ b/@commitlint/config-validator/src/validate.ts @@ -1,22 +1,22 @@ -import {createRequire} from 'node:module'; +import { createRequire } from "node:module"; -import {UserConfig} from '@commitlint/types'; -import _Ajv from 'ajv'; +import { UserConfig } from "@commitlint/types"; +import _Ajv from "ajv"; -import {formatErrors} from './formatErrors.js'; +import { formatErrors } from "./formatErrors.js"; const require = createRequire(import.meta.url); -const schema: typeof import('./commitlint.schema.json') = require('./commitlint.schema.json'); +const schema: typeof import("./commitlint.schema.json") = require("./commitlint.schema.json"); const TYPE_OF = [ - 'undefined', - 'string', - 'number', - 'object', - 'function', - 'boolean', - 'symbol', + "undefined", + "string", + "number", + "object", + "function", + "boolean", + "symbol", ]; // FIXME: https://github.com/ajv-validator/ajv/issues/2132 @@ -24,7 +24,7 @@ const Ajv = _Ajv as unknown as typeof _Ajv.default; export function validateConfig( source: string, - config: unknown + config: unknown, ): asserts config is UserConfig { const ajv = new Ajv({ meta: false, @@ -35,11 +35,11 @@ export function validateConfig( }); ajv.addKeyword({ - keyword: 'typeof', + keyword: "typeof", validate: function typeOfFunc(schema: any, data: any) { return typeof data === schema; }, - metaSchema: {type: 'string', enum: TYPE_OF}, + metaSchema: { type: "string", enum: TYPE_OF }, schema: true, }); @@ -49,8 +49,8 @@ export function validateConfig( if (!isValid && validate.errors && validate.errors.length) { throw new Error( `Commitlint configuration in ${source} is invalid:\n${formatErrors( - validate.errors - )}` + validate.errors, + )}`, ); } } diff --git a/@commitlint/config-validator/tsconfig.json b/@commitlint/config-validator/tsconfig.json index 65f2e6c397..5ef37ea5e3 100644 --- a/@commitlint/config-validator/tsconfig.json +++ b/@commitlint/config-validator/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src/**/*.ts", "./src/**/*.json"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../types"}] + "references": [{ "path": "../types" }] } diff --git a/@commitlint/config-workspace-scopes/index.js b/@commitlint/config-workspace-scopes/index.js index c365c099d6..e4fc5ea0f3 100644 --- a/@commitlint/config-workspace-scopes/index.js +++ b/@commitlint/config-workspace-scopes/index.js @@ -1,15 +1,15 @@ -import {createRequire} from 'node:module'; -import Path from 'node:path'; +import { createRequire } from "node:module"; +import Path from "node:path"; -import {globSync} from 'glob'; +import { globSync } from "glob"; const require = createRequire(import.meta.url); export default { - utils: {getPackages}, + utils: { getPackages }, rules: { - 'scope-enum': (ctx) => - getPackages(ctx).then((packages) => [2, 'always', packages]), + "scope-enum": (ctx) => + getPackages(ctx).then((packages) => [2, "always", packages]), }, }; @@ -19,15 +19,15 @@ function getPackages(context) { const ctx = context || {}; const cwd = ctx.cwd || process.cwd(); - const {workspaces} = require(Path.join(cwd, 'package.json')); + const { workspaces } = require(Path.join(cwd, "package.json")); if (!Array.isArray(workspaces)) { // no workspaces configured, skipping return []; } const wsGlobs = workspaces.flatMap((ws) => { - const path = Path.posix.join(ws, 'package.json'); - return globSync(path, {cwd, ignore: ['**/node_modules/**']}); + const path = Path.posix.join(ws, "package.json"); + return globSync(path, { cwd, ignore: ["**/node_modules/**"] }); }); return wsGlobs.sort().map((pJson) => require(Path.join(cwd, pJson))); @@ -36,6 +36,6 @@ function getPackages(context) { return packages .map((pkg) => pkg.name) .filter(Boolean) - .map((name) => (name.charAt(0) === '@' ? name.split('/')[1] : name)); + .map((name) => (name.charAt(0) === "@" ? name.split("/")[1] : name)); }); } diff --git a/@commitlint/config-workspace-scopes/index.test.js b/@commitlint/config-workspace-scopes/index.test.js index e969f4dc58..a7d09239a0 100644 --- a/@commitlint/config-workspace-scopes/index.test.js +++ b/@commitlint/config-workspace-scopes/index.test.js @@ -1,86 +1,86 @@ -import {test, expect} from 'vitest'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { test, expect } from "vitest"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {npm} from '@commitlint/test'; +import { npm } from "@commitlint/test"; -import config from './index.js'; +import config from "./index.js"; -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -test('exports rules key', () => { - expect(config).toHaveProperty('rules'); +test("exports rules key", () => { + expect(config).toHaveProperty("rules"); }); -test('rules hold object', () => { +test("rules hold object", () => { expect(config).toMatchObject({ rules: expect.any(Object), }); }); -test('rules contain scope-enum', () => { +test("rules contain scope-enum", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.anything(), + "scope-enum": expect.anything(), }, }); }); -test('scope-enum is function', () => { +test("scope-enum is function", () => { expect(config).toMatchObject({ rules: { - 'scope-enum': expect.any(Function), + "scope-enum": expect.any(Function), }, }); }); -test('scope-enum does not throw for missing context', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum does not throw for missing context", async () => { + const { "scope-enum": fn } = config.rules; await expect(fn()).resolves.toBeTruthy(); }); -test('scope-enum has expected severity', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected severity", async () => { + const { "scope-enum": fn } = config.rules; const [severity] = await fn(); expect(severity).toBe(2); }); -test('scope-enum has expected modifier', async () => { - const {'scope-enum': fn} = config.rules; +test("scope-enum has expected modifier", async () => { + const { "scope-enum": fn } = config.rules; const [, modifier] = await fn(); - expect(modifier).toBe('always'); + expect(modifier).toBe("always"); }); -test('returns empty value for empty workspaces', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/empty', __dirname); - const [, , value] = await fn({cwd}); +test("returns empty value for empty workspaces", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/empty", __dirname); + const [, , value] = await fn({ cwd }); expect(value).toEqual([]); }); -test('returns expected value for basic workspaces', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/basic', __dirname); +test("returns expected value for basic workspaces", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/basic", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['a', 'b']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["a", "b"]); }); -test('returns expected value for scoped workspaces', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/scoped', __dirname); +test("returns expected value for scoped workspaces", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/scoped", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(['a', 'b']); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(["a", "b"]); }); -test('returns expected value for workspaces has nested packages', async () => { - const {'scope-enum': fn} = config.rules; - const cwd = await npm.bootstrap('fixtures/nested-workspaces', __dirname); +test("returns expected value for workspaces has nested packages", async () => { + const { "scope-enum": fn } = config.rules; + const cwd = await npm.bootstrap("fixtures/nested-workspaces", __dirname); - const [, , value] = await fn({cwd}); - expect(value).toEqual(expect.arrayContaining(['nested-a', 'nested-b'])); + const [, , value] = await fn({ cwd }); + expect(value).toEqual(expect.arrayContaining(["nested-a", "nested-b"])); expect(value).toEqual( - expect.not.arrayContaining(['dependency-a', 'dependency-b']) + expect.not.arrayContaining(["dependency-a", "dependency-b"]), ); }); diff --git a/@commitlint/core/src/core.ts b/@commitlint/core/src/core.ts index eeee4f41b5..3181e0ac71 100644 --- a/@commitlint/core/src/core.ts +++ b/@commitlint/core/src/core.ts @@ -1,6 +1,6 @@ -import format from '@commitlint/format'; -import load from '@commitlint/load'; -import lint from '@commitlint/lint'; -import read from '@commitlint/read'; +import format from "@commitlint/format"; +import load from "@commitlint/load"; +import lint from "@commitlint/lint"; +import read from "@commitlint/read"; -export {format, load, lint, read}; +export { format, load, lint, read }; diff --git a/@commitlint/cz-commitlint/src/Process.test.ts b/@commitlint/cz-commitlint/src/Process.test.ts index 7c6def0f1e..fefca0c40a 100644 --- a/@commitlint/cz-commitlint/src/Process.test.ts +++ b/@commitlint/cz-commitlint/src/Process.test.ts @@ -1,13 +1,13 @@ -import {describe, test, expect, vi, beforeEach, afterEach} from 'vitest'; +import { describe, test, expect, vi, beforeEach, afterEach } from "vitest"; import { QualifiedRules, RuleConfigSeverity, UserPromptConfig, -} from '@commitlint/types'; -import {Answers, DistinctQuestion} from 'inquirer'; -import isFunction from 'lodash.isfunction'; +} from "@commitlint/types"; +import { Answers, DistinctQuestion } from "inquirer"; +import isFunction from "lodash.isfunction"; -import process from './Process.js'; +import process from "./Process.js"; const mockShowTitle = vi.fn(); const mockShowValidation = vi.fn((message) => message); @@ -15,23 +15,23 @@ const mockShowValidation = vi.fn((message) => message); // mock inquirer const mockPrompt = vi.fn(async function ( questions: DistinctQuestion[], - answers: Answers + answers: Answers, ) { - for (const {name, message, when, filter, validate} of questions) { - if (typeof when !== 'function' || (await when(answers))) { + for (const { name, message, when, filter, validate } of questions) { + if (typeof when !== "function" || (await when(answers))) { const title = message && isFunction(message) ? await message(answers) - : typeof message === 'string' - ? message - : ''; + : typeof message === "string" + ? message + : ""; mockShowTitle(title); const validation = - typeof validate !== 'function' || - (await validate((name && answers[name]) ?? '', answers)); + typeof validate !== "function" || + (await validate((name && answers[name]) ?? "", answers)); - if (typeof validation === 'string') { + if (typeof validation === "string") { mockShowValidation(validation); break; } else if (filter && name && answers[name]) { @@ -53,12 +53,12 @@ function InquirerFactory(answers: Answers) { } const MESSAGES = { - skip: '(press enter to skip)', - max: 'upper %d chars', - min: '%d chars at least', - emptyWarning: '%s can not be empty', - upperLimitWarning: '%s: %s over limit %d', - lowerLimitWarning: '%s: %s below limit %d', + skip: "(press enter to skip)", + max: "upper %d chars", + min: "%d chars at least", + emptyWarning: "%s can not be empty", + upperLimitWarning: "%s: %s over limit %d", + lowerLimitWarning: "%s: %s below limit %d", }; let rules: QualifiedRules; @@ -69,38 +69,38 @@ afterEach(() => { mockShowValidation.mockClear(); }); -describe('conventional-changlog', () => { +describe("conventional-changlog", () => { beforeEach(() => { rules = { - 'body-leading-blank': [RuleConfigSeverity.Warning, 'always'], - 'body-max-line-length': [RuleConfigSeverity.Error, 'always', 100], - 'footer-leading-blank': [RuleConfigSeverity.Warning, 'always'], - 'footer-max-line-length': [RuleConfigSeverity.Error, 'always', 100], - 'header-max-length': [RuleConfigSeverity.Error, 'always', 100], - 'subject-case': [ + "body-leading-blank": [RuleConfigSeverity.Warning, "always"], + "body-max-line-length": [RuleConfigSeverity.Error, "always", 100], + "footer-leading-blank": [RuleConfigSeverity.Warning, "always"], + "footer-max-line-length": [RuleConfigSeverity.Error, "always", 100], + "header-max-length": [RuleConfigSeverity.Error, "always", 100], + "subject-case": [ RuleConfigSeverity.Error, - 'never', - ['sentence-case', 'start-case', 'pascal-case', 'upper-case'], + "never", + ["sentence-case", "start-case", "pascal-case", "upper-case"], ], - 'subject-empty': [RuleConfigSeverity.Error, 'never'], - 'subject-full-stop': [RuleConfigSeverity.Error, 'never', '.'], - 'type-case': [RuleConfigSeverity.Error, 'always', 'lower-case'], - 'type-empty': [RuleConfigSeverity.Error, 'never'], - 'type-enum': [ + "subject-empty": [RuleConfigSeverity.Error, "never"], + "subject-full-stop": [RuleConfigSeverity.Error, "never", "."], + "type-case": [RuleConfigSeverity.Error, "always", "lower-case"], + "type-empty": [RuleConfigSeverity.Error, "never"], + "type-enum": [ RuleConfigSeverity.Error, - 'always', + "always", [ - 'build', - 'chore', - 'ci', - 'docs', - 'feat', - 'fix', - 'perf', - 'refactor', - 'revert', - 'style', - 'test', + "build", + "chore", + "ci", + "docs", + "feat", + "fix", + "perf", + "refactor", + "revert", + "style", + "test", ], ], }; @@ -111,93 +111,93 @@ describe('conventional-changlog', () => { description: "Select the type of change that you're committing:", enum: { feat: { - description: 'A new feature', - title: 'Features', - emoji: '✨', + description: "A new feature", + title: "Features", + emoji: "✨", }, fix: { - description: 'A bug fix', - title: 'Bug Fixes', - emoji: '🐛', + description: "A bug fix", + title: "Bug Fixes", + emoji: "🐛", }, docs: { - description: 'Documentation only changes', - title: 'Documentation', - emoji: '📚', + description: "Documentation only changes", + title: "Documentation", + emoji: "📚", }, style: { description: - 'Changes that do not affect the meaning of the code (white-space, formatting, missing semi-colons, etc)', - title: 'Styles', - emoji: '💎', + "Changes that do not affect the meaning of the code (white-space, formatting, missing semi-colons, etc)", + title: "Styles", + emoji: "💎", }, refactor: { description: - 'A code change that neither fixes a bug nor adds a feature', - title: 'Code Refactoring', - emoji: '📦', + "A code change that neither fixes a bug nor adds a feature", + title: "Code Refactoring", + emoji: "📦", }, perf: { - description: 'A code change that improves performance', - title: 'Performance Improvements', - emoji: '🚀', + description: "A code change that improves performance", + title: "Performance Improvements", + emoji: "🚀", }, test: { - description: 'Adding missing tests or correcting existing tests', - title: 'Tests', - emoji: '🚨', + description: "Adding missing tests or correcting existing tests", + title: "Tests", + emoji: "🚨", }, build: { description: - 'Changes that affect the build system or external dependencies (example scopes: gulp, broccoli, npm)', - title: 'Builds', - emoji: '🛠', + "Changes that affect the build system or external dependencies (example scopes: gulp, broccoli, npm)", + title: "Builds", + emoji: "🛠", }, ci: { description: - 'Changes to our CI configuration files and scripts (example scopes: Travis, Circle, BrowserStack, SauceLabs)', - title: 'Continuous Integrations', - emoji: '⚙️', + "Changes to our CI configuration files and scripts (example scopes: Travis, Circle, BrowserStack, SauceLabs)", + title: "Continuous Integrations", + emoji: "⚙️", }, chore: { description: "Other changes that don't modify src or test files", - title: 'Chores', - emoji: '♻️', + title: "Chores", + emoji: "♻️", }, revert: { - description: 'Reverts a previous commit', - title: 'Reverts', - emoji: '🗑', + description: "Reverts a previous commit", + title: "Reverts", + emoji: "🗑", }, }, }, scope: { description: - 'What is the scope of this change (e.g. component or file name)', + "What is the scope of this change (e.g. component or file name)", }, subject: { description: - 'Write a short, imperative tense description of the change', + "Write a short, imperative tense description of the change", }, body: { - description: 'Provide a longer description of the change', + description: "Provide a longer description of the change", }, isBreaking: { - description: 'Are there any breaking changes?', + description: "Are there any breaking changes?", }, breakingBody: { description: - 'A BREAKING CHANGE commit requires a body. Please enter a longer description of the commit itself', + "A BREAKING CHANGE commit requires a body. Please enter a longer description of the commit itself", }, breaking: { - description: 'Describe the breaking changes', + description: "Describe the breaking changes", }, isIssueAffected: { - description: 'Does this change affect any open issues?', + description: "Does this change affect any open issues?", }, issuesBody: { description: - 'If issues are closed, the commit requires a body. Please enter a longer description of the commit itself', + "If issues are closed, the commit requires a body. Please enter a longer description of the commit itself", }, issues: { description: 'Add issue references (e.g. "fix #123", "re #123".)', @@ -205,39 +205,39 @@ describe('conventional-changlog', () => { }, }; }); - test('should process works well', () => { + test("should process works well", () => { const answers = { - type: 'refactor', - scope: 'prompt', - subject: 'refactor prompt based on inquirer', - body: 'inspired by commitizen/cz-conventional-changelog', + type: "refactor", + scope: "prompt", + subject: "refactor prompt based on inquirer", + body: "inspired by commitizen/cz-conventional-changelog", isBreaking: true, - breaking: 'refactor types', + breaking: "refactor types", isIssueAffected: true, - issues: 'https://github.com/conventional-changelog/commitlint/issues/94', + issues: "https://github.com/conventional-changelog/commitlint/issues/94", }; return process(rules, prompts, InquirerFactory(answers)).then( (commitMessage) => { expect(commitMessage).toBe( - 'refactor(prompt): refactor prompt based on inquirer\n\ninspired by commitizen/cz-conventional-changelog\n\nBREAKING CHANGE: refactor types\nhttps://github.com/conventional-changelog/commitlint/issues/94' + "refactor(prompt): refactor prompt based on inquirer\n\ninspired by commitizen/cz-conventional-changelog\n\nBREAKING CHANGE: refactor types\nhttps://github.com/conventional-changelog/commitlint/issues/94", ); - } + }, ); }); - test('should show validation and stop process when subject is empty', () => { + test("should show validation and stop process when subject is empty", () => { const answers = { - type: 'refactor', - scope: 'prompt', - body: 'inspired by commitizen/cz-conventional-changelog', + type: "refactor", + scope: "prompt", + body: "inspired by commitizen/cz-conventional-changelog", isBreaking: true, - breaking: 'refactor types', + breaking: "refactor types", isIssueAffected: true, - issues: 'https://github.com/conventional-changelog/commitlint/issues/94', + issues: "https://github.com/conventional-changelog/commitlint/issues/94", }; return process(rules, prompts, InquirerFactory(answers)).then(() => { expect(mockShowValidation).toHaveBeenCalledWith( - 'subject can not be empty' + "subject can not be empty", ); expect(mockShowTitle).toHaveBeenCalledTimes(3); }); diff --git a/@commitlint/cz-commitlint/src/Process.ts b/@commitlint/cz-commitlint/src/Process.ts index 4023477bff..48ec039d6f 100644 --- a/@commitlint/cz-commitlint/src/Process.ts +++ b/@commitlint/cz-commitlint/src/Process.ts @@ -1,27 +1,27 @@ -import {QualifiedRules, UserPromptConfig} from '@commitlint/types'; -import type {Answers, DistinctQuestion} from 'inquirer'; +import { QualifiedRules, UserPromptConfig } from "@commitlint/types"; +import type { Answers, DistinctQuestion } from "inquirer"; import { combineCommitMessage as combineBody, getQuestions as getBodyQuestions, -} from './SectionBody.js'; +} from "./SectionBody.js"; import { combineCommitMessage as combineFooter, getQuestions as getFooterQuestions, -} from './SectionFooter.js'; +} from "./SectionFooter.js"; import { combineCommitMessage as combineHeader, getQuestions as getHeaderQuestions, -} from './SectionHeader.js'; -import {setPromptConfig} from './store/prompts.js'; -import {setRules} from './store/rules.js'; +} from "./SectionHeader.js"; +import { setPromptConfig } from "./store/prompts.js"; +import { setRules } from "./store/rules.js"; export default async function ( rules: QualifiedRules, prompts: UserPromptConfig, inquirer: { prompt(questions: DistinctQuestion[]): Promise<Answers>; - } + }, ): Promise<string> { setRules(rules); setPromptConfig(prompts); @@ -35,5 +35,5 @@ export default async function ( const body = combineBody(answers); const footer = combineFooter(answers); - return [header, body, footer].filter(Boolean).join('\n'); + return [header, body, footer].filter(Boolean).join("\n"); } diff --git a/@commitlint/cz-commitlint/src/Question.test.ts b/@commitlint/cz-commitlint/src/Question.test.ts index fd9ea3eb7f..d04ba708fb 100644 --- a/@commitlint/cz-commitlint/src/Question.test.ts +++ b/@commitlint/cz-commitlint/src/Question.test.ts @@ -1,19 +1,19 @@ -import {describe, test, expect, vi} from 'vitest'; -import chalk from 'chalk'; -import inquirer, {Answers, InputQuestionOptions} from 'inquirer'; +import { describe, test, expect, vi } from "vitest"; +import chalk from "chalk"; +import inquirer, { Answers, InputQuestionOptions } from "inquirer"; -import Question from './Question.js'; +import Question from "./Question.js"; const MESSAGES = { - skip: '(press enter to skip)', - max: 'upper %d chars', - min: '%d chars at least', - emptyWarning: '%s can not be empty', - upperLimitWarning: '%s: %s over limit %d', - lowerLimitWarning: '%s: %s below limit %d', + skip: "(press enter to skip)", + max: "upper %d chars", + min: "%d chars at least", + emptyWarning: "%s can not be empty", + upperLimitWarning: "%s: %s over limit %d", + lowerLimitWarning: "%s: %s below limit %d", }; const QUESTION_CONFIG = { - title: 'please input', + title: "please input", messages: MESSAGES, }; @@ -22,347 +22,347 @@ const caseFn = (input: string | string[], delimiter?: string) => .map((segment) => segment[0].toUpperCase() + segment.slice(1)) .join(delimiter); -describe('name', () => { - test('should throw error when name is not a meaningful string', () => { +describe("name", () => { + test("should throw error when name is not a meaningful string", () => { expect( () => - new Question('' as any, { + new Question("" as any, { ...QUESTION_CONFIG, - }) + }), ).toThrow(); expect( () => new Question( function () { - return 'scope'; + return "scope"; } as any, { ...QUESTION_CONFIG, - } - ) + }, + ), ).toThrow(); }); - test('should set name when name is valid', () => { + test("should set name when name is valid", () => { expect( - new Question('test' as any, { + new Question("test" as any, { ...QUESTION_CONFIG, - }).question - ).toHaveProperty('name', 'test'); + }).question, + ).toHaveProperty("name", "test"); }); }); -describe('type', () => { +describe("type", () => { test('should return "list" type when enumList is array and multipleSelectDefaultDelimiter is undefined', () => { - const question = new Question('scope', { + const question = new Question("scope", { ...QUESTION_CONFIG, - enumList: ['cli', 'core'], + enumList: ["cli", "core"], }).question; - expect(question).toHaveProperty('type', 'list'); - expect(question).toHaveProperty('choices', ['cli', 'core']); - expect(question).not.toHaveProperty('transformer'); + expect(question).toHaveProperty("type", "list"); + expect(question).toHaveProperty("choices", ["cli", "core"]); + expect(question).not.toHaveProperty("transformer"); }); test('should return "checkbox" type when enumList is array and multipleSelectDefaultDelimiter is defined', () => { - const question = new Question('scope', { + const question = new Question("scope", { ...QUESTION_CONFIG, - enumList: ['cli', 'core'], - multipleSelectDefaultDelimiter: ',', + enumList: ["cli", "core"], + multipleSelectDefaultDelimiter: ",", }).question; - expect(question).toHaveProperty('type', 'checkbox'); - expect(question).toHaveProperty('choices', ['cli', 'core']); - expect(question).not.toHaveProperty('transformer'); + expect(question).toHaveProperty("type", "checkbox"); + expect(question).toHaveProperty("choices", ["cli", "core"]); + expect(question).not.toHaveProperty("transformer"); }); test('should contain "skip" list item when enumList is array and skip is true', () => { - const question = new Question('scope', { + const question = new Question("scope", { ...QUESTION_CONFIG, - enumList: ['cli', 'core'], + enumList: ["cli", "core"], skip: true, }).question; - expect(question).toHaveProperty('type', 'list'); - expect(question).toHaveProperty('choices', [ - 'cli', - 'core', + expect(question).toHaveProperty("type", "list"); + expect(question).toHaveProperty("choices", [ + "cli", + "core", new inquirer.Separator(), { - name: 'empty', - value: '', + name: "empty", + value: "", }, ]); - expect(question).not.toHaveProperty('transformer'); + expect(question).not.toHaveProperty("transformer"); }); test('should return "confirm" type when name is start with "is"', () => { - const question = new Question('isSubmit' as any, { + const question = new Question("isSubmit" as any, { ...QUESTION_CONFIG, }).question; - expect(question).toHaveProperty('type', 'confirm'); - expect(question).not.toHaveProperty('choices'); - expect(question).not.toHaveProperty('transformer'); + expect(question).toHaveProperty("type", "confirm"); + expect(question).not.toHaveProperty("choices"); + expect(question).not.toHaveProperty("transformer"); }); test('should return "input" type in other cases', () => { - const question = new Question('body', { + const question = new Question("body", { ...QUESTION_CONFIG, }).question; - expect(question).toHaveProperty('type', 'input'); - expect(question).not.toHaveProperty('choices'); - expect(question).toHaveProperty('transformer', expect.any(Function)); + expect(question).toHaveProperty("type", "input"); + expect(question).not.toHaveProperty("choices"); + expect(question).toHaveProperty("transformer", expect.any(Function)); }); }); -describe('message', () => { - test('should display title when it is not input', () => { - const question = new Question('body', { +describe("message", () => { + test("should display title when it is not input", () => { + const question = new Question("body", { ...QUESTION_CONFIG, - enumList: ['cli', 'core'], + enumList: ["cli", "core"], }).question; - expect(question).toHaveProperty('message', expect.any(Function)); - expect((question.message as any)()).toBe('please input:'); + expect(question).toHaveProperty("message", expect.any(Function)); + expect((question.message as any)()).toBe("please input:"); }); - test('should display skip hint when it is input and can skip', () => { - const question = new Question('body' as any, { + test("should display skip hint when it is input and can skip", () => { + const question = new Question("body" as any, { ...QUESTION_CONFIG, skip: true, }).question; - expect(question).toHaveProperty('message', expect.any(Function)); + expect(question).toHaveProperty("message", expect.any(Function)); expect((question.message as any)()).toBe( - 'please input (press enter to skip):\n' + "please input (press enter to skip):\n", ); }); - test('should not display skip hint when it is input and without skip string', () => { - const question = new Question('scope', { + test("should not display skip hint when it is input and without skip string", () => { + const question = new Question("scope", { ...QUESTION_CONFIG, messages: {}, skip: true, } as any).question; - expect(question).toHaveProperty('message', expect.any(Function)); - expect((question.message as any)()).toBe('please input:\n'); + expect(question).toHaveProperty("message", expect.any(Function)); + expect((question.message as any)()).toBe("please input:\n"); }); - test('should display upper limit hint when it is input and has max length', () => { - const question = new Question('scope', { + test("should display upper limit hint when it is input and has max length", () => { + const question = new Question("scope", { ...QUESTION_CONFIG, maxLength: 80, } as any).question; - expect(question).toHaveProperty('message', expect.any(Function)); - expect((question.message as any)()).toBe('please input: upper 80 chars\n'); + expect(question).toHaveProperty("message", expect.any(Function)); + expect((question.message as any)()).toBe("please input: upper 80 chars\n"); }); - test('should display lower limit hint when it is input and has min length', () => { - const question = new Question('scope', { + test("should display lower limit hint when it is input and has min length", () => { + const question = new Question("scope", { ...QUESTION_CONFIG, minLength: 10, } as any).question; - expect(question).toHaveProperty('message', expect.any(Function)); + expect(question).toHaveProperty("message", expect.any(Function)); expect((question.message as any)()).toBe( - 'please input: 10 chars at least\n' + "please input: 10 chars at least\n", ); }); - test('should display hints with correct format', () => { - const question = new Question('scope', { + test("should display hints with correct format", () => { + const question = new Question("scope", { ...QUESTION_CONFIG, minLength: 10, maxLength: 80, skip: true, } as any).question; - expect(question).toHaveProperty('message', expect.any(Function)); + expect(question).toHaveProperty("message", expect.any(Function)); expect((question.message as any)()).toBe( - 'please input (press enter to skip): 10 chars at least, upper 80 chars\n' + "please input (press enter to skip): 10 chars at least, upper 80 chars\n", ); }); - test('should execute function beforeQuestionStart when init message', () => { + test("should execute function beforeQuestionStart when init message", () => { const mockFn = vi.fn(); class CustomQuestion extends Question { beforeQuestionStart(answers: Answers): void { mockFn(answers); } } - const question = new CustomQuestion('body', { + const question = new CustomQuestion("body", { ...QUESTION_CONFIG, } as any).question; - expect(question).toHaveProperty('message', expect.any(Function)); + expect(question).toHaveProperty("message", expect.any(Function)); const answers = { - header: 'This is header', - footer: 'This is footer', + header: "This is header", + footer: "This is footer", }; (question.message as any)(answers); expect(mockFn).toHaveBeenCalledWith(answers); }); }); -describe('filter', () => { - test('should auto fix case and full-stop', () => { - const question = new Question('body', { +describe("filter", () => { + test("should auto fix case and full-stop", () => { + const question = new Question("body", { ...QUESTION_CONFIG, caseFn, - fullStopFn: (input: string) => input + '!', + fullStopFn: (input: string) => input + "!", }).question; - expect(question.filter?.('xxxx', {})).toBe('Xxxx!'); + expect(question.filter?.("xxxx", {})).toBe("Xxxx!"); }); - test('should transform each item with same case when input is array', () => { - const question = new Question('body', { + test("should transform each item with same case when input is array", () => { + const question = new Question("body", { ...QUESTION_CONFIG, caseFn, - fullStopFn: (input: string) => input + '!', + fullStopFn: (input: string) => input + "!", }).question; - expect(question.filter?.(['xxxx', 'yyyy'], {})).toBe('Xxxx,Yyyy!'); + expect(question.filter?.(["xxxx", "yyyy"], {})).toBe("Xxxx,Yyyy!"); }); - test('should concat items with multipleSelectDefaultDelimiter when input is array', () => { - const question = new Question('body', { + test("should concat items with multipleSelectDefaultDelimiter when input is array", () => { + const question = new Question("body", { ...QUESTION_CONFIG, caseFn, - fullStopFn: (input: string) => input + '!', - multipleSelectDefaultDelimiter: '|', + fullStopFn: (input: string) => input + "!", + multipleSelectDefaultDelimiter: "|", }).question; - expect(question.filter?.(['xxxx', 'yyyy'], {})).toBe('Xxxx|Yyyy!'); + expect(question.filter?.(["xxxx", "yyyy"], {})).toBe("Xxxx|Yyyy!"); }); - test('should split the string to items when multipleValueDelimiters is defined', () => { - const question = new Question('body', { + test("should split the string to items when multipleValueDelimiters is defined", () => { + const question = new Question("body", { ...QUESTION_CONFIG, caseFn, - fullStopFn: (input: string) => input + '!', + fullStopFn: (input: string) => input + "!", multipleValueDelimiters: /,|\|/g, }).question; - expect(question.filter?.('xxxx,yyyy|zzzz', {})).toBe('Xxxx,Yyyy|Zzzz!'); - expect(question.filter?.('xxxx-yyyy-zzzz', {})).toBe('Xxxx-yyyy-zzzz!'); + expect(question.filter?.("xxxx,yyyy|zzzz", {})).toBe("Xxxx,Yyyy|Zzzz!"); + expect(question.filter?.("xxxx-yyyy-zzzz", {})).toBe("Xxxx-yyyy-zzzz!"); }); - test('should works well when does not pass caseFn/fullStopFn', () => { - const question = new Question('body', { + test("should works well when does not pass caseFn/fullStopFn", () => { + const question = new Question("body", { ...QUESTION_CONFIG, }).question; - expect(question.filter?.('xxxx', {})).toBe('xxxx'); + expect(question.filter?.("xxxx", {})).toBe("xxxx"); }); }); -describe('validate', () => { - test('should display empty warning when can not skip but string is empty', () => { - const question = new Question('body', { +describe("validate", () => { + test("should display empty warning when can not skip but string is empty", () => { + const question = new Question("body", { ...QUESTION_CONFIG, skip: false, }).question; - expect(question.validate?.('')).toBe('body can not be empty'); + expect(question.validate?.("")).toBe("body can not be empty"); }); - test('should ignore empty validation when can skip', () => { - const question = new Question('body', { + test("should ignore empty validation when can skip", () => { + const question = new Question("body", { ...QUESTION_CONFIG, skip: true, }).question; - expect(question.validate?.('')).toBe(true); + expect(question.validate?.("")).toBe(true); }); - test('should display upper limit warning when char count is over upper limit', () => { - const question = new Question('body', { + test("should display upper limit warning when char count is over upper limit", () => { + const question = new Question("body", { ...QUESTION_CONFIG, maxLength: 5, }).question; - expect(question.validate?.('xxxxxx')).toBe('body: body over limit 1'); + expect(question.validate?.("xxxxxx")).toBe("body: body over limit 1"); }); - test('should display lower limit warning when char count is less than lower limit', () => { - const question = new Question('body', { + test("should display lower limit warning when char count is less than lower limit", () => { + const question = new Question("body", { ...QUESTION_CONFIG, minLength: 5, }).question; - expect(question.validate?.('xxx')).toBe('body: body below limit 2'); + expect(question.validate?.("xxx")).toBe("body: body below limit 2"); }); - test('should validate the final submit string', () => { - const question = new Question('body', { + test("should validate the final submit string", () => { + const question = new Question("body", { ...QUESTION_CONFIG, - caseFn: () => '', + caseFn: () => "", skip: false, }).question; - expect(question.validate?.('xxxx')).not.toBe(true); + expect(question.validate?.("xxxx")).not.toBe(true); }); }); -describe('transformer', () => { - test('should auto transform case and full-stop', () => { - const question = new Question('body', { +describe("transformer", () => { + test("should auto transform case and full-stop", () => { + const question = new Question("body", { ...QUESTION_CONFIG, caseFn, - fullStopFn: (input: string) => input + '!', + fullStopFn: (input: string) => input + "!", }).question; expect( - (question as InputQuestionOptions)?.transformer?.('xxxx', {}, {}) - ).toBe('Xxxx!'); + (question as InputQuestionOptions)?.transformer?.("xxxx", {}, {}), + ).toBe("Xxxx!"); }); - test('should char count with green color when in the limit range', () => { - let question = new Question('body', { + test("should char count with green color when in the limit range", () => { + let question = new Question("body", { ...QUESTION_CONFIG, maxLength: 5, }).question; expect( - (question as InputQuestionOptions)?.transformer?.('xxx', {}, {}) + (question as InputQuestionOptions)?.transformer?.("xxx", {}, {}), ).toEqual(chalk.green(`(3) xxx`)); - question = new Question('body', { + question = new Question("body", { ...QUESTION_CONFIG, minLength: 2, }).question; expect( - (question as InputQuestionOptions)?.transformer?.('xxx', {}, {}) + (question as InputQuestionOptions)?.transformer?.("xxx", {}, {}), ).toEqual(chalk.green(`(3) xxx`)); }); - test('should char count with red color when over the limit range', () => { - let question = new Question('body', { + test("should char count with red color when over the limit range", () => { + let question = new Question("body", { ...QUESTION_CONFIG, maxLength: 5, }).question; expect( - (question as InputQuestionOptions)?.transformer?.('xxxxxx', {}, {}) + (question as InputQuestionOptions)?.transformer?.("xxxxxx", {}, {}), ).toEqual(chalk.red(`(6) xxxxxx`)); - question = new Question('body', { + question = new Question("body", { ...QUESTION_CONFIG, minLength: 2, }).question; expect( - (question as InputQuestionOptions)?.transformer?.('x', {}, {}) + (question as InputQuestionOptions)?.transformer?.("x", {}, {}), ).toEqual(chalk.red(`(1) x`)); }); }); -describe('inquirer question', () => { +describe("inquirer question", () => { test('should pass "when" and "default" field to inquirer question', () => { const when = (answers: Answers) => !!answers.header; - const question = new Question('body', { + const question = new Question("body", { ...QUESTION_CONFIG, when, - defaultValue: 'update', + defaultValue: "update", }).question; - expect(question).toHaveProperty('default', 'update'); - expect(question).toHaveProperty('when', when); + expect(question).toHaveProperty("default", "update"); + expect(question).toHaveProperty("when", when); }); }); diff --git a/@commitlint/cz-commitlint/src/Question.ts b/@commitlint/cz-commitlint/src/Question.ts index a641a4436a..c6a7ab24ad 100644 --- a/@commitlint/cz-commitlint/src/Question.ts +++ b/@commitlint/cz-commitlint/src/Question.ts @@ -1,9 +1,13 @@ -import {PromptMessages, PromptName} from '@commitlint/types'; -import chalk from 'chalk'; -import inquirer, {Answers, ChoiceCollection, DistinctQuestion} from 'inquirer'; +import { PromptMessages, PromptName } from "@commitlint/types"; +import chalk from "chalk"; +import inquirer, { + Answers, + ChoiceCollection, + DistinctQuestion, +} from "inquirer"; -import {CaseFn} from './utils/case-fn.js'; -import {FullStopFn} from './utils/full-stop-fn.js'; +import { CaseFn } from "./utils/case-fn.js"; +import { FullStopFn } from "./utils/full-stop-fn.js"; export type QuestionConfig = { title: string; @@ -11,7 +15,7 @@ export type QuestionConfig = { maxLength?: number; minLength?: number; defaultValue?: string; - when?: DistinctQuestion['when']; + when?: DistinctQuestion["when"]; skip?: boolean; enumList?: ChoiceCollection<{ name: string; @@ -49,15 +53,15 @@ export default class Question { minLength, multipleValueDelimiters, multipleSelectDefaultDelimiter, - }: QuestionConfig + }: QuestionConfig, ) { - if (!name || typeof name !== 'string') - throw new Error('Question: name is required'); + if (!name || typeof name !== "string") + throw new Error("Question: name is required"); this._maxLength = maxLength ?? Infinity; this._minLength = minLength ?? 0; this.messages = messages; - this.title = title ?? ''; + this.title = title ?? ""; this.skip = skip ?? false; this.fullStopFn = fullStopFn ?? ((_: string) => _); this.caseFn = @@ -69,25 +73,25 @@ export default class Question { if (enumList && Array.isArray(enumList)) { this._question = { - type: multipleSelectDefaultDelimiter ? 'checkbox' : 'list', + type: multipleSelectDefaultDelimiter ? "checkbox" : "list", choices: skip ? [ ...enumList, new inquirer.Separator(), { - name: 'empty', - value: '', + name: "empty", + value: "", }, - ] + ] : [...enumList], }; } else if (/^is[A-Z]/.test(name)) { this._question = { - type: 'confirm', + type: "confirm", }; } else { this._question = { - type: 'input', + type: "input", transformer: this.transformer.bind(this), }; } @@ -103,7 +107,7 @@ export default class Question { } getMessage(key: string): string { - return this.messages[key] ?? ''; + return this.messages[key] ?? ""; } get question(): Readonly<DistinctQuestion> { @@ -132,19 +136,19 @@ export default class Question { protected validate(input: string): boolean | string { const output = this.filter(input); - const questionName = this.question.name ?? ''; + const questionName = this.question.name ?? ""; if (!this.skip && output.length === 0) { - return this.getMessage('emptyWarning').replace(/%s/g, questionName); + return this.getMessage("emptyWarning").replace(/%s/g, questionName); } if (output.length > this.maxLength) { - return this.getMessage('upperLimitWarning') + return this.getMessage("upperLimitWarning") .replace(/%s/g, questionName) .replace(/%d/g, `${output.length - this.maxLength}`); } if (output.length < this.minLength) { - return this.getMessage('lowerLimitWarning') + return this.getMessage("lowerLimitWarning") .replace(/%s/g, questionName) .replace(/%d/g, `${this.minLength - output.length}`); } @@ -158,13 +162,13 @@ export default class Question { toCased = this.caseFn(input, this.multipleSelectDefaultDelimiter); } else if (this.multipleValueDelimiters) { const segments = input.split(this.multipleValueDelimiters); - const casedString = this.caseFn(segments, ','); - const casedSegments = casedString.split(','); + const casedString = this.caseFn(segments, ","); + const casedSegments = casedString.split(","); toCased = input.replace( - new RegExp(`[^${this.multipleValueDelimiters.source}]+`, 'g'), + new RegExp(`[^${this.multipleValueDelimiters.source}]+`, "g"), (segment) => { return casedSegments[segments.indexOf(segment)]; - } + }, ); } else { toCased = this.caseFn(input); @@ -183,38 +187,38 @@ export default class Question { output.length <= this.maxLength && output.length >= this.minLength ? chalk.green : chalk.red; - return color('(' + output.length + ') ' + output); + return color("(" + output.length + ") " + output); } protected decorateMessage(_answers: Answers): string { if (this.beforeQuestionStart) { this.beforeQuestionStart(_answers); } - if (this.question.type === 'input') { + if (this.question.type === "input") { const countLimitMessage = (() => { const messages = []; - if (this.minLength > 0 && this.getMessage('min')) { + if (this.minLength > 0 && this.getMessage("min")) { messages.push( - this.getMessage('min').replace(/%d/g, this.minLength + '') + this.getMessage("min").replace(/%d/g, this.minLength + ""), ); } - if (this.maxLength < Infinity && this.getMessage('max')) { + if (this.maxLength < Infinity && this.getMessage("max")) { messages.push( - this.getMessage('max').replace(/%d/g, this.maxLength + '') + this.getMessage("max").replace(/%d/g, this.maxLength + ""), ); } - return messages.join(', '); + return messages.join(", "); })(); - const skipMessage = this.skip && this.getMessage('skip'); + const skipMessage = this.skip && this.getMessage("skip"); return ( this.title + - (skipMessage ? ` ${skipMessage}` : '') + - ':' + - (countLimitMessage ? ` ${countLimitMessage}` : '') + - '\n' + (skipMessage ? ` ${skipMessage}` : "") + + ":" + + (countLimitMessage ? ` ${countLimitMessage}` : "") + + "\n" ); } else { return `${this.title}:`; diff --git a/@commitlint/cz-commitlint/src/SectionBody.test.ts b/@commitlint/cz-commitlint/src/SectionBody.test.ts index 5846ff6129..0d7e2bf9c9 100644 --- a/@commitlint/cz-commitlint/src/SectionBody.test.ts +++ b/@commitlint/cz-commitlint/src/SectionBody.test.ts @@ -1,96 +1,96 @@ -import {describe, test, expect} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { describe, test, expect } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; -import {combineCommitMessage, getQuestions} from './SectionBody.js'; -import {setRules} from './store/rules.js'; +import { combineCommitMessage, getQuestions } from "./SectionBody.js"; +import { setRules } from "./store/rules.js"; -describe('getQuestions', () => { - test('should exclude question when body must be empty', () => { +describe("getQuestions", () => { + test("should exclude question when body must be empty", () => { setRules({ - 'body-empty': [RuleConfigSeverity.Error, 'always'], + "body-empty": [RuleConfigSeverity.Error, "always"], }); const questions = getQuestions(); expect(questions).toHaveLength(0); }); - test('should only return body question', () => { + test("should only return body question", () => { setRules({}); const questions = getQuestions(); expect(questions).toHaveLength(1); expect(questions).toEqual([ expect.objectContaining({ - name: 'body', + name: "body", }), ]); }); }); -describe('combineCommitMessage', () => { - test('should wrap message to multi lines when max-line-length set', () => { +describe("combineCommitMessage", () => { + test("should wrap message to multi lines when max-line-length set", () => { setRules({ - 'body-max-line-length': [RuleConfigSeverity.Error, 'always', 10], + "body-max-line-length": [RuleConfigSeverity.Error, "always", 10], }); const commitMessage = combineCommitMessage({ - body: 'This is the body message.', + body: "This is the body message.", }); - expect(commitMessage).toBe('This is\nthe body\nmessage.'); + expect(commitMessage).toBe("This is\nthe body\nmessage."); }); - test('should auto apply leading blank', () => { + test("should auto apply leading blank", () => { setRules({ - 'body-leading-blank': [RuleConfigSeverity.Error, 'always'], + "body-leading-blank": [RuleConfigSeverity.Error, "always"], }); const commitMessage = combineCommitMessage({ - body: 'This is the body message.', + body: "This is the body message.", }); - expect(commitMessage).toBe('\nThis is the body message.'); + expect(commitMessage).toBe("\nThis is the body message."); }); - test('should return correct string when leading-blank and max-line-length both set', () => { + test("should return correct string when leading-blank and max-line-length both set", () => { setRules({ - 'body-max-line-length': [RuleConfigSeverity.Error, 'always', 10], - 'body-leading-blank': [RuleConfigSeverity.Error, 'always'], + "body-max-line-length": [RuleConfigSeverity.Error, "always", 10], + "body-leading-blank": [RuleConfigSeverity.Error, "always"], }); const commitMessage = combineCommitMessage({ - body: 'This is the body message.', + body: "This is the body message.", }); - expect(commitMessage).toBe('\nThis is\nthe body\nmessage.'); + expect(commitMessage).toBe("\nThis is\nthe body\nmessage."); }); - test('should use breakingBody when body message is empty but commit has BREAK CHANGE', () => { + test("should use breakingBody when body message is empty but commit has BREAK CHANGE", () => { setRules({}); const commitMessage = combineCommitMessage({ - breakingBody: 'This is breaking body message.', + breakingBody: "This is breaking body message.", }); - expect(commitMessage).toBe('This is breaking body message.'); + expect(commitMessage).toBe("This is breaking body message."); }); - test('should use issueBody when body message is empty but commit has issue note', () => { + test("should use issueBody when body message is empty but commit has issue note", () => { setRules({}); const commitMessage = combineCommitMessage({ - issuesBody: 'This is issue body message.', + issuesBody: "This is issue body message.", }); - expect(commitMessage).toBe('This is issue body message.'); + expect(commitMessage).toBe("This is issue body message."); }); - test('should use issueBody when body message is empty string but commit has issue note', () => { + test("should use issueBody when body message is empty string but commit has issue note", () => { setRules({}); const commitMessage = combineCommitMessage({ - body: '', - issuesBody: 'This is issue body message.', + body: "", + issuesBody: "This is issue body message.", }); - expect(commitMessage).toBe('This is issue body message.'); + expect(commitMessage).toBe("This is issue body message."); }); - test('should return empty message when body is empty', () => { + test("should return empty message when body is empty", () => { setRules({}); const commitMessage = combineCommitMessage({ - body: '', + body: "", }); - expect(commitMessage).toBe(''); + expect(commitMessage).toBe(""); }); }); diff --git a/@commitlint/cz-commitlint/src/SectionBody.ts b/@commitlint/cz-commitlint/src/SectionBody.ts index 68fa78a433..07f1c22cd0 100644 --- a/@commitlint/cz-commitlint/src/SectionBody.ts +++ b/@commitlint/cz-commitlint/src/SectionBody.ts @@ -1,26 +1,26 @@ -import {Answers, DistinctQuestion} from 'inquirer'; -import wrap from 'word-wrap'; +import { Answers, DistinctQuestion } from "inquirer"; +import wrap from "word-wrap"; -import Question from './Question.js'; -import getRuleQuestionConfig from './services/getRuleQuestionConfig.js'; -import {getRule} from './store/rules.js'; -import getLeadingBlankFn from './utils/leading-blank-fn.js'; -import {getMaxLength} from './utils/rules.js'; +import Question from "./Question.js"; +import getRuleQuestionConfig from "./services/getRuleQuestionConfig.js"; +import { getRule } from "./store/rules.js"; +import getLeadingBlankFn from "./utils/leading-blank-fn.js"; +import { getMaxLength } from "./utils/rules.js"; export function getQuestions(): Array<DistinctQuestion> { // body - const questionConfig = getRuleQuestionConfig('body'); + const questionConfig = getRuleQuestionConfig("body"); if (!questionConfig) return []; - else return [new Question('body', questionConfig).question]; + else return [new Question("body", questionConfig).question]; } export function combineCommitMessage(answers: Answers): string { - const maxLineLength = getMaxLength(getRule('body', 'max-line-length')); - const leadingBlankFn = getLeadingBlankFn(getRule('body', 'leading-blank')); - const {body, breakingBody, issuesBody} = answers; + const maxLineLength = getMaxLength(getRule("body", "max-line-length")); + const leadingBlankFn = getLeadingBlankFn(getRule("body", "leading-blank")); + const { body, breakingBody, issuesBody } = answers; - const commitBody = body || breakingBody || issuesBody || ''; + const commitBody = body || breakingBody || issuesBody || ""; if (commitBody) { return leadingBlankFn( @@ -28,11 +28,11 @@ export function combineCommitMessage(answers: Answers): string { ? wrap(commitBody, { width: maxLineLength, trim: true, - indent: '', - }) - : commitBody.trim() + indent: "", + }) + : commitBody.trim(), ); } else { - return ''; + return ""; } } diff --git a/@commitlint/cz-commitlint/src/SectionFooter.test.ts b/@commitlint/cz-commitlint/src/SectionFooter.test.ts index 6e1c497958..e16c9fadc8 100644 --- a/@commitlint/cz-commitlint/src/SectionFooter.test.ts +++ b/@commitlint/cz-commitlint/src/SectionFooter.test.ts @@ -1,24 +1,24 @@ -import {describe, test, expect, beforeEach} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { describe, test, expect, beforeEach } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; -import {combineCommitMessage, getQuestions} from './SectionFooter.js'; -import {setPromptConfig} from './store/prompts.js'; -import {setRules} from './store/rules.js'; +import { combineCommitMessage, getQuestions } from "./SectionFooter.js"; +import { setPromptConfig } from "./store/prompts.js"; +import { setRules } from "./store/rules.js"; beforeEach(() => { setRules({}); setPromptConfig({}); }); -describe('getQuestions', () => { - test('should only ask questions that listed in prompt question config', () => { +describe("getQuestions", () => { + test("should only ask questions that listed in prompt question config", () => { setPromptConfig({ questions: { footer: { description: - '<footer> holds further meta data, such as breaking changes and issue ids', + "<footer> holds further meta data, such as breaking changes and issue ids", }, issues: { - description: '<issues> link', + description: "<issues> link", }, }, }); @@ -28,19 +28,19 @@ describe('getQuestions', () => { expect(questions).toHaveLength(2); expect(questions).toEqual([ expect.objectContaining({ - name: 'issues', + name: "issues", }), expect.objectContaining({ - name: 'footer', + name: "footer", }), ]); }); - test('should not have break change as default', () => { + test("should not have break change as default", () => { setPromptConfig({ questions: { isBreaking: { - description: 'Are there any breaking changes?', + description: "Are there any breaking changes?", }, }, }); @@ -48,20 +48,20 @@ describe('getQuestions', () => { const questions = getQuestions(); expect(questions).toEqual([ expect.objectContaining({ - name: 'isBreaking', + name: "isBreaking", default: false, }), ]); }); - test('should ask for break change info when have break change', () => { + test("should ask for break change info when have break change", () => { setPromptConfig({ questions: { isBreaking: { - description: 'Are there any breaking changes?', + description: "Are there any breaking changes?", }, breaking: { - description: 'Describe the breaking changes', + description: "Describe the breaking changes", }, }, }); @@ -70,24 +70,24 @@ describe('getQuestions', () => { expect( (questions[1].when as any)({ isBreaking: false, - }) + }), ).toBe(false); expect( (questions[1].when as any)({ isBreaking: true, - }) + }), ).toBe(true); }); - test('should ask for body info when have break change but does not have body message', () => { + test("should ask for body info when have break change but does not have body message", () => { setPromptConfig({ questions: { isBreaking: { - description: 'Describe the breaking changes', + description: "Describe the breaking changes", }, breakingBody: { description: - 'A BREAKING CHANGE commit requires a body. Please enter a longer description of the commit itself', + "A BREAKING CHANGE commit requires a body. Please enter a longer description of the commit itself", }, }, }); @@ -97,28 +97,28 @@ describe('getQuestions', () => { expect( (questions[1].when as any)({ isBreaking: true, - }) + }), ).toBe(true); expect( (questions[1].when as any)({ isBreaking: true, - body: 'xxx', - }) + body: "xxx", + }), ).toBe(false); expect( (questions[1].when as any)({ isBreaking: false, - }) + }), ).toBe(false); }); - test('should change does not affect any issues as default', () => { + test("should change does not affect any issues as default", () => { setPromptConfig({ questions: { isIssueAffected: { - description: 'Does this change affect any open issues?', + description: "Does this change affect any open issues?", }, }, }); @@ -126,17 +126,17 @@ describe('getQuestions', () => { const questions = getQuestions(); expect(questions).toEqual([ expect.objectContaining({ - name: 'isIssueAffected', + name: "isIssueAffected", default: false, }), ]); }); - test('should ask for issue info when have issue affected', () => { + test("should ask for issue info when have issue affected", () => { setPromptConfig({ questions: { isIssueAffected: { - description: 'Does this change affect any open issues?', + description: "Does this change affect any open issues?", }, issues: { description: 'Add issue references (e.g. "fix #123", "re #123".)', @@ -148,24 +148,24 @@ describe('getQuestions', () => { expect( (questions[1].when as any)({ isIssueAffected: false, - }) + }), ).toBe(false); expect( (questions[1].when as any)({ isIssueAffected: true, - }) + }), ).toBe(true); }); - test('should ask for body info when have issue affected but does not have body message', () => { + test("should ask for body info when have issue affected but does not have body message", () => { setPromptConfig({ questions: { isIssueAffected: { - description: 'Does this change affect any open issues?', + description: "Does this change affect any open issues?", }, issuesBody: { description: - 'If issues are closed, the commit requires a body. Please enter a longer description of the commit itself', + "If issues are closed, the commit requires a body. Please enter a longer description of the commit itself", }, issues: { description: 'Add issue references (e.g. "fix #123", "re #123".)', @@ -178,139 +178,139 @@ describe('getQuestions', () => { expect( (questions[1].when as any)({ isIssueAffected: true, - }) + }), ).toBe(true); expect( (questions[1].when as any)({ isIssueAffected: true, - body: 'xxx', - }) + body: "xxx", + }), ).toBe(false); expect( (questions[1].when as any)({ isIssueAffected: false, - breaking: 'xxxxx', - }) + breaking: "xxxxx", + }), ).toBe(false); }); }); -describe('combineCommitMessage', () => { +describe("combineCommitMessage", () => { test('should return BreakChange start with "BREAKING CHANGE: "', () => { let commitMessage = combineCommitMessage({ - breaking: 'BREAKING CHANGE: xxxxxx', + breaking: "BREAKING CHANGE: xxxxxx", }); - expect(commitMessage).toBe('BREAKING CHANGE: xxxxxx'); + expect(commitMessage).toBe("BREAKING CHANGE: xxxxxx"); commitMessage = combineCommitMessage({ - breaking: 'xxxxxx', + breaking: "xxxxxx", }); - expect(commitMessage).toBe('BREAKING CHANGE: xxxxxx'); + expect(commitMessage).toBe("BREAKING CHANGE: xxxxxx"); }); - test('should return correct string with BreakChange,issue,footer', () => { + test("should return correct string with BreakChange,issue,footer", () => { const commitMessage = combineCommitMessage({ issues: - 'https://github.com/conventional-changelog/commitlint/issues/2507', - breaking: 'BREAKING CHANGE: xxxxxx', - footer: 'Other footer information.', + "https://github.com/conventional-changelog/commitlint/issues/2507", + breaking: "BREAKING CHANGE: xxxxxx", + footer: "Other footer information.", }); expect(commitMessage).toBe( - 'BREAKING CHANGE: xxxxxx\nhttps://github.com/conventional-changelog/commitlint/issues/2507\nOther footer information.' + "BREAKING CHANGE: xxxxxx\nhttps://github.com/conventional-changelog/commitlint/issues/2507\nOther footer information.", ); }); - test('should return wrap string with footer-max-line-length', () => { + test("should return wrap string with footer-max-line-length", () => { setRules({ - 'footer-max-line-length': [RuleConfigSeverity.Error, 'always', 10], + "footer-max-line-length": [RuleConfigSeverity.Error, "always", 10], }); const commitMessage = combineCommitMessage({ issues: - 'https://github.com/conventional-changelog/commitlint/issues/2507', - breaking: 'BREAKING CHANGE: xxxxxx', - footer: 'Other footer information.', + "https://github.com/conventional-changelog/commitlint/issues/2507", + breaking: "BREAKING CHANGE: xxxxxx", + footer: "Other footer information.", }); expect(commitMessage).toBe( - 'BREAKING\nCHANGE:\nxxxxxx\nhttps://github.com/conventional-changelog/commitlint/issues/2507\nOther\nfooter\ninformation.' + "BREAKING\nCHANGE:\nxxxxxx\nhttps://github.com/conventional-changelog/commitlint/issues/2507\nOther\nfooter\ninformation.", ); }); - test('should auto leading blank when footer-leading-blank is set', () => { + test("should auto leading blank when footer-leading-blank is set", () => { setRules({ - 'footer-max-line-length': [RuleConfigSeverity.Error, 'always', 10], - 'footer-leading-blank': [RuleConfigSeverity.Error, 'always'], + "footer-max-line-length": [RuleConfigSeverity.Error, "always", 10], + "footer-leading-blank": [RuleConfigSeverity.Error, "always"], }); const commitMessage = combineCommitMessage({ issues: - 'https://github.com/conventional-changelog/commitlint/issues/2507', - breaking: 'BREAKING CHANGE: xxxxxx', - footer: 'Other footer information.', + "https://github.com/conventional-changelog/commitlint/issues/2507", + breaking: "BREAKING CHANGE: xxxxxx", + footer: "Other footer information.", }); expect(commitMessage).toBe( - '\nBREAKING\nCHANGE:\nxxxxxx\nhttps://github.com/conventional-changelog/commitlint/issues/2507\nOther\nfooter\ninformation.' + "\nBREAKING\nCHANGE:\nxxxxxx\nhttps://github.com/conventional-changelog/commitlint/issues/2507\nOther\nfooter\ninformation.", ); }); - test('when does not have break change', () => { + test("when does not have break change", () => { const commitMessage = combineCommitMessage({ issues: - 'https://github.com/conventional-changelog/commitlint/issues/2507', - footer: 'Other footer information.', + "https://github.com/conventional-changelog/commitlint/issues/2507", + footer: "Other footer information.", }); expect(commitMessage).toBe( - 'https://github.com/conventional-changelog/commitlint/issues/2507\nOther footer information.' + "https://github.com/conventional-changelog/commitlint/issues/2507\nOther footer information.", ); }); - test('when does not have issue', () => { + test("when does not have issue", () => { const commitMessage = combineCommitMessage({ - footer: 'Other footer information.', + footer: "Other footer information.", }); - expect(commitMessage).toBe('Other footer information.'); + expect(commitMessage).toBe("Other footer information."); }); }); -describe('FooterQuestion', () => { - test('should limited by footer maxLength and minLength', () => { +describe("FooterQuestion", () => { + test("should limited by footer maxLength and minLength", () => { setRules({ - 'footer-max-length': [RuleConfigSeverity.Error, 'always', 30], - 'footer-min-length': [RuleConfigSeverity.Error, 'always', 10], + "footer-max-length": [RuleConfigSeverity.Error, "always", 30], + "footer-min-length": [RuleConfigSeverity.Error, "always", 10], }); setPromptConfig({ messages: { - skip: '(press enter to skip)', - max: 'upper %d chars', - min: '%d chars at least', - emptyWarning: '%s can not be empty', - upperLimitWarning: '%s: %s over limit %d', - lowerLimitWarning: '%s: %s below limit %d', + skip: "(press enter to skip)", + max: "upper %d chars", + min: "%d chars at least", + emptyWarning: "%s can not be empty", + upperLimitWarning: "%s: %s over limit %d", + lowerLimitWarning: "%s: %s below limit %d", }, questions: { breaking: { - description: 'Describe the breaking changes', + description: "Describe the breaking changes", }, issues: { - description: '<issues> link', + description: "<issues> link", }, footer: { description: - '<footer> holds further meta data, such as breaking changes and issue ids', + "<footer> holds further meta data, such as breaking changes and issue ids", }, }, }); const questions = getQuestions(); const answers = { - breaking: 'BREAKING CHANGE: xxxxxx', - issues: ''.padEnd(6, 'y'), + breaking: "BREAKING CHANGE: xxxxxx", + issues: "".padEnd(6, "y"), }; const lastQuestion = questions[2]; (lastQuestion.message as any)(answers); - expect(lastQuestion?.validate?.(''.padEnd(10, 'z'), answers)).toBe( - 'footer: footer over limit 11' + expect(lastQuestion?.validate?.("".padEnd(10, "z"), answers)).toBe( + "footer: footer over limit 11", ); }); }); diff --git a/@commitlint/cz-commitlint/src/SectionFooter.ts b/@commitlint/cz-commitlint/src/SectionFooter.ts index 620bca2d05..f278e226eb 100644 --- a/@commitlint/cz-commitlint/src/SectionFooter.ts +++ b/@commitlint/cz-commitlint/src/SectionFooter.ts @@ -1,13 +1,13 @@ -import {PromptName} from '@commitlint/types'; -import {Answers, DistinctQuestion} from 'inquirer'; -import wrap from 'word-wrap'; +import { PromptName } from "@commitlint/types"; +import { Answers, DistinctQuestion } from "inquirer"; +import wrap from "word-wrap"; -import Question, {QuestionConfig} from './Question.js'; -import getRuleQuestionConfig from './services/getRuleQuestionConfig.js'; -import {getPromptMessages, getPromptQuestions} from './store/prompts.js'; -import {getRule} from './store/rules.js'; -import getLeadingBlankFn from './utils/leading-blank-fn.js'; -import {getMaxLength} from './utils/rules.js'; +import Question, { QuestionConfig } from "./Question.js"; +import getRuleQuestionConfig from "./services/getRuleQuestionConfig.js"; +import { getPromptMessages, getPromptQuestions } from "./store/prompts.js"; +import { getRule } from "./store/rules.js"; +import getLeadingBlankFn from "./utils/leading-blank-fn.js"; +import { getMaxLength } from "./utils/rules.js"; export class FooterQuestion extends Question { footerMaxLength: number; @@ -16,7 +16,7 @@ export class FooterQuestion extends Question { name: PromptName, questionConfig: QuestionConfig, footerMaxLength?: number, - footerMinLength?: number + footerMinLength?: number, ) { super(name, questionConfig); this.footerMaxLength = footerMaxLength ?? Infinity; @@ -24,14 +24,14 @@ export class FooterQuestion extends Question { } beforeQuestionStart(answers: Answers): void { const footerRemainLength = - this.footerMaxLength - combineCommitMessage(answers).length - '\n'.length; + this.footerMaxLength - combineCommitMessage(answers).length - "\n".length; this.maxLength = Math.min(this.maxLength, footerRemainLength); this.minLength = Math.min(this.minLength, this.footerMinLength); } } export function getQuestions(): Array<DistinctQuestion> { - const footerQuestionConfig = getRuleQuestionConfig('footer'); + const footerQuestionConfig = getRuleQuestionConfig("footer"); if (!footerQuestionConfig) return []; @@ -39,13 +39,13 @@ export function getQuestions(): Array<DistinctQuestion> { const footerMinLength = footerQuestionConfig.minLength; const fields: PromptName[] = [ - 'isBreaking', - 'breakingBody', - 'breaking', - 'isIssueAffected', - 'issuesBody', - 'issues', - 'footer', + "isBreaking", + "breakingBody", + "breaking", + "isIssueAffected", + "issuesBody", + "issues", + "footer", ]; return fields @@ -54,19 +54,19 @@ export function getQuestions(): Array<DistinctQuestion> { const questions = getPromptQuestions(); const questionConfigs = { - title: questions[name]?.description ?? '', + title: questions[name]?.description ?? "", messages: getPromptMessages(), footerMaxLength, footerMinLength, }; - if (name === 'isBreaking') { + if (name === "isBreaking") { Object.assign(questionConfigs, { defaultValue: false, }); } - if (name === 'breakingBody') { + if (name === "breakingBody") { Object.assign(questionConfigs, { when: (answers: Answers) => { return answers.isBreaking && !answers.body; @@ -74,7 +74,7 @@ export function getQuestions(): Array<DistinctQuestion> { }); } - if (name === 'breaking') { + if (name === "breaking") { Object.assign(questionConfigs, { when: (answers: Answers) => { return answers.isBreaking; @@ -82,13 +82,13 @@ export function getQuestions(): Array<DistinctQuestion> { }); } - if (name === 'isIssueAffected') { + if (name === "isIssueAffected") { Object.assign(questionConfigs, { defaultValue: false, }); } - if (name === 'issuesBody') { + if (name === "issuesBody") { Object.assign(questionConfigs, { when: (answers: Answers) => { return ( @@ -98,7 +98,7 @@ export function getQuestions(): Array<DistinctQuestion> { }); } - if (name === 'issues') { + if (name === "issues") { Object.assign(questionConfigs, { when: (answers: Answers) => { return answers.isIssueAffected; @@ -106,7 +106,7 @@ export function getQuestions(): Array<DistinctQuestion> { }); } - if (name === 'footer') { + if (name === "footer") { Object.assign(questionConfigs, { ...footerQuestionConfig, }); @@ -116,7 +116,7 @@ export function getQuestions(): Array<DistinctQuestion> { name, questionConfigs, footerMaxLength, - footerMinLength + footerMinLength, ); return instance.question; @@ -126,24 +126,24 @@ export function getQuestions(): Array<DistinctQuestion> { export function combineCommitMessage(answers: Answers): string { // TODO references-empty // TODO signed-off-by - const maxLineLength = getMaxLength(getRule('footer', 'max-line-length')); - const leadingBlankFn = getLeadingBlankFn(getRule('footer', 'leading-blank')); + const maxLineLength = getMaxLength(getRule("footer", "max-line-length")); + const leadingBlankFn = getLeadingBlankFn(getRule("footer", "leading-blank")); - const {footer, breaking, issues} = answers; + const { footer, breaking, issues } = answers; const footerNotes: string[] = []; if (breaking) { - const BREAKING_CHANGE = 'BREAKING CHANGE: '; + const BREAKING_CHANGE = "BREAKING CHANGE: "; const message = - BREAKING_CHANGE + breaking.replace(new RegExp(`^${BREAKING_CHANGE}`), ''); + BREAKING_CHANGE + breaking.replace(new RegExp(`^${BREAKING_CHANGE}`), ""); footerNotes.push( maxLineLength < Infinity ? wrap(message, { width: maxLineLength, trim: true, - indent: '', - }) - : message.trim() + indent: "", + }) + : message.trim(), ); } @@ -153,9 +153,9 @@ export function combineCommitMessage(answers: Answers): string { ? wrap(issues, { width: maxLineLength, trim: true, - indent: '', - }) - : issues.trim() + indent: "", + }) + : issues.trim(), ); } @@ -165,11 +165,11 @@ export function combineCommitMessage(answers: Answers): string { ? wrap(footer, { width: maxLineLength, trim: true, - indent: '', - }) - : footer + indent: "", + }) + : footer, ); } - return leadingBlankFn(footerNotes.join('\n')); + return leadingBlankFn(footerNotes.join("\n")); } diff --git a/@commitlint/cz-commitlint/src/SectionHeader.test.ts b/@commitlint/cz-commitlint/src/SectionHeader.test.ts index 5ff96f2c83..350c1fe746 100644 --- a/@commitlint/cz-commitlint/src/SectionHeader.test.ts +++ b/@commitlint/cz-commitlint/src/SectionHeader.test.ts @@ -1,156 +1,156 @@ -import {describe, test, expect, beforeEach} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { describe, test, expect, beforeEach } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; import { combineCommitMessage, getQuestions, getQuestionConfig, -} from './SectionHeader.js'; -import {setPromptConfig} from './store/prompts.js'; -import {setRules} from './store/rules.js'; +} from "./SectionHeader.js"; +import { setPromptConfig } from "./store/prompts.js"; +import { setRules } from "./store/rules.js"; beforeEach(() => { setRules({}); setPromptConfig({}); }); -describe('getQuestions', () => { +describe("getQuestions", () => { test("should contain 'type','scope','subject'", () => { const questions = getQuestions(); expect(questions).toHaveLength(3); expect(questions).toEqual([ expect.objectContaining({ - name: 'type', + name: "type", }), expect.objectContaining({ - name: 'scope', + name: "scope", }), expect.objectContaining({ - name: 'subject', + name: "subject", }), ]); }); - test('should exclude question when must be empty', () => { + test("should exclude question when must be empty", () => { setRules({ - 'scope-empty': [RuleConfigSeverity.Error, 'always'], + "scope-empty": [RuleConfigSeverity.Error, "always"], }); const questions = getQuestions(); expect(questions).toHaveLength(2); expect(questions).toEqual([ expect.objectContaining({ - name: 'type', + name: "type", }), expect.objectContaining({ - name: 'subject', + name: "subject", }), ]); }); }); -describe('getQuestionConfig', () => { +describe("getQuestionConfig", () => { test("should 'scope' supports multiple items separated with ',\\/'", () => { - const config = getQuestionConfig('scope'); + const config = getQuestionConfig("scope"); expect(config).toEqual( expect.objectContaining({ multipleValueDelimiters: /\/|\\|,/g, - }) + }), ); }); test("should 'scope' supports multiple select separated with settings.scopeEnumSeparator and enableMultipleScopes", () => { setPromptConfig({ settings: { - scopeEnumSeparator: '/', + scopeEnumSeparator: "/", enableMultipleScopes: true, }, }); - const config = getQuestionConfig('scope'); + const config = getQuestionConfig("scope"); expect(config).toEqual( expect.objectContaining({ - multipleSelectDefaultDelimiter: '/', - }) + multipleSelectDefaultDelimiter: "/", + }), ); }); test("should 'scope' disable multiple select by default", () => { - const config = getQuestionConfig('scope'); - expect(config).not.toContain('multipleSelectDefaultDelimiter'); + const config = getQuestionConfig("scope"); + expect(config).not.toContain("multipleSelectDefaultDelimiter"); }); }); -describe('combineCommitMessage', () => { - test('should return correct string when type,scope,subject are not empty', () => { +describe("combineCommitMessage", () => { + test("should return correct string when type,scope,subject are not empty", () => { const commitMessage = combineCommitMessage({ - type: 'build', - scope: 'typescript', - subject: 'update tsconfig.json', + type: "build", + scope: "typescript", + subject: "update tsconfig.json", }); - expect(commitMessage).toBe('build(typescript): update tsconfig.json'); + expect(commitMessage).toBe("build(typescript): update tsconfig.json"); }); - test('when type is empty', () => { + test("when type is empty", () => { let commitMessage = combineCommitMessage({ - scope: 'typescript', - subject: 'update tsconfig.json', + scope: "typescript", + subject: "update tsconfig.json", }); - expect(commitMessage).toBe('(typescript): update tsconfig.json'); + expect(commitMessage).toBe("(typescript): update tsconfig.json"); commitMessage = combineCommitMessage({ - scope: 'typescript', + scope: "typescript", }); - expect(commitMessage).toBe('(typescript)'); + expect(commitMessage).toBe("(typescript)"); }); - test('when scope is empty', () => { + test("when scope is empty", () => { let commitMessage = combineCommitMessage({ - type: 'build', - subject: 'update tsconfig.json', + type: "build", + subject: "update tsconfig.json", }); - expect(commitMessage).toBe('build: update tsconfig.json'); + expect(commitMessage).toBe("build: update tsconfig.json"); commitMessage = combineCommitMessage({ - subject: 'update tsconfig.json', + subject: "update tsconfig.json", }); - expect(commitMessage).toBe('update tsconfig.json'); + expect(commitMessage).toBe("update tsconfig.json"); }); - test('when subject is empty', () => { + test("when subject is empty", () => { const commitMessage = combineCommitMessage({ - type: 'build', - scope: 'typescript', + type: "build", + scope: "typescript", }); - expect(commitMessage).toBe('build(typescript)'); + expect(commitMessage).toBe("build(typescript)"); }); }); -describe('HeaderQuestion', () => { - test('should limited by header maxLength and minLength', () => { +describe("HeaderQuestion", () => { + test("should limited by header maxLength and minLength", () => { setRules({ - 'header-max-length': [RuleConfigSeverity.Error, 'always', 20], - 'header-min-length': [RuleConfigSeverity.Error, 'always', 10], - 'subject-max-length': [RuleConfigSeverity.Error, 'always', 10], - 'subject-min-length': [RuleConfigSeverity.Error, 'always', 5], + "header-max-length": [RuleConfigSeverity.Error, "always", 20], + "header-min-length": [RuleConfigSeverity.Error, "always", 10], + "subject-max-length": [RuleConfigSeverity.Error, "always", 10], + "subject-min-length": [RuleConfigSeverity.Error, "always", 5], }); setPromptConfig({ messages: { - skip: '(press enter to skip)', - max: 'upper %d chars', - min: '%d chars at least', - emptyWarning: '%s can not be empty', - upperLimitWarning: '%s: %s over limit %d', - lowerLimitWarning: '%s: %s below limit %d', + skip: "(press enter to skip)", + max: "upper %d chars", + min: "%d chars at least", + emptyWarning: "%s can not be empty", + upperLimitWarning: "%s: %s over limit %d", + lowerLimitWarning: "%s: %s below limit %d", }, }); const questions = getQuestions(); const answers = { - type: ''.padEnd(8, 'x'), - scope: ''.padEnd(6, 'y'), + type: "".padEnd(8, "x"), + scope: "".padEnd(6, "y"), }; const lastQuestion = questions[2]; (lastQuestion.message as any)(answers); - expect(lastQuestion?.validate?.(''.padEnd(10, 'z'), answers)).toBe( - 'subject: subject over limit 6' + expect(lastQuestion?.validate?.("".padEnd(10, "z"), answers)).toBe( + "subject: subject over limit 6", ); }); }); diff --git a/@commitlint/cz-commitlint/src/SectionHeader.ts b/@commitlint/cz-commitlint/src/SectionHeader.ts index 1952db3c70..bf43f0a2a3 100644 --- a/@commitlint/cz-commitlint/src/SectionHeader.ts +++ b/@commitlint/cz-commitlint/src/SectionHeader.ts @@ -1,9 +1,9 @@ -import {PromptName, RuleField} from '@commitlint/types'; -import {Answers, DistinctQuestion} from 'inquirer'; +import { PromptName, RuleField } from "@commitlint/types"; +import { Answers, DistinctQuestion } from "inquirer"; -import Question, {QuestionConfig} from './Question.js'; -import getRuleQuestionConfig from './services/getRuleQuestionConfig.js'; -import {getPromptSettings} from './store/prompts.js'; +import Question, { QuestionConfig } from "./Question.js"; +import getRuleQuestionConfig from "./services/getRuleQuestionConfig.js"; +import { getPromptSettings } from "./store/prompts.js"; export class HeaderQuestion extends Question { headerMaxLength: number; @@ -12,7 +12,7 @@ export class HeaderQuestion extends Question { name: PromptName, questionConfig: QuestionConfig, headerMaxLength?: number, - headerMinLength?: number + headerMinLength?: number, ) { super(name, questionConfig); this.headerMaxLength = headerMaxLength ?? Infinity; @@ -27,11 +27,11 @@ export class HeaderQuestion extends Question { } export function combineCommitMessage(answers: Answers): string { - const {type = '', scope = '', subject = ''} = answers; - const prefix = `${type}${scope ? `(${scope})` : ''}`; + const { type = "", scope = "", subject = "" } = answers; + const prefix = `${type}${scope ? `(${scope})` : ""}`; if (subject) { - return ((prefix ? prefix + ': ' : '') + subject).trim(); + return ((prefix ? prefix + ": " : "") + subject).trim(); } else { return prefix.trim(); } @@ -41,8 +41,8 @@ export function getQuestions(): Array<DistinctQuestion> { // header: type, scope, subject const questions: Array<DistinctQuestion> = []; - const headerRuleFields: RuleField[] = ['type', 'scope', 'subject']; - const headerRuleQuestionConfig = getRuleQuestionConfig('header'); + const headerRuleFields: RuleField[] = ["type", "scope", "subject"]; + const headerRuleQuestionConfig = getRuleQuestionConfig("header"); if (!headerRuleQuestionConfig) { return []; @@ -55,7 +55,7 @@ export function getQuestions(): Array<DistinctQuestion> { name, questionConfig, headerRuleQuestionConfig.maxLength, - headerRuleQuestionConfig.minLength + headerRuleQuestionConfig.minLength, ); questions.push(instance.question); } @@ -64,15 +64,15 @@ export function getQuestions(): Array<DistinctQuestion> { } export function getQuestionConfig( - name: RuleField + name: RuleField, ): ReturnType<typeof getRuleQuestionConfig> { const questionConfig = getRuleQuestionConfig(name); if (questionConfig) { - if (name === 'scope') { - if (getPromptSettings()['enableMultipleScopes']) { + if (name === "scope") { + if (getPromptSettings()["enableMultipleScopes"]) { questionConfig.multipleSelectDefaultDelimiter = - getPromptSettings()['scopeEnumSeparator']; + getPromptSettings()["scopeEnumSeparator"]; } // split scope string to segments, match commitlint rules questionConfig.multipleValueDelimiters = /\/|\\|,/g; diff --git a/@commitlint/cz-commitlint/src/index.ts b/@commitlint/cz-commitlint/src/index.ts index 6011d5b4c5..0baeefbf2c 100644 --- a/@commitlint/cz-commitlint/src/index.ts +++ b/@commitlint/cz-commitlint/src/index.ts @@ -1,7 +1,7 @@ -import load from '@commitlint/load'; -import type {Answers, DistinctQuestion} from 'inquirer'; +import load from "@commitlint/load"; +import type { Answers, DistinctQuestion } from "inquirer"; -import process from './Process.js'; +import process from "./Process.js"; type Commit = (message: string) => void; /** @@ -14,9 +14,9 @@ export function prompter( inquirerIns: { prompt(questions: DistinctQuestion[]): Promise<Answers>; }, - commit: Commit + commit: Commit, ): void { - load().then(({rules, prompt = {}}) => { + load().then(({ rules, prompt = {} }) => { process(rules, prompt, inquirerIns).then(commit); }); } diff --git a/@commitlint/cz-commitlint/src/services/getRuleQuestionConfig.test.ts b/@commitlint/cz-commitlint/src/services/getRuleQuestionConfig.test.ts index 338f323c8f..e28879f546 100644 --- a/@commitlint/cz-commitlint/src/services/getRuleQuestionConfig.test.ts +++ b/@commitlint/cz-commitlint/src/services/getRuleQuestionConfig.test.ts @@ -1,60 +1,60 @@ -import {describe, test, expect} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { describe, test, expect } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; -import {setPromptConfig} from '../store/prompts.js'; -import {setRules} from '../store/rules.js'; -import getRuleQuestionConfig from './getRuleQuestionConfig.js'; +import { setPromptConfig } from "../store/prompts.js"; +import { setRules } from "../store/rules.js"; +import getRuleQuestionConfig from "./getRuleQuestionConfig.js"; // let rules = {}; // let rules: QualifiedRules = {}; // const getRules = jest.fn().mockReturnValue(rules); -describe('empty rule', () => { - test('should return null when must be empty', () => { +describe("empty rule", () => { + test("should return null when must be empty", () => { setRules({ - 'body-empty': [RuleConfigSeverity.Error, 'always'], + "body-empty": [RuleConfigSeverity.Error, "always"], }); - expect(getRuleQuestionConfig('body')).toBe(null); + expect(getRuleQuestionConfig("body")).toBe(null); }); test("should field 'skip' be false when can not be empty", () => { setRules({ - 'body-empty': [RuleConfigSeverity.Error, 'never'], + "body-empty": [RuleConfigSeverity.Error, "never"], }); - expect(getRuleQuestionConfig('body')?.skip).toBe(false); + expect(getRuleQuestionConfig("body")?.skip).toBe(false); }); test('should field "skip" be true when not set empty rule', () => { setRules({ - 'body-case': [RuleConfigSeverity.Warning, 'never', 'camel-case'], - 'body-max-length': [RuleConfigSeverity.Error, 'always', 100], + "body-case": [RuleConfigSeverity.Warning, "never", "camel-case"], + "body-max-length": [RuleConfigSeverity.Error, "always", 100], }); - expect(getRuleQuestionConfig('body')?.skip).toBe(true); + expect(getRuleQuestionConfig("body")?.skip).toBe(true); }); test('should field "skip" be true when disable empty rule', () => { setRules({ - 'body-empty': [RuleConfigSeverity.Disabled], + "body-empty": [RuleConfigSeverity.Disabled], }); - expect(getRuleQuestionConfig('body')?.skip).toBe(true); + expect(getRuleQuestionConfig("body")?.skip).toBe(true); setRules({ - 'body-empty': [RuleConfigSeverity.Disabled, 'always'], + "body-empty": [RuleConfigSeverity.Disabled, "always"], }); - expect(getRuleQuestionConfig('body')?.skip).toBe(true); + expect(getRuleQuestionConfig("body")?.skip).toBe(true); setRules({ - 'body-empty': [RuleConfigSeverity.Disabled, 'never'], + "body-empty": [RuleConfigSeverity.Disabled, "never"], }); - expect(getRuleQuestionConfig('body')?.skip).toBe(true); + expect(getRuleQuestionConfig("body")?.skip).toBe(true); }); }); -describe('title', () => { +describe("title", () => { test("should field 'title' set by 'description config'", () => { - const TEST_DESC = 'test the description'; + const TEST_DESC = "test the description"; setPromptConfig({ questions: { body: { @@ -63,7 +63,7 @@ describe('title', () => { }, }); - expect(getRuleQuestionConfig('body')?.title).toBe(TEST_DESC); + expect(getRuleQuestionConfig("body")?.title).toBe(TEST_DESC); }); test("should field 'title' be default string when without 'description' config", () => { @@ -73,83 +73,83 @@ describe('title', () => { }, }); - expect(getRuleQuestionConfig('body')?.title).toBe('body:'); + expect(getRuleQuestionConfig("body")?.title).toBe("body:"); }); }); -describe('enum list', () => { - test('should enumList be undefined when without enum rule', () => { +describe("enum list", () => { + test("should enumList be undefined when without enum rule", () => { setRules({ - 'scope-case': [RuleConfigSeverity.Warning, 'never', 'camel-case'], + "scope-case": [RuleConfigSeverity.Warning, "never", "camel-case"], }); - expect(getRuleQuestionConfig('scope')?.enumList).toBeUndefined(); + expect(getRuleQuestionConfig("scope")?.enumList).toBeUndefined(); }); - test('should enumList be undefined when enum rule is not active', () => { + test("should enumList be undefined when enum rule is not active", () => { setRules({ - 'scope-enum': [RuleConfigSeverity.Disabled], + "scope-enum": [RuleConfigSeverity.Disabled], }); - expect(getRuleQuestionConfig('scope')?.enumList).toBeUndefined(); + expect(getRuleQuestionConfig("scope")?.enumList).toBeUndefined(); setRules({ - 'scope-enum': [ + "scope-enum": [ RuleConfigSeverity.Error, - 'never', - ['cli', 'core', 'lint'], + "never", + ["cli", "core", "lint"], ], }); - expect(getRuleQuestionConfig('scope')?.enumList).toBeUndefined(); + expect(getRuleQuestionConfig("scope")?.enumList).toBeUndefined(); setRules({ - 'scope-enum': [RuleConfigSeverity.Error, 'always'], + "scope-enum": [RuleConfigSeverity.Error, "always"], } as any); - expect(getRuleQuestionConfig('scope')?.enumList).toBeUndefined(); + expect(getRuleQuestionConfig("scope")?.enumList).toBeUndefined(); }); - test('should enumList be undefined when enum rule is not a array', () => { + test("should enumList be undefined when enum rule is not a array", () => { setRules({ - 'scope-enum': [RuleConfigSeverity.Error, 'always', {}], + "scope-enum": [RuleConfigSeverity.Error, "always", {}], } as any); - expect(getRuleQuestionConfig('scope')?.enumList).toBeUndefined(); + expect(getRuleQuestionConfig("scope")?.enumList).toBeUndefined(); }); test("should enumList same with enum rule when without 'enum' config", () => { - const ENUM_RULE_LIST = ['cli', 'core', 'lint']; + const ENUM_RULE_LIST = ["cli", "core", "lint"]; setRules({ - 'scope-enum': [RuleConfigSeverity.Error, 'always', ENUM_RULE_LIST], + "scope-enum": [RuleConfigSeverity.Error, "always", ENUM_RULE_LIST], } as any); setPromptConfig({ questions: { scope: { - description: 'test scope', + description: "test scope", }, }, }); - const enumList = getRuleQuestionConfig('scope')?.enumList; + const enumList = getRuleQuestionConfig("scope")?.enumList; expect(enumList).not.toBe(ENUM_RULE_LIST); expect(enumList).toEqual(ENUM_RULE_LIST); }); - test('should enumList item concat description', () => { - const ENUM_RULE_LIST = ['cli', 'core', 'lint']; + test("should enumList item concat description", () => { + const ENUM_RULE_LIST = ["cli", "core", "lint"]; setRules({ - 'scope-enum': [RuleConfigSeverity.Error, 'always', ENUM_RULE_LIST], + "scope-enum": [RuleConfigSeverity.Error, "always", ENUM_RULE_LIST], } as any); setPromptConfig({ questions: { scope: { - description: 'test scope', + description: "test scope", enum: { cli: { - description: 'CLI', + description: "CLI", }, core: { - description: 'CORE', + description: "CORE", }, lint: {}, }, @@ -157,70 +157,70 @@ describe('enum list', () => { }, }); - const enumList = getRuleQuestionConfig('scope')?.enumList; + const enumList = getRuleQuestionConfig("scope")?.enumList; expect(enumList).toHaveLength(3); expect(enumList).toEqual([ { name: expect.stringMatching(/cli:[\s]*CLI/), - value: 'cli', - short: 'cli', + value: "cli", + short: "cli", }, { name: expect.stringMatching(/core:[\s]*CORE/), - value: 'core', - short: 'core', + value: "core", + short: "core", }, - 'lint', + "lint", ]); }); - test('should enumList item padding format with 4 blank', () => { + test("should enumList item padding format with 4 blank", () => { const LONGEST = 12; - const longestItem = ''.padEnd(LONGEST, 'x'); - const enumRuleList = ['cli', 'core', longestItem]; + const longestItem = "".padEnd(LONGEST, "x"); + const enumRuleList = ["cli", "core", longestItem]; setRules({ - 'scope-enum': [RuleConfigSeverity.Error, 'always', enumRuleList], + "scope-enum": [RuleConfigSeverity.Error, "always", enumRuleList], } as any); setPromptConfig({ questions: { scope: { - description: 'test scope', + description: "test scope", enum: { cli: { - description: 'Test CLI', + description: "Test CLI", }, core: { - description: 'Test CORE', + description: "Test CORE", }, [longestItem]: { - description: 'Test', + description: "Test", }, }, }, }, }); - const enumList = getRuleQuestionConfig('scope')?.enumList; + const enumList = getRuleQuestionConfig("scope")?.enumList; expect(enumList).toHaveLength(3); expect(enumList).toEqual([ { name: expect.stringMatching( - new RegExp(`^cli:[\\s]{${LONGEST - 4 + 4}}Test CLI$`) + new RegExp(`^cli:[\\s]{${LONGEST - 4 + 4}}Test CLI$`), ), - value: 'cli', - short: 'cli', + value: "cli", + short: "cli", }, { name: expect.stringMatching( - new RegExp(`^core:[\\s]{${LONGEST - 5 + 4}}Test CORE$`) + new RegExp(`^core:[\\s]{${LONGEST - 5 + 4}}Test CORE$`), ), - value: 'core', - short: 'core', + value: "core", + short: "core", }, { name: expect.stringMatching( - new RegExp(`^${longestItem}:[\\s]{${-1 + 4}}Test$`) + new RegExp(`^${longestItem}:[\\s]{${-1 + 4}}Test$`), ), value: longestItem, short: longestItem, @@ -229,15 +229,15 @@ describe('enum list', () => { }); test("should enumList item sorted by 'enum' config order", () => { - const ENUM_RULE_LIST = ['cli', 'core', 'lint']; + const ENUM_RULE_LIST = ["cli", "core", "lint"]; setRules({ - 'scope-enum': [RuleConfigSeverity.Error, 'always', ENUM_RULE_LIST], + "scope-enum": [RuleConfigSeverity.Error, "always", ENUM_RULE_LIST], } as any); setPromptConfig({ questions: { scope: { - description: 'test scope', + description: "test scope", enum: { core: {}, lint: {}, @@ -247,89 +247,89 @@ describe('enum list', () => { }, }); - const enumList = getRuleQuestionConfig('scope')?.enumList; + const enumList = getRuleQuestionConfig("scope")?.enumList; expect(enumList).toHaveLength(3); - expect(enumList?.[0]).toBe('core'); - expect(enumList?.[1]).toBe('lint'); - expect(enumList?.[2]).toBe('cli'); + expect(enumList?.[0]).toBe("core"); + expect(enumList?.[1]).toBe("lint"); + expect(enumList?.[2]).toBe("cli"); }); }); -test('should return correct question config', () => { +test("should return correct question config", () => { setRules({ - 'body-empty': [RuleConfigSeverity.Error, 'never'], - 'body-case': [RuleConfigSeverity.Error, 'always', 'sentence-case'], - 'body-full-stop': [RuleConfigSeverity.Error, 'always', '!'], - 'body-min-length': [RuleConfigSeverity.Error, 'always', 10], - 'body-max-length': [RuleConfigSeverity.Error, 'always', 100], - 'scope-enum': [RuleConfigSeverity.Error, 'always', ['cli', 'core', 'lint']], + "body-empty": [RuleConfigSeverity.Error, "never"], + "body-case": [RuleConfigSeverity.Error, "always", "sentence-case"], + "body-full-stop": [RuleConfigSeverity.Error, "always", "!"], + "body-min-length": [RuleConfigSeverity.Error, "always", 10], + "body-max-length": [RuleConfigSeverity.Error, "always", 100], + "scope-enum": [RuleConfigSeverity.Error, "always", ["cli", "core", "lint"]], } as any); const MESSAGES = { - skip: ':skip', - max: 'upper %d chars', - min: '%d chars at least', - emptyWarning: 'can not be empty', - upperLimitWarning: 'over limit', - lowerLimitWarning: 'below limit', + skip: ":skip", + max: "upper %d chars", + min: "%d chars at least", + emptyWarning: "can not be empty", + upperLimitWarning: "over limit", + lowerLimitWarning: "below limit", }; setPromptConfig({ messages: MESSAGES, questions: { body: { - description: 'please input body: (Test)', + description: "please input body: (Test)", }, scope: { - description: 'please choose the scope: (Test)', + description: "please choose the scope: (Test)", enum: { core: { - description: 'CORE', + description: "CORE", }, lint: { - description: 'LINT', + description: "LINT", }, cli: { - description: 'CLI', + description: "CLI", }, }, }, }, }); - const scopeQuestionConfig = getRuleQuestionConfig('scope'); + const scopeQuestionConfig = getRuleQuestionConfig("scope"); expect(scopeQuestionConfig).toEqual({ skip: true, - title: 'please choose the scope: (Test)', + title: "please choose the scope: (Test)", messages: MESSAGES, minLength: 0, maxLength: Infinity, enumList: [ { - name: 'core: CORE', - value: 'core', - short: 'core', + name: "core: CORE", + value: "core", + short: "core", }, { - name: 'lint: LINT', - value: 'lint', - short: 'lint', + name: "lint: LINT", + value: "lint", + short: "lint", }, { - name: 'cli: CLI', - value: 'cli', - short: 'cli', + name: "cli: CLI", + value: "cli", + short: "cli", }, ], caseFn: expect.any(Function), fullStopFn: expect.any(Function), }); - expect(scopeQuestionConfig?.caseFn?.('xxxx')).toBe('xxxx'); - expect(scopeQuestionConfig?.fullStopFn?.('xxxx')).toBe('xxxx'); + expect(scopeQuestionConfig?.caseFn?.("xxxx")).toBe("xxxx"); + expect(scopeQuestionConfig?.fullStopFn?.("xxxx")).toBe("xxxx"); - const bodyQuestionConfig = getRuleQuestionConfig('body'); + const bodyQuestionConfig = getRuleQuestionConfig("body"); expect(bodyQuestionConfig).toEqual({ skip: false, - title: 'please input body: (Test)', + title: "please input body: (Test)", messages: MESSAGES, minLength: 10, maxLength: 100, @@ -337,6 +337,6 @@ test('should return correct question config', () => { caseFn: expect.any(Function), fullStopFn: expect.any(Function), }); - expect(bodyQuestionConfig?.caseFn?.('xxxx')).toBe('Xxxx'); - expect(bodyQuestionConfig?.fullStopFn?.('xxxx')).toBe('xxxx!'); + expect(bodyQuestionConfig?.caseFn?.("xxxx")).toBe("Xxxx"); + expect(bodyQuestionConfig?.fullStopFn?.("xxxx")).toBe("xxxx!"); }); diff --git a/@commitlint/cz-commitlint/src/services/getRuleQuestionConfig.ts b/@commitlint/cz-commitlint/src/services/getRuleQuestionConfig.ts index f1f146fbe6..7cc85fe7fc 100644 --- a/@commitlint/cz-commitlint/src/services/getRuleQuestionConfig.ts +++ b/@commitlint/cz-commitlint/src/services/getRuleQuestionConfig.ts @@ -1,9 +1,9 @@ -import {RuleField} from '@commitlint/types'; -import {QuestionConfig} from '../Question.js'; -import {getPromptMessages, getPromptQuestions} from '../store/prompts.js'; -import {getRule} from '../store/rules.js'; -import getCaseFn from '../utils/case-fn.js'; -import getFullStopFn from '../utils/full-stop-fn.js'; +import { RuleField } from "@commitlint/types"; +import { QuestionConfig } from "../Question.js"; +import { getPromptMessages, getPromptQuestions } from "../store/prompts.js"; +import { getRule } from "../store/rules.js"; +import getCaseFn from "../utils/case-fn.js"; +import getFullStopFn from "../utils/full-stop-fn.js"; import { enumRuleIsActive, getEnumList, @@ -12,12 +12,12 @@ import { ruleIsActive, ruleIsApplicable, ruleIsDisabled, -} from '../utils/rules.js'; +} from "../utils/rules.js"; export default function (rulePrefix: RuleField): QuestionConfig | null { const questions = getPromptQuestions(); const questionSettings = questions[rulePrefix]; - const emptyRule = getRule(rulePrefix, 'empty'); + const emptyRule = getRule(rulePrefix, "empty"); const mustBeEmpty = emptyRule && ruleIsActive(emptyRule) && ruleIsApplicable(emptyRule); @@ -28,18 +28,18 @@ export default function (rulePrefix: RuleField): QuestionConfig | null { const canBeSkip = !emptyRule || ruleIsDisabled(emptyRule); - const enumRule = getRule(rulePrefix, 'enum'); + const enumRule = getRule(rulePrefix, "enum"); const enumRuleList = enumRule && enumRuleIsActive(enumRule) ? getEnumList(enumRule) : null; let enumList; if (enumRuleList) { - const enumDescriptions = questionSettings?.['enum']; + const enumDescriptions = questionSettings?.["enum"]; if (enumDescriptions) { const enumNames = Object.keys(enumDescriptions); const longest = Math.max( - ...enumRuleList.map((enumName) => enumName.length) + ...enumRuleList.map((enumName) => enumName.length), ); // TODO emoji + title enumList = enumRuleList @@ -64,11 +64,11 @@ export default function (rulePrefix: RuleField): QuestionConfig | null { return { skip: canBeSkip, enumList, - title: questionSettings?.['description'] ?? `${rulePrefix}:`, - caseFn: getCaseFn(getRule(rulePrefix, 'case')), - fullStopFn: getFullStopFn(getRule(rulePrefix, 'full-stop')), - minLength: getMinLength(getRule(rulePrefix, 'min-length')), - maxLength: getMaxLength(getRule(rulePrefix, 'max-length')), + title: questionSettings?.["description"] ?? `${rulePrefix}:`, + caseFn: getCaseFn(getRule(rulePrefix, "case")), + fullStopFn: getFullStopFn(getRule(rulePrefix, "full-stop")), + minLength: getMinLength(getRule(rulePrefix, "min-length")), + maxLength: getMaxLength(getRule(rulePrefix, "max-length")), messages: getPromptMessages(), }; } diff --git a/@commitlint/cz-commitlint/src/store/defaultPromptConfigs.ts b/@commitlint/cz-commitlint/src/store/defaultPromptConfigs.ts index e4a4ce8998..650b3762d8 100644 --- a/@commitlint/cz-commitlint/src/store/defaultPromptConfigs.ts +++ b/@commitlint/cz-commitlint/src/store/defaultPromptConfigs.ts @@ -1,33 +1,33 @@ export default { settings: { - scopeEnumSeparator: ',', + scopeEnumSeparator: ",", enableMultipleScopes: false, }, messages: { - skip: '(press enter to skip)', - max: '(max %d chars)', - min: '(min %d chars)', - emptyWarning: '(%s is required)', - upperLimitWarning: '%s is %d characters longer than the upper limit', - lowerLimitWarning: '%s is %d characters less than the lower limit', + skip: "(press enter to skip)", + max: "(max %d chars)", + min: "(min %d chars)", + emptyWarning: "(%s is required)", + upperLimitWarning: "%s is %d characters longer than the upper limit", + lowerLimitWarning: "%s is %d characters less than the lower limit", }, questions: { type: { - description: '<type> holds information about the goal of a change.', + description: "<type> holds information about the goal of a change.", }, scope: { description: - '<scope> marks which sub-component of the project is affected', + "<scope> marks which sub-component of the project is affected", }, subject: { - description: '<subject> is a short, high-level description of the change', + description: "<subject> is a short, high-level description of the change", }, body: { - description: '<body> holds additional information about the change', + description: "<body> holds additional information about the change", }, footer: { description: - '<footer> holds further meta data, such as breaking changes and issue ids', + "<footer> holds further meta data, such as breaking changes and issue ids", }, }, }; diff --git a/@commitlint/cz-commitlint/src/store/prompts.test.ts b/@commitlint/cz-commitlint/src/store/prompts.test.ts index 37e1ceeaa0..9d378b4ed5 100644 --- a/@commitlint/cz-commitlint/src/store/prompts.test.ts +++ b/@commitlint/cz-commitlint/src/store/prompts.test.ts @@ -1,5 +1,5 @@ -import {describe, test, expect, vi, beforeEach} from 'vitest'; -import * as prompts from './prompts.js'; +import { describe, test, expect, vi, beforeEach } from "vitest"; +import * as prompts from "./prompts.js"; let getPromptQuestions: typeof prompts.getPromptQuestions; let getPromptMessages: typeof prompts.getPromptMessages; @@ -8,16 +8,20 @@ let setPromptConfig: typeof prompts.setPromptConfig; beforeEach(async () => { vi.resetModules(); - ({getPromptQuestions, getPromptMessages, getPromptSettings, setPromptConfig} = - await import('./prompts.js')); + ({ + getPromptQuestions, + getPromptMessages, + getPromptSettings, + setPromptConfig, + } = await import("./prompts.js")); }); -describe('setPromptConfig', () => { - test('should cover questions when prompt config questions is plain object', () => { +describe("setPromptConfig", () => { + test("should cover questions when prompt config questions is plain object", () => { const promptConfig = { questions: { type: { - description: 'input type', + description: "input type", }, }, }; @@ -25,15 +29,15 @@ describe('setPromptConfig', () => { expect(getPromptQuestions()).toBe(promptConfig.questions); }); - test('should not set questions when prompt config questions is not a plain object', () => { - const initialQuestions = {...getPromptQuestions()}; + test("should not set questions when prompt config questions is not a plain object", () => { + const initialQuestions = { ...getPromptQuestions() }; setPromptConfig({ questions: null, } as any); expect(getPromptQuestions()).toEqual(initialQuestions); setPromptConfig({ - questions: 'questions', + questions: "questions", } as any); expect(getPromptQuestions()).toEqual(initialQuestions); @@ -43,66 +47,66 @@ describe('setPromptConfig', () => { expect(getPromptQuestions()).toEqual(initialQuestions); }); - test('should merge message when prompt config message is string', () => { - const initialMessages = {...getPromptMessages()}; + test("should merge message when prompt config message is string", () => { + const initialMessages = { ...getPromptMessages() }; const promptConfig = { messages: { - emptyWarning: '(%s can not be empty)', + emptyWarning: "(%s can not be empty)", }, }; setPromptConfig(promptConfig); - expect(getPromptMessages()['emptyWarning']).toBe( - promptConfig.messages.emptyWarning + expect(getPromptMessages()["emptyWarning"]).toBe( + promptConfig.messages.emptyWarning, ); - expect(getPromptMessages()['lowerLimitWarning']).toBe( - initialMessages['lowerLimitWarning'] + expect(getPromptMessages()["lowerLimitWarning"]).toBe( + initialMessages["lowerLimitWarning"], ); }); - test('should not merge message when prompt config message is not a string', () => { - const initialMessages = {...getPromptMessages()}; + test("should not merge message when prompt config message is not a string", () => { + const initialMessages = { ...getPromptMessages() }; const promptConfig = { messages: { - emptyWarning: '(%s can not be empty)', + emptyWarning: "(%s can not be empty)", min: function () { - return 'min:'; + return "min:"; }, }, }; setPromptConfig(promptConfig as any); - expect(getPromptMessages()['emptyWarning']).toBe( - promptConfig.messages.emptyWarning + expect(getPromptMessages()["emptyWarning"]).toBe( + promptConfig.messages.emptyWarning, ); - expect(getPromptMessages()['min']).toBe(initialMessages['min']); + expect(getPromptMessages()["min"]).toBe(initialMessages["min"]); }); - test('should ignore non-essential message', () => { - const initialMessages = {...getPromptMessages()}; + test("should ignore non-essential message", () => { + const initialMessages = { ...getPromptMessages() }; const promptConfig = { messages: { - more: 'learn more', + more: "learn more", }, }; setPromptConfig(promptConfig); expect(getPromptMessages()).toEqual(initialMessages); }); - test('should fields be independent', () => { - const initialQuestions = {...getPromptQuestions()}; + test("should fields be independent", () => { + const initialQuestions = { ...getPromptQuestions() }; setPromptConfig({ messages: { - emptyWarning: '(%s can not be empty)', + emptyWarning: "(%s can not be empty)", }, }); expect(getPromptQuestions()).toEqual(initialQuestions); - const initialMessages = {...getPromptMessages()}; + const initialMessages = { ...getPromptMessages() }; setPromptConfig({ questions: { type: { - description: 'input type', + description: "input type", }, }, }); @@ -112,29 +116,29 @@ describe('setPromptConfig', () => { test('should settings scopeEnumSeparator be set when value is ",\\/"', () => { setPromptConfig({ settings: { - scopeEnumSeparator: '/', + scopeEnumSeparator: "/", }, }); - expect(getPromptSettings()['scopeEnumSeparator']).toEqual('/'); + expect(getPromptSettings()["scopeEnumSeparator"]).toEqual("/"); const processExit = vi - .spyOn(process, 'exit') + .spyOn(process, "exit") .mockImplementation(() => undefined as never); setPromptConfig({ settings: { - scopeEnumSeparator: '-', + scopeEnumSeparator: "-", }, }); expect(processExit).toHaveBeenCalledWith(1); processExit.mockClear(); }); - test('should pass on settings', () => { + test("should pass on settings", () => { setPromptConfig({ settings: { enableMultipleScopes: true, }, }); - expect(getPromptSettings()['enableMultipleScopes']).toEqual(true); + expect(getPromptSettings()["enableMultipleScopes"]).toEqual(true); }); }); diff --git a/@commitlint/cz-commitlint/src/store/prompts.ts b/@commitlint/cz-commitlint/src/store/prompts.ts index 87faf0e047..dfa1846833 100644 --- a/@commitlint/cz-commitlint/src/store/prompts.ts +++ b/@commitlint/cz-commitlint/src/store/prompts.ts @@ -1,9 +1,9 @@ -import type {PromptConfig, UserPromptConfig} from '@commitlint/types'; -import isPlainObject from 'lodash.isplainobject'; +import type { PromptConfig, UserPromptConfig } from "@commitlint/types"; +import isPlainObject from "lodash.isplainobject"; -import defaultPromptConfigs from './defaultPromptConfigs.js'; +import defaultPromptConfigs from "./defaultPromptConfigs.js"; -const storeKey = Symbol('promptConfig'); +const storeKey = Symbol("promptConfig"); const store: { [storeKey]: PromptConfig; @@ -12,46 +12,46 @@ const store: { }; export function setPromptConfig(newPromptConfig: UserPromptConfig): void { - const {settings, messages, questions} = newPromptConfig; + const { settings, messages, questions } = newPromptConfig; if (messages) { const requiredMessageKeys = Object.keys(defaultPromptConfigs.messages); requiredMessageKeys.forEach((key: string) => { const message = messages[key]; - if (typeof message === 'string') { - store[storeKey]['messages'][key] = message; + if (typeof message === "string") { + store[storeKey]["messages"][key] = message; } }); } if (questions && isPlainObject(questions)) { - store[storeKey]['questions'] = questions; + store[storeKey]["questions"] = questions; } if (settings && isPlainObject(settings)) { if ( - settings['scopeEnumSeparator'] && - !/^\/|\\|,$/.test(settings['scopeEnumSeparator']) + settings["scopeEnumSeparator"] && + !/^\/|\\|,$/.test(settings["scopeEnumSeparator"]) ) { console.log( - `prompt.settings.scopeEnumSeparator must be one of ',', '\\', '/'.` + `prompt.settings.scopeEnumSeparator must be one of ',', '\\', '/'.`, ); process.exit(1); } - store[storeKey]['settings'] = { + store[storeKey]["settings"] = { ...defaultPromptConfigs.settings, ...settings, }; } } -export function getPromptMessages(): Readonly<PromptConfig['messages']> { - return (store[storeKey] && store[storeKey]['messages']) ?? {}; +export function getPromptMessages(): Readonly<PromptConfig["messages"]> { + return (store[storeKey] && store[storeKey]["messages"]) ?? {}; } -export function getPromptQuestions(): Readonly<PromptConfig['questions']> { - return (store[storeKey] && store[storeKey]['questions']) ?? {}; +export function getPromptQuestions(): Readonly<PromptConfig["questions"]> { + return (store[storeKey] && store[storeKey]["questions"]) ?? {}; } -export function getPromptSettings(): Readonly<PromptConfig['settings']> { - return (store[storeKey] && store[storeKey]['settings']) ?? {}; +export function getPromptSettings(): Readonly<PromptConfig["settings"]> { + return (store[storeKey] && store[storeKey]["settings"]) ?? {}; } diff --git a/@commitlint/cz-commitlint/src/store/rules.test.ts b/@commitlint/cz-commitlint/src/store/rules.test.ts index 9fb5280943..373dd6f101 100644 --- a/@commitlint/cz-commitlint/src/store/rules.test.ts +++ b/@commitlint/cz-commitlint/src/store/rules.test.ts @@ -1,70 +1,70 @@ -import {describe, test, expect, vi, beforeEach} from 'vitest'; -import {QualifiedRules, RuleConfigSeverity} from '@commitlint/types'; +import { describe, test, expect, vi, beforeEach } from "vitest"; +import { QualifiedRules, RuleConfigSeverity } from "@commitlint/types"; -import {GetRuleMethod, SetRulesMethod} from './rules.js'; +import { GetRuleMethod, SetRulesMethod } from "./rules.js"; let getRule: GetRuleMethod; let setRules: SetRulesMethod; beforeEach(async () => { vi.resetModules(); - ({getRule, setRules} = await import('./rules.js')); + ({ getRule, setRules } = await import("./rules.js")); }); -describe('getRule', () => { - test('should get rule when prefix and property strict match', () => { +describe("getRule", () => { + test("should get rule when prefix and property strict match", () => { const rules: QualifiedRules = { - 'body-max-length': [RuleConfigSeverity.Error, 'always', 100], - 'footer-max-line-length': [RuleConfigSeverity.Error, 'always', 100], - 'subject-empty': [RuleConfigSeverity.Error, 'never'], + "body-max-length": [RuleConfigSeverity.Error, "always", 100], + "footer-max-line-length": [RuleConfigSeverity.Error, "always", 100], + "subject-empty": [RuleConfigSeverity.Error, "never"], }; setRules(rules); - expect(getRule('body', 'max-length')).toBe(rules['body-max-length']); - expect(getRule('footer', 'max-line-length')).toBe( - rules['footer-max-line-length'] + expect(getRule("body", "max-length")).toBe(rules["body-max-length"]); + expect(getRule("footer", "max-line-length")).toBe( + rules["footer-max-line-length"], ); - expect(getRule('subject', 'empty')).toBe(rules['subject-empty']); + expect(getRule("subject", "empty")).toBe(rules["subject-empty"]); }); - test('should not get rule when prefix is invalid', () => { + test("should not get rule when prefix is invalid", () => { const rules: QualifiedRules = { - 'body-max-length': [RuleConfigSeverity.Error, 'always', 100], + "body-max-length": [RuleConfigSeverity.Error, "always", 100], }; setRules(rules); - expect(getRule('body-max', 'length')).toBeUndefined(); - expect(getRule('body-max', 'max-length')).toBeUndefined(); - expect(getRule('', 'body-max-length')).toBeUndefined(); + expect(getRule("body-max", "length")).toBeUndefined(); + expect(getRule("body-max", "max-length")).toBeUndefined(); + expect(getRule("", "body-max-length")).toBeUndefined(); }); - test('should not get rule when property is partial match', () => { + test("should not get rule when property is partial match", () => { const rules: QualifiedRules = { - 'body-max-length': [RuleConfigSeverity.Error, 'always', 100], - 'body-leading-blank': [RuleConfigSeverity.Warning, 'always'], + "body-max-length": [RuleConfigSeverity.Error, "always", 100], + "body-leading-blank": [RuleConfigSeverity.Warning, "always"], }; setRules(rules); - expect(getRule('body', 'length')).toBeUndefined(); - expect(getRule('body', 'line-leading-blank')).toBeUndefined(); + expect(getRule("body", "length")).toBeUndefined(); + expect(getRule("body", "line-leading-blank")).toBeUndefined(); }); }); -describe('setRule', () => { - test('should overwrite all rules when setRule', () => { - expect(getRule('body', 'max-length')).toBeUndefined(); +describe("setRule", () => { + test("should overwrite all rules when setRule", () => { + expect(getRule("body", "max-length")).toBeUndefined(); let rules: QualifiedRules = { - 'body-max-length': [RuleConfigSeverity.Error, 'always', 100], + "body-max-length": [RuleConfigSeverity.Error, "always", 100], }; setRules(rules); - expect(getRule('body', 'max-length')).toBe(rules['body-max-length']); + expect(getRule("body", "max-length")).toBe(rules["body-max-length"]); rules = { - 'footer-max-length': [RuleConfigSeverity.Error, 'always', 100], + "footer-max-length": [RuleConfigSeverity.Error, "always", 100], }; setRules(rules); - expect(getRule('body', 'max-length')).toBeUndefined(); - expect(getRule('footer', 'max-length')).toBe(rules['footer-max-length']); + expect(getRule("body", "max-length")).toBeUndefined(); + expect(getRule("footer", "max-length")).toBe(rules["footer-max-length"]); }); }); diff --git a/@commitlint/cz-commitlint/src/store/rules.ts b/@commitlint/cz-commitlint/src/store/rules.ts index 5308b4fb9e..661d4e0ebd 100644 --- a/@commitlint/cz-commitlint/src/store/rules.ts +++ b/@commitlint/cz-commitlint/src/store/rules.ts @@ -1,8 +1,8 @@ -import {QualifiedRules} from '@commitlint/types'; +import { QualifiedRules } from "@commitlint/types"; -import type {Rule} from '../types.js'; +import type { Rule } from "../types.js"; -const storeKey = Symbol('rules'); +const storeKey = Symbol("rules"); const store: { [storeKey]: QualifiedRules; @@ -11,7 +11,7 @@ const store: { }; export function getRule(key: string, property: string): Rule | undefined { - if (key.split('-').length > 1) { + if (key.split("-").length > 1) { return; } return store[storeKey][`${key}-${property}`]; diff --git a/@commitlint/cz-commitlint/src/types.ts b/@commitlint/cz-commitlint/src/types.ts index fba53c54eb..b0c2d2c528 100644 --- a/@commitlint/cz-commitlint/src/types.ts +++ b/@commitlint/cz-commitlint/src/types.ts @@ -1,4 +1,4 @@ -import {RuleConfigCondition, RuleConfigSeverity} from '@commitlint/types'; +import { RuleConfigCondition, RuleConfigSeverity } from "@commitlint/types"; export type Rule = | Readonly<[RuleConfigSeverity.Disabled]> diff --git a/@commitlint/cz-commitlint/src/utils/case-fn.test.ts b/@commitlint/cz-commitlint/src/utils/case-fn.test.ts index 4861cb3462..a1c0a44f33 100644 --- a/@commitlint/cz-commitlint/src/utils/case-fn.test.ts +++ b/@commitlint/cz-commitlint/src/utils/case-fn.test.ts @@ -1,93 +1,93 @@ -import {test, expect} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { test, expect } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; -import getCaseFn from './case-fn.js'; +import getCaseFn from "./case-fn.js"; -test('should not transform when rule is disabled', () => { +test("should not transform when rule is disabled", () => { let rule = getCaseFn([RuleConfigSeverity.Disabled]); - expect(rule('test')).toBe('test'); - expect(rule('test-foo')).toBe('test-foo'); - expect(rule('testFoo')).toBe('testFoo'); - expect(rule('TEST_FOO')).toBe('TEST_FOO'); + expect(rule("test")).toBe("test"); + expect(rule("test-foo")).toBe("test-foo"); + expect(rule("testFoo")).toBe("testFoo"); + expect(rule("TEST_FOO")).toBe("TEST_FOO"); rule = getCaseFn(); - expect(rule('test')).toBe('test'); - expect(rule('test-foo')).toBe('test-foo'); - expect(rule('testFoo')).toBe('testFoo'); - expect(rule('TEST_FOO')).toBe('TEST_FOO'); - - rule = getCaseFn([RuleConfigSeverity.Warning, 'never']); - expect(rule('test')).toBe('test'); - expect(rule('test-foo')).toBe('test-foo'); - expect(rule('testFoo')).toBe('testFoo'); - expect(rule('TEST_FOO')).toBe('TEST_FOO'); + expect(rule("test")).toBe("test"); + expect(rule("test-foo")).toBe("test-foo"); + expect(rule("testFoo")).toBe("testFoo"); + expect(rule("TEST_FOO")).toBe("TEST_FOO"); + + rule = getCaseFn([RuleConfigSeverity.Warning, "never"]); + expect(rule("test")).toBe("test"); + expect(rule("test-foo")).toBe("test-foo"); + expect(rule("testFoo")).toBe("testFoo"); + expect(rule("TEST_FOO")).toBe("TEST_FOO"); }); -test('should throw error on invalid casing', () => { - let rule = getCaseFn([RuleConfigSeverity.Warning, 'always']); - expect(() => rule('test')).toThrow('Unknown target case "undefined"'); +test("should throw error on invalid casing", () => { + let rule = getCaseFn([RuleConfigSeverity.Warning, "always"]); + expect(() => rule("test")).toThrow('Unknown target case "undefined"'); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'foo']); - expect(() => rule('test')).toThrow('Unknown target case "foo"'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "foo"]); + expect(() => rule("test")).toThrow('Unknown target case "foo"'); }); -test('should transform text correctly with single case', () => { - let rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'camel-case']); - expect(rule('TEST_FOOBar-baz baz')).toBe('testFooBarBazBaz'); +test("should transform text correctly with single case", () => { + let rule = getCaseFn([RuleConfigSeverity.Warning, "always", "camel-case"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("testFooBarBazBaz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'kebab-case']); - expect(rule('TEST_FOOBar-baz baz')).toBe('test-foo-bar-baz-baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "kebab-case"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("test-foo-bar-baz-baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'snake-case']); - expect(rule('TEST_FOOBar-baz baz')).toBe('test_foo_bar_baz_baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "snake-case"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("test_foo_bar_baz_baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'pascal-case']); - expect(rule('TEST_FOOBar-baz baz')).toBe('TestFooBarBazBaz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "pascal-case"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("TestFooBarBazBaz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'start-case']); - expect(rule('TEST_FOOBar-baz baz')).toBe('TEST FOO Bar Baz Baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "start-case"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("TEST FOO Bar Baz Baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'upper-case']); - expect(rule('TEST_FOOBar-baz baz')).toBe('TEST_FOOBAR-BAZ BAZ'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "upper-case"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("TEST_FOOBAR-BAZ BAZ"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'uppercase']); - expect(rule('TEST_FOOBar-baz baz')).toBe('TEST_FOOBAR-BAZ BAZ'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "uppercase"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("TEST_FOOBAR-BAZ BAZ"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'sentence-case']); - expect(rule('tEST_FOOBar-baz baz')).toBe('TEST_FOOBar-baz baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "sentence-case"]); + expect(rule("tEST_FOOBar-baz baz")).toBe("TEST_FOOBar-baz baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'sentencecase']); - expect(rule('tEST_FOOBar-baz baz')).toBe('TEST_FOOBar-baz baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "sentencecase"]); + expect(rule("tEST_FOOBar-baz baz")).toBe("TEST_FOOBar-baz baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'lower-case']); - expect(rule('TEST_FOOBar-baz baz')).toBe('test_foobar-baz baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "lower-case"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("test_foobar-baz baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'lowercase']); - expect(rule('TEST_FOOBar-baz baz')).toBe('test_foobar-baz baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "lowercase"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("test_foobar-baz baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'lowerCase']); - expect(rule('TEST_FOOBar-baz baz')).toBe('test_foobar-baz baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "lowerCase"]); + expect(rule("TEST_FOOBar-baz baz")).toBe("test_foobar-baz baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'lowerCase']); - expect(rule(['TEST_FOOBar-baz', 'bAz'])).toBe('test_foobar-baz,baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "lowerCase"]); + expect(rule(["TEST_FOOBar-baz", "bAz"])).toBe("test_foobar-baz,baz"); - rule = getCaseFn([RuleConfigSeverity.Warning, 'always', 'lowerCase']); - expect(rule(['TEST_FOOBar-baz', 'bAz'], '|')).toBe('test_foobar-baz|baz'); + rule = getCaseFn([RuleConfigSeverity.Warning, "always", "lowerCase"]); + expect(rule(["TEST_FOOBar-baz", "bAz"], "|")).toBe("test_foobar-baz|baz"); }); -test('should transform text correctly with multiple cases', () => { +test("should transform text correctly with multiple cases", () => { const rule = getCaseFn([ RuleConfigSeverity.Warning, - 'always', - ['camel-case', 'lowercase'], + "always", + ["camel-case", "lowercase"], ]); - expect(rule('test')).toBe('test'); - expect(rule('test-foo')).toBe('test-foo'); - expect(rule('testFoo')).toBe('testFoo'); - expect(rule('TEST_FOO')).toBe('testFoo'); - - expect(rule(['testFoo', 'test_foo'])).toBe('testFoo,testFoo'); - expect(rule(['TEST_foo', 'test_foo'])).toBe('test_foo,test_foo'); - expect(rule(['TEST_FOO', 'Test_foo'])).toBe('testFoo,testFoo'); - expect(rule(['TEST_FOO', 'Test_foo'], '|')).toBe('testFoo|testFoo'); + expect(rule("test")).toBe("test"); + expect(rule("test-foo")).toBe("test-foo"); + expect(rule("testFoo")).toBe("testFoo"); + expect(rule("TEST_FOO")).toBe("testFoo"); + + expect(rule(["testFoo", "test_foo"])).toBe("testFoo,testFoo"); + expect(rule(["TEST_foo", "test_foo"])).toBe("test_foo,test_foo"); + expect(rule(["TEST_FOO", "Test_foo"])).toBe("testFoo,testFoo"); + expect(rule(["TEST_FOO", "Test_foo"], "|")).toBe("testFoo|testFoo"); }); diff --git a/@commitlint/cz-commitlint/src/utils/case-fn.ts b/@commitlint/cz-commitlint/src/utils/case-fn.ts index 394b786a0c..81723af7ca 100644 --- a/@commitlint/cz-commitlint/src/utils/case-fn.ts +++ b/@commitlint/cz-commitlint/src/utils/case-fn.ts @@ -1,8 +1,8 @@ -import {case as ensureCase, toCase} from '@commitlint/ensure'; -import {TargetCaseType} from '@commitlint/types'; +import { case as ensureCase, toCase } from "@commitlint/ensure"; +import { TargetCaseType } from "@commitlint/types"; -import {Rule} from '../types.js'; -import {ruleIsActive, ruleIsNotApplicable} from './rules.js'; +import { Rule } from "../types.js"; +import { ruleIsActive, ruleIsNotApplicable } from "./rules.js"; export type CaseFn = (input: string | string[], delimiter?: string) => string; diff --git a/@commitlint/cz-commitlint/src/utils/full-stop-fn.test.ts b/@commitlint/cz-commitlint/src/utils/full-stop-fn.test.ts index a70c2a0c18..418af8af35 100644 --- a/@commitlint/cz-commitlint/src/utils/full-stop-fn.test.ts +++ b/@commitlint/cz-commitlint/src/utils/full-stop-fn.test.ts @@ -1,69 +1,69 @@ -import {test, expect} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { test, expect } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; -import getFullStopFn from './full-stop-fn.js'; +import getFullStopFn from "./full-stop-fn.js"; -test('should not apply', () => { +test("should not apply", () => { let rule = getFullStopFn([RuleConfigSeverity.Disabled]); - expect(rule('test.')).toBe('test.'); - expect(rule('test')).toBe('test'); - expect(rule('test..')).toBe('test..'); - expect(rule('')).toBe(''); + expect(rule("test.")).toBe("test."); + expect(rule("test")).toBe("test"); + expect(rule("test..")).toBe("test.."); + expect(rule("")).toBe(""); rule = getFullStopFn(); - expect(rule('test.')).toBe('test.'); - expect(rule('test')).toBe('test'); - expect(rule('test..')).toBe('test..'); - expect(rule('')).toBe(''); + expect(rule("test.")).toBe("test."); + expect(rule("test")).toBe("test"); + expect(rule("test..")).toBe("test.."); + expect(rule("")).toBe(""); - rule = getFullStopFn([RuleConfigSeverity.Disabled, 'always']); - expect(rule('test.')).toBe('test.'); - expect(rule('test')).toBe('test'); - expect(rule('test..')).toBe('test..'); - expect(rule('')).toBe(''); + rule = getFullStopFn([RuleConfigSeverity.Disabled, "always"]); + expect(rule("test.")).toBe("test."); + expect(rule("test")).toBe("test"); + expect(rule("test..")).toBe("test.."); + expect(rule("")).toBe(""); - rule = getFullStopFn([RuleConfigSeverity.Disabled, 'always', 1]); - expect(rule('test.')).toBe('test.'); - expect(rule('test')).toBe('test'); - expect(rule('test..')).toBe('test..'); - expect(rule('')).toBe(''); + rule = getFullStopFn([RuleConfigSeverity.Disabled, "always", 1]); + expect(rule("test.")).toBe("test."); + expect(rule("test")).toBe("test"); + expect(rule("test..")).toBe("test.."); + expect(rule("")).toBe(""); - rule = getFullStopFn([RuleConfigSeverity.Disabled, 'never']); - expect(rule('test.')).toBe('test.'); - expect(rule('test')).toBe('test'); - expect(rule('test..')).toBe('test..'); - expect(rule('')).toBe(''); + rule = getFullStopFn([RuleConfigSeverity.Disabled, "never"]); + expect(rule("test.")).toBe("test."); + expect(rule("test")).toBe("test"); + expect(rule("test..")).toBe("test.."); + expect(rule("")).toBe(""); - rule = getFullStopFn([RuleConfigSeverity.Disabled, 'never', ['.']]); - expect(rule('test.')).toBe('test.'); - expect(rule('test')).toBe('test'); - expect(rule('test..')).toBe('test..'); - expect(rule('')).toBe(''); + rule = getFullStopFn([RuleConfigSeverity.Disabled, "never", ["."]]); + expect(rule("test.")).toBe("test."); + expect(rule("test")).toBe("test"); + expect(rule("test..")).toBe("test.."); + expect(rule("")).toBe(""); }); -test('should add full stop', () => { - let rule = getFullStopFn([RuleConfigSeverity.Error, 'always', '.']); - expect(rule('test')).toBe('test.'); - expect(rule('test.')).toBe('test.'); - expect(rule('')).toBe('.'); +test("should add full stop", () => { + let rule = getFullStopFn([RuleConfigSeverity.Error, "always", "."]); + expect(rule("test")).toBe("test."); + expect(rule("test.")).toBe("test."); + expect(rule("")).toBe("."); - rule = getFullStopFn([RuleConfigSeverity.Error, 'always', '\n']); - expect(rule('test')).toBe('test\n'); - expect(rule('test.')).toBe('test.\n'); - expect(rule('')).toBe('\n'); + rule = getFullStopFn([RuleConfigSeverity.Error, "always", "\n"]); + expect(rule("test")).toBe("test\n"); + expect(rule("test.")).toBe("test.\n"); + expect(rule("")).toBe("\n"); }); -test('should remove full stop', () => { - let rule = getFullStopFn([RuleConfigSeverity.Error, 'never', '.']); - expect(rule('test')).toBe('test'); - expect(rule('test.')).toBe('test'); - expect(rule('')).toBe(''); - expect(rule('test..')).toBe('test'); - expect(rule('test.end')).toBe('test.end'); +test("should remove full stop", () => { + let rule = getFullStopFn([RuleConfigSeverity.Error, "never", "."]); + expect(rule("test")).toBe("test"); + expect(rule("test.")).toBe("test"); + expect(rule("")).toBe(""); + expect(rule("test..")).toBe("test"); + expect(rule("test.end")).toBe("test.end"); - rule = getFullStopFn([RuleConfigSeverity.Error, 'never', '\n']); - expect(rule('test')).toBe('test'); - expect(rule('test.')).toBe('test.'); - expect(rule('test\n\n')).toBe('test'); - expect(rule('test.\n')).toBe('test.'); + rule = getFullStopFn([RuleConfigSeverity.Error, "never", "\n"]); + expect(rule("test")).toBe("test"); + expect(rule("test.")).toBe("test."); + expect(rule("test\n\n")).toBe("test"); + expect(rule("test.\n")).toBe("test."); }); diff --git a/@commitlint/cz-commitlint/src/utils/full-stop-fn.ts b/@commitlint/cz-commitlint/src/utils/full-stop-fn.ts index 9b219e0001..659a15e915 100644 --- a/@commitlint/cz-commitlint/src/utils/full-stop-fn.ts +++ b/@commitlint/cz-commitlint/src/utils/full-stop-fn.ts @@ -1,5 +1,5 @@ -import {Rule} from '../types.js'; -import {ruleIsActive, ruleIsNotApplicable} from './rules.js'; +import { Rule } from "../types.js"; +import { ruleIsActive, ruleIsNotApplicable } from "./rules.js"; export type FullStopFn = (input: string) => string; @@ -15,7 +15,7 @@ export default function getFullStopFn(rule?: Rule): FullStopFn { return noop; } - if (typeof rule[2] !== 'string') return noop; + if (typeof rule[2] !== "string") return noop; const symbol: string = rule[2]; diff --git a/@commitlint/cz-commitlint/src/utils/leading-blank-fn.test.ts b/@commitlint/cz-commitlint/src/utils/leading-blank-fn.test.ts index 9eb773b87c..c82893859c 100644 --- a/@commitlint/cz-commitlint/src/utils/leading-blank-fn.test.ts +++ b/@commitlint/cz-commitlint/src/utils/leading-blank-fn.test.ts @@ -1,39 +1,39 @@ -import {test, expect} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { test, expect } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; -import getLeadingBlankFn from './leading-blank-fn.js'; +import getLeadingBlankFn from "./leading-blank-fn.js"; -test('should not apply', () => { +test("should not apply", () => { let rule = getLeadingBlankFn([RuleConfigSeverity.Disabled]); - expect(rule('test')).toBe('test'); - expect(rule('\ntest')).toBe('\ntest'); - expect(rule('aaa\ntest')).toBe('aaa\ntest'); - expect(rule('')).toBe(''); + expect(rule("test")).toBe("test"); + expect(rule("\ntest")).toBe("\ntest"); + expect(rule("aaa\ntest")).toBe("aaa\ntest"); + expect(rule("")).toBe(""); rule = getLeadingBlankFn(); - expect(rule('test')).toBe('test'); - expect(rule('\ntest')).toBe('\ntest'); - expect(rule('aaa\ntest')).toBe('aaa\ntest'); - expect(rule('')).toBe(''); + expect(rule("test")).toBe("test"); + expect(rule("\ntest")).toBe("\ntest"); + expect(rule("aaa\ntest")).toBe("aaa\ntest"); + expect(rule("")).toBe(""); }); -test('should add leading blank', () => { - const rule = getLeadingBlankFn([RuleConfigSeverity.Error, 'always']); - expect(rule('test')).toBe('\ntest'); - expect(rule('\ntest')).toBe('\ntest'); - expect(rule('\n\ntest')).toBe('\n\ntest'); - expect(rule('aaa\ntest')).toBe('\naaa\ntest'); - expect(rule('\naaa\ntest')).toBe('\naaa\ntest'); - expect(rule('')).toBe(''); +test("should add leading blank", () => { + const rule = getLeadingBlankFn([RuleConfigSeverity.Error, "always"]); + expect(rule("test")).toBe("\ntest"); + expect(rule("\ntest")).toBe("\ntest"); + expect(rule("\n\ntest")).toBe("\n\ntest"); + expect(rule("aaa\ntest")).toBe("\naaa\ntest"); + expect(rule("\naaa\ntest")).toBe("\naaa\ntest"); + expect(rule("")).toBe(""); }); -test('should remove leading blank', () => { - const rule = getLeadingBlankFn([RuleConfigSeverity.Error, 'never']); - expect(rule('test')).toBe('test'); - expect(rule('\ntest')).toBe('test'); - expect(rule('\n\ntest')).toBe('test'); - expect(rule('aaa\ntest')).toBe('aaa\ntest'); - expect(rule('\naaa\ntest')).toBe('aaa\ntest'); - expect(rule('\n\n\naaa\ntest')).toBe('aaa\ntest'); - expect(rule('')).toBe(''); +test("should remove leading blank", () => { + const rule = getLeadingBlankFn([RuleConfigSeverity.Error, "never"]); + expect(rule("test")).toBe("test"); + expect(rule("\ntest")).toBe("test"); + expect(rule("\n\ntest")).toBe("test"); + expect(rule("aaa\ntest")).toBe("aaa\ntest"); + expect(rule("\naaa\ntest")).toBe("aaa\ntest"); + expect(rule("\n\n\naaa\ntest")).toBe("aaa\ntest"); + expect(rule("")).toBe(""); }); diff --git a/@commitlint/cz-commitlint/src/utils/leading-blank-fn.ts b/@commitlint/cz-commitlint/src/utils/leading-blank-fn.ts index c40e15637d..9400b8c1ed 100644 --- a/@commitlint/cz-commitlint/src/utils/leading-blank-fn.ts +++ b/@commitlint/cz-commitlint/src/utils/leading-blank-fn.ts @@ -1,5 +1,5 @@ -import type {Rule} from '../types.js'; -import {ruleIsActive, ruleIsNotApplicable} from './rules.js'; +import type { Rule } from "../types.js"; +import { ruleIsActive, ruleIsNotApplicable } from "./rules.js"; /** * Get forced leading for rule @@ -7,22 +7,22 @@ import {ruleIsActive, ruleIsNotApplicable} from './rules.js'; * @return transform function applying the leading */ export default function getLeadingBlankFn( - rule?: Rule + rule?: Rule, ): (input: string) => string { if (!rule || !ruleIsActive(rule)) { return (input: string): string => input; } const remove = (input: string): string => { - const fragments = input.split('\n'); - while (fragments.length > 0 && fragments[0] === '') { + const fragments = input.split("\n"); + while (fragments.length > 0 && fragments[0] === "") { fragments.shift(); } - return fragments.join('\n'); + return fragments.join("\n"); }; const lead = (input: string): string => { - const fragments = input.split('\n'); - return fragments[0] === '' ? input : ['', ...fragments].join('\n'); + const fragments = input.split("\n"); + return fragments[0] === "" ? input : ["", ...fragments].join("\n"); }; return !ruleIsNotApplicable(rule) ? lead : remove; diff --git a/@commitlint/cz-commitlint/src/utils/rules.test.ts b/@commitlint/cz-commitlint/src/utils/rules.test.ts index af93a40f7d..4c9855078c 100644 --- a/@commitlint/cz-commitlint/src/utils/rules.test.ts +++ b/@commitlint/cz-commitlint/src/utils/rules.test.ts @@ -1,5 +1,5 @@ -import {test, expect} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { test, expect } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; import { enumRuleIsActive, @@ -10,118 +10,118 @@ import { ruleIsApplicable, ruleIsDisabled, ruleIsNotApplicable, -} from './rules.js'; +} from "./rules.js"; -test('ruleIsDisabled', () => { +test("ruleIsDisabled", () => { expect(ruleIsDisabled([RuleConfigSeverity.Disabled])).toBe(true); - expect(ruleIsDisabled([RuleConfigSeverity.Disabled, 'never'])).toBe(true); - expect(ruleIsDisabled([RuleConfigSeverity.Disabled, 'always'])).toBe(true); + expect(ruleIsDisabled([RuleConfigSeverity.Disabled, "never"])).toBe(true); + expect(ruleIsDisabled([RuleConfigSeverity.Disabled, "always"])).toBe(true); expect(ruleIsDisabled([RuleConfigSeverity.Error] as any)).toBe(false); - expect(ruleIsDisabled([RuleConfigSeverity.Error, 'always'] as any)).toBe( - false + expect(ruleIsDisabled([RuleConfigSeverity.Error, "always"] as any)).toBe( + false, ); }); -test('ruleIsActive', () => { - expect(ruleIsActive([RuleConfigSeverity.Error, 'always'])).toBe(true); - expect(ruleIsActive([RuleConfigSeverity.Warning, 'never'])).toBe(true); - expect(ruleIsActive([RuleConfigSeverity.Disabled, 'always'])).toBe(false); +test("ruleIsActive", () => { + expect(ruleIsActive([RuleConfigSeverity.Error, "always"])).toBe(true); + expect(ruleIsActive([RuleConfigSeverity.Warning, "never"])).toBe(true); + expect(ruleIsActive([RuleConfigSeverity.Disabled, "always"])).toBe(false); expect(ruleIsActive([RuleConfigSeverity.Error] as any)).toBe(true); }); -test('ruleIsApplicable', () => { - expect(ruleIsApplicable([RuleConfigSeverity.Error, 'always'])).toBe(true); - expect(ruleIsApplicable([RuleConfigSeverity.Warning, 'always'])).toBe(true); - expect(ruleIsApplicable([RuleConfigSeverity.Disabled, 'always'])).toBe(true); +test("ruleIsApplicable", () => { + expect(ruleIsApplicable([RuleConfigSeverity.Error, "always"])).toBe(true); + expect(ruleIsApplicable([RuleConfigSeverity.Warning, "always"])).toBe(true); + expect(ruleIsApplicable([RuleConfigSeverity.Disabled, "always"])).toBe(true); expect(ruleIsApplicable(undefined as any)).toBe(false); - expect(ruleIsApplicable('' as any)).toBe(false); + expect(ruleIsApplicable("" as any)).toBe(false); expect(ruleIsApplicable([RuleConfigSeverity.Disabled])).toBe(false); - expect(ruleIsApplicable([RuleConfigSeverity.Disabled, 'never'])).toBe(false); + expect(ruleIsApplicable([RuleConfigSeverity.Disabled, "never"])).toBe(false); }); -test('ruleIsNotApplicable', () => { - expect(ruleIsNotApplicable([RuleConfigSeverity.Error, 'never'])).toBe(true); - expect(ruleIsNotApplicable([RuleConfigSeverity.Warning, 'never'])).toBe(true); - expect(ruleIsNotApplicable([RuleConfigSeverity.Disabled, 'never'])).toBe( - true +test("ruleIsNotApplicable", () => { + expect(ruleIsNotApplicable([RuleConfigSeverity.Error, "never"])).toBe(true); + expect(ruleIsNotApplicable([RuleConfigSeverity.Warning, "never"])).toBe(true); + expect(ruleIsNotApplicable([RuleConfigSeverity.Disabled, "never"])).toBe( + true, ); expect(ruleIsNotApplicable(undefined as any)).toBe(false); - expect(ruleIsNotApplicable('' as any)).toBe(false); + expect(ruleIsNotApplicable("" as any)).toBe(false); expect(ruleIsNotApplicable([RuleConfigSeverity.Error] as any)).toBe(false); - expect(ruleIsNotApplicable([RuleConfigSeverity.Error, 'always'])).toBe(false); - expect(ruleIsNotApplicable([RuleConfigSeverity.Error, 'always', 100])).toBe( - false + expect(ruleIsNotApplicable([RuleConfigSeverity.Error, "always"])).toBe(false); + expect(ruleIsNotApplicable([RuleConfigSeverity.Error, "always", 100])).toBe( + false, ); }); -test('getMaxLength', () => { - expect(getMaxLength([RuleConfigSeverity.Error, 'always', 100])).toBe(100); - expect(getMaxLength([RuleConfigSeverity.Warning, 'never'])).toBe(Infinity); - expect(getMaxLength([RuleConfigSeverity.Disabled, 'always'])).toBe(Infinity); +test("getMaxLength", () => { + expect(getMaxLength([RuleConfigSeverity.Error, "always", 100])).toBe(100); + expect(getMaxLength([RuleConfigSeverity.Warning, "never"])).toBe(Infinity); + expect(getMaxLength([RuleConfigSeverity.Disabled, "always"])).toBe(Infinity); expect(getMaxLength([RuleConfigSeverity.Error] as any)).toBe(Infinity); const rules: any = { - 'body-max-line-length': [RuleConfigSeverity.Error, 'always', 100], - 'header-max-length': [RuleConfigSeverity.Error, 'always', 100], - 'test-max-length': [RuleConfigSeverity.Disabled, 'always', 100], + "body-max-line-length": [RuleConfigSeverity.Error, "always", 100], + "header-max-length": [RuleConfigSeverity.Error, "always", 100], + "test-max-length": [RuleConfigSeverity.Disabled, "always", 100], }; - let lengthRule = rules['header-max-length']; + let lengthRule = rules["header-max-length"]; expect(getMaxLength(lengthRule)).toBe(100); - lengthRule = rules['body-max-line-length']; + lengthRule = rules["body-max-line-length"]; expect(getMaxLength(lengthRule)).toBe(100); - lengthRule = rules['body-max-length']; + lengthRule = rules["body-max-length"]; expect(getMaxLength(lengthRule)).toBe(Infinity); - lengthRule = rules['test-max-length']; + lengthRule = rules["test-max-length"]; expect(getMaxLength(lengthRule)).toBe(Infinity); }); -test('getMinLength', () => { - expect(getMinLength([RuleConfigSeverity.Error, 'always', 10])).toBe(10); - expect(getMinLength([RuleConfigSeverity.Warning, 'never'])).toBe(0); - expect(getMinLength([RuleConfigSeverity.Disabled, 'always'])).toBe(0); +test("getMinLength", () => { + expect(getMinLength([RuleConfigSeverity.Error, "always", 10])).toBe(10); + expect(getMinLength([RuleConfigSeverity.Warning, "never"])).toBe(0); + expect(getMinLength([RuleConfigSeverity.Disabled, "always"])).toBe(0); expect(getMinLength([RuleConfigSeverity.Error] as any)).toBe(0); const rules: any = { - 'body-min-length': [RuleConfigSeverity.Error, 'always', 10], - 'footer-min-length': [RuleConfigSeverity.Error, 'always', 20], - 'test-min-length': [RuleConfigSeverity.Disabled, 'always', 100], + "body-min-length": [RuleConfigSeverity.Error, "always", 10], + "footer-min-length": [RuleConfigSeverity.Error, "always", 20], + "test-min-length": [RuleConfigSeverity.Disabled, "always", 100], }; - let lengthRule = rules['header-min-length']; + let lengthRule = rules["header-min-length"]; expect(getMinLength(lengthRule)).toBe(0); - lengthRule = rules['body-min-length']; + lengthRule = rules["body-min-length"]; expect(getMinLength(lengthRule)).toBe(10); - lengthRule = rules['test-min-length']; + lengthRule = rules["test-min-length"]; expect(getMinLength(lengthRule)).toBe(0); }); -test('enumRuleIsActive', () => { +test("enumRuleIsActive", () => { const rules: any = { - 'enum-string': [RuleConfigSeverity.Warning, 'always', ['1', '2', '3']], - 'type-enum': [RuleConfigSeverity.Error, 'always', ['build', 'chore', 'ci']], - 'scope-enum': [RuleConfigSeverity.Error, 'never', ['cli', 'core', 'lint']], - 'bar-enum': [RuleConfigSeverity.Disabled, 'always', ['foo', 'bar', 'baz']], + "enum-string": [RuleConfigSeverity.Warning, "always", ["1", "2", "3"]], + "type-enum": [RuleConfigSeverity.Error, "always", ["build", "chore", "ci"]], + "scope-enum": [RuleConfigSeverity.Error, "never", ["cli", "core", "lint"]], + "bar-enum": [RuleConfigSeverity.Disabled, "always", ["foo", "bar", "baz"]], }; - expect(enumRuleIsActive(rules['type-enum'])).toBe(true); - expect(enumRuleIsActive(rules['string-enum'])).toBe(false); - expect(enumRuleIsActive(rules['enum-string'])).toBe(true); - expect(enumRuleIsActive(rules['bar-enum'])).toBe(false); - expect(enumRuleIsActive(rules['scope-enum'])).toBe(false); + expect(enumRuleIsActive(rules["type-enum"])).toBe(true); + expect(enumRuleIsActive(rules["string-enum"])).toBe(false); + expect(enumRuleIsActive(rules["enum-string"])).toBe(true); + expect(enumRuleIsActive(rules["bar-enum"])).toBe(false); + expect(enumRuleIsActive(rules["scope-enum"])).toBe(false); }); -test('getEnumList', () => { +test("getEnumList", () => { const rules: any = { - 'type-enum': [RuleConfigSeverity.Error, 'always', ['build', 'chore', 'ci']], - 'scope-enum': [RuleConfigSeverity.Error, 'never', ''], - 'bar-enum': [RuleConfigSeverity.Disabled, 'always'], + "type-enum": [RuleConfigSeverity.Error, "always", ["build", "chore", "ci"]], + "scope-enum": [RuleConfigSeverity.Error, "never", ""], + "bar-enum": [RuleConfigSeverity.Disabled, "always"], }; - expect(getEnumList(rules['type-enum'])).toEqual(['build', 'chore', 'ci']); - expect(getEnumList(rules['scope-enum'])).toEqual([]); - expect(getEnumList(rules['bar-enum'])).toEqual([]); + expect(getEnumList(rules["type-enum"])).toEqual(["build", "chore", "ci"]); + expect(getEnumList(rules["scope-enum"])).toEqual([]); + expect(getEnumList(rules["bar-enum"])).toEqual([]); }); diff --git a/@commitlint/cz-commitlint/src/utils/rules.ts b/@commitlint/cz-commitlint/src/utils/rules.ts index 03557c4eef..d2570cd392 100644 --- a/@commitlint/cz-commitlint/src/utils/rules.ts +++ b/@commitlint/cz-commitlint/src/utils/rules.ts @@ -1,8 +1,8 @@ -import {RuleConfigSeverity} from '@commitlint/types'; -import type {Rule} from '../types.js'; +import { RuleConfigSeverity } from "@commitlint/types"; +import type { Rule } from "../types.js"; export function ruleIsDisabled( - rule: Rule + rule: Rule, ): rule is Readonly<[RuleConfigSeverity.Disabled]> { if (rule && Array.isArray(rule) && rule[0] === RuleConfigSeverity.Disabled) { return true; @@ -16,7 +16,7 @@ export function ruleIsDisabled( * @return if the rule definition is active */ export function ruleIsActive<T extends Rule>( - rule: T + rule: T, ): rule is Exclude<T, Readonly<[RuleConfigSeverity.Disabled]>> { if (rule && Array.isArray(rule)) { return rule[0] > RuleConfigSeverity.Disabled; @@ -30,12 +30,12 @@ export function ruleIsActive<T extends Rule>( * @return if the rule definition is applicable */ export function ruleIsApplicable( - rule: Rule + rule: Rule, ): rule is - | Readonly<[RuleConfigSeverity, 'always']> - | Readonly<[RuleConfigSeverity, 'always', unknown]> { + | Readonly<[RuleConfigSeverity, "always"]> + | Readonly<[RuleConfigSeverity, "always", unknown]> { if (rule && Array.isArray(rule)) { - return rule[1] === 'always'; + return rule[1] === "always"; } return false; } @@ -46,20 +46,20 @@ export function ruleIsApplicable( * @return if the rule definition is applicable */ export function ruleIsNotApplicable( - rule: Rule + rule: Rule, ): rule is - | Readonly<[RuleConfigSeverity, 'never']> - | Readonly<[RuleConfigSeverity, 'never', unknown]> { + | Readonly<[RuleConfigSeverity, "never"]> + | Readonly<[RuleConfigSeverity, "never", unknown]> { if (rule && Array.isArray(rule)) { - return rule[1] === 'never'; + return rule[1] === "never"; } return false; } export function enumRuleIsActive( - rule: Rule + rule: Rule, ): rule is Readonly< - [RuleConfigSeverity.Warning | RuleConfigSeverity.Error, 'always', string[]] + [RuleConfigSeverity.Warning | RuleConfigSeverity.Error, "always", string[]] > { return ( ruleIsActive(rule) && @@ -78,7 +78,7 @@ export function getMaxLength(rule?: Rule): number { rule && ruleIsActive(rule) && ruleIsApplicable(rule) && - typeof rule[2] === 'number' + typeof rule[2] === "number" ) { return rule[2]; } @@ -90,7 +90,7 @@ export function getMinLength(rule?: Rule): number { rule && ruleIsActive(rule) && ruleIsApplicable(rule) && - typeof rule[2] === 'number' + typeof rule[2] === "number" ) { return rule[2]; } diff --git a/@commitlint/cz-commitlint/tsconfig.json b/@commitlint/cz-commitlint/tsconfig.json index ff127af5ca..47e6ae4531 100644 --- a/@commitlint/cz-commitlint/tsconfig.json +++ b/@commitlint/cz-commitlint/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./src/**/*-test.ts", "./lib/**/*"], - "references": [{"path": "../cli"}] + "references": [{ "path": "../cli" }] } diff --git a/@commitlint/ensure/src/case.test.ts b/@commitlint/ensure/src/case.test.ts index 19957b0fb0..d812da8bf4 100644 --- a/@commitlint/ensure/src/case.test.ts +++ b/@commitlint/ensure/src/case.test.ts @@ -1,340 +1,340 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import ensure from './case.js'; +import ensure from "./case.js"; -test('true for no params', () => { +test("true for no params", () => { const actual = ensure(); expect(actual).toBe(true); }); -test('true for empty', () => { - const actual = ensure(''); +test("true for empty", () => { + const actual = ensure(""); expect(actual).toBe(true); }); -test('true for lowercase', () => { - const actual = ensure('a'); +test("true for lowercase", () => { + const actual = ensure("a"); expect(actual).toBe(true); }); -test('false for uppercase', () => { - const actual = ensure('A'); +test("false for uppercase", () => { + const actual = ensure("A"); expect(actual).toBe(false); }); -test('true for lowercase on lowercase', () => { - const actual = ensure('a', 'lowercase'); +test("true for lowercase on lowercase", () => { + const actual = ensure("a", "lowercase"); expect(actual).toBe(true); }); -test('false for uppercase on lowercase', () => { - const actual = ensure('A', 'lowercase'); +test("false for uppercase on lowercase", () => { + const actual = ensure("A", "lowercase"); expect(actual).toBe(false); }); -test('true for * on lowercase', () => { - const actual = ensure('*', 'lowercase'); +test("true for * on lowercase", () => { + const actual = ensure("*", "lowercase"); expect(actual).toBe(true); }); -test('true for uppercase on uppercase', () => { - const actual = ensure('A', 'uppercase'); +test("true for uppercase on uppercase", () => { + const actual = ensure("A", "uppercase"); expect(actual).toBe(true); }); -test('false for lowercase on uppercase', () => { - const actual = ensure('a', 'uppercase'); +test("false for lowercase on uppercase", () => { + const actual = ensure("a", "uppercase"); expect(actual).toBe(false); }); -test('true for * on uppercase', () => { - const actual = ensure('*', 'uppercase'); +test("true for * on uppercase", () => { + const actual = ensure("*", "uppercase"); expect(actual).toBe(true); }); -test('true for sentencecase on sentencecase', () => { - const actual = ensure('Sentence case', 'sentence-case'); +test("true for sentencecase on sentencecase", () => { + const actual = ensure("Sentence case", "sentence-case"); expect(actual).toBe(true); }); -test('false for lowercase on sentencecase', () => { - const actual = ensure('sentence case', 'sentence-case'); +test("false for lowercase on sentencecase", () => { + const actual = ensure("sentence case", "sentence-case"); expect(actual).toBe(false); }); -test('true for UPPERCASE on sentencecase', () => { - const actual = ensure('UPPERCASE', 'sentence-case'); +test("true for UPPERCASE on sentencecase", () => { + const actual = ensure("UPPERCASE", "sentence-case"); expect(actual).toBe(true); }); -test('true for Start Case on sentencecase', () => { - const actual = ensure('Start Case', 'sentence-case'); +test("true for Start Case on sentencecase", () => { + const actual = ensure("Start Case", "sentence-case"); expect(actual).toBe(true); }); -test('true for PascalCase on sentencecase', () => { - const actual = ensure('PascalCase', 'sentence-case'); +test("true for PascalCase on sentencecase", () => { + const actual = ensure("PascalCase", "sentence-case"); expect(actual).toBe(true); }); -test('false for kebab-case on sentencecase', () => { - const actual = ensure('kebab-case', 'sentence-case'); +test("false for kebab-case on sentencecase", () => { + const actual = ensure("kebab-case", "sentence-case"); expect(actual).toBe(false); }); -test('false for snake_case on sentencecase', () => { - const actual = ensure('snake_case', 'sentence-case'); +test("false for snake_case on sentencecase", () => { + const actual = ensure("snake_case", "sentence-case"); expect(actual).toBe(false); }); -test('false for camelCase on sentencecase', () => { - const actual = ensure('camelCase', 'sentence-case'); +test("false for camelCase on sentencecase", () => { + const actual = ensure("camelCase", "sentence-case"); expect(actual).toBe(false); }); -test('true for * on sentence-case', () => { - const actual = ensure('*', 'sentence-case'); +test("true for * on sentence-case", () => { + const actual = ensure("*", "sentence-case"); expect(actual).toBe(true); }); -test('true for * on camel-case', () => { - const actual = ensure('*', 'camel-case'); +test("true for * on camel-case", () => { + const actual = ensure("*", "camel-case"); expect(actual).toBe(true); }); -test('true for * on kebab-case', () => { - const actual = ensure('*', 'kebab-case'); +test("true for * on kebab-case", () => { + const actual = ensure("*", "kebab-case"); expect(actual).toBe(true); }); -test('true for * on snake-case', () => { - const actual = ensure('*', 'snake-case'); +test("true for * on snake-case", () => { + const actual = ensure("*", "snake-case"); expect(actual).toBe(true); }); -test('true for * on pascal-case', () => { - const actual = ensure('*', 'pascal-case'); +test("true for * on pascal-case", () => { + const actual = ensure("*", "pascal-case"); expect(actual).toBe(true); }); -test('true for * on start-case', () => { - const actual = ensure('*', 'start-case'); +test("true for * on start-case", () => { + const actual = ensure("*", "start-case"); expect(actual).toBe(true); }); -test('true for `Any_CASE_iN_back-quotes` on lowercase', () => { - const actual = ensure('`Any_CASE_iN_back-quotes`', 'lowercase'); +test("true for `Any_CASE_iN_back-quotes` on lowercase", () => { + const actual = ensure("`Any_CASE_iN_back-quotes`", "lowercase"); expect(actual).toBe(true); }); -test('true for `Any_CASE_iN_back-quotes` on uppercase', () => { - const actual = ensure('`Any_CASE_iN_back-quotes`', 'uppercase'); +test("true for `Any_CASE_iN_back-quotes` on uppercase", () => { + const actual = ensure("`Any_CASE_iN_back-quotes`", "uppercase"); expect(actual).toBe(true); }); -test('true for `Any_CASE_iN_back-quotes` on sentence-case', () => { - const actual = ensure('`Any_CASE_iN_back-quotes`', 'sentence-case'); +test("true for `Any_CASE_iN_back-quotes` on sentence-case", () => { + const actual = ensure("`Any_CASE_iN_back-quotes`", "sentence-case"); expect(actual).toBe(true); }); -test('true for `Any_CASE_iN_back-quotes` on camel-case', () => { - const actual = ensure('`Any_CASE_iN_back-quotes`', 'camel-case'); +test("true for `Any_CASE_iN_back-quotes` on camel-case", () => { + const actual = ensure("`Any_CASE_iN_back-quotes`", "camel-case"); expect(actual).toBe(true); }); -test('true for `Any_CASE_iN_back-quotes` on kebab-case', () => { - const actual = ensure('`Any_CASE_iN_back-quotes`', 'kebab-case'); +test("true for `Any_CASE_iN_back-quotes` on kebab-case", () => { + const actual = ensure("`Any_CASE_iN_back-quotes`", "kebab-case"); expect(actual).toBe(true); }); -test('true for `Any_CASE_iN_back-quotes` on snake-case', () => { - const actual = ensure('`Any_CASE_iN_back-quotes`', 'snake-case'); +test("true for `Any_CASE_iN_back-quotes` on snake-case", () => { + const actual = ensure("`Any_CASE_iN_back-quotes`", "snake-case"); expect(actual).toBe(true); }); -test('true for `Any_CASE_iN_back-quotes` on pascal-case', () => { - const actual = ensure('`Any_CASE_iN_back-quotes`', 'pascal-case'); +test("true for `Any_CASE_iN_back-quotes` on pascal-case", () => { + const actual = ensure("`Any_CASE_iN_back-quotes`", "pascal-case"); expect(actual).toBe(true); }); -test('true for `Any_CASE_iN_back-quotes` on start-case', () => { - const actual = ensure('`Any_CASE_iN_back-quotes`', 'start-case'); +test("true for `Any_CASE_iN_back-quotes` on start-case", () => { + const actual = ensure("`Any_CASE_iN_back-quotes`", "start-case"); expect(actual).toBe(true); }); -test('true for lowercase `Any_CASE_iN_back-quotes` lowercase on lowercase', () => { +test("true for lowercase `Any_CASE_iN_back-quotes` lowercase on lowercase", () => { const actual = ensure( - 'lowercase `Any_CASE_iN_back-quotes` lowercase', - 'lowercase' + "lowercase `Any_CASE_iN_back-quotes` lowercase", + "lowercase", ); expect(actual).toBe(true); }); -test('false for UPPERCASE `Any_CASE_iN_back-quotes` UPPERCASE on lowercase', () => { +test("false for UPPERCASE `Any_CASE_iN_back-quotes` UPPERCASE on lowercase", () => { const actual = ensure( - 'UPPERCASE `Any_CASE_iN_back-quotes` UPPERCASE', - 'lowercase' + "UPPERCASE `Any_CASE_iN_back-quotes` UPPERCASE", + "lowercase", ); expect(actual).toBe(false); }); -test('true for UPPERCASE `Any_CASE_iN_back-quotes` UPPERCASE on uppercase', () => { +test("true for UPPERCASE `Any_CASE_iN_back-quotes` UPPERCASE on uppercase", () => { const actual = ensure( - 'UPPERCASE `Any_CASE_iN_back-quotes` UPPERCASE', - 'uppercase' + "UPPERCASE `Any_CASE_iN_back-quotes` UPPERCASE", + "uppercase", ); expect(actual).toBe(true); }); -test('false for lowercase `Any_CASE_iN_back-quotes` lowercase on uppercase', () => { +test("false for lowercase `Any_CASE_iN_back-quotes` lowercase on uppercase", () => { const actual = ensure( - 'lowercase `Any_CASE_iN_back-quotes` lowercase', - 'uppercase' + "lowercase `Any_CASE_iN_back-quotes` lowercase", + "uppercase", ); expect(actual).toBe(false); }); -test('true for fooBar`Any_CASE_iN_back-quotes`fooBar on camel-case', () => { - const actual = ensure('fooBar`Any_CASE_iN_back-quotes`fooBar', 'camel-case'); +test("true for fooBar`Any_CASE_iN_back-quotes`fooBar on camel-case", () => { + const actual = ensure("fooBar`Any_CASE_iN_back-quotes`fooBar", "camel-case"); expect(actual).toBe(true); }); -test('false for Foo Bar`Any_CASE_iN_back-quotes` Foo Bar on camel-case', () => { +test("false for Foo Bar`Any_CASE_iN_back-quotes` Foo Bar on camel-case", () => { const actual = ensure( - 'Foo Bar`Any_CASE_iN_back-quotes` Foo Bar', - 'camel-case' + "Foo Bar`Any_CASE_iN_back-quotes` Foo Bar", + "camel-case", ); expect(actual).toBe(false); }); -test('true for foo-bar`Any_CASE_iN_back-quotes`foo-bar on kebab-case', () => { +test("true for foo-bar`Any_CASE_iN_back-quotes`foo-bar on kebab-case", () => { const actual = ensure( - 'foo-bar`Any_CASE_iN_back-quotes`foo-bar', - 'kebab-case' + "foo-bar`Any_CASE_iN_back-quotes`foo-bar", + "kebab-case", ); expect(actual).toBe(true); }); -test('false for Foo Bar `Any_CASE_iN_back-quotes` Foo Bar on kebab-case', () => { +test("false for Foo Bar `Any_CASE_iN_back-quotes` Foo Bar on kebab-case", () => { const actual = ensure( - 'Foo Bar `Any_CASE_iN_back-quotes` Foo Bar', - 'kebab-case' + "Foo Bar `Any_CASE_iN_back-quotes` Foo Bar", + "kebab-case", ); expect(actual).toBe(false); }); -test('true for foo_bar`Any_CASE_iN_back-quotes`foo_bar on snake-case', () => { +test("true for foo_bar`Any_CASE_iN_back-quotes`foo_bar on snake-case", () => { const actual = ensure( - 'foo_bar`Any_CASE_iN_back-quotes`foo_bar', - 'snake-case' + "foo_bar`Any_CASE_iN_back-quotes`foo_bar", + "snake-case", ); expect(actual).toBe(true); }); -test('false for Foo Bar `Any_CASE_iN_back-quotes` Foo Bar on snake-case', () => { +test("false for Foo Bar `Any_CASE_iN_back-quotes` Foo Bar on snake-case", () => { const actual = ensure( - 'Foo Bar `Any_CASE_iN_back-quotes` Foo Bar', - 'snake-case' + "Foo Bar `Any_CASE_iN_back-quotes` Foo Bar", + "snake-case", ); expect(actual).toBe(false); }); -test('true for PascalCase`Any_CASE_iN_back-quotes`PascalCase on pascal-case', () => { +test("true for PascalCase`Any_CASE_iN_back-quotes`PascalCase on pascal-case", () => { const actual = ensure( - 'PascalCase`Any_CASE_iN_back-quotes`PascalCase', - 'pascal-case' + "PascalCase`Any_CASE_iN_back-quotes`PascalCase", + "pascal-case", ); expect(actual).toBe(true); }); -test('false for Foo Bar `Any_CASE_iN_back-quotes` Foo Bar on pascal-case', () => { +test("false for Foo Bar `Any_CASE_iN_back-quotes` Foo Bar on pascal-case", () => { const actual = ensure( - 'Foo Bar `Any_CASE_iN_back-quotes` Foo Bar', - 'pascal-case' + "Foo Bar `Any_CASE_iN_back-quotes` Foo Bar", + "pascal-case", ); expect(actual).toBe(false); }); -test('true for Foo Bar`Any_CASE_iN_back-quotes` Foo Bar on start-case', () => { +test("true for Foo Bar`Any_CASE_iN_back-quotes` Foo Bar on start-case", () => { const actual = ensure( - 'Foo Bar `Any_CASE_iN_back-quotes`Foo Bar', - 'start-case' + "Foo Bar `Any_CASE_iN_back-quotes`Foo Bar", + "start-case", ); expect(actual).toBe(true); }); -test('false for foo_bar`Any_CASE_iN_back-quotes`foo_bar on start-case', () => { +test("false for foo_bar`Any_CASE_iN_back-quotes`foo_bar on start-case", () => { const actual = ensure( - 'foo_bar`Any_CASE_iN_back-quotes`foo_bar', - 'start-case' + "foo_bar`Any_CASE_iN_back-quotes`foo_bar", + "start-case", ); expect(actual).toBe(false); }); -test('true for lowercase `Any_CASE_iN_back-quotes` `Any_CASE_iN_back-quotes` lowercase on lowercase', () => { +test("true for lowercase `Any_CASE_iN_back-quotes` `Any_CASE_iN_back-quotes` lowercase on lowercase", () => { const actual = ensure( - 'lowercase `Any_CASE_iN_back-quotes` `Any_CASE_iN_back-quotes` lowercase', - 'lowercase' + "lowercase `Any_CASE_iN_back-quotes` `Any_CASE_iN_back-quotes` lowercase", + "lowercase", ); expect(actual).toBe(true); }); test("true for 'Any_CASE_iN_single-quotes' on lowercase", () => { - const actual = ensure("'Any_CASE_iN_single-quotes'", 'lowercase'); + const actual = ensure("'Any_CASE_iN_single-quotes'", "lowercase"); expect(actual).toBe(true); }); test('true for "Any_CASE_iN_double-quotes" on lowercase', () => { - const actual = ensure('"Any_CASE_iN_double-quotes"', 'lowercase'); + const actual = ensure('"Any_CASE_iN_double-quotes"', "lowercase"); expect(actual).toBe(true); }); -test('true for `lowercasel"\'` on lowercase', () => { - const actual = ensure('`lowercasel"\'`', 'lowercase'); +test("true for `lowercasel\"'` on lowercase", () => { + const actual = ensure("`lowercasel\"'`", "lowercase"); expect(actual).toBe(true); }); -test('false for `LOWERCASE on lowercase', () => { - const actual = ensure('`LOWERCASE', 'lowercase'); +test("false for `LOWERCASE on lowercase", () => { + const actual = ensure("`LOWERCASE", "lowercase"); expect(actual).toBe(false); }); -test('true for numeric on camel-case', () => { - const actual = ensure('1.0.0', 'camel-case'); +test("true for numeric on camel-case", () => { + const actual = ensure("1.0.0", "camel-case"); expect(actual).toBe(true); }); -test('true for numeric on kebab-case', () => { - const actual = ensure('1.0.0', 'kebab-case'); +test("true for numeric on kebab-case", () => { + const actual = ensure("1.0.0", "kebab-case"); expect(actual).toBe(true); }); -test('true for numeric on snake-case', () => { - const actual = ensure('1.0.0', 'snake-case'); +test("true for numeric on snake-case", () => { + const actual = ensure("1.0.0", "snake-case"); expect(actual).toBe(true); }); -test('true for numeric on pascal-case', () => { - const actual = ensure('1.0.0', 'pascal-case'); +test("true for numeric on pascal-case", () => { + const actual = ensure("1.0.0", "pascal-case"); expect(actual).toBe(true); }); -test('true for numeric on uppercase', () => { - const actual = ensure('1.0.0', 'uppercase'); +test("true for numeric on uppercase", () => { + const actual = ensure("1.0.0", "uppercase"); expect(actual).toBe(true); }); -test('true for numeric on sentencecase', () => { - const actual = ensure('1.0.0', 'sentencecase'); +test("true for numeric on sentencecase", () => { + const actual = ensure("1.0.0", "sentencecase"); expect(actual).toBe(true); }); -test('true for numeric on lowercase', () => { - const actual = ensure('1.0.0', 'lowercase'); +test("true for numeric on lowercase", () => { + const actual = ensure("1.0.0", "lowercase"); expect(actual).toBe(true); }); -test('throw TypeError for invalid case name', () => { - const actualFn = () => ensure('anything', 'someweirdcase' as any); +test("throw TypeError for invalid case name", () => { + const actualFn = () => ensure("anything", "someweirdcase" as any); expect(actualFn).toThrow(TypeError); }); diff --git a/@commitlint/ensure/src/case.ts b/@commitlint/ensure/src/case.ts index bae88a0bff..710f7e79b8 100644 --- a/@commitlint/ensure/src/case.ts +++ b/@commitlint/ensure/src/case.ts @@ -1,22 +1,22 @@ -import type {TargetCaseType} from '@commitlint/types'; +import type { TargetCaseType } from "@commitlint/types"; -import toCase from './to-case.js'; +import toCase from "./to-case.js"; export default ensureCase; function ensureCase( - raw: string = '', - target: TargetCaseType = 'lowercase' + raw: string = "", + target: TargetCaseType = "lowercase", ): boolean { // We delete any content together with quotes because he can contains proper names (example `refactor: `Eslint` configuration`). // We need trim string because content with quotes can be at the beginning or end of a line const input = String(raw) - .replace(/`.*?`|".*?"|'.*?'/g, '') + .replace(/`.*?`|".*?"|'.*?'/g, "") .trim(); const transformed = toCase(input, target); - if (transformed === '' || transformed.match(/^\d/)) { + if (transformed === "" || transformed.match(/^\d/)) { return true; } diff --git a/@commitlint/ensure/src/enum.test.ts b/@commitlint/ensure/src/enum.test.ts index a09b70bec2..817f2ce072 100644 --- a/@commitlint/ensure/src/enum.test.ts +++ b/@commitlint/ensure/src/enum.test.ts @@ -1,48 +1,48 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import ensure from './enum.js'; +import ensure from "./enum.js"; -test('false for no params', () => { +test("false for no params", () => { const actual = (ensure as () => boolean)(); expect(actual).toBe(false); }); -test('false for not array enums', () => { - const actual = ensure('a', 'a' as any); +test("false for not array enums", () => { + const actual = ensure("a", "a" as any); expect(actual).toBe(false); }); -test('true for a against a', () => { - const actual = ensure('a', ['a']); +test("true for a against a", () => { + const actual = ensure("a", ["a"]); expect(actual).toBe(true); }); -test('false for a against b', () => { - const actual = ensure('a', ['b']); +test("false for a against b", () => { + const actual = ensure("a", ["b"]); expect(actual).toBe(false); }); -test('true for a against a, b', () => { - const actual = ensure('a', ['a', 'b']); +test("true for a against a, b", () => { + const actual = ensure("a", ["a", "b"]); expect(actual).toBe(true); }); -test('false for b against a', () => { - const actual = ensure('b', ['a']); +test("false for b against a", () => { + const actual = ensure("b", ["a"]); expect(actual).toBe(false); }); -test('true for b against b', () => { - const actual = ensure('b', ['b']); +test("true for b against b", () => { + const actual = ensure("b", ["b"]); expect(actual).toBe(true); }); -test('true for b against a, b', () => { - const actual = ensure('b', ['a', 'b']); +test("true for b against a, b", () => { + const actual = ensure("b", ["a", "b"]); expect(actual).toBe(true); }); -test('false for c against a, b', () => { - const actual = ensure('c', ['a', 'b']); +test("false for c against a, b", () => { + const actual = ensure("c", ["a", "b"]); expect(actual).toBe(false); }); diff --git a/@commitlint/ensure/src/index.test.ts b/@commitlint/ensure/src/index.test.ts index 4267fd7a6e..b58bb64adc 100644 --- a/@commitlint/ensure/src/index.test.ts +++ b/@commitlint/ensure/src/index.test.ts @@ -1,17 +1,17 @@ -import {test, expect} from 'vitest'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { test, expect } from "vitest"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {globSync} from 'glob'; -import camelCase from 'lodash.camelcase'; +import { globSync } from "glob"; +import camelCase from "lodash.camelcase"; -import * as ensure from './index.js'; +import * as ensure from "./index.js"; -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -test('exports all checkers', async () => { - const ignore = ['types']; - const expected = _glob('*.ts') +test("exports all checkers", async () => { + const ignore = ["types"]; + const expected = _glob("*.ts") .map((f) => camelCase(f)) .sort() .filter((item) => !ignore.includes(item)); @@ -19,14 +19,14 @@ test('exports all checkers', async () => { expect(actual).toEqual(expected); }); -test('rules export functions', () => { +test("rules export functions", () => { const actual = Object.values(ensure); - expect(actual.every((rule) => typeof rule === 'function')).toBe(true); + expect(actual.every((rule) => typeof rule === "function")).toBe(true); }); function _glob(pattern: string): string[] { const files = globSync(pattern, { - ignore: ['**/index.ts', '**/*.test.ts'], + ignore: ["**/index.ts", "**/*.test.ts"], cwd: __dirname, }); return files.map(relative).map(toExport); diff --git a/@commitlint/ensure/src/index.ts b/@commitlint/ensure/src/index.ts index 496832bf57..0590b145a3 100644 --- a/@commitlint/ensure/src/index.ts +++ b/@commitlint/ensure/src/index.ts @@ -1,11 +1,11 @@ -import ensureCase from './case.js'; -import ensureEnum from './enum.js'; -import maxLength from './max-length.js'; -import maxLineLength from './max-line-length.js'; -import minLength from './min-length.js'; -import notEmpty from './not-empty.js'; -import toCase from './to-case.js'; +import ensureCase from "./case.js"; +import ensureEnum from "./enum.js"; +import maxLength from "./max-length.js"; +import maxLineLength from "./max-line-length.js"; +import minLength from "./min-length.js"; +import notEmpty from "./not-empty.js"; +import toCase from "./to-case.js"; -export {ensureCase as case}; -export {ensureEnum as enum}; -export {maxLength, maxLineLength, minLength, notEmpty, toCase}; +export { ensureCase as case }; +export { ensureEnum as enum }; +export { maxLength, maxLineLength, minLength, notEmpty, toCase }; diff --git a/@commitlint/ensure/src/max-length.test.ts b/@commitlint/ensure/src/max-length.test.ts index 99c3813281..c18af918e8 100644 --- a/@commitlint/ensure/src/max-length.test.ts +++ b/@commitlint/ensure/src/max-length.test.ts @@ -1,28 +1,28 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import ensure from './max-length.js'; +import ensure from "./max-length.js"; -test('false for no params', () => { +test("false for no params", () => { const actual = (ensure as () => boolean)(); expect(actual).toBe(false); }); -test('true for a against 1', () => { - const actual = ensure('a', 1); +test("true for a against 1", () => { + const actual = ensure("a", 1); expect(actual).toBe(true); }); -test('false for ab against 0', () => { - const actual = ensure('a', 0); +test("false for ab against 0", () => { + const actual = ensure("a", 0); expect(actual).toBe(false); }); -test('true for a against 2', () => { - const actual = ensure('a', 2); +test("true for a against 2", () => { + const actual = ensure("a", 2); expect(actual).toBe(true); }); -test('true for ab against 2', () => { - const actual = ensure('ab', 2); +test("true for ab against 2", () => { + const actual = ensure("ab", 2); expect(actual).toBe(true); }); diff --git a/@commitlint/ensure/src/max-length.ts b/@commitlint/ensure/src/max-length.ts index 009ee0fa2e..2c78246b8a 100644 --- a/@commitlint/ensure/src/max-length.ts +++ b/@commitlint/ensure/src/max-length.ts @@ -1,2 +1,2 @@ export default (value: string | null, max: number): boolean => - typeof value === 'string' && value.length <= max; + typeof value === "string" && value.length <= max; diff --git a/@commitlint/ensure/src/max-line-length.test.ts b/@commitlint/ensure/src/max-line-length.test.ts index a51069a29a..8755824abd 100644 --- a/@commitlint/ensure/src/max-line-length.test.ts +++ b/@commitlint/ensure/src/max-line-length.test.ts @@ -1,49 +1,49 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import ensure from './max-line-length.js'; +import ensure from "./max-line-length.js"; -test('false for no params', () => { +test("false for no params", () => { const actual = (ensure as () => boolean)(); expect(actual).toBe(false); }); -test('true for a against 1', () => { - const actual = ensure('a', 1); +test("true for a against 1", () => { + const actual = ensure("a", 1); expect(actual).toBe(true); }); -test('false for ab against 0', () => { - const actual = ensure('a', 0); +test("false for ab against 0", () => { + const actual = ensure("a", 0); expect(actual).toBe(false); }); -test('true for a against 2', () => { - const actual = ensure('a', 2); +test("true for a against 2", () => { + const actual = ensure("a", 2); expect(actual).toBe(true); }); -test('true for ab against 2', () => { - const actual = ensure('ab', 2); +test("true for ab against 2", () => { + const actual = ensure("ab", 2); expect(actual).toBe(true); }); -test('false for ab/\nab/\nab 1', () => { +test("false for ab/\nab/\nab 1", () => { const actual = ensure( `ab ab ab`, - 2 + 2, ); expect(actual).toBe(true); }); -test('true for ab/\nab/\nab 2', () => { +test("true for ab/\nab/\nab 2", () => { const actual = ensure( `ab ab ab`, - 2 + 2, ); expect(actual).toBe(true); diff --git a/@commitlint/ensure/src/max-line-length.ts b/@commitlint/ensure/src/max-line-length.ts index 51f0bfaa4b..02f908c374 100644 --- a/@commitlint/ensure/src/max-line-length.ts +++ b/@commitlint/ensure/src/max-line-length.ts @@ -1,5 +1,5 @@ -import ensure from './max-length.js'; +import ensure from "./max-length.js"; export default (value: string, max: number): boolean => - typeof value === 'string' && + typeof value === "string" && value.split(/\r?\n/).every((line) => ensure(line, max)); diff --git a/@commitlint/ensure/src/min-length.test.ts b/@commitlint/ensure/src/min-length.test.ts index 8530b80811..a62395e3d1 100644 --- a/@commitlint/ensure/src/min-length.test.ts +++ b/@commitlint/ensure/src/min-length.test.ts @@ -1,28 +1,28 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import ensure from './min-length.js'; +import ensure from "./min-length.js"; -test('false for no params', () => { +test("false for no params", () => { const actual = (ensure as () => boolean)(); expect(actual).toBe(false); }); -test('true for a against 1', () => { - const actual = ensure('a', 1); +test("true for a against 1", () => { + const actual = ensure("a", 1); expect(actual).toBe(true); }); -test('false for ab against 0', () => { - const actual = ensure('a', 0); +test("false for ab against 0", () => { + const actual = ensure("a", 0); expect(actual).toBe(true); }); -test('true for a against 2', () => { - const actual = ensure('a', 2); +test("true for a against 2", () => { + const actual = ensure("a", 2); expect(actual).toBe(false); }); -test('true for ab against 2', () => { - const actual = ensure('ab', 2); +test("true for ab against 2", () => { + const actual = ensure("ab", 2); expect(actual).toBe(true); }); diff --git a/@commitlint/ensure/src/min-length.ts b/@commitlint/ensure/src/min-length.ts index 97ad15993e..e7a8186bbb 100644 --- a/@commitlint/ensure/src/min-length.ts +++ b/@commitlint/ensure/src/min-length.ts @@ -1,2 +1,2 @@ export default (value: string | null, min: number): boolean => - typeof value === 'string' && value.length >= min; + typeof value === "string" && value.length >= min; diff --git a/@commitlint/ensure/src/not-empty.test.ts b/@commitlint/ensure/src/not-empty.test.ts index 172a523caa..a0fa271b3d 100644 --- a/@commitlint/ensure/src/not-empty.test.ts +++ b/@commitlint/ensure/src/not-empty.test.ts @@ -1,18 +1,18 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import ensure from './not-empty.js'; +import ensure from "./not-empty.js"; -test('false for no params', () => { +test("false for no params", () => { const actual = (ensure as () => boolean)(); expect(actual).toBe(false); }); test('false for ""', () => { - const actual = ensure(''); + const actual = ensure(""); expect(actual).toBe(false); }); -test('true for a', () => { - const actual = ensure('a'); +test("true for a", () => { + const actual = ensure("a"); expect(actual).toBe(true); }); diff --git a/@commitlint/ensure/src/not-empty.ts b/@commitlint/ensure/src/not-empty.ts index 540cf99a3f..008380de35 100644 --- a/@commitlint/ensure/src/not-empty.ts +++ b/@commitlint/ensure/src/not-empty.ts @@ -1,2 +1,2 @@ export default (value: string): boolean => - typeof value === 'string' && value.length > 0; + typeof value === "string" && value.length > 0; diff --git a/@commitlint/ensure/src/to-case.ts b/@commitlint/ensure/src/to-case.ts index e3490faf17..df41e0033e 100644 --- a/@commitlint/ensure/src/to-case.ts +++ b/@commitlint/ensure/src/to-case.ts @@ -1,31 +1,31 @@ -import {TargetCaseType} from '@commitlint/types'; -import camelCase from 'lodash.camelcase'; -import kebabCase from 'lodash.kebabcase'; -import snakeCase from 'lodash.snakecase'; -import upperFirst from 'lodash.upperfirst'; -import startCase from 'lodash.startcase'; +import { TargetCaseType } from "@commitlint/types"; +import camelCase from "lodash.camelcase"; +import kebabCase from "lodash.kebabcase"; +import snakeCase from "lodash.snakecase"; +import upperFirst from "lodash.upperfirst"; +import startCase from "lodash.startcase"; export default function toCase(input: string, target: TargetCaseType): string { switch (target) { - case 'camel-case': + case "camel-case": return camelCase(input); - case 'kebab-case': + case "kebab-case": return kebabCase(input); - case 'snake-case': + case "snake-case": return snakeCase(input); - case 'pascal-case': + case "pascal-case": return upperFirst(camelCase(input)); - case 'start-case': + case "start-case": return startCase(input); - case 'upper-case': - case 'uppercase': + case "upper-case": + case "uppercase": return input.toUpperCase(); - case 'sentence-case': - case 'sentencecase': + case "sentence-case": + case "sentencecase": return upperFirst(input); - case 'lower-case': - case 'lowercase': - case 'lowerCase': // Backwards compat config-angular v4 + case "lower-case": + case "lowercase": + case "lowerCase": // Backwards compat config-angular v4 return input.toLowerCase(); default: throw new TypeError(`to-case: Unknown target case "${target}"`); diff --git a/@commitlint/ensure/tsconfig.json b/@commitlint/ensure/tsconfig.json index f3092129e3..0cc393e13d 100644 --- a/@commitlint/ensure/tsconfig.json +++ b/@commitlint/ensure/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src/**/*.ts"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../types"}] + "references": [{ "path": "../types" }] } diff --git a/@commitlint/execute-rule/src/index.test.ts b/@commitlint/execute-rule/src/index.test.ts index f3dfb34869..23a3259707 100644 --- a/@commitlint/execute-rule/src/index.test.ts +++ b/@commitlint/execute-rule/src/index.test.ts @@ -1,28 +1,28 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import execute from './index.js'; +import execute from "./index.js"; -test('does nothing without params', async () => { +test("does nothing without params", async () => { const exec = execute as any; expect(await exec()).toBeNull(); }); -test('returns plain config', async () => { - const actual = await execute(['name', 'config']); - expect(actual).toEqual(['name', 'config']); +test("returns plain config", async () => { + const actual = await execute(["name", "config"]); + expect(actual).toEqual(["name", "config"]); }); -test('unwraps promised config', async () => { - const actual = await execute(['name', Promise.resolve('config')]); - expect(actual).toEqual(['name', 'config']); +test("unwraps promised config", async () => { + const actual = await execute(["name", Promise.resolve("config")]); + expect(actual).toEqual(["name", "config"]); }); -test('executes config functions', async () => { - const actual = await execute(['name', () => 'config']); - expect(actual).toEqual(['name', 'config']); +test("executes config functions", async () => { + const actual = await execute(["name", () => "config"]); + expect(actual).toEqual(["name", "config"]); }); -test('executes async config functions', async () => { - const actual = await execute(['name', async () => 'config']); - expect(actual).toEqual(['name', 'config']); +test("executes async config functions", async () => { + const actual = await execute(["name", async () => "config"]); + expect(actual).toEqual(["name", "config"]); }); diff --git a/@commitlint/execute-rule/src/index.ts b/@commitlint/execute-rule/src/index.ts index 47029f4b89..4ef89f9275 100644 --- a/@commitlint/execute-rule/src/index.ts +++ b/@commitlint/execute-rule/src/index.ts @@ -7,7 +7,7 @@ type ExecutedRule<T> = readonly [string, T]; export default execute; export async function execute<T = unknown>( - rule?: Rule<T> + rule?: Rule<T>, ): Promise<ExecutedRule<T> | null> { if (!Array.isArray(rule)) { return null; @@ -21,5 +21,5 @@ export async function execute<T = unknown>( } function executable<T>(config: Config<T>): config is ExectableConfig<T> { - return typeof config === 'function'; + return typeof config === "function"; } diff --git a/@commitlint/format/src/format.test.ts b/@commitlint/format/src/format.test.ts index 10b70e76aa..3388e96afb 100644 --- a/@commitlint/format/src/format.test.ts +++ b/@commitlint/format/src/format.test.ts @@ -1,23 +1,23 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import {format, formatResult} from './index.js'; +import { format, formatResult } from "./index.js"; -test('does nothing without arguments', () => { +test("does nothing without arguments", () => { const actual = format(); - expect(actual).toEqual(''); + expect(actual).toEqual(""); }); -test('does nothing without report results', () => { - const actual = format({results: []}); - expect(actual).toEqual(''); +test("does nothing without report results", () => { + const actual = format({ results: [] }); + expect(actual).toEqual(""); }); -test('does nothing without .errors and .warnings', () => { - const actual = format({results: [{}]}); - expect(actual).toEqual(''); +test("does nothing without .errors and .warnings", () => { + const actual = format({ results: [{}] }); + expect(actual).toEqual(""); }); -test('returns empty summary if verbose', () => { +test("returns empty summary if verbose", () => { const actual = format( { results: [ @@ -29,13 +29,13 @@ test('returns empty summary if verbose', () => { }, { verbose: true, - } + }, ); - expect(actual).toContain('0 problems, 0 warnings'); + expect(actual).toContain("0 problems, 0 warnings"); }); -test('returns empty summary with full commit message if verbose', () => { +test("returns empty summary with full commit message if verbose", () => { const actual = format( { results: [ @@ -43,30 +43,30 @@ test('returns empty summary with full commit message if verbose', () => { errors: [], warnings: [], input: - 'feat(cli): this is a valid header\n\nThis is a valid body\n\nSigned-off-by: tester', + "feat(cli): this is a valid header\n\nThis is a valid body\n\nSigned-off-by: tester", }, ], }, { verbose: true, color: false, - } + }, ); expect(actual).toStrictEqual( - '⧗ input: feat(cli): this is a valid header\n\nThis is a valid body\n\nSigned-off-by: tester\n✔ found 0 problems, 0 warnings' + "⧗ input: feat(cli): this is a valid header\n\nThis is a valid body\n\nSigned-off-by: tester\n✔ found 0 problems, 0 warnings", ); }); -test('returns a correct summary of empty .errors and .warnings', () => { +test("returns a correct summary of empty .errors and .warnings", () => { const actualError = format({ results: [ { errors: [ { level: 2, - name: 'error-name', - message: 'There was an error', + name: "error-name", + message: "There was an error", }, ], }, @@ -79,29 +79,29 @@ test('returns a correct summary of empty .errors and .warnings', () => { warnings: [ { level: 1, - name: 'warning-name', - message: 'There was a problem', + name: "warning-name", + message: "There was a problem", }, ], }, ], }); - expect(actualError).toContain('There was an error'); - expect(actualError).toContain('1 problems, 0 warnings'); - expect(actualWarning).toContain('There was a problem'); - expect(actualWarning).toContain('0 problems, 1 warnings'); + expect(actualError).toContain("There was an error"); + expect(actualError).toContain("1 problems, 0 warnings"); + expect(actualWarning).toContain("There was a problem"); + expect(actualWarning).toContain("0 problems, 1 warnings"); }); -test('uses appropriate signs by default', () => { +test("uses appropriate signs by default", () => { const actualError = format({ results: [ { errors: [ { level: 2, - name: 'error-name', - message: 'There was an error', + name: "error-name", + message: "There was an error", }, ], }, @@ -114,20 +114,20 @@ test('uses appropriate signs by default', () => { warnings: [ { level: 1, - name: 'warning-name', - message: 'There was a problem', + name: "warning-name", + message: "There was a problem", }, ], }, ], }); - expect(actualError).toContain('✖'); - expect(actualWarning).toContain('⚠'); + expect(actualError).toContain("✖"); + expect(actualWarning).toContain("⚠"); }); -test('uses signs as configured', () => { - const options = {signs: ['HNT', 'WRN', 'ERR'] as [string, string, string]}; +test("uses signs as configured", () => { + const options = { signs: ["HNT", "WRN", "ERR"] as [string, string, string] }; const actualError = format( { results: [ @@ -135,14 +135,14 @@ test('uses signs as configured', () => { errors: [ { level: 2, - name: 'error-name', - message: 'There was an error', + name: "error-name", + message: "There was an error", }, ], }, ], }, - options + options, ); const actualWarning = format( @@ -152,154 +152,154 @@ test('uses signs as configured', () => { warnings: [ { level: 1, - name: 'warning-name', - message: 'There was a problem', + name: "warning-name", + message: "There was a problem", }, ], }, ], }, - options + options, ); - expect(actualError).toContain('ERR'); - expect(actualWarning).toContain('WRN'); + expect(actualError).toContain("ERR"); + expect(actualWarning).toContain("WRN"); }); -test('format result is empty without arguments', () => { +test("format result is empty without arguments", () => { const actual = formatResult(); - const actualText = actual.join('\n'); - expect(actualText).toBe(''); + const actualText = actual.join("\n"); + expect(actualText).toBe(""); }); -test('format result transforms error to text', () => { +test("format result transforms error to text", () => { const actual = formatResult({ errors: [ { level: 2, - name: 'error-name', - message: 'There was an error', + name: "error-name", + message: "There was an error", }, ], }); - const actualText = actual.join('\n'); + const actualText = actual.join("\n"); - expect(actualText).toContain('error-name'); - expect(actualText).toContain('There was an error'); - expect(actualText).toContain('1 problems, 0 warnings'); + expect(actualText).toContain("error-name"); + expect(actualText).toContain("There was an error"); + expect(actualText).toContain("1 problems, 0 warnings"); }); -test('format result transforms warning to text', () => { +test("format result transforms warning to text", () => { const actual = formatResult({ warnings: [ { level: 1, - name: 'warning-name', - message: 'There was a warning', + name: "warning-name", + message: "There was a warning", }, ], }); - const actualText = actual.join('\n'); + const actualText = actual.join("\n"); - expect(actualText).toContain('warning-name'); - expect(actualText).toContain('There was a warning'); - expect(actualText).toContain('0 problems, 1 warnings'); + expect(actualText).toContain("warning-name"); + expect(actualText).toContain("There was a warning"); + expect(actualText).toContain("0 problems, 1 warnings"); }); -test('format result prints help for errors', () => { +test("format result prints help for errors", () => { const actual = formatResult( { errors: [ { level: 2, - name: 'error-name', - message: 'There was an error', + name: "error-name", + message: "There was an error", }, ], }, { - helpUrl: 'https://example.com', - } + helpUrl: "https://example.com", + }, ); expect(actual).toEqual( - expect.arrayContaining([expect.stringContaining('Get help:')]) + expect.arrayContaining([expect.stringContaining("Get help:")]), ); }); -test('format result prints help for warnings', () => { +test("format result prints help for warnings", () => { const actual = formatResult( { warnings: [ { level: 2, - name: 'warning-name', - message: 'There was a warning', + name: "warning-name", + message: "There was a warning", }, ], }, { - helpUrl: 'https://example.com', - } + helpUrl: "https://example.com", + }, ); expect(actual).toEqual( - expect.arrayContaining([expect.stringContaining('Get help:')]) + expect.arrayContaining([expect.stringContaining("Get help:")]), ); }); -test('format result help cotains options.helpUrl', () => { - const helpUrl = 'https://example.com'; +test("format result help cotains options.helpUrl", () => { + const helpUrl = "https://example.com"; const actual = formatResult( { warnings: [ { level: 2, - name: 'warning-name', - message: 'There was a warning', + name: "warning-name", + message: "There was a warning", }, ], }, { helpUrl, - } + }, ); expect(actual).toEqual( - expect.arrayContaining([expect.stringContaining(helpUrl)]) + expect.arrayContaining([expect.stringContaining(helpUrl)]), ); }); -test('format result omits help for empty problems', () => { +test("format result omits help for empty problems", () => { const actual = formatResult({ warnings: [], }); expect(actual).not.toEqual( - expect.arrayContaining([expect.stringContaining('Get help:')]) + expect.arrayContaining([expect.stringContaining("Get help:")]), ); }); -test('format result should not contain `Get help` prefix if helpUrl is not provided', () => { +test("format result should not contain `Get help` prefix if helpUrl is not provided", () => { const actual = formatResult( { warnings: [ { level: 2, - name: 'warning-name', - message: 'There was a warning', + name: "warning-name", + message: "There was a warning", }, ], }, { - helpUrl: '', - } + helpUrl: "", + }, ); expect(actual).not.toEqual( - expect.arrayContaining([expect.stringContaining('Get help:')]) + expect.arrayContaining([expect.stringContaining("Get help:")]), ); }); diff --git a/@commitlint/format/src/format.ts b/@commitlint/format/src/format.ts index 13baf4bf5e..8c43f74c64 100644 --- a/@commitlint/format/src/format.ts +++ b/@commitlint/format/src/format.ts @@ -1,20 +1,20 @@ -import chalk from 'chalk'; +import chalk from "chalk"; import { ChalkColor, FormattableReport, FormatOptions, FormattableResult, WithInput, -} from '@commitlint/types'; +} from "@commitlint/types"; -const DEFAULT_SIGNS = [' ', '⚠', '✖'] as const; -const DEFAULT_COLORS = ['white', 'yellow', 'red'] as const; +const DEFAULT_SIGNS = [" ", "⚠", "✖"] as const; +const DEFAULT_COLORS = ["white", "yellow", "red"] as const; export function format( report: FormattableReport = {}, - options: FormatOptions = {} + options: FormatOptions = {}, ): string { - const {results = []} = report; + const { results = [] } = report; const fi = (result: FormattableResult & WithInput) => formatInput(result, options); const fr = (result: FormattableResult) => formatResult(result, options); @@ -24,23 +24,23 @@ export function format( .map((result) => [...fi(result), ...fr(result)]) .reduce( (acc, item) => (Array.isArray(item) ? [...acc, ...item] : [...acc, item]), - [] + [], ) - .join('\n'); + .join("\n"); } function formatInput( result: FormattableResult & WithInput, - options: FormatOptions = {} + options: FormatOptions = {}, ): string[] { - const {color: enabled = true} = options; - const {errors = [], warnings = [], input = ''} = result; + const { color: enabled = true } = options; + const { errors = [], warnings = [], input = "" } = result; if (!input) { - return ['']; + return [""]; } - const sign = '⧗'; + const sign = "⧗"; const decoration = enabled ? chalk.gray(sign) : sign; const decoratedInput = enabled ? chalk.bold(input) : input; @@ -53,18 +53,18 @@ function formatInput( export function formatResult( result: FormattableResult = {}, - options: FormatOptions = {} + options: FormatOptions = {}, ): string[] { const { signs = DEFAULT_SIGNS, colors = DEFAULT_COLORS, color: enabled = true, } = options; - const {errors = [], warnings = []} = result; + const { errors = [], warnings = [] } = result; const problems = [...errors, ...warnings].map((problem) => { - const sign = signs[problem.level] || ''; - const color: ChalkColor = colors[problem.level] || ('white' as const); + const sign = signs[problem.level] || ""; + const color: ChalkColor = colors[problem.level] || ("white" as const); const decoration = enabled ? chalk[color](sign) : sign; const name = enabled ? chalk.grey(`[${problem.name}]`) @@ -86,7 +86,7 @@ export function formatResult( : undefined; const fmtSummary = - enabled && typeof summary === 'string' ? chalk.bold(summary) : summary; + enabled && typeof summary === "string" ? chalk.bold(summary) : summary; const help = hasProblems && options.helpUrl @@ -95,25 +95,25 @@ export function formatResult( return [ ...problems, - hasProblems ? '' : undefined, + hasProblems ? "" : undefined, fmtSummary, help, - hasProblems ? '' : undefined, - ].filter((line): line is string => typeof line === 'string'); + hasProblems ? "" : undefined, + ].filter((line): line is string => typeof line === "string"); } export default format; function selectSign(result: FormattableResult): string { if ((result.errors || []).length > 0) { - return '✖'; + return "✖"; } - return (result.warnings || []).length ? '⚠' : '✔'; + return (result.warnings || []).length ? "⚠" : "✔"; } function selectColor(result: FormattableResult): ChalkColor { if ((result.errors || []).length > 0) { - return 'red'; + return "red"; } - return (result.warnings || []).length ? 'yellow' : 'green'; + return (result.warnings || []).length ? "yellow" : "green"; } diff --git a/@commitlint/format/src/index.ts b/@commitlint/format/src/index.ts index 9ec36ba06a..6f7327f1bb 100644 --- a/@commitlint/format/src/index.ts +++ b/@commitlint/format/src/index.ts @@ -1,2 +1,2 @@ -export {default} from './format.js'; -export * from './format.js'; +export { default } from "./format.js"; +export * from "./format.js"; diff --git a/@commitlint/format/tsconfig.json b/@commitlint/format/tsconfig.json index 119e645565..d691164788 100644 --- a/@commitlint/format/tsconfig.json +++ b/@commitlint/format/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../types"}] + "references": [{ "path": "../types" }] } diff --git a/@commitlint/is-ignored/src/defaults.ts b/@commitlint/is-ignored/src/defaults.ts index b9357cc75f..02fbcd6b46 100644 --- a/@commitlint/is-ignored/src/defaults.ts +++ b/@commitlint/is-ignored/src/defaults.ts @@ -1,14 +1,14 @@ -import semver from 'semver'; -import {Matcher} from '@commitlint/types'; +import semver from "semver"; +import { Matcher } from "@commitlint/types"; const isSemver = (c: string): boolean => { - const firstLine = c.split('\n').shift(); + const firstLine = c.split("\n").shift(); - if (typeof firstLine !== 'string') { + if (typeof firstLine !== "string") { return false; } - const stripped = firstLine.replace(/^chore(\([^)]+\))?:/, '').trim(); + const stripped = firstLine.replace(/^chore(\([^)]+\))?:/, "").trim(); return semver.valid(stripped) !== null; }; @@ -16,7 +16,7 @@ const test = (r: RegExp): ((c: string) => boolean) => r.test.bind(r); export const wildcards: Matcher[] = [ test( - /^((Merge pull request)|(Merge (.*?) into (.*?)|(Merge branch (.*?)))(?:\r?\n)*$)/m + /^((Merge pull request)|(Merge (.*?) into (.*?)|(Merge branch (.*?)))(?:\r?\n)*$)/m, ), test(/^(Merge tag (.*?))(?:\r?\n)*$/m), test(/^(R|r)evert (.*)/), diff --git a/@commitlint/is-ignored/src/index.ts b/@commitlint/is-ignored/src/index.ts index 603f7c5fe0..1e53818df3 100644 --- a/@commitlint/is-ignored/src/index.ts +++ b/@commitlint/is-ignored/src/index.ts @@ -1,2 +1,2 @@ -export * from './is-ignored.js'; -export {default} from './is-ignored.js'; +export * from "./is-ignored.js"; +export { default } from "./is-ignored.js"; diff --git a/@commitlint/is-ignored/src/is-ignored.test.ts b/@commitlint/is-ignored/src/is-ignored.test.ts index d3b89d7df6..07e25d1267 100644 --- a/@commitlint/is-ignored/src/is-ignored.test.ts +++ b/@commitlint/is-ignored/src/is-ignored.test.ts @@ -1,28 +1,28 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import isIgnored from './is-ignored.js'; +import isIgnored from "./is-ignored.js"; const VERSION_MESSAGES = [ - '0.0.1', - '0.1.0', - '1.0.0', - '0.0.1-alpha', - '0.0.1-some-crazy-tag', - '0.0.1-0', - '0.0.1-999', - '0.0.1-alpha.0', - '0.0.1-alpha.999', - '0.0.1-some-crazy-tag.0', - '0.0.1-some-crazy-tag.999', - '0.0.1-1e69d54', - 'v0.0.1', - ' v3.0.0', + "0.0.1", + "0.1.0", + "1.0.0", + "0.0.1-alpha", + "0.0.1-some-crazy-tag", + "0.0.1-0", + "0.0.1-999", + "0.0.1-alpha.0", + "0.0.1-alpha.999", + "0.0.1-some-crazy-tag.0", + "0.0.1-some-crazy-tag.999", + "0.0.1-1e69d54", + "v0.0.1", + " v3.0.0", ]; const AMENDMENTS = [ - 'Signed-off-by: Developer <example@example.com>', - 'Change-Id: I895114872a515a269487a683124b63303818e19c', - 'Signed-off-by: Developer <example@example.com>\nChange-Id: I895114872a515a269487a683124b63303818e19c', + "Signed-off-by: Developer <example@example.com>", + "Change-Id: I895114872a515a269487a683124b63303818e19c", + "Signed-off-by: Developer <example@example.com>\nChange-Id: I895114872a515a269487a683124b63303818e19c", ]; const AMENDED_VERSION_MESSAGES = VERSION_MESSAGES.reduce<string[]>( @@ -32,176 +32,176 @@ const AMENDED_VERSION_MESSAGES = VERSION_MESSAGES.reduce<string[]>( ...AMENDMENTS.map((amendment) => `${message}\n\n${amendment}`), ]; }, - [] + [], ); -test('should return false when called without arguments', () => { +test("should return false when called without arguments", () => { expect(isIgnored()).toBe(false); }); -test('should return false when called with empty string', () => { - expect(isIgnored('')).toBe(false); +test("should return false when called with empty string", () => { + expect(isIgnored("")).toBe(false); }); -test('should return false for normal commit', () => { - expect(isIgnored('initial commit')).toBe(false); +test("should return false for normal commit", () => { + expect(isIgnored("initial commit")).toBe(false); }); -test('should return true for branch merges', () => { +test("should return true for branch merges", () => { expect(isIgnored("Merge branch 'iss53'")).toBe(true); }); -test('should return true for branch merges with newline characters', () => { +test("should return true for branch merges with newline characters", () => { expect(isIgnored("Merge branch 'ctrom-YarnBuild'\n")).toBe(true); expect(isIgnored("Merge branch 'ctrom-YarnBuild'\r\n")).toBe(true); }); -test('should return true for branch merges with multiple newline characters', () => { +test("should return true for branch merges with multiple newline characters", () => { expect(isIgnored("Merge branch 'ctrom-YarnBuild'\n\n\n")).toBe(true); expect(isIgnored("Merge branch 'ctrom-YarnBuild'\r\n\r\n\r\n")).toBe(true); }); -test('should return true for merged PRs', () => { - expect(isIgnored('Merge pull request #369')).toBe(true); +test("should return true for merged PRs", () => { + expect(isIgnored("Merge pull request #369")).toBe(true); }); -test('should return true for branch merges with newline characters and more characters after it', () => { +test("should return true for branch merges with newline characters and more characters after it", () => { expect(isIgnored("Merge branch 'ctrom-YarnBuild'\n ")).toBe(true); expect(isIgnored("Merge branch 'ctrom-YarnBuild'\r\n # some comment")).toBe( - true + true, ); }); -test('should return true for tag merges', () => { +test("should return true for tag merges", () => { expect(isIgnored("Merge tag '1.1.1'")).toBe(true); expect(isIgnored("Merge tag 'a tag'")).toBe(true); }); -test('should return true for tag merges with newline characters', () => { +test("should return true for tag merges with newline characters", () => { expect(isIgnored("Merge tag '1.1.1'\n")).toBe(true); expect(isIgnored("Merge tag '1.1.1'\r\n")).toBe(true); }); -test('should return true for tag merges with multiple newline characters', () => { +test("should return true for tag merges with multiple newline characters", () => { expect(isIgnored("Merge tag '1.1.1'\n\n\n")).toBe(true); expect(isIgnored("Merge tag '1.1.1'\r\n\r\n\r\n")).toBe(true); }); -test('should return true for tag merges with newline characters and more characters after it', () => { +test("should return true for tag merges with newline characters and more characters after it", () => { expect(isIgnored("Merge tag '1.1.1'\n ")).toBe(true); expect(isIgnored("Merge tag '1.1.1'\r\n # some comment")).toBe(true); }); -test('should return true for revert commits', () => { +test("should return true for revert commits", () => { expect( isIgnored( - `Revert "docs: add recipe for linting of all commits in a PR (#36)"\n\nThis reverts commit 1e69d542c16c2a32acfd139e32efa07a45f19111.` - ) + `Revert "docs: add recipe for linting of all commits in a PR (#36)"\n\nThis reverts commit 1e69d542c16c2a32acfd139e32efa07a45f19111.`, + ), ).toBe(true); expect( isIgnored( - `revert "docs: add recipe for linting of all commits in a PR (#36)"\n\nThis reverts commit 1e69d542c16c2a32acfd139e32efa07a45f19111.` - ) + `revert "docs: add recipe for linting of all commits in a PR (#36)"\n\nThis reverts commit 1e69d542c16c2a32acfd139e32efa07a45f19111.`, + ), ).toBe(true); }); -test('should ignore npm semver commits', () => { +test("should ignore npm semver commits", () => { VERSION_MESSAGES.forEach((message) => expect(isIgnored(message)).toBe(true)); }); -test('should ignore npm semver commits with chore', () => { +test("should ignore npm semver commits with chore", () => { VERSION_MESSAGES.forEach((message) => - expect(isIgnored(`chore: ${message}`)).toBe(true) + expect(isIgnored(`chore: ${message}`)).toBe(true), ); VERSION_MESSAGES.forEach((message) => - expect(isIgnored(`chore(release): ${message}`)).toBe(true) + expect(isIgnored(`chore(release): ${message}`)).toBe(true), ); }); -test('should ignore npm semver commits with footers', () => { +test("should ignore npm semver commits with footers", () => { AMENDED_VERSION_MESSAGES.forEach((message) => - expect(isIgnored(message)).toBe(true) + expect(isIgnored(message)).toBe(true), ); }); -test('should return true amend commits', () => { - expect(isIgnored('amend! initial commit')).toBe(true); +test("should return true amend commits", () => { + expect(isIgnored("amend! initial commit")).toBe(true); }); -test('should return true fixup commits', () => { - expect(isIgnored('fixup! initial commit')).toBe(true); +test("should return true fixup commits", () => { + expect(isIgnored("fixup! initial commit")).toBe(true); }); -test('should return true squash commits', () => { - expect(isIgnored('squash! initial commit')).toBe(true); +test("should return true squash commits", () => { + expect(isIgnored("squash! initial commit")).toBe(true); }); -test('should return true for bitbucket merge commits', () => { +test("should return true for bitbucket merge commits", () => { expect( - isIgnored('Merged in feature/facebook-friends-sync (pull request #8)') + isIgnored("Merged in feature/facebook-friends-sync (pull request #8)"), ).toBe(true); expect( - isIgnored('Merged develop into feature/component-form-select-card') + isIgnored("Merged develop into feature/component-form-select-card"), ).toBe(true); - expect(isIgnored('Automatic merge')).toBe(true); + expect(isIgnored("Automatic merge")).toBe(true); }); -test('should return true for automatic merge commits', () => { - expect(isIgnored('Auto-merged develop into master')).toBe(true); - expect(isIgnored('Merge remote-tracking branch')).toBe(true); +test("should return true for automatic merge commits", () => { + expect(isIgnored("Auto-merged develop into master")).toBe(true); + expect(isIgnored("Merge remote-tracking branch")).toBe(true); }); -test('should return true for azure devops merge commits', () => { - expect(isIgnored('Merged PR 123: Description here')).toBe(true); +test("should return true for azure devops merge commits", () => { + expect(isIgnored("Merged PR 123: Description here")).toBe(true); }); -test('should return false for commits containing, but not starting, with merge branch', () => { - expect(isIgnored('foo bar Merge branch xxx')).toBe(false); +test("should return false for commits containing, but not starting, with merge branch", () => { + expect(isIgnored("foo bar Merge branch xxx")).toBe(false); }); -test('should return false for commits containing, but not starting, with merge tag', () => { +test("should return false for commits containing, but not starting, with merge tag", () => { expect(isIgnored("foo bar Merge tag '1.1.1'")).toBe(false); }); -test('should return false for ignored message if defaults is false', () => { +test("should return false for ignored message if defaults is false", () => { expect( - isIgnored('Auto-merged develop into master', { + isIgnored("Auto-merged develop into master", { defaults: false, - }) + }), ).toBe(false); }); -test('should return false for ignored message if custom ignores and defaults is false', () => { +test("should return false for ignored message if custom ignores and defaults is false", () => { expect( - isIgnored('Auto-merged develop into master', { + isIgnored("Auto-merged develop into master", { defaults: false, - }) + }), ).toBe(false); }); -test('should throw error if ignores is not an array', () => { - const ignoredString = 'this should be ignored'; +test("should throw error if ignores is not an array", () => { + const ignoredString = "this should be ignored"; expect(() => { isIgnored(ignoredString, { - ignores: 'throws error', + ignores: "throws error", } as any); - }).toThrow('ignores must be of type array, received '); + }).toThrow("ignores must be of type array, received "); }); -test('should return true for custom ignores as function', () => { - const ignoredString = 'this should be ignored'; +test("should return true for custom ignores as function", () => { + const ignoredString = "this should be ignored"; expect( isIgnored(ignoredString, { ignores: [(c) => c === ignoredString], - }) + }), ).toBe(true); }); -test('should throw error if any element of ignores is not a function', () => { - const ignoredString = 'this should be ignored'; +test("should throw error if any element of ignores is not a function", () => { + const ignoredString = "this should be ignored"; expect(() => { isIgnored(ignoredString, { - ignores: ['throws error'], + ignores: ["throws error"], } as any); - }).toThrow('ignores must be array of type function, received items of type:'); + }).toThrow("ignores must be array of type function, received items of type:"); }); diff --git a/@commitlint/is-ignored/src/is-ignored.ts b/@commitlint/is-ignored/src/is-ignored.ts index a3782b1f5b..98faa4c38f 100644 --- a/@commitlint/is-ignored/src/is-ignored.ts +++ b/@commitlint/is-ignored/src/is-ignored.ts @@ -1,25 +1,25 @@ -import {wildcards} from './defaults.js'; -import {IsIgnoredOptions} from '@commitlint/types'; +import { wildcards } from "./defaults.js"; +import { IsIgnoredOptions } from "@commitlint/types"; export default function isIgnored( - commit: string = '', - opts: IsIgnoredOptions = {} + commit: string = "", + opts: IsIgnoredOptions = {}, ): boolean { - const ignores = typeof opts.ignores === 'undefined' ? [] : opts.ignores; + const ignores = typeof opts.ignores === "undefined" ? [] : opts.ignores; if (!Array.isArray(ignores)) { throw new Error( - `ignores must be of type array, received ${ignores} of type ${typeof ignores}` + `ignores must be of type array, received ${ignores} of type ${typeof ignores}`, ); } - const invalids = ignores.filter((c) => typeof c !== 'function'); + const invalids = ignores.filter((c) => typeof c !== "function"); if (invalids.length > 0) { throw new Error( `ignores must be array of type function, received items of type: ${invalids .map((i) => typeof i) - .join(', ')}` + .join(", ")}`, ); } diff --git a/@commitlint/is-ignored/tsconfig.json b/@commitlint/is-ignored/tsconfig.json index f3092129e3..0cc393e13d 100644 --- a/@commitlint/is-ignored/tsconfig.json +++ b/@commitlint/is-ignored/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src/**/*.ts"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../types"}] + "references": [{ "path": "../types" }] } diff --git a/@commitlint/lint/src/commit-message.ts b/@commitlint/lint/src/commit-message.ts index 7d8c99f047..fb9d8363ee 100644 --- a/@commitlint/lint/src/commit-message.ts +++ b/@commitlint/lint/src/commit-message.ts @@ -14,5 +14,5 @@ export const buildCommitMessage = ({ message = body ? `${message}\n\n${body}` : message; message = footer ? `${message}\n\n${footer}` : message; - return message || ''; + return message || ""; }; diff --git a/@commitlint/lint/src/lint.test.ts b/@commitlint/lint/src/lint.test.ts index f8b47f3523..0d37aca402 100644 --- a/@commitlint/lint/src/lint.test.ts +++ b/@commitlint/lint/src/lint.test.ts @@ -1,315 +1,315 @@ -import {test, expect} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { test, expect } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; -import lint from './lint.js'; +import lint from "./lint.js"; -test('throws without params', async () => { +test("throws without params", async () => { const error = (lint as any)(); - await expect(error).rejects.toThrow('Expected a raw commit'); + await expect(error).rejects.toThrow("Expected a raw commit"); }); -test('positive on empty message', async () => { - expect(await lint('')).toMatchObject({ +test("positive on empty message", async () => { + expect(await lint("")).toMatchObject({ valid: true, errors: [], warnings: [], }); }); -test('positive on stub message and no rule', async () => { - const actual = await lint('foo: bar'); +test("positive on stub message and no rule", async () => { + const actual = await lint("foo: bar"); expect(actual.valid).toBe(true); }); -test('positive on stub message and adhered rule', async () => { - const actual = await lint('foo: bar', { - 'type-enum': [RuleConfigSeverity.Error, 'always', ['foo']], +test("positive on stub message and adhered rule", async () => { + const actual = await lint("foo: bar", { + "type-enum": [RuleConfigSeverity.Error, "always", ["foo"]], }); expect(actual.valid).toBe(true); }); -test('negative on stub message and broken rule', async () => { - const actual = await lint('foo: bar', { - 'type-enum': [RuleConfigSeverity.Error, 'never', ['foo']], +test("negative on stub message and broken rule", async () => { + const actual = await lint("foo: bar", { + "type-enum": [RuleConfigSeverity.Error, "never", ["foo"]], }); expect(actual.valid).toBe(false); }); -test('positive on ignored message and broken rule', async () => { +test("positive on ignored message and broken rule", async () => { const actual = await lint('Revert "some bogus commit"', { - 'type-empty': [RuleConfigSeverity.Error, 'never'], + "type-empty": [RuleConfigSeverity.Error, "never"], }); expect(actual.valid).toBe(true); expect(actual.input).toBe('Revert "some bogus commit"'); }); -test('negative on ignored message, disabled ignored messages and broken rule', async () => { +test("negative on ignored message, disabled ignored messages and broken rule", async () => { const actual = await lint( 'Revert "some bogus commit"', { - 'type-empty': [RuleConfigSeverity.Error, 'never'], + "type-empty": [RuleConfigSeverity.Error, "never"], }, { defaultIgnores: false, - } + }, ); expect(actual.valid).toBe(false); }); -test('positive on custom ignored message and broken rule', async () => { - const ignoredMessage = 'some ignored custom message'; +test("positive on custom ignored message and broken rule", async () => { + const ignoredMessage = "some ignored custom message"; const actual = await lint( ignoredMessage, { - 'type-empty': [RuleConfigSeverity.Error, 'never'], + "type-empty": [RuleConfigSeverity.Error, "never"], }, { ignores: [(c) => c === ignoredMessage], - } + }, ); expect(actual.valid).toBe(true); expect(actual.input).toBe(ignoredMessage); }); -test('positive on stub message and opts', async () => { +test("positive on stub message and opts", async () => { const actual = await lint( - 'foo-bar', + "foo-bar", { - 'type-enum': [RuleConfigSeverity.Error, 'always', ['foo']], - 'type-empty': [RuleConfigSeverity.Error, 'never'], + "type-enum": [RuleConfigSeverity.Error, "always", ["foo"]], + "type-empty": [RuleConfigSeverity.Error, "never"], }, { parserOpts: { headerPattern: /^(\w*)(?:\((.*)\))?-(.*)$/, }, - } + }, ); expect(actual.valid).toBe(true); }); -test('throws for invalid rule names', async () => { - const error = lint('foo', { - foo: [RuleConfigSeverity.Error, 'always'], - bar: [RuleConfigSeverity.Warning, 'never'], +test("throws for invalid rule names", async () => { + const error = lint("foo", { + foo: [RuleConfigSeverity.Error, "always"], + bar: [RuleConfigSeverity.Warning, "never"], }); await expect(error).rejects.toThrow( - /^Found rules without implementation: foo, bar/ + /^Found rules without implementation: foo, bar/, ); }); -test('throws for invalid rule config', async () => { - const error = lint('type(scope): foo', { - 'type-enum': 1, - 'scope-enum': {0: 2, 1: 'never', 2: ['foo'], length: 3}, +test("throws for invalid rule config", async () => { + const error = lint("type(scope): foo", { + "type-enum": 1, + "scope-enum": { 0: 2, 1: "never", 2: ["foo"], length: 3 }, } as any); - await expect(error).rejects.toThrow('type-enum must be array'); - await expect(error).rejects.toThrow('scope-enum must be array'); + await expect(error).rejects.toThrow("type-enum must be array"); + await expect(error).rejects.toThrow("scope-enum must be array"); }); -test('allows disable shorthand', async () => { - const result = lint('foo', {'type-enum': [0], 'scope-enum': [0]}); +test("allows disable shorthand", async () => { + const result = lint("foo", { "type-enum": [0], "scope-enum": [0] }); await expect(result).resolves.toEqual({ errors: [], - input: 'foo', + input: "foo", valid: true, warnings: [], }); }); -test('throws for rule with invalid length', async () => { - const error = lint('type(scope): foo', {'scope-enum': [1, 2, 3, 4]} as any); +test("throws for rule with invalid length", async () => { + const error = lint("type(scope): foo", { "scope-enum": [1, 2, 3, 4] } as any); - await expect(error).rejects.toThrow('scope-enum must be 2 or 3 items long'); + await expect(error).rejects.toThrow("scope-enum must be 2 or 3 items long"); }); -test('throws for rule with invalid level', async () => { - const error = lint('type(scope): foo', { - 'type-enum': ['2', 'always'] as any, - 'header-max-length': [{}, 'always'] as any, +test("throws for rule with invalid level", async () => { + const error = lint("type(scope): foo", { + "type-enum": ["2", "always"] as any, + "header-max-length": [{}, "always"] as any, }); - await expect(error).rejects.toThrow('rule type-enum must be number'); - await expect(error).rejects.toThrow('rule header-max-length must be number'); + await expect(error).rejects.toThrow("rule type-enum must be number"); + await expect(error).rejects.toThrow("rule header-max-length must be number"); }); -test('throws for rule with out of range level', async () => { - const error = lint('type(scope): foo', { - 'type-enum': [-1, 'always'] as any, - 'header-max-length': [3, 'always'] as any, +test("throws for rule with out of range level", async () => { + const error = lint("type(scope): foo", { + "type-enum": [-1, "always"] as any, + "header-max-length": [3, "always"] as any, }); - await expect(error).rejects.toThrow('rule type-enum must be between 0 and 2'); + await expect(error).rejects.toThrow("rule type-enum must be between 0 and 2"); await expect(error).rejects.toThrow( - 'rule header-max-length must be between 0 and 2' + "rule header-max-length must be between 0 and 2", ); }); -test('throws for rule with invalid condition', async () => { - const error = lint('type(scope): foo', { - 'type-enum': [1, 2] as any, - 'header-max-length': [1, {}] as any, +test("throws for rule with invalid condition", async () => { + const error = lint("type(scope): foo", { + "type-enum": [1, 2] as any, + "header-max-length": [1, {}] as any, }); - await expect(error).rejects.toThrow('type-enum must be string'); - await expect(error).rejects.toThrow('header-max-length must be string'); + await expect(error).rejects.toThrow("type-enum must be string"); + await expect(error).rejects.toThrow("header-max-length must be string"); }); -test('throws for rule with out of range condition', async () => { - const error = lint('type(scope): foo', { - 'type-enum': [RuleConfigSeverity.Warning, 'foo'] as any, - 'header-max-length': [RuleConfigSeverity.Warning, 'bar'] as any, +test("throws for rule with out of range condition", async () => { + const error = lint("type(scope): foo", { + "type-enum": [RuleConfigSeverity.Warning, "foo"] as any, + "header-max-length": [RuleConfigSeverity.Warning, "bar"] as any, }); await expect(error).rejects.toThrow('type-enum must be "always" or "never"'); await expect(error).rejects.toThrow( - 'header-max-length must be "always" or "never"' + 'header-max-length must be "always" or "never"', ); }); -test('succeds for issue', async () => { - const report = await lint('somehting #1', { - 'references-empty': [RuleConfigSeverity.Error, 'never'], +test("succeds for issue", async () => { + const report = await lint("somehting #1", { + "references-empty": [RuleConfigSeverity.Error, "never"], }); expect(report.valid).toBe(true); }); -test('fails for issue', async () => { - const report = await lint('somehting #1', { - 'references-empty': [RuleConfigSeverity.Error, 'always'], +test("fails for issue", async () => { + const report = await lint("somehting #1", { + "references-empty": [RuleConfigSeverity.Error, "always"], }); expect(report.valid).toBe(false); }); -test('succeds for custom issue prefix', async () => { +test("succeds for custom issue prefix", async () => { const report = await lint( - 'somehting REF-1', + "somehting REF-1", { - 'references-empty': [RuleConfigSeverity.Error, 'never'], + "references-empty": [RuleConfigSeverity.Error, "never"], }, { parserOpts: { - issuePrefixes: ['REF-'], + issuePrefixes: ["REF-"], }, - } + }, ); expect(report.valid).toBe(true); }); -test('fails for custom issue prefix', async () => { +test("fails for custom issue prefix", async () => { const report = await lint( - 'somehting #1', + "somehting #1", { - 'references-empty': [RuleConfigSeverity.Error, 'never'], + "references-empty": [RuleConfigSeverity.Error, "never"], }, { parserOpts: { - issuePrefixes: ['REF-'], + issuePrefixes: ["REF-"], }, - } + }, ); expect(report.valid).toBe(false); }); -test('fails for custom plugin rule', async () => { +test("fails for custom plugin rule", async () => { const report = await lint( - 'somehting #1', + "somehting #1", { - 'plugin-rule': [RuleConfigSeverity.Error, 'never'], + "plugin-rule": [RuleConfigSeverity.Error, "never"], }, { plugins: { - 'plugin-example': { + "plugin-example": { rules: { - 'plugin-rule': () => [false], + "plugin-rule": () => [false], }, }, }, - } + }, ); expect(report.valid).toBe(false); }); -test('passes for custom plugin rule', async () => { +test("passes for custom plugin rule", async () => { const report = await lint( - 'somehting #1', + "somehting #1", { - 'plugin-rule': [RuleConfigSeverity.Error, 'never'], + "plugin-rule": [RuleConfigSeverity.Error, "never"], }, { plugins: { - 'plugin-example': { + "plugin-example": { rules: { - 'plugin-rule': () => [true], + "plugin-rule": () => [true], }, }, }, - } + }, ); expect(report.valid).toBe(true); }); -test('returns original message only with commit header', async () => { - const message = 'foo: bar'; +test("returns original message only with commit header", async () => { + const message = "foo: bar"; const report = await lint(message); expect(report.input).toBe(message); }); -test('returns original message with commit header and body', async () => { - const message = 'foo: bar/n/nFoo bar bizz buzz.'; +test("returns original message with commit header and body", async () => { + const message = "foo: bar/n/nFoo bar bizz buzz."; const report = await lint(message); expect(report.input).toBe(message); }); -test('returns original message with commit header, body and footer', async () => { - const message = 'foo: bar/n/nFoo bar bizz buzz./n/nCloses #1'; +test("returns original message with commit header, body and footer", async () => { + const message = "foo: bar/n/nFoo bar bizz buzz./n/nCloses #1"; const report = await lint(message); expect(report.input).toBe(message); }); -test('returns original message with commit header, body and footer, parsing comments', async () => { - const expected = 'foo: bar/n/nFoo bar bizz buzz./n/nCloses #1'; +test("returns original message with commit header, body and footer, parsing comments", async () => { + const expected = "foo: bar/n/nFoo bar bizz buzz./n/nCloses #1"; const message = `${expected}\n\n# Some comment to ignore`; const report = await lint( message, { - 'references-empty': [RuleConfigSeverity.Error, 'never'], + "references-empty": [RuleConfigSeverity.Error, "never"], }, { parserOpts: { - commentChar: '#', + commentChar: "#", }, - } + }, ); expect(report.input).toBe(expected); }); -test('passes for async rule', async () => { +test("passes for async rule", async () => { const report = await lint( - 'somehting #1', + "somehting #1", { - 'async-rule': [RuleConfigSeverity.Error, 'never'], + "async-rule": [RuleConfigSeverity.Error, "never"], }, { plugins: { - 'example-plugin': { + "example-plugin": { rules: { - 'async-rule': async () => [true, 'all good'] as const, + "async-rule": async () => [true, "all good"] as const, }, }, }, - } + }, ); expect(report.valid).toBe(true); diff --git a/@commitlint/lint/src/lint.ts b/@commitlint/lint/src/lint.ts index 7ad92c10c8..c64bb829e0 100644 --- a/@commitlint/lint/src/lint.ts +++ b/@commitlint/lint/src/lint.ts @@ -1,7 +1,7 @@ -import util from 'node:util'; -import isIgnored from '@commitlint/is-ignored'; -import parse from '@commitlint/parse'; -import defaultRules from '@commitlint/rules'; +import util from "node:util"; +import isIgnored from "@commitlint/is-ignored"; +import parse from "@commitlint/parse"; +import defaultRules from "@commitlint/rules"; import type { LintOptions, LintOutcome, @@ -10,24 +10,24 @@ import type { BaseRule, RuleType, QualifiedRules, -} from '@commitlint/types'; -import {RuleConfigSeverity} from '@commitlint/types'; +} from "@commitlint/types"; +import { RuleConfigSeverity } from "@commitlint/types"; -import {buildCommitMessage} from './commit-message.js'; +import { buildCommitMessage } from "./commit-message.js"; export default async function lint( message: string, rawRulesConfig?: QualifiedRules, - rawOpts?: LintOptions + rawOpts?: LintOptions, ): Promise<LintOutcome> { const opts = rawOpts ? rawOpts - : {defaultIgnores: undefined, ignores: undefined}; + : { defaultIgnores: undefined, ignores: undefined }; const rulesConfig = rawRulesConfig || {}; // Found a wildcard match, skip if ( - isIgnored(message, {defaults: opts.defaultIgnores, ignores: opts.ignores}) + isIgnored(message, { defaults: opts.defaultIgnores, ignores: opts.ignores }) ) { return { valid: true, @@ -39,8 +39,8 @@ export default async function lint( // Parse the commit message const parsed = - message === '' - ? {header: null, body: null, footer: null} + message === "" + ? { header: null, body: null, footer: null } : await parse(message, undefined, opts.parserOpts); if ( @@ -58,14 +58,14 @@ export default async function lint( } const allRules: Map<string, BaseRule<never, RuleType>> = new Map( - Object.entries(defaultRules) + Object.entries(defaultRules), ); if (opts.plugins) { Object.values(opts.plugins).forEach((plugin) => { if (plugin.rules) { Object.keys(plugin.rules).forEach((ruleKey) => - allRules.set(ruleKey, plugin.rules[ruleKey]) + allRules.set(ruleKey, plugin.rules[ruleKey]), ); } }); @@ -73,16 +73,16 @@ export default async function lint( // Find invalid rules configs const missing = Object.keys(rulesConfig).filter( - (name) => typeof allRules.get(name) !== 'function' + (name) => typeof allRules.get(name) !== "function", ); if (missing.length > 0) { const names = [...allRules.keys()]; throw new RangeError( [ - `Found rules without implementation: ${missing.join(', ')}.`, - `Supported rules are: ${names.join(', ')}.`, - ].join('\n') + `Found rules without implementation: ${missing.join(", ")}.`, + `Supported rules are: ${names.join(", ")}.`, + ].join("\n"), ); } @@ -91,8 +91,8 @@ export default async function lint( if (!Array.isArray(config)) { return new Error( `config for rule ${name} must be array, received ${util.inspect( - config - )} of type ${typeof config}` + config, + )} of type ${typeof config}`, ); } @@ -104,43 +104,43 @@ export default async function lint( const [, when] = config; - if (typeof level !== 'number' || isNaN(level)) { + if (typeof level !== "number" || isNaN(level)) { return new Error( `level for rule ${name} must be number, received ${util.inspect( - level - )} of type ${typeof level}` + level, + )} of type ${typeof level}`, ); } if (config.length < 2 || config.length > 3) { return new Error( `config for rule ${name} must be 2 or 3 items long, received ${util.inspect( - config - )} of length ${config.length}` + config, + )} of length ${config.length}`, ); } if (level < 0 || level > 2) { return new RangeError( `level for rule ${name} must be between 0 and 2, received ${util.inspect( - level - )}` + level, + )}`, ); } - if (typeof when !== 'string') { + if (typeof when !== "string") { return new Error( `condition for rule ${name} must be string, received ${util.inspect( - when - )} of type ${typeof when}` + when, + )} of type ${typeof when}`, ); } - if (when !== 'never' && when !== 'always') { + if (when !== "never" && when !== "always") { return new Error( `condition for rule ${name} must be "always" or "never", received ${util.inspect( - when - )}` + when, + )}`, ); } @@ -149,7 +149,7 @@ export default async function lint( .filter((item): item is Error => item instanceof Error); if (invalid.length > 0) { - throw new Error(invalid.map((i) => i.message).join('\n')); + throw new Error(invalid.map((i) => i.message).join("\n")); } // Validate against all rules @@ -178,14 +178,14 @@ export default async function lint( }); const results = (await Promise.all(pendingResults)).filter( - (result): result is LintRuleOutcome => result !== null + (result): result is LintRuleOutcome => result !== null, ); const errors = results.filter( - (result) => result.level === RuleConfigSeverity.Error && !result.valid + (result) => result.level === RuleConfigSeverity.Error && !result.valid, ); const warnings = results.filter( - (result) => result.level === RuleConfigSeverity.Warning && !result.valid + (result) => result.level === RuleConfigSeverity.Warning && !result.valid, ); const valid = errors.length === 0; diff --git a/@commitlint/lint/tsconfig.json b/@commitlint/lint/tsconfig.json index d30e6bdbf0..bcd59cb2a3 100644 --- a/@commitlint/lint/tsconfig.json +++ b/@commitlint/lint/tsconfig.json @@ -8,9 +8,9 @@ "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], "references": [ - {"path": "../is-ignored"}, - {"path": "../parse"}, - {"path": "../rules"}, - {"path": "../types"} + { "path": "../is-ignored" }, + { "path": "../parse" }, + { "path": "../rules" }, + { "path": "../types" } ] } diff --git a/@commitlint/load/src/load.test.ts b/@commitlint/load/src/load.test.ts index cb7b49b062..43a02d4bf5 100644 --- a/@commitlint/load/src/load.test.ts +++ b/@commitlint/load/src/load.test.ts @@ -1,23 +1,23 @@ -import {describe, test, expect, vi} from 'vitest'; -import {readFileSync, writeFileSync} from 'node:fs'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { describe, test, expect, vi } from "vitest"; +import { readFileSync, writeFileSync } from "node:fs"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {RuleConfigSeverity} from '@commitlint/types'; -import {fix, git, npm} from '@commitlint/test'; +import { RuleConfigSeverity } from "@commitlint/types"; +import { fix, git, npm } from "@commitlint/test"; -import load, {resolveFrom} from './load.js'; -import {isDynamicAwaitSupported} from './utils/load-config.js'; +import load, { resolveFrom } from "./load.js"; +import { isDynamicAwaitSupported } from "./utils/load-config.js"; -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); const plugin = vi.fn(); const scopedPlugin = vi.fn(); -vi.mock('commitlint-plugin-example', () => ({ +vi.mock("commitlint-plugin-example", () => ({ default: plugin, })); -vi.mock('@scope/commitlint-plugin-example', () => ({ +vi.mock("@scope/commitlint-plugin-example", () => ({ default: scopedPlugin, })); @@ -25,110 +25,113 @@ const fixBootstrap = (name: string) => fix.bootstrap(name, __dirname); const gitBootstrap = (name: string) => git.bootstrap(name, __dirname); const npmBootstrap = (name: string) => npm.bootstrap(name, __dirname); -test('extends-empty should have no rules', async () => { - const cwd = await gitBootstrap('fixtures/extends-empty'); - const actual = await load({}, {cwd}); +test("extends-empty should have no rules", async () => { + const cwd = await gitBootstrap("fixtures/extends-empty"); + const actual = await load({}, { cwd }); expect(actual.rules).toMatchObject({}); expect(actual.parserPreset).not.toBeDefined(); }); -test('uses seed as configured', async () => { - const cwd = await gitBootstrap('fixtures/extends-empty'); +test("uses seed as configured", async () => { + const cwd = await gitBootstrap("fixtures/extends-empty"); const rules = { - 'body-case': [RuleConfigSeverity.Warning, 'never', 'camel-case'] as any, + "body-case": [RuleConfigSeverity.Warning, "never", "camel-case"] as any, }; - const actual = await load({rules}, {cwd}); + const actual = await load({ rules }, { cwd }); - expect(actual.rules['body-case']).toStrictEqual([ + expect(actual.rules["body-case"]).toStrictEqual([ RuleConfigSeverity.Warning, - 'never', - 'camel-case', + "never", + "camel-case", ]); }); -test('rules should be loaded from local', async () => { +test("rules should be loaded from local", async () => { const actual = await load({ rules: { - direct: [RuleConfigSeverity.Warning, 'never', 'foo'], - func: () => [RuleConfigSeverity.Warning, 'never', 'foo'], - async: async () => [RuleConfigSeverity.Warning, 'never', 'foo'], + direct: [RuleConfigSeverity.Warning, "never", "foo"], + func: () => [RuleConfigSeverity.Warning, "never", "foo"], + async: async () => [RuleConfigSeverity.Warning, "never", "foo"], promise: () => - Promise.resolve([RuleConfigSeverity.Warning, 'never', 'foo']), + Promise.resolve([RuleConfigSeverity.Warning, "never", "foo"]), }, }); - expect(actual.rules['direct']).toStrictEqual([ + expect(actual.rules["direct"]).toStrictEqual([ RuleConfigSeverity.Warning, - 'never', - 'foo', + "never", + "foo", ]); - expect(actual.rules['func']).toStrictEqual([ + expect(actual.rules["func"]).toStrictEqual([ RuleConfigSeverity.Warning, - 'never', - 'foo', + "never", + "foo", ]); - expect(actual.rules['async']).toStrictEqual([ + expect(actual.rules["async"]).toStrictEqual([ RuleConfigSeverity.Warning, - 'never', - 'foo', + "never", + "foo", ]); - expect(actual.rules['promise']).toStrictEqual([ + expect(actual.rules["promise"]).toStrictEqual([ RuleConfigSeverity.Warning, - 'never', - 'foo', + "never", + "foo", ]); }); -test('rules should be loaded from relative config file', async () => { - const file = 'config/commitlint.config.js'; - const cwd = await gitBootstrap('fixtures/specify-config-file'); +test("rules should be loaded from relative config file", async () => { + const file = "config/commitlint.config.js"; + const cwd = await gitBootstrap("fixtures/specify-config-file"); const rules = { - 'body-case': [RuleConfigSeverity.Warning, 'never', 'camel-case'] as any, + "body-case": [RuleConfigSeverity.Warning, "never", "camel-case"] as any, }; - const actual = await load({rules}, {cwd, file}); + const actual = await load({ rules }, { cwd, file }); - expect(actual.rules['body-case']).toStrictEqual([ + expect(actual.rules["body-case"]).toStrictEqual([ RuleConfigSeverity.Warning, - 'never', - 'camel-case', + "never", + "camel-case", ]); }); -test('rules should be loaded from absolute config file', async () => { - const cwd = await gitBootstrap('fixtures/specify-config-file'); - const file = path.resolve(cwd, 'config/commitlint.config.js'); +test("rules should be loaded from absolute config file", async () => { + const cwd = await gitBootstrap("fixtures/specify-config-file"); + const file = path.resolve(cwd, "config/commitlint.config.js"); const rules = { - 'body-case': [RuleConfigSeverity.Warning, 'never', 'camel-case'] as any, + "body-case": [RuleConfigSeverity.Warning, "never", "camel-case"] as any, }; - const actual = await load({rules}, {cwd: process.cwd(), file}); + const actual = await load({ rules }, { cwd: process.cwd(), file }); - expect(actual.rules['body-case']).toStrictEqual([ + expect(actual.rules["body-case"]).toStrictEqual([ RuleConfigSeverity.Warning, - 'never', - 'camel-case', + "never", + "camel-case", ]); }); -test('plugins should be loaded from seed', async () => { - const cwd = await gitBootstrap('fixtures/extends-empty'); - const actual = await load({plugins: ['example', '@scope/example']}, {cwd}); +test("plugins should be loaded from seed", async () => { + const cwd = await gitBootstrap("fixtures/extends-empty"); + const actual = await load( + { plugins: ["example", "@scope/example"] }, + { cwd }, + ); expect(actual.plugins).toMatchObject({ example: plugin, - '@scope/example': scopedPlugin, + "@scope/example": scopedPlugin, }); }); -test('plugins should be loaded from local', async () => { +test("plugins should be loaded from local", async () => { const actual = await load({ plugins: [ { rules: { - test: () => [true, 'asd'], + test: () => [true, "asd"], }, }, ], @@ -141,122 +144,122 @@ test('plugins should be loaded from local', async () => { test: expect.any(Function), }, }, - }) + }), ); }); -test('plugins should be loaded from config', async () => { - const cwd = await gitBootstrap('fixtures/extends-plugins'); - const actual = await load({}, {cwd}); +test("plugins should be loaded from config", async () => { + const cwd = await gitBootstrap("fixtures/extends-plugins"); + const actual = await load({}, { cwd }); expect(actual.plugins).toMatchObject({ example: plugin, - '@scope/example': scopedPlugin, + "@scope/example": scopedPlugin, }); }); -test('plugins should be loaded from shareable config', async () => { - const cwd = await gitBootstrap('fixtures/extends-with-plugins'); - const actual = await load({}, {cwd}); +test("plugins should be loaded from shareable config", async () => { + const cwd = await gitBootstrap("fixtures/extends-with-plugins"); + const actual = await load({}, { cwd }); expect(actual.plugins).toMatchObject({ example: plugin, - '@scope/example': scopedPlugin, + "@scope/example": scopedPlugin, }); }); -test('local plugins should be loaded from shareable configs', async () => { - const cwd = await gitBootstrap('fixtures/extends-with-local-plugins'); - const actual = await load({}, {cwd}); +test("local plugins should be loaded from shareable configs", async () => { + const cwd = await gitBootstrap("fixtures/extends-with-local-plugins"); + const actual = await load({}, { cwd }); expect(actual.plugins).toEqual( expect.objectContaining({ local: { rules: { - 'hello-world-rule': expect.any(Function), - 'is-positive': expect.any(Function), + "hello-world-rule": expect.any(Function), + "is-positive": expect.any(Function), }, }, - }) + }), ); }); -test('uses seed with parserPreset', async () => { - const cwd = await gitBootstrap('fixtures/parser-preset'); - const {parserPreset: actual} = await load( - {parserPreset: './conventional-changelog-custom'}, - {cwd} +test("uses seed with parserPreset", async () => { + const cwd = await gitBootstrap("fixtures/parser-preset"); + const { parserPreset: actual } = await load( + { parserPreset: "./conventional-changelog-custom" }, + { cwd }, ); expect(actual).toBeDefined(); - expect(actual!.name).toBe('./conventional-changelog-custom'); + expect(actual!.name).toBe("./conventional-changelog-custom"); expect(actual!.parserOpts).toMatchObject({ headerPattern: /^(\w*)(?:\((.*)\))?-(.*)$/, }); }); -test('invalid extend should throw', async () => { - const cwd = await gitBootstrap('fixtures/extends-invalid'); +test("invalid extend should throw", async () => { + const cwd = await gitBootstrap("fixtures/extends-invalid"); - await expect(load({}, {cwd})).rejects.toThrow(); + await expect(load({}, { cwd })).rejects.toThrow(); }); -test('empty file should have no rules', async () => { - const cwd = await gitBootstrap('fixtures/empty-object-file'); - const actual = await load({}, {cwd}); +test("empty file should have no rules", async () => { + const cwd = await gitBootstrap("fixtures/empty-object-file"); + const actual = await load({}, { cwd }); expect(actual.rules).toMatchObject({}); }); -test('empty file should extend nothing', async () => { - const cwd = await gitBootstrap('fixtures/empty-file'); - const actual = await load({}, {cwd}); +test("empty file should extend nothing", async () => { + const cwd = await gitBootstrap("fixtures/empty-file"); + const actual = await load({}, { cwd }); expect(actual.extends).toHaveLength(0); }); -test('respects cwd option', async () => { - const cwd = await gitBootstrap('fixtures/recursive-extends/first-extended'); - const actual = await load({}, {cwd}); +test("respects cwd option", async () => { + const cwd = await gitBootstrap("fixtures/recursive-extends/first-extended"); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: '@commitlint/format', - extends: ['./second-extended'], + formatter: "@commitlint/format", + extends: ["./second-extended"], plugins: {}, rules: { - one: [RuleConfigSeverity.Warning, 'always'], - two: [RuleConfigSeverity.Error, 'never'], + one: [RuleConfigSeverity.Warning, "always"], + two: [RuleConfigSeverity.Error, "never"], }, }); }); -describe.each([['basic'], ['extends']])('%s config', (template) => { - const isExtendsTemplate = template === 'extends'; +describe.each([["basic"], ["extends"]])("%s config", (template) => { + const isExtendsTemplate = template === "extends"; const configFiles = [ - 'commitlint.config.cjs', - 'commitlint.config.js', - 'commitlint.config.mjs', - 'package.json', - 'package.yaml', - '.commitlintrc', - '.commitlintrc.cjs', - '.commitlintrc.js', - '.commitlintrc.json', - '.commitlintrc.mjs', - '.commitlintrc.yml', - '.commitlintrc.yaml', + "commitlint.config.cjs", + "commitlint.config.js", + "commitlint.config.mjs", + "package.json", + "package.yaml", + ".commitlintrc", + ".commitlintrc.cjs", + ".commitlintrc.js", + ".commitlintrc.json", + ".commitlintrc.mjs", + ".commitlintrc.yml", + ".commitlintrc.yaml", ]; const configTestCases = [ ...configFiles - .filter((filename) => !filename.endsWith('.mjs')) - .map((filename) => ({filename, isEsm: false})), + .filter((filename) => !filename.endsWith(".mjs")) + .map((filename) => ({ filename, isEsm: false })), ...configFiles .filter((filename) => - ['.mjs', '.js'].some((ext) => filename.endsWith(ext)) + [".mjs", ".js"].some((ext) => filename.endsWith(ext)), ) - .map((filename) => ({filename, isEsm: true})), + .map((filename) => ({ filename, isEsm: true })), ]; const getConfigContents = ({ @@ -266,60 +269,60 @@ describe.each([['basic'], ['extends']])('%s config', (template) => { filename: string; isEsm: boolean; }): string | NodeJS.ArrayBufferView => { - if (filename === 'package.json') { + if (filename === "package.json") { const configPath = path.join( __dirname, - `../fixtures/${template}-config/.commitlintrc.json` + `../fixtures/${template}-config/.commitlintrc.json`, ); const commitlint = JSON.parse( - readFileSync(configPath, {encoding: 'utf-8'}) + readFileSync(configPath, { encoding: "utf-8" }), ); - return JSON.stringify({commitlint}); - } else if (filename === 'package.yaml') { + return JSON.stringify({ commitlint }); + } else if (filename === "package.yaml") { const configPath = path.join( __dirname, - `../fixtures/${template}-config/.commitlintrc.yaml` + `../fixtures/${template}-config/.commitlintrc.yaml`, ); - const yaml = readFileSync(configPath, {encoding: 'utf-8'}); - return `commitlint:\n${yaml.replace(/^/gm, ' ')}`; + const yaml = readFileSync(configPath, { encoding: "utf-8" }); + return `commitlint:\n${yaml.replace(/^/gm, " ")}`; } else { - const filePath = ['..', 'fixtures', `${template}-config`, filename]; + const filePath = ["..", "fixtures", `${template}-config`, filename]; if (isEsm) { - filePath.splice(3, 0, 'esm'); + filePath.splice(3, 0, "esm"); } - const configPath = path.join(__dirname, filePath.join('/')); + const configPath = path.join(__dirname, filePath.join("/")); return readFileSync(configPath); } }; const esmBootstrap = (cwd: string) => { - const packageJsonPath = path.join(cwd, 'package.json'); + const packageJsonPath = path.join(cwd, "package.json"); const packageJSON = JSON.parse( - readFileSync(packageJsonPath, {encoding: 'utf-8'}) + readFileSync(packageJsonPath, { encoding: "utf-8" }), ); writeFileSync( packageJsonPath, JSON.stringify({ ...packageJSON, - type: 'module', - }) + type: "module", + }), ); }; - const templateFolder = [template, isExtendsTemplate ? 'js' : '', 'template'] + const templateFolder = [template, isExtendsTemplate ? "js" : "", "template"] .filter((elem) => elem) - .join('-'); + .join("-"); test.each( configTestCases // Skip ESM tests for the extends suite until resolve-extends supports ESM - .filter(({isEsm}) => template !== 'extends' || !isEsm) + .filter(({ isEsm }) => template !== "extends" || !isEsm) // Skip ESM tests if dynamic await is not supported; Jest will crash with a seg fault error - .filter(({isEsm}) => isDynamicAwaitSupported() || !isEsm) - )('$filename, ESM: $isEsm', async ({filename, isEsm}) => { + .filter(({ isEsm }) => isDynamicAwaitSupported() || !isEsm), + )("$filename, ESM: $isEsm", async ({ filename, isEsm }) => { const cwd = await gitBootstrap(`fixtures/${templateFolder}`); if (isEsm) { @@ -328,253 +331,253 @@ describe.each([['basic'], ['extends']])('%s config', (template) => { writeFileSync( path.join(cwd, filename), - getConfigContents({filename, isEsm}) + getConfigContents({ filename, isEsm }), ); - const actual = await load({}, {cwd}); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: '@commitlint/format', - extends: isExtendsTemplate ? ['./first-extended'] : [], + formatter: "@commitlint/format", + extends: isExtendsTemplate ? ["./first-extended"] : [], plugins: {}, rules: { - zero: [RuleConfigSeverity.Disabled, 'never'], - one: [RuleConfigSeverity.Warning, 'always'], - two: [RuleConfigSeverity.Error, 'never'], + zero: [RuleConfigSeverity.Disabled, "never"], + one: [RuleConfigSeverity.Warning, "always"], + two: [RuleConfigSeverity.Error, "never"], }, }); }); }); -test('recursive extends with ts file', async () => { - const cwd = await gitBootstrap('fixtures/recursive-extends-ts'); - const actual = await load({}, {cwd}); +test("recursive extends with ts file", async () => { + const cwd = await gitBootstrap("fixtures/recursive-extends-ts"); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: '@commitlint/format', - extends: ['./first-extended/index.ts'], + formatter: "@commitlint/format", + extends: ["./first-extended/index.ts"], plugins: {}, rules: { - zero: [RuleConfigSeverity.Disabled, 'never', 'zero'], - one: [RuleConfigSeverity.Warning, 'never', 'one'], - two: [RuleConfigSeverity.Error, 'never', 'two'], + zero: [RuleConfigSeverity.Disabled, "never", "zero"], + one: [RuleConfigSeverity.Warning, "never", "one"], + two: [RuleConfigSeverity.Error, "never", "two"], }, }); }); -test('parser preset overwrites completely instead of merging', async () => { - const cwd = await gitBootstrap('fixtures/parser-preset-override'); - const actual = await load({}, {cwd}); +test("parser preset overwrites completely instead of merging", async () => { + const cwd = await gitBootstrap("fixtures/parser-preset-override"); + const actual = await load({}, { cwd }); expect(actual.parserPreset).toBeDefined(); - expect(actual.parserPreset!.name).toBe('./custom'); + expect(actual.parserPreset!.name).toBe("./custom"); expect(actual.parserPreset!.parserOpts).toMatchObject({ headerPattern: /.*/, }); }); -test('recursive extends with parserPreset', async () => { - const cwd = await gitBootstrap('fixtures/recursive-parser-preset'); - const actual = await load({}, {cwd}); +test("recursive extends with parserPreset", async () => { + const cwd = await gitBootstrap("fixtures/recursive-parser-preset"); + const actual = await load({}, { cwd }); expect(actual.parserPreset).toBeDefined(); - expect(actual.parserPreset!.name).toBe('./conventional-changelog-custom'); + expect(actual.parserPreset!.name).toBe("./conventional-changelog-custom"); expect(actual.parserPreset!.parserOpts).toMatchObject({ headerPattern: /^(\w*)(?:\((.*)\))?-(.*)$/, }); }); -test('ignores unknown keys', async () => { - const cwd = await gitBootstrap('fixtures/trash-file'); - const actual = await load({}, {cwd}); +test("ignores unknown keys", async () => { + const cwd = await gitBootstrap("fixtures/trash-file"); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: '@commitlint/format', + formatter: "@commitlint/format", extends: [], plugins: {}, rules: { - foo: [RuleConfigSeverity.Warning, 'always', 'bar'], - baz: [RuleConfigSeverity.Warning, 'always', 'bar'], + foo: [RuleConfigSeverity.Warning, "always", "bar"], + baz: [RuleConfigSeverity.Warning, "always", "bar"], }, }); }); -test('ignores unknown keys recursively', async () => { - const cwd = await gitBootstrap('fixtures/trash-extend'); - const actual = await load({}, {cwd}); +test("ignores unknown keys recursively", async () => { + const cwd = await gitBootstrap("fixtures/trash-extend"); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: '@commitlint/format', - extends: ['./one'], + formatter: "@commitlint/format", + extends: ["./one"], plugins: {}, rules: { - zero: [RuleConfigSeverity.Disabled, 'always', 'zero'], - one: [RuleConfigSeverity.Warning, 'always', 'one'], + zero: [RuleConfigSeverity.Disabled, "always", "zero"], + one: [RuleConfigSeverity.Warning, "always", "one"], }, }); }); -test('find up from given cwd', async () => { - const outer = await fixBootstrap('fixtures/outer-scope'); - await git.init(path.join(outer, 'inner-scope')); - const cwd = path.join(outer, 'inner-scope', 'child-scope'); - const actual = await load({}, {cwd}); +test("find up from given cwd", async () => { + const outer = await fixBootstrap("fixtures/outer-scope"); + await git.init(path.join(outer, "inner-scope")); + const cwd = path.join(outer, "inner-scope", "child-scope"); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: '@commitlint/format', + formatter: "@commitlint/format", extends: [], plugins: {}, rules: { - child: [RuleConfigSeverity.Error, 'always', true], - inner: [RuleConfigSeverity.Error, 'always', false], - outer: [RuleConfigSeverity.Error, 'always', false], + child: [RuleConfigSeverity.Error, "always", true], + inner: [RuleConfigSeverity.Error, "always", false], + outer: [RuleConfigSeverity.Error, "always", false], }, }); }); -test('find up config from outside current git repo', async () => { - const outer = await fixBootstrap('fixtures/outer-scope'); - const cwd = await git.init(path.join(outer, 'inner-scope')); - const actual = await load({}, {cwd}); +test("find up config from outside current git repo", async () => { + const outer = await fixBootstrap("fixtures/outer-scope"); + const cwd = await git.init(path.join(outer, "inner-scope")); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: '@commitlint/format', + formatter: "@commitlint/format", extends: [], plugins: {}, rules: { - child: [RuleConfigSeverity.Warning, 'never', false], - inner: [RuleConfigSeverity.Warning, 'never', false], - outer: [RuleConfigSeverity.Warning, 'never', true], + child: [RuleConfigSeverity.Warning, "never", false], + inner: [RuleConfigSeverity.Warning, "never", false], + outer: [RuleConfigSeverity.Warning, "never", true], }, }); }); -test('respects formatter option', async () => { - const cwd = await gitBootstrap('fixtures/formatter'); - const actual = await load({}, {cwd}); +test("respects formatter option", async () => { + const cwd = await gitBootstrap("fixtures/formatter"); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: 'commitlint-junit', + formatter: "commitlint-junit", extends: [], plugins: {}, rules: {}, }); }); -test('resolves formatter relative from config directory', async () => { - const cwd = await gitBootstrap('fixtures/formatter-local-module'); - const actual = await load({}, {cwd}); +test("resolves formatter relative from config directory", async () => { + const cwd = await gitBootstrap("fixtures/formatter-local-module"); + const actual = await load({}, { cwd }); expect(actual).toMatchObject({ - formatter: resolveFrom('./formatters/custom.js', cwd), + formatter: resolveFrom("./formatters/custom.js", cwd), extends: [], plugins: {}, rules: {}, }); }); -test('returns formatter name when unable to resolve from config directory', async () => { - const cwd = await gitBootstrap('fixtures/formatter-local-module'); - const actual = await load({formatter: './doesnt/exists.js'}, {cwd}); +test("returns formatter name when unable to resolve from config directory", async () => { + const cwd = await gitBootstrap("fixtures/formatter-local-module"); + const actual = await load({ formatter: "./doesnt/exists.js" }, { cwd }); expect(actual).toMatchObject({ - formatter: './doesnt/exists.js', + formatter: "./doesnt/exists.js", extends: [], plugins: {}, rules: {}, }); }); -test('does not mutate config module reference', async () => { - const file = 'config/commitlint.config.js'; - const cwd = await gitBootstrap('fixtures/specify-config-file'); +test("does not mutate config module reference", async () => { + const file = "config/commitlint.config.js"; + const cwd = await gitBootstrap("fixtures/specify-config-file"); const rules = { - 'body-case': [RuleConfigSeverity.Warning, 'never', 'camel-case'] as any, + "body-case": [RuleConfigSeverity.Warning, "never", "camel-case"] as any, }; const configPath = path.join(cwd, file); - const before = readFileSync(configPath, {encoding: 'utf-8'}); - await load({rules}, {cwd, file}); - const after = readFileSync(configPath, {encoding: 'utf-8'}); + const before = readFileSync(configPath, { encoding: "utf-8" }); + await load({ rules }, { cwd, file }); + const after = readFileSync(configPath, { encoding: "utf-8" }); expect(after).toBe(before); }); -test('resolves parser preset from conventional commits', async () => { - const cwd = await npmBootstrap('fixtures/parser-preset-conventionalcommits'); - const actual = await load({}, {cwd}); +test("resolves parser preset from conventional commits", async () => { + const cwd = await npmBootstrap("fixtures/parser-preset-conventionalcommits"); + const actual = await load({}, { cwd }); expect(actual.parserPreset).toBeDefined(); expect(actual.parserPreset!.name).toBe( - 'conventional-changelog-conventionalcommits' + "conventional-changelog-conventionalcommits", ); - expect(typeof actual.parserPreset!.parserOpts).toBe('object'); + expect(typeof actual.parserPreset!.parserOpts).toBe("object"); expect((actual.parserPreset!.parserOpts as any).headerPattern).toEqual( - /^(\w*)(?:\((.*)\))?!?: (.*)$/ + /^(\w*)(?:\((.*)\))?!?: (.*)$/, ); }); -test('resolves parser preset from conventional angular', async () => { - const cwd = await npmBootstrap('fixtures/parser-preset-angular'); - const actual = await load({}, {cwd}); +test("resolves parser preset from conventional angular", async () => { + const cwd = await npmBootstrap("fixtures/parser-preset-angular"); + const actual = await load({}, { cwd }); expect(actual.parserPreset).toBeDefined(); - expect(actual.parserPreset!.name).toBe('conventional-changelog-angular'); - expect(typeof actual.parserPreset!.parserOpts).toBe('object'); + expect(actual.parserPreset!.name).toBe("conventional-changelog-angular"); + expect(typeof actual.parserPreset!.parserOpts).toBe("object"); expect((actual.parserPreset!.parserOpts as any).headerPattern).toEqual( - /^(\w*)(?:\((.*)\))?: (.*)$/ + /^(\w*)(?:\((.*)\))?: (.*)$/, ); }); -test('recursive resolves parser preset from conventional atom', async () => { +test("recursive resolves parser preset from conventional atom", async () => { const cwd = await gitBootstrap( - 'fixtures/recursive-parser-preset-conventional-atom' + "fixtures/recursive-parser-preset-conventional-atom", ); await npm.installModules( - path.resolve(cwd, 'first-extended', 'second-extended') + path.resolve(cwd, "first-extended", "second-extended"), ); - const actual = await load({}, {cwd}); + const actual = await load({}, { cwd }); expect(actual.parserPreset).toBeDefined(); - expect(actual.parserPreset!.name).toBe('conventional-changelog-atom'); - expect(typeof actual.parserPreset!.parserOpts).toBe('object'); + expect(actual.parserPreset!.name).toBe("conventional-changelog-atom"); + expect(typeof actual.parserPreset!.parserOpts).toBe("object"); expect((actual.parserPreset!.parserOpts as any).headerPattern).toEqual( - /^(:.*?:) (.*)$/ + /^(:.*?:) (.*)$/, ); }); -test('resolves parser preset from conventional commits without factory support', async () => { +test("resolves parser preset from conventional commits without factory support", async () => { const cwd = await npmBootstrap( - 'fixtures/parser-preset-conventional-without-factory' + "fixtures/parser-preset-conventional-without-factory", ); - const actual = await load({}, {cwd}); + const actual = await load({}, { cwd }); expect(actual.parserPreset).toBeDefined(); expect(actual.parserPreset!.name).toBe( - 'conventional-changelog-conventionalcommits' + "conventional-changelog-conventionalcommits", ); - expect(typeof actual.parserPreset!.parserOpts).toBe('object'); + expect(typeof actual.parserPreset!.parserOpts).toBe("object"); expect((actual.parserPreset!.parserOpts as any).headerPattern).toEqual( - /^(\w*)(?:\((.*)\))?!?: (.*)$/ + /^(\w*)(?:\((.*)\))?!?: (.*)$/, ); }); -test('helpUrl should be loaded from the shareable config', async () => { - const cwd = await gitBootstrap('fixtures/help-url'); - const actual = await load({}, {cwd}); +test("helpUrl should be loaded from the shareable config", async () => { + const cwd = await gitBootstrap("fixtures/help-url"); + const actual = await load({}, { cwd }); expect(actual.helpUrl).toStrictEqual( - 'https://github.com/conventional-changelog/commitlint' + "https://github.com/conventional-changelog/commitlint", ); }); -test('default helpUrl should be loaded if not provided in shareable configs', async () => { - const cwd = await gitBootstrap('fixtures/basic'); - const actual = await load({}, {cwd}); +test("default helpUrl should be loaded if not provided in shareable configs", async () => { + const cwd = await gitBootstrap("fixtures/basic"); + const actual = await load({}, { cwd }); expect(actual.helpUrl).toStrictEqual( - 'https://github.com/conventional-changelog/commitlint/#what-is-commitlint' + "https://github.com/conventional-changelog/commitlint/#what-is-commitlint", ); }); diff --git a/@commitlint/load/src/load.ts b/@commitlint/load/src/load.ts index 16a08606f0..c20f39f245 100644 --- a/@commitlint/load/src/load.ts +++ b/@commitlint/load/src/load.ts @@ -1,27 +1,27 @@ -import path from 'node:path'; +import path from "node:path"; -import {validateConfig} from '@commitlint/config-validator'; -import executeRule from '@commitlint/execute-rule'; +import { validateConfig } from "@commitlint/config-validator"; +import executeRule from "@commitlint/execute-rule"; import resolveExtends, { resolveFrom, resolveFromSilent, resolveGlobalSilent, loadParserPreset, -} from '@commitlint/resolve-extends'; +} from "@commitlint/resolve-extends"; import { LoadOptions, PluginRecords, QualifiedConfig, QualifiedRules, UserConfig, -} from '@commitlint/types'; -import isPlainObject from 'lodash.isplainobject'; -import merge from 'lodash.merge'; -import uniq from 'lodash.uniq'; +} from "@commitlint/types"; +import isPlainObject from "lodash.isplainobject"; +import merge from "lodash.merge"; +import uniq from "lodash.uniq"; -import {loadConfig} from './utils/load-config.js'; -import {loadParserOpts} from './utils/load-parser-opts.js'; -import loadPlugin from './utils/load-plugin.js'; +import { loadConfig } from "./utils/load-config.js"; +import { loadParserOpts } from "./utils/load-parser-opts.js"; +import loadPlugin from "./utils/load-plugin.js"; /** * formatter should be kept as is when unable to resolve it from config directory @@ -36,15 +36,15 @@ const resolveFormatter = (formatter: string, parent?: string): string => { export default async function load( seed: UserConfig = {}, - options: LoadOptions = {} + options: LoadOptions = {}, ): Promise<QualifiedConfig> { - const cwd = typeof options.cwd === 'undefined' ? process.cwd() : options.cwd; + const cwd = typeof options.cwd === "undefined" ? process.cwd() : options.cwd; const loaded = await loadConfig(cwd, options.file); const baseDirectory = loaded?.filepath ? path.dirname(loaded.filepath) : cwd; const configFilePath = loaded?.filepath; let config: UserConfig = {}; if (loaded) { - validateConfig(loaded.filepath || '', loaded.config); + validateConfig(loaded.filepath || "", loaded.config); config = loaded.config; } @@ -56,14 +56,14 @@ export default async function load( rules: {}, }, config, - seed + seed, ); // Resolve parserPreset key - if (typeof config.parserPreset === 'string') { + if (typeof config.parserPreset === "string") { const resolvedParserPreset = resolveFrom( config.parserPreset, - configFilePath + configFilePath, ); config.parserPreset = { @@ -74,23 +74,23 @@ export default async function load( // Resolve extends key const extended = await resolveExtends(config, { - prefix: 'commitlint-config', + prefix: "commitlint-config", cwd: baseDirectory, parserPreset: await config.parserPreset, }); - if (!extended.formatter || typeof extended.formatter !== 'string') { - extended.formatter = '@commitlint/format'; + if (!extended.formatter || typeof extended.formatter !== "string") { + extended.formatter = "@commitlint/format"; } let plugins: PluginRecords = {}; if (Array.isArray(extended.plugins)) { for (const plugin of uniq(extended.plugins)) { - if (typeof plugin === 'string') { + if (typeof plugin === "string") { plugins = await loadPlugin( plugins, plugin, - process.env.DEBUG === 'true' + process.env.DEBUG === "true", ); } else { plugins.local = plugin; @@ -100,7 +100,7 @@ export default async function load( const rules = ( await Promise.all( - Object.entries(extended.rules || {}).map((entry) => executeRule(entry)) + Object.entries(extended.rules || {}).map((entry) => executeRule(entry)), ) ).reduce<QualifiedRules>((registry, item) => { // type of `item` can be null, but Object.entries always returns key pair @@ -110,11 +110,11 @@ export default async function load( }, {}); const helpUrl = - typeof extended.helpUrl === 'string' + typeof extended.helpUrl === "string" ? extended.helpUrl - : typeof config.helpUrl === 'string' - ? config.helpUrl - : 'https://github.com/conventional-changelog/commitlint/#what-is-commitlint'; + : typeof config.helpUrl === "string" + ? config.helpUrl + : "https://github.com/conventional-changelog/commitlint/#what-is-commitlint"; const prompt = extended.prompt && isPlainObject(extended.prompt) ? extended.prompt : {}; @@ -122,9 +122,9 @@ export default async function load( return { extends: Array.isArray(extended.extends) ? extended.extends - : typeof extended.extends === 'string' - ? [extended.extends] - : [], + : typeof extended.extends === "string" + ? [extended.extends] + : [], // Resolve config-relative formatter module formatter: resolveFormatter(extended.formatter, configFilePath), // Resolve parser-opts from preset @@ -138,4 +138,4 @@ export default async function load( }; } -export {resolveFrom, resolveFromSilent, resolveGlobalSilent}; +export { resolveFrom, resolveFromSilent, resolveGlobalSilent }; diff --git a/@commitlint/load/src/utils/load-config.ts b/@commitlint/load/src/utils/load-config.ts index 97ba7738ed..0db5148ae6 100644 --- a/@commitlint/load/src/utils/load-config.ts +++ b/@commitlint/load/src/utils/load-config.ts @@ -1,13 +1,13 @@ -import {existsSync, readFileSync} from 'node:fs'; -import path from 'node:path'; +import { existsSync, readFileSync } from "node:fs"; +import path from "node:path"; import { cosmiconfig, defaultLoadersSync, type Loader, defaultLoaders, -} from 'cosmiconfig'; -import {TypeScriptLoader} from 'cosmiconfig-typescript-loader'; +} from "cosmiconfig"; +import { TypeScriptLoader } from "cosmiconfig-typescript-loader"; export interface LoadConfigResult { config: unknown; @@ -15,12 +15,12 @@ export interface LoadConfigResult { isEmpty?: boolean; } -const moduleName = 'commitlint'; -const searchStrategy = 'global'; +const moduleName = "commitlint"; +const searchStrategy = "global"; export async function loadConfig( cwd: string, - configPath?: string + configPath?: string, ): Promise<LoadConfigResult | null> { let tsLoaderInstance: Loader | undefined; const tsLoader: Loader = (...args) => { @@ -42,8 +42,8 @@ export async function loadConfig( searchPlaces: [ // cosmiconfig overrides default searchPlaces if any new search place is added (For e.g. `*.ts` files), // we need to manually merge default searchPlaces from https://github.com/davidtheclark/cosmiconfig#searchplaces - 'package.json', - 'package.yaml', + "package.json", + "package.yaml", `.${moduleName}rc`, `.${moduleName}rc.json`, `.${moduleName}rc.yaml`, @@ -62,10 +62,10 @@ export async function loadConfig( `${moduleName}.config.cts`, ], loaders: { - '.ts': tsLoader, - '.cts': tsLoader, - '.cjs': loaders['.cjs'], - '.js': loaders['.js'], + ".ts": tsLoader, + ".cts": tsLoader, + ".cjs": loaders[".cjs"], + ".js": loaders[".js"], }, }); @@ -86,8 +86,8 @@ export async function loadConfig( // - Resolution: https://github.com/nodejs/node/pull/48510 (Node v20.8.0) export const isDynamicAwaitSupported = () => { const [major, minor] = process.version - .replace('v', '') - .split('.') + .replace("v", "") + .split(".") .map((val) => parseInt(val)); return major >= 20 && minor >= 8; @@ -95,12 +95,12 @@ export const isDynamicAwaitSupported = () => { // Is the given directory set up to use ESM (ECMAScript Modules)? export const isEsmModule = (cwd: string) => { - const packagePath = path.join(cwd, 'package.json'); + const packagePath = path.join(cwd, "package.json"); if (!existsSync(packagePath)) { return false; } - const packageJSON = readFileSync(packagePath, {encoding: 'utf-8'}); - return JSON.parse(packageJSON)?.type === 'module'; + const packageJSON = readFileSync(packagePath, { encoding: "utf-8" }); + return JSON.parse(packageJSON)?.type === "module"; }; diff --git a/@commitlint/load/src/utils/load-parser-opts.test.ts b/@commitlint/load/src/utils/load-parser-opts.test.ts index b7e7989d74..2575aa7a14 100644 --- a/@commitlint/load/src/utils/load-parser-opts.test.ts +++ b/@commitlint/load/src/utils/load-parser-opts.test.ts @@ -1,7 +1,7 @@ -import {test, expect} from 'vitest'; -import {loadParserOpts} from './load-parser-opts.js'; +import { test, expect } from "vitest"; +import { loadParserOpts } from "./load-parser-opts.js"; -test('handles a plain preset', async () => { +test("handles a plain preset", async () => { const preset = { parserOpts: {}, }; @@ -9,18 +9,18 @@ test('handles a plain preset', async () => { expect(await loadParserOpts(preset)).toEqual(preset); }); -test('handles primitive values', async () => { - expect(await loadParserOpts('')).toEqual(undefined); +test("handles primitive values", async () => { + expect(await loadParserOpts("")).toEqual(undefined); expect(await loadParserOpts(undefined)).toEqual(undefined); }); -test('handles an object without any parserOpts', async () => { +test("handles an object without any parserOpts", async () => { const preset = {}; expect(await loadParserOpts(preset)).toEqual(preset); }); -test('handles nested parserOpts', async () => { - const opts = {a: 4}; +test("handles nested parserOpts", async () => { + const opts = { a: 4 }; // plain nested parserOpts let loaded = await loadParserOpts({ @@ -28,7 +28,7 @@ test('handles nested parserOpts', async () => { parserOpts: opts, }, }); - expect(loaded).toHaveProperty('parserOpts', opts); + expect(loaded).toHaveProperty("parserOpts", opts); // async nested parserOpts loaded = await loadParserOpts({ @@ -36,10 +36,10 @@ test('handles nested parserOpts', async () => { parserOpts: opts, }), }); - expect(loaded).toHaveProperty('parserOpts', opts); + expect(loaded).toHaveProperty("parserOpts", opts); }); -test('runs a sync function which returns the preset', async () => { +test("runs a sync function which returns the preset", async () => { const preset = {}; const fn = () => preset; const opts = await loadParserOpts(fn); @@ -47,7 +47,7 @@ test('runs a sync function which returns the preset', async () => { expect(opts).toEqual(preset); }); -test('runs an async function which returns the preset', async () => { +test("runs an async function which returns the preset", async () => { const preset = {}; const fn = async () => preset; const opts = await loadParserOpts(fn); diff --git a/@commitlint/load/src/utils/load-parser-opts.ts b/@commitlint/load/src/utils/load-parser-opts.ts index 11bcdcb119..34957e10d4 100644 --- a/@commitlint/load/src/utils/load-parser-opts.ts +++ b/@commitlint/load/src/utils/load-parser-opts.ts @@ -1,19 +1,19 @@ -import {ParserPreset} from '@commitlint/types'; +import { ParserPreset } from "@commitlint/types"; type Awaitable<T> = T | PromiseLike<T>; function isObjectLike(obj: unknown): obj is Record<string, unknown> { - return Boolean(obj) && typeof obj === 'object'; // typeof null === 'object' + return Boolean(obj) && typeof obj === "object"; // typeof null === 'object' } function isParserOptsFunction<T extends ParserPreset>( - obj: T + obj: T, ): obj is T & { parserOpts: ( - cb: (_: never, parserOpts: Record<string, unknown>) => unknown + cb: (_: never, parserOpts: Record<string, unknown>) => unknown, ) => Record<string, unknown> | undefined; } { - return typeof obj.parserOpts === 'function'; + return typeof obj.parserOpts === "function"; } export async function loadParserOpts( @@ -21,13 +21,13 @@ export async function loadParserOpts( | string | Awaitable<ParserPreset> | (() => Awaitable<ParserPreset>) - | undefined + | undefined, ): Promise<ParserPreset | undefined> { - if (typeof pendingParser === 'function') { + if (typeof pendingParser === "function") { return loadParserOpts(pendingParser()); } - if (!pendingParser || typeof pendingParser !== 'object') { + if (!pendingParser || typeof pendingParser !== "object") { return undefined; } // Await for the module, loaded with require @@ -39,7 +39,7 @@ export async function loadParserOpts( } // Pull nested parserOpts, might happen if overwritten with a module in main config - if (typeof parser.parserOpts === 'object') { + if (typeof parser.parserOpts === "object") { // Await parser opts if applicable parser.parserOpts = await parser.parserOpts; if ( @@ -54,8 +54,8 @@ export async function loadParserOpts( // Create parser opts from factory if ( isParserOptsFunction(parser) && - typeof parser.name === 'string' && - parser.name.startsWith('conventional-changelog-') + typeof parser.name === "string" && + parser.name.startsWith("conventional-changelog-") ) { return new Promise((resolve) => { const result = parser.parserOpts((_: never, opts) => { diff --git a/@commitlint/load/src/utils/load-plugin.test.ts b/@commitlint/load/src/utils/load-plugin.test.ts index 59ec7a3b13..cfb0193b85 100644 --- a/@commitlint/load/src/utils/load-plugin.test.ts +++ b/@commitlint/load/src/utils/load-plugin.test.ts @@ -1,116 +1,116 @@ -import {test, expect, vi} from 'vitest'; -import {AsyncRule, Plugin, Rule, SyncRule} from '@commitlint/types'; +import { test, expect, vi } from "vitest"; +import { AsyncRule, Plugin, Rule, SyncRule } from "@commitlint/types"; -import loadPlugin from './load-plugin.js'; +import loadPlugin from "./load-plugin.js"; -vi.mock('commitlint-plugin-example', () => ({example: true})); +vi.mock("commitlint-plugin-example", () => ({ example: true })); -vi.mock('@scope/commitlint-plugin-example', () => ({scope: true})); +vi.mock("@scope/commitlint-plugin-example", () => ({ scope: true })); -vi.mock('commitlint-plugin-rule', (): Plugin => { +vi.mock("commitlint-plugin-rule", (): Plugin => { const rule: Rule<number> = (_parsed, when, _value) => { - return [when === 'never']; + return [when === "never"]; }; - return {rules: {rule}}; + return { rules: { rule } }; }); -vi.mock('commitlint-plugin-sync-rule', (): Plugin => { +vi.mock("commitlint-plugin-sync-rule", (): Plugin => { const syncRule: SyncRule<number> = (_parsed, when, _value) => { - return [when === 'never']; + return [when === "never"]; }; - return {rules: {syncRule}}; + return { rules: { syncRule } }; }); -vi.mock('commitlint-plugin-async-rule', (): Plugin => { +vi.mock("commitlint-plugin-async-rule", (): Plugin => { const asyncRule: AsyncRule<number> = (_parsed, when, _value) => { - return new Promise(() => [when === 'never']); + return new Promise(() => [when === "never"]); }; - return {rules: {asyncRule}}; + return { rules: { asyncRule } }; }); -test('should load a plugin when referenced by short name', async () => { - const plugins = await loadPlugin({}, 'example'); - expect(plugins['example']).toBe( +test("should load a plugin when referenced by short name", async () => { + const plugins = await loadPlugin({}, "example"); + expect(plugins["example"]).toBe( // @ts-expect-error -- mocked module - await import('commitlint-plugin-example') + await import("commitlint-plugin-example"), ); }); -test('should load a plugin when referenced by long name', async () => { - const plugins = await loadPlugin({}, 'commitlint-plugin-example'); - expect(plugins['example']).toBe( +test("should load a plugin when referenced by long name", async () => { + const plugins = await loadPlugin({}, "commitlint-plugin-example"); + expect(plugins["example"]).toBe( // @ts-expect-error -- mocked module - await import('commitlint-plugin-example') + await import("commitlint-plugin-example"), ); }); -test('should load a plugin with a rule', async () => { - const plugins = await loadPlugin({}, 'commitlint-plugin-rule'); - expect(plugins['rule']).toBe( +test("should load a plugin with a rule", async () => { + const plugins = await loadPlugin({}, "commitlint-plugin-rule"); + expect(plugins["rule"]).toBe( // @ts-expect-error -- mocked module - await import('commitlint-plugin-rule') + await import("commitlint-plugin-rule"), ); }); -test('should load a plugin with a sync rule', async () => { - const plugins = await loadPlugin({}, 'commitlint-plugin-sync-rule'); - expect(plugins['sync-rule']).toBe( +test("should load a plugin with a sync rule", async () => { + const plugins = await loadPlugin({}, "commitlint-plugin-sync-rule"); + expect(plugins["sync-rule"]).toBe( // @ts-expect-error -- mocked module - await import('commitlint-plugin-sync-rule') + await import("commitlint-plugin-sync-rule"), ); }); -test('should load a plugin with an async rule', async () => { - const plugins = await loadPlugin({}, 'commitlint-plugin-async-rule'); - expect(plugins['async-rule']).toBe( +test("should load a plugin with an async rule", async () => { + const plugins = await loadPlugin({}, "commitlint-plugin-async-rule"); + expect(plugins["async-rule"]).toBe( // @ts-expect-error -- mocked module - await import('commitlint-plugin-async-rule') + await import("commitlint-plugin-async-rule"), ); }); -test('should throw an error when a plugin has whitespace', async () => { - await expect(() => loadPlugin({}, 'whitespace ')).rejects.toThrow( - "Whitespace found in plugin name 'whitespace '" +test("should throw an error when a plugin has whitespace", async () => { + await expect(() => loadPlugin({}, "whitespace ")).rejects.toThrow( + "Whitespace found in plugin name 'whitespace '", ); - await expect(() => loadPlugin({}, 'whitespace\t')).rejects.toThrow( - 'Whitespace found in plugin name' + await expect(() => loadPlugin({}, "whitespace\t")).rejects.toThrow( + "Whitespace found in plugin name", ); - await expect(() => loadPlugin({}, 'whitespace\n')).rejects.toThrow( - 'Whitespace found in plugin name' + await expect(() => loadPlugin({}, "whitespace\n")).rejects.toThrow( + "Whitespace found in plugin name", ); - await expect(() => loadPlugin({}, 'whitespace\r')).rejects.toThrow( - 'Whitespace found in plugin name' + await expect(() => loadPlugin({}, "whitespace\r")).rejects.toThrow( + "Whitespace found in plugin name", ); }); test("should throw an error when a plugin doesn't exist", () => - expect(() => loadPlugin({}, 'nonexistentplugin')).rejects.toThrow( - 'Failed to load plugin' + expect(() => loadPlugin({}, "nonexistentplugin")).rejects.toThrow( + "Failed to load plugin", )); -test('should load a scoped plugin when referenced by short name', async () => { - const plugins = await loadPlugin({}, '@scope/example'); - expect(plugins['@scope/example']).toBe( +test("should load a scoped plugin when referenced by short name", async () => { + const plugins = await loadPlugin({}, "@scope/example"); + expect(plugins["@scope/example"]).toBe( // @ts-expect-error -- mocked module - await import('@scope/commitlint-plugin-example') + await import("@scope/commitlint-plugin-example"), ); }); -test('should load a scoped plugin when referenced by long name', async () => { - const plugins = await loadPlugin({}, '@scope/commitlint-plugin-example'); - expect(plugins['@scope/example']).toBe( +test("should load a scoped plugin when referenced by long name", async () => { + const plugins = await loadPlugin({}, "@scope/commitlint-plugin-example"); + expect(plugins["@scope/example"]).toBe( // @ts-expect-error -- mocked module - await import('@scope/commitlint-plugin-example') + await import("@scope/commitlint-plugin-example"), ); }); /* when referencing a scope plugin and omitting @scope/ */ test("should load a scoped plugin when referenced by short name, but should not get the plugin if '@scope/' is omitted", async () => { - const plugins = await loadPlugin({}, '@scope/example'); - expect(plugins['example']).toBeUndefined(); + const plugins = await loadPlugin({}, "@scope/example"); + expect(plugins["example"]).toBeUndefined(); }); test("should load a scoped plugin when referenced by long name, but should not get the plugin if '@scope/' is omitted", async () => { - const plugins = await loadPlugin({}, '@scope/commitlint-plugin-example'); - expect(plugins['example']).toBeUndefined(); + const plugins = await loadPlugin({}, "@scope/commitlint-plugin-example"); + expect(plugins["example"]).toBeUndefined(); }); diff --git a/@commitlint/load/src/utils/load-plugin.ts b/@commitlint/load/src/utils/load-plugin.ts index bdaf9f2390..03e2e68e96 100644 --- a/@commitlint/load/src/utils/load-plugin.ts +++ b/@commitlint/load/src/utils/load-plugin.ts @@ -1,28 +1,28 @@ -import {createRequire} from 'node:module'; -import path from 'node:path'; -import {fileURLToPath, pathToFileURL} from 'node:url'; +import { createRequire } from "node:module"; +import path from "node:path"; +import { fileURLToPath, pathToFileURL } from "node:url"; -import {Plugin, PluginRecords} from '@commitlint/types'; -import chalk from 'chalk'; +import { Plugin, PluginRecords } from "@commitlint/types"; +import chalk from "chalk"; -import {normalizePackageName, getShorthandName} from './plugin-naming.js'; -import {WhitespacePluginError, MissingPluginError} from './plugin-errors.js'; +import { normalizePackageName, getShorthandName } from "./plugin-naming.js"; +import { WhitespacePluginError, MissingPluginError } from "./plugin-errors.js"; const require = createRequire(import.meta.url); -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); const dynamicImport = async <T>(id: string): Promise<T> => { const imported = await import( path.isAbsolute(id) ? pathToFileURL(id).toString() : id ); - return ('default' in imported && imported.default) || imported; + return ("default" in imported && imported.default) || imported; }; export default async function loadPlugin( plugins: PluginRecords, pluginName: string, - debug: boolean = false + debug: boolean = false, ): Promise<PluginRecords> { const longName = normalizePackageName(pluginName); const shortName = getShorthandName(longName); @@ -47,10 +47,10 @@ export default async function loadPlugin( // If the plugin can't be resolved, display the missing plugin error (usually a config or install error) console.error(chalk.red(`Failed to load plugin ${longName}.`)); - const message = error?.message || 'Unknown error occurred'; + const message = error?.message || "Unknown error occurred"; throw new MissingPluginError(pluginName, message, { pluginName: longName, - commitlintPath: path.resolve(__dirname, '../..'), + commitlintPath: path.resolve(__dirname, "../.."), }); } @@ -76,8 +76,8 @@ export default async function loadPlugin( console.log( chalk.blue( - `Loaded plugin ${pluginName} (${loadedPluginAndVersion}) (from ${resolvedPath})` - ) + `Loaded plugin ${pluginName} (${loadedPluginAndVersion}) (from ${resolvedPath})`, + ), ); } diff --git a/@commitlint/load/src/utils/plugin-errors.ts b/@commitlint/load/src/utils/plugin-errors.ts index 4c7b1f0e29..2f1036ec80 100644 --- a/@commitlint/load/src/utils/plugin-errors.ts +++ b/@commitlint/load/src/utils/plugin-errors.ts @@ -1,7 +1,7 @@ export class WhitespacePluginError extends Error { __proto__ = Error; - public messageTemplate: string = 'whitespace-found'; + public messageTemplate: string = "whitespace-found"; public messageData: any = {}; constructor(pluginName?: string, data: any = {}) { @@ -16,10 +16,10 @@ export class WhitespacePluginError extends Error { export class MissingPluginError extends Error { __proto__ = Error; - public messageTemplate: string = 'plugin-missing'; + public messageTemplate: string = "plugin-missing"; public messageData: any; - constructor(pluginName?: string, errorMessage: string = '', data: any = {}) { + constructor(pluginName?: string, errorMessage: string = "", data: any = {}) { super(`Failed to load plugin ${pluginName}: ${errorMessage}`); this.messageData = data; diff --git a/@commitlint/load/src/utils/plugin-naming.ts b/@commitlint/load/src/utils/plugin-naming.ts index 17cf43ed5d..9ec5254eff 100644 --- a/@commitlint/load/src/utils/plugin-naming.ts +++ b/@commitlint/load/src/utils/plugin-naming.ts @@ -1,14 +1,14 @@ -import path from 'node:path'; +import path from "node:path"; // largely adapted from eslint's plugin system const NAMESPACE_REGEX = /^@.*\//u; // In eslint this is a parameter - we don't need to support the extra options -const prefix = 'commitlint-plugin'; +const prefix = "commitlint-plugin"; // Replace Windows with posix style paths function convertPathToPosix(filepath: string) { const normalizedFilepath = path.normalize(filepath); - const posixFilepath = normalizedFilepath.replace(/\\/gu, '/'); + const posixFilepath = normalizedFilepath.replace(/\\/gu, "/"); return posixFilepath; } @@ -27,34 +27,34 @@ export function normalizePackageName(name: string) { * Normalize to Unix first to avoid errors later on. * https://github.com/eslint/eslint/issues/5644 */ - if (normalizedName.indexOf('\\') > -1) { + if (normalizedName.indexOf("\\") > -1) { normalizedName = convertPathToPosix(normalizedName); } - if (normalizedName.charAt(0) === '@') { + if (normalizedName.charAt(0) === "@") { /** * it's a scoped package * package name is the prefix, or just a username */ const scopedPackageShortcutRegex = new RegExp( `^(@[^/]+)(?:/(?:${prefix})?)?$`, - 'u' + "u", ), - scopedPackageNameRegex = new RegExp(`^${prefix}(?:-|$)`, 'u'); + scopedPackageNameRegex = new RegExp(`^${prefix}(?:-|$)`, "u"); if (scopedPackageShortcutRegex.test(normalizedName)) { normalizedName = normalizedName.replace( scopedPackageShortcutRegex, - `$1/${prefix}` + `$1/${prefix}`, ); - } else if (!scopedPackageNameRegex.test(normalizedName.split('/')[1])) { + } else if (!scopedPackageNameRegex.test(normalizedName.split("/")[1])) { /** * for scoped packages, insert the prefix after the first / unless * the path is already @scope/eslint or @scope/eslint-xxx-yyy */ normalizedName = normalizedName.replace( /^@([^/]+)\/(.*)$/u, - `@$1/${prefix}-$2` + `@$1/${prefix}-$2`, ); } } else if (normalizedName.indexOf(`${prefix}-`) !== 0) { @@ -70,14 +70,14 @@ export function normalizePackageName(name: string) { * @returns {string} The term without prefix. */ export function getShorthandName(fullname: string) { - if (fullname[0] === '@') { - let matchResult = new RegExp(`^(@[^/]+)/${prefix}$`, 'u').exec(fullname); + if (fullname[0] === "@") { + let matchResult = new RegExp(`^(@[^/]+)/${prefix}$`, "u").exec(fullname); if (matchResult) { return matchResult[1]; } - matchResult = new RegExp(`^(@[^/]+)/${prefix}-(.+)$`, 'u').exec(fullname); + matchResult = new RegExp(`^(@[^/]+)/${prefix}-(.+)$`, "u").exec(fullname); if (matchResult) { return `${matchResult[1]}/${matchResult[2]}`; } @@ -96,5 +96,5 @@ export function getShorthandName(fullname: string) { export function getNamespaceFromTerm(term: string) { const match = NAMESPACE_REGEX.exec(term); - return match ? match[0] : ''; + return match ? match[0] : ""; } diff --git a/@commitlint/load/tsconfig.json b/@commitlint/load/tsconfig.json index 1b645658c1..7ce5e84e02 100644 --- a/@commitlint/load/tsconfig.json +++ b/@commitlint/load/tsconfig.json @@ -8,9 +8,9 @@ "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], "references": [ - {"path": "../execute-rule"}, - {"path": "../resolve-extends"}, - {"path": "../config-validator"}, - {"path": "../types"} + { "path": "../execute-rule" }, + { "path": "../resolve-extends" }, + { "path": "../config-validator" }, + { "path": "../types" } ] } diff --git a/@commitlint/message/src/index.test.ts b/@commitlint/message/src/index.test.ts index 1baa149d66..acfcb49273 100644 --- a/@commitlint/message/src/index.test.ts +++ b/@commitlint/message/src/index.test.ts @@ -1,17 +1,17 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import message from './index.js'; +import message from "./index.js"; -test('should return an empty string for empty input', () => { - expect(message()).toBe(''); +test("should return an empty string for empty input", () => { + expect(message()).toBe(""); }); -test('should return an empty string for empty input array', () => { - expect(message([])).toBe(''); +test("should return an empty string for empty input array", () => { + expect(message([])).toBe(""); }); -test('should filter falsy values', () => { - expect(message([null, 'some', undefined, 'message', null])).toBe( - 'some message' +test("should filter falsy values", () => { + expect(message([null, "some", undefined, "message", null])).toBe( + "some message", ); }); diff --git a/@commitlint/message/src/index.ts b/@commitlint/message/src/index.ts index 32b2b00c81..c329f09917 100644 --- a/@commitlint/message/src/index.ts +++ b/@commitlint/message/src/index.ts @@ -1,3 +1,3 @@ export default function message(input: (string | null | undefined)[] = []) { - return input.filter(Boolean).join(' '); + return input.filter(Boolean).join(" "); } diff --git a/@commitlint/parse/README.md b/@commitlint/parse/README.md index be40697885..8021452469 100644 --- a/@commitlint/parse/README.md +++ b/@commitlint/parse/README.md @@ -11,7 +11,7 @@ npm install --save @commitlint/parse ## Use ```js -const parse = require('@commitlint/parse'); +const parse = require("@commitlint/parse"); ``` ## API diff --git a/@commitlint/parse/src/index.test.ts b/@commitlint/parse/src/index.test.ts index cdf82b2dda..8fb892f37c 100644 --- a/@commitlint/parse/src/index.test.ts +++ b/@commitlint/parse/src/index.test.ts @@ -1,23 +1,23 @@ -import {test, expect} from 'vitest'; -import parse from './index.js'; +import { test, expect } from "vitest"; +import parse from "./index.js"; -test('throws when called without params', async () => { - await expect((parse as any)()).rejects.toThrow('Expected a raw commit'); +test("throws when called without params", async () => { + await expect((parse as any)()).rejects.toThrow("Expected a raw commit"); }); -test('throws when called with empty message', async () => { - await expect(parse('')).rejects.toThrow('Expected a raw commit'); +test("throws when called with empty message", async () => { + await expect(parse("")).rejects.toThrow("Expected a raw commit"); }); -test('returns object with raw message', async () => { - const message = 'type(scope): subject'; +test("returns object with raw message", async () => { + const message = "type(scope): subject"; const actual = await parse(message); - expect(actual).toHaveProperty('raw', message); + expect(actual).toHaveProperty("raw", message); }); -test('calls parser with message and passed options', async () => { - const message = 'message'; +test("calls parser with message and passed options", async () => { + const message = "message"; expect.assertions(1); await parse(message, (m: string): any => { @@ -26,25 +26,25 @@ test('calls parser with message and passed options', async () => { }); }); -test('passes object up from parser function', async () => { - const message = 'message'; +test("passes object up from parser function", async () => { + const message = "message"; const result: any = {}; const actual = await parse(message, () => result); expect(actual).toBe(result); }); -test('returns object with expected keys', async () => { - const message = 'message'; +test("returns object with expected keys", async () => { + const message = "message"; const actual = await parse(message); const expected = { body: null, footer: null, - header: 'message', + header: "message", mentions: [], merge: null, notes: [], - raw: 'message', + raw: "message", references: [], revert: null, scope: null, @@ -55,29 +55,29 @@ test('returns object with expected keys', async () => { expect(actual).toMatchObject(expected); }); -test('uses angular grammar', async () => { - const message = 'type(scope): subject'; +test("uses angular grammar", async () => { + const message = "type(scope): subject"; const actual = await parse(message); const expected = { body: null, footer: null, - header: 'type(scope): subject', + header: "type(scope): subject", mentions: [], merge: null, notes: [], - raw: 'type(scope): subject', + raw: "type(scope): subject", references: [], revert: null, - scope: 'scope', - subject: 'subject', - type: 'type', + scope: "scope", + subject: "subject", + type: "type", }; expect(actual).toMatchObject(expected); }); -test('uses custom opts parser', async () => { - const message = 'type(scope)-subject'; +test("uses custom opts parser", async () => { + const message = "type(scope)-subject"; const changelogOpts = { parserOpts: { headerPattern: /^(\w*)(?:\((.*)\))?-(.*)$/, @@ -87,112 +87,112 @@ test('uses custom opts parser', async () => { const expected = { body: null, footer: null, - header: 'type(scope)-subject', + header: "type(scope)-subject", mentions: [], merge: null, notes: [], - raw: 'type(scope)-subject', + raw: "type(scope)-subject", references: [], revert: null, - scope: 'scope', - subject: 'subject', - type: 'type', + scope: "scope", + subject: "subject", + type: "type", }; expect(actual).toMatchObject(expected); }); -test('does not merge array properties with custom opts', async () => { - const message = 'type: subject'; +test("does not merge array properties with custom opts", async () => { + const message = "type: subject"; const actual = await parse(message, undefined, { headerPattern: /^(.*):\s(.*)$/, - headerCorrespondence: ['type', 'subject'], + headerCorrespondence: ["type", "subject"], }); const expected = { body: null, footer: null, - header: 'type: subject', + header: "type: subject", mentions: [], merge: null, notes: [], - raw: 'type: subject', + raw: "type: subject", references: [], revert: null, - subject: 'subject', - type: 'type', + subject: "subject", + type: "type", }; expect(actual).toMatchObject(expected); }); -test('supports scopes with /', async () => { - const message = 'type(some/scope): subject'; +test("supports scopes with /", async () => { + const message = "type(some/scope): subject"; const actual = await parse(message); - expect(actual.scope).toBe('some/scope'); - expect(actual.subject).toBe('subject'); + expect(actual.scope).toBe("some/scope"); + expect(actual.subject).toBe("subject"); }); -test('supports scopes with / and empty parserOpts', async () => { - const message = 'type(some/scope): subject'; +test("supports scopes with / and empty parserOpts", async () => { + const message = "type(some/scope): subject"; const actual = await parse(message, undefined, {}); - expect(actual.scope).toBe('some/scope'); - expect(actual.subject).toBe('subject'); + expect(actual.scope).toBe("some/scope"); + expect(actual.subject).toBe("subject"); }); -test('ignores comments', async () => { - const message = 'type(some/scope): subject\n# some comment'; +test("ignores comments", async () => { + const message = "type(some/scope): subject\n# some comment"; // @ts-expect-error -- no typings - const changelogOpts = await import('conventional-changelog-angular'); + const changelogOpts = await import("conventional-changelog-angular"); const opts = { ...changelogOpts.parserOpts, - commentChar: '#', + commentChar: "#", }; const actual = await parse(message, undefined, opts); expect(actual.body).toBe(null); expect(actual.footer).toBe(null); - expect(actual.subject).toBe('subject'); + expect(actual.subject).toBe("subject"); }); -test('registers inline #', async () => { +test("registers inline #", async () => { const message = - 'type(some/scope): subject #reference\n# some comment\nthings #reference'; + "type(some/scope): subject #reference\n# some comment\nthings #reference"; // @ts-expect-error -- no typings - const changelogOpts = await import('conventional-changelog-angular'); + const changelogOpts = await import("conventional-changelog-angular"); const opts = { ...changelogOpts.parserOpts, - commentChar: '#', + commentChar: "#", }; const actual = await parse(message, undefined, opts); - expect(actual.subject).toBe('subject #reference'); - expect(actual.body).toBe('things #reference'); + expect(actual.subject).toBe("subject #reference"); + expect(actual.body).toBe("things #reference"); }); -test('keep -side notes- in the body section', async () => { - const header = 'type(some/scope): subject'; +test("keep -side notes- in the body section", async () => { + const header = "type(some/scope): subject"; const body = - 'CI on master branch caught this:\n\n' + - '```\n' + - 'Unhandled Exception:\n' + + "CI on master branch caught this:\n\n" + + "```\n" + + "Unhandled Exception:\n" + "System.AggregateException: One or more errors occurred. (Some problem when connecting to 'api.mycryptoapi.com/eth')\n\n" + - '--- End of stack trace from previous location where exception was thrown ---\n\n' + - 'at GWallet.Backend.FSharpUtil.ReRaise (System.Exception ex) [0x00000] in /Users/runner/work/geewallet/geewallet/src/GWallet.Backend/FSharpUtil.fs:206\n' + - '...\n' + - '```'; + "--- End of stack trace from previous location where exception was thrown ---\n\n" + + "at GWallet.Backend.FSharpUtil.ReRaise (System.Exception ex) [0x00000] in /Users/runner/work/geewallet/geewallet/src/GWallet.Backend/FSharpUtil.fs:206\n" + + "...\n" + + "```"; - const message = header + '\n\n' + body; + const message = header + "\n\n" + body; const actual = await parse(message); expect(actual.body).toBe(body); }); -test('allows separating -side nodes- by setting parserOpts.fieldPattern', async () => { +test("allows separating -side nodes- by setting parserOpts.fieldPattern", async () => { const message = - 'type(scope): subject\n\nbody text\n-authorName-\nrenovate[bot]'; + "type(scope): subject\n\nbody text\n-authorName-\nrenovate[bot]"; const changelogOpts = { parserOpts: { fieldPattern: /^-(.*)-$/, @@ -200,54 +200,54 @@ test('allows separating -side nodes- by setting parserOpts.fieldPattern', async }; const actual = await parse(message, undefined, changelogOpts.parserOpts); - expect(actual.body).toBe('body text'); - expect(actual).toHaveProperty('authorName', 'renovate[bot]'); + expect(actual.body).toBe("body text"); + expect(actual).toHaveProperty("authorName", "renovate[bot]"); }); -test('parses references leading subject', async () => { - const message = '#1 some subject'; +test("parses references leading subject", async () => { + const message = "#1 some subject"; // @ts-expect-error -- no typings - const opts = await import('conventional-changelog-angular'); + const opts = await import("conventional-changelog-angular"); const { references: [actual], } = await parse(message, undefined, opts); - expect(actual.issue).toBe('1'); + expect(actual.issue).toBe("1"); }); -test('parses custom references', async () => { - const message = '#1 some subject PREFIX-2'; - const {references} = await parse(message, undefined, { - issuePrefixes: ['PREFIX-'], +test("parses custom references", async () => { + const message = "#1 some subject PREFIX-2"; + const { references } = await parse(message, undefined, { + issuePrefixes: ["PREFIX-"], }); - expect(references.find((ref) => ref.issue === '1')).toBeFalsy(); - expect(references.find((ref) => ref.issue === '2')).toMatchObject({ + expect(references.find((ref) => ref.issue === "1")).toBeFalsy(); + expect(references.find((ref) => ref.issue === "2")).toMatchObject({ action: null, - issue: '2', + issue: "2", owner: null, - prefix: 'PREFIX-', - raw: '#1 some subject PREFIX-2', + prefix: "PREFIX-", + raw: "#1 some subject PREFIX-2", repository: null, }); }); -test('uses permissive default regex without parser opts', async () => { - const message = 'chore(component,demo): bump'; +test("uses permissive default regex without parser opts", async () => { + const message = "chore(component,demo): bump"; const actual = await parse(message); - expect(actual.scope).toBe('component,demo'); + expect(actual.scope).toBe("component,demo"); }); -test('uses permissive default regex with other parser opts', async () => { - const message = 'chore(component,demo): bump'; - const actual = await parse(message, undefined, {commentChar: '#'}); +test("uses permissive default regex with other parser opts", async () => { + const message = "chore(component,demo): bump"; + const actual = await parse(message, undefined, { commentChar: "#" }); - expect(actual.scope).toBe('component,demo'); + expect(actual.scope).toBe("component,demo"); }); -test('uses restrictive default regex in passed parser opts', async () => { - const message = 'chore(component,demo): bump'; +test("uses restrictive default regex in passed parser opts", async () => { + const message = "chore(component,demo): bump"; const actual = await parse(message, undefined, { headerPattern: /^(\w*)(?:\(([a-z]*)\))?: (.*)$/, }); @@ -256,16 +256,16 @@ test('uses restrictive default regex in passed parser opts', async () => { expect(actual.scope).toBe(null); }); -test('works with chinese scope by default', async () => { - const message = 'fix(面试评价): 测试'; - const actual = await parse(message, undefined, {commentChar: '#'}); +test("works with chinese scope by default", async () => { + const message = "fix(面试评价): 测试"; + const actual = await parse(message, undefined, { commentChar: "#" }); expect(actual.subject).not.toBe(null); expect(actual.scope).not.toBe(null); }); -test('does not work with chinese scopes with incompatible pattern', async () => { - const message = 'fix(面试评价): 测试'; +test("does not work with chinese scopes with incompatible pattern", async () => { + const message = "fix(面试评价): 测试"; const actual = await parse(message, undefined, { headerPattern: /^(\w*)(?:\(([a-z]*)\))?: (.*)$/, }); diff --git a/@commitlint/parse/src/index.ts b/@commitlint/parse/src/index.ts index 7490fc88ec..86173827a7 100644 --- a/@commitlint/parse/src/index.ts +++ b/@commitlint/parse/src/index.ts @@ -1,13 +1,13 @@ -import type {Parser} from '@commitlint/types'; +import type { Parser } from "@commitlint/types"; -import {type Commit, type Options, sync} from 'conventional-commits-parser'; +import { type Commit, type Options, sync } from "conventional-commits-parser"; // @ts-expect-error -- no typings -import defaultChangelogOpts from 'conventional-changelog-angular'; +import defaultChangelogOpts from "conventional-changelog-angular"; export async function parse( message: string, parser: Parser = sync, - parserOpts?: Options + parserOpts?: Options, ): Promise<Commit> { const preset = await defaultChangelogOpts(); const defaultOpts = preset.parserOpts; diff --git a/@commitlint/parse/tsconfig.json b/@commitlint/parse/tsconfig.json index 119e645565..d691164788 100644 --- a/@commitlint/parse/tsconfig.json +++ b/@commitlint/parse/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../types"}] + "references": [{ "path": "../types" }] } diff --git a/@commitlint/prompt-cli/cli.js b/@commitlint/prompt-cli/cli.js index 155819526e..7ab4aa8181 100755 --- a/@commitlint/prompt-cli/cli.js +++ b/@commitlint/prompt-cli/cli.js @@ -1,7 +1,7 @@ #!/usr/bin/env node -import {prompter} from '@commitlint/prompt'; -import inquirer from 'inquirer'; -import {x} from 'tinyexec'; +import { prompter } from "@commitlint/prompt"; +import inquirer from "inquirer"; +import { x } from "tinyexec"; main().catch((err) => { setTimeout(() => { @@ -14,7 +14,7 @@ function main() { .then((empty) => { if (empty) { console.log( - `Nothing to commit. Stage your changes via "git add" execute "commit" again` + `Nothing to commit. Stage your changes via "git add" execute "commit" again`, ); process.exit(1); } @@ -23,11 +23,11 @@ function main() { } function isStageEmpty() { - return x('git', ['diff', '--cached']).then((r) => r.stdout === ''); + return x("git", ["diff", "--cached"]).then((r) => r.stdout === ""); } function commit(message) { - const result = x('git', ['commit', '-m', message]); + const result = x("git", ["commit", "-m", message]); result.process.stdout.pipe(process.stdout); result.process.stderr.pipe(process.stderr); } diff --git a/@commitlint/prompt-cli/cli.test.js b/@commitlint/prompt-cli/cli.test.js index 787fc47dcc..d1bfc50283 100644 --- a/@commitlint/prompt-cli/cli.test.js +++ b/@commitlint/prompt-cli/cli.test.js @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import {createRequire} from 'node:module'; -import {git} from '@commitlint/test'; -import {x} from 'tinyexec'; +import { test, expect } from "vitest"; +import { createRequire } from "node:module"; +import { git } from "@commitlint/test"; +import { x } from "tinyexec"; const require = createRequire(import.meta.url); -const bin = require.resolve('./cli.js'); +const bin = require.resolve("./cli.js"); const cli = (args, options) => { - return (input = '') => { + return (input = "") => { const result = x(bin, args, { nodeOptions: { cwd: options.cwd, @@ -23,9 +23,9 @@ const cli = (args, options) => { }; }; -test('should print warning if stage is empty', async () => { +test("should print warning if stage is empty", async () => { const cwd = await git.bootstrap(); - const actual = await cli([], {cwd})('foo: bar'); - expect(actual.stdout).toContain('Nothing to commit.'); - expect(actual.stderr).toBe(''); + const actual = await cli([], { cwd })("foo: bar"); + expect(actual.stdout).toContain("Nothing to commit."); + expect(actual.stderr).toBe(""); }, 10000); diff --git a/@commitlint/prompt/src/index.ts b/@commitlint/prompt/src/index.ts index 22f3145c88..2985ec0fc6 100644 --- a/@commitlint/prompt/src/index.ts +++ b/@commitlint/prompt/src/index.ts @@ -1,6 +1,6 @@ -import inquirer from 'inquirer'; +import inquirer from "inquirer"; -import {input} from './input.js'; +import { input } from "./input.js"; type Commit = (input: string) => void; diff --git a/@commitlint/prompt/src/input.test.ts b/@commitlint/prompt/src/input.test.ts index 7b9cb5dfe6..20d3e9572a 100644 --- a/@commitlint/prompt/src/input.test.ts +++ b/@commitlint/prompt/src/input.test.ts @@ -1,17 +1,17 @@ /// <reference path="./inquirer/inquirer.d.ts" /> -import {expect, test, vi} from 'vitest'; +import { expect, test, vi } from "vitest"; // @ts-expect-error -- no typings -import config from '@commitlint/config-angular'; -import chalk from 'chalk'; +import config from "@commitlint/config-angular"; +import chalk from "chalk"; import { Answers, DistinctQuestion, InputCustomOptions, PromptModule, -} from 'inquirer'; +} from "inquirer"; -import {input} from './input.js'; +import { input } from "./input.js"; const testConfig = { parserPreset: config.parserPreset, @@ -20,86 +20,86 @@ const testConfig = { }, }; -vi.mock('@commitlint/load', () => ({ +vi.mock("@commitlint/load", () => ({ default: () => testConfig, })); -test('should work with all fields filled', async () => { +test("should work with all fields filled", async () => { const prompt = stub({ - 'input-custom': { - type: 'fix', - scope: 'test', - subject: 'subject', - body: 'body', - footer: 'footer', + "input-custom": { + type: "fix", + scope: "test", + subject: "subject", + body: "body", + footer: "footer", }, }); const message = await input(prompt); - expect(message).toEqual('fix(test): subject\n' + '\nbody\n' + '\nfooter'); + expect(message).toEqual("fix(test): subject\n" + "\nbody\n" + "\nfooter"); }); -test('should not add leading blank line to body and footer if rules are disabled', async () => { - testConfig.rules['body-leading-blank'] = ['1', 'never']; - testConfig.rules['footer-leading-blank'] = ['1', 'never']; +test("should not add leading blank line to body and footer if rules are disabled", async () => { + testConfig.rules["body-leading-blank"] = ["1", "never"]; + testConfig.rules["footer-leading-blank"] = ["1", "never"]; const prompt = stub({ - 'input-custom': { - type: 'fix', - scope: 'test', - subject: 'subject', - body: 'body', - footer: 'footer', + "input-custom": { + type: "fix", + scope: "test", + subject: "subject", + body: "body", + footer: "footer", }, }); const message = await input(prompt); - expect(message).toEqual('fix(test): subject\n' + 'body\n' + 'footer'); + expect(message).toEqual("fix(test): subject\n" + "body\n" + "footer"); // reset config mock - testConfig.rules['body-leading-blank'] = config.rules['body-leading-blank']; - testConfig.rules['footer-leading-blank'] = - config.rules['footer-leading-blank']; + testConfig.rules["body-leading-blank"] = config.rules["body-leading-blank"]; + testConfig.rules["footer-leading-blank"] = + config.rules["footer-leading-blank"]; }); -test('should work without scope', async () => { +test("should work without scope", async () => { const prompt = stub({ - 'input-custom': { - type: 'fix', - scope: '', - subject: 'subject', - body: 'body', - footer: 'footer', + "input-custom": { + type: "fix", + scope: "", + subject: "subject", + body: "body", + footer: "footer", }, }); const message = await input(prompt); - expect(message).toEqual('fix: subject\n' + '\nbody\n' + '\nfooter'); + expect(message).toEqual("fix: subject\n" + "\nbody\n" + "\nfooter"); }); -test('should fail without type', async () => { - const spy = vi.spyOn(console, 'error'); +test("should fail without type", async () => { + const spy = vi.spyOn(console, "error"); const prompt = stub({ - 'input-custom': { - type: '', - scope: '', - subject: '', - body: '', - footer: '', + "input-custom": { + type: "", + scope: "", + subject: "", + body: "", + footer: "", }, }); const message = await input(prompt); - expect(message).toEqual(''); + expect(message).toEqual(""); expect(console.error).toHaveBeenCalledTimes(1); expect(console.error).toHaveBeenLastCalledWith( - new Error(`⚠ ${chalk.bold('type')} may not be empty.`) + new Error(`⚠ ${chalk.bold("type")} may not be empty.`), ); spy.mockRestore(); }); function stub(config: Record<string, Record<string, unknown>>): PromptModule { const prompt = async ( - questions: DistinctQuestion | DistinctQuestion[] + questions: DistinctQuestion | DistinctQuestion[], ): Promise<any> => { const result: Answers = {}; const resolvedConfig = Array.isArray(questions) ? questions : [questions]; for (const promptConfig of resolvedConfig) { - const configType = promptConfig.type || 'input'; + const configType = promptConfig.type || "input"; const questions = config[configType]; if (!questions) { throw new Error(`Unexpected config type: ${configType}`); diff --git a/@commitlint/prompt/src/input.ts b/@commitlint/prompt/src/input.ts index d0bbfe90e2..d2db897fe2 100644 --- a/@commitlint/prompt/src/input.ts +++ b/@commitlint/prompt/src/input.ts @@ -1,12 +1,12 @@ -import load from '@commitlint/load'; -import type {DistinctQuestion, PromptModule} from 'inquirer'; +import load from "@commitlint/load"; +import type { DistinctQuestion, PromptModule } from "inquirer"; -import format from './library/format.js'; -import getPrompt from './library/get-prompt.js'; -import settings from './settings.js'; -import type {InputSetting, Result} from './library/types.js'; -import {getHasName, getMaxLength, getRules} from './library/utils.js'; -import InputCustomPrompt from './inquirer/InputCustomPrompt.js'; +import format from "./library/format.js"; +import getPrompt from "./library/get-prompt.js"; +import settings from "./settings.js"; +import type { InputSetting, Result } from "./library/types.js"; +import { getHasName, getMaxLength, getRules } from "./library/utils.js"; +import InputCustomPrompt from "./inquirer/InputCustomPrompt.js"; /** * Get user input by interactive prompt based on @@ -15,18 +15,18 @@ import InputCustomPrompt from './inquirer/InputCustomPrompt.js'; * @return commit message */ export async function input(prompter: PromptModule): Promise<string> { - const {rules} = await load(); - const parts = ['type', 'scope', 'subject', 'body', 'footer'] as const; - const headerParts = ['type', 'scope', 'subject']; + const { rules } = await load(); + const parts = ["type", "scope", "subject", "body", "footer"] as const; + const headerParts = ["type", "scope", "subject"]; - const headerLengthRule = getRules('header', rules).find( - getHasName('max-length') + const headerLengthRule = getRules("header", rules).find( + getHasName("max-length"), ); const maxLength = getMaxLength(headerLengthRule); try { const questions: DistinctQuestion<Result>[] = []; - prompter.registerPrompt('input-custom', InputCustomPrompt); + prompter.registerPrompt("input-custom", InputCustomPrompt); for (const input of parts) { const inputSetting: InputSetting = settings[input]; @@ -46,6 +46,6 @@ export async function input(prompter: PromptModule): Promise<string> { return format(results); } catch (err) { console.error(err); - return ''; + return ""; } } diff --git a/@commitlint/prompt/src/inquirer/InputCustomPrompt.ts b/@commitlint/prompt/src/inquirer/InputCustomPrompt.ts index 05ed36c214..2cc7ce8400 100644 --- a/@commitlint/prompt/src/inquirer/InputCustomPrompt.ts +++ b/@commitlint/prompt/src/inquirer/InputCustomPrompt.ts @@ -1,11 +1,11 @@ /// <reference path="./inquirer.d.ts" /> -import chalk from 'chalk'; +import chalk from "chalk"; -import inquirer, {type Answers, type InputCustomOptions} from 'inquirer'; -import InputPrompt from 'inquirer/lib/prompts/input.js'; -import observe from 'inquirer/lib/utils/events.js'; -import type {Interface as ReadlineInterface, Key} from 'node:readline'; -import type {Subscription} from 'rxjs'; +import inquirer, { type Answers, type InputCustomOptions } from "inquirer"; +import InputPrompt from "inquirer/lib/prompts/input.js"; +import observe from "inquirer/lib/utils/events.js"; +import type { Interface as ReadlineInterface, Key } from "node:readline"; +import type { Subscription } from "rxjs"; import SuccessfulPromptStateData = inquirer.prompts.SuccessfulPromptStateData; @@ -15,7 +15,7 @@ interface KeyDescriptor { } export default class InputCustomPrompt< - TQuestion extends InputCustomOptions = InputCustomOptions + TQuestion extends InputCustomOptions = InputCustomOptions, > extends InputPrompt<TQuestion> { private lineSubscription: Subscription; private readonly tabCompletion: string[]; @@ -23,7 +23,7 @@ export default class InputCustomPrompt< constructor( question: TQuestion, readLine: ReadlineInterface, - answers: Answers + answers: Answers, ) { super(question, readLine, answers); @@ -32,12 +32,12 @@ export default class InputCustomPrompt< } if (!this.opt.maxLength) { - this.throwParamError('maxLength'); + this.throwParamError("maxLength"); } const events = observe(this.rl); this.lineSubscription = events.keypress.subscribe( - this.onKeyPress2.bind(this) + this.onKeyPress2.bind(this), ); this.tabCompletion = (this.opt.tabCompletion || []) .map((item) => item.value) @@ -56,13 +56,13 @@ export default class InputCustomPrompt< * @see https://nodejs.org/api/readline.html#readline_rl_line */ updateLine(line: string): void { - this.rl.write(null as any, {ctrl: true, name: 'b'}); - this.rl.write(null as any, {ctrl: true, name: 'd'}); + this.rl.write(null as any, { ctrl: true, name: "b" }); + this.rl.write(null as any, { ctrl: true, name: "d" }); this.rl.write(line.substr(this.rl.line.length)); } onKeyPress2(e: KeyDescriptor): void { - if (e.key.name === 'tab' && this.tabCompletion.length > 0) { + if (e.key.name === "tab" && this.tabCompletion.length > 0) { let line = this.rl.line.trim(); if (line.length > 0) { for (const item of this.tabCompletion) { @@ -84,7 +84,7 @@ export default class InputCustomPrompt< } render(error?: string): void { - const answered = this.status === 'answered'; + const answered = this.status === "answered"; let message = this.getQuestion(); const length = this.measureInput(this.rl.line); @@ -95,10 +95,10 @@ export default class InputCustomPrompt< message += this.opt.transformer(this.rl.line, this.answers, {}); } - let bottomContent = ''; + let bottomContent = ""; if (error) { - bottomContent = chalk.red('>> ') + error; + bottomContent = chalk.red(">> ") + error; } else if (!answered) { const maxLength = this.opt.maxLength(this.answers); if (maxLength < Infinity) { @@ -107,8 +107,8 @@ export default class InputCustomPrompt< lengthRemaining <= 5 ? chalk.red : lengthRemaining <= 10 - ? chalk.yellow - : chalk.grey; + ? chalk.yellow + : chalk.grey; bottomContent = color(`${lengthRemaining} characters left`); } } diff --git a/@commitlint/prompt/src/inquirer/inquirer.d.ts b/@commitlint/prompt/src/inquirer/inquirer.d.ts index 98af94d2a7..1d8df10d5f 100644 --- a/@commitlint/prompt/src/inquirer/inquirer.d.ts +++ b/@commitlint/prompt/src/inquirer/inquirer.d.ts @@ -1,6 +1,6 @@ -import {Answers, InputQuestionOptions} from 'inquirer'; +import { Answers, InputQuestionOptions } from "inquirer"; -declare module 'inquirer' { +declare module "inquirer" { interface InputCustomCompletionOption { value: string; description?: string; @@ -11,7 +11,7 @@ declare module 'inquirer' { /** * @inheritdoc */ - type?: 'input-custom'; + type?: "input-custom"; log?(answers?: T): string; tabCompletion?: InputCustomCompletionOption[]; maxLength(answers?: T): number; @@ -19,6 +19,6 @@ declare module 'inquirer' { } interface QuestionMap<T extends Answers = Answers> { - 'input-custom': InputCustomOptions<T>; + "input-custom": InputCustomOptions<T>; } } diff --git a/@commitlint/prompt/src/library/format.test.ts b/@commitlint/prompt/src/library/format.test.ts index bd8e17d83b..e2a69d7516 100644 --- a/@commitlint/prompt/src/library/format.test.ts +++ b/@commitlint/prompt/src/library/format.test.ts @@ -1,56 +1,56 @@ -import {test, expect} from 'vitest'; -import type {Result} from './types.js'; -import format from './format.js'; +import { test, expect } from "vitest"; +import type { Result } from "./types.js"; +import format from "./format.js"; -test('should return empty string', () => { +test("should return empty string", () => { const result: Result = {}; - expect(format(result)).toBe(' '); + expect(format(result)).toBe(" "); }); -test('should omit scope', () => { +test("should omit scope", () => { const result: Result = { - type: 'fix', - subject: 'test', + type: "fix", + subject: "test", }; - expect(format(result)).toBe('fix: test'); + expect(format(result)).toBe("fix: test"); }); -test('should include scope', () => { +test("should include scope", () => { const result: Result = { - type: 'fix', - scope: 'prompt', - subject: 'test', + type: "fix", + scope: "prompt", + subject: "test", }; - expect(format(result)).toBe('fix(prompt): test'); + expect(format(result)).toBe("fix(prompt): test"); }); -test('should include body', () => { +test("should include body", () => { const result: Result = { - type: 'fix', - scope: 'prompt', - subject: 'test', - body: 'some body', + type: "fix", + scope: "prompt", + subject: "test", + body: "some body", }; - expect(format(result)).toBe('fix(prompt): test\nsome body'); + expect(format(result)).toBe("fix(prompt): test\nsome body"); }); -test('should include footer', () => { +test("should include footer", () => { const result: Result = { - type: 'fix', - scope: 'prompt', - subject: 'test', - footer: 'some footer', + type: "fix", + scope: "prompt", + subject: "test", + footer: "some footer", }; - expect(format(result)).toBe('fix(prompt): test\nsome footer'); + expect(format(result)).toBe("fix(prompt): test\nsome footer"); }); -test('should include body and footer', () => { +test("should include body and footer", () => { const result: Result = { - type: 'fix', - scope: 'prompt', - subject: 'test', - body: 'some body', - footer: 'some footer', + type: "fix", + scope: "prompt", + subject: "test", + body: "some body", + footer: "some footer", }; - expect(format(result)).toBe('fix(prompt): test\nsome body\nsome footer'); + expect(format(result)).toBe("fix(prompt): test\nsome body\nsome footer"); }); diff --git a/@commitlint/prompt/src/library/format.ts b/@commitlint/prompt/src/library/format.ts index e80b57166a..414af8920f 100644 --- a/@commitlint/prompt/src/library/format.ts +++ b/@commitlint/prompt/src/library/format.ts @@ -1,6 +1,6 @@ -import chalk from 'chalk'; +import chalk from "chalk"; -import type {Result, ResultPart} from './types.js'; +import type { Result, ResultPart } from "./types.js"; /** * Get formatted commit message @@ -22,18 +22,18 @@ export default function format(input: Result, debug = false): string { registry[name as ResultPart] = value === undefined ? chalk.grey(`<${name}>`) : chalk.bold(value); return registry; - }, {}) + }, {}) : defaultInput; // Return formatted string - const {type, scope, subject, body, footer} = results; + const { type, scope, subject, body, footer } = results; return [ - `${type || ''}${scope ? `(${scope})` : ''}${type || scope ? ':' : ''} ${ - subject || '' + `${type || ""}${scope ? `(${scope})` : ""}${type || scope ? ":" : ""} ${ + subject || "" }`, body, footer, ] .filter(Boolean) - .join('\n'); + .join("\n"); } diff --git a/@commitlint/prompt/src/library/get-forced-case-fn.test.ts b/@commitlint/prompt/src/library/get-forced-case-fn.test.ts index 932f1e7bdb..c96caa562a 100644 --- a/@commitlint/prompt/src/library/get-forced-case-fn.test.ts +++ b/@commitlint/prompt/src/library/get-forced-case-fn.test.ts @@ -1,118 +1,118 @@ -import {test, expect} from 'vitest'; -import {RuleConfigSeverity} from '@commitlint/types'; +import { test, expect } from "vitest"; +import { RuleConfigSeverity } from "@commitlint/types"; -import getForcedCaseFn from './get-forced-case-fn.js'; +import getForcedCaseFn from "./get-forced-case-fn.js"; -test('should not apply', () => { - let rule = getForcedCaseFn(['name', [RuleConfigSeverity.Disabled]]); - expect(rule('test')).toBe('test'); - expect(rule('test-foo')).toBe('test-foo'); - expect(rule('testFoo')).toBe('testFoo'); - expect(rule('TEST_FOO')).toBe('TEST_FOO'); +test("should not apply", () => { + let rule = getForcedCaseFn(["name", [RuleConfigSeverity.Disabled]]); + expect(rule("test")).toBe("test"); + expect(rule("test-foo")).toBe("test-foo"); + expect(rule("testFoo")).toBe("testFoo"); + expect(rule("TEST_FOO")).toBe("TEST_FOO"); rule = getForcedCaseFn(); - expect(rule('test')).toBe('test'); - expect(rule('test-foo')).toBe('test-foo'); - expect(rule('testFoo')).toBe('testFoo'); - expect(rule('TEST_FOO')).toBe('TEST_FOO'); + expect(rule("test")).toBe("test"); + expect(rule("test-foo")).toBe("test-foo"); + expect(rule("testFoo")).toBe("testFoo"); + expect(rule("TEST_FOO")).toBe("TEST_FOO"); - rule = getForcedCaseFn(['name', [RuleConfigSeverity.Warning, 'never']]); - expect(rule('test')).toBe('test'); - expect(rule('test-foo')).toBe('test-foo'); - expect(rule('testFoo')).toBe('testFoo'); - expect(rule('TEST_FOO')).toBe('TEST_FOO'); + rule = getForcedCaseFn(["name", [RuleConfigSeverity.Warning, "never"]]); + expect(rule("test")).toBe("test"); + expect(rule("test-foo")).toBe("test-foo"); + expect(rule("testFoo")).toBe("testFoo"); + expect(rule("TEST_FOO")).toBe("TEST_FOO"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', ['camel-case', 'lowercase']], + "name", + [RuleConfigSeverity.Warning, "always", ["camel-case", "lowercase"]], ]); - expect(rule('test')).toBe('test'); - expect(rule('test-foo')).toBe('test-foo'); - expect(rule('testFoo')).toBe('testFoo'); - expect(rule('TEST_FOO')).toBe('TEST_FOO'); + expect(rule("test")).toBe("test"); + expect(rule("test-foo")).toBe("test-foo"); + expect(rule("testFoo")).toBe("testFoo"); + expect(rule("TEST_FOO")).toBe("TEST_FOO"); }); -test('should throw error on invalid casing', () => { - let rule = getForcedCaseFn(['name', [RuleConfigSeverity.Warning, 'always']]); - expect(() => rule('test')).toThrow('Unknown target case "undefined"'); +test("should throw error on invalid casing", () => { + let rule = getForcedCaseFn(["name", [RuleConfigSeverity.Warning, "always"]]); + expect(() => rule("test")).toThrow('Unknown target case "undefined"'); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'foo'], + "name", + [RuleConfigSeverity.Warning, "always", "foo"], ]); - expect(() => rule('test')).toThrow('Unknown target case "foo"'); + expect(() => rule("test")).toThrow('Unknown target case "foo"'); }); -test('should convert text correctly', () => { +test("should convert text correctly", () => { let rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'camel-case'], + "name", + [RuleConfigSeverity.Warning, "always", "camel-case"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('testFooBarBazBaz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("testFooBarBazBaz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'kebab-case'], + "name", + [RuleConfigSeverity.Warning, "always", "kebab-case"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('test-foo-bar-baz-baz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("test-foo-bar-baz-baz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'snake-case'], + "name", + [RuleConfigSeverity.Warning, "always", "snake-case"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('test_foo_bar_baz_baz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("test_foo_bar_baz_baz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'pascal-case'], + "name", + [RuleConfigSeverity.Warning, "always", "pascal-case"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('TestFooBarBazBaz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("TestFooBarBazBaz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'start-case'], + "name", + [RuleConfigSeverity.Warning, "always", "start-case"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('TEST FOO Bar Baz Baz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("TEST FOO Bar Baz Baz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'upper-case'], + "name", + [RuleConfigSeverity.Warning, "always", "upper-case"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('TEST_FOOBAR-BAZ BAZ'); + expect(rule("TEST_FOOBar-baz baz")).toBe("TEST_FOOBAR-BAZ BAZ"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'uppercase'], + "name", + [RuleConfigSeverity.Warning, "always", "uppercase"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('TEST_FOOBAR-BAZ BAZ'); + expect(rule("TEST_FOOBar-baz baz")).toBe("TEST_FOOBAR-BAZ BAZ"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'sentence-case'], + "name", + [RuleConfigSeverity.Warning, "always", "sentence-case"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('TEST_FOOBar-baz baz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("TEST_FOOBar-baz baz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'sentencecase'], + "name", + [RuleConfigSeverity.Warning, "always", "sentencecase"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('TEST_FOOBar-baz baz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("TEST_FOOBar-baz baz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'lower-case'], + "name", + [RuleConfigSeverity.Warning, "always", "lower-case"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('test_foobar-baz baz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("test_foobar-baz baz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'lowercase'], + "name", + [RuleConfigSeverity.Warning, "always", "lowercase"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('test_foobar-baz baz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("test_foobar-baz baz"); rule = getForcedCaseFn([ - 'name', - [RuleConfigSeverity.Warning, 'always', 'lowerCase'], + "name", + [RuleConfigSeverity.Warning, "always", "lowerCase"], ]); - expect(rule('TEST_FOOBar-baz baz')).toBe('test_foobar-baz baz'); + expect(rule("TEST_FOOBar-baz baz")).toBe("test_foobar-baz baz"); }); diff --git a/@commitlint/prompt/src/library/get-forced-case-fn.ts b/@commitlint/prompt/src/library/get-forced-case-fn.ts index 90f2c92b6c..11b91fb178 100644 --- a/@commitlint/prompt/src/library/get-forced-case-fn.ts +++ b/@commitlint/prompt/src/library/get-forced-case-fn.ts @@ -1,8 +1,8 @@ -import {toCase} from '@commitlint/ensure'; -import type {TargetCaseType} from '@commitlint/types'; +import { toCase } from "@commitlint/ensure"; +import type { TargetCaseType } from "@commitlint/types"; -import type {RuleEntry} from './types.js'; -import {ruleIsActive, ruleIsNotApplicable} from './utils.js'; +import type { RuleEntry } from "./types.js"; +import { ruleIsActive, ruleIsNotApplicable } from "./utils.js"; /** * Get forced case for rule @@ -10,7 +10,7 @@ import {ruleIsActive, ruleIsNotApplicable} from './utils.js'; * @return transform function applying the enforced case */ export default function getForcedCaseFn( - rule?: RuleEntry + rule?: RuleEntry, ): (input: string) => string { const noop = (input: string) => input; diff --git a/@commitlint/prompt/src/library/get-forced-leading-fn.ts b/@commitlint/prompt/src/library/get-forced-leading-fn.ts index 652ba5709b..7a750ee201 100644 --- a/@commitlint/prompt/src/library/get-forced-leading-fn.ts +++ b/@commitlint/prompt/src/library/get-forced-leading-fn.ts @@ -1,5 +1,5 @@ -import type {RuleEntry} from './types.js'; -import {ruleIsActive, ruleIsNotApplicable} from './utils.js'; +import type { RuleEntry } from "./types.js"; +import { ruleIsActive, ruleIsNotApplicable } from "./utils.js"; /** * Get forced leading for rule @@ -7,19 +7,19 @@ import {ruleIsActive, ruleIsNotApplicable} from './utils.js'; * @return transform function applying the leading */ export default function getForcedLeadingFn( - rule?: RuleEntry + rule?: RuleEntry, ): (input: string) => string { if (!rule || !ruleIsActive(rule)) { return (input: string): string => input; } const remove = (input: string): string => { - const fragments = input.split('\n'); - return fragments[0] === '' ? fragments.slice(1).join('\n') : input; + const fragments = input.split("\n"); + return fragments[0] === "" ? fragments.slice(1).join("\n") : input; }; const lead = (input: string): string => { - const fragments = input.split('\n'); - return fragments[0] === '' ? input : ['', ...fragments].join('\n'); + const fragments = input.split("\n"); + return fragments[0] === "" ? input : ["", ...fragments].join("\n"); }; return !ruleIsNotApplicable(rule) ? lead : remove; diff --git a/@commitlint/prompt/src/library/get-prompt.ts b/@commitlint/prompt/src/library/get-prompt.ts index 4e57f035c9..924549c007 100644 --- a/@commitlint/prompt/src/library/get-prompt.ts +++ b/@commitlint/prompt/src/library/get-prompt.ts @@ -1,12 +1,12 @@ -import chalk from 'chalk'; -import type {InputCustomOptions} from 'inquirer'; +import chalk from "chalk"; +import type { InputCustomOptions } from "inquirer"; -import type {InputSetting, RuleEntry, Result, ResultPart} from './types.js'; +import type { InputSetting, RuleEntry, Result, ResultPart } from "./types.js"; -import format from './format.js'; -import getForcedCaseFn from './get-forced-case-fn.js'; -import getForcedLeadingFn from './get-forced-leading-fn.js'; -import meta from './meta.js'; +import format from "./format.js"; +import getForcedCaseFn from "./get-forced-case-fn.js"; +import getForcedLeadingFn from "./get-forced-leading-fn.js"; +import meta from "./meta.js"; import { enumRuleIsActive, getHasName, @@ -14,9 +14,9 @@ import { ruleIsActive, ruleIsApplicable, ruleIsNotApplicable, -} from './utils.js'; +} from "./utils.js"; -const EOL = '\n'; +const EOL = "\n"; /** * Get a cli prompt based on rule configuration @@ -28,9 +28,9 @@ const EOL = '\n'; export default function getPrompt( type: ResultPart, rules: RuleEntry[] = [], - settings: InputSetting = {} + settings: InputSetting = {}, ): InputCustomOptions<Result> | null { - const emptyRule = rules.filter(getHasName('empty')).find(ruleIsActive); + const emptyRule = rules.filter(getHasName("empty")).find(ruleIsActive); const mustBeEmpty = emptyRule ? ruleIsApplicable(emptyRule) : false; @@ -40,24 +40,24 @@ export default function getPrompt( const required = emptyRule ? ruleIsNotApplicable(emptyRule) : false; - const forceCaseFn = getForcedCaseFn(rules.find(getHasName('case'))); + const forceCaseFn = getForcedCaseFn(rules.find(getHasName("case"))); const forceLeadingBlankFn = getForcedLeadingFn( - rules.find(getHasName('leading-blank')) + rules.find(getHasName("leading-blank")), ); - const maxLengthRule = rules.find(getHasName('max-length')); + const maxLengthRule = rules.find(getHasName("max-length")); const inputMaxLength = getMaxLength(maxLengthRule); - const enumRule = rules.filter(getHasName('enum')).find(enumRuleIsActive); + const enumRule = rules.filter(getHasName("enum")).find(enumRuleIsActive); const tabCompletion = enumRule ? enumRule[1][2].map((enumerable) => { const enumSettings = (settings.enumerables || {})[enumerable] || {}; return { value: forceLeadingBlankFn(forceCaseFn(enumerable)), - description: enumSettings.description || '', + description: enumSettings.description || "", }; - }) + }) : []; const maxLength = (res: Result) => { @@ -74,12 +74,12 @@ export default function getPrompt( }; return { - type: 'input-custom', + type: "input-custom", name: type, message: `${type}:`, validate(input, answers) { if (input.length > maxLength(answers || {})) { - return 'Input contains too many characters!'; + return "Input contains too many characters!"; } if (required && input.trim().length === 0) { // Show help if enum is defined and input may not be empty @@ -92,19 +92,19 @@ export default function getPrompt( tabValues.length > 0 && !tabValues.includes(input) ) { - return `⚠ ${chalk.bold(type)} must be one of ${tabValues.join(', ')}.`; + return `⚠ ${chalk.bold(type)} must be one of ${tabValues.join(", ")}.`; } return true; }, tabCompletion, log(answers?: Result) { let prefix = - `${chalk.white('Please enter a')} ${chalk.bold(type)}: ${meta({ + `${chalk.white("Please enter a")} ${chalk.bold(type)}: ${meta({ optional: !required, required: required, - 'tab-completion': typeof enumRule !== 'undefined', - header: typeof settings.header !== 'undefined', - 'multi-line': settings.multiline, + "tab-completion": typeof enumRule !== "undefined", + header: typeof settings.header !== "undefined", + "multi-line": settings.multiline, })}` + EOL; if (settings.description) { diff --git a/@commitlint/prompt/src/library/meta.ts b/@commitlint/prompt/src/library/meta.ts index 61c9a412eb..b361364a07 100644 --- a/@commitlint/prompt/src/library/meta.ts +++ b/@commitlint/prompt/src/library/meta.ts @@ -1,4 +1,4 @@ -import chalk from 'chalk'; +import chalk from "chalk"; /** * Get formatted meta hints for configuration @@ -11,8 +11,8 @@ export default function meta(settings: Record<string, unknown>): string { .filter((item) => item[1]) .map((item) => { const [name, value] = item; - return typeof value === 'boolean' ? `[${name}]` : `[${name}=${value}]`; + return typeof value === "boolean" ? `[${name}]` : `[${name}=${value}]`; }) - .join(' ') + .join(" "), ); } diff --git a/@commitlint/prompt/src/library/types.ts b/@commitlint/prompt/src/library/types.ts index be8582ad28..65b8bc3ad9 100644 --- a/@commitlint/prompt/src/library/types.ts +++ b/@commitlint/prompt/src/library/types.ts @@ -1,4 +1,7 @@ -import type {RuleConfigCondition, RuleConfigSeverity} from '@commitlint/types'; +import type { + RuleConfigCondition, + RuleConfigSeverity, +} from "@commitlint/types"; export type RuleEntry = | [string, Readonly<[RuleConfigSeverity.Disabled]>] @@ -19,6 +22,6 @@ export type InputSetting = { }; }; -export type ResultPart = 'type' | 'scope' | 'subject' | 'body' | 'footer'; +export type ResultPart = "type" | "scope" | "subject" | "body" | "footer"; export type Result = Partial<Record<ResultPart, string | undefined>>; diff --git a/@commitlint/prompt/src/library/utils.test.ts b/@commitlint/prompt/src/library/utils.test.ts index 2893800ea3..96f1ae6d6f 100644 --- a/@commitlint/prompt/src/library/utils.test.ts +++ b/@commitlint/prompt/src/library/utils.test.ts @@ -1,9 +1,9 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; import { RuleConfigQuality, RuleConfigSeverity, RulesConfig, -} from '@commitlint/types'; +} from "@commitlint/types"; import { enumRuleIsActive, @@ -13,118 +13,118 @@ import { getRulePrefix, getRules, ruleIsActive, -} from './utils.js'; +} from "./utils.js"; -test('getRulePrefix', () => { - expect(getRulePrefix('body-leading-blank')).toEqual('body'); - expect(getRulePrefix('body-max-line-length')).toEqual('body'); - expect(getRulePrefix('footer-leading-blank')).toEqual('footer'); - expect(getRulePrefix('footer-max-line-length')).toEqual('footer'); - expect(getRulePrefix('header-max-length')).toEqual('header'); - expect(getRulePrefix('scope-case')).toEqual('scope'); - expect(getRulePrefix('scope-enum')).toEqual('scope'); - expect(getRulePrefix('subject-case')).toEqual('subject'); - expect(getRulePrefix('subject-empty')).toEqual('subject'); - expect(getRulePrefix('subject-full-stop')).toEqual('subject'); - expect(getRulePrefix('type-case')).toEqual('type'); - expect(getRulePrefix('type-empty')).toEqual('type'); - expect(getRulePrefix('type-enum')).toEqual('type'); +test("getRulePrefix", () => { + expect(getRulePrefix("body-leading-blank")).toEqual("body"); + expect(getRulePrefix("body-max-line-length")).toEqual("body"); + expect(getRulePrefix("footer-leading-blank")).toEqual("footer"); + expect(getRulePrefix("footer-max-line-length")).toEqual("footer"); + expect(getRulePrefix("header-max-length")).toEqual("header"); + expect(getRulePrefix("scope-case")).toEqual("scope"); + expect(getRulePrefix("scope-enum")).toEqual("scope"); + expect(getRulePrefix("subject-case")).toEqual("subject"); + expect(getRulePrefix("subject-empty")).toEqual("subject"); + expect(getRulePrefix("subject-full-stop")).toEqual("subject"); + expect(getRulePrefix("type-case")).toEqual("type"); + expect(getRulePrefix("type-empty")).toEqual("type"); + expect(getRulePrefix("type-enum")).toEqual("type"); }); -test('getRuleName', () => { - expect(getRuleName('body-leading-blank')).toEqual('leading-blank'); - expect(getRuleName('body-max-line-length')).toEqual('max-line-length'); - expect(getRuleName('footer-leading-blank')).toEqual('leading-blank'); - expect(getRuleName('footer-max-line-length')).toEqual('max-line-length'); - expect(getRuleName('header-max-length')).toEqual('max-length'); - expect(getRuleName('scope-case')).toEqual('case'); - expect(getRuleName('scope-enum')).toEqual('enum'); - expect(getRuleName('subject-case')).toEqual('case'); - expect(getRuleName('subject-empty')).toEqual('empty'); - expect(getRuleName('subject-full-stop')).toEqual('full-stop'); - expect(getRuleName('type-case')).toEqual('case'); - expect(getRuleName('type-empty')).toEqual('empty'); - expect(getRuleName('type-enum')).toEqual('enum'); +test("getRuleName", () => { + expect(getRuleName("body-leading-blank")).toEqual("leading-blank"); + expect(getRuleName("body-max-line-length")).toEqual("max-line-length"); + expect(getRuleName("footer-leading-blank")).toEqual("leading-blank"); + expect(getRuleName("footer-max-line-length")).toEqual("max-line-length"); + expect(getRuleName("header-max-length")).toEqual("max-length"); + expect(getRuleName("scope-case")).toEqual("case"); + expect(getRuleName("scope-enum")).toEqual("enum"); + expect(getRuleName("subject-case")).toEqual("case"); + expect(getRuleName("subject-empty")).toEqual("empty"); + expect(getRuleName("subject-full-stop")).toEqual("full-stop"); + expect(getRuleName("type-case")).toEqual("case"); + expect(getRuleName("type-empty")).toEqual("empty"); + expect(getRuleName("type-enum")).toEqual("enum"); }); -test('ruleIsActive', () => { - expect(ruleIsActive(['', [RuleConfigSeverity.Error, 'always', 100]])).toBe( - true +test("ruleIsActive", () => { + expect(ruleIsActive(["", [RuleConfigSeverity.Error, "always", 100]])).toBe( + true, ); - expect(ruleIsActive(['', [RuleConfigSeverity.Warning, 'never', 100]])).toBe( - true + expect(ruleIsActive(["", [RuleConfigSeverity.Warning, "never", 100]])).toBe( + true, ); - expect(ruleIsActive(['', [RuleConfigSeverity.Disabled, 'always', 100]])).toBe( - false + expect(ruleIsActive(["", [RuleConfigSeverity.Disabled, "always", 100]])).toBe( + false, ); - expect(ruleIsActive(['', [RuleConfigSeverity.Error]] as any)).toBe(true); + expect(ruleIsActive(["", [RuleConfigSeverity.Error]] as any)).toBe(true); }); -test('getMaxLength', () => { - expect(getMaxLength(['', [RuleConfigSeverity.Error, 'always', 100]])).toBe( - 100 +test("getMaxLength", () => { + expect(getMaxLength(["", [RuleConfigSeverity.Error, "always", 100]])).toBe( + 100, ); - expect(getMaxLength(['', [RuleConfigSeverity.Warning, 'never', 100]])).toBe( - Infinity + expect(getMaxLength(["", [RuleConfigSeverity.Warning, "never", 100]])).toBe( + Infinity, ); - expect(getMaxLength(['', [RuleConfigSeverity.Disabled, 'always', 100]])).toBe( - Infinity + expect(getMaxLength(["", [RuleConfigSeverity.Disabled, "always", 100]])).toBe( + Infinity, ); - expect(getMaxLength(['', [RuleConfigSeverity.Error, 100]] as any)).toBe( - Infinity + expect(getMaxLength(["", [RuleConfigSeverity.Error, 100]] as any)).toBe( + Infinity, ); const rules: any = { - 'body-max-line-length': [RuleConfigSeverity.Error, 'always', 100], - 'header-max-length': [RuleConfigSeverity.Error, 'always', 100], - 'test-max-length': [RuleConfigSeverity.Disabled, 'always', 100], + "body-max-line-length": [RuleConfigSeverity.Error, "always", 100], + "header-max-length": [RuleConfigSeverity.Error, "always", 100], + "test-max-length": [RuleConfigSeverity.Disabled, "always", 100], }; - let lengthRule = getRules('header', rules).find(getHasName('max-length')); + let lengthRule = getRules("header", rules).find(getHasName("max-length")); expect(getMaxLength(lengthRule)).toBe(100); - lengthRule = getRules('body', rules).find(getHasName('max-length')); + lengthRule = getRules("body", rules).find(getHasName("max-length")); expect(getMaxLength(lengthRule)).toBe(Infinity); - lengthRule = getRules('test', rules).find(getHasName('max-length')); + lengthRule = getRules("test", rules).find(getHasName("max-length")); expect(getMaxLength(lengthRule)).toBe(Infinity); }); -test('check enum rule filters', () => { +test("check enum rule filters", () => { const rules: Partial<RulesConfig<RuleConfigQuality.Qualified>> = { - 'enum-string': [RuleConfigSeverity.Warning, 'always', ['1', '2', '3']], - 'type-enum': [RuleConfigSeverity.Error, 'always', ['build', 'chore', 'ci']], - 'scope-enum': [RuleConfigSeverity.Error, 'never', ['cli', 'core', 'lint']], - 'bar-enum': [RuleConfigSeverity.Disabled, 'always', ['foo', 'bar', 'baz']], + "enum-string": [RuleConfigSeverity.Warning, "always", ["1", "2", "3"]], + "type-enum": [RuleConfigSeverity.Error, "always", ["build", "chore", "ci"]], + "scope-enum": [RuleConfigSeverity.Error, "never", ["cli", "core", "lint"]], + "bar-enum": [RuleConfigSeverity.Disabled, "always", ["foo", "bar", "baz"]], }; - let enumRule = getRules('type', rules) - .filter(getHasName('enum')) + let enumRule = getRules("type", rules) + .filter(getHasName("enum")) .find(enumRuleIsActive); expect(enumRule).toEqual([ - 'type-enum', - [RuleConfigSeverity.Error, 'always', ['build', 'chore', 'ci']], + "type-enum", + [RuleConfigSeverity.Error, "always", ["build", "chore", "ci"]], ]); - enumRule = getRules('string', rules) - .filter(getHasName('enum')) + enumRule = getRules("string", rules) + .filter(getHasName("enum")) .find(enumRuleIsActive); expect(enumRule).toEqual(undefined); - enumRule = getRules('enum', rules) - .filter(getHasName('string')) + enumRule = getRules("enum", rules) + .filter(getHasName("string")) .find(enumRuleIsActive); expect(enumRule).toEqual([ - 'enum-string', - [RuleConfigSeverity.Warning, 'always', ['1', '2', '3']], + "enum-string", + [RuleConfigSeverity.Warning, "always", ["1", "2", "3"]], ]); - enumRule = getRules('bar', rules) - .filter(getHasName('enum')) + enumRule = getRules("bar", rules) + .filter(getHasName("enum")) .find(enumRuleIsActive); expect(enumRule).toEqual(undefined); - enumRule = getRules('scope', rules) - .filter(getHasName('enum')) + enumRule = getRules("scope", rules) + .filter(getHasName("enum")) .find(enumRuleIsActive); expect(enumRule).toEqual(undefined); }); diff --git a/@commitlint/prompt/src/library/utils.ts b/@commitlint/prompt/src/library/utils.ts index eaa6245a24..aaca4e2004 100644 --- a/@commitlint/prompt/src/library/utils.ts +++ b/@commitlint/prompt/src/library/utils.ts @@ -1,7 +1,7 @@ -import {RuleConfigSeverity} from '@commitlint/types'; -import type {QualifiedRules} from '@commitlint/types'; +import { RuleConfigSeverity } from "@commitlint/types"; +import type { QualifiedRules } from "@commitlint/types"; -import type {RuleEntry} from './types.js'; +import type { RuleEntry } from "./types.js"; /** * Get name for a given rule id @@ -9,8 +9,8 @@ import type {RuleEntry} from './types.js'; * @return name of the rule */ export function getRuleName(id: string): string { - const fragments = id.split('-'); - return fragments.length > 1 ? fragments.slice(1).join('-') : fragments[0]; + const fragments = id.split("-"); + return fragments.length > 1 ? fragments.slice(1).join("-") : fragments[0]; } /** @@ -19,7 +19,7 @@ export function getRuleName(id: string): string { * @return prefix of the rule */ export function getRulePrefix(id: string): string | null { - const fragments = id.split('-'); + const fragments = id.split("-"); return fragments.length > 1 ? fragments[0] : null; } @@ -28,7 +28,7 @@ export function getRulePrefix(id: string): string | null { */ export function getHasName(name: string) { return <T extends RuleEntry>( - rule: RuleEntry + rule: RuleEntry, ): rule is Exclude<T, [string, undefined]> => getRuleName(rule[0]) === name; } @@ -38,7 +38,7 @@ export function getHasName(name: string) { * @return if the rule definition is active */ export function ruleIsActive<T extends RuleEntry>( - rule: T + rule: T, ): rule is Exclude<T, [string, Readonly<[RuleConfigSeverity.Disabled]>]> { const [, value] = rule; if (value && Array.isArray(value)) { @@ -53,13 +53,13 @@ export function ruleIsActive<T extends RuleEntry>( * @return if the rule definition is applicable */ export function ruleIsApplicable( - rule: RuleEntry + rule: RuleEntry, ): rule is - | [string, Readonly<[RuleConfigSeverity, 'always']>] - | [string, Readonly<[RuleConfigSeverity, 'always', unknown]>] { + | [string, Readonly<[RuleConfigSeverity, "always"]>] + | [string, Readonly<[RuleConfigSeverity, "always", unknown]>] { const [, value] = rule; if (value && Array.isArray(value)) { - return value[1] === 'always'; + return value[1] === "always"; } return false; } @@ -70,24 +70,24 @@ export function ruleIsApplicable( * @return if the rule definition is applicable */ export function ruleIsNotApplicable( - rule: RuleEntry + rule: RuleEntry, ): rule is - | [string, Readonly<[RuleConfigSeverity, 'never']>] - | [string, Readonly<[RuleConfigSeverity, 'never', unknown]>] { + | [string, Readonly<[RuleConfigSeverity, "never"]>] + | [string, Readonly<[RuleConfigSeverity, "never", unknown]>] { const [, value] = rule; if (value && Array.isArray(value)) { - return value[1] === 'never'; + return value[1] === "never"; } return false; } export function enumRuleIsActive( - rule: RuleEntry + rule: RuleEntry, ): rule is [ string, Readonly< - [RuleConfigSeverity.Warning | RuleConfigSeverity.Error, 'always', string[]] - > + [RuleConfigSeverity.Warning | RuleConfigSeverity.Error, "always", string[]] + >, ] { return ( ruleIsActive(rule) && @@ -105,7 +105,7 @@ export function enumRuleIsActive( */ export function getRules(prefix: string, rules: QualifiedRules): RuleEntry[] { return Object.entries(rules).filter( - (rule): rule is RuleEntry => getRulePrefix(rule[0]) === prefix + (rule): rule is RuleEntry => getRulePrefix(rule[0]) === prefix, ); } @@ -114,7 +114,7 @@ export function getMaxLength(rule?: RuleEntry): number { rule && ruleIsActive(rule) && ruleIsApplicable(rule) && - typeof rule[1][2] === 'number' + typeof rule[1][2] === "number" ) { return rule[1][2]; } diff --git a/@commitlint/prompt/src/settings.ts b/@commitlint/prompt/src/settings.ts index 8c80f14247..a85a9a5394 100644 --- a/@commitlint/prompt/src/settings.ts +++ b/@commitlint/prompt/src/settings.ts @@ -1,56 +1,56 @@ export default { type: { - description: '<type> holds information about the goal of a change.', + description: "<type> holds information about the goal of a change.", enumerables: { feat: { - description: 'Adds a new feature.', + description: "Adds a new feature.", }, fix: { - description: 'Solves a bug.', + description: "Solves a bug.", }, chore: { description: "Other changes that don't modify src or test files", }, docs: { - description: 'Adds or alters documentation.', + description: "Adds or alters documentation.", }, style: { - description: 'Improves formatting, white-space.', + description: "Improves formatting, white-space.", }, refactor: { description: - 'Rewrites code without feature, performance or bug changes.', + "Rewrites code without feature, performance or bug changes.", }, perf: { - description: 'Improves performance.', + description: "Improves performance.", }, test: { - description: 'Adds or modifies tests.', + description: "Adds or modifies tests.", }, build: { - description: 'Affects the build system or external dependencies.', + description: "Affects the build system or external dependencies.", }, ci: { - description: 'Changes CI configuration files and scripts.', + description: "Changes CI configuration files and scripts.", }, revert: { - description: 'Reverts a previous commit.', + description: "Reverts a previous commit.", }, }, }, scope: { - description: '<scope> marks which sub-component of the project is affected', + description: "<scope> marks which sub-component of the project is affected", }, subject: { - description: '<subject> is a short, high-level description of the change', + description: "<subject> is a short, high-level description of the change", }, body: { - description: '<body> holds additional information about the change', + description: "<body> holds additional information about the change", multiline: true, }, footer: { description: - '<footer> holds further meta data, such as breaking changes and issue ids', + "<footer> holds further meta data, such as breaking changes and issue ids", multiline: true, }, }; diff --git a/@commitlint/prompt/tsconfig.json b/@commitlint/prompt/tsconfig.json index 76dd5e38cb..52e48f310a 100644 --- a/@commitlint/prompt/tsconfig.json +++ b/@commitlint/prompt/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../types"}, {"path": "../load"}] + "references": [{ "path": "../types" }, { "path": "../load" }] } diff --git a/@commitlint/read/src/get-edit-commit.ts b/@commitlint/read/src/get-edit-commit.ts index 9dc4739e17..7754ecb802 100644 --- a/@commitlint/read/src/get-edit-commit.ts +++ b/@commitlint/read/src/get-edit-commit.ts @@ -1,21 +1,21 @@ -import toplevel from '@commitlint/top-level'; -import fs from 'fs/promises'; +import toplevel from "@commitlint/top-level"; +import fs from "fs/promises"; -import {getEditFilePath} from './get-edit-file-path.js'; +import { getEditFilePath } from "./get-edit-file-path.js"; // Get recently edited commit message export async function getEditCommit( cwd?: string, - edit?: boolean | string + edit?: boolean | string, ): Promise<string[]> { const top = await toplevel(cwd); - if (typeof top !== 'string') { + if (typeof top !== "string") { throw new TypeError(`Could not find git root from ${cwd}`); } const editFilePath = await getEditFilePath(top, edit); const editFile: Buffer = await fs.readFile(editFilePath); - return [`${editFile.toString('utf-8')}\n`]; + return [`${editFile.toString("utf-8")}\n`]; } diff --git a/@commitlint/read/src/get-edit-file-path.ts b/@commitlint/read/src/get-edit-file-path.ts index 191cf6376a..b323dce1e2 100644 --- a/@commitlint/read/src/get-edit-file-path.ts +++ b/@commitlint/read/src/get-edit-file-path.ts @@ -1,26 +1,26 @@ -import path from 'node:path'; -import {Stats} from 'node:fs'; -import fs from 'fs/promises'; +import path from "node:path"; +import { Stats } from "node:fs"; +import fs from "fs/promises"; // Get path to recently edited commit message file export async function getEditFilePath( top: string, - edit?: boolean | string + edit?: boolean | string, ): Promise<string> { - if (typeof edit === 'string') { + if (typeof edit === "string") { return path.resolve(top, edit); } - const dotgitPath = path.join(top, '.git'); + const dotgitPath = path.join(top, ".git"); const dotgitStats: Stats = await fs.lstat(dotgitPath); if (dotgitStats.isDirectory()) { - return path.join(top, '.git/COMMIT_EDITMSG'); + return path.join(top, ".git/COMMIT_EDITMSG"); } const gitFile: string = await fs.readFile(dotgitPath, { - encoding: 'utf-8', + encoding: "utf-8", }); - const relativeGitPath = gitFile.replace('gitdir: ', '').replace('\n', ''); - return path.resolve(top, relativeGitPath, 'COMMIT_EDITMSG'); + const relativeGitPath = gitFile.replace("gitdir: ", "").replace("\n", ""); + return path.resolve(top, relativeGitPath, "COMMIT_EDITMSG"); } diff --git a/@commitlint/read/src/get-history-commits.ts b/@commitlint/read/src/get-history-commits.ts index 0abb3f4879..ad9fc0a705 100644 --- a/@commitlint/read/src/get-history-commits.ts +++ b/@commitlint/read/src/get-history-commits.ts @@ -1,11 +1,11 @@ -import gitRawCommits from 'git-raw-commits'; +import gitRawCommits from "git-raw-commits"; -import {streamToPromise} from './stream-to-promise.js'; +import { streamToPromise } from "./stream-to-promise.js"; // Get commit messages from history export async function getHistoryCommits( options: gitRawCommits.GitOptions, - opts: {cwd?: string} = {} + opts: { cwd?: string } = {}, ): Promise<string[]> { - return streamToPromise(gitRawCommits(options, {cwd: opts.cwd})); + return streamToPromise(gitRawCommits(options, { cwd: opts.cwd })); } diff --git a/@commitlint/read/src/read.test.ts b/@commitlint/read/src/read.test.ts index 4cf4622edf..c1903b1609 100644 --- a/@commitlint/read/src/read.test.ts +++ b/@commitlint/read/src/read.test.ts @@ -1,152 +1,152 @@ -import {test, expect} from 'vitest'; -import fs from 'fs/promises'; -import path from 'node:path'; -import {git} from '@commitlint/test'; -import {x} from 'tinyexec'; +import { test, expect } from "vitest"; +import fs from "fs/promises"; +import path from "node:path"; +import { git } from "@commitlint/test"; +import { x } from "tinyexec"; -import read from './read.js'; +import read from "./read.js"; -test('get edit commit message specified by the `edit` flag', async () => { +test("get edit commit message specified by the `edit` flag", async () => { const cwd: string = await git.bootstrap(); - await fs.writeFile(path.join(cwd, 'commit-msg-file'), 'foo'); + await fs.writeFile(path.join(cwd, "commit-msg-file"), "foo"); - const expected = ['foo\n']; - const actual = await read({edit: 'commit-msg-file', cwd}); + const expected = ["foo\n"]; + const actual = await read({ edit: "commit-msg-file", cwd }); expect(actual).toEqual(expected); }); -test('get edit commit message from git root', async () => { +test("get edit commit message from git root", async () => { const cwd: string = await git.bootstrap(); - await fs.writeFile(path.join(cwd, 'alpha.txt'), 'alpha'); - await x('git', ['add', '.'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', 'alpha'], {nodeOptions: {cwd}}); - const expected = ['alpha\n\n']; - const actual = await read({edit: true, cwd}); + await fs.writeFile(path.join(cwd, "alpha.txt"), "alpha"); + await x("git", ["add", "."], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", "alpha"], { nodeOptions: { cwd } }); + const expected = ["alpha\n\n"]; + const actual = await read({ edit: true, cwd }); expect(actual).toEqual(expected); }); -test('get history commit messages', async () => { +test("get history commit messages", async () => { const cwd: string = await git.bootstrap(); - await fs.writeFile(path.join(cwd, 'alpha.txt'), 'alpha'); - await x('git', ['add', 'alpha.txt'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', 'alpha'], {nodeOptions: {cwd}}); - await x('git', ['rm', 'alpha.txt'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', 'remove alpha'], {nodeOptions: {cwd}}); - - const expected = ['remove alpha\n\n', 'alpha\n\n']; - const actual = await read({cwd}); + await fs.writeFile(path.join(cwd, "alpha.txt"), "alpha"); + await x("git", ["add", "alpha.txt"], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", "alpha"], { nodeOptions: { cwd } }); + await x("git", ["rm", "alpha.txt"], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", "remove alpha"], { nodeOptions: { cwd } }); + + const expected = ["remove alpha\n\n", "alpha\n\n"]; + const actual = await read({ cwd }); expect(actual).toEqual(expected); }); -test('get edit commit message from git subdirectory', async () => { +test("get edit commit message from git subdirectory", async () => { const cwd: string = await git.bootstrap(); - await fs.mkdir(path.join(cwd, 'beta')); - await fs.writeFile(path.join(cwd, 'beta/beta.txt'), 'beta'); + await fs.mkdir(path.join(cwd, "beta")); + await fs.writeFile(path.join(cwd, "beta/beta.txt"), "beta"); - await x('git', ['add', '.'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', 'beta'], {nodeOptions: {cwd}}); + await x("git", ["add", "."], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", "beta"], { nodeOptions: { cwd } }); - const expected = ['beta\n\n']; - const actual = await read({edit: true, cwd}); + const expected = ["beta\n\n"]; + const actual = await read({ edit: true, cwd }); expect(actual).toEqual(expected); }); -test('get edit commit message while skipping first commit', async () => { +test("get edit commit message while skipping first commit", async () => { const cwd: string = await git.bootstrap(); - await fs.mkdir(path.join(cwd, 'beta')); - await fs.writeFile(path.join(cwd, 'beta/beta.txt'), 'beta'); - - await fs.writeFile(path.join(cwd, 'alpha.txt'), 'alpha'); - await x('git', ['add', 'alpha.txt'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', 'alpha'], {nodeOptions: {cwd}}); - await fs.writeFile(path.join(cwd, 'beta.txt'), 'beta'); - await x('git', ['add', 'beta.txt'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', 'beta'], {nodeOptions: {cwd}}); - await fs.writeFile(path.join(cwd, 'gamma.txt'), 'gamma'); - await x('git', ['add', 'gamma.txt'], {nodeOptions: {cwd}}); - await x('git', ['commit', '-m', 'gamma'], {nodeOptions: {cwd}}); - - const expected = ['beta\n\n']; - const actual = await read({from: 'HEAD~2', cwd, gitLogArgs: '--skip 1'}); + await fs.mkdir(path.join(cwd, "beta")); + await fs.writeFile(path.join(cwd, "beta/beta.txt"), "beta"); + + await fs.writeFile(path.join(cwd, "alpha.txt"), "alpha"); + await x("git", ["add", "alpha.txt"], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", "alpha"], { nodeOptions: { cwd } }); + await fs.writeFile(path.join(cwd, "beta.txt"), "beta"); + await x("git", ["add", "beta.txt"], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", "beta"], { nodeOptions: { cwd } }); + await fs.writeFile(path.join(cwd, "gamma.txt"), "gamma"); + await x("git", ["add", "gamma.txt"], { nodeOptions: { cwd } }); + await x("git", ["commit", "-m", "gamma"], { nodeOptions: { cwd } }); + + const expected = ["beta\n\n"]; + const actual = await read({ from: "HEAD~2", cwd, gitLogArgs: "--skip 1" }); expect(actual).toEqual(expected); }); -test('should only read the last commit', async () => { +test("should only read the last commit", async () => { const cwd: string = await git.bootstrap(); - await x('git', ['commit', '--allow-empty', '-m', 'commit Z'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit Z"], { + nodeOptions: { cwd }, }); - await x('git', ['commit', '--allow-empty', '-m', 'commit Y'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit Y"], { + nodeOptions: { cwd }, }); - await x('git', ['commit', '--allow-empty', '-m', 'commit X'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit X"], { + nodeOptions: { cwd }, }); - const result = await read({cwd, last: true}); + const result = await read({ cwd, last: true }); - expect(result).toEqual(['commit X']); + expect(result).toEqual(["commit X"]); }); -test('should read commits from the last annotated tag', async () => { +test("should read commits from the last annotated tag", async () => { const cwd: string = await git.bootstrap(); - await x('git', ['commit', '--allow-empty', '-m', 'chore: release v1.0.0'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "chore: release v1.0.0"], { + nodeOptions: { cwd }, }); - await x('git', ['tag', 'v1.0.0', '--annotate', '-m', 'v1.0.0'], { - nodeOptions: {cwd}, + await x("git", ["tag", "v1.0.0", "--annotate", "-m", "v1.0.0"], { + nodeOptions: { cwd }, }); - await x('git', ['commit', '--allow-empty', '-m', 'commit 1'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit 1"], { + nodeOptions: { cwd }, }); - await x('git', ['commit', '--allow-empty', '-m', 'commit 2'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit 2"], { + nodeOptions: { cwd }, }); - const result = await read({cwd, fromLastTag: true}); + const result = await read({ cwd, fromLastTag: true }); - expect(result).toEqual(['commit 2\n\n', 'commit 1\n\n']); + expect(result).toEqual(["commit 2\n\n", "commit 1\n\n"]); }); -test('should read commits from the last lightweight tag', async () => { +test("should read commits from the last lightweight tag", async () => { const cwd: string = await git.bootstrap(); await x( - 'git', - ['commit', '--allow-empty', '-m', 'chore: release v9.9.9-alpha.1'], - {nodeOptions: {cwd}} + "git", + ["commit", "--allow-empty", "-m", "chore: release v9.9.9-alpha.1"], + { nodeOptions: { cwd } }, ); - await x('git', ['tag', 'v9.9.9-alpha.1'], {nodeOptions: {cwd}}); - await x('git', ['commit', '--allow-empty', '-m', 'commit A'], { - nodeOptions: {cwd}, + await x("git", ["tag", "v9.9.9-alpha.1"], { nodeOptions: { cwd } }); + await x("git", ["commit", "--allow-empty", "-m", "commit A"], { + nodeOptions: { cwd }, }); - await x('git', ['commit', '--allow-empty', '-m', 'commit B'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit B"], { + nodeOptions: { cwd }, }); - const result = await read({cwd, fromLastTag: true}); + const result = await read({ cwd, fromLastTag: true }); - expect(result).toEqual(['commit B\n\n', 'commit A\n\n']); + expect(result).toEqual(["commit B\n\n", "commit A\n\n"]); }); -test('should not read any commits when there are no tags', async () => { +test("should not read any commits when there are no tags", async () => { const cwd: string = await git.bootstrap(); - await x('git', ['commit', '--allow-empty', '-m', 'commit 7'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit 7"], { + nodeOptions: { cwd }, }); - await x('git', ['commit', '--allow-empty', '-m', 'commit 8'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit 8"], { + nodeOptions: { cwd }, }); - await x('git', ['commit', '--allow-empty', '-m', 'commit 9'], { - nodeOptions: {cwd}, + await x("git", ["commit", "--allow-empty", "-m", "commit 9"], { + nodeOptions: { cwd }, }); - const result = await read({cwd, fromLastTag: true}); + const result = await read({ cwd, fromLastTag: true }); expect(result).toHaveLength(0); }); diff --git a/@commitlint/read/src/read.ts b/@commitlint/read/src/read.ts index 0e5c422720..ae991a52d1 100644 --- a/@commitlint/read/src/read.ts +++ b/@commitlint/read/src/read.ts @@ -1,10 +1,10 @@ -import minimist from 'minimist'; -import type {GitOptions} from 'git-raw-commits'; +import minimist from "minimist"; +import type { GitOptions } from "git-raw-commits"; -import {getHistoryCommits} from './get-history-commits.js'; -import {getEditCommit} from './get-edit-commit.js'; +import { getHistoryCommits } from "./get-history-commits.js"; +import { getEditCommit } from "./get-edit-commit.js"; -import {x} from 'tinyexec'; +import { x } from "tinyexec"; interface GetCommitMessageOptions { cwd?: string; @@ -18,9 +18,9 @@ interface GetCommitMessageOptions { // Get commit messages export default async function getCommitMessages( - settings: GetCommitMessageOptions + settings: GetCommitMessageOptions, ): Promise<string[]> { - const {cwd, fromLastTag, to, last, edit, gitLogArgs} = settings; + const { cwd, fromLastTag, to, last, edit, gitLogArgs } = settings; let from = settings.from; if (edit) { @@ -29,9 +29,9 @@ export default async function getCommitMessages( if (last) { const gitCommandResult = await x( - 'git', - ['log', '-1', '--pretty=format:%B'], - {nodeOptions: {cwd}} + "git", + ["log", "-1", "--pretty=format:%B"], + { nodeOptions: { cwd } }, ); let output = gitCommandResult.stdout.trim(); // strip output of extra quotation marks ("") @@ -42,16 +42,16 @@ export default async function getCommitMessages( if (!from && fromLastTag) { const output = await x( - 'git', + "git", [ - 'describe', - '--abbrev=40', - '--always', - '--first-parent', - '--long', - '--tags', + "describe", + "--abbrev=40", + "--always", + "--first-parent", + "--long", + "--tags", ], - {nodeOptions: {cwd}} + { nodeOptions: { cwd } }, ); const stdout = output.stdout.trim(); @@ -63,20 +63,20 @@ export default async function getCommitMessages( // Description will be in the format: <tag>-<count>-g<hash> // Example: v3.2.0-11-g9057371a52adaae5180d93fe4d0bb808d874b9fb // Minus zero based (1), dash (1), "g" prefix (1), hash (40) = -43 - const tagSlice = stdout.lastIndexOf('-', stdout.length - 43); + const tagSlice = stdout.lastIndexOf("-", stdout.length - 43); from = stdout.slice(0, tagSlice); } } - let gitOptions: GitOptions = {from, to}; + let gitOptions: GitOptions = { from, to }; if (gitLogArgs) { gitOptions = { - ...minimist(gitLogArgs.split(' ')), + ...minimist(gitLogArgs.split(" ")), from, to, }; } - return getHistoryCommits(gitOptions, {cwd}); + return getHistoryCommits(gitOptions, { cwd }); } diff --git a/@commitlint/read/src/stream-to-promise.ts b/@commitlint/read/src/stream-to-promise.ts index d1610cc7b8..149fb05049 100644 --- a/@commitlint/read/src/stream-to-promise.ts +++ b/@commitlint/read/src/stream-to-promise.ts @@ -1,11 +1,11 @@ -import {Readable} from 'node:stream'; +import { Readable } from "node:stream"; export function streamToPromise(stream: Readable): Promise<string[]> { const data: string[] = []; return new Promise((resolve, reject) => stream - .on('data', (chunk) => data.push(chunk.toString('utf-8'))) - .on('error', reject) - .on('end', () => resolve(data)) + .on("data", (chunk) => data.push(chunk.toString("utf-8"))) + .on("error", reject) + .on("end", () => resolve(data)), ); } diff --git a/@commitlint/read/tsconfig.json b/@commitlint/read/tsconfig.json index f54e2e29b1..6edb67bd92 100644 --- a/@commitlint/read/tsconfig.json +++ b/@commitlint/read/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../top-level"}] + "references": [{ "path": "../top-level" }] } diff --git a/@commitlint/resolve-extends/src/index.test.ts b/@commitlint/resolve-extends/src/index.test.ts index 35ed266d91..0e2306c48b 100644 --- a/@commitlint/resolve-extends/src/index.test.ts +++ b/@commitlint/resolve-extends/src/index.test.ts @@ -1,64 +1,64 @@ -import {test, expect, vi} from 'vitest'; -import {createRequire} from 'node:module'; -import {RuleConfigSeverity, UserConfig} from '@commitlint/types'; +import { test, expect, vi } from "vitest"; +import { createRequire } from "node:module"; +import { RuleConfigSeverity, UserConfig } from "@commitlint/types"; -import resolveExtends, {ResolveExtendsContext} from './index.js'; +import resolveExtends, { ResolveExtendsContext } from "./index.js"; const require = createRequire(import.meta.url); const id = (id: unknown) => id; -test('returns empty object when called without params', async () => { +test("returns empty object when called without params", async () => { const actual = await resolveExtends(); expect(actual).toEqual({}); }); -test('returns an equivalent object as passed in', async () => { - const expected = {foo: 'bar'}; +test("returns an equivalent object as passed in", async () => { + const expected = { foo: "bar" }; const actual = await resolveExtends(expected); expect(actual).toEqual(expected); }); -test('falls back to global install', async () => { - const resolveGlobal = vi.fn(() => '@commitlint/foo-bar'); +test("falls back to global install", async () => { + const resolveGlobal = vi.fn(() => "@commitlint/foo-bar"); const dynamicImport = vi.fn(() => ({})); - const ctx = {resolveGlobal, dynamicImport} as ResolveExtendsContext; + const ctx = { resolveGlobal, dynamicImport } as ResolveExtendsContext; - resolveExtends({extends: ['@commitlint/foo-bar']}, ctx); - expect(ctx.resolveGlobal).toHaveBeenCalledWith('@commitlint/foo-bar'); + resolveExtends({ extends: ["@commitlint/foo-bar"] }, ctx); + expect(ctx.resolveGlobal).toHaveBeenCalledWith("@commitlint/foo-bar"); }); -test('fails for missing extends', async () => { +test("fails for missing extends", async () => { await expect(() => - resolveExtends({extends: ['@commitlint/foo-bar']}) + resolveExtends({ extends: ["@commitlint/foo-bar"] }), ).rejects.toThrow(/Cannot find module "@commitlint\/foo-bar" from/); }); -test('resolves extends for single config', async () => { - const input = {extends: 'extender-name'}; +test("resolves extends for single config", async () => { + const input = { extends: "extender-name" }; const ctx = { resolve: id, dynamicImport: vi.fn(() => ({})), } as ResolveExtendsContext; await resolveExtends(input, ctx); - expect(ctx.dynamicImport).toHaveBeenCalledWith('extender-name'); + expect(ctx.dynamicImport).toHaveBeenCalledWith("extender-name"); }); -test('uses empty prefix by default', async () => { - const input = {extends: ['extender-name']}; +test("uses empty prefix by default", async () => { + const input = { extends: ["extender-name"] }; const ctx = { resolve: id, dynamicImport: vi.fn(() => ({})), } as ResolveExtendsContext; await resolveExtends(input, ctx); - expect(ctx.dynamicImport).toHaveBeenCalledWith('extender-name'); + expect(ctx.dynamicImport).toHaveBeenCalledWith("extender-name"); }); -test('uses prefix as configured', async () => { - const input = {extends: ['extender-name']}; +test("uses prefix as configured", async () => { + const input = { extends: ["extender-name"] }; const ctx = { resolve: id, dynamicImport: vi.fn(() => ({})), @@ -66,14 +66,14 @@ test('uses prefix as configured', async () => { await resolveExtends(input, { ...ctx, - prefix: 'prefix', + prefix: "prefix", }); - expect(ctx.dynamicImport).toHaveBeenCalledWith('prefix-extender-name'); + expect(ctx.dynamicImport).toHaveBeenCalledWith("prefix-extender-name"); }); -test('ignores prefix for scoped extends', async () => { - const input = {extends: ['@scope/extender-name']}; +test("ignores prefix for scoped extends", async () => { + const input = { extends: ["@scope/extender-name"] }; const ctx = { resolve: id, dynamicImport: vi.fn(() => ({})), @@ -81,14 +81,14 @@ test('ignores prefix for scoped extends', async () => { await resolveExtends(input, { ...ctx, - prefix: 'prefix', + prefix: "prefix", }); - expect(ctx.dynamicImport).toHaveBeenCalledWith('@scope/extender-name'); + expect(ctx.dynamicImport).toHaveBeenCalledWith("@scope/extender-name"); }); -test('adds prefix as suffix for scopes only', async () => { - const input = {extends: ['@scope']}; +test("adds prefix as suffix for scopes only", async () => { + const input = { extends: ["@scope"] }; const ctx = { resolve: id, dynamicImport: vi.fn(() => ({})), @@ -96,14 +96,14 @@ test('adds prefix as suffix for scopes only', async () => { await resolveExtends(input, { ...ctx, - prefix: 'prefix', + prefix: "prefix", }); - expect(ctx.dynamicImport).toHaveBeenCalledWith('@scope/prefix'); + expect(ctx.dynamicImport).toHaveBeenCalledWith("@scope/prefix"); }); -test('ignores prefix for relative extends', async () => { - const input = {extends: ['./extender']}; +test("ignores prefix for relative extends", async () => { + const input = { extends: ["./extender"] }; const ctx = { resolve: id, dynamicImport: vi.fn(() => ({})), @@ -111,15 +111,15 @@ test('ignores prefix for relative extends', async () => { await resolveExtends(input, { ...ctx, - prefix: 'prefix', + prefix: "prefix", }); - expect(ctx.dynamicImport).toHaveBeenCalledWith('./extender'); + expect(ctx.dynamicImport).toHaveBeenCalledWith("./extender"); }); -test('ignores prefix for absolute extends', async () => { - const absolutePath = require.resolve('@commitlint/config-angular'); - const input = {extends: [absolutePath]}; +test("ignores prefix for absolute extends", async () => { + const absolutePath = require.resolve("@commitlint/config-angular"); + const input = { extends: [absolutePath] }; const ctx = { resolve: id, dynamicImport: vi.fn(() => ({})), @@ -127,15 +127,15 @@ test('ignores prefix for absolute extends', async () => { await resolveExtends(input, { ...ctx, - prefix: 'prefix', + prefix: "prefix", }); expect(ctx.dynamicImport).toHaveBeenCalledWith(absolutePath); }); -test('propagates return value of require function', async () => { - const input = {extends: ['extender-name']}; - const propagated = {foo: 'bar'}; +test("propagates return value of require function", async () => { + const input = { extends: ["extender-name"] }; + const propagated = { foo: "bar" }; const ctx = { resolve: id, dynamicImport: vi.fn(() => propagated), @@ -145,15 +145,15 @@ test('propagates return value of require function', async () => { expect(actual).toEqual(expect.objectContaining(propagated)); }); -test('resolves extends recursively', async () => { - const input = {extends: ['extender-name']}; +test("resolves extends recursively", async () => { + const input = { extends: ["extender-name"] }; const dynamicImport = (id: string) => { switch (id) { - case 'extender-name': - return {extends: ['recursive-extender-name']}; - case 'recursive-extender-name': - return {foo: 'bar'}; + case "extender-name": + return { extends: ["recursive-extender-name"] }; + case "recursive-extender-name": + return { foo: "bar" }; default: return {}; } @@ -165,19 +165,19 @@ test('resolves extends recursively', async () => { } as ResolveExtendsContext; await resolveExtends(input, ctx); - expect(ctx.dynamicImport).toHaveBeenCalledWith('extender-name'); - expect(ctx.dynamicImport).toHaveBeenCalledWith('recursive-extender-name'); + expect(ctx.dynamicImport).toHaveBeenCalledWith("extender-name"); + expect(ctx.dynamicImport).toHaveBeenCalledWith("recursive-extender-name"); }); -test('uses prefix key recursively', async () => { - const input = {extends: ['extender-name']}; +test("uses prefix key recursively", async () => { + const input = { extends: ["extender-name"] }; const dynamicImport = (id: string) => { switch (id) { - case 'prefix-extender-name': - return {extends: ['recursive-extender-name']}; - case 'prefix-recursive-extender-name': - return {foo: 'bar'}; + case "prefix-extender-name": + return { extends: ["recursive-extender-name"] }; + case "prefix-recursive-extender-name": + return { foo: "bar" }; default: return {}; } @@ -190,24 +190,24 @@ test('uses prefix key recursively', async () => { await resolveExtends(input, { ...ctx, - prefix: 'prefix', + prefix: "prefix", }); - expect(ctx.dynamicImport).toHaveBeenCalledWith('prefix-extender-name'); + expect(ctx.dynamicImport).toHaveBeenCalledWith("prefix-extender-name"); expect(ctx.dynamicImport).toHaveBeenCalledWith( - 'prefix-recursive-extender-name' + "prefix-recursive-extender-name", ); }); -test('propagates contents recursively', async () => { - const input = {extends: ['extender-name']}; +test("propagates contents recursively", async () => { + const input = { extends: ["extender-name"] }; const dynamicImport = (id: string) => { switch (id) { - case 'extender-name': - return {extends: ['recursive-extender-name'], foo: 'bar'}; - case 'recursive-extender-name': - return {baz: 'bar'}; + case "extender-name": + return { extends: ["recursive-extender-name"], foo: "bar" }; + case "recursive-extender-name": + return { baz: "bar" }; default: return {}; } @@ -221,26 +221,26 @@ test('propagates contents recursively', async () => { const actual = await resolveExtends(input, ctx); const expected = { - extends: ['extender-name'], - foo: 'bar', - baz: 'bar', + extends: ["extender-name"], + foo: "bar", + baz: "bar", }; expect(actual).toEqual(expected); }); -test('propagates contents recursively with overlap', async () => { - const input: UserConfig = {extends: ['extender-name']}; +test("propagates contents recursively with overlap", async () => { + const input: UserConfig = { extends: ["extender-name"] }; const dynamicImport = (id: string): UserConfig => { switch (id) { - case 'extender-name': + case "extender-name": return { - extends: ['recursive-extender-name'], - rules: {rule: [RuleConfigSeverity.Warning, 'always']}, + extends: ["recursive-extender-name"], + rules: { rule: [RuleConfigSeverity.Warning, "always"] }, }; - case 'recursive-extender-name': - return {rules: {rule: [RuleConfigSeverity.Error, 'never', 'four']}}; + case "recursive-extender-name": + return { rules: { rule: [RuleConfigSeverity.Error, "never", "four"] } }; default: return {}; } @@ -254,27 +254,27 @@ test('propagates contents recursively with overlap', async () => { const actual = await resolveExtends(input, ctx); const expected: UserConfig = { - extends: ['extender-name'], + extends: ["extender-name"], rules: { - rule: [RuleConfigSeverity.Warning, 'always'], + rule: [RuleConfigSeverity.Warning, "always"], }, }; expect(actual).toEqual(expected); }); -test('extends rules from left to right with overlap', async () => { - const input: UserConfig = {extends: ['left', 'right']}; +test("extends rules from left to right with overlap", async () => { + const input: UserConfig = { extends: ["left", "right"] }; const dynamicImport = (id: string): UserConfig => { switch (id) { - case 'left': - return {rules: {a: [RuleConfigSeverity.Disabled, 'never', true]}}; - case 'right': + case "left": + return { rules: { a: [RuleConfigSeverity.Disabled, "never", true] } }; + case "right": return { rules: { - a: [RuleConfigSeverity.Disabled, 'never', false], - b: [RuleConfigSeverity.Disabled, 'never', true], + a: [RuleConfigSeverity.Disabled, "never", false], + b: [RuleConfigSeverity.Disabled, "never", true], }, }; default: @@ -290,32 +290,32 @@ test('extends rules from left to right with overlap', async () => { const actual = await resolveExtends(input, ctx); const expected: UserConfig = { - extends: ['left', 'right'], + extends: ["left", "right"], rules: { - a: [RuleConfigSeverity.Disabled, 'never', false], - b: [RuleConfigSeverity.Disabled, 'never', true], + a: [RuleConfigSeverity.Disabled, "never", false], + b: [RuleConfigSeverity.Disabled, "never", true], }, }; expect(actual).toEqual(expected); }); -test('extending contents should take precedence', async () => { - const input = {extends: ['extender-name'], zero: 'root'}; +test("extending contents should take precedence", async () => { + const input = { extends: ["extender-name"], zero: "root" }; const dynamicImport = (id: string) => { switch (id) { - case 'extender-name': - return {extends: ['recursive-extender-name'], zero: id, one: id}; - case 'recursive-extender-name': + case "extender-name": + return { extends: ["recursive-extender-name"], zero: id, one: id }; + case "recursive-extender-name": return { - extends: ['second-recursive-extender-name'], + extends: ["second-recursive-extender-name"], zero: id, one: id, two: id, }; - case 'second-recursive-extender-name': - return {zero: id, one: id, two: id, three: id}; + case "second-recursive-extender-name": + return { zero: id, one: id, two: id, three: id }; default: return {}; } @@ -329,30 +329,30 @@ test('extending contents should take precedence', async () => { const actual = await resolveExtends(input, ctx); const expected = { - extends: ['extender-name'], - zero: 'root', - one: 'extender-name', - two: 'recursive-extender-name', - three: 'second-recursive-extender-name', + extends: ["extender-name"], + zero: "root", + one: "extender-name", + two: "recursive-extender-name", + three: "second-recursive-extender-name", }; expect(actual).toEqual(expected); }); -test('should fall back to conventional-changelog-lint-config prefix', async () => { - const input = {extends: ['extender-name']}; +test("should fall back to conventional-changelog-lint-config prefix", async () => { + const input = { extends: ["extender-name"] }; const resolve = (id: string) => { - if (id === 'conventional-changelog-lint-config-extender-name') { - return 'conventional-changelog-lint-config-extender-name'; + if (id === "conventional-changelog-lint-config-extender-name") { + return "conventional-changelog-lint-config-extender-name"; } throw new Error(`Could not find module "*${id}"`); }; const dynamicImport = (id: string) => { switch (id) { - case 'conventional-changelog-lint-config-extender-name': - return {rules: {fallback: true}}; + case "conventional-changelog-lint-config-extender-name": + return { rules: { fallback: true } }; default: return {}; } @@ -365,31 +365,31 @@ test('should fall back to conventional-changelog-lint-config prefix', async () = const actual = await resolveExtends(input, { ...ctx, - prefix: 'prefix', + prefix: "prefix", }); expect(actual).toEqual({ - extends: ['extender-name'], + extends: ["extender-name"], rules: { fallback: true, }, }); }); -test('plugins should be merged correctly', async () => { - const input = {extends: ['extender-name'], zero: 'root'}; +test("plugins should be merged correctly", async () => { + const input = { extends: ["extender-name"], zero: "root" }; const dynamicImport = (id: string) => { switch (id) { - case 'extender-name': - return {extends: ['recursive-extender-name'], plugins: ['test']}; - case 'recursive-extender-name': + case "extender-name": + return { extends: ["recursive-extender-name"], plugins: ["test"] }; + case "recursive-extender-name": return { - extends: ['second-recursive-extender-name'], - plugins: ['test2'], + extends: ["second-recursive-extender-name"], + plugins: ["test2"], }; - case 'second-recursive-extender-name': - return {plugins: ['test3']}; + case "second-recursive-extender-name": + return { plugins: ["test3"] }; default: return {}; } @@ -403,34 +403,34 @@ test('plugins should be merged correctly', async () => { const actual = await resolveExtends(input, ctx); const expected = { - extends: ['extender-name'], - plugins: ['test3', 'test2', 'test'], - zero: 'root', + extends: ["extender-name"], + plugins: ["test3", "test2", "test"], + zero: "root", }; expect(actual).toEqual(expected); }); -test('rules should be merged correctly', async () => { +test("rules should be merged correctly", async () => { const input: UserConfig = { - extends: ['extender-name'], - rules: {test1: [RuleConfigSeverity.Warning, 'never', 'base']}, + extends: ["extender-name"], + rules: { test1: [RuleConfigSeverity.Warning, "never", "base"] }, }; const dynamicImport = (id: string): UserConfig => { switch (id) { - case 'extender-name': + case "extender-name": return { - extends: ['recursive-extender-name'], - rules: {test2: [RuleConfigSeverity.Error, 'never', id]}, + extends: ["recursive-extender-name"], + rules: { test2: [RuleConfigSeverity.Error, "never", id] }, }; - case 'recursive-extender-name': + case "recursive-extender-name": return { - extends: ['second-recursive-extender-name'], - rules: {test1: [RuleConfigSeverity.Disabled, 'never', id]}, + extends: ["second-recursive-extender-name"], + rules: { test1: [RuleConfigSeverity.Disabled, "never", id] }, }; - case 'second-recursive-extender-name': - return {rules: {test2: [RuleConfigSeverity.Warning, 'never', id]}}; + case "second-recursive-extender-name": + return { rules: { test2: [RuleConfigSeverity.Warning, "never", id] } }; default: return {}; } @@ -444,10 +444,10 @@ test('rules should be merged correctly', async () => { const actual = await resolveExtends(input, ctx); const expected: UserConfig = { - extends: ['extender-name'], + extends: ["extender-name"], rules: { - test1: [RuleConfigSeverity.Warning, 'never', 'base'], - test2: [RuleConfigSeverity.Error, 'never', 'extender-name'], + test1: [RuleConfigSeverity.Warning, "never", "base"], + test2: [RuleConfigSeverity.Error, "never", "extender-name"], }, }; @@ -455,23 +455,23 @@ test('rules should be merged correctly', async () => { }); // https://github.com/conventional-changelog/commitlint/issues/327 -test('parserPreset should resolve correctly in extended configuration', async () => { - const input = {extends: ['extender-name'], zero: 'root'}; +test("parserPreset should resolve correctly in extended configuration", async () => { + const input = { extends: ["extender-name"], zero: "root" }; const dynamicImport = (id: string) => { switch (id) { - case 'extender-name': + case "extender-name": return { - extends: ['recursive-extender-name'], + extends: ["recursive-extender-name"], parserPreset: { parserOpts: { - issuePrefixes: ['#', '!', '&', 'no-references'], + issuePrefixes: ["#", "!", "&", "no-references"], referenceActions: null, }, }, }; - case 'recursive-extender-name': - return {parserPreset: {parserOpts: {issuePrefixes: ['#', '!']}}}; + case "recursive-extender-name": + return { parserPreset: { parserOpts: { issuePrefixes: ["#", "!"] } } }; default: return {}; } @@ -485,35 +485,35 @@ test('parserPreset should resolve correctly in extended configuration', async () const actual = await resolveExtends(input, ctx); const expected = { - extends: ['extender-name'], + extends: ["extender-name"], parserPreset: { parserOpts: { - issuePrefixes: ['#', '!', '&', 'no-references'], + issuePrefixes: ["#", "!", "&", "no-references"], referenceActions: null, }, }, - zero: 'root', + zero: "root", }; expect(actual).toEqual(expected); }); -test('parserPreset should be merged correctly', async () => { - const input = {extends: ['extender-name'], zero: 'root'}; +test("parserPreset should be merged correctly", async () => { + const input = { extends: ["extender-name"], zero: "root" }; const dynamicImport = (id: string) => { switch (id) { - case 'extender-name': + case "extender-name": return { - extends: ['recursive-extender-name'], + extends: ["recursive-extender-name"], parserPreset: { parserOpts: { referenceActions: null, }, }, }; - case 'recursive-extender-name': - return {parserPreset: {parserOpts: {issuePrefixes: ['#', '!']}}}; + case "recursive-extender-name": + return { parserPreset: { parserOpts: { issuePrefixes: ["#", "!"] } } }; default: return {}; } @@ -527,39 +527,39 @@ test('parserPreset should be merged correctly', async () => { const actual = await resolveExtends(input, ctx); const expected = { - extends: ['extender-name'], + extends: ["extender-name"], parserPreset: { parserOpts: { - issuePrefixes: ['#', '!'], + issuePrefixes: ["#", "!"], referenceActions: null, }, }, - zero: 'root', + zero: "root", }; expect(actual).toEqual(expected); }); -test('should correctly merge nested configs', async () => { - const input = {extends: ['extender-1']}; +test("should correctly merge nested configs", async () => { + const input = { extends: ["extender-1"] }; const dynamicImport = (id: string) => { switch (id) { - case 'extender-1': - return {extends: ['extender-3', 'extender-2']}; - case 'extender-2': - return {extends: ['extender-4']}; - case 'extender-3': - return {rules: {test: [RuleConfigSeverity.Warning, 'never', 3]}}; - case 'extender-4': + case "extender-1": + return { extends: ["extender-3", "extender-2"] }; + case "extender-2": + return { extends: ["extender-4"] }; + case "extender-3": + return { rules: { test: [RuleConfigSeverity.Warning, "never", 3] } }; + case "extender-4": return { - extends: ['extender-5', 'extender-6'], - rules: {test: [RuleConfigSeverity.Warning, 'never', 4]}, + extends: ["extender-5", "extender-6"], + rules: { test: [RuleConfigSeverity.Warning, "never", 4] }, }; - case 'extender-5': - return {rules: {test: [RuleConfigSeverity.Warning, 'never', 5]}}; - case 'extender-6': - return {rules: {test: [RuleConfigSeverity.Warning, 'never', 6]}}; + case "extender-5": + return { rules: { test: [RuleConfigSeverity.Warning, "never", 5] } }; + case "extender-6": + return { rules: { test: [RuleConfigSeverity.Warning, "never", 6] } }; default: return {}; } @@ -573,9 +573,9 @@ test('should correctly merge nested configs', async () => { const actual = await resolveExtends(input, ctx); const expected = { - extends: ['extender-1'], + extends: ["extender-1"], rules: { - test: [RuleConfigSeverity.Warning, 'never', 4], + test: [RuleConfigSeverity.Warning, "never", 4], }, }; diff --git a/@commitlint/resolve-extends/src/index.ts b/@commitlint/resolve-extends/src/index.ts index f31a3458ca..8c6942db27 100644 --- a/@commitlint/resolve-extends/src/index.ts +++ b/@commitlint/resolve-extends/src/index.ts @@ -1,32 +1,32 @@ -import fs from 'node:fs'; -import path from 'node:path'; -import {pathToFileURL, fileURLToPath} from 'node:url'; +import fs from "node:fs"; +import path from "node:path"; +import { pathToFileURL, fileURLToPath } from "node:url"; -import globalDirectory from 'global-directory'; -import {moduleResolve} from 'import-meta-resolve'; -import mergeWith from 'lodash.mergewith'; -import resolveFrom_ from 'resolve-from'; -import {validateConfig} from '@commitlint/config-validator'; -import type {ParserPreset, UserConfig} from '@commitlint/types'; +import globalDirectory from "global-directory"; +import { moduleResolve } from "import-meta-resolve"; +import mergeWith from "lodash.mergewith"; +import resolveFrom_ from "resolve-from"; +import { validateConfig } from "@commitlint/config-validator"; +import type { ParserPreset, UserConfig } from "@commitlint/types"; const dynamicImport = async <T>(id: string): Promise<T> => { const imported = await import( path.isAbsolute(id) ? pathToFileURL(id).toString() : id ); - return ('default' in imported && imported.default) || imported; + return ("default" in imported && imported.default) || imported; }; const pathSuffixes = [ - '', - '.js', - '.json', + "", + ".js", + ".json", `${path.sep}index.js`, `${path.sep}index.json`, ]; -const specifierSuffixes = ['', '.js', '.json', '/index.js', '/index.json']; +const specifierSuffixes = ["", ".js", ".json", "/index.js", "/index.json"]; -const conditions = new Set(['import', 'node']); +const conditions = new Set(["import", "node"]); /** * @see moduleResolve @@ -46,9 +46,9 @@ export const resolveFrom = (lookup: string, parent?: string): string => { const base = pathToFileURL( parent ? fs.statSync(parent).isDirectory() - ? path.join(parent, 'noop.js') + ? path.join(parent, "noop.js") : parent - : import.meta.url + : import.meta.url, ); for (const suffix of specifierSuffixes) { @@ -78,14 +78,14 @@ export const resolveFrom = (lookup: string, parent?: string): string => { * @returns path and parserOpts function retrieved from `resolvedParserPreset` */ export const loadParserPreset = async ( - resolvedParserPreset: string -): Promise<Pick<ParserPreset, 'path' | 'parserOpts'>> => { + resolvedParserPreset: string, +): Promise<Pick<ParserPreset, "path" | "parserOpts">> => { const finalParserOpts = await dynamicImport(resolvedParserPreset); const relativeParserPath = path.relative(process.cwd(), resolvedParserPreset); return { - path: `./${relativeParserPath}`.split(path.sep).join('/'), + path: `./${relativeParserPath}`.split(path.sep).join("/"), parserOpts: finalParserOpts, }; }; @@ -94,22 +94,22 @@ export interface ResolveExtendsContext { cwd?: string; parserPreset?: string | ParserPreset; prefix?: string; - resolve?(id: string, ctx?: {prefix?: string; cwd?: string}): string; + resolve?(id: string, ctx?: { prefix?: string; cwd?: string }): string; resolveGlobal?: (id: string) => string; dynamicImport?<T>(id: string): T | Promise<T>; } export default async function resolveExtends( config: UserConfig = {}, - context: ResolveExtendsContext = {} + context: ResolveExtendsContext = {}, ): Promise<UserConfig> { - const {extends: e} = config; + const { extends: e } = config; const extended = await loadExtends(config, context); extended.push(config); return extended.reduce( - (r, {extends: _, ...c}) => + (r, { extends: _, ...c }) => mergeWith(r, c, (objValue, srcValue, key) => { - if (key === 'plugins') { + if (key === "plugins") { if (Array.isArray(objValue)) { return objValue.concat(srcValue); } @@ -117,15 +117,15 @@ export default async function resolveExtends( return srcValue; } }), - e ? {extends: e} : {} + e ? { extends: e } : {}, ); } async function loadExtends( config: UserConfig = {}, - context: ResolveExtendsContext = {} + context: ResolveExtendsContext = {}, ): Promise<UserConfig[]> { - const {extends: e} = config; + const { extends: e } = config; const ext = e ? (Array.isArray(e) ? e : [e]) : []; return await ext.reduce(async (configs, raw) => { @@ -135,13 +135,13 @@ async function loadExtends( parserPreset?: string; }>(resolved); const cwd = path.dirname(resolved); - const ctx = {...context, cwd}; + const ctx = { ...context, cwd }; // Resolve parser preset if none was present before if ( !context.parserPreset && - typeof c === 'object' && - typeof c.parserPreset === 'string' + typeof c === "object" && + typeof c.parserPreset === "string" ) { const resolvedParserPreset = resolveFrom(c.parserPreset, cwd); @@ -160,22 +160,22 @@ async function loadExtends( }, Promise.resolve<UserConfig[]>([])); } -function getId(raw: string = '', prefix: string = ''): string { +function getId(raw: string = "", prefix: string = ""): string { const first = raw.charAt(0); - const scoped = first === '@'; - const relative = first === '.'; + const scoped = first === "@"; + const relative = first === "."; const absolute = path.isAbsolute(raw); if (scoped) { - return raw.includes('/') ? raw : [raw, prefix].filter(String).join('/'); + return raw.includes("/") ? raw : [raw, prefix].filter(String).join("/"); } - return relative || absolute ? raw : [prefix, raw].filter(String).join('-'); + return relative || absolute ? raw : [prefix, raw].filter(String).join("-"); } function resolveConfig( raw: string, - context: ResolveExtendsContext = {} + context: ResolveExtendsContext = {}, ): string { const resolve = context.resolve || resolveId; const id = getId(raw, context.prefix); @@ -184,10 +184,10 @@ function resolveConfig( try { resolved = resolve(id, context); } catch (err) { - const legacy = getId(raw, 'conventional-changelog-lint-config'); + const legacy = getId(raw, "conventional-changelog-lint-config"); resolved = resolve(legacy, context); console.warn( - `Resolving ${raw} to legacy config ${legacy}. To silence this warning raise an issue at 'npm repo ${legacy}' to rename to ${id}.` + `Resolving ${raw} to legacy config ${legacy}. To silence this warning raise an issue at 'npm repo ${legacy}' to rename to ${id}.`, ); } @@ -196,29 +196,29 @@ function resolveConfig( function resolveId( specifier: string, - context: ResolveExtendsContext = {} + context: ResolveExtendsContext = {}, ): string { const cwd = context.cwd || process.cwd(); const localPath = resolveFromSilent(specifier, cwd); - if (typeof localPath === 'string') { + if (typeof localPath === "string") { return localPath; } const resolveGlobal = context.resolveGlobal || resolveGlobalSilent; const globalPath = resolveGlobal(specifier); - if (typeof globalPath === 'string') { + if (typeof globalPath === "string") { return globalPath; } const err = new Error(`Cannot find module "${specifier}" from "${cwd}"`); - throw Object.assign(err, {code: 'MODULE_NOT_FOUND'}); + throw Object.assign(err, { code: "MODULE_NOT_FOUND" }); } export function resolveFromSilent( specifier: string, - parent: string + parent: string, ): string | void { try { return resolveFrom(specifier, parent); diff --git a/@commitlint/resolve-extends/tsconfig.json b/@commitlint/resolve-extends/tsconfig.json index d424776e00..ebcddb79e9 100644 --- a/@commitlint/resolve-extends/tsconfig.json +++ b/@commitlint/resolve-extends/tsconfig.json @@ -8,5 +8,5 @@ }, "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../types"}, {"path": "../config-validator"}] + "references": [{ "path": "../types" }, { "path": "../config-validator" }] } diff --git a/@commitlint/rules/src/body-case.test.ts b/@commitlint/rules/src/body-case.test.ts index 4bff32d233..9ff7b5dc23 100644 --- a/@commitlint/rules/src/body-case.test.ts +++ b/@commitlint/rules/src/body-case.test.ts @@ -1,12 +1,12 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {bodyCase} from './body-case.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { bodyCase } from "./body-case.js"; const messages = { - empty: 'test: subject', - lowercase: 'test: subject\nbody', - mixedcase: 'test: subject\nBody', - uppercase: 'test: subject\nBODY', + empty: "test: subject", + lowercase: "test: subject\nbody", + mixedcase: "test: subject\nBody", + uppercase: "test: subject\nBODY", }; const parsed = { @@ -17,73 +17,73 @@ const parsed = { }; test('with empty body should succeed for "never lowercase"', async () => { - const [actual] = bodyCase(await parsed.empty, 'never', 'lowercase'); + const [actual] = bodyCase(await parsed.empty, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty body should succeed for "always lowercase"', async () => { - const [actual] = bodyCase(await parsed.empty, 'always', 'lowercase'); + const [actual] = bodyCase(await parsed.empty, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty body should succeed for "never uppercase"', async () => { - const [actual] = bodyCase(await parsed.empty, 'never', 'uppercase'); + const [actual] = bodyCase(await parsed.empty, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty body should succeed for "always uppercase"', async () => { - const [actual] = bodyCase(await parsed.empty, 'always', 'uppercase'); + const [actual] = bodyCase(await parsed.empty, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with lowercase body should fail for "never lowercase"', async () => { - const [actual] = bodyCase(await parsed.lowercase, 'never', 'lowercase'); + const [actual] = bodyCase(await parsed.lowercase, "never", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with lowercase body should succeed for "always lowercase"', async () => { - const [actual] = bodyCase(await parsed.lowercase, 'always', 'lowercase'); + const [actual] = bodyCase(await parsed.lowercase, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase body should succeed for "never lowercase"', async () => { - const [actual] = bodyCase(await parsed.mixedcase, 'never', 'lowercase'); + const [actual] = bodyCase(await parsed.mixedcase, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase body should fail for "always lowercase"', async () => { - const [actual] = bodyCase(await parsed.mixedcase, 'always', 'lowercase'); + const [actual] = bodyCase(await parsed.mixedcase, "always", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase body should succeed for "never uppercase"', async () => { - const [actual] = bodyCase(await parsed.mixedcase, 'never', 'uppercase'); + const [actual] = bodyCase(await parsed.mixedcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase body should fail for "always uppercase"', async () => { - const [actual] = bodyCase(await parsed.mixedcase, 'always', 'uppercase'); + const [actual] = bodyCase(await parsed.mixedcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with uppercase body should fail for "never uppercase"', async () => { - const [actual] = bodyCase(await parsed.uppercase, 'never', 'uppercase'); + const [actual] = bodyCase(await parsed.uppercase, "never", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with lowercase body should succeed for "always uppercase"', async () => { - const [actual] = bodyCase(await parsed.uppercase, 'always', 'uppercase'); + const [actual] = bodyCase(await parsed.uppercase, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/body-case.ts b/@commitlint/rules/src/body-case.ts index 6c0291c22d..3870fb6238 100644 --- a/@commitlint/rules/src/body-case.ts +++ b/@commitlint/rules/src/body-case.ts @@ -1,24 +1,24 @@ -import {case as ensureCase} from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {TargetCaseType, SyncRule} from '@commitlint/types'; +import { case as ensureCase } from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { TargetCaseType, SyncRule } from "@commitlint/types"; -const negated = (when?: string) => when === 'never'; +const negated = (when?: string) => when === "never"; export const bodyCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( parsed, - when = 'always', - value = [] + when = "always", + value = [], ) => { - const {body} = parsed; + const { body } = parsed; if (!body) { return [true]; } const checks = (Array.isArray(value) ? value : [value]).map((check) => { - if (typeof check === 'string') { + if (typeof check === "string") { return { - when: 'always', + when: "always", case: check, }; } @@ -30,7 +30,7 @@ export const bodyCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( return negated(check.when) ? !r : r; }); - const list = checks.map((c) => c.case).join(', '); + const list = checks.map((c) => c.case).join(", "); return [ negated(when) ? !result : result, diff --git a/@commitlint/rules/src/body-empty.test.ts b/@commitlint/rules/src/body-empty.test.ts index 1150957207..fb1f82cbe9 100644 --- a/@commitlint/rules/src/body-empty.test.ts +++ b/@commitlint/rules/src/body-empty.test.ts @@ -1,10 +1,10 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {bodyEmpty} from './body-empty.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { bodyEmpty } from "./body-empty.js"; const messages = { - empty: 'test: subject', - filled: 'test: subject\nbody', + empty: "test: subject", + filled: "test: subject\nbody", }; const parsed = { @@ -12,38 +12,38 @@ const parsed = { filled: parse(messages.filled), }; -test('with empty body should succeed for empty keyword', async () => { +test("with empty body should succeed for empty keyword", async () => { const [actual] = bodyEmpty(await parsed.empty); const expected = true; expect(actual).toEqual(expected); }); test('with empty body should fail for "never"', async () => { - const [actual] = bodyEmpty(await parsed.empty, 'never'); + const [actual] = bodyEmpty(await parsed.empty, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with empty body should succeed for "always"', async () => { - const [actual] = bodyEmpty(await parsed.empty, 'always'); + const [actual] = bodyEmpty(await parsed.empty, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with body should fail for empty keyword', async () => { +test("with body should fail for empty keyword", async () => { const [actual] = bodyEmpty(await parsed.filled); const expected = false; expect(actual).toEqual(expected); }); test('with body should succeed for "never"', async () => { - const [actual] = bodyEmpty(await parsed.filled, 'never'); + const [actual] = bodyEmpty(await parsed.filled, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with body should fail for "always"', async () => { - const [actual] = bodyEmpty(await parsed.filled, 'always'); + const [actual] = bodyEmpty(await parsed.filled, "always"); const expected = false; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/body-empty.ts b/@commitlint/rules/src/body-empty.ts index 76ddc72ae6..520f251acb 100644 --- a/@commitlint/rules/src/body-empty.ts +++ b/@commitlint/rules/src/body-empty.ts @@ -1,13 +1,13 @@ -import * as ensure from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import * as ensure from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; -export const bodyEmpty: SyncRule = (parsed, when = 'always') => { - const negated = when === 'never'; - const notEmpty = ensure.notEmpty(parsed.body || ''); +export const bodyEmpty: SyncRule = (parsed, when = "always") => { + const negated = when === "never"; + const notEmpty = ensure.notEmpty(parsed.body || ""); return [ negated ? notEmpty : !notEmpty, - message(['body', negated ? 'may not' : 'must', 'be empty']), + message(["body", negated ? "may not" : "must", "be empty"]), ]; }; diff --git a/@commitlint/rules/src/body-full-stop.test.ts b/@commitlint/rules/src/body-full-stop.test.ts index d84d3629d1..0c08f7b8c1 100644 --- a/@commitlint/rules/src/body-full-stop.test.ts +++ b/@commitlint/rules/src/body-full-stop.test.ts @@ -1,9 +1,9 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {bodyFullStop} from './body-full-stop.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { bodyFullStop } from "./body-full-stop.js"; const messages = { - empty: 'test:\n', + empty: "test:\n", with: `test: subject\n\nbody.`, without: `test: subject\n\nbody`, }; @@ -15,37 +15,37 @@ const parsed = { }; test('empty against "always" should succeed', async () => { - const [actual] = bodyFullStop(await parsed.empty, 'always', '.'); + const [actual] = bodyFullStop(await parsed.empty, "always", "."); const expected = true; expect(actual).toEqual(expected); }); test('empty against "never ." should succeed', async () => { - const [actual] = bodyFullStop(await parsed.empty, 'never', '.'); + const [actual] = bodyFullStop(await parsed.empty, "never", "."); const expected = true; expect(actual).toEqual(expected); }); test('with against "always ." should succeed', async () => { - const [actual] = bodyFullStop(await parsed.with, 'always', '.'); + const [actual] = bodyFullStop(await parsed.with, "always", "."); const expected = true; expect(actual).toEqual(expected); }); test('with against "never ." should fail', async () => { - const [actual] = bodyFullStop(await parsed.with, 'never', '.'); + const [actual] = bodyFullStop(await parsed.with, "never", "."); const expected = false; expect(actual).toEqual(expected); }); test('without against "always ." should fail', async () => { - const [actual] = bodyFullStop(await parsed.without, 'always', '.'); + const [actual] = bodyFullStop(await parsed.without, "always", "."); const expected = false; expect(actual).toEqual(expected); }); test('without against "never ." should succeed', async () => { - const [actual] = bodyFullStop(await parsed.without, 'never', '.'); + const [actual] = bodyFullStop(await parsed.without, "never", "."); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/body-full-stop.ts b/@commitlint/rules/src/body-full-stop.ts index 61d79ec7c8..845b0f5790 100644 --- a/@commitlint/rules/src/body-full-stop.ts +++ b/@commitlint/rules/src/body-full-stop.ts @@ -1,10 +1,10 @@ -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; export const bodyFullStop: SyncRule<string> = ( parsed, - when = 'always', - value = '.' + when = "always", + value = ".", ) => { const input = parsed.body; @@ -12,11 +12,11 @@ export const bodyFullStop: SyncRule<string> = ( return [true]; } - const negated = when === 'never'; + const negated = when === "never"; const hasStop = input[input.length - 1] === value; return [ negated ? !hasStop : hasStop, - message(['body', negated ? 'may not' : 'must', 'end with full stop']), + message(["body", negated ? "may not" : "must", "end with full stop"]), ]; }; diff --git a/@commitlint/rules/src/body-leading-blank.test.ts b/@commitlint/rules/src/body-leading-blank.test.ts index 9c63a34d23..a30e243afa 100644 --- a/@commitlint/rules/src/body-leading-blank.test.ts +++ b/@commitlint/rules/src/body-leading-blank.test.ts @@ -1,11 +1,11 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {bodyLeadingBlank} from './body-leading-blank.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { bodyLeadingBlank } from "./body-leading-blank.js"; const messages = { - simple: 'test: subject', - without: 'test: subject\nbody', - with: 'test: subject\n\nbody', + simple: "test: subject", + without: "test: subject\nbody", + with: "test: subject\n\nbody", }; const parsed = { @@ -14,56 +14,56 @@ const parsed = { with: parse(messages.with), }; -test('with simple message should succeed for empty keyword', async () => { +test("with simple message should succeed for empty keyword", async () => { const [actual] = bodyLeadingBlank(await parsed.simple); const expected = true; expect(actual).toEqual(expected); }); test('with simple message should succeed for "never"', async () => { - const [actual] = bodyLeadingBlank(await parsed.simple, 'never'); + const [actual] = bodyLeadingBlank(await parsed.simple, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with simple message should succeed for "always"', async () => { - const [actual] = bodyLeadingBlank(await parsed.simple, 'always'); + const [actual] = bodyLeadingBlank(await parsed.simple, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('without blank line before body should fail for empty keyword', async () => { +test("without blank line before body should fail for empty keyword", async () => { const [actual] = bodyLeadingBlank(await parsed.without); const expected = false; expect(actual).toEqual(expected); }); test('without blank line before body should succeed for "never"', async () => { - const [actual] = bodyLeadingBlank(await parsed.without, 'never'); + const [actual] = bodyLeadingBlank(await parsed.without, "never"); const expected = true; expect(actual).toEqual(expected); }); test('without blank line before body should fail for "always"', async () => { - const [actual] = bodyLeadingBlank(await parsed.without, 'always'); + const [actual] = bodyLeadingBlank(await parsed.without, "always"); const expected = false; expect(actual).toEqual(expected); }); -test('with blank line before body should succeed for empty keyword', async () => { +test("with blank line before body should succeed for empty keyword", async () => { const [actual] = bodyLeadingBlank(await parsed.with); const expected = true; expect(actual).toEqual(expected); }); test('with blank line before body should fail for "never"', async () => { - const [actual] = bodyLeadingBlank(await parsed.with, 'never'); + const [actual] = bodyLeadingBlank(await parsed.with, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with blank line before body should succeed for "always"', async () => { - const [actual] = bodyLeadingBlank(await parsed.with, 'always'); + const [actual] = bodyLeadingBlank(await parsed.with, "always"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/body-leading-blank.ts b/@commitlint/rules/src/body-leading-blank.ts index 36a4ce7d5e..ae55973341 100644 --- a/@commitlint/rules/src/body-leading-blank.ts +++ b/@commitlint/rules/src/body-leading-blank.ts @@ -1,6 +1,6 @@ -import toLines from '@commitlint/to-lines'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import toLines from "@commitlint/to-lines"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; export const bodyLeadingBlank: SyncRule = (parsed, when) => { // Flunk if no body is found @@ -8,14 +8,14 @@ export const bodyLeadingBlank: SyncRule = (parsed, when) => { return [true]; } - const negated = when === 'never'; + const negated = when === "never"; const [leading] = toLines(parsed.raw).slice(1); // Check if the first line of body is empty - const succeeds = leading === ''; + const succeeds = leading === ""; return [ negated ? !succeeds : succeeds, - message(['body', negated ? 'may not' : 'must', 'have leading blank line']), + message(["body", negated ? "may not" : "must", "have leading blank line"]), ]; }; diff --git a/@commitlint/rules/src/body-max-length.test.ts b/@commitlint/rules/src/body-max-length.test.ts index fb22498d64..0b85c58b0f 100644 --- a/@commitlint/rules/src/body-max-length.test.ts +++ b/@commitlint/rules/src/body-max-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {bodyMaxLength} from './body-max-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { bodyMaxLength } from "./body-max-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = short.length; const messages = { - empty: 'test: subject', + empty: "test: subject", short: `test: subject\n${short}`, long: `test: subject\n${long}`, }; @@ -19,19 +19,19 @@ const parsed = { long: parse(messages.long), }; -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = bodyMaxLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should succeed', async () => { +test("with short should succeed", async () => { const [actual] = bodyMaxLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long should fail', async () => { +test("with long should fail", async () => { const [actual] = bodyMaxLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/body-max-length.ts b/@commitlint/rules/src/body-max-length.ts index 9121129056..2b0ca2f1b2 100644 --- a/@commitlint/rules/src/body-max-length.ts +++ b/@commitlint/rules/src/body-max-length.ts @@ -1,10 +1,10 @@ -import {maxLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { maxLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const bodyMaxLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.body; diff --git a/@commitlint/rules/src/body-max-line-length.test.ts b/@commitlint/rules/src/body-max-line-length.test.ts index d2a4628415..26974ca6cc 100644 --- a/@commitlint/rules/src/body-max-line-length.test.ts +++ b/@commitlint/rules/src/body-max-line-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {bodyMaxLineLength} from './body-max-line-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { bodyMaxLineLength } from "./body-max-line-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = short.length; const messages = { - empty: 'test: subject', + empty: "test: subject", short: `test: subject\n${short}`, long: `test: subject\n${long}`, shortMultipleLines: `test:subject\n${short}\n${short}\n${short}`, @@ -21,31 +21,31 @@ const parsed = { long: parse(messages.long), }; -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = bodyMaxLineLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should succeed', async () => { +test("with short should succeed", async () => { const [actual] = bodyMaxLineLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long should fail', async () => { +test("with long should fail", async () => { const [actual] = bodyMaxLineLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); }); -test('with short with multiple lines should succeed', async () => { +test("with short with multiple lines should succeed", async () => { const [actual] = bodyMaxLineLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long with multiple lines should fail', async () => { +test("with long with multiple lines should fail", async () => { const [actual] = bodyMaxLineLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/body-max-line-length.ts b/@commitlint/rules/src/body-max-line-length.ts index 5e937ef7e9..5049b09eec 100644 --- a/@commitlint/rules/src/body-max-line-length.ts +++ b/@commitlint/rules/src/body-max-line-length.ts @@ -1,10 +1,10 @@ -import {maxLineLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { maxLineLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const bodyMaxLineLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.body; diff --git a/@commitlint/rules/src/body-min-length.test.ts b/@commitlint/rules/src/body-min-length.test.ts index 33d8e57475..bc9413c14e 100644 --- a/@commitlint/rules/src/body-min-length.test.ts +++ b/@commitlint/rules/src/body-min-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {bodyMinLength} from './body-min-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { bodyMinLength } from "./body-min-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = long.length; const messages = { - simple: 'test: subject', + simple: "test: subject", short: `test: subject\n${short}`, long: `test: subject\n${long}`, }; @@ -19,19 +19,19 @@ const parsed = { long: parse(messages.long), }; -test('with simple should succeed', async () => { +test("with simple should succeed", async () => { const [actual] = bodyMinLength(await parsed.simple, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should fail', async () => { +test("with short should fail", async () => { const [actual] = bodyMinLength(await parsed.short, undefined, value); const expected = false; expect(actual).toEqual(expected); }); -test('with long should succeed', async () => { +test("with long should succeed", async () => { const [actual] = bodyMinLength(await parsed.long, undefined, value); const expected = true; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/body-min-length.ts b/@commitlint/rules/src/body-min-length.ts index f769e1a4a9..958e39af0c 100644 --- a/@commitlint/rules/src/body-min-length.ts +++ b/@commitlint/rules/src/body-min-length.ts @@ -1,10 +1,10 @@ -import {minLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { minLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const bodyMinLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { if (!parsed.body) { return [true]; diff --git a/@commitlint/rules/src/footer-empty.test.ts b/@commitlint/rules/src/footer-empty.test.ts index bfe001c7b2..da98f6541b 100644 --- a/@commitlint/rules/src/footer-empty.test.ts +++ b/@commitlint/rules/src/footer-empty.test.ts @@ -1,11 +1,11 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {footerEmpty} from './footer-empty.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { footerEmpty } from "./footer-empty.js"; const messages = { - simple: 'test: subject', - empty: 'test: subject\nbody', - filled: 'test: subject\nBREAKING CHANGE: something important', + simple: "test: subject", + empty: "test: subject\nbody", + filled: "test: subject\nBREAKING CHANGE: something important", }; const parsed = { @@ -14,56 +14,56 @@ const parsed = { filled: parse(messages.filled), }; -test('with simple message should succeed for empty keyword', async () => { +test("with simple message should succeed for empty keyword", async () => { const [actual] = footerEmpty(await parsed.simple); const expected = true; expect(actual).toEqual(expected); }); test('with simple message should fail for "never"', async () => { - const [actual] = footerEmpty(await parsed.simple, 'never'); + const [actual] = footerEmpty(await parsed.simple, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with simple message should succeed for "always"', async () => { - const [actual] = footerEmpty(await parsed.simple, 'always'); + const [actual] = footerEmpty(await parsed.simple, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with empty footer should succeed for empty keyword', async () => { +test("with empty footer should succeed for empty keyword", async () => { const [actual] = footerEmpty(await parsed.empty); const expected = true; expect(actual).toEqual(expected); }); test('with empty footer should fail for "never"', async () => { - const [actual] = footerEmpty(await parsed.empty, 'never'); + const [actual] = footerEmpty(await parsed.empty, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with empty footer should succeed for "always"', async () => { - const [actual] = footerEmpty(await parsed.empty, 'always'); + const [actual] = footerEmpty(await parsed.empty, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with footer should fail for empty keyword', async () => { +test("with footer should fail for empty keyword", async () => { const [actual] = footerEmpty(await parsed.filled); const expected = false; expect(actual).toEqual(expected); }); test('with footer should succeed for "never"', async () => { - const [actual] = footerEmpty(await parsed.filled, 'never'); + const [actual] = footerEmpty(await parsed.filled, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with footer should fail for "always"', async () => { - const [actual] = footerEmpty(await parsed.filled, 'always'); + const [actual] = footerEmpty(await parsed.filled, "always"); const expected = false; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/footer-empty.ts b/@commitlint/rules/src/footer-empty.ts index 9a3d8a81c1..c007f025c8 100644 --- a/@commitlint/rules/src/footer-empty.ts +++ b/@commitlint/rules/src/footer-empty.ts @@ -1,13 +1,13 @@ -import * as ensure from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import * as ensure from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; -export const footerEmpty: SyncRule = (parsed, when = 'always') => { - const negated = when === 'never'; - const notEmpty = ensure.notEmpty(parsed.footer || ''); +export const footerEmpty: SyncRule = (parsed, when = "always") => { + const negated = when === "never"; + const notEmpty = ensure.notEmpty(parsed.footer || ""); return [ negated ? notEmpty : !notEmpty, - message(['footer', negated ? 'may not' : 'must', 'be empty']), + message(["footer", negated ? "may not" : "must", "be empty"]), ]; }; diff --git a/@commitlint/rules/src/footer-leading-blank.test.ts b/@commitlint/rules/src/footer-leading-blank.test.ts index a0566a9ae8..8e17c4d343 100644 --- a/@commitlint/rules/src/footer-leading-blank.test.ts +++ b/@commitlint/rules/src/footer-leading-blank.test.ts @@ -1,20 +1,20 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {footerLeadingBlank} from './footer-leading-blank.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { footerLeadingBlank } from "./footer-leading-blank.js"; const messages = { - simple: 'test: subject', - body: 'test: subject\nbody', - trailing: 'test: subject\nbody\n\n', - without: 'test: subject\nbody\nBREAKING CHANGE: something important', + simple: "test: subject", + body: "test: subject\nbody", + trailing: "test: subject\nbody\n\n", + without: "test: subject\nbody\nBREAKING CHANGE: something important", withoutBody: - 'feat(new-parser): introduces a new parsing library\n\nBREAKING CHANGE: new library does not support foo-construct', + "feat(new-parser): introduces a new parsing library\n\nBREAKING CHANGE: new library does not support foo-construct", withBodyWithComment: - 'feat(new-parser): introduces a new parsing library\n\nBody Line 1\n# comment\nBody Line 2\n\nBREAKING CHANGE: new library does not support foo-construct', - with: 'test: subject\nbody\n\nBREAKING CHANGE: something important', + "feat(new-parser): introduces a new parsing library\n\nBody Line 1\n# comment\nBody Line 2\n\nBREAKING CHANGE: new library does not support foo-construct", + with: "test: subject\nbody\n\nBREAKING CHANGE: something important", withMulitLine: - 'test: subject\nmulti\nline\nbody\n\nBREAKING CHANGE: something important', - withDoubleNewLine: 'fix: some issue\n\ndetailed explanation\n\ncloses #123', + "test: subject\nmulti\nline\nbody\n\nBREAKING CHANGE: something important", + withDoubleNewLine: "fix: some issue\n\ndetailed explanation\n\ncloses #123", }; const parsed = { @@ -24,141 +24,141 @@ const parsed = { without: parse(messages.without), withoutBody: parse(messages.withoutBody), withBodyWithComment: parse(messages.withBodyWithComment, undefined, { - commentChar: '#', + commentChar: "#", }), with: parse(messages.with), withMulitLine: parse(messages.withMulitLine), withDoubleNewLine: parse(messages.withDoubleNewLine), }; -test('with simple message should succeed for empty keyword', async () => { +test("with simple message should succeed for empty keyword", async () => { const [actual] = footerLeadingBlank(await parsed.simple); const expected = true; expect(actual).toEqual(expected); }); test('with simple message should succeed for "never"', async () => { - const [actual] = footerLeadingBlank(await parsed.simple, 'never'); + const [actual] = footerLeadingBlank(await parsed.simple, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with simple message should succeed for "always"', async () => { - const [actual] = footerLeadingBlank(await parsed.simple, 'always'); + const [actual] = footerLeadingBlank(await parsed.simple, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with body message should succeed for empty keyword', async () => { +test("with body message should succeed for empty keyword", async () => { const [actual] = footerLeadingBlank(await parsed.body); const expected = true; expect(actual).toEqual(expected); }); test('with body message should succeed for "never"', async () => { - const [actual] = footerLeadingBlank(await parsed.body, 'never'); + const [actual] = footerLeadingBlank(await parsed.body, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with body message should succeed for "always"', async () => { - const [actual] = footerLeadingBlank(await parsed.body, 'always'); + const [actual] = footerLeadingBlank(await parsed.body, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with trailing message should succeed for empty keyword', async () => { +test("with trailing message should succeed for empty keyword", async () => { const [actual] = footerLeadingBlank(await parsed.trailing); const expected = true; expect(actual).toEqual(expected); }); test('with trailing message should succeed for "never"', async () => { - const [actual] = footerLeadingBlank(await parsed.trailing, 'never'); + const [actual] = footerLeadingBlank(await parsed.trailing, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with trailing message should succeed for "always"', async () => { - const [actual] = footerLeadingBlank(await parsed.trailing, 'always'); + const [actual] = footerLeadingBlank(await parsed.trailing, "always"); const expected = true; expect(actual).toEqual(expected); }); test('without body should fail for "never"', async () => { - const [actual] = footerLeadingBlank(await parsed.withoutBody, 'never'); + const [actual] = footerLeadingBlank(await parsed.withoutBody, "never"); const expected = false; expect(actual).toEqual(expected); }); test('without body should succeed for "always"', async () => { - const [actual] = footerLeadingBlank(await parsed.withoutBody, 'always'); + const [actual] = footerLeadingBlank(await parsed.withoutBody, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('without blank line before footer should fail for empty keyword', async () => { +test("without blank line before footer should fail for empty keyword", async () => { const [actual] = footerLeadingBlank(await parsed.without); const expected = false; expect(actual).toEqual(expected); }); test('without blank line before footer should succeed for "never"', async () => { - const [actual] = footerLeadingBlank(await parsed.without, 'never'); + const [actual] = footerLeadingBlank(await parsed.without, "never"); const expected = true; expect(actual).toEqual(expected); }); test('without blank line before footer should fail for "always"', async () => { - const [actual] = footerLeadingBlank(await parsed.without, 'always'); + const [actual] = footerLeadingBlank(await parsed.without, "always"); const expected = false; expect(actual).toEqual(expected); }); -test('with blank line before footer should succeed for empty keyword', async () => { +test("with blank line before footer should succeed for empty keyword", async () => { const [actual] = footerLeadingBlank(await parsed.with); const expected = true; expect(actual).toEqual(expected); }); test('with blank line before footer should fail for "never"', async () => { - const [actual] = footerLeadingBlank(await parsed.with, 'never'); + const [actual] = footerLeadingBlank(await parsed.with, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with blank line before footer should succeed for "always"', async () => { - const [actual] = footerLeadingBlank(await parsed.with, 'always'); + const [actual] = footerLeadingBlank(await parsed.with, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with blank line before footer and multiline body should succeed for empty keyword', async () => { +test("with blank line before footer and multiline body should succeed for empty keyword", async () => { const [actual] = footerLeadingBlank(await parsed.withMulitLine); const expected = true; expect(actual).toEqual(expected); }); test('with blank line before footer and multiline body should fail for "never"', async () => { - const [actual] = footerLeadingBlank(await parsed.withMulitLine, 'never'); + const [actual] = footerLeadingBlank(await parsed.withMulitLine, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with blank line before footer and multiline body should succeed for "always"', async () => { - const [actual] = footerLeadingBlank(await parsed.withMulitLine, 'always'); + const [actual] = footerLeadingBlank(await parsed.withMulitLine, "always"); const expected = true; expect(actual).toEqual(expected); }); test('with double blank line before footer and double line in body should fail for "never"', async () => { - const [actual] = footerLeadingBlank(await parsed.withDoubleNewLine, 'never'); + const [actual] = footerLeadingBlank(await parsed.withDoubleNewLine, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with double blank line before footer and double line in body should succeed for "always"', async () => { - const [actual] = footerLeadingBlank(await parsed.withDoubleNewLine, 'always'); + const [actual] = footerLeadingBlank(await parsed.withDoubleNewLine, "always"); const expected = true; expect(actual).toEqual(expected); }); @@ -166,7 +166,7 @@ test('with double blank line before footer and double line in body should succee test('with body containing comments should succeed for "always"', async () => { const [actual] = footerLeadingBlank( await parsed.withBodyWithComment, - 'always' + "always", ); const expected = true; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/footer-leading-blank.ts b/@commitlint/rules/src/footer-leading-blank.ts index ad8e2756bc..3f83b089a1 100644 --- a/@commitlint/rules/src/footer-leading-blank.ts +++ b/@commitlint/rules/src/footer-leading-blank.ts @@ -1,28 +1,28 @@ -import toLines from '@commitlint/to-lines'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import toLines from "@commitlint/to-lines"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; -export const footerLeadingBlank: SyncRule = (parsed, when = 'always') => { +export const footerLeadingBlank: SyncRule = (parsed, when = "always") => { // Flunk if no footer is found if (!parsed.footer) { return [true]; } - const negated = when === 'never'; + const negated = when === "never"; const rawLines = toLines(parsed.raw); const footerLines = toLines(parsed.footer); const footerOffset = rawLines.indexOf(footerLines[0]); const [leading] = rawLines.slice(footerOffset - 1); // Check if the first line of footer is empty - const succeeds = leading === ''; + const succeeds = leading === ""; return [ negated ? !succeeds : succeeds, message([ - 'footer', - negated ? 'may not' : 'must', - 'have leading blank line', + "footer", + negated ? "may not" : "must", + "have leading blank line", ]), ]; }; diff --git a/@commitlint/rules/src/footer-max-length.test.ts b/@commitlint/rules/src/footer-max-length.test.ts index be41154709..0dd0a3cb23 100644 --- a/@commitlint/rules/src/footer-max-length.test.ts +++ b/@commitlint/rules/src/footer-max-length.test.ts @@ -1,15 +1,15 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {footerMaxLength} from './footer-max-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { footerMaxLength } from "./footer-max-length.js"; -const short = 'BREAKING CHANGE: a'; -const long = 'BREAKING CHANGE: ab'; +const short = "BREAKING CHANGE: a"; +const long = "BREAKING CHANGE: ab"; const value = short.length; const messages = { - simple: 'test: subject', - empty: 'test: subject\nbody', + simple: "test: subject", + empty: "test: subject\nbody", short: `test: subject\n${short}`, long: `test: subject\n${long}`, }; @@ -21,25 +21,25 @@ const parsed = { long: parse(messages.long), }; -test('with simple should succeed', async () => { +test("with simple should succeed", async () => { const [actual] = footerMaxLength(await parsed.simple, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = footerMaxLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should succeed', async () => { +test("with short should succeed", async () => { const [actual] = footerMaxLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long should fail', async () => { +test("with long should fail", async () => { const [actual] = footerMaxLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/footer-max-length.ts b/@commitlint/rules/src/footer-max-length.ts index 43520ae546..d20a03ab45 100644 --- a/@commitlint/rules/src/footer-max-length.ts +++ b/@commitlint/rules/src/footer-max-length.ts @@ -1,10 +1,10 @@ -import {maxLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { maxLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const footerMaxLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.footer; diff --git a/@commitlint/rules/src/footer-max-line-length.test.ts b/@commitlint/rules/src/footer-max-line-length.test.ts index 5ce73cec90..7efa44c686 100644 --- a/@commitlint/rules/src/footer-max-line-length.test.ts +++ b/@commitlint/rules/src/footer-max-line-length.test.ts @@ -1,15 +1,15 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {footerMaxLineLength} from './footer-max-line-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { footerMaxLineLength } from "./footer-max-line-length.js"; -const short = 'BREAKING CHANGE: a'; -const long = 'BREAKING CHANGE: ab'; +const short = "BREAKING CHANGE: a"; +const long = "BREAKING CHANGE: ab"; const value = short.length; const messages = { - simple: 'test: subject', - empty: 'test: subject\nbody', + simple: "test: subject", + empty: "test: subject\nbody", short: `test: subject\n${short}`, long: `test: subject\n${long}`, shortMultipleLines: `test:subject\n${short}\n${short}\n${short}`, @@ -23,37 +23,37 @@ const parsed = { long: parse(messages.long), }; -test('with simple should succeed', async () => { +test("with simple should succeed", async () => { const [actual] = footerMaxLineLength(await parsed.simple, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = footerMaxLineLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should succeed', async () => { +test("with short should succeed", async () => { const [actual] = footerMaxLineLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long should fail', async () => { +test("with long should fail", async () => { const [actual] = footerMaxLineLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); }); -test('with short with multiple lines should succeed', async () => { +test("with short with multiple lines should succeed", async () => { const [actual] = footerMaxLineLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long with multiple lines should fail', async () => { +test("with long with multiple lines should fail", async () => { const [actual] = footerMaxLineLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/footer-max-line-length.ts b/@commitlint/rules/src/footer-max-line-length.ts index 34aea097dd..61366556fe 100644 --- a/@commitlint/rules/src/footer-max-line-length.ts +++ b/@commitlint/rules/src/footer-max-line-length.ts @@ -1,10 +1,10 @@ -import {maxLineLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { maxLineLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const footerMaxLineLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.footer; diff --git a/@commitlint/rules/src/footer-min-length.test.ts b/@commitlint/rules/src/footer-min-length.test.ts index 2526b76ebe..a70d86044a 100644 --- a/@commitlint/rules/src/footer-min-length.test.ts +++ b/@commitlint/rules/src/footer-min-length.test.ts @@ -1,15 +1,15 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {footerMinLength} from './footer-min-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { footerMinLength } from "./footer-min-length.js"; -const short = 'BREAKING CHANGE: a'; -const long = 'BREAKING CHANGE: ab'; +const short = "BREAKING CHANGE: a"; +const long = "BREAKING CHANGE: ab"; const value = long.length; const messages = { - simple: 'test: subject', - empty: 'test: subject\nbody', + simple: "test: subject", + empty: "test: subject\nbody", short: `test: subject\n${short}`, long: `test: subject\n${long}`, }; @@ -21,25 +21,25 @@ const parsed = { long: parse(messages.long), }; -test('with simple should succeed', async () => { +test("with simple should succeed", async () => { const [actual] = footerMinLength(await parsed.simple, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = footerMinLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should fail', async () => { +test("with short should fail", async () => { const [actual] = footerMinLength(await parsed.short, undefined, value); const expected = false; expect(actual).toEqual(expected); }); -test('with long should succeed', async () => { +test("with long should succeed", async () => { const [actual] = footerMinLength(await parsed.long, undefined, value); const expected = true; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/footer-min-length.ts b/@commitlint/rules/src/footer-min-length.ts index 9959cb788c..54f7c6143c 100644 --- a/@commitlint/rules/src/footer-min-length.ts +++ b/@commitlint/rules/src/footer-min-length.ts @@ -1,10 +1,10 @@ -import {minLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { minLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const footerMinLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { if (!parsed.footer) { return [true]; diff --git a/@commitlint/rules/src/header-case.test.ts b/@commitlint/rules/src/header-case.test.ts index a2e79c0ceb..edda2b957c 100644 --- a/@commitlint/rules/src/header-case.test.ts +++ b/@commitlint/rules/src/header-case.test.ts @@ -1,17 +1,17 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {headerCase} from './header-case.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { headerCase } from "./header-case.js"; const messages = { - numeric: '1.0.0\n', - lowercase: 'header\n', - mixedcase: 'hEaDeR\n', - uppercase: 'HEADER\n', - camelcase: 'heaDer\n', - kebabcase: 'hea-der\n', - pascalcase: 'HeaDer\n', - snakecase: 'hea_der\n', - startcase: 'Hea Der\n', + numeric: "1.0.0\n", + lowercase: "header\n", + mixedcase: "hEaDeR\n", + uppercase: "HEADER\n", + camelcase: "heaDer\n", + kebabcase: "hea-der\n", + pascalcase: "HeaDer\n", + snakecase: "hea_der\n", + startcase: "Hea Der\n", }; const parsed = { @@ -27,199 +27,199 @@ const parsed = { }; test('with lowercase header should fail for "never lowercase"', async () => { - const [actual] = headerCase(await parsed.lowercase, 'never', 'lowercase'); + const [actual] = headerCase(await parsed.lowercase, "never", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with lowercase header should succeed for "always lowercase"', async () => { - const [actual] = headerCase(await parsed.lowercase, 'always', 'lowercase'); + const [actual] = headerCase(await parsed.lowercase, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase header should succeed for "never lowercase"', async () => { - const [actual] = headerCase(await parsed.mixedcase, 'never', 'lowercase'); + const [actual] = headerCase(await parsed.mixedcase, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase header should fail for "always lowercase"', async () => { - const [actual] = headerCase(await parsed.mixedcase, 'always', 'lowercase'); + const [actual] = headerCase(await parsed.mixedcase, "always", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase header should succeed for "never uppercase"', async () => { - const [actual] = headerCase(await parsed.mixedcase, 'never', 'uppercase'); + const [actual] = headerCase(await parsed.mixedcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase header should fail for "always uppercase"', async () => { - const [actual] = headerCase(await parsed.mixedcase, 'always', 'uppercase'); + const [actual] = headerCase(await parsed.mixedcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with uppercase header should fail for "never uppercase"', async () => { - const [actual] = headerCase(await parsed.uppercase, 'never', 'uppercase'); + const [actual] = headerCase(await parsed.uppercase, "never", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with lowercase header should succeed for "always uppercase"', async () => { - const [actual] = headerCase(await parsed.uppercase, 'always', 'uppercase'); + const [actual] = headerCase(await parsed.uppercase, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with camelcase header should fail for "always uppercase"', async () => { - const [actual] = headerCase(await parsed.camelcase, 'always', 'uppercase'); + const [actual] = headerCase(await parsed.camelcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase header should succeed for "never uppercase"', async () => { - const [actual] = headerCase(await parsed.camelcase, 'never', 'uppercase'); + const [actual] = headerCase(await parsed.camelcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with camelcase header should fail for "always pascalcase"', async () => { - const [actual] = headerCase(await parsed.camelcase, 'always', 'pascal-case'); + const [actual] = headerCase(await parsed.camelcase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase header should fail for "always kebabcase"', async () => { - const [actual] = headerCase(await parsed.camelcase, 'always', 'kebab-case'); + const [actual] = headerCase(await parsed.camelcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase header should fail for "always snakecase"', async () => { - const [actual] = headerCase(await parsed.camelcase, 'always', 'snake-case'); + const [actual] = headerCase(await parsed.camelcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase header should succeed for "always camelcase"', async () => { - const [actual] = headerCase(await parsed.camelcase, 'always', 'camel-case'); + const [actual] = headerCase(await parsed.camelcase, "always", "camel-case"); const expected = true; expect(actual).toEqual(expected); }); test('with pascalcase header should fail for "always uppercase"', async () => { - const [actual] = headerCase(await parsed.pascalcase, 'always', 'uppercase'); + const [actual] = headerCase(await parsed.pascalcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase header should succeed for "never uppercase"', async () => { - const [actual] = headerCase(await parsed.pascalcase, 'never', 'uppercase'); + const [actual] = headerCase(await parsed.pascalcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with pascalcase header should succeed for "always pascalcase"', async () => { - const [actual] = headerCase(await parsed.pascalcase, 'always', 'pascal-case'); + const [actual] = headerCase(await parsed.pascalcase, "always", "pascal-case"); const expected = true; expect(actual).toEqual(expected); }); test('with pascalcase header should fail for "always kebabcase"', async () => { - const [actual] = headerCase(await parsed.pascalcase, 'always', 'kebab-case'); + const [actual] = headerCase(await parsed.pascalcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase header should fail for "always snakecase"', async () => { - const [actual] = headerCase(await parsed.pascalcase, 'always', 'snake-case'); + const [actual] = headerCase(await parsed.pascalcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase header should fail for "always camelcase"', async () => { - const [actual] = headerCase(await parsed.pascalcase, 'always', 'camel-case'); + const [actual] = headerCase(await parsed.pascalcase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase header should fail for "always uppercase"', async () => { - const [actual] = headerCase(await parsed.snakecase, 'always', 'uppercase'); + const [actual] = headerCase(await parsed.snakecase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase header should succeed for "never uppercase"', async () => { - const [actual] = headerCase(await parsed.snakecase, 'never', 'uppercase'); + const [actual] = headerCase(await parsed.snakecase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase header should fail for "always pascalcase"', async () => { - const [actual] = headerCase(await parsed.snakecase, 'always', 'pascal-case'); + const [actual] = headerCase(await parsed.snakecase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase header should fail for "always kebabcase"', async () => { - const [actual] = headerCase(await parsed.snakecase, 'always', 'kebab-case'); + const [actual] = headerCase(await parsed.snakecase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase header should succeed for "always snakecase"', async () => { - const [actual] = headerCase(await parsed.snakecase, 'always', 'snake-case'); + const [actual] = headerCase(await parsed.snakecase, "always", "snake-case"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase header should fail for "always camelcase"', async () => { - const [actual] = headerCase(await parsed.snakecase, 'always', 'camel-case'); + const [actual] = headerCase(await parsed.snakecase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase header should fail for "always uppercase"', async () => { - const [actual] = headerCase(await parsed.startcase, 'always', 'uppercase'); + const [actual] = headerCase(await parsed.startcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase header should succeed for "never uppercase"', async () => { - const [actual] = headerCase(await parsed.startcase, 'never', 'uppercase'); + const [actual] = headerCase(await parsed.startcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with startcase header should fail for "always pascalcase"', async () => { - const [actual] = headerCase(await parsed.startcase, 'always', 'pascal-case'); + const [actual] = headerCase(await parsed.startcase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase header should fail for "always kebabcase"', async () => { - const [actual] = headerCase(await parsed.startcase, 'always', 'kebab-case'); + const [actual] = headerCase(await parsed.startcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase header should fail for "always snakecase"', async () => { - const [actual] = headerCase(await parsed.startcase, 'always', 'snake-case'); + const [actual] = headerCase(await parsed.startcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase header should fail for "always camelcase"', async () => { - const [actual] = headerCase(await parsed.startcase, 'always', 'camel-case'); + const [actual] = headerCase(await parsed.startcase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase header should succeed for "always startcase"', async () => { - const [actual] = headerCase(await parsed.startcase, 'always', 'start-case'); + const [actual] = headerCase(await parsed.startcase, "always", "start-case"); const expected = true; expect(actual).toEqual(expected); }); @@ -227,92 +227,92 @@ test('with startcase header should succeed for "always startcase"', async () => test('should use expected message with "always"', async () => { const [, message] = headerCase( await parsed.uppercase, - 'always', - 'lower-case' + "always", + "lower-case", ); - expect(message).toContain('must be lower-case'); + expect(message).toContain("must be lower-case"); }); test('should use expected message with "never"', async () => { - const [, message] = headerCase(await parsed.uppercase, 'never', 'upper-case'); - expect(message).toContain('must not be upper-case'); + const [, message] = headerCase(await parsed.uppercase, "never", "upper-case"); + expect(message).toContain("must not be upper-case"); }); test('with uppercase scope should succeed for "always [uppercase, lowercase]"', async () => { - const [actual] = headerCase(await parsed.uppercase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = headerCase(await parsed.uppercase, "always", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with lowercase header should succeed for "always [uppercase, lowercase]"', async () => { - const [actual] = headerCase(await parsed.lowercase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = headerCase(await parsed.lowercase, "always", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase header should fail for "always [uppercase, lowercase]"', async () => { - const [actual] = headerCase(await parsed.mixedcase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = headerCase(await parsed.mixedcase, "always", [ + "uppercase", + "lowercase", ]); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase header should pass for "always [uppercase, lowercase, camel-case]"', async () => { - const [actual] = headerCase(await parsed.mixedcase, 'always', [ - 'uppercase', - 'lowercase', - 'camel-case', + const [actual] = headerCase(await parsed.mixedcase, "always", [ + "uppercase", + "lowercase", + "camel-case", ]); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase scope should pass for "never [uppercase, lowercase]"', async () => { - const [actual] = headerCase(await parsed.mixedcase, 'never', [ - 'uppercase', - 'lowercase', + const [actual] = headerCase(await parsed.mixedcase, "never", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with uppercase scope should fail for "never [uppercase, lowercase]"', async () => { - const [actual] = headerCase(await parsed.uppercase, 'never', [ - 'uppercase', - 'lowercase', + const [actual] = headerCase(await parsed.uppercase, "never", [ + "uppercase", + "lowercase", ]); const expected = false; expect(actual).toEqual(expected); }); test('with numeric header should succeed for "never lowercase"', async () => { - const [actual] = headerCase(await parsed.numeric, 'never', 'lowercase'); + const [actual] = headerCase(await parsed.numeric, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with numeric header should succeed for "always lowercase"', async () => { - const [actual] = headerCase(await parsed.numeric, 'always', 'lowercase'); + const [actual] = headerCase(await parsed.numeric, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with numeric header should succeed for "never uppercase"', async () => { - const [actual] = headerCase(await parsed.numeric, 'never', 'uppercase'); + const [actual] = headerCase(await parsed.numeric, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with numeric header should succeed for "always uppercase"', async () => { - const [actual] = headerCase(await parsed.numeric, 'always', 'uppercase'); + const [actual] = headerCase(await parsed.numeric, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/header-case.ts b/@commitlint/rules/src/header-case.ts index cb907c9e40..310b8a753e 100644 --- a/@commitlint/rules/src/header-case.ts +++ b/@commitlint/rules/src/header-case.ts @@ -1,24 +1,24 @@ -import {case as ensureCase} from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {TargetCaseType, SyncRule} from '@commitlint/types'; +import { case as ensureCase } from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { TargetCaseType, SyncRule } from "@commitlint/types"; -const negated = (when?: string) => when === 'never'; +const negated = (when?: string) => when === "never"; export const headerCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( parsed, - when = 'always', - value = [] + when = "always", + value = [], ) => { - const {header} = parsed; + const { header } = parsed; - if (typeof header !== 'string' || !header.match(/^[a-z]/i)) { + if (typeof header !== "string" || !header.match(/^[a-z]/i)) { return [true]; } const checks = (Array.isArray(value) ? value : [value]).map((check) => { - if (typeof check === 'string') { + if (typeof check === "string") { return { - when: 'always', + when: "always", case: check, }; } @@ -30,7 +30,7 @@ export const headerCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( return negated(check.when) ? !r : r; }); - const list = checks.map((c) => c.case).join(', '); + const list = checks.map((c) => c.case).join(", "); return [ negated(when) ? !result : result, diff --git a/@commitlint/rules/src/header-full-stop.test.ts b/@commitlint/rules/src/header-full-stop.test.ts index 667cfc80dd..98fd156437 100644 --- a/@commitlint/rules/src/header-full-stop.test.ts +++ b/@commitlint/rules/src/header-full-stop.test.ts @@ -1,6 +1,6 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {headerFullStop} from './header-full-stop.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { headerFullStop } from "./header-full-stop.js"; const messages = { with: `header.\n`, @@ -13,25 +13,25 @@ const parsed = { }; test('with against "always ." should succeed', async () => { - const [actual] = headerFullStop(await parsed.with, 'always', '.'); + const [actual] = headerFullStop(await parsed.with, "always", "."); const expected = true; expect(actual).toEqual(expected); }); test('with against "never ." should fail', async () => { - const [actual] = headerFullStop(await parsed.with, 'never', '.'); + const [actual] = headerFullStop(await parsed.with, "never", "."); const expected = false; expect(actual).toEqual(expected); }); test('without against "always ." should fail', async () => { - const [actual] = headerFullStop(await parsed.without, 'always', '.'); + const [actual] = headerFullStop(await parsed.without, "always", "."); const expected = false; expect(actual).toEqual(expected); }); test('without against "never ." should succeed', async () => { - const [actual] = headerFullStop(await parsed.without, 'never', '.'); + const [actual] = headerFullStop(await parsed.without, "never", "."); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/header-full-stop.ts b/@commitlint/rules/src/header-full-stop.ts index 1cb5031918..ae57cd26e5 100644 --- a/@commitlint/rules/src/header-full-stop.ts +++ b/@commitlint/rules/src/header-full-stop.ts @@ -1,17 +1,17 @@ -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; export const headerFullStop: SyncRule<string> = ( parsed, - when = 'always', - value = '.' + when = "always", + value = ".", ) => { - const {header} = parsed; - const negated = when === 'never'; + const { header } = parsed; + const negated = when === "never"; const hasStop = header?.[header.length - 1] === value; return [ negated ? !hasStop : hasStop, - message(['header', negated ? 'may not' : 'must', 'end with full stop']), + message(["header", negated ? "may not" : "must", "end with full stop"]), ]; }; diff --git a/@commitlint/rules/src/header-max-length.test.ts b/@commitlint/rules/src/header-max-length.test.ts index d57626e797..c7180e66b0 100644 --- a/@commitlint/rules/src/header-max-length.test.ts +++ b/@commitlint/rules/src/header-max-length.test.ts @@ -1,9 +1,9 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {headerMaxLength} from './header-max-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { headerMaxLength } from "./header-max-length.js"; -const short = 'test: a'; -const long = 'test: ab'; +const short = "test: a"; +const long = "test: ab"; const value = short.length; @@ -17,13 +17,13 @@ const parsed = { long: parse(messages.long), }; -test('with short should succeed', async () => { +test("with short should succeed", async () => { const [actual] = headerMaxLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long should fail', async () => { +test("with long should fail", async () => { const [actual] = headerMaxLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/header-max-length.ts b/@commitlint/rules/src/header-max-length.ts index 7cb3a6b4e6..0147c9d67f 100644 --- a/@commitlint/rules/src/header-max-length.ts +++ b/@commitlint/rules/src/header-max-length.ts @@ -1,10 +1,10 @@ -import {maxLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { maxLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const headerMaxLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { return [ maxLength(parsed.header, value), diff --git a/@commitlint/rules/src/header-min-length.test.ts b/@commitlint/rules/src/header-min-length.test.ts index 7991371978..e97dfe3d48 100644 --- a/@commitlint/rules/src/header-min-length.test.ts +++ b/@commitlint/rules/src/header-min-length.test.ts @@ -1,9 +1,9 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {headerMinLength} from './header-min-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { headerMinLength } from "./header-min-length.js"; -const short = 'BREAKING CHANGE: a'; -const long = 'BREAKING CHANGE: ab'; +const short = "BREAKING CHANGE: a"; +const long = "BREAKING CHANGE: ab"; const value = long.length; @@ -17,13 +17,13 @@ const parsed = { long: parse(messages.long), }; -test('with short should fail', async () => { +test("with short should fail", async () => { const [actual] = headerMinLength(await parsed.short, undefined, value); const expected = false; expect(actual).toEqual(expected); }); -test('with long should succeed', async () => { +test("with long should succeed", async () => { const [actual] = headerMinLength(await parsed.long, undefined, value); const expected = true; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/header-min-length.ts b/@commitlint/rules/src/header-min-length.ts index bd9ae29662..d332b077b3 100644 --- a/@commitlint/rules/src/header-min-length.ts +++ b/@commitlint/rules/src/header-min-length.ts @@ -1,10 +1,10 @@ -import {minLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { minLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const headerMinLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { return [ minLength(parsed.header, value), diff --git a/@commitlint/rules/src/header-trim.test.ts b/@commitlint/rules/src/header-trim.test.ts index 410cfc1bc2..f9280b2bf7 100644 --- a/@commitlint/rules/src/header-trim.test.ts +++ b/@commitlint/rules/src/header-trim.test.ts @@ -1,23 +1,23 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import type {Commit} from 'conventional-commits-parser'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import type { Commit } from "conventional-commits-parser"; -import {headerTrim} from './header-trim.js'; +import { headerTrim } from "./header-trim.js"; const messages = { - correct: 'test: subject', + correct: "test: subject", - whitespaceStart: ' test: subject', - whitespaceEnd: 'test: subject ', - whitespaceSurround: ' test: subject ', + whitespaceStart: " test: subject", + whitespaceEnd: "test: subject ", + whitespaceSurround: " test: subject ", - tabStart: '\t\ttest: subject', - tabEnd: 'test: subject\t\t', - tabSurround: '\t\ttest: subject\t', + tabStart: "\t\ttest: subject", + tabEnd: "test: subject\t\t", + tabSurround: "\t\ttest: subject\t", - mixStart: '\t\ttest: subject', - mixEnd: 'test: subject\t\t', - mixSurround: '\t \ttest: subject \t \t', + mixStart: "\t\ttest: subject", + mixEnd: "test: subject\t\t", + mixSurround: "\t \ttest: subject \t \t", }; const parsed = Object.entries(messages).reduce( @@ -25,49 +25,49 @@ const parsed = Object.entries(messages).reduce( Object.assign(_parsed, { [key]: parse(message), }), - {} as Record<keyof typeof messages, Promise<Commit>> + {} as Record<keyof typeof messages, Promise<Commit>>, ); -test('should succeed when header is not surrounded by whitespace', async () => { +test("should succeed when header is not surrounded by whitespace", async () => { const result = headerTrim(await parsed.correct); expect(result).toEqual(expect.arrayContaining([true])); }); test.each([ - {scenario: 'mixed whitespace ', commit: parsed.mixStart}, - {scenario: 'whitespace', commit: parsed.whitespaceStart}, - {scenario: 'tab', commit: parsed.tabStart}, -] as const)('should fail when starts with $scenario', async ({commit}) => { + { scenario: "mixed whitespace ", commit: parsed.mixStart }, + { scenario: "whitespace", commit: parsed.whitespaceStart }, + { scenario: "tab", commit: parsed.tabStart }, +] as const)("should fail when starts with $scenario", async ({ commit }) => { const result = headerTrim(await commit); expect(result).toEqual( - expect.arrayContaining([false, 'header must not start with whitespace']) + expect.arrayContaining([false, "header must not start with whitespace"]), ); }); test.each([ - {scenario: 'mixed whitespace', commit: parsed.mixEnd}, - {scenario: 'whitespace', commit: parsed.whitespaceEnd}, - {scenario: 'tab', commit: parsed.tabEnd}, -] as const)('should fail when ends with $scenario', async ({commit}) => { + { scenario: "mixed whitespace", commit: parsed.mixEnd }, + { scenario: "whitespace", commit: parsed.whitespaceEnd }, + { scenario: "tab", commit: parsed.tabEnd }, +] as const)("should fail when ends with $scenario", async ({ commit }) => { const result = headerTrim(await commit); expect(result).toEqual( - expect.arrayContaining([false, 'header must not end with whitespace']) + expect.arrayContaining([false, "header must not end with whitespace"]), ); }); test.each([ - {scenario: 'mixed whitespace', commit: parsed.mixSurround}, - {scenario: 'whitespace', commit: parsed.whitespaceSurround}, - {scenario: 'tab', commit: parsed.tabSurround}, + { scenario: "mixed whitespace", commit: parsed.mixSurround }, + { scenario: "whitespace", commit: parsed.whitespaceSurround }, + { scenario: "tab", commit: parsed.tabSurround }, ] as const)( - 'should fail when surrounded by with $scenario', - async ({commit}) => { + "should fail when surrounded by with $scenario", + async ({ commit }) => { const result = headerTrim(await commit); expect(result).toEqual( expect.arrayContaining([ false, - 'header must not be surrounded by whitespace', - ]) + "header must not be surrounded by whitespace", + ]), ); - } + }, ); diff --git a/@commitlint/rules/src/header-trim.ts b/@commitlint/rules/src/header-trim.ts index f1ef65be66..289c1881a0 100644 --- a/@commitlint/rules/src/header-trim.ts +++ b/@commitlint/rules/src/header-trim.ts @@ -1,8 +1,8 @@ -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; export const headerTrim: SyncRule = (parsed) => { - const {header} = parsed; + const { header } = parsed; if (!header) { return [true]; @@ -15,14 +15,14 @@ export const headerTrim: SyncRule = (parsed) => { case startsWithWhiteSpace && endsWithWhiteSpace: return [ false, - message(['header', 'must not be surrounded by whitespace']), + message(["header", "must not be surrounded by whitespace"]), ]; case startsWithWhiteSpace: - return [false, message(['header', 'must not start with whitespace'])]; + return [false, message(["header", "must not start with whitespace"])]; case endsWithWhiteSpace: - return [false, message(['header', 'must not end with whitespace'])]; + return [false, message(["header", "must not end with whitespace"])]; default: return [true]; diff --git a/@commitlint/rules/src/index.test.ts b/@commitlint/rules/src/index.test.ts index feb4d4088e..22f3b91847 100644 --- a/@commitlint/rules/src/index.test.ts +++ b/@commitlint/rules/src/index.test.ts @@ -1,41 +1,41 @@ -import {test, expect} from 'vitest'; -import fs from 'node:fs'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { test, expect } from "vitest"; +import fs from "node:fs"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {globSync} from 'glob'; +import { globSync } from "glob"; -import rules from './index.js'; +import rules from "./index.js"; -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -test('exports all rules', () => { - const expected = _glob('*.ts').sort(); +test("exports all rules", () => { + const expected = _glob("*.ts").sort(); const actual = Object.keys(rules).sort(); expect(actual).toEqual(expected); }); -test('rules export functions', () => { +test("rules export functions", () => { const actual = Object.values(rules); - expect(actual.every((rule) => typeof rule === 'function')).toBe(true); + expect(actual.every((rule) => typeof rule === "function")).toBe(true); }); -test('all rules are present in documentation', () => { +test("all rules are present in documentation", () => { const file = fs.readFileSync( - path.join(__dirname, '../../../docs/reference/rules.md'), - 'utf-8' + path.join(__dirname, "../../../docs/reference/rules.md"), + "utf-8", ); const results = file .split(/(\n|\r)/) - .filter((s) => s.startsWith('##') && !s.includes('`deprecated`')) - .map((s) => s.replace('## ', '')); + .filter((s) => s.startsWith("##") && !s.includes("`deprecated`")) + .map((s) => s.replace("## ", "")); expect(Object.keys(rules)).toEqual(expect.arrayContaining(results)); }); function _glob(pattern: string) { const files = globSync(pattern, { - ignore: ['**/index.ts', '**/*.test.ts'], + ignore: ["**/index.ts", "**/*.test.ts"], cwd: __dirname, }); return files.map(relative).map(toExport); diff --git a/@commitlint/rules/src/index.ts b/@commitlint/rules/src/index.ts index c3b3f6b4d1..0a27f0b81a 100644 --- a/@commitlint/rules/src/index.ts +++ b/@commitlint/rules/src/index.ts @@ -1,75 +1,75 @@ -import {bodyCase} from './body-case.js'; -import {bodyEmpty} from './body-empty.js'; -import {bodyFullStop} from './body-full-stop.js'; -import {bodyLeadingBlank} from './body-leading-blank.js'; -import {bodyMaxLength} from './body-max-length.js'; -import {bodyMaxLineLength} from './body-max-line-length.js'; -import {bodyMinLength} from './body-min-length.js'; -import {footerEmpty} from './footer-empty.js'; -import {footerLeadingBlank} from './footer-leading-blank.js'; -import {footerMaxLength} from './footer-max-length.js'; -import {footerMaxLineLength} from './footer-max-line-length.js'; -import {footerMinLength} from './footer-min-length.js'; -import {headerCase} from './header-case.js'; -import {headerFullStop} from './header-full-stop.js'; -import {headerMaxLength} from './header-max-length.js'; -import {headerMinLength} from './header-min-length.js'; -import {headerTrim} from './header-trim.js'; -import {referencesEmpty} from './references-empty.js'; -import {scopeCase} from './scope-case.js'; -import {scopeEmpty} from './scope-empty.js'; -import {scopeEnum} from './scope-enum.js'; -import {scopeMaxLength} from './scope-max-length.js'; -import {scopeMinLength} from './scope-min-length.js'; -import {signedOffBy} from './signed-off-by.js'; -import {subjectCase} from './subject-case.js'; -import {subjectEmpty} from './subject-empty.js'; -import {subjectFullStop} from './subject-full-stop.js'; -import {subjectMaxLength} from './subject-max-length.js'; -import {subjectMinLength} from './subject-min-length.js'; -import {subjectExclamationMark} from './subject-exclamation-mark.js'; -import {trailerExists} from './trailer-exists.js'; -import {typeCase} from './type-case.js'; -import {typeEmpty} from './type-empty.js'; -import {typeEnum} from './type-enum.js'; -import {typeMaxLength} from './type-max-length.js'; -import {typeMinLength} from './type-min-length.js'; +import { bodyCase } from "./body-case.js"; +import { bodyEmpty } from "./body-empty.js"; +import { bodyFullStop } from "./body-full-stop.js"; +import { bodyLeadingBlank } from "./body-leading-blank.js"; +import { bodyMaxLength } from "./body-max-length.js"; +import { bodyMaxLineLength } from "./body-max-line-length.js"; +import { bodyMinLength } from "./body-min-length.js"; +import { footerEmpty } from "./footer-empty.js"; +import { footerLeadingBlank } from "./footer-leading-blank.js"; +import { footerMaxLength } from "./footer-max-length.js"; +import { footerMaxLineLength } from "./footer-max-line-length.js"; +import { footerMinLength } from "./footer-min-length.js"; +import { headerCase } from "./header-case.js"; +import { headerFullStop } from "./header-full-stop.js"; +import { headerMaxLength } from "./header-max-length.js"; +import { headerMinLength } from "./header-min-length.js"; +import { headerTrim } from "./header-trim.js"; +import { referencesEmpty } from "./references-empty.js"; +import { scopeCase } from "./scope-case.js"; +import { scopeEmpty } from "./scope-empty.js"; +import { scopeEnum } from "./scope-enum.js"; +import { scopeMaxLength } from "./scope-max-length.js"; +import { scopeMinLength } from "./scope-min-length.js"; +import { signedOffBy } from "./signed-off-by.js"; +import { subjectCase } from "./subject-case.js"; +import { subjectEmpty } from "./subject-empty.js"; +import { subjectFullStop } from "./subject-full-stop.js"; +import { subjectMaxLength } from "./subject-max-length.js"; +import { subjectMinLength } from "./subject-min-length.js"; +import { subjectExclamationMark } from "./subject-exclamation-mark.js"; +import { trailerExists } from "./trailer-exists.js"; +import { typeCase } from "./type-case.js"; +import { typeEmpty } from "./type-empty.js"; +import { typeEnum } from "./type-enum.js"; +import { typeMaxLength } from "./type-max-length.js"; +import { typeMinLength } from "./type-min-length.js"; export default { - 'body-case': bodyCase, - 'body-empty': bodyEmpty, - 'body-full-stop': bodyFullStop, - 'body-leading-blank': bodyLeadingBlank, - 'body-max-length': bodyMaxLength, - 'body-max-line-length': bodyMaxLineLength, - 'body-min-length': bodyMinLength, - 'footer-empty': footerEmpty, - 'footer-leading-blank': footerLeadingBlank, - 'footer-max-length': footerMaxLength, - 'footer-max-line-length': footerMaxLineLength, - 'footer-min-length': footerMinLength, - 'header-case': headerCase, - 'header-full-stop': headerFullStop, - 'header-max-length': headerMaxLength, - 'header-min-length': headerMinLength, - 'header-trim': headerTrim, - 'references-empty': referencesEmpty, - 'scope-case': scopeCase, - 'scope-empty': scopeEmpty, - 'scope-enum': scopeEnum, - 'scope-max-length': scopeMaxLength, - 'scope-min-length': scopeMinLength, - 'signed-off-by': signedOffBy, - 'subject-case': subjectCase, - 'subject-empty': subjectEmpty, - 'subject-full-stop': subjectFullStop, - 'subject-max-length': subjectMaxLength, - 'subject-min-length': subjectMinLength, - 'subject-exclamation-mark': subjectExclamationMark, - 'trailer-exists': trailerExists, - 'type-case': typeCase, - 'type-empty': typeEmpty, - 'type-enum': typeEnum, - 'type-max-length': typeMaxLength, - 'type-min-length': typeMinLength, + "body-case": bodyCase, + "body-empty": bodyEmpty, + "body-full-stop": bodyFullStop, + "body-leading-blank": bodyLeadingBlank, + "body-max-length": bodyMaxLength, + "body-max-line-length": bodyMaxLineLength, + "body-min-length": bodyMinLength, + "footer-empty": footerEmpty, + "footer-leading-blank": footerLeadingBlank, + "footer-max-length": footerMaxLength, + "footer-max-line-length": footerMaxLineLength, + "footer-min-length": footerMinLength, + "header-case": headerCase, + "header-full-stop": headerFullStop, + "header-max-length": headerMaxLength, + "header-min-length": headerMinLength, + "header-trim": headerTrim, + "references-empty": referencesEmpty, + "scope-case": scopeCase, + "scope-empty": scopeEmpty, + "scope-enum": scopeEnum, + "scope-max-length": scopeMaxLength, + "scope-min-length": scopeMinLength, + "signed-off-by": signedOffBy, + "subject-case": subjectCase, + "subject-empty": subjectEmpty, + "subject-full-stop": subjectFullStop, + "subject-max-length": subjectMaxLength, + "subject-min-length": subjectMinLength, + "subject-exclamation-mark": subjectExclamationMark, + "trailer-exists": trailerExists, + "type-case": typeCase, + "type-empty": typeEmpty, + "type-enum": typeEnum, + "type-max-length": typeMaxLength, + "type-min-length": typeMinLength, }; diff --git a/@commitlint/rules/src/references-empty.test.ts b/@commitlint/rules/src/references-empty.test.ts index cd6465aac6..03b12bd060 100644 --- a/@commitlint/rules/src/references-empty.test.ts +++ b/@commitlint/rules/src/references-empty.test.ts @@ -1,21 +1,21 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {referencesEmpty} from './references-empty.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { referencesEmpty } from "./references-empty.js"; // @ts-expect-error -- no typings -import preset from 'conventional-changelog-angular'; +import preset from "conventional-changelog-angular"; const messages = { - plain: 'foo: bar', - comment: 'foo: baz\n#1 Comment', - reference: '#comment\nfoo: baz \nCloses #1', - references: '#comment\nfoo: bar \nCloses #1, #2, #3', - prefix: 'bar REF-1234', + plain: "foo: bar", + comment: "foo: baz\n#1 Comment", + reference: "#comment\nfoo: baz \nCloses #1", + references: "#comment\nfoo: bar \nCloses #1, #2, #3", + prefix: "bar REF-1234", }; const opts = (async () => { const o = await preset(); - o.parserOpts.commentChar = '#'; + o.parserOpts.commentChar = "#"; return o; })(); @@ -29,60 +29,60 @@ const parsed = { references: (async () => parse(messages.references, undefined, (await opts).parserOpts))(), prefix: parse(messages.prefix, undefined, { - issuePrefixes: ['REF-'], + issuePrefixes: ["REF-"], }), }; -test('defaults to never and fails for plain', async () => { +test("defaults to never and fails for plain", async () => { const [actual] = referencesEmpty(await parsed.plain); const expected = false; expect(actual).toEqual(expected); }); -test('defaults to never and succeeds for reference', async () => { +test("defaults to never and succeeds for reference", async () => { const [actual] = referencesEmpty(await parsed.reference); const expected = true; expect(actual).toEqual(expected); }); -test('fails for comment with never', async () => { - const [actual] = referencesEmpty(await parsed.comment, 'never'); +test("fails for comment with never", async () => { + const [actual] = referencesEmpty(await parsed.comment, "never"); const expected = false; expect(actual).toEqual(expected); }); -test('succeeds for comment with always', async () => { - const [actual] = referencesEmpty(await parsed.comment, 'always'); +test("succeeds for comment with always", async () => { + const [actual] = referencesEmpty(await parsed.comment, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('succeeds for reference with never', async () => { - const [actual] = referencesEmpty(await parsed.reference, 'never'); +test("succeeds for reference with never", async () => { + const [actual] = referencesEmpty(await parsed.reference, "never"); const expected = true; expect(actual).toEqual(expected); }); -test('fails for reference with always', async () => { - const [actual] = referencesEmpty(await parsed.reference, 'always'); +test("fails for reference with always", async () => { + const [actual] = referencesEmpty(await parsed.reference, "always"); const expected = false; expect(actual).toEqual(expected); }); -test('succeeds for references with never', async () => { - const [actual] = referencesEmpty(await parsed.references, 'never'); +test("succeeds for references with never", async () => { + const [actual] = referencesEmpty(await parsed.references, "never"); const expected = true; expect(actual).toEqual(expected); }); -test('fails for references with always', async () => { - const [actual] = referencesEmpty(await parsed.references, 'always'); +test("fails for references with always", async () => { + const [actual] = referencesEmpty(await parsed.references, "always"); const expected = false; expect(actual).toEqual(expected); }); -test('succeeds for custom references with always', async () => { - const [actual] = referencesEmpty(await parsed.prefix, 'never'); +test("succeeds for custom references with always", async () => { + const [actual] = referencesEmpty(await parsed.prefix, "never"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/references-empty.ts b/@commitlint/rules/src/references-empty.ts index 6682d1d99f..650675e087 100644 --- a/@commitlint/rules/src/references-empty.ts +++ b/@commitlint/rules/src/references-empty.ts @@ -1,11 +1,11 @@ -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; -export const referencesEmpty: SyncRule = (parsed, when = 'never') => { - const negated = when === 'always'; +export const referencesEmpty: SyncRule = (parsed, when = "never") => { + const negated = when === "always"; const notEmpty = parsed.references.length > 0; return [ negated ? !notEmpty : notEmpty, - message(['references', negated ? 'must' : 'may not', 'be empty']), + message(["references", negated ? "must" : "may not", "be empty"]), ]; }; diff --git a/@commitlint/rules/src/scope-case.test.ts b/@commitlint/rules/src/scope-case.test.ts index ba55acf731..4e352e7017 100644 --- a/@commitlint/rules/src/scope-case.test.ts +++ b/@commitlint/rules/src/scope-case.test.ts @@ -1,17 +1,17 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {scopeCase} from './scope-case.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { scopeCase } from "./scope-case.js"; const messages = { - empty: 'test: subject', - lowercase: 'test(scope): subject', - mixedcase: 'test(sCoPe): subject', - uppercase: 'test(SCOPE): subject', - camelcase: 'test(myScope): subject', - kebabcase: 'test(my-scope): subject', - pascalcase: 'test(MyScope): subject', - snakecase: 'test(my_scope): subject', - startcase: 'test(My Scope): subject', + empty: "test: subject", + lowercase: "test(scope): subject", + mixedcase: "test(sCoPe): subject", + uppercase: "test(SCOPE): subject", + camelcase: "test(myScope): subject", + kebabcase: "test(my-scope): subject", + pascalcase: "test(MyScope): subject", + snakecase: "test(my_scope): subject", + startcase: "test(My Scope): subject", }; const parsed = { @@ -27,298 +27,298 @@ const parsed = { }; test('with empty scope should succeed for "never lowercase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'lowercase'); + const [actual] = scopeCase(await parsed.empty, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "always lowercase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'always', 'lowercase'); + const [actual] = scopeCase(await parsed.empty, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "never uppercase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'uppercase'); + const [actual] = scopeCase(await parsed.empty, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "always uppercase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'always', 'uppercase'); + const [actual] = scopeCase(await parsed.empty, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "never camelcase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'camel-case'); + const [actual] = scopeCase(await parsed.empty, "never", "camel-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "always camelcase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'camel-case'); + const [actual] = scopeCase(await parsed.empty, "never", "camel-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "never kebabcase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'kebab-case'); + const [actual] = scopeCase(await parsed.empty, "never", "kebab-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "always kebabcase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'kebab-case'); + const [actual] = scopeCase(await parsed.empty, "never", "kebab-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "never pascalcase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'pascal-case'); + const [actual] = scopeCase(await parsed.empty, "never", "pascal-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "always pascalcase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'pascal-case'); + const [actual] = scopeCase(await parsed.empty, "never", "pascal-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "never snakecase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'snake-case'); + const [actual] = scopeCase(await parsed.empty, "never", "snake-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "always snakecase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'snake-case'); + const [actual] = scopeCase(await parsed.empty, "never", "snake-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "never startcase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'start-case'); + const [actual] = scopeCase(await parsed.empty, "never", "start-case"); const expected = true; expect(actual).toEqual(expected); }); test('with empty scope should succeed for "always startcase"', async () => { - const [actual] = scopeCase(await parsed.empty, 'never', 'start-case'); + const [actual] = scopeCase(await parsed.empty, "never", "start-case"); const expected = true; expect(actual).toEqual(expected); }); test('with lowercase scope should fail for "never lowercase"', async () => { - const [actual] = scopeCase(await parsed.lowercase, 'never', 'lowercase'); + const [actual] = scopeCase(await parsed.lowercase, "never", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with lowercase scope should succeed for "always lowercase"', async () => { - const [actual] = scopeCase(await parsed.lowercase, 'always', 'lowercase'); + const [actual] = scopeCase(await parsed.lowercase, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase scope should succeed for "never lowercase"', async () => { - const [actual] = scopeCase(await parsed.mixedcase, 'never', 'lowercase'); + const [actual] = scopeCase(await parsed.mixedcase, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase scope should fail for "always lowercase"', async () => { - const [actual] = scopeCase(await parsed.mixedcase, 'always', 'lowercase'); + const [actual] = scopeCase(await parsed.mixedcase, "always", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase scope should succeed for "never uppercase"', async () => { - const [actual] = scopeCase(await parsed.mixedcase, 'never', 'uppercase'); + const [actual] = scopeCase(await parsed.mixedcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with kebabcase scope should succeed for "always lowercase"', async () => { - const [actual] = scopeCase(await parsed.kebabcase, 'always', 'lowercase'); + const [actual] = scopeCase(await parsed.kebabcase, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with kebabcase scope should fail for "always camelcase"', async () => { - const [actual] = scopeCase(await parsed.kebabcase, 'always', 'camel-case'); + const [actual] = scopeCase(await parsed.kebabcase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with kebabcase scope should fail for "always pascalcase"', async () => { - const [actual] = scopeCase(await parsed.kebabcase, 'always', 'pascal-case'); + const [actual] = scopeCase(await parsed.kebabcase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with kebabcase scope should succeed for "always kebabcase"', async () => { - const [actual] = scopeCase(await parsed.kebabcase, 'always', 'kebab-case'); + const [actual] = scopeCase(await parsed.kebabcase, "always", "kebab-case"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase scope should succeed for "always lowercase"', async () => { - const [actual] = scopeCase(await parsed.snakecase, 'always', 'lowercase'); + const [actual] = scopeCase(await parsed.snakecase, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase scope should fail for "always camelcase"', async () => { - const [actual] = scopeCase(await parsed.snakecase, 'always', 'camel-case'); + const [actual] = scopeCase(await parsed.snakecase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase scope should fail for "always pascalcase"', async () => { - const [actual] = scopeCase(await parsed.snakecase, 'always', 'pascal-case'); + const [actual] = scopeCase(await parsed.snakecase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase scope should succeed for "always snakecase"', async () => { - const [actual] = scopeCase(await parsed.snakecase, 'always', 'snake-case'); + const [actual] = scopeCase(await parsed.snakecase, "always", "snake-case"); const expected = true; expect(actual).toEqual(expected); }); test('with camelcase scope should fail for "always lowercase"', async () => { - const [actual] = scopeCase(await parsed.camelcase, 'always', 'lowercase'); + const [actual] = scopeCase(await parsed.camelcase, "always", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase scope should succeed for "always camelcase"', async () => { - const [actual] = scopeCase(await parsed.camelcase, 'always', 'camel-case'); + const [actual] = scopeCase(await parsed.camelcase, "always", "camel-case"); const expected = true; expect(actual).toEqual(expected); }); test('with camelcase scope should fail for "always kebabcase"', async () => { - const [actual] = scopeCase(await parsed.camelcase, 'always', 'kebab-case'); + const [actual] = scopeCase(await parsed.camelcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase scope should fail for "always pascalcase"', async () => { - const [actual] = scopeCase(await parsed.camelcase, 'always', 'pascal-case'); + const [actual] = scopeCase(await parsed.camelcase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase scope should fail for "always lowercase"', async () => { - const [actual] = scopeCase(await parsed.pascalcase, 'always', 'lowercase'); + const [actual] = scopeCase(await parsed.pascalcase, "always", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase scope should fail for "always kebabcase"', async () => { - const [actual] = scopeCase(await parsed.pascalcase, 'always', 'kebab-case'); + const [actual] = scopeCase(await parsed.pascalcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase scope should fail for "always camelcase"', async () => { - const [actual] = scopeCase(await parsed.pascalcase, 'always', 'camel-case'); + const [actual] = scopeCase(await parsed.pascalcase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase scope should succeed for "always pascalcase"', async () => { - const [actual] = scopeCase(await parsed.pascalcase, 'always', 'pascal-case'); + const [actual] = scopeCase(await parsed.pascalcase, "always", "pascal-case"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase scope should fail for "always uppercase"', async () => { - const [actual] = scopeCase(await parsed.mixedcase, 'always', 'uppercase'); + const [actual] = scopeCase(await parsed.mixedcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with uppercase scope should fail for "never uppercase"', async () => { - const [actual] = scopeCase(await parsed.uppercase, 'never', 'uppercase'); + const [actual] = scopeCase(await parsed.uppercase, "never", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with uppercase scope should succeed for "always uppercase"', async () => { - const [actual] = scopeCase(await parsed.uppercase, 'always', 'uppercase'); + const [actual] = scopeCase(await parsed.uppercase, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with uppercase scope should succeed for "always [uppercase, lowercase]"', async () => { - const [actual] = scopeCase(await parsed.uppercase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = scopeCase(await parsed.uppercase, "always", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with lowercase scope should succeed for "always [uppercase, lowercase]"', async () => { - const [actual] = scopeCase(await parsed.lowercase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = scopeCase(await parsed.lowercase, "always", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase scope should fail for "always [uppercase, lowercase]"', async () => { - const [actual] = scopeCase(await parsed.mixedcase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = scopeCase(await parsed.mixedcase, "always", [ + "uppercase", + "lowercase", ]); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase scope should pass for "always [uppercase, lowercase, camel-case]"', async () => { - const [actual] = scopeCase(await parsed.mixedcase, 'always', [ - 'uppercase', - 'lowercase', - 'camel-case', + const [actual] = scopeCase(await parsed.mixedcase, "always", [ + "uppercase", + "lowercase", + "camel-case", ]); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase scope should pass for "never [uppercase, lowercase]"', async () => { - const [actual] = scopeCase(await parsed.mixedcase, 'never', [ - 'uppercase', - 'lowercase', + const [actual] = scopeCase(await parsed.mixedcase, "never", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with uppercase scope should fail for "never [uppercase, lowercase]"', async () => { - const [actual] = scopeCase(await parsed.uppercase, 'never', [ - 'uppercase', - 'lowercase', + const [actual] = scopeCase(await parsed.uppercase, "never", [ + "uppercase", + "lowercase", ]); const expected = false; expect(actual).toEqual(expected); }); test('with slash in scope should succeed for "always pascal-case"', async () => { - const commit = await parse('feat(Modules/Graph): add Pie Chart'); - const [actual] = scopeCase(commit, 'always', 'pascal-case'); + const commit = await parse("feat(Modules/Graph): add Pie Chart"); + const [actual] = scopeCase(commit, "always", "pascal-case"); const expected = true; expect(actual).toEqual(expected); }); test('with slash in subject should succeed for "always sentence case"', async () => { - const commit = await parse('chore: Update @angular/core'); - const [actual] = scopeCase(commit, 'always', 'sentencecase'); + const commit = await parse("chore: Update @angular/core"); + const [actual] = scopeCase(commit, "always", "sentencecase"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/scope-case.ts b/@commitlint/rules/src/scope-case.ts index 7544cc1fa0..c620086eff 100644 --- a/@commitlint/rules/src/scope-case.ts +++ b/@commitlint/rules/src/scope-case.ts @@ -1,24 +1,24 @@ -import {case as ensureCase} from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {TargetCaseType, SyncRule} from '@commitlint/types'; +import { case as ensureCase } from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { TargetCaseType, SyncRule } from "@commitlint/types"; -const negated = (when?: string) => when === 'never'; +const negated = (when?: string) => when === "never"; export const scopeCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( parsed, - when = 'always', - value = [] + when = "always", + value = [], ) => { - const {scope} = parsed; + const { scope } = parsed; if (!scope) { return [true]; } const checks = (Array.isArray(value) ? value : [value]).map((check) => { - if (typeof check === 'string') { + if (typeof check === "string") { return { - when: 'always', + when: "always", case: check, }; } @@ -32,13 +32,13 @@ export const scopeCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( const result = checks.some((check) => { const r = scopeSegments.every( - (segment) => delimiters.test(segment) || ensureCase(segment, check.case) + (segment) => delimiters.test(segment) || ensureCase(segment, check.case), ); return negated(check.when) ? !r : r; }); - const list = checks.map((c) => c.case).join(', '); + const list = checks.map((c) => c.case).join(", "); return [ negated(when) ? !result : result, diff --git a/@commitlint/rules/src/scope-empty.test.ts b/@commitlint/rules/src/scope-empty.test.ts index b4c535fdd4..88977f8c17 100644 --- a/@commitlint/rules/src/scope-empty.test.ts +++ b/@commitlint/rules/src/scope-empty.test.ts @@ -1,11 +1,11 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {scopeEmpty} from './scope-empty.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { scopeEmpty } from "./scope-empty.js"; const messages = { - plain: 'foo(bar): baz', - superfluous: 'foo(): baz', - empty: 'foo: baz', + plain: "foo(bar): baz", + superfluous: "foo(): baz", + empty: "foo: baz", }; const parsed = { @@ -14,56 +14,56 @@ const parsed = { empty: parse(messages.empty), }; -test('with plain message it should succeed for empty keyword', async () => { +test("with plain message it should succeed for empty keyword", async () => { const [actual] = scopeEmpty(await parsed.plain); const expected = true; expect(actual).toEqual(expected); }); test('with plain message it should succeed for "never"', async () => { - const [actual] = scopeEmpty(await parsed.plain, 'never'); + const [actual] = scopeEmpty(await parsed.plain, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with plain message it should fail for "always"', async () => { - const [actual] = scopeEmpty(await parsed.plain, 'always'); + const [actual] = scopeEmpty(await parsed.plain, "always"); const expected = false; expect(actual).toEqual(expected); }); -test('with superfluous message it should fail for empty keyword', async () => { +test("with superfluous message it should fail for empty keyword", async () => { const [actual] = scopeEmpty(await parsed.superfluous); const expected = false; expect(actual).toEqual(expected); }); test('with superfluous message it should fail for "never"', async () => { - const [actual] = scopeEmpty(await parsed.superfluous, 'never'); + const [actual] = scopeEmpty(await parsed.superfluous, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with superfluous message it should fail for "always"', async () => { - const [actual] = scopeEmpty(await parsed.superfluous, 'always'); + const [actual] = scopeEmpty(await parsed.superfluous, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with empty message it should fail for empty keyword', async () => { +test("with empty message it should fail for empty keyword", async () => { const [actual] = scopeEmpty(await parsed.empty); const expected = false; expect(actual).toEqual(expected); }); test('with empty message it should fail for "never"', async () => { - const [actual] = scopeEmpty(await parsed.empty, 'never'); + const [actual] = scopeEmpty(await parsed.empty, "never"); const expected = false; expect(actual).toEqual(expected); }); test('with empty message it should fail for "always"', async () => { - const [actual] = scopeEmpty(await parsed.empty, 'always'); + const [actual] = scopeEmpty(await parsed.empty, "always"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/scope-empty.ts b/@commitlint/rules/src/scope-empty.ts index 3ea0fa1f81..d7a9bb0e2e 100644 --- a/@commitlint/rules/src/scope-empty.ts +++ b/@commitlint/rules/src/scope-empty.ts @@ -1,12 +1,12 @@ -import * as ensure from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import * as ensure from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; -export const scopeEmpty: SyncRule = (parsed, when = 'never') => { - const negated = when === 'always'; - const notEmpty = ensure.notEmpty(parsed.scope || ''); +export const scopeEmpty: SyncRule = (parsed, when = "never") => { + const negated = when === "always"; + const notEmpty = ensure.notEmpty(parsed.scope || ""); return [ negated ? !notEmpty : notEmpty, - message(['scope', negated ? 'must' : 'may not', 'be empty']), + message(["scope", negated ? "must" : "may not", "be empty"]), ]; }; diff --git a/@commitlint/rules/src/scope-enum.test.ts b/@commitlint/rules/src/scope-enum.test.ts index 184534b608..1e7fb7efa7 100644 --- a/@commitlint/rules/src/scope-enum.test.ts +++ b/@commitlint/rules/src/scope-enum.test.ts @@ -1,52 +1,52 @@ -import {describe, test, it, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {RuleConfigCondition} from '@commitlint/types'; +import { describe, test, it, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { RuleConfigCondition } from "@commitlint/types"; -import {scopeEnum} from './scope-enum.js'; +import { scopeEnum } from "./scope-enum.js"; const messagesByScope = { single: { - plain: 'foo(bar): baz', + plain: "foo(bar): baz", }, multiple: { - multiple: 'foo(bar,baz): qux', - multipleCommaSpace: 'foo(bar, baz): qux', - multipleSlash: 'foo(bar/baz): qux', + multiple: "foo(bar,baz): qux", + multipleCommaSpace: "foo(bar, baz): qux", + multipleSlash: "foo(bar/baz): qux", }, none: { - empty: 'foo: baz', - superfluous: 'foo(): baz', + empty: "foo: baz", + superfluous: "foo(): baz", }, }; -const {single, multiple, none} = messagesByScope; +const { single, multiple, none } = messagesByScope; const messages = Object.values(messagesByScope).reduce<Record<string, string>>( - (acc, curr) => ({...acc, ...curr}), - {} + (acc, curr) => ({ ...acc, ...curr }), + {}, ); -const conditions: RuleConfigCondition[] = ['always', 'never']; +const conditions: RuleConfigCondition[] = ["always", "never"]; -describe('Scope Enum Validation', () => { - describe.each(conditions)('condition: %s', (condition) => { - describe('Enum without Scopes', () => { +describe("Scope Enum Validation", () => { + describe.each(conditions)("condition: %s", (condition) => { + describe("Enum without Scopes", () => { test.each(Object.keys(messages))( `Succeeds with a %s message and '${condition}'`, async (messageType) => { const [actual, message] = scopeEnum( await parse(messages[messageType]), condition, - [] + [], ); const expected = true; expect(actual).toEqual(expected); - expect(message).toEqual(''); - } + expect(message).toEqual(""); + }, ); }); - describe('Messages without Scopes', () => { + describe("Messages without Scopes", () => { Object.keys(none).forEach((messageType) => { const fakeMessage = messages[messageType]; @@ -54,7 +54,7 @@ describe('Scope Enum Validation', () => { const [actual, message] = scopeEnum( await parse(fakeMessage), condition, - ['bar'] + ["bar"], ); expect(actual).toBeTruthy(); expect(message).toBeFalsy(); @@ -64,7 +64,7 @@ describe('Scope Enum Validation', () => { const [actual, message] = scopeEnum( await parse(fakeMessage), condition, - ['bar', 'baz'] + ["bar", "baz"], ); expect(actual).toBeTruthy(); expect(message).toBeFalsy(); @@ -73,134 +73,134 @@ describe('Scope Enum Validation', () => { }); }); - describe('Always', () => { - describe('Single-Scope Messages', () => { + describe("Always", () => { + describe("Single-Scope Messages", () => { Object.keys(single).forEach((messageType) => { const fakeMessage = messages[messageType]; it(`Succeeds with a '${messageType}' message when all message scopes are included in single-scope enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'always', - ['bar'] + "always", + ["bar"], ); expect(actual).toBeTruthy(); - expect(message).toEqual('scope must be one of [bar]'); + expect(message).toEqual("scope must be one of [bar]"); }); test(`Succeeds with a '${messageType}' message when all message scopes are included in multi-scope enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'always', - ['bar', 'baz'] + "always", + ["bar", "baz"], ); expect(actual).toBeTruthy(); - expect(message).toEqual('scope must be one of [bar, baz]'); + expect(message).toEqual("scope must be one of [bar, baz]"); }); test(`Fails with a '${messageType}' message when any message scope is not included in enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'always', - ['foo'] + "always", + ["foo"], ); expect(actual).toBeFalsy(); - expect(message).toEqual('scope must be one of [foo]'); + expect(message).toEqual("scope must be one of [foo]"); }); }); }); - describe('Multi-Scope Messages', () => { + describe("Multi-Scope Messages", () => { Object.keys(multiple).forEach((messageType) => { const fakeMessage = messages[messageType]; test(`Succeeds with a '${messageType}' message when all message scopes are included in enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'always', - ['bar', 'baz'] + "always", + ["bar", "baz"], ); expect(actual).toBeTruthy(); - expect(message).toEqual('scope must be one of [bar, baz]'); + expect(message).toEqual("scope must be one of [bar, baz]"); }); test(`Fails with a '${messageType}' message when no message scopes are included in enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'always', - ['foo'] + "always", + ["foo"], ); expect(actual).toBeFalsy(); - expect(message).toEqual('scope must be one of [foo]'); + expect(message).toEqual("scope must be one of [foo]"); }); it(`Fails with a '${messageType}' message when only some message scopes are included in enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'always', - ['bar'] + "always", + ["bar"], ); expect(actual).toBeFalsy(); - expect(message).toEqual('scope must be one of [bar]'); + expect(message).toEqual("scope must be one of [bar]"); }); }); test(`Succeeds with a 'multipleSlash' message when the scopes are included in enum`, async () => { const [actual, message] = scopeEnum( - await parse(messages['multipleSlash']), - 'always', - ['bar/baz'] + await parse(messages["multipleSlash"]), + "always", + ["bar/baz"], ); expect(actual).toBeTruthy(); - expect(message).toEqual('scope must be one of [bar/baz]'); + expect(message).toEqual("scope must be one of [bar/baz]"); }); }); }); - describe('Never', () => { - describe('Messages with Scopes', () => { - Object.keys({...single, ...multiple}).forEach((messageType) => { + describe("Never", () => { + describe("Messages with Scopes", () => { + Object.keys({ ...single, ...multiple }).forEach((messageType) => { const fakeMessage = messages[messageType]; test(`Succeeds with a '${messageType}' message when no message scopes are included in enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'never', - ['foo'] + "never", + ["foo"], ); expect(actual).toBeTruthy(); - expect(message).toEqual('scope must not be one of [foo]'); + expect(message).toEqual("scope must not be one of [foo]"); }); it(`Fails with a '${messageType}' message when any message scope is included in single-scope enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'never', - ['bar'] + "never", + ["bar"], ); expect(actual).toBeFalsy(); - expect(message).toEqual('scope must not be one of [bar]'); + expect(message).toEqual("scope must not be one of [bar]"); }); test(`Fails with a '${messageType}' message when any message scope is included in multi-scope enum`, async () => { const [actual, message] = scopeEnum( await parse(fakeMessage), - 'never', - ['bar', 'baz'] + "never", + ["bar", "baz"], ); expect(actual).toBeFalsy(); - expect(message).toEqual('scope must not be one of [bar, baz]'); + expect(message).toEqual("scope must not be one of [bar, baz]"); }); }); test(`Fails with a 'multipleSlash' message when the scopes are included in enum`, async () => { const [actual, message] = scopeEnum( - await parse(messages['multipleSlash']), - 'never', - ['bar/baz'] + await parse(messages["multipleSlash"]), + "never", + ["bar/baz"], ); expect(actual).toBeFalsy(); - expect(message).toEqual('scope must not be one of [bar/baz]'); + expect(message).toEqual("scope must not be one of [bar/baz]"); }); }); }); diff --git a/@commitlint/rules/src/scope-enum.ts b/@commitlint/rules/src/scope-enum.ts index d7f5957f45..59cef26df9 100644 --- a/@commitlint/rules/src/scope-enum.ts +++ b/@commitlint/rules/src/scope-enum.ts @@ -1,27 +1,27 @@ -import * as ensure from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import * as ensure from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; export const scopeEnum: SyncRule<string[]> = ( - {scope}, - when = 'always', - value = [] + { scope }, + when = "always", + value = [], ) => { if (!scope || !value.length) { - return [true, '']; + return [true, ""]; } // Scopes may contain slash or comma delimiters to separate them and mark them as individual segments. // This means that each of these segments should be tested separately with `ensure`. const delimiters = /\/|\\|, ?/g; const messageScopes = scope.split(delimiters); - const errorMessage = ['scope must', `be one of [${value.join(', ')}]`]; + const errorMessage = ["scope must", `be one of [${value.join(", ")}]`]; const isScopeInEnum = (scope: string) => ensure.enum(scope, value); let isValid; - if (when === 'never') { + if (when === "never") { isValid = !messageScopes.some(isScopeInEnum) && !isScopeInEnum(scope); - errorMessage.splice(1, 0, 'not'); + errorMessage.splice(1, 0, "not"); } else { isValid = messageScopes.every(isScopeInEnum) || isScopeInEnum(scope); } diff --git a/@commitlint/rules/src/scope-max-length.test.ts b/@commitlint/rules/src/scope-max-length.test.ts index c8535118bb..97e5e4f6fa 100644 --- a/@commitlint/rules/src/scope-max-length.test.ts +++ b/@commitlint/rules/src/scope-max-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {scopeMaxLength} from './scope-max-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { scopeMaxLength } from "./scope-max-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = short.length; const messages = { - empty: 'test: \n', + empty: "test: \n", short: `test(${short}): \n`, long: `test(${long}): \n`, }; @@ -19,19 +19,19 @@ const parsed = { long: parse(messages.long), }; -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = scopeMaxLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should succeed', async () => { +test("with short should succeed", async () => { const [actual] = scopeMaxLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long should fail', async () => { +test("with long should fail", async () => { const [actual] = scopeMaxLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/scope-max-length.ts b/@commitlint/rules/src/scope-max-length.ts index 917d548f91..bcdf6f81ce 100644 --- a/@commitlint/rules/src/scope-max-length.ts +++ b/@commitlint/rules/src/scope-max-length.ts @@ -1,10 +1,10 @@ -import {maxLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { maxLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const scopeMaxLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.scope; diff --git a/@commitlint/rules/src/scope-min-length.test.ts b/@commitlint/rules/src/scope-min-length.test.ts index 327f5de49d..3ff18920ec 100644 --- a/@commitlint/rules/src/scope-min-length.test.ts +++ b/@commitlint/rules/src/scope-min-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {scopeMinLength} from './scope-min-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { scopeMinLength } from "./scope-min-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = long.length; const messages = { - empty: 'test:\n', + empty: "test:\n", short: `test(${short}): \n`, long: `test(${long}): \n`, }; @@ -19,19 +19,19 @@ const parsed = { long: parse(messages.long), }; -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = scopeMinLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should fail', async () => { +test("with short should fail", async () => { const [actual] = scopeMinLength(await parsed.short, undefined, value); const expected = false; expect(actual).toEqual(expected); }); -test('with long should succeed', async () => { +test("with long should succeed", async () => { const [actual] = scopeMinLength(await parsed.long, undefined, value); const expected = true; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/scope-min-length.ts b/@commitlint/rules/src/scope-min-length.ts index 55a69da3e9..40b4c909f9 100644 --- a/@commitlint/rules/src/scope-min-length.ts +++ b/@commitlint/rules/src/scope-min-length.ts @@ -1,10 +1,10 @@ -import {minLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { minLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const scopeMinLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.scope; if (!input) { diff --git a/@commitlint/rules/src/signed-off-by.test.ts b/@commitlint/rules/src/signed-off-by.test.ts index 469f40e7fa..d47353927a 100644 --- a/@commitlint/rules/src/signed-off-by.test.ts +++ b/@commitlint/rules/src/signed-off-by.test.ts @@ -1,9 +1,9 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {signedOffBy} from './signed-off-by.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { signedOffBy } from "./signed-off-by.js"; const messages = { - empty: 'test:\n', + empty: "test:\n", with: `test: subject\nbody\nfooter\nSigned-off-by:\n\n`, without: `test: subject\nbody\nfooter\n\n`, inSubject: `test: subject Signed-off-by:\nbody\nfooter\n\n`, @@ -29,25 +29,25 @@ const parsed = { }; test('empty against "always signed-off-by" should fail', async () => { - const [actual] = signedOffBy(await parsed.empty, 'always', 'Signed-off-by:'); + const [actual] = signedOffBy(await parsed.empty, "always", "Signed-off-by:"); const expected = false; expect(actual).toEqual(expected); }); test('empty against "never signed-off-by" should succeed', async () => { - const [actual] = signedOffBy(await parsed.empty, 'never', 'Signed-off-by:'); + const [actual] = signedOffBy(await parsed.empty, "never", "Signed-off-by:"); const expected = true; expect(actual).toEqual(expected); }); test('with against "always signed-off-by" should succeed', async () => { - const [actual] = signedOffBy(await parsed.with, 'always', 'Signed-off-by:'); + const [actual] = signedOffBy(await parsed.with, "always", "Signed-off-by:"); const expected = true; expect(actual).toEqual(expected); }); test('with against "never signed-off-by" should fail', async () => { - const [actual] = signedOffBy(await parsed.with, 'never', 'Signed-off-by:'); + const [actual] = signedOffBy(await parsed.with, "never", "Signed-off-by:"); const expected = false; expect(actual).toEqual(expected); }); @@ -55,24 +55,24 @@ test('with against "never signed-off-by" should fail', async () => { test('without against "always signed-off-by" should fail', async () => { const [actual] = signedOffBy( await parsed.without, - 'always', - 'Signed-off-by:' + "always", + "Signed-off-by:", ); const expected = false; expect(actual).toEqual(expected); }); test('without against "never signed-off-by" should succeed', async () => { - const [actual] = signedOffBy(await parsed.without, 'never', 'Signed-off-by:'); + const [actual] = signedOffBy(await parsed.without, "never", "Signed-off-by:"); const expected = true; expect(actual).toEqual(expected); }); -test('trailing comments should be ignored', async () => { +test("trailing comments should be ignored", async () => { const [actual] = signedOffBy( await parsed.withSignoffAndComments, - 'always', - 'Signed-off-by:' + "always", + "Signed-off-by:", ); const expected = true; expect(actual).toEqual(expected); @@ -81,8 +81,8 @@ test('trailing comments should be ignored', async () => { test('inSubject against "always signed-off-by" should fail', async () => { const [actual] = signedOffBy( await parsed.inSubject, - 'always', - 'Signed-off-by:' + "always", + "Signed-off-by:", ); const expected = false; expect(actual).toEqual(expected); @@ -91,21 +91,21 @@ test('inSubject against "always signed-off-by" should fail', async () => { test('inSubject against "never signed-off-by" should succeed', async () => { const [actual] = signedOffBy( await parsed.inSubject, - 'never', - 'Signed-off-by:' + "never", + "Signed-off-by:", ); const expected = true; expect(actual).toEqual(expected); }); test('inBody against "always signed-off-by" should fail', async () => { - const [actual] = signedOffBy(await parsed.inBody, 'always', 'Signed-off-by:'); + const [actual] = signedOffBy(await parsed.inBody, "always", "Signed-off-by:"); const expected = false; expect(actual).toEqual(expected); }); test('inBody against "never signed-off-by" should succeed', async () => { - const [actual] = signedOffBy(await parsed.inBody, 'never', 'Signed-off-by:'); + const [actual] = signedOffBy(await parsed.inBody, "never", "Signed-off-by:"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/signed-off-by.ts b/@commitlint/rules/src/signed-off-by.ts index 0a30c03e23..5a53c32395 100644 --- a/@commitlint/rules/src/signed-off-by.ts +++ b/@commitlint/rules/src/signed-off-by.ts @@ -1,29 +1,29 @@ -import message from '@commitlint/message'; -import toLines from '@commitlint/to-lines'; -import {SyncRule} from '@commitlint/types'; +import message from "@commitlint/message"; +import toLines from "@commitlint/to-lines"; +import { SyncRule } from "@commitlint/types"; export const signedOffBy: SyncRule<string> = ( parsed, - when = 'always', - value = '' + when = "always", + value = "", ) => { const lines = toLines(parsed.raw).filter( (ln) => // skip comments - !ln.startsWith('#') && + !ln.startsWith("#") && // ignore empty lines - Boolean(ln) + Boolean(ln), ); const last = lines[lines.length - 1]; - const negated = when === 'never'; + const negated = when === "never"; const hasSignedOffBy = // empty commit message last ? last.startsWith(value) : false; return [ negated ? !hasSignedOffBy : hasSignedOffBy, - message(['message', negated ? 'must not' : 'must', 'be signed off']), + message(["message", negated ? "must not" : "must", "be signed off"]), ]; }; diff --git a/@commitlint/rules/src/subject-case.test.ts b/@commitlint/rules/src/subject-case.test.ts index 5c8281bda6..911b8d5321 100644 --- a/@commitlint/rules/src/subject-case.test.ts +++ b/@commitlint/rules/src/subject-case.test.ts @@ -1,28 +1,28 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {subjectCase} from './subject-case.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { subjectCase } from "./subject-case.js"; const messages = { - empty: 'test:\n', - numeric: 'test: 1.0.0', - lowercase: 'test: subject', - lowercase_unicode: 'test: тема', // Bulgarian for `subject` - mixedcase: 'test: sUbJeCt', - caseless: 'test: 这是一次提交', // Chinese for `this is a commit` - uppercase: 'test: SUBJECT', - uppercase_unicode: 'test: ÛNDERWERP', // Frisian for `SUBJECT` - camelcase: 'test: subJect', - camelcase_unicode: 'test: θέΜα', // Greek for `subJect` - kebabcase: 'test: sub-ject', - kebabcase_unicode: 'test: áb-har', // Irish for `sub-ject` - pascalcase: 'test: SubJect', - pascalcase_unicode: 'test: ТақыРып', // Kazakh for `SubJect` - snakecase: 'test: sub_ject', - snakecase_unicode: 'test: сэ_дэв', // Mongolian for `sub_ject` - startcase: 'test: Sub Ject', - startcase_unicode: 'test: Äm Ne', // Swedish for `Sub Ject` - sentencecase: 'test: Sub ject', - sentencecase_unicode: 'test: Мав зуъ', // Tajik for `Sub ject` + empty: "test:\n", + numeric: "test: 1.0.0", + lowercase: "test: subject", + lowercase_unicode: "test: тема", // Bulgarian for `subject` + mixedcase: "test: sUbJeCt", + caseless: "test: 这是一次提交", // Chinese for `this is a commit` + uppercase: "test: SUBJECT", + uppercase_unicode: "test: ÛNDERWERP", // Frisian for `SUBJECT` + camelcase: "test: subJect", + camelcase_unicode: "test: θέΜα", // Greek for `subJect` + kebabcase: "test: sub-ject", + kebabcase_unicode: "test: áb-har", // Irish for `sub-ject` + pascalcase: "test: SubJect", + pascalcase_unicode: "test: ТақыРып", // Kazakh for `SubJect` + snakecase: "test: sub_ject", + snakecase_unicode: "test: сэ_дэв", // Mongolian for `sub_ject` + startcase: "test: Sub Ject", + startcase_unicode: "test: Äm Ne", // Swedish for `Sub Ject` + sentencecase: "test: Sub ject", + sentencecase_unicode: "test: Мав зуъ", // Tajik for `Sub ject` }; const parsed = { @@ -49,37 +49,37 @@ const parsed = { }; test('with empty subject should succeed for "never lowercase"', async () => { - const [actual] = subjectCase(await parsed.empty, 'never', 'lowercase'); + const [actual] = subjectCase(await parsed.empty, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty subject should succeed for "always lowercase"', async () => { - const [actual] = subjectCase(await parsed.empty, 'always', 'lowercase'); + const [actual] = subjectCase(await parsed.empty, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty subject should succeed for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.empty, 'never', 'uppercase'); + const [actual] = subjectCase(await parsed.empty, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty subject should succeed for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.empty, 'always', 'uppercase'); + const [actual] = subjectCase(await parsed.empty, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with lowercase subject should fail for "never lowercase"', async () => { - const [actual] = subjectCase(await parsed.lowercase, 'never', 'lowercase'); + const [actual] = subjectCase(await parsed.lowercase, "never", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with lowercase subject should succeed for "always lowercase"', async () => { - const [actual] = subjectCase(await parsed.lowercase, 'always', 'lowercase'); + const [actual] = subjectCase(await parsed.lowercase, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); @@ -87,63 +87,63 @@ test('with lowercase subject should succeed for "always lowercase"', async () => test('with lowercase unicode subject should fail for "always uppercase"', async () => { const [actual] = subjectCase( await parsed.lowercase_unicode, - 'always', - 'upper-case' + "always", + "upper-case", ); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase subject should succeed for "never lowercase"', async () => { - const [actual] = subjectCase(await parsed.mixedcase, 'never', 'lowercase'); + const [actual] = subjectCase(await parsed.mixedcase, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase subject should fail for "always lowercase"', async () => { - const [actual] = subjectCase(await parsed.mixedcase, 'always', 'lowercase'); + const [actual] = subjectCase(await parsed.mixedcase, "always", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase subject should succeed for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.mixedcase, 'never', 'uppercase'); + const [actual] = subjectCase(await parsed.mixedcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase subject should fail for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.mixedcase, 'always', 'uppercase'); + const [actual] = subjectCase(await parsed.mixedcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with caseless subject should succeed for "never sentencecase"', async () => { - const [actual] = subjectCase(await parsed.caseless, 'never', 'sentence-case'); + const [actual] = subjectCase(await parsed.caseless, "never", "sentence-case"); const expected = true; expect(actual).toEqual(expected); }); test('with caseless subject should succeed for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.caseless, 'never', 'upper-case'); + const [actual] = subjectCase(await parsed.caseless, "never", "upper-case"); const expected = true; expect(actual).toEqual(expected); }); test('with caseless subject should succeed for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.caseless, 'always', 'upper-case'); + const [actual] = subjectCase(await parsed.caseless, "always", "upper-case"); const expected = true; expect(actual).toEqual(expected); }); test('with uppercase subject should fail for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.uppercase, 'never', 'uppercase'); + const [actual] = subjectCase(await parsed.uppercase, "never", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with uppercase subject should succeed for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.uppercase, 'always', 'uppercase'); + const [actual] = subjectCase(await parsed.uppercase, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); @@ -151,45 +151,45 @@ test('with uppercase subject should succeed for "always uppercase"', async () => test('with uppercase unicode subject should fail for "always lowercase"', async () => { const [actual] = subjectCase( await parsed.uppercase_unicode, - 'always', - 'lower-case' + "always", + "lower-case", ); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase subject should fail for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.camelcase, 'always', 'uppercase'); + const [actual] = subjectCase(await parsed.camelcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase subject should succeed for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.camelcase, 'never', 'uppercase'); + const [actual] = subjectCase(await parsed.camelcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with camelcase subject should fail for "always pascalcase"', async () => { - const [actual] = subjectCase(await parsed.camelcase, 'always', 'pascal-case'); + const [actual] = subjectCase(await parsed.camelcase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase subject should fail for "always kebabcase"', async () => { - const [actual] = subjectCase(await parsed.camelcase, 'always', 'kebab-case'); + const [actual] = subjectCase(await parsed.camelcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase subject should fail for "always snakecase"', async () => { - const [actual] = subjectCase(await parsed.camelcase, 'always', 'snake-case'); + const [actual] = subjectCase(await parsed.camelcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase subject should succeed for "always camelcase"', async () => { - const [actual] = subjectCase(await parsed.camelcase, 'always', 'camel-case'); + const [actual] = subjectCase(await parsed.camelcase, "always", "camel-case"); const expected = true; expect(actual).toEqual(expected); }); @@ -197,8 +197,8 @@ test('with camelcase subject should succeed for "always camelcase"', async () => test('with camelcase unicode subject should fail for "always sentencecase"', async () => { const [actual] = subjectCase( await parsed.camelcase_unicode, - 'always', - 'sentence-case' + "always", + "sentence-case", ); const expected = false; expect(actual).toEqual(expected); @@ -207,21 +207,21 @@ test('with camelcase unicode subject should fail for "always sentencecase"', asy test('with kebabcase unicode subject should fail for "always camelcase"', async () => { const [actual] = subjectCase( await parsed.kebabcase_unicode, - 'always', - 'camel-case' + "always", + "camel-case", ); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase subject should fail for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.pascalcase, 'always', 'uppercase'); + const [actual] = subjectCase(await parsed.pascalcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase subject should succeed for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.pascalcase, 'never', 'uppercase'); + const [actual] = subjectCase(await parsed.pascalcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); @@ -229,27 +229,27 @@ test('with pascalcase subject should succeed for "never uppercase"', async () => test('with pascalcase subject should succeed for "always pascalcase"', async () => { const [actual] = subjectCase( await parsed.pascalcase, - 'always', - 'pascal-case' + "always", + "pascal-case", ); const expected = true; expect(actual).toEqual(expected); }); test('with pascalcase subject should fail for "always kebabcase"', async () => { - const [actual] = subjectCase(await parsed.pascalcase, 'always', 'kebab-case'); + const [actual] = subjectCase(await parsed.pascalcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase subject should fail for "always snakecase"', async () => { - const [actual] = subjectCase(await parsed.pascalcase, 'always', 'snake-case'); + const [actual] = subjectCase(await parsed.pascalcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase subject should fail for "always camelcase"', async () => { - const [actual] = subjectCase(await parsed.pascalcase, 'always', 'camel-case'); + const [actual] = subjectCase(await parsed.pascalcase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); @@ -257,45 +257,45 @@ test('with pascalcase subject should fail for "always camelcase"', async () => { test('with pascalcase unicode subject should fail for "always uppercase"', async () => { const [actual] = subjectCase( await parsed.pascalcase_unicode, - 'always', - 'upper-case' + "always", + "upper-case", ); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase subject should fail for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.snakecase, 'always', 'uppercase'); + const [actual] = subjectCase(await parsed.snakecase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase subject should succeed for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.snakecase, 'never', 'uppercase'); + const [actual] = subjectCase(await parsed.snakecase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase subject should fail for "always pascalcase"', async () => { - const [actual] = subjectCase(await parsed.snakecase, 'always', 'pascal-case'); + const [actual] = subjectCase(await parsed.snakecase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase subject should fail for "always kebabcase"', async () => { - const [actual] = subjectCase(await parsed.snakecase, 'always', 'kebab-case'); + const [actual] = subjectCase(await parsed.snakecase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase subject should succeed for "always snakecase"', async () => { - const [actual] = subjectCase(await parsed.snakecase, 'always', 'snake-case'); + const [actual] = subjectCase(await parsed.snakecase, "always", "snake-case"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase subject should fail for "always camelcase"', async () => { - const [actual] = subjectCase(await parsed.snakecase, 'always', 'camel-case'); + const [actual] = subjectCase(await parsed.snakecase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); @@ -303,51 +303,51 @@ test('with snakecase subject should fail for "always camelcase"', async () => { test('with snakecase unicode subject should fail for "never lowercase"', async () => { const [actual] = subjectCase( await parsed.snakecase_unicode, - 'never', - 'lower-case' + "never", + "lower-case", ); const expected = false; expect(actual).toEqual(expected); }); test('with startcase subject should fail for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.startcase, 'always', 'uppercase'); + const [actual] = subjectCase(await parsed.startcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase subject should succeed for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.startcase, 'never', 'uppercase'); + const [actual] = subjectCase(await parsed.startcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with startcase subject should fail for "always pascalcase"', async () => { - const [actual] = subjectCase(await parsed.startcase, 'always', 'pascal-case'); + const [actual] = subjectCase(await parsed.startcase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase subject should fail for "always kebabcase"', async () => { - const [actual] = subjectCase(await parsed.startcase, 'always', 'kebab-case'); + const [actual] = subjectCase(await parsed.startcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase subject should fail for "always snakecase"', async () => { - const [actual] = subjectCase(await parsed.startcase, 'always', 'snake-case'); + const [actual] = subjectCase(await parsed.startcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase subject should fail for "always camelcase"', async () => { - const [actual] = subjectCase(await parsed.startcase, 'always', 'camel-case'); + const [actual] = subjectCase(await parsed.startcase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase subject should succeed for "always startcase"', async () => { - const [actual] = subjectCase(await parsed.startcase, 'always', 'start-case'); + const [actual] = subjectCase(await parsed.startcase, "always", "start-case"); const expected = true; expect(actual).toEqual(expected); }); @@ -355,8 +355,8 @@ test('with startcase subject should succeed for "always startcase"', async () => test('with startcase unicode subject should fail for "always pascalcase"', async () => { const [actual] = subjectCase( await parsed.startcase_unicode, - 'always', - 'pascal-case' + "always", + "pascal-case", ); const expected = false; expect(actual).toEqual(expected); @@ -365,8 +365,8 @@ test('with startcase unicode subject should fail for "always pascalcase"', async test('with sentencecase subject should succeed for "always sentence-case"', async () => { const [actual] = subjectCase( await parsed.sentencecase, - 'always', - 'sentence-case' + "always", + "sentence-case", ); const expected = true; expect(actual).toEqual(expected); @@ -375,8 +375,8 @@ test('with sentencecase subject should succeed for "always sentence-case"', asyn test('with sentencecase subject should fail for "never sentencecase"', async () => { const [actual] = subjectCase( await parsed.sentencecase, - 'never', - 'sentence-case' + "never", + "sentence-case", ); const expected = false; expect(actual).toEqual(expected); @@ -385,8 +385,8 @@ test('with sentencecase subject should fail for "never sentencecase"', async () test('with sentencecase subject should fail for "always pascalcase"', async () => { const [actual] = subjectCase( await parsed.sentencecase, - 'always', - 'pascal-case' + "always", + "pascal-case", ); const expected = false; expect(actual).toEqual(expected); @@ -395,8 +395,8 @@ test('with sentencecase subject should fail for "always pascalcase"', async () = test('with sentencecase subject should succeed for "never camelcase"', async () => { const [actual] = subjectCase( await parsed.sentencecase, - 'never', - 'camel-case' + "never", + "camel-case", ); const expected = true; expect(actual).toEqual(expected); @@ -405,8 +405,8 @@ test('with sentencecase subject should succeed for "never camelcase"', async () test('with sentencecase unicode subject should fail for "always camelcase"', async () => { const [actual] = subjectCase( await parsed.sentencecase_unicode, - 'always', - 'camel-case' + "always", + "camel-case", ); const expected = false; expect(actual).toEqual(expected); @@ -415,96 +415,96 @@ test('with sentencecase unicode subject should fail for "always camelcase"', asy test('should use expected message with "always"', async () => { const [, message] = subjectCase( await parsed.uppercase, - 'always', - 'lower-case' + "always", + "lower-case", ); - expect(message).toContain('must be lower-case'); + expect(message).toContain("must be lower-case"); }); test('should use expected message with "never"', async () => { const [, message] = subjectCase( await parsed.uppercase, - 'never', - 'upper-case' + "never", + "upper-case", ); - expect(message).toContain('must not be upper-case'); + expect(message).toContain("must not be upper-case"); }); test('with uppercase scope should succeed for "always [uppercase, lowercase]"', async () => { - const [actual] = subjectCase(await parsed.uppercase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = subjectCase(await parsed.uppercase, "always", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with lowercase subject should succeed for "always [uppercase, lowercase]"', async () => { - const [actual] = subjectCase(await parsed.lowercase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = subjectCase(await parsed.lowercase, "always", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase subject should fail for "always [uppercase, lowercase]"', async () => { - const [actual] = subjectCase(await parsed.mixedcase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = subjectCase(await parsed.mixedcase, "always", [ + "uppercase", + "lowercase", ]); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase subject should pass for "always [uppercase, lowercase, camel-case]"', async () => { - const [actual] = subjectCase(await parsed.mixedcase, 'always', [ - 'uppercase', - 'lowercase', - 'camel-case', + const [actual] = subjectCase(await parsed.mixedcase, "always", [ + "uppercase", + "lowercase", + "camel-case", ]); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase scope should pass for "never [uppercase, lowercase]"', async () => { - const [actual] = subjectCase(await parsed.mixedcase, 'never', [ - 'uppercase', - 'lowercase', + const [actual] = subjectCase(await parsed.mixedcase, "never", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with uppercase scope should fail for "never [uppercase, lowercase]"', async () => { - const [actual] = subjectCase(await parsed.uppercase, 'never', [ - 'uppercase', - 'lowercase', + const [actual] = subjectCase(await parsed.uppercase, "never", [ + "uppercase", + "lowercase", ]); const expected = false; expect(actual).toEqual(expected); }); test('with numeric subject should succeed for "never lowercase"', async () => { - const [actual] = subjectCase(await parsed.numeric, 'never', 'lowercase'); + const [actual] = subjectCase(await parsed.numeric, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with numeric subject should succeed for "always lowercase"', async () => { - const [actual] = subjectCase(await parsed.numeric, 'always', 'lowercase'); + const [actual] = subjectCase(await parsed.numeric, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with numeric subject should succeed for "never uppercase"', async () => { - const [actual] = subjectCase(await parsed.numeric, 'never', 'uppercase'); + const [actual] = subjectCase(await parsed.numeric, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with numeric subject should succeed for "always uppercase"', async () => { - const [actual] = subjectCase(await parsed.numeric, 'always', 'uppercase'); + const [actual] = subjectCase(await parsed.numeric, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/subject-case.ts b/@commitlint/rules/src/subject-case.ts index 13e7de850a..c5bfa610b7 100644 --- a/@commitlint/rules/src/subject-case.ts +++ b/@commitlint/rules/src/subject-case.ts @@ -1,6 +1,6 @@ -import {case as ensureCase} from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {TargetCaseType, SyncRule} from '@commitlint/types'; +import { case as ensureCase } from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { TargetCaseType, SyncRule } from "@commitlint/types"; /** * Since the rule requires first symbol of a subject to be a letter, use @@ -19,23 +19,23 @@ import {TargetCaseType, SyncRule} from '@commitlint/types'; */ const startsWithLetterRegex = /^[\p{Ll}\p{Lu}\p{Lt}]/iu; -const negated = (when?: string) => when === 'never'; +const negated = (when?: string) => when === "never"; export const subjectCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( parsed, - when = 'always', - value = [] + when = "always", + value = [], ) => { - const {subject} = parsed; + const { subject } = parsed; - if (typeof subject !== 'string' || !subject.match(startsWithLetterRegex)) { + if (typeof subject !== "string" || !subject.match(startsWithLetterRegex)) { return [true]; } const checks = (Array.isArray(value) ? value : [value]).map((check) => { - if (typeof check === 'string') { + if (typeof check === "string") { return { - when: 'always', + when: "always", case: check, }; } @@ -47,7 +47,7 @@ export const subjectCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( return negated(check.when) ? !r : r; }); - const list = checks.map((c) => c.case).join(', '); + const list = checks.map((c) => c.case).join(", "); return [ negated(when) ? !result : result, diff --git a/@commitlint/rules/src/subject-empty.test.ts b/@commitlint/rules/src/subject-empty.test.ts index dca594d9ed..e8c6440c84 100644 --- a/@commitlint/rules/src/subject-empty.test.ts +++ b/@commitlint/rules/src/subject-empty.test.ts @@ -1,10 +1,10 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {subjectEmpty} from './subject-empty.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { subjectEmpty } from "./subject-empty.js"; const messages = { - empty: 'test: \nbody', - filled: 'test: subject\nbody', + empty: "test: \nbody", + filled: "test: subject\nbody", }; const parsed = { @@ -12,38 +12,38 @@ const parsed = { filled: parse(messages.filled), }; -test('without subject should succeed for empty keyword', async () => { +test("without subject should succeed for empty keyword", async () => { const [actual] = subjectEmpty(await parsed.empty); const expected = true; expect(actual).toEqual(expected); }); test('without subject should fail for "never"', async () => { - const [actual] = subjectEmpty(await parsed.empty, 'never'); + const [actual] = subjectEmpty(await parsed.empty, "never"); const expected = false; expect(actual).toEqual(expected); }); test('without subject should succeed for "always"', async () => { - const [actual] = subjectEmpty(await parsed.empty, 'always'); + const [actual] = subjectEmpty(await parsed.empty, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with subject fail for empty keyword', async () => { +test("with subject fail for empty keyword", async () => { const [actual] = subjectEmpty(await parsed.filled); const expected = false; expect(actual).toEqual(expected); }); test('with subject succeed for "never"', async () => { - const [actual] = subjectEmpty(await parsed.filled, 'never'); + const [actual] = subjectEmpty(await parsed.filled, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with subject fail for "always"', async () => { - const [actual] = subjectEmpty(await parsed.filled, 'always'); + const [actual] = subjectEmpty(await parsed.filled, "always"); const expected = false; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/subject-empty.ts b/@commitlint/rules/src/subject-empty.ts index fc94daefcb..d489b2c3ab 100644 --- a/@commitlint/rules/src/subject-empty.ts +++ b/@commitlint/rules/src/subject-empty.ts @@ -1,13 +1,13 @@ -import * as ensure from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import * as ensure from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; -export const subjectEmpty: SyncRule = (parsed, when = 'always') => { - const negated = when === 'never'; - const notEmpty = ensure.notEmpty(parsed.subject || ''); +export const subjectEmpty: SyncRule = (parsed, when = "always") => { + const negated = when === "never"; + const notEmpty = ensure.notEmpty(parsed.subject || ""); return [ negated ? notEmpty : !notEmpty, - message(['subject', negated ? 'may not' : 'must', 'be empty']), + message(["subject", negated ? "may not" : "must", "be empty"]), ]; }; diff --git a/@commitlint/rules/src/subject-exclamation-mark.test.ts b/@commitlint/rules/src/subject-exclamation-mark.test.ts index ef1a9b2e28..55e47d0e7a 100644 --- a/@commitlint/rules/src/subject-exclamation-mark.test.ts +++ b/@commitlint/rules/src/subject-exclamation-mark.test.ts @@ -1,17 +1,17 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; // @ts-expect-error -- no typings -import preset from 'conventional-changelog-angular'; +import preset from "conventional-changelog-angular"; -import {subjectExclamationMark} from './subject-exclamation-mark.js'; +import { subjectExclamationMark } from "./subject-exclamation-mark.js"; const parseMessage = async (str: string) => { - const {parserOpts} = await preset(); + const { parserOpts } = await preset(); return parse(str, undefined, parserOpts); }; const messages = { - empty: 'test:\n', + empty: "test:\n", with: `test!: subject\n`, without: `test: subject\n`, }; @@ -23,37 +23,37 @@ const parsed = { }; test('empty against "always" should fail', async () => { - const [actual] = subjectExclamationMark(await parsed.empty, 'always'); + const [actual] = subjectExclamationMark(await parsed.empty, "always"); const expected = false; expect(actual).toEqual(expected); }); test('empty against "never" should succeed', async () => { - const [actual] = subjectExclamationMark(await parsed.empty, 'never'); + const [actual] = subjectExclamationMark(await parsed.empty, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with against "always" should succeed', async () => { - const [actual] = subjectExclamationMark(await parsed.with, 'always'); + const [actual] = subjectExclamationMark(await parsed.with, "always"); const expected = true; expect(actual).toEqual(expected); }); test('with against "never" should fail', async () => { - const [actual] = subjectExclamationMark(await parsed.with, 'never'); + const [actual] = subjectExclamationMark(await parsed.with, "never"); const expected = false; expect(actual).toEqual(expected); }); test('without against "always" should fail', async () => { - const [actual] = subjectExclamationMark(await parsed.without, 'always'); + const [actual] = subjectExclamationMark(await parsed.without, "always"); const expected = false; expect(actual).toEqual(expected); }); test('without against "never" should succeed', async () => { - const [actual] = subjectExclamationMark(await parsed.without, 'never'); + const [actual] = subjectExclamationMark(await parsed.without, "never"); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/subject-exclamation-mark.ts b/@commitlint/rules/src/subject-exclamation-mark.ts index 11cc29b590..19bf8eacca 100644 --- a/@commitlint/rules/src/subject-exclamation-mark.ts +++ b/@commitlint/rules/src/subject-exclamation-mark.ts @@ -1,21 +1,21 @@ -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; -export const subjectExclamationMark: SyncRule = (parsed, when = 'always') => { +export const subjectExclamationMark: SyncRule = (parsed, when = "always") => { const input = parsed.header; if (!input) { - return [true, '']; + return [true, ""]; } - const negated = when === 'never'; + const negated = when === "never"; const hasExclamationMark = /!:/.test(input); return [ negated ? !hasExclamationMark : hasExclamationMark, message([ - 'subject', - negated ? 'must not' : 'must', - 'have an exclamation mark in the subject to identify a breaking change', + "subject", + negated ? "must not" : "must", + "have an exclamation mark in the subject to identify a breaking change", ]), ]; }; diff --git a/@commitlint/rules/src/subject-full-stop.test.ts b/@commitlint/rules/src/subject-full-stop.test.ts index d787a537f8..344f65652b 100644 --- a/@commitlint/rules/src/subject-full-stop.test.ts +++ b/@commitlint/rules/src/subject-full-stop.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {subjectFullStop} from './subject-full-stop.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { subjectFullStop } from "./subject-full-stop.js"; const messages = { - empty: 'test:\n', + empty: "test:\n", with: `test: subject.\n`, without: `test: subject\n`, standardScopeWith: `type(scope): subject.\n`, - nonStandardScopeWith: 'type.scope: subject.\n', - ellipsisMessage: 'test: subject ends with ellipsis...', + nonStandardScopeWith: "type.scope: subject.\n", + ellipsisMessage: "test: subject ends with ellipsis...", }; const parsed = { @@ -21,37 +21,37 @@ const parsed = { }; test('empty against "always" should succeed', async () => { - const [actual] = subjectFullStop(await parsed.empty, 'always', '.'); + const [actual] = subjectFullStop(await parsed.empty, "always", "."); const expected = true; expect(actual).toEqual(expected); }); test('empty against "never ." should succeed', async () => { - const [actual] = subjectFullStop(await parsed.empty, 'never', '.'); + const [actual] = subjectFullStop(await parsed.empty, "never", "."); const expected = true; expect(actual).toEqual(expected); }); test('with against "always ." should succeed', async () => { - const [actual] = subjectFullStop(await parsed.with, 'always', '.'); + const [actual] = subjectFullStop(await parsed.with, "always", "."); const expected = true; expect(actual).toEqual(expected); }); test('with against "never ." should fail', async () => { - const [actual] = subjectFullStop(await parsed.with, 'never', '.'); + const [actual] = subjectFullStop(await parsed.with, "never", "."); const expected = false; expect(actual).toEqual(expected); }); test('without against "always ." should fail', async () => { - const [actual] = subjectFullStop(await parsed.without, 'always', '.'); + const [actual] = subjectFullStop(await parsed.without, "always", "."); const expected = false; expect(actual).toEqual(expected); }); test('without against "never ." should succeed', async () => { - const [actual] = subjectFullStop(await parsed.without, 'never', '.'); + const [actual] = subjectFullStop(await parsed.without, "never", "."); const expected = true; expect(actual).toEqual(expected); }); @@ -59,8 +59,8 @@ test('without against "never ." should succeed', async () => { test('commit message title with standard scope and full-stop against "never ." should fail', async () => { const [actual] = subjectFullStop( await parsed.standardScopeWith, - 'never', - '.' + "never", + ".", ); const expected = false; expect(actual).toEqual(expected); @@ -69,15 +69,15 @@ test('commit message title with standard scope and full-stop against "never ." s test('commit message title with non standard scope and full-stop against "never ." should fail', async () => { const [actual] = subjectFullStop( await parsed.nonStandardScopeWith, - 'never', - '.' + "never", + ".", ); const expected = false; expect(actual).toEqual(expected); }); test('ellipsis is not fullstop so commit title ending with it against "never ." should not fail', async () => { - const [actual] = subjectFullStop(await parsed.ellipsisMessage, 'never', '.'); + const [actual] = subjectFullStop(await parsed.ellipsisMessage, "never", "."); const expected = true; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/subject-full-stop.ts b/@commitlint/rules/src/subject-full-stop.ts index 1b4acd88cb..6f1eed4aef 100644 --- a/@commitlint/rules/src/subject-full-stop.ts +++ b/@commitlint/rules/src/subject-full-stop.ts @@ -1,26 +1,26 @@ -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; export const subjectFullStop: SyncRule<string> = ( parsed, - when = 'always', - value = '.' + when = "always", + value = ".", ) => { - const colonIndex = parsed.header?.indexOf(':') || 0; + const colonIndex = parsed.header?.indexOf(":") || 0; if (colonIndex > 0 && colonIndex === parsed.header!.length - 1) { return [true]; } const input = parsed.header; - const negated = when === 'never'; + const negated = when === "never"; let hasStop = input?.[input.length - 1] === value; - if (input?.slice(-3) === '...') { + if (input?.slice(-3) === "...") { hasStop = false; } return [ negated ? !hasStop : hasStop, - message(['subject', negated ? 'may not' : 'must', 'end with full stop']), + message(["subject", negated ? "may not" : "must", "end with full stop"]), ]; }; diff --git a/@commitlint/rules/src/subject-max-length.test.ts b/@commitlint/rules/src/subject-max-length.test.ts index 0cffa76800..c89b8c246d 100644 --- a/@commitlint/rules/src/subject-max-length.test.ts +++ b/@commitlint/rules/src/subject-max-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {subjectMaxLength} from './subject-max-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { subjectMaxLength } from "./subject-max-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = short.length; const messages = { - empty: 'test:\n', + empty: "test:\n", short: `test: ${short}\n`, long: `test: ${long}\n`, }; @@ -19,19 +19,19 @@ const parsed = { long: parse(messages.long), }; -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = subjectMaxLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should succeed', async () => { +test("with short should succeed", async () => { const [actual] = subjectMaxLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long should fail', async () => { +test("with long should fail", async () => { const [actual] = subjectMaxLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/subject-max-length.ts b/@commitlint/rules/src/subject-max-length.ts index 86d27ed60c..ca2c148cfa 100644 --- a/@commitlint/rules/src/subject-max-length.ts +++ b/@commitlint/rules/src/subject-max-length.ts @@ -1,10 +1,10 @@ -import {maxLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { maxLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const subjectMaxLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.subject; diff --git a/@commitlint/rules/src/subject-min-length.test.ts b/@commitlint/rules/src/subject-min-length.test.ts index fa22f8c0b8..d269f6e22a 100644 --- a/@commitlint/rules/src/subject-min-length.test.ts +++ b/@commitlint/rules/src/subject-min-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {subjectMinLength} from './subject-min-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { subjectMinLength } from "./subject-min-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = long.length; const messages = { - empty: 'test:\n', + empty: "test:\n", short: `test: ${short}\n`, long: `test: ${long}\n`, }; @@ -19,19 +19,19 @@ const parsed = { long: parse(messages.long), }; -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = subjectMinLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should fail', async () => { +test("with short should fail", async () => { const [actual] = subjectMinLength(await parsed.short, undefined, value); const expected = false; expect(actual).toEqual(expected); }); -test('with long should succeed', async () => { +test("with long should succeed", async () => { const [actual] = subjectMinLength(await parsed.long, undefined, value); const expected = true; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/subject-min-length.ts b/@commitlint/rules/src/subject-min-length.ts index 98310a4fb3..b0835e8159 100644 --- a/@commitlint/rules/src/subject-min-length.ts +++ b/@commitlint/rules/src/subject-min-length.ts @@ -1,10 +1,10 @@ -import {minLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { minLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const subjectMinLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.subject; if (!input) { diff --git a/@commitlint/rules/src/trailer-exists.test.ts b/@commitlint/rules/src/trailer-exists.test.ts index dd959a08a3..c090ad7b11 100644 --- a/@commitlint/rules/src/trailer-exists.test.ts +++ b/@commitlint/rules/src/trailer-exists.test.ts @@ -1,9 +1,9 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {trailerExists} from './trailer-exists.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { trailerExists } from "./trailer-exists.js"; const messages = { - empty: 'test:\n', + empty: "test:\n", with: `test: subject\n\nbody\n\nfooter\n\nSigned-off-by:\n\n`, without: `test: subject\n\nbody\n\nfooter\n\n`, inSubject: `test: subject Signed-off-by:\n\nbody\n\nfooter\n\n`, @@ -33,8 +33,8 @@ const parsed = { test('empty against "always trailer-exists" should fail', async () => { const [actual] = trailerExists( await parsed.empty, - 'always', - 'Signed-off-by:' + "always", + "Signed-off-by:", ); const expected = false; @@ -42,19 +42,19 @@ test('empty against "always trailer-exists" should fail', async () => { }); test('empty against "never trailer-exists" should succeed', async () => { - const [actual] = trailerExists(await parsed.empty, 'never', 'Signed-off-by:'); + const [actual] = trailerExists(await parsed.empty, "never", "Signed-off-by:"); const expected = true; expect(actual).toEqual(expected); }); test('with against "always trailer-exists" should succeed', async () => { - const [actual] = trailerExists(await parsed.with, 'always', 'Signed-off-by:'); + const [actual] = trailerExists(await parsed.with, "always", "Signed-off-by:"); const expected = true; expect(actual).toEqual(expected); }); test('with against "never trailer-exists" should fail', async () => { - const [actual] = trailerExists(await parsed.with, 'never', 'Signed-off-by:'); + const [actual] = trailerExists(await parsed.with, "never", "Signed-off-by:"); const expected = false; expect(actual).toEqual(expected); }); @@ -62,8 +62,8 @@ test('with against "never trailer-exists" should fail', async () => { test('without against "always trailer-exists" should fail', async () => { const [actual] = trailerExists( await parsed.without, - 'always', - 'Signed-off-by:' + "always", + "Signed-off-by:", ); const expected = false; @@ -73,19 +73,19 @@ test('without against "always trailer-exists" should fail', async () => { test('without against "never trailer-exists" should succeed', async () => { const [actual] = trailerExists( await parsed.without, - 'never', - 'Signed-off-by:' + "never", + "Signed-off-by:", ); const expected = true; expect(actual).toEqual(expected); }); -test('comments and other trailers should be ignored', async () => { +test("comments and other trailers should be ignored", async () => { const [actual] = trailerExists( await parsed.withSignoffAndNoise, - 'always', - 'Signed-off-by:' + "always", + "Signed-off-by:", ); const expected = true; @@ -95,8 +95,8 @@ test('comments and other trailers should be ignored', async () => { test('inSubject against "always trailer-exists" should fail', async () => { const [actual] = trailerExists( await parsed.inSubject, - 'always', - 'Signed-off-by:' + "always", + "Signed-off-by:", ); const expected = false; @@ -106,8 +106,8 @@ test('inSubject against "always trailer-exists" should fail', async () => { test('inSubject against "never trailer-exists" should succeed', async () => { const [actual] = trailerExists( await parsed.inSubject, - 'never', - 'Signed-off-by:' + "never", + "Signed-off-by:", ); const expected = true; @@ -117,8 +117,8 @@ test('inSubject against "never trailer-exists" should succeed', async () => { test('inBody against "always trailer-exists" should fail', async () => { const [actual] = trailerExists( await parsed.inBody, - 'always', - 'Signed-off-by:' + "always", + "Signed-off-by:", ); const expected = false; @@ -128,8 +128,8 @@ test('inBody against "always trailer-exists" should fail', async () => { test('inBody against "never trailer-exists" should succeed', async () => { const [actual] = trailerExists( await parsed.inBody, - 'never', - 'Signed-off-by:' + "never", + "Signed-off-by:", ); const expected = true; diff --git a/@commitlint/rules/src/trailer-exists.ts b/@commitlint/rules/src/trailer-exists.ts index dca7d1478d..3dc516767e 100644 --- a/@commitlint/rules/src/trailer-exists.ts +++ b/@commitlint/rules/src/trailer-exists.ts @@ -1,30 +1,30 @@ -import {spawnSync} from 'node:child_process'; -import message from '@commitlint/message'; -import toLines from '@commitlint/to-lines'; -import {SyncRule} from '@commitlint/types'; +import { spawnSync } from "node:child_process"; +import message from "@commitlint/message"; +import toLines from "@commitlint/to-lines"; +import { SyncRule } from "@commitlint/types"; export const trailerExists: SyncRule<string> = ( parsed, - when = 'always', - value = '' + when = "always", + value = "", ) => { - const trailers = spawnSync('git', ['interpret-trailers', '--parse'], { - input: parsed.raw || '', + const trailers = spawnSync("git", ["interpret-trailers", "--parse"], { + input: parsed.raw || "", }).stdout; const matches = toLines(trailers.toString()).filter((ln) => - ln.startsWith(value) + ln.startsWith(value), ).length; - const negated = when === 'never'; + const negated = when === "never"; const hasTrailer = matches > 0; return [ negated ? !hasTrailer : hasTrailer, message([ - 'message', - negated ? 'must not' : 'must', - 'have `' + value + '` trailer', + "message", + negated ? "must not" : "must", + "have `" + value + "` trailer", ]), ]; }; diff --git a/@commitlint/rules/src/type-case.test.ts b/@commitlint/rules/src/type-case.test.ts index 79ab7b8f98..b482e53cc0 100644 --- a/@commitlint/rules/src/type-case.test.ts +++ b/@commitlint/rules/src/type-case.test.ts @@ -1,17 +1,17 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {typeCase} from './type-case.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { typeCase } from "./type-case.js"; const messages = { - empty: '(scope): subject', - lowercase: 'type: subject', - mixedcase: 'tYpE: subject', - uppercase: 'TYPE: subject', - camelcase: 'tyPe: subject', - pascalcase: 'TyPe: subject', - snakecase: 'ty_pe: subject', - kebabcase: 'ty-pe: subject', - startcase: 'Ty Pe: subject', + empty: "(scope): subject", + lowercase: "type: subject", + mixedcase: "tYpE: subject", + uppercase: "TYPE: subject", + camelcase: "tyPe: subject", + pascalcase: "TyPe: subject", + snakecase: "ty_pe: subject", + kebabcase: "ty-pe: subject", + startcase: "Ty Pe: subject", }; const parsed = { @@ -25,300 +25,300 @@ const parsed = { kebabcase: parse(messages.kebabcase), startcase: parse(messages.startcase, undefined, { headerPattern: /^(.*): (.*)$/, - headerCorrespondence: ['type', 'subject'], + headerCorrespondence: ["type", "subject"], }), }; test('with empty type should succeed for "never lowercase"', async () => { - const [actual] = typeCase(await parsed.empty, 'never', 'lowercase'); + const [actual] = typeCase(await parsed.empty, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty type should succeed for "always lowercase"', async () => { - const [actual] = typeCase(await parsed.empty, 'always', 'lowercase'); + const [actual] = typeCase(await parsed.empty, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty type should succeed for "never uppercase"', async () => { - const [actual] = typeCase(await parsed.empty, 'never', 'uppercase'); + const [actual] = typeCase(await parsed.empty, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with empty type should succeed for "always uppercase"', async () => { - const [actual] = typeCase(await parsed.empty, 'always', 'uppercase'); + const [actual] = typeCase(await parsed.empty, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with lowercase type should fail for "never lowercase"', async () => { - const [actual] = typeCase(await parsed.lowercase, 'never', 'lowercase'); + const [actual] = typeCase(await parsed.lowercase, "never", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with lowercase type should succeed for "always lowercase"', async () => { - const [actual] = typeCase(await parsed.lowercase, 'always', 'lowercase'); + const [actual] = typeCase(await parsed.lowercase, "always", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase type should succeed for "never lowercase"', async () => { - const [actual] = typeCase(await parsed.mixedcase, 'never', 'lowercase'); + const [actual] = typeCase(await parsed.mixedcase, "never", "lowercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase type should fail for "always lowercase"', async () => { - const [actual] = typeCase(await parsed.mixedcase, 'always', 'lowercase'); + const [actual] = typeCase(await parsed.mixedcase, "always", "lowercase"); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase type should succeed for "never uppercase"', async () => { - const [actual] = typeCase(await parsed.mixedcase, 'never', 'uppercase'); + const [actual] = typeCase(await parsed.mixedcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase type should fail for "always uppercase"', async () => { - const [actual] = typeCase(await parsed.mixedcase, 'always', 'uppercase'); + const [actual] = typeCase(await parsed.mixedcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with uppercase type should fail for "never uppercase"', async () => { - const [actual] = typeCase(await parsed.uppercase, 'never', 'uppercase'); + const [actual] = typeCase(await parsed.uppercase, "never", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with lowercase type should succeed for "always uppercase"', async () => { - const [actual] = typeCase(await parsed.uppercase, 'always', 'uppercase'); + const [actual] = typeCase(await parsed.uppercase, "always", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with camelcase type should fail for "always uppercase"', async () => { - const [actual] = typeCase(await parsed.camelcase, 'always', 'uppercase'); + const [actual] = typeCase(await parsed.camelcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase type should succeed for "never uppercase"', async () => { - const [actual] = typeCase(await parsed.camelcase, 'never', 'uppercase'); + const [actual] = typeCase(await parsed.camelcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with camelcase type should fail for "always pascalcase"', async () => { - const [actual] = typeCase(await parsed.camelcase, 'always', 'pascal-case'); + const [actual] = typeCase(await parsed.camelcase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase type should fail for "always kebabcase"', async () => { - const [actual] = typeCase(await parsed.camelcase, 'always', 'kebab-case'); + const [actual] = typeCase(await parsed.camelcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase type should fail for "always snakecase"', async () => { - const [actual] = typeCase(await parsed.camelcase, 'always', 'snake-case'); + const [actual] = typeCase(await parsed.camelcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase type should fail for "always startcase"', async () => { - const [actual] = typeCase(await parsed.camelcase, 'always', 'start-case'); + const [actual] = typeCase(await parsed.camelcase, "always", "start-case"); const expected = false; expect(actual).toEqual(expected); }); test('with camelcase type should succeed for "always camelcase"', async () => { - const [actual] = typeCase(await parsed.camelcase, 'always', 'camel-case'); + const [actual] = typeCase(await parsed.camelcase, "always", "camel-case"); const expected = true; expect(actual).toEqual(expected); }); test('with pascalcase type should fail for "always uppercase"', async () => { - const [actual] = typeCase(await parsed.pascalcase, 'always', 'uppercase'); + const [actual] = typeCase(await parsed.pascalcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase type should succeed for "never uppercase"', async () => { - const [actual] = typeCase(await parsed.pascalcase, 'never', 'uppercase'); + const [actual] = typeCase(await parsed.pascalcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with pascalcase type should fail for "always camelcase"', async () => { - const [actual] = typeCase(await parsed.pascalcase, 'always', 'camel-case'); + const [actual] = typeCase(await parsed.pascalcase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase type should fail for "always kebabcase"', async () => { - const [actual] = typeCase(await parsed.pascalcase, 'always', 'kebab-case'); + const [actual] = typeCase(await parsed.pascalcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase type should fail for "always snakecase"', async () => { - const [actual] = typeCase(await parsed.pascalcase, 'always', 'snake-case'); + const [actual] = typeCase(await parsed.pascalcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase type should fail for "always startcase"', async () => { - const [actual] = typeCase(await parsed.pascalcase, 'always', 'start-case'); + const [actual] = typeCase(await parsed.pascalcase, "always", "start-case"); const expected = false; expect(actual).toEqual(expected); }); test('with pascalcase type should succeed for "always pascalcase"', async () => { - const [actual] = typeCase(await parsed.pascalcase, 'always', 'pascal-case'); + const [actual] = typeCase(await parsed.pascalcase, "always", "pascal-case"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase type should fail for "always uppercase"', async () => { - const [actual] = typeCase(await parsed.snakecase, 'always', 'uppercase'); + const [actual] = typeCase(await parsed.snakecase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase type should succeed for "never uppercase"', async () => { - const [actual] = typeCase(await parsed.snakecase, 'never', 'uppercase'); + const [actual] = typeCase(await parsed.snakecase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase type should fail for "always camelcase"', async () => { - const [actual] = typeCase(await parsed.snakecase, 'always', 'camel-case'); + const [actual] = typeCase(await parsed.snakecase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase type should fail for "always kebabcase"', async () => { - const [actual] = typeCase(await parsed.snakecase, 'always', 'kebab-case'); + const [actual] = typeCase(await parsed.snakecase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase type should succeed for "always snakecase"', async () => { - const [actual] = typeCase(await parsed.snakecase, 'always', 'snake-case'); + const [actual] = typeCase(await parsed.snakecase, "always", "snake-case"); const expected = true; expect(actual).toEqual(expected); }); test('with snakecase type should fail for "always pascalcase"', async () => { - const [actual] = typeCase(await parsed.snakecase, 'always', 'pascal-case'); + const [actual] = typeCase(await parsed.snakecase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with snakecase type should fail for "always start case"', async () => { - const [actual] = typeCase(await parsed.snakecase, 'always', 'start-case'); + const [actual] = typeCase(await parsed.snakecase, "always", "start-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase type should fail for "always uppercase"', async () => { - const [actual] = typeCase(await parsed.startcase, 'always', 'uppercase'); + const [actual] = typeCase(await parsed.startcase, "always", "uppercase"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase type should succeed for "never uppercase"', async () => { - const [actual] = typeCase(await parsed.startcase, 'never', 'uppercase'); + const [actual] = typeCase(await parsed.startcase, "never", "uppercase"); const expected = true; expect(actual).toEqual(expected); }); test('with startcase type should fail for "always camelcase"', async () => { - const [actual] = typeCase(await parsed.startcase, 'always', 'camel-case'); + const [actual] = typeCase(await parsed.startcase, "always", "camel-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase type should fail for "always kebabcase"', async () => { - const [actual] = typeCase(await parsed.startcase, 'always', 'kebab-case'); + const [actual] = typeCase(await parsed.startcase, "always", "kebab-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase type should fail for "always snakecase"', async () => { - const [actual] = typeCase(await parsed.startcase, 'always', 'snake-case'); + const [actual] = typeCase(await parsed.startcase, "always", "snake-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase type should fail for "always pascalcase"', async () => { - const [actual] = typeCase(await parsed.startcase, 'always', 'pascal-case'); + const [actual] = typeCase(await parsed.startcase, "always", "pascal-case"); const expected = false; expect(actual).toEqual(expected); }); test('with startcase type should succeed for "always startcase"', async () => { - const [actual] = typeCase(await parsed.startcase, 'always', 'start-case'); + const [actual] = typeCase(await parsed.startcase, "always", "start-case"); const expected = true; expect(actual).toEqual(expected); }); test('with uppercase scope should succeed for "always [uppercase, lowercase]"', async () => { - const [actual] = typeCase(await parsed.uppercase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = typeCase(await parsed.uppercase, "always", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with lowercase subject should succeed for "always [uppercase, lowercase]"', async () => { - const [actual] = typeCase(await parsed.lowercase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = typeCase(await parsed.lowercase, "always", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase subject should fail for "always [uppercase, lowercase]"', async () => { - const [actual] = typeCase(await parsed.mixedcase, 'always', [ - 'uppercase', - 'lowercase', + const [actual] = typeCase(await parsed.mixedcase, "always", [ + "uppercase", + "lowercase", ]); const expected = false; expect(actual).toEqual(expected); }); test('with mixedcase subject should pass for "always [uppercase, lowercase, camel-case]"', async () => { - const [actual] = typeCase(await parsed.mixedcase, 'always', [ - 'uppercase', - 'lowercase', - 'camel-case', + const [actual] = typeCase(await parsed.mixedcase, "always", [ + "uppercase", + "lowercase", + "camel-case", ]); const expected = true; expect(actual).toEqual(expected); }); test('with mixedcase scope should pass for "never [uppercase, lowercase]"', async () => { - const [actual] = typeCase(await parsed.mixedcase, 'never', [ - 'uppercase', - 'lowercase', + const [actual] = typeCase(await parsed.mixedcase, "never", [ + "uppercase", + "lowercase", ]); const expected = true; expect(actual).toEqual(expected); }); test('with uppercase scope should fail for "never [uppercase, lowercase]"', async () => { - const [actual] = typeCase(await parsed.uppercase, 'never', [ - 'uppercase', - 'lowercase', + const [actual] = typeCase(await parsed.uppercase, "never", [ + "uppercase", + "lowercase", ]); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/type-case.ts b/@commitlint/rules/src/type-case.ts index 71aa2fafdc..8c622e26ff 100644 --- a/@commitlint/rules/src/type-case.ts +++ b/@commitlint/rules/src/type-case.ts @@ -1,24 +1,24 @@ -import {case as ensureCase} from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {TargetCaseType, SyncRule} from '@commitlint/types'; +import { case as ensureCase } from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { TargetCaseType, SyncRule } from "@commitlint/types"; -const negated = (when?: string) => when === 'never'; +const negated = (when?: string) => when === "never"; export const typeCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( parsed, - when = 'always', - value = [] + when = "always", + value = [], ) => { - const {type} = parsed; + const { type } = parsed; if (!type) { return [true]; } const checks = (Array.isArray(value) ? value : [value]).map((check) => { - if (typeof check === 'string') { + if (typeof check === "string") { return { - when: 'always', + when: "always", case: check, }; } @@ -30,7 +30,7 @@ export const typeCase: SyncRule<TargetCaseType | TargetCaseType[]> = ( return negated(check.when) ? !r : r; }); - const list = checks.map((c) => c.case).join(', '); + const list = checks.map((c) => c.case).join(", "); return [ negated(when) ? !result : result, diff --git a/@commitlint/rules/src/type-empty.test.ts b/@commitlint/rules/src/type-empty.test.ts index 862fb3ae31..48b5d3a893 100644 --- a/@commitlint/rules/src/type-empty.test.ts +++ b/@commitlint/rules/src/type-empty.test.ts @@ -1,10 +1,10 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {typeEmpty} from './type-empty.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { typeEmpty } from "./type-empty.js"; const messages = { - empty: '(scope):', - filled: 'type: subject', + empty: "(scope):", + filled: "type: subject", }; const parsed = { @@ -12,38 +12,38 @@ const parsed = { filled: parse(messages.filled), }; -test('without type should succeed for empty keyword', async () => { +test("without type should succeed for empty keyword", async () => { const [actual] = typeEmpty(await parsed.empty); const expected = true; expect(actual).toEqual(expected); }); test('without type should fail for "never"', async () => { - const [actual] = typeEmpty(await parsed.empty, 'never'); + const [actual] = typeEmpty(await parsed.empty, "never"); const expected = false; expect(actual).toEqual(expected); }); test('without type should succeed for "always"', async () => { - const [actual] = typeEmpty(await parsed.empty, 'always'); + const [actual] = typeEmpty(await parsed.empty, "always"); const expected = true; expect(actual).toEqual(expected); }); -test('with type fail for empty keyword', async () => { +test("with type fail for empty keyword", async () => { const [actual] = typeEmpty(await parsed.filled); const expected = false; expect(actual).toEqual(expected); }); test('with type succeed for "never"', async () => { - const [actual] = typeEmpty(await parsed.filled, 'never'); + const [actual] = typeEmpty(await parsed.filled, "never"); const expected = true; expect(actual).toEqual(expected); }); test('with type fail for "always"', async () => { - const [actual] = typeEmpty(await parsed.filled, 'always'); + const [actual] = typeEmpty(await parsed.filled, "always"); const expected = false; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/type-empty.ts b/@commitlint/rules/src/type-empty.ts index 8802e00d77..867f6120e5 100644 --- a/@commitlint/rules/src/type-empty.ts +++ b/@commitlint/rules/src/type-empty.ts @@ -1,12 +1,12 @@ -import * as ensure from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import * as ensure from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; -export const typeEmpty: SyncRule = (parsed, when = 'always') => { - const negated = when === 'never'; - const notEmpty = ensure.notEmpty(parsed.type || ''); +export const typeEmpty: SyncRule = (parsed, when = "always") => { + const negated = when === "never"; + const notEmpty = ensure.notEmpty(parsed.type || ""); return [ negated ? notEmpty : !notEmpty, - message(['type', negated ? 'may not' : 'must', 'be empty']), + message(["type", negated ? "may not" : "must", "be empty"]), ]; }; diff --git a/@commitlint/rules/src/type-enum.test.ts b/@commitlint/rules/src/type-enum.test.ts index 4f3dd6ca31..dda24c27ea 100644 --- a/@commitlint/rules/src/type-enum.test.ts +++ b/@commitlint/rules/src/type-enum.test.ts @@ -1,11 +1,11 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {typeEnum} from './type-enum.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { typeEnum } from "./type-enum.js"; const messages = { - empty: '(): \n', - a: 'a(): \n', - b: 'b(): \n', + empty: "(): \n", + a: "a(): \n", + b: "b(): \n", }; const parsed = { @@ -14,110 +14,110 @@ const parsed = { b: parse(messages.b), }; -test('empty succeeds', async () => { +test("empty succeeds", async () => { const [actual] = typeEnum(await parsed.empty); const expected = true; expect(actual).toEqual(expected); }); test('empty on "a" succeeds', async () => { - const [actual] = typeEnum(await parsed.empty, undefined, ['a']); + const [actual] = typeEnum(await parsed.empty, undefined, ["a"]); const expected = true; expect(actual).toEqual(expected); }); test('empty on "always a" succeeds', async () => { - const [actual] = typeEnum(await parsed.empty, 'always', ['a']); + const [actual] = typeEnum(await parsed.empty, "always", ["a"]); const expected = true; expect(actual).toEqual(expected); }); test('empty on "never a" succeeds', async () => { - const [actual] = typeEnum(await parsed.empty, 'never', ['a']); + const [actual] = typeEnum(await parsed.empty, "never", ["a"]); const expected = true; expect(actual).toEqual(expected); }); test('empty on "always a, b" succeeds', async () => { - const [actual] = typeEnum(await parsed.empty, 'always', ['a', 'b']); + const [actual] = typeEnum(await parsed.empty, "always", ["a", "b"]); const expected = true; expect(actual).toEqual(expected); }); test('empty on "never a, b" succeeds', async () => { - const [actual] = typeEnum(await parsed.empty, 'never', ['a', 'b']); + const [actual] = typeEnum(await parsed.empty, "never", ["a", "b"]); const expected = true; expect(actual).toEqual(expected); }); test('a on "a" succeeds', async () => { - const [actual] = typeEnum(await parsed.a, undefined, ['a']); + const [actual] = typeEnum(await parsed.a, undefined, ["a"]); const expected = true; expect(actual).toEqual(expected); }); test('a on "always a" succeeds', async () => { - const [actual] = typeEnum(await parsed.a, 'always', ['a']); + const [actual] = typeEnum(await parsed.a, "always", ["a"]); const expected = true; expect(actual).toEqual(expected); }); test('a on "never a" fails', async () => { - const [actual] = typeEnum(await parsed.a, 'never', ['a']); + const [actual] = typeEnum(await parsed.a, "never", ["a"]); const expected = false; expect(actual).toEqual(expected); }); test('b on "b" succeeds', async () => { - const [actual] = typeEnum(await parsed.b, undefined, ['b']); + const [actual] = typeEnum(await parsed.b, undefined, ["b"]); const expected = true; expect(actual).toEqual(expected); }); test('b on "always b" succeeds', async () => { - const [actual] = typeEnum(await parsed.b, 'always', ['b']); + const [actual] = typeEnum(await parsed.b, "always", ["b"]); const expected = true; expect(actual).toEqual(expected); }); test('b on "never b" fails', async () => { - const [actual] = typeEnum(await parsed.b, 'never', ['b']); + const [actual] = typeEnum(await parsed.b, "never", ["b"]); const expected = false; expect(actual).toEqual(expected); }); test('a on "a, b" succeeds', async () => { - const [actual] = typeEnum(await parsed.a, undefined, ['a', 'b']); + const [actual] = typeEnum(await parsed.a, undefined, ["a", "b"]); const expected = true; expect(actual).toEqual(expected); }); test('a on "always a, b" succeeds', async () => { - const [actual] = typeEnum(await parsed.a, 'always', ['a', 'b']); + const [actual] = typeEnum(await parsed.a, "always", ["a", "b"]); const expected = true; expect(actual).toEqual(expected); }); test('a on "never a, b" fails', async () => { - const [actual] = typeEnum(await parsed.a, 'never', ['a', 'b']); + const [actual] = typeEnum(await parsed.a, "never", ["a", "b"]); const expected = false; expect(actual).toEqual(expected); }); test('b on "a, b" succeeds', async () => { - const [actual] = typeEnum(await parsed.b, undefined, ['a', 'b']); + const [actual] = typeEnum(await parsed.b, undefined, ["a", "b"]); const expected = true; expect(actual).toEqual(expected); }); test('b on "always a, b" succeeds', async () => { - const [actual] = typeEnum(await parsed.b, 'always', ['a', 'b']); + const [actual] = typeEnum(await parsed.b, "always", ["a", "b"]); const expected = true; expect(actual).toEqual(expected); }); test('b on "never a, b" fails', async () => { - const [actual] = typeEnum(await parsed.b, 'never', ['a', 'b']); + const [actual] = typeEnum(await parsed.b, "never", ["a", "b"]); const expected = false; expect(actual).toEqual(expected); }); diff --git a/@commitlint/rules/src/type-enum.ts b/@commitlint/rules/src/type-enum.ts index c4a8f9aa18..4ae17d9574 100644 --- a/@commitlint/rules/src/type-enum.ts +++ b/@commitlint/rules/src/type-enum.ts @@ -1,19 +1,19 @@ -import * as ensure from '@commitlint/ensure'; -import message from '@commitlint/message'; -import {SyncRule} from '@commitlint/types'; +import * as ensure from "@commitlint/ensure"; +import message from "@commitlint/message"; +import { SyncRule } from "@commitlint/types"; export const typeEnum: SyncRule<string[]> = ( parsed, - when = 'always', - value = [] + when = "always", + value = [], ) => { - const {type: input} = parsed; + const { type: input } = parsed; if (!input) { return [true]; } - const negated = when === 'never'; + const negated = when === "never"; const result = ensure.enum(input, value); return [ @@ -21,7 +21,7 @@ export const typeEnum: SyncRule<string[]> = ( message([ `type must`, negated ? `not` : null, - `be one of [${value.join(', ')}]`, + `be one of [${value.join(", ")}]`, ]), ]; }; diff --git a/@commitlint/rules/src/type-max-length.test.ts b/@commitlint/rules/src/type-max-length.test.ts index c77312ab49..2ce7601fcd 100644 --- a/@commitlint/rules/src/type-max-length.test.ts +++ b/@commitlint/rules/src/type-max-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {typeMaxLength} from './type-max-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { typeMaxLength } from "./type-max-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = short.length; const messages = { - empty: '():\n', + empty: "():\n", short: `${short}: \n`, long: `${long}: \n`, }; @@ -19,19 +19,19 @@ const parsed = { long: parse(messages.long), }; -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = typeMaxLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should succeed', async () => { +test("with short should succeed", async () => { const [actual] = typeMaxLength(await parsed.short, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with long should fail', async () => { +test("with long should fail", async () => { const [actual] = typeMaxLength(await parsed.long, undefined, value); const expected = false; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/type-max-length.ts b/@commitlint/rules/src/type-max-length.ts index 1e4d27766f..7398ef3138 100644 --- a/@commitlint/rules/src/type-max-length.ts +++ b/@commitlint/rules/src/type-max-length.ts @@ -1,10 +1,10 @@ -import {maxLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { maxLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const typeMaxLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.type; diff --git a/@commitlint/rules/src/type-min-length.test.ts b/@commitlint/rules/src/type-min-length.test.ts index 3503c920cc..7caf3a91c5 100644 --- a/@commitlint/rules/src/type-min-length.test.ts +++ b/@commitlint/rules/src/type-min-length.test.ts @@ -1,14 +1,14 @@ -import {test, expect} from 'vitest'; -import parse from '@commitlint/parse'; -import {typeMinLength} from './type-min-length.js'; +import { test, expect } from "vitest"; +import parse from "@commitlint/parse"; +import { typeMinLength } from "./type-min-length.js"; -const short = 'a'; -const long = 'ab'; +const short = "a"; +const long = "ab"; const value = long.length; const messages = { - empty: '():\n', + empty: "():\n", short: `${short}: \n`, long: `${long}: \n`, }; @@ -19,19 +19,19 @@ const parsed = { long: parse(messages.long), }; -test('with empty should succeed', async () => { +test("with empty should succeed", async () => { const [actual] = typeMinLength(await parsed.empty, undefined, value); const expected = true; expect(actual).toEqual(expected); }); -test('with short should fail', async () => { +test("with short should fail", async () => { const [actual] = typeMinLength(await parsed.short, undefined, value); const expected = false; expect(actual).toEqual(expected); }); -test('with long should succeed', async () => { +test("with long should succeed", async () => { const [actual] = typeMinLength(await parsed.long, undefined, value); const expected = true; expect(actual).toEqual(expected); diff --git a/@commitlint/rules/src/type-min-length.ts b/@commitlint/rules/src/type-min-length.ts index f7ff3ea38b..619f7593ad 100644 --- a/@commitlint/rules/src/type-min-length.ts +++ b/@commitlint/rules/src/type-min-length.ts @@ -1,10 +1,10 @@ -import {minLength} from '@commitlint/ensure'; -import {SyncRule} from '@commitlint/types'; +import { minLength } from "@commitlint/ensure"; +import { SyncRule } from "@commitlint/types"; export const typeMinLength: SyncRule<number> = ( parsed, _when = undefined, - value = 0 + value = 0, ) => { const input = parsed.type; if (!input) { diff --git a/@commitlint/rules/tsconfig.json b/@commitlint/rules/tsconfig.json index 3f6d480309..2bc7f16034 100644 --- a/@commitlint/rules/tsconfig.json +++ b/@commitlint/rules/tsconfig.json @@ -8,9 +8,9 @@ "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], "references": [ - {"path": "../ensure"}, - {"path": "../message"}, - {"path": "../to-lines"}, - {"path": "../types"} + { "path": "../ensure" }, + { "path": "../message" }, + { "path": "../to-lines" }, + { "path": "../types" } ] } diff --git a/@commitlint/to-lines/src/index.test.ts b/@commitlint/to-lines/src/index.test.ts index 095a9758df..8df9e30d52 100644 --- a/@commitlint/to-lines/src/index.test.ts +++ b/@commitlint/to-lines/src/index.test.ts @@ -1,27 +1,27 @@ -import {test, expect} from 'vitest'; +import { test, expect } from "vitest"; -import toLines from './index.js'; +import toLines from "./index.js"; -test('should return an array for empty input', () => { +test("should return an array for empty input", () => { expect((toLines as () => string[])()).toStrictEqual([]); }); -test('should return an array for null input', () => { +test("should return an array for null input", () => { expect((toLines as (input: any) => string[])(null)).toStrictEqual([]); }); -test('should return an array for empty string input', () => { - expect(toLines('')).toStrictEqual(['']); +test("should return an array for empty string input", () => { + expect(toLines("")).toStrictEqual([""]); }); -test('should split LF newlines', () => { - expect(toLines('some\nweird\ntext')).toStrictEqual(['some', 'weird', 'text']); +test("should split LF newlines", () => { + expect(toLines("some\nweird\ntext")).toStrictEqual(["some", "weird", "text"]); }); -test('should split CR+LF newlines', () => { - expect(toLines('some\r\nweird\r\ntext')).toStrictEqual([ - 'some', - 'weird', - 'text', +test("should split CR+LF newlines", () => { + expect(toLines("some\r\nweird\r\ntext")).toStrictEqual([ + "some", + "weird", + "text", ]); }); diff --git a/@commitlint/to-lines/src/index.ts b/@commitlint/to-lines/src/index.ts index 4870c2bcbf..ccc1d1b7d2 100644 --- a/@commitlint/to-lines/src/index.ts +++ b/@commitlint/to-lines/src/index.ts @@ -1,5 +1,5 @@ export default function toLines(input?: string | null): string[] { - if (typeof input !== 'string') { + if (typeof input !== "string") { return []; } diff --git a/@commitlint/top-level/src/index.ts b/@commitlint/top-level/src/index.ts index ed71acbad8..4996d4f8ee 100644 --- a/@commitlint/top-level/src/index.ts +++ b/@commitlint/top-level/src/index.ts @@ -1,5 +1,5 @@ -import path from 'node:path'; -import {findUp} from 'find-up'; +import path from "node:path"; +import { findUp } from "find-up"; export default toplevel; @@ -9,19 +9,19 @@ export default toplevel; async function toplevel(cwd?: string) { const found = await searchDotGit(cwd); - if (typeof found !== 'string') { + if (typeof found !== "string") { return found; } - return path.join(found, '..'); + return path.join(found, ".."); } /** * Search .git, the '.git' can be a file(submodule), also can be a directory(normal) */ async function searchDotGit(cwd?: string) { - const foundFile = await findUp('.git', {cwd, type: 'file'}); - const foundDir = await findUp('.git', {cwd, type: 'directory'}); + const foundFile = await findUp(".git", { cwd, type: "file" }); + const foundDir = await findUp(".git", { cwd, type: "directory" }); return foundFile || foundDir; } diff --git a/@commitlint/travis-cli/cli.js b/@commitlint/travis-cli/cli.js index 1bda77159f..940e27804b 100755 --- a/@commitlint/travis-cli/cli.js +++ b/@commitlint/travis-cli/cli.js @@ -1,2 +1,2 @@ #!/usr/bin/env node -import './lib/cli.js'; +import "./lib/cli.js"; diff --git a/@commitlint/travis-cli/src/cli.test.ts b/@commitlint/travis-cli/src/cli.test.ts index 848c47bfdf..b276a40792 100644 --- a/@commitlint/travis-cli/src/cli.test.ts +++ b/@commitlint/travis-cli/src/cli.test.ts @@ -1,67 +1,67 @@ -import {SpawnOptions} from 'node:child_process'; +import { SpawnOptions } from "node:child_process"; -import {test, expect} from 'vitest'; -import {createRequire} from 'node:module'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; +import { test, expect } from "vitest"; +import { createRequire } from "node:module"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; -import {git} from '@commitlint/test'; -import {x} from 'tinyexec'; +import { git } from "@commitlint/test"; +import { x } from "tinyexec"; const require = createRequire(import.meta.url); -const __dirname = path.resolve(fileURLToPath(import.meta.url), '..'); +const __dirname = path.resolve(fileURLToPath(import.meta.url), ".."); -const bin = require.resolve('../cli.js'); +const bin = require.resolve("../cli.js"); -const TRAVIS_COMMITLINT_BIN = require.resolve('../fixtures/commitlint'); -const TRAVIS_COMMITLINT_GIT_BIN = require.resolve('../fixtures/git'); +const TRAVIS_COMMITLINT_BIN = require.resolve("../fixtures/commitlint"); +const TRAVIS_COMMITLINT_GIT_BIN = require.resolve("../fixtures/git"); const validBaseEnv = { - TRAVIS: 'true', - CI: 'true', - TRAVIS_COMMIT: 'TRAVIS_COMMIT', + TRAVIS: "true", + CI: "true", + TRAVIS_COMMIT: "TRAVIS_COMMIT", TRAVIS_COMMITLINT_BIN: TRAVIS_COMMITLINT_BIN, TRAVIS_COMMITLINT_GIT_BIN: TRAVIS_COMMITLINT_GIT_BIN, - TRAVIS_COMMIT_RANGE: 'TRAVIS_COMMIT_A.TRAVIS_COMMIT_B', - TRAVIS_EVENT_TYPE: 'TRAVIS_EVENT_TYPE', - TRAVIS_REPO_SLUG: 'TRAVIS_REPO_SLUG', - TRAVIS_PULL_REQUEST_SLUG: 'TRAVIS_PULL_REQUEST_SLUG', + TRAVIS_COMMIT_RANGE: "TRAVIS_COMMIT_A.TRAVIS_COMMIT_B", + TRAVIS_EVENT_TYPE: "TRAVIS_EVENT_TYPE", + TRAVIS_REPO_SLUG: "TRAVIS_REPO_SLUG", + TRAVIS_PULL_REQUEST_SLUG: "TRAVIS_PULL_REQUEST_SLUG", }; const cli = async (nodeOptions: SpawnOptions = {}, args: string[] = []) => - x(bin, args, {nodeOptions}); + x(bin, args, { nodeOptions }); -test('should throw when not on travis ci', async () => { +test("should throw when not on travis ci", async () => { const env = { - CI: 'false', - TRAVIS: 'false', + CI: "false", + TRAVIS: "false", }; - const output = await cli({env}); + const output = await cli({ env }); expect(output.stderr).toContain( - '@commitlint/travis-cli is intended to be used on Travis CI' + "@commitlint/travis-cli is intended to be used on Travis CI", ); }); -test('should throw when on travis ci, but env vars are missing', async () => { +test("should throw when on travis ci, but env vars are missing", async () => { const env = { - TRAVIS: 'true', - CI: 'true', + TRAVIS: "true", + CI: "true", }; - const output = await cli({env}); + const output = await cli({ env }); expect(output.stderr).toContain( - 'TRAVIS_COMMIT, TRAVIS_COMMIT_RANGE, TRAVIS_EVENT_TYPE, TRAVIS_REPO_SLUG, TRAVIS_PULL_REQUEST_SLUG' + "TRAVIS_COMMIT, TRAVIS_COMMIT_RANGE, TRAVIS_EVENT_TYPE, TRAVIS_REPO_SLUG, TRAVIS_PULL_REQUEST_SLUG", ); }); -test('should call git with expected args (test might fail locally)', async () => { +test("should call git with expected args (test might fail locally)", async () => { const cwd = await git.clone( - 'https://github.com/conventional-changelog/commitlint.git', - ['--depth=10'], + "https://github.com/conventional-changelog/commitlint.git", + ["--depth=10"], __dirname, - TRAVIS_COMMITLINT_GIT_BIN + TRAVIS_COMMITLINT_GIT_BIN, ); const result = await cli({ @@ -75,69 +75,69 @@ test('should call git with expected args (test might fail locally)', async () => const [stash, branches, commitlint] = invocations; - expect(stash).toEqual(['git', 'stash', '-k', '-u', '--quiet']); - expect(branches).toEqual(['git', 'stash', 'pop', '--quiet']); - expect(commitlint).toEqual(['commitlint']); + expect(stash).toEqual(["git", "stash", "-k", "-u", "--quiet"]); + expect(branches).toEqual(["git", "stash", "pop", "--quiet"]); + expect(commitlint).toEqual(["commitlint"]); }); -test('should call git with expected args on pull_request (test might fail locally)', async () => { +test("should call git with expected args on pull_request (test might fail locally)", async () => { const cwd = await git.clone( - 'https://github.com/conventional-changelog/commitlint.git', - ['--depth=10'], + "https://github.com/conventional-changelog/commitlint.git", + ["--depth=10"], __dirname, - TRAVIS_COMMITLINT_GIT_BIN + TRAVIS_COMMITLINT_GIT_BIN, ); const result = await cli({ cwd, - env: {...validBaseEnv, TRAVIS_EVENT_TYPE: 'pull_request'}, + env: { ...validBaseEnv, TRAVIS_EVENT_TYPE: "pull_request" }, }); const invocations = getInvocations(result.stdout); expect(invocations.length).toBe(3); const [stash, branches, commitlint] = invocations; - expect(stash).toEqual(['git', 'stash', '-k', '-u', '--quiet']); - expect(branches).toEqual(['git', 'stash', 'pop', '--quiet']); + expect(stash).toEqual(["git", "stash", "-k", "-u", "--quiet"]); + expect(branches).toEqual(["git", "stash", "pop", "--quiet"]); expect(commitlint).toEqual([ - 'commitlint', - '--from', - 'TRAVIS_COMMIT_A', - '--to', - 'TRAVIS_COMMIT_B', + "commitlint", + "--from", + "TRAVIS_COMMIT_A", + "--to", + "TRAVIS_COMMIT_B", ]); }); -test('should call git with extra expected args on pull_request (test might fail locally)', async () => { +test("should call git with extra expected args on pull_request (test might fail locally)", async () => { const cwd = await git.clone( - 'https://github.com/conventional-changelog/commitlint.git', - ['--depth=10'], + "https://github.com/conventional-changelog/commitlint.git", + ["--depth=10"], __dirname, - TRAVIS_COMMITLINT_GIT_BIN + TRAVIS_COMMITLINT_GIT_BIN, ); const result = await cli( { cwd, - env: {...validBaseEnv, TRAVIS_EVENT_TYPE: 'pull_request'}, + env: { ...validBaseEnv, TRAVIS_EVENT_TYPE: "pull_request" }, }, - ['--config', './config/commitlint.config.js'] + ["--config", "./config/commitlint.config.js"], ); const invocations = getInvocations(result.stdout); expect(invocations.length).toBe(3); const [stash, branches, commitlint] = invocations; - expect(stash).toEqual(['git', 'stash', '-k', '-u', '--quiet']); - expect(branches).toEqual(['git', 'stash', 'pop', '--quiet']); + expect(stash).toEqual(["git", "stash", "-k", "-u", "--quiet"]); + expect(branches).toEqual(["git", "stash", "pop", "--quiet"]); expect(commitlint).toEqual([ - 'commitlint', - '--from', - 'TRAVIS_COMMIT_A', - '--to', - 'TRAVIS_COMMIT_B', - '--config', - './config/commitlint.config.js', + "commitlint", + "--from", + "TRAVIS_COMMIT_A", + "--to", + "TRAVIS_COMMIT_B", + "--config", + "./config/commitlint.config.js", ]); }); @@ -146,12 +146,12 @@ function getInvocations(stdout: string): string[][] { const raw = Array.isArray(matches) ? matches : []; return raw - .filter((invocation) => invocation !== '\n') + .filter((invocation) => invocation !== "\n") .map((invocation) => invocation - .split(',') + .split(",") .map((fragment) => fragment.trim()) .map((fragment) => fragment.substring(1, fragment.length - 1)) - .filter(Boolean) + .filter(Boolean), ); } diff --git a/@commitlint/travis-cli/src/cli.ts b/@commitlint/travis-cli/src/cli.ts index 943b37203b..ad4c586277 100644 --- a/@commitlint/travis-cli/src/cli.ts +++ b/@commitlint/travis-cli/src/cli.ts @@ -1,29 +1,29 @@ -import {SpawnOptions} from 'node:child_process'; +import { SpawnOptions } from "node:child_process"; -import {createRequire} from 'node:module'; +import { createRequire } from "node:module"; -import {x} from 'tinyexec'; +import { x } from "tinyexec"; const require = createRequire(import.meta.url); // Allow to override used bins for testing purposes -const GIT = process.env.TRAVIS_COMMITLINT_GIT_BIN || 'git'; +const GIT = process.env.TRAVIS_COMMITLINT_GIT_BIN || "git"; const COMMITLINT = - process.env.TRAVIS_COMMITLINT_BIN || require('@commitlint/cli'); + process.env.TRAVIS_COMMITLINT_BIN || require("@commitlint/cli"); const REQUIRED = [ - 'TRAVIS_COMMIT', - 'TRAVIS_COMMIT_RANGE', - 'TRAVIS_EVENT_TYPE', - 'TRAVIS_REPO_SLUG', - 'TRAVIS_PULL_REQUEST_SLUG', + "TRAVIS_COMMIT", + "TRAVIS_COMMIT_RANGE", + "TRAVIS_EVENT_TYPE", + "TRAVIS_REPO_SLUG", + "TRAVIS_PULL_REQUEST_SLUG", ]; -const COMMIT = process.env.TRAVIS_COMMIT || ''; +const COMMIT = process.env.TRAVIS_COMMIT || ""; const REPO_SLUG = process.env.TRAVIS_REPO_SLUG; const PR_SLUG = process.env.TRAVIS_PULL_REQUEST_SLUG || REPO_SLUG; const RANGE = process.env.TRAVIS_COMMIT_RANGE; -const IS_PR = process.env.TRAVIS_EVENT_TYPE === 'pull_request'; +const IS_PR = process.env.TRAVIS_EVENT_TYPE === "pull_request"; main().catch((err) => { console.error(err); @@ -38,9 +38,10 @@ async function main() { // Make base and source available as dedicated remotes await Promise.all([ - () => fetch({name: 'base', url: `https://github.com/${REPO_SLUG}.git`}), + () => fetch({ name: "base", url: `https://github.com/${REPO_SLUG}.git` }), IS_PR - ? () => fetch({name: 'source', url: `https://github.com/${PR_SLUG}.git`}) + ? () => + fetch({ name: "source", url: `https://github.com/${PR_SLUG}.git` }) : () => Promise.resolve(), ]); @@ -51,8 +52,8 @@ async function main() { // Lint all commits in TRAVIS_COMMIT_RANGE if available if (IS_PR && RANGE) { - const [start, end] = RANGE.split('.').filter(Boolean); - await lint(['--from', start, '--to', end, ...args]); + const [start, end] = RANGE.split(".").filter(Boolean); + await lint(["--from", start, "--to", end, ...args]); } else { const input = await log(COMMIT); await lint(args, {}, input); @@ -62,20 +63,20 @@ async function main() { async function git(args: string[], nodeOptions: SpawnOptions = {}) { return x(GIT, args, { nodeOptions: { - stdio: 'inherit', + stdio: "inherit", ...nodeOptions, }, }); } -async function fetch({name, url}: {name: string; url: string}) { - await git(['remote', 'add', name, url]); - await git(['fetch', name, '--quiet']); +async function fetch({ name, url }: { name: string; url: string }) { + await git(["remote", "add", name, url]); + await git(["fetch", name, "--quiet"]); } async function isClean() { - const result = await git(['status', '--porcelain'], { - stdio: ['pipe', 'pipe', 'pipe'], + const result = await git(["status", "--porcelain"], { + stdio: ["pipe", "pipe", "pipe"], }); return !(result.stdout && result.stdout.trim()); } @@ -83,11 +84,11 @@ async function isClean() { async function lint( args: string[], nodeOptions: SpawnOptions = {}, - input: string = '' + input: string = "", ) { const result = x(COMMITLINT, args, { nodeOptions: { - stdio: ['pipe', 'inherit', 'inherit'], + stdio: ["pipe", "inherit", "inherit"], ...nodeOptions, }, }); @@ -99,8 +100,8 @@ async function lint( } async function log(hash: string) { - const result = await git(['log', '-n', '1', '--pretty=format:%B', hash], { - stdio: 'pipe', + const result = await git(["log", "-n", "1", "--pretty=format:%B", hash], { + stdio: "pipe", }); return result.stdout; } @@ -109,23 +110,23 @@ async function stash() { if (await isClean()) { return () => Promise.resolve(); } - await git(['stash', '-k', '-u', '--quiet']); - return () => git(['stash', 'pop', '--quiet']); + await git(["stash", "-k", "-u", "--quiet"]); + return () => git(["stash", "pop", "--quiet"]); } function validate() { - if (process.env.CI !== 'true' || process.env.TRAVIS !== 'true') { + if (process.env.CI !== "true" || process.env.TRAVIS !== "true") { throw new Error( - `@commitlint/travis-cli is intended to be used on Travis CI` + `@commitlint/travis-cli is intended to be used on Travis CI`, ); } const missing = REQUIRED.filter((envVar) => !(envVar in process.env)); if (missing.length > 0) { - const stanza = missing.length > 1 ? 'they were not' : 'it was not'; + const stanza = missing.length > 1 ? "they were not" : "it was not"; throw new Error( - `Expected ${missing.join(', ')} to be defined globally, ${stanza}.` + `Expected ${missing.join(", ")} to be defined globally, ${stanza}.`, ); } } diff --git a/@commitlint/travis-cli/tsconfig.json b/@commitlint/travis-cli/tsconfig.json index 2a6d93a0fa..12cd1d4571 100644 --- a/@commitlint/travis-cli/tsconfig.json +++ b/@commitlint/travis-cli/tsconfig.json @@ -7,5 +7,5 @@ }, "include": ["./src"], "exclude": ["./src/**/*.test.ts", "./lib/**/*"], - "references": [{"path": "../cli"}] + "references": [{ "path": "../cli" }] } diff --git a/@commitlint/types/src/ensure.ts b/@commitlint/types/src/ensure.ts index 9d7be804af..309271e0a3 100644 --- a/@commitlint/types/src/ensure.ts +++ b/@commitlint/types/src/ensure.ts @@ -1,13 +1,13 @@ export type TargetCaseType = - | 'camel-case' - | 'kebab-case' - | 'snake-case' - | 'pascal-case' - | 'start-case' - | 'upper-case' - | 'uppercase' - | 'sentence-case' - | 'sentencecase' - | 'lower-case' - | 'lowercase' - | 'lowerCase'; + | "camel-case" + | "kebab-case" + | "snake-case" + | "pascal-case" + | "start-case" + | "upper-case" + | "uppercase" + | "sentence-case" + | "sentencecase" + | "lower-case" + | "lowercase" + | "lowerCase"; diff --git a/@commitlint/types/src/format.ts b/@commitlint/types/src/format.ts index 0ae167ebee..2ae1030d1f 100644 --- a/@commitlint/types/src/format.ts +++ b/@commitlint/types/src/format.ts @@ -1,11 +1,11 @@ -import type {ColorName, ModifierName} from 'chalk'; +import type { ColorName, ModifierName } from "chalk"; -import {QualifiedRules} from './load.js'; -import {RuleConfigSeverity} from './rules.js'; +import { QualifiedRules } from "./load.js"; +import { RuleConfigSeverity } from "./rules.js"; export type Formatter = ( report: FormattableReport, - options: FormatOptions + options: FormatOptions, ) => string; export interface FormattableProblem { diff --git a/@commitlint/types/src/index.ts b/@commitlint/types/src/index.ts index 8014dcdf76..aa363ca5ae 100644 --- a/@commitlint/types/src/index.ts +++ b/@commitlint/types/src/index.ts @@ -1,8 +1,8 @@ -export * from './ensure.js'; -export * from './format.js'; -export * from './is-ignored.js'; -export * from './lint.js'; -export * from './load.js'; -export * from './parse.js'; -export * from './prompt.js'; -export * from './rules.js'; +export * from "./ensure.js"; +export * from "./format.js"; +export * from "./is-ignored.js"; +export * from "./lint.js"; +export * from "./load.js"; +export * from "./parse.js"; +export * from "./prompt.js"; +export * from "./rules.js"; diff --git a/@commitlint/types/src/lint.ts b/@commitlint/types/src/lint.ts index 6e473e4b5c..f2cc02b002 100644 --- a/@commitlint/types/src/lint.ts +++ b/@commitlint/types/src/lint.ts @@ -1,7 +1,7 @@ -import type {Options} from 'conventional-commits-parser'; -import {IsIgnoredOptions} from './is-ignored.js'; -import {PluginRecords} from './load.js'; -import {RuleConfigSeverity, RuleConfigTuple} from './rules.js'; +import type { Options } from "conventional-commits-parser"; +import { IsIgnoredOptions } from "./is-ignored.js"; +import { PluginRecords } from "./load.js"; +import { RuleConfigSeverity, RuleConfigTuple } from "./rules.js"; export type LintRuleConfig = Record< string, @@ -12,9 +12,9 @@ export type LintRuleConfig = Record< export interface LintOptions { /** If it should ignore the default commit messages (defaults to `true`) */ - defaultIgnores?: IsIgnoredOptions['defaults']; + defaultIgnores?: IsIgnoredOptions["defaults"]; /** Additional commits to ignore, defined by ignore matchers */ - ignores?: IsIgnoredOptions['ignores']; + ignores?: IsIgnoredOptions["ignores"]; /** The parser configuration to use when linting the commit */ parserOpts?: Options; diff --git a/@commitlint/types/src/load.ts b/@commitlint/types/src/load.ts index 686fa01ebe..e095387fe2 100644 --- a/@commitlint/types/src/load.ts +++ b/@commitlint/types/src/load.ts @@ -1,11 +1,11 @@ -import {UserPromptConfig} from './prompt.js'; +import { UserPromptConfig } from "./prompt.js"; import { AsyncRule, Rule, RuleConfigQuality, RulesConfig, SyncRule, -} from './rules.js'; +} from "./rules.js"; export type PluginRecords = Record<string, Plugin>; diff --git a/@commitlint/types/src/parse.ts b/@commitlint/types/src/parse.ts index 6b7a3a4c07..c162098b5e 100644 --- a/@commitlint/types/src/parse.ts +++ b/@commitlint/types/src/parse.ts @@ -1,3 +1,3 @@ -import type {Commit, Options} from 'conventional-commits-parser'; +import type { Commit, Options } from "conventional-commits-parser"; -export type Parser = (message: string, options: Options) => Omit<Commit, 'raw'>; +export type Parser = (message: string, options: Options) => Omit<Commit, "raw">; diff --git a/@commitlint/types/src/prompt.ts b/@commitlint/types/src/prompt.ts index 25ca44385a..92cada6bde 100644 --- a/@commitlint/types/src/prompt.ts +++ b/@commitlint/types/src/prompt.ts @@ -1,19 +1,19 @@ export type RuleField = - | 'header' - | 'type' - | 'scope' - | 'subject' - | 'body' - | 'footer'; + | "header" + | "type" + | "scope" + | "subject" + | "body" + | "footer"; export type PromptName = | RuleField - | 'isBreaking' - | 'breakingBody' - | 'breaking' - | 'isIssueAffected' - | 'issuesBody' - | 'issues'; + | "isBreaking" + | "breakingBody" + | "breaking" + | "isIssueAffected" + | "issuesBody" + | "issues"; export type PromptConfig = { settings: { @@ -26,7 +26,7 @@ export type PromptConfig = { PromptName, { description?: string; - messages?: {[K: string]: string}; + messages?: { [K: string]: string }; enum?: { [enumName: string]: { description?: string; diff --git a/@commitlint/types/src/rules.ts b/@commitlint/types/src/rules.ts index 930a0d2613..3d8f2bcdb2 100644 --- a/@commitlint/types/src/rules.ts +++ b/@commitlint/types/src/rules.ts @@ -1,6 +1,6 @@ -import type {Commit} from 'conventional-commits-parser'; +import type { Commit } from "conventional-commits-parser"; -import {TargetCaseType} from './ensure.js'; +import { TargetCaseType } from "./ensure.js"; /** * Rules match the input either as successful or failed. @@ -13,23 +13,23 @@ export type RuleOutcome = Readonly<[boolean, string?]>; * Rules receive a parsed commit, condition, and possible additional settings through value. * All rules should provide the most sensible rule condition and value. */ -export type RuleType = 'async' | 'sync' | 'either'; +export type RuleType = "async" | "sync" | "either"; -export type BaseRule<Value = never, Type extends RuleType = 'either'> = ( +export type BaseRule<Value = never, Type extends RuleType = "either"> = ( parsed: Commit, when?: RuleConfigCondition, - value?: Value -) => Type extends 'either' + value?: Value, +) => Type extends "either" ? RuleOutcome | Promise<RuleOutcome> - : Type extends 'async' - ? Promise<RuleOutcome> - : Type extends 'sync' - ? RuleOutcome - : never; + : Type extends "async" + ? Promise<RuleOutcome> + : Type extends "sync" + ? RuleOutcome + : never; -export type Rule<Value = never> = BaseRule<Value, 'either'>; -export type AsyncRule<Value = never> = BaseRule<Value, 'async'>; -export type SyncRule<Value = never> = BaseRule<Value, 'sync'>; +export type Rule<Value = never> = BaseRule<Value, "either">; +export type AsyncRule<Value = never> = BaseRule<Value, "async">; +export type SyncRule<Value = never> = BaseRule<Value, "sync">; /** * Rules always have a severity. @@ -49,7 +49,7 @@ export enum RuleConfigSeverity { * It can be either "always" (as tested), or "never" (as tested). * For example, `header-full-stop` can be enforced as "always" or "never". */ -export type RuleConfigCondition = 'always' | 'never'; +export type RuleConfigCondition = "always" | "never"; export type RuleConfigTuple<T> = T extends void ? @@ -71,7 +71,7 @@ export type QualifiedRuleConfig<T> = export type RuleConfig< V = RuleConfigQuality.Qualified, - T = void + T = void, > = V extends RuleConfigQuality.Qualified ? RuleConfigTuple<T> : QualifiedRuleConfig<T>; @@ -90,41 +90,41 @@ export type EnumRuleConfig<V = RuleConfigQuality.User> = RuleConfig< >; export type RulesConfig<V = RuleConfigQuality.User> = { - 'body-case': CaseRuleConfig<V>; - 'body-empty': RuleConfig<V>; - 'body-full-stop': RuleConfig<V, string>; - 'body-leading-blank': RuleConfig<V>; - 'body-max-length': LengthRuleConfig<V>; - 'body-max-line-length': LengthRuleConfig<V>; - 'body-min-length': LengthRuleConfig<V>; - 'footer-empty': RuleConfig<V>; - 'footer-leading-blank': RuleConfig<V>; - 'footer-max-length': LengthRuleConfig<V>; - 'footer-max-line-length': LengthRuleConfig<V>; - 'footer-min-length': LengthRuleConfig<V>; - 'header-case': CaseRuleConfig<V>; - 'header-full-stop': RuleConfig<V, string>; - 'header-max-length': LengthRuleConfig<V>; - 'header-min-length': LengthRuleConfig<V>; - 'header-trim': RuleConfig<V>; - 'references-empty': RuleConfig<V>; - 'scope-case': CaseRuleConfig<V>; - 'scope-empty': RuleConfig<V>; - 'scope-enum': EnumRuleConfig<V>; - 'scope-max-length': LengthRuleConfig<V>; - 'scope-min-length': LengthRuleConfig<V>; - 'signed-off-by': RuleConfig<V, string>; - 'subject-case': CaseRuleConfig<V>; - 'subject-empty': RuleConfig<V>; - 'subject-full-stop': RuleConfig<V, string>; - 'subject-max-length': LengthRuleConfig<V>; - 'subject-min-length': LengthRuleConfig<V>; - 'trailer-exists': RuleConfig<V, string>; - 'type-case': CaseRuleConfig<V>; - 'type-empty': RuleConfig<V>; - 'type-enum': EnumRuleConfig<V>; - 'type-max-length': LengthRuleConfig<V>; - 'type-min-length': LengthRuleConfig<V>; + "body-case": CaseRuleConfig<V>; + "body-empty": RuleConfig<V>; + "body-full-stop": RuleConfig<V, string>; + "body-leading-blank": RuleConfig<V>; + "body-max-length": LengthRuleConfig<V>; + "body-max-line-length": LengthRuleConfig<V>; + "body-min-length": LengthRuleConfig<V>; + "footer-empty": RuleConfig<V>; + "footer-leading-blank": RuleConfig<V>; + "footer-max-length": LengthRuleConfig<V>; + "footer-max-line-length": LengthRuleConfig<V>; + "footer-min-length": LengthRuleConfig<V>; + "header-case": CaseRuleConfig<V>; + "header-full-stop": RuleConfig<V, string>; + "header-max-length": LengthRuleConfig<V>; + "header-min-length": LengthRuleConfig<V>; + "header-trim": RuleConfig<V>; + "references-empty": RuleConfig<V>; + "scope-case": CaseRuleConfig<V>; + "scope-empty": RuleConfig<V>; + "scope-enum": EnumRuleConfig<V>; + "scope-max-length": LengthRuleConfig<V>; + "scope-min-length": LengthRuleConfig<V>; + "signed-off-by": RuleConfig<V, string>; + "subject-case": CaseRuleConfig<V>; + "subject-empty": RuleConfig<V>; + "subject-full-stop": RuleConfig<V, string>; + "subject-max-length": LengthRuleConfig<V>; + "subject-min-length": LengthRuleConfig<V>; + "trailer-exists": RuleConfig<V, string>; + "type-case": CaseRuleConfig<V>; + "type-empty": RuleConfig<V>; + "type-enum": EnumRuleConfig<V>; + "type-max-length": LengthRuleConfig<V>; + "type-min-length": LengthRuleConfig<V>; // Plugins may add their custom rules [key: string]: AnyRuleConfig<V>; }; diff --git a/@packages/test-environment/src/test-environment.ts b/@packages/test-environment/src/test-environment.ts index be67cd56ff..448bf7f73e 100644 --- a/@packages/test-environment/src/test-environment.ts +++ b/@packages/test-environment/src/test-environment.ts @@ -1,14 +1,14 @@ // https://github.com/raszi/node-tmp/issues/229 -import type {Environment} from 'vitest'; -import {builtinEnvironments} from 'vitest/environments'; -import tmp from 'tmp'; +import type { Environment } from "vitest"; +import { builtinEnvironments } from "vitest/environments"; +import tmp from "tmp"; const nodeEnv = builtinEnvironments.node; const env: Environment = { ...nodeEnv, - name: 'commitlint', + name: "commitlint", async setup(global: object, options: Record<string, unknown>) { const setupEnv = await nodeEnv.setup(global, options); return { diff --git a/@packages/test/src/fix.ts b/@packages/test/src/fix.ts index 1227833968..eca5fd03f8 100644 --- a/@packages/test/src/fix.ts +++ b/@packages/test/src/fix.ts @@ -1,8 +1,8 @@ -import path from 'node:path'; +import path from "node:path"; -import fs from 'fs-extra'; -import {packageDirectory as pkgDir} from 'pkg-dir'; -import tmp from 'tmp'; +import fs from "fs-extra"; +import { packageDirectory as pkgDir } from "pkg-dir"; +import tmp from "tmp"; export async function bootstrap(fixture?: string, directory?: string) { const tmpDir = tmp.dirSync({ @@ -10,8 +10,8 @@ export async function bootstrap(fixture?: string, directory?: string) { unsafeCleanup: true, }); - if (typeof fixture !== 'undefined') { - const packageDir = await pkgDir({cwd: directory}); + if (typeof fixture !== "undefined") { + const packageDir = await pkgDir({ cwd: directory }); if (!packageDir) { throw new Error(`ENOENT, no such file or directory '${packageDir}'`); } diff --git a/@packages/test/src/git.ts b/@packages/test/src/git.ts index e58c7f46ed..04ea365aae 100644 --- a/@packages/test/src/git.ts +++ b/@packages/test/src/git.ts @@ -1,6 +1,6 @@ -import {x} from 'tinyexec'; +import { x } from "tinyexec"; -import * as fix from './fix.js'; +import * as fix from "./fix.js"; export async function bootstrap(fixture?: string, directory?: string) { const cwd = await fix.bootstrap(fixture, directory); @@ -13,35 +13,37 @@ export async function clone( source: string, args: string[], directory?: string, - gitCommand = 'git' + gitCommand = "git", ) { const cwd = await fix.bootstrap(undefined, directory); - await x(gitCommand, ['clone', ...args, source, cwd]); + await x(gitCommand, ["clone", ...args, source, cwd]); await setup(cwd, gitCommand); return cwd; } export async function init(cwd: string) { - await x('git', ['init', cwd]); + await x("git", ["init", cwd]); await setup(cwd); return cwd; } -async function setup(cwd: string, gitCommand = 'git') { +async function setup(cwd: string, gitCommand = "git") { try { - await x(gitCommand, ['config', 'user.name', 'ava'], {nodeOptions: {cwd}}); - await x(gitCommand, ['config', 'user.email', 'test@example.com'], { - nodeOptions: {cwd}, + await x(gitCommand, ["config", "user.name", "ava"], { + nodeOptions: { cwd }, }); - await x(gitCommand, ['config', 'commit.gpgsign', 'false'], { - nodeOptions: {cwd}, + await x(gitCommand, ["config", "user.email", "test@example.com"], { + nodeOptions: { cwd }, + }); + await x(gitCommand, ["config", "commit.gpgsign", "false"], { + nodeOptions: { cwd }, }); } catch (err: any) { - if (typeof err === 'object' && typeof err.message === 'object') { + if (typeof err === "object" && typeof err.message === "object") { console.warn(`git config in ${cwd} failed`, err.message); } else { - console.error('An unknown error occurred setting up the git environment'); + console.error("An unknown error occurred setting up the git environment"); } } } diff --git a/@packages/test/src/index.test.ts b/@packages/test/src/index.test.ts index 9b11836021..0202eeeeb5 100644 --- a/@packages/test/src/index.test.ts +++ b/@packages/test/src/index.test.ts @@ -1,34 +1,34 @@ -import {test, expect} from 'vitest'; -import os from 'node:os'; -import path from 'node:path'; -import fs from 'fs-extra'; +import { test, expect } from "vitest"; +import os from "node:os"; +import path from "node:path"; +import fs from "fs-extra"; -import * as u from './index.js'; +import * as u from "./index.js"; -test('exports a git namespace', () => { - expect(typeof u.git).toBe('object'); +test("exports a git namespace", () => { + expect(typeof u.git).toBe("object"); }); -test('git namespace has bootstrap', () => { - expect(typeof u.git.bootstrap).toBe('function'); +test("git namespace has bootstrap", () => { + expect(typeof u.git.bootstrap).toBe("function"); }); -test('git namespace has clone', () => { - expect(typeof u.git.clone).toBe('function'); +test("git namespace has clone", () => { + expect(typeof u.git.clone).toBe("function"); }); -test('expect to create tmp directory', async () => { +test("expect to create tmp directory", async () => { const directory = await u.git.bootstrap(); - expect(directory).toContain('tmp-'); + expect(directory).toContain("tmp-"); expect(directory).toContain(os.tmpdir()); }); -test('expect to create tmp from directory from src', async () => { - const directory = await u.git.bootstrap('.github'); - expect(directory).toContain('tmp-'); +test("expect to create tmp from directory from src", async () => { + const directory = await u.git.bootstrap(".github"); + expect(directory).toContain("tmp-"); expect(directory).toContain(os.tmpdir()); expect(fs.existsSync(directory)).toBeTruthy(); - const indexFile = path.join(directory, 'PULL_REQUEST_TEMPLATE.md'); + const indexFile = path.join(directory, "PULL_REQUEST_TEMPLATE.md"); expect(fs.existsSync(indexFile)).toBeTruthy(); }); diff --git a/@packages/test/src/index.ts b/@packages/test/src/index.ts index b488ca1393..fb1c9a26a6 100644 --- a/@packages/test/src/index.ts +++ b/@packages/test/src/index.ts @@ -1,5 +1,5 @@ -import * as fix from './fix.js'; -import * as git from './git.js'; -import * as npm from './npm.js'; +import * as fix from "./fix.js"; +import * as git from "./git.js"; +import * as npm from "./npm.js"; -export {fix, git, npm}; +export { fix, git, npm }; diff --git a/@packages/test/src/npm.ts b/@packages/test/src/npm.ts index f017ac32f3..2c31e5520b 100644 --- a/@packages/test/src/npm.ts +++ b/@packages/test/src/npm.ts @@ -1,19 +1,18 @@ -import path from 'node:path'; +import path from "node:path"; -import fs from 'fs-extra'; -import resolvePkg from 'resolve-pkg'; +import fs from "fs-extra"; +import resolvePkg from "resolve-pkg"; -import * as git from './git.js'; +import * as git from "./git.js"; export async function installModules(cwd: string) { - const manifestPath = path.join(cwd, 'package.json'); - const targetModulesPath = path.join(cwd, 'node_modules'); + const manifestPath = path.join(cwd, "package.json"); + const targetModulesPath = path.join(cwd, "node_modules"); if (await fs.pathExists(manifestPath)) { - const {dependencies = {}, devDependencies = {}} = await fs.readJson( - manifestPath - ); - const deps = Object.keys({...dependencies, ...devDependencies}); + const { dependencies = {}, devDependencies = {} } = + await fs.readJson(manifestPath); + const deps = Object.keys({ ...dependencies, ...devDependencies }); await Promise.all( deps.map(async (dependency: any) => { const sourcePath = resolvePkg(dependency); @@ -22,7 +21,7 @@ export async function installModules(cwd: string) { throw new Error(`Could not resolve dependency ${dependency}`); } - const sourceModulesPath = findParentPath(sourcePath, 'node_modules'); + const sourceModulesPath = findParentPath(sourcePath, "node_modules"); if (!sourceModulesPath) { throw new Error(`Could not determine node_modules for ${sourcePath}`); @@ -31,9 +30,9 @@ export async function installModules(cwd: string) { const relativePath = path.relative(sourceModulesPath, sourcePath); const targetPath = path.join(targetModulesPath, relativePath); - await fs.mkdirp(path.join(targetPath, '..')); + await fs.mkdirp(path.join(targetPath, "..")); await fs.symlink(sourcePath, targetPath); - }) + }), ); } } @@ -46,23 +45,23 @@ export async function bootstrap(fixture: string, directory?: string) { function findParentPath( parentPath: string, - dirname: string + dirname: string, ): string | undefined { const rawFragments = parentPath.split(path.sep); - const {matched, fragments} = rawFragments.reduceRight( - ({fragments, matched}, item) => { + const { matched, fragments } = rawFragments.reduceRight( + ({ fragments, matched }, item) => { if (item === dirname && !matched) { - return {fragments, matched: true}; + return { fragments, matched: true }; } if (!matched && fragments.length > 0) { fragments.pop(); } - return {fragments, matched}; + return { fragments, matched }; }, - {fragments: rawFragments, matched: false} + { fragments: rawFragments, matched: false }, ); return matched ? fragments.join(path.sep) : undefined; diff --git a/@packages/utils/dep-check.js b/@packages/utils/dep-check.js index 833a19ac13..8f96322333 100755 --- a/@packages/utils/dep-check.js +++ b/@packages/utils/dep-check.js @@ -1,26 +1,26 @@ #!/usr/bin/env node -import path from 'node:path'; -import {x} from 'tinyexec'; +import path from "node:path"; +import { x } from "tinyexec"; const cwd = process.cwd(); function main() { return Promise.all([ - check(['--missing', '--no-dev', '.']), - check(['--extra', '--no-dev', '.']), + check(["--missing", "--no-dev", "."]), + check(["--extra", "--no-dev", "."]), ]) - .then((tasks) => [null, tasks.map((t) => t.stdout).join('\n')]) + .then((tasks) => [null, tasks.map((t) => t.stdout).join("\n")]) .catch((err) => [err]); } function check(args) { - return x('dependency-check', args, {nodeOptions: {cwd}}); + return x("dependency-check", args, { nodeOptions: { cwd } }); } main().then((args) => { const err = args[0]; const out = args[1]; - console.log(`Checking dependencies ${path.join(cwd, 'package.json')}`); + console.log(`Checking dependencies ${path.join(cwd, "package.json")}`); if (err) { console.error(err.stderr); process.exit(err.exitCode); diff --git a/@packages/utils/pkg-check.js b/@packages/utils/pkg-check.js index 893bdd07cb..4f360df846 100755 --- a/@packages/utils/pkg-check.js +++ b/@packages/utils/pkg-check.js @@ -1,14 +1,14 @@ #!/usr/bin/env node -import path from 'node:path'; -import fs from 'node:fs'; +import path from "node:path"; +import fs from "node:fs"; -import readPkg from 'read-pkg'; -import requireFromString from 'require-from-string'; -import tar from 'tar-fs'; -import {x} from 'tinyexec'; -import tmp from 'tmp'; -import yargs from 'yargs'; -import zlib from 'node:zlib'; +import readPkg from "read-pkg"; +import requireFromString from "require-from-string"; +import tar from "tar-fs"; +import { x } from "tinyexec"; +import tmp from "tmp"; +import yargs from "yargs"; +import zlib from "node:zlib"; tmp.setGracefulCleanup(); @@ -32,16 +32,16 @@ Module._load = function(path, parent) { function main(flags) { if (!Proxy) { console - .warn('Skipping pkg-check, detected missing Proxy support') + .warn("Skipping pkg-check, detected missing Proxy support") .process.exit(0); } const cwd = flags.cwd || process.cwd(); const skipImport = - typeof flags.skipImport === 'boolean' ? flags.skipImport : false; + typeof flags.skipImport === "boolean" ? flags.skipImport : false; - return readPkg({cwd}).then((pkg) => { - return getTarballFiles(cwd, {write: !skipImport}).then((tarball) => { + return readPkg({ cwd }).then((pkg) => { + return getTarballFiles(cwd, { write: !skipImport }).then((tarball) => { return getPackageFiles(cwd).then((pkgFiles) => { let problems = []; @@ -50,16 +50,16 @@ function main(flags) { pkgFiles.bin .filter((binFile) => tarball.files.indexOf(binFile) === -1) .map((binFile) => ({ - type: 'bin', + type: "bin", file: binFile, message: `Required bin file ${binFile} not found for ${pkg.name}`, - })) + })), ); } if (!flags.skipMain && tarball.files.indexOf(pkgFiles.main) === -1) { problems.push({ - type: 'main', + type: "main", file: pkgFiles.main, message: `Required main file ${pkgFiles.main} not found for ${pkg.name}`, }); @@ -67,11 +67,11 @@ function main(flags) { if (!flags.skipImport && !flags.skipMain) { const importable = fileImportable( - path.join(tarball.dirname, pkgFiles.main) + path.join(tarball.dirname, pkgFiles.main), ); if (!importable[1]) { problems.push({ - type: 'import', + type: "import", file: pkgFiles.main, message: `Error while importing ${pkgFiles.main}: ${importable[0].message}`, }); @@ -93,37 +93,37 @@ main( yargs .options({ cwd: { - description: 'directory to execute in', - type: 'string', + description: "directory to execute in", + type: "string", }, skipMain: { default: false, - type: 'boolean', - description: 'Skip main checks', + type: "boolean", + description: "Skip main checks", }, skipBin: { default: false, - type: 'boolean', - description: 'Skip bin checks', + type: "boolean", + description: "Skip bin checks", }, skipImport: { default: false, - type: 'boolean', - description: 'Skip import smoke test', + type: "boolean", + description: "Skip import smoke test", }, }) - .scriptName('pkg-check') - .usage('pkg-check\n') - .usage('Check if a package creates valid tarballs') - .example('$0', '') + .scriptName("pkg-check") + .usage("pkg-check\n") + .usage("Check if a package creates valid tarballs") + .example("$0", "") .help() .version() - .strict().argv + .strict().argv, ) .then((report) => { if (report.problems.length > 0) { console.log( - `Found ${report.problems.length} problems while checking tarball for ${report.pkg.name}:` + `Found ${report.problems.length} problems while checking tarball for ${report.pkg.name}:`, ); report.problems.forEach((problem) => { @@ -145,16 +145,16 @@ async function getTarballFiles(source, options) { unsafeCleanup: true, }); const cwd = tmpDir.name; - const tarball = path.join(cwd, 'test-archive.tgz'); - await x('yarn', ['pack', '--filename', tarball], { - nodeOptions: {cwd: source}, + const tarball = path.join(cwd, "test-archive.tgz"); + await x("yarn", ["pack", "--filename", tarball], { + nodeOptions: { cwd: source }, }); return getArchiveFiles(tarball, options); } function getArchiveFiles(filePath, options) { - const write = typeof options.write === 'boolean' ? options.write : true; + const write = typeof options.write === "boolean" ? options.write : true; return new Promise((resolve, reject) => { const files = []; @@ -163,17 +163,17 @@ function getArchiveFiles(filePath, options) { .pipe( tar.extract(path.dirname(filePath), { ignore(_, header) { - files.push(path.relative('package', header.name)); + files.push(path.relative("package", header.name)); return !write; }, - }) + }), ) - .once('error', (err) => reject(err)) - .once('finish', () => + .once("error", (err) => reject(err)) + .once("finish", () => resolve({ - dirname: path.join(path.dirname(filePath), 'package'), + dirname: path.join(path.dirname(filePath), "package"), files: files, - }) + }), ); }); } @@ -181,7 +181,7 @@ function getArchiveFiles(filePath, options) { function getPackageFiles(source) { return readPkg(source).then((pkg) => { return { - main: normalizeMainPath(pkg.main || './index.js'), + main: normalizeMainPath(pkg.main || "./index.js"), bin: getPkgBinFiles(pkg.bin), }; }); @@ -200,11 +200,11 @@ function getPkgBinFiles(bin) { return []; } - if (typeof bin === 'string') { + if (typeof bin === "string") { return [path.normalize(bin)]; } - if (typeof bin === 'object') { + if (typeof bin === "object") { return Object.values(bin).map((b) => path.normalize(b)); } } @@ -216,7 +216,7 @@ function fileImportable(file) { ${PRELUDE} ${fs.readFileSync(file)} `, - file + file, ); return [null, true]; } catch (err) { diff --git a/docker-compose.yml b/docker-compose.yml index 401320c97e..5776609a51 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -1,4 +1,4 @@ -version: '3' +version: "3" services: commitlint: build: @@ -6,7 +6,7 @@ services: dockerfile: Dockerfile.dev image: marionebl/commitlint-cubicle ports: - - '8443:8443' + - "8443:8443" environment: - SSH_AUTH_SOCK=/.ssh-agent/socket - SSH_AUTH_PROXY_SOCK=/.ssh-agent/proxy-socket diff --git a/docs/.vitepress/config.ts b/docs/.vitepress/config.ts index 3bafab5417..55de22edfd 100644 --- a/docs/.vitepress/config.ts +++ b/docs/.vitepress/config.ts @@ -1,98 +1,100 @@ -import {defineConfig} from 'vitepress'; -import {tabsMarkdownPlugin} from 'vitepress-plugin-tabs'; +import { defineConfig } from "vitepress"; +import { tabsMarkdownPlugin } from "vitepress-plugin-tabs"; // https://vitepress.dev/reference/site-config export default defineConfig({ - title: 'commitlint', - description: 'Lint commit messages', + title: "commitlint", + description: "Lint commit messages", - head: [['link', {rel: 'icon', type: 'image/png', href: '/assets/icon.png'}]], + head: [ + ["link", { rel: "icon", type: "image/png", href: "/assets/icon.png" }], + ], themeConfig: { // https://vitepress.dev/reference/default-theme-config editLink: { pattern: - 'https://github.com/conventional-changelog/commitlint/edit/master/docs/:path', + "https://github.com/conventional-changelog/commitlint/edit/master/docs/:path", }, - logo: '/assets/icon.png', + logo: "/assets/icon.png", nav: [ - {text: 'Home', link: '/'}, - {text: 'Guides', link: '/guides/getting-started'}, - {text: 'Reference', link: '/reference/configuration'}, + { text: "Home", link: "/" }, + { text: "Guides", link: "/guides/getting-started" }, + { text: "Reference", link: "/reference/configuration" }, ], sidebar: [ { - text: 'Guides', - base: '/guides', + text: "Guides", + base: "/guides", items: [ - {text: 'Getting started', link: '/getting-started'}, - {text: 'Local setup', link: '/local-setup'}, - {text: 'CI setup', link: '/ci-setup'}, - {text: 'Use prompt', link: '/use-prompt'}, + { text: "Getting started", link: "/getting-started" }, + { text: "Local setup", link: "/local-setup" }, + { text: "CI setup", link: "/ci-setup" }, + { text: "Use prompt", link: "/use-prompt" }, ], }, { - text: 'Reference', - base: '/reference', + text: "Reference", + base: "/reference", items: [ - {text: 'CLI', link: '/cli'}, - {text: 'Configuration', link: '/configuration'}, - {text: 'Rules configuration', link: '/rules-configuration'}, - {text: 'Rules', link: '/rules'}, - {text: 'Plugins', link: '/plugins'}, - {text: 'Prompt', link: '/prompt'}, - {text: 'Examples', link: '/examples'}, - {text: 'Community projects', link: '/community-projects'}, + { text: "CLI", link: "/cli" }, + { text: "Configuration", link: "/configuration" }, + { text: "Rules configuration", link: "/rules-configuration" }, + { text: "Rules", link: "/rules" }, + { text: "Plugins", link: "/plugins" }, + { text: "Prompt", link: "/prompt" }, + { text: "Examples", link: "/examples" }, + { text: "Community projects", link: "/community-projects" }, ], }, { - text: 'API', - base: '/api', + text: "API", + base: "/api", collapsed: true, items: [ - {text: '@commitlint/load', link: '/load'}, - {text: '@commitlint/read', link: '/read'}, - {text: '@commitlint/lint', link: '/lint'}, - {text: '@commitlint/format', link: '/format'}, + { text: "@commitlint/load", link: "/load" }, + { text: "@commitlint/read", link: "/read" }, + { text: "@commitlint/lint", link: "/lint" }, + { text: "@commitlint/format", link: "/format" }, ], }, { - text: 'Concepts', - base: '/concepts', + text: "Concepts", + base: "/concepts", collapsed: true, items: [ - {text: 'Commit-conventions', link: '/commit-conventions'}, - {text: 'Shareable config', link: '/shareable-config'}, + { text: "Commit-conventions", link: "/commit-conventions" }, + { text: "Shareable config", link: "/shareable-config" }, ], }, { - text: 'Support', - base: '/support', + text: "Support", + base: "/support", collapsed: true, items: [ - {text: 'Troubleshooting', link: '/troubleshooting'}, - {text: 'Releases', link: '/releases'}, - {text: 'Upgrade commitlint', link: '/upgrade'}, + { text: "Troubleshooting", link: "/troubleshooting" }, + { text: "Releases", link: "/releases" }, + { text: "Upgrade commitlint", link: "/upgrade" }, ], }, { - text: 'Attributions', - link: '/attributions', + text: "Attributions", + link: "/attributions", }, ], socialLinks: [ { - icon: 'github', - link: 'https://github.com/conventional-changelog/commitlint', + icon: "github", + link: "https://github.com/conventional-changelog/commitlint", }, ], search: { - provider: 'local', + provider: "local", }, }, diff --git a/docs/.vitepress/theme/index.ts b/docs/.vitepress/theme/index.ts index c1b1900e45..afe3923ee8 100644 --- a/docs/.vitepress/theme/index.ts +++ b/docs/.vitepress/theme/index.ts @@ -1,11 +1,11 @@ // .vitepress/theme/index.ts -import type {Theme} from 'vitepress'; -import DefaultTheme from 'vitepress/theme'; -import {enhanceAppWithTabs} from 'vitepress-plugin-tabs/client'; +import type { Theme } from "vitepress"; +import DefaultTheme from "vitepress/theme"; +import { enhanceAppWithTabs } from "vitepress-plugin-tabs/client"; export default { extends: DefaultTheme, - enhanceApp({app}) { + enhanceApp({ app }) { enhanceAppWithTabs(app); }, } satisfies Theme; diff --git a/docs/api/format.md b/docs/api/format.md index b490bb972a..55a8ead843 100644 --- a/docs/api/format.md +++ b/docs/api/format.md @@ -68,7 +68,7 @@ format(report?: Report = {}, options?: formatOptions = {}) => string[]; ## Import ```js -import format from '@commitlint/format'; +import format from "@commitlint/format"; ``` ## Examples @@ -94,20 +94,20 @@ format( warnings: [ { level: 0, - name: 'some-hint', - message: 'This will not show up as it has level 0', + name: "some-hint", + message: "This will not show up as it has level 0", }, { level: 1, - name: 'some-warning', - message: 'This will show up yellow as it has level 1', + name: "some-warning", + message: "This will show up yellow as it has level 1", }, ], errors: [ { level: 2, - name: 'some-error', - message: 'This will show up red as it has level 2', + name: "some-error", + message: "This will show up red as it has level 2", }, ], }, @@ -115,7 +115,7 @@ format( }, { color: false, - } + }, ); /* => [ diff --git a/docs/api/lint.md b/docs/api/lint.md index 3f8b7cb439..dbd676563d 100644 --- a/docs/api/lint.md +++ b/docs/api/lint.md @@ -45,13 +45,13 @@ lint(message: string, rules: {[ruleName: string]: Rule}, opts?: Options) => Prom ### Import ```js -import lint from '@commitlint/lint'; +import lint from "@commitlint/lint"; ``` ### Usage without config ```js -const report = await lint('foo: bar'); +const report = await lint("foo: bar"); console.log(report); // => { valid: true, errors: [], warnings: [] } ``` @@ -59,7 +59,7 @@ console.log(report); ### Usage with type-enum rules and valid message ```js -const report = await lint('foo: bar', {'type-enum': [1, 'always', ['foo']]}); +const report = await lint("foo: bar", { "type-enum": [1, "always", ["foo"]] }); console.log(report); // => { valid: true, errors: [], warnings: [] } ``` @@ -67,7 +67,7 @@ console.log(report); ### Usage with type-enum rules and invalid message ```js -const report = await lint('foo: bar', {'type-enum': [1, 'always', ['bar']]}); +const report = await lint("foo: bar", { "type-enum": [1, "always", ["bar"]] }); console.log(report); /* => { @@ -91,14 +91,14 @@ console.log(report); const opts = { parserOpts: { headerPattern: /^(\w*)-(\w*)/, - headerCorrespondence: ['type', 'scope'], + headerCorrespondence: ["type", "scope"], }, }; const report = await lint( - 'foo-bar', - {'type-enum': [2, 'always', ['foo']]}, - opts + "foo-bar", + { "type-enum": [2, "always", ["foo"]] }, + opts, ); console.log(report); // => { valid: true, errors: [], warnings: [] } @@ -107,18 +107,18 @@ console.log(report); ## Load configuration ```js -import load from '@commitlint/load'; -import lint from '@commitlint/lint'; +import load from "@commitlint/load"; +import lint from "@commitlint/lint"; const CONFIG = { - extends: ['@commitlint/config-conventional'], + extends: ["@commitlint/config-conventional"], }; const opts = await load(CONFIG); const report = await lint( - 'foo: bar', + "foo: bar", opts.rules, - opts.parserPreset ? {parserOpts: opts.parserPreset.parserOpts} : {} + opts.parserPreset ? { parserOpts: opts.parserPreset.parserOpts } : {}, ); console.log(report); /* => @@ -140,14 +140,14 @@ console.log(report); ## Read git history ```js -import lint from '@commitlint/lint'; -import read from '@commitlint/read'; +import lint from "@commitlint/lint"; +import read from "@commitlint/read"; const RULES = { - 'type-enum': [2, 'always', ['foo']], + "type-enum": [2, "always", ["foo"]], }; -const commits = await read({to: 'HEAD', from: 'HEAD~2'}); +const commits = await read({ to: "HEAD", from: "HEAD~2" }); console.info(commits.map((commit) => lint(commit, RULES))); ``` @@ -155,17 +155,17 @@ console.info(commits.map((commit) => lint(commit, RULES))); ## Simplified last-commit checker ```js -import load from '@commitlint/load'; -import read from '@commitlint/read'; -import lint from '@commitlint/lint'; +import load from "@commitlint/load"; +import read from "@commitlint/read"; +import lint from "@commitlint/lint"; -const {rules, parserPreset} = load(); -const [commit] = await read({from: 'HEAD~1'}); +const { rules, parserPreset } = load(); +const [commit] = await read({ from: "HEAD~1" }); const report = await lint( commit, rules, - parserPreset ? {parserOpts: parserPreset.parserOpts} : {} + parserPreset ? { parserOpts: parserPreset.parserOpts } : {}, ); console.log(JSON.stringify(result.valid)); diff --git a/docs/api/load.md b/docs/api/load.md index b8d917233a..87fa67a439 100644 --- a/docs/api/load.md +++ b/docs/api/load.md @@ -127,7 +127,7 @@ load(seed: Seed = {}, options?: LoadOptions = {cwd: process.cwd()}) => Promise<C ## Import ```js -import load from '@commitlint/load'; +import load from "@commitlint/load"; ``` ## Examples @@ -137,7 +137,7 @@ import load from '@commitlint/load'; ```js const config = await load({ rules: { - 'body-leading-blank': [2, 'always'], + "body-leading-blank": [2, "always"], }, }); console.log(config); @@ -147,7 +147,7 @@ console.log(config); ### Reference a file ```js -const config = await load({extends: ['./package']}); +const config = await load({ extends: ["./package"] }); console.log(config); // => { extends: ['./package', './package-b'], rules: {} } ``` @@ -155,7 +155,7 @@ console.log(config); ### Inline `parserPreset` ```js -const config = await load({parserPreset: './parser-preset.js'}); +const config = await load({ parserPreset: "./parser-preset.js" }); console.log(config); /* => { @@ -173,7 +173,10 @@ console.log(config); ### Config file with with current working directory ```js -const config = await load({}, {file: '.commitlintrc.yml', cwd: process.cwd()}); +const config = await load( + {}, + { file: ".commitlintrc.yml", cwd: process.cwd() }, +); console.log(config); /* => { diff --git a/docs/api/read.md b/docs/api/read.md index 6cfaab96e9..1c66452194 100644 --- a/docs/api/read.md +++ b/docs/api/read.md @@ -26,7 +26,7 @@ read(range: Range) => Promise<string[]> ## Import ```js -import read from '@commitlint/read'; +import read from "@commitlint/read"; ``` ## Examples @@ -39,7 +39,7 @@ Consider to have a repository with two commits: ### Using `edit: true` ```js -const result = await read({edit: true}); +const result = await read({ edit: true }); console.info(result); // => ['I did something\n\n'] ``` @@ -47,7 +47,7 @@ console.info(result); ### Read last two commits ```js -const result = await read({from: 'HEAD~2'}); +const result = await read({ from: "HEAD~2" }); console.info(result); // => ['I did something\n\n', 'Initial commit\n\n'] ``` @@ -55,7 +55,7 @@ console.info(result); ### Read commits within a range ```js -const result = await read({from: 'HEAD~2', to: 'HEAD~1'}); +const result = await read({ from: "HEAD~2", to: "HEAD~1" }); console.info(result); // => ['Initial commit\n\n'] ``` @@ -63,7 +63,7 @@ console.info(result); ### Read commit message from git gui file ```js -const result = await read({edit: './git/GITGUI_EDITMESSAGE'}); +const result = await read({ edit: "./git/GITGUI_EDITMESSAGE" }); console.info(result); // => ['I did something via git gui\n\n'] ``` diff --git a/docs/concepts/shareable-config.md b/docs/concepts/shareable-config.md index 95b2689a40..c94748a456 100644 --- a/docs/concepts/shareable-config.md +++ b/docs/concepts/shareable-config.md @@ -10,7 +10,7 @@ an object containing `.rules` as default. To use shared configuration you specif * @type {import('@commitlint/types').UserConfig} */ export default { - extends: ['example'], // => commitlint-config-example + extends: ["example"], // => commitlint-config-example }; ``` @@ -39,7 +39,7 @@ This must always start with a `.` (dot). ```js [commitlint.config.js] export default { - extends: ['./example'], // => ./example.js + extends: ["./example"], // => ./example.js }; ``` @@ -55,7 +55,7 @@ You can provide the full path of the package like: ```js [commitlint.config.js] export default { - extends: ['@commitlint/config-conventional'], // => @commitlint/config-conventional + extends: ["@commitlint/config-conventional"], // => @commitlint/config-conventional }; ``` @@ -70,7 +70,7 @@ Or just the scope/owner of the package. ```js [commitlint.config.js] export default { - extends: ['@coolcompany'], // => @coolcompany/commitlint-config + extends: ["@coolcompany"], // => @coolcompany/commitlint-config }; ``` diff --git a/docs/guides/ci-setup.md b/docs/guides/ci-setup.md index c75cba0ebb..d23519e62e 100644 --- a/docs/guides/ci-setup.md +++ b/docs/guides/ci-setup.md @@ -143,11 +143,11 @@ Setting `GIT_DEPTH: 0` removes this limitation, so `commitlint` can check larger ## GitLab CI with pre-build container ```yaml -stages: ['lint', 'build', 'test'] +stages: ["lint", "build", "test"] lint:commit: image: name: registry.hub.docker.com/commitlint/commitlint:latest - entrypoint: [''] + entrypoint: [""] stage: lint script: # Uncomment the next line if you are extending the @commitlint/config-nx-scopes in your commitlint configuration @@ -206,7 +206,7 @@ steps: - task: NodeTool@0 inputs: - versionSpec: '20.x' + versionSpec: "20.x" checkLatest: true - script: | diff --git a/docs/reference/configuration.md b/docs/reference/configuration.md index f4364fedcd..079a9b20f9 100644 --- a/docs/reference/configuration.md +++ b/docs/reference/configuration.md @@ -43,22 +43,22 @@ const Configuration = { * Resolve and load @commitlint/config-conventional from node_modules. * Referenced packages must be installed */ - extends: ['@commitlint/config-conventional'], + extends: ["@commitlint/config-conventional"], /* * Resolve and load conventional-changelog-atom from node_modules. * Referenced packages must be installed */ - parserPreset: 'conventional-changelog-atom', + parserPreset: "conventional-changelog-atom", /* * Resolve and load @commitlint/format from node_modules. * Referenced package must be installed */ - formatter: '@commitlint/format', + formatter: "@commitlint/format", /* * Any rules defined here will override rules from @commitlint/config-conventional */ rules: { - 'type-enum': [2, 'always', ['foo']], + "type-enum": [2, "always", ["foo"]], }, /* * Array of functions that return true if commitlint should ignore the given message. @@ -72,7 +72,7 @@ const Configuration = { * To see full list, check https://github.com/conventional-changelog/commitlint/blob/master/%40commitlint/is-ignored/src/defaults.ts. * To disable those ignores and run rules always, set `defaultIgnores: false` as shown below. */ - ignores: [(commit) => commit === ''], + ignores: [(commit) => commit === ""], /* * Whether commitlint uses the default ignore rules, see the description above. */ @@ -81,7 +81,7 @@ const Configuration = { * Custom URL to show upon failure */ helpUrl: - 'https://github.com/conventional-changelog/commitlint/#what-is-commitlint', + "https://github.com/conventional-changelog/commitlint/#what-is-commitlint", /* * Custom prompt configs */ @@ -89,7 +89,7 @@ const Configuration = { messages: {}, questions: { type: { - description: 'please input type:', + description: "please input type:", }, }, }, @@ -114,16 +114,16 @@ Relevant types and enums can be imported from `@commitlint/types`. Below you can see main changes from a standard js file: ```ts -import type {UserConfig} from '@commitlint/types'; // [!code focus] -import {RuleConfigSeverity} from '@commitlint/types'; // [!code focus] +import type { UserConfig } from "@commitlint/types"; // [!code focus] +import { RuleConfigSeverity } from "@commitlint/types"; // [!code focus] const Configuration: UserConfig = { // [!code focus] - extends: ['@commitlint/config-conventional'], - parserPreset: 'conventional-changelog-atom', - formatter: '@commitlint/format', + extends: ["@commitlint/config-conventional"], + parserPreset: "conventional-changelog-atom", + formatter: "@commitlint/format", rules: { - 'type-enum': [RuleConfigSeverity.Error, 'always', ['foo']], // [!code focus] + "type-enum": [RuleConfigSeverity.Error, "always", ["foo"]], // [!code focus] }, // ... }; @@ -163,7 +163,7 @@ export default { ```js [commitlint.config.js] export default { - extends: ['./commitlint.base.js', './commitlint.types.js'], + extends: ["./commitlint.base.js", "./commitlint.types.js"], }; ``` @@ -171,7 +171,7 @@ export default { // will be picked up by commitlint.config.js export default { rules: { - 'type-enum': [2, 'always', ['foo']], + "type-enum": [2, "always", ["foo"]], }, }; ``` @@ -179,8 +179,8 @@ export default { ```js [commitlint.base.js] // will be picked up by commitlint.config.js export default { - extends: ['@commitlint/config-conventional'], // extends can be nested - parserPreset: 'conventional-changelog-atom', + extends: ["@commitlint/config-conventional"], // extends can be nested + parserPreset: "conventional-changelog-atom", }; ``` @@ -206,7 +206,7 @@ npm install --save-dev conventional-changelog-atom ```js [commitlint.config.js] export default { - parserPreset: 'conventional-changelog-atom', + parserPreset: "conventional-changelog-atom", }; ``` @@ -216,7 +216,7 @@ export default { ```js [commitlint.config.js] export default { - parserPreset: './parser-preset', + parserPreset: "./parser-preset", }; ``` @@ -224,7 +224,7 @@ export default { export default { parserOpts: { headerPattern: /^(\w*)\((\w*)\)-(\w*)\s(.*)$/, - headerCorrespondence: ['type', 'scope', 'ticket', 'subject'], + headerCorrespondence: ["type", "scope", "ticket", "subject"], }, }; ``` @@ -238,7 +238,7 @@ Use ids resolvable by the node resolve algorithm. ```js export default { - formatter: '@commitlint/format', + formatter: "@commitlint/format", }; ``` diff --git a/docs/reference/plugins.md b/docs/reference/plugins.md index 2233107143..251eeb65c3 100644 --- a/docs/reference/plugins.md +++ b/docs/reference/plugins.md @@ -10,7 +10,7 @@ Plugins can expose additional rules for use in commitlint. To do so, the plugin ```js export default { rules: { - 'dollar-sign': function (parsed, when, value) { + "dollar-sign": function (parsed, when, value) { // rule implementation ... }, }, @@ -54,13 +54,13 @@ In case you want to develop your plugins locally without the need to publish to ```js [commitlint.config.js] export default { rules: { - 'hello-world-rule': [2, 'always'], + "hello-world-rule": [2, "always"], }, plugins: [ { rules: { - 'hello-world-rule': ({subject}) => { - const HELLO_WORLD = 'Hello World'; + "hello-world-rule": ({ subject }) => { + const HELLO_WORLD = "Hello World"; return [ subject.includes(HELLO_WORLD), `Your subject should contain ${HELLO_WORLD} message`, diff --git a/docs/reference/rules-configuration.md b/docs/reference/rules-configuration.md index f991de5f5e..09494a12b9 100644 --- a/docs/reference/rules-configuration.md +++ b/docs/reference/rules-configuration.md @@ -16,7 +16,7 @@ Rule configurations are either of type `array` residing on a key with the rule's export default { // ... rules: { - 'header-max-length': [0, 'always', 72], // [!code focus] + "header-max-length": [0, "always", 72], // [!code focus] }, // ... }; @@ -32,7 +32,7 @@ export default { export default { // ... rules: { - 'header-max-length': () => [0, 'always', 72], // [!code focus] + "header-max-length": () => [0, "always", 72], // [!code focus] }, // ... }; @@ -48,7 +48,7 @@ export default { export default { // ... rules: { - 'header-max-length': async () => [0, 'always', 72], // [!code focus] + "header-max-length": async () => [0, "always", 72], // [!code focus] }, // ... }; diff --git a/docs/reference/rules.md b/docs/reference/rules.md index 18ad59a7b3..8180e753e0 100644 --- a/docs/reference/rules.md +++ b/docs/reference/rules.md @@ -64,14 +64,14 @@ ```js [ - 'lower-case', // default - 'upper-case', // UPPERCASE - 'camel-case', // camelCase - 'kebab-case', // kebab-case - 'pascal-case', // PascalCase - 'sentence-case', // Sentence case - 'snake-case', // snake_case - 'start-case', // Start Case + "lower-case", // default + "upper-case", // UPPERCASE + "camel-case", // camelCase + "kebab-case", // kebab-case + "pascal-case", // PascalCase + "sentence-case", // Sentence case + "snake-case", // snake_case + "start-case", // Start Case ]; ``` @@ -129,14 +129,14 @@ ```js [ - 'lower-case', // default - 'upper-case', // UPPERCASE - 'camel-case', // camelCase - 'kebab-case', // kebab-case - 'pascal-case', // PascalCase - 'sentence-case', // Sentence case - 'snake-case', // snake_case - 'start-case', // Start Case + "lower-case", // default + "upper-case", // UPPERCASE + "camel-case", // camelCase + "kebab-case", // kebab-case + "pascal-case", // PascalCase + "sentence-case", // Sentence case + "snake-case", // snake_case + "start-case", // Start Case ]; ``` @@ -210,14 +210,14 @@ ```js [ - 'lower-case', // default - 'upper-case', // UPPERCASE - 'camel-case', // camelCase - 'kebab-case', // kebab-case - 'pascal-case', // PascalCase - 'sentence-case', // Sentence case - 'snake-case', // snake_case - 'start-case', // Start Case + "lower-case", // default + "upper-case", // UPPERCASE + "camel-case", // camelCase + "kebab-case", // kebab-case + "pascal-case", // PascalCase + "sentence-case", // Sentence case + "snake-case", // snake_case + "start-case", // Start Case ]; ``` @@ -253,21 +253,21 @@ Infinity - **value** ```js -['sentence-case', 'start-case', 'pascal-case', 'upper-case']; +["sentence-case", "start-case", "pascal-case", "upper-case"]; ``` - **possible values** ```js [ - 'lower-case', // lower case - 'upper-case', // UPPERCASE - 'camel-case', // camelCase - 'kebab-case', // kebab-case - 'pascal-case', // PascalCase - 'sentence-case', // Sentence case - 'snake-case', // snake_case - 'start-case', // Start Case + "lower-case", // lower case + "upper-case", // UPPERCASE + "camel-case", // camelCase + "kebab-case", // kebab-case + "pascal-case", // PascalCase + "sentence-case", // Sentence case + "snake-case", // snake_case + "start-case", // Start Case ]; ``` @@ -319,17 +319,17 @@ Infinity ```js [ - 'build', - 'chore', - 'ci', - 'docs', - 'feat', - 'fix', - 'perf', - 'refactor', - 'revert', - 'style', - 'test', + "build", + "chore", + "ci", + "docs", + "feat", + "fix", + "perf", + "refactor", + "revert", + "style", + "test", ]; ``` @@ -347,14 +347,14 @@ Infinity ```js [ - 'lower-case', // default - 'upper-case', // UPPERCASE - 'camel-case', // camelCase - 'kebab-case', // kebab-case - 'pascal-case', // PascalCase - 'sentence-case', // Sentence case - 'snake-case', // snake_case - 'start-case', // Start Case + "lower-case", // default + "upper-case", // UPPERCASE + "camel-case", // camelCase + "kebab-case", // kebab-case + "pascal-case", // PascalCase + "sentence-case", // Sentence case + "snake-case", // snake_case + "start-case", // Start Case ]; ``` diff --git a/docs/support/upgrade.md b/docs/support/upgrade.md index ad455b5b79..ec54313e83 100644 --- a/docs/support/upgrade.md +++ b/docs/support/upgrade.md @@ -62,10 +62,10 @@ npm install --save-dev husky ```js module.exports = { - extends: ['@commitlint/config-conventional'], + extends: ["@commitlint/config-conventional"], rules: { // Place your rules here - 'scope-enum': [2, 'always', ['a', 'b']], // error if scope is given but not in provided list + "scope-enum": [2, "always", ["a", "b"]], // error if scope is given but not in provided list }, }; ``` diff --git a/package.json b/package.json index e219152bfa..b5f86419b5 100644 --- a/package.json +++ b/package.json @@ -18,7 +18,7 @@ "lint": "eslint", "lint-fix": "eslint --fix", "format": "prettier **/*.{ts,js,json,yml,md} --check", - "format-fix": "prettier **/*.{ts,js,json,yml,md} --write", + "format-fix": "prettier \"**/*.{ts,js,json,yml,md}\" --write", "publish": "lerna publish --conventional-commits", "reinstall": "yarn clean && yarn install", "start": "yarn watch", @@ -31,10 +31,6 @@ "@commitlint/config-workspace-scopes" ] }, - "prettier": { - "singleQuote": true, - "bracketSpacing": false - }, "lint-staged": { "*.{ts,js,json,yml,md}": [ "prettier --write" @@ -102,7 +98,7 @@ "husky": "^9.1.5", "lerna": "^8.2.0", "lint-staged": "15.4.3", - "prettier": "^2.8.8", + "prettier": "^3.5.3", "typescript": "^5.2.2", "vitepress": "^1.3.4", "vitepress-plugin-tabs": "^0.6.0", diff --git a/tsconfig.json b/tsconfig.json index b8dc904d8d..90481ab49f 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -7,27 +7,27 @@ "noEmit": true }, "references": [ - {"path": "@packages/test-environment"}, - {"path": "@packages/test"}, - {"path": "@commitlint/config-validator"}, - {"path": "@commitlint/ensure"}, - {"path": "@commitlint/execute-rule"}, - {"path": "@commitlint/format"}, - {"path": "@commitlint/is-ignored"}, - {"path": "@commitlint/load"}, - {"path": "@commitlint/message"}, - {"path": "@commitlint/parse"}, - {"path": "@commitlint/resolve-extends"}, - {"path": "@commitlint/to-lines"}, - {"path": "@commitlint/top-level"}, - {"path": "@commitlint/read"}, - {"path": "@commitlint/rules"}, - {"path": "@commitlint/lint"}, - {"path": "@commitlint/core"}, - {"path": "@commitlint/cli"}, - {"path": "@commitlint/travis-cli"}, - {"path": "@commitlint/prompt"}, - {"path": "@commitlint/cz-commitlint"}, - {"path": "@commitlint/config-conventional"} + { "path": "@packages/test-environment" }, + { "path": "@packages/test" }, + { "path": "@commitlint/config-validator" }, + { "path": "@commitlint/ensure" }, + { "path": "@commitlint/execute-rule" }, + { "path": "@commitlint/format" }, + { "path": "@commitlint/is-ignored" }, + { "path": "@commitlint/load" }, + { "path": "@commitlint/message" }, + { "path": "@commitlint/parse" }, + { "path": "@commitlint/resolve-extends" }, + { "path": "@commitlint/to-lines" }, + { "path": "@commitlint/top-level" }, + { "path": "@commitlint/read" }, + { "path": "@commitlint/rules" }, + { "path": "@commitlint/lint" }, + { "path": "@commitlint/core" }, + { "path": "@commitlint/cli" }, + { "path": "@commitlint/travis-cli" }, + { "path": "@commitlint/prompt" }, + { "path": "@commitlint/cz-commitlint" }, + { "path": "@commitlint/config-conventional" } ] } diff --git a/vitest.config.ts b/vitest.config.ts index c1b94cdba0..cd76172eba 100644 --- a/vitest.config.ts +++ b/vitest.config.ts @@ -1,12 +1,12 @@ -import {defineConfig} from 'vitest/config'; +import { defineConfig } from "vitest/config"; export default defineConfig({ test: { - exclude: ['**/node_modules/**', '**/lib/*.test.js'], - environment: 'commitlint', + exclude: ["**/node_modules/**", "**/lib/*.test.js"], + environment: "commitlint", coverage: { - provider: 'istanbul', - include: ['**/@commitlint/*/src/**'], + provider: "istanbul", + include: ["**/@commitlint/*/src/**"], }, }, }); diff --git a/yarn.lock b/yarn.lock index 348ac146bc..40f6abea12 100644 --- a/yarn.lock +++ b/yarn.lock @@ -6797,10 +6797,10 @@ prelude-ls@^1.2.1: resolved "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz#debc6489d7a6e6b0e7611888cec880337d316396" integrity sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g== -prettier@^2.8.8: - version "2.8.8" - resolved "https://registry.npmjs.org/prettier/-/prettier-2.8.8.tgz#e8c5d7e98a4305ffe3de2e1fc4aca1a71c28b1da" - integrity sha512-tdN8qQGvNjw4CHbY+XXk0JgCXn9QiF21a55rBe5LJAU+kDyC4WQn4+awm2Xfk2lQMk5fKup9XgzTZtGkjBdP9Q== +prettier@^3.5.3: + version "3.5.3" + resolved "https://registry.npmjs.org/prettier/-/prettier-3.5.3.tgz#4fc2ce0d657e7a02e602549f053b239cb7dfe1b5" + integrity sha512-QQtaxnoDJeAkDvDKWCLiwIXkTgRhwYDEQCghU9Z6q03iyek/rxRh/2lC3HB7P8sWT2xC/y5JDctPLBIGzHKbhw== pretty-format@^29.7.0: version "29.7.0"