Skip to content

Commit 8d62811

Browse files
committed
feat(core): add kebab-case, camelCase, PascalCase options
1 parent e6ef072 commit 8d62811

File tree

4 files changed

+143
-5
lines changed

4 files changed

+143
-5
lines changed
+20-3
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,28 @@
1+
import {camelCase, kebabCase, snakeCase, startCase} from 'lodash';
2+
13
export default (raw = '', target = 'lowercase') => {
2-
const normalized = String(raw);
4+
const input = String(raw);
35

6+
let normalized;
47
switch (target) {
8+
case 'camelcase':
9+
normalized = camelCase(input);
10+
break;
11+
case 'kebabcase':
12+
normalized = kebabCase(input);
13+
break;
14+
case 'snakecase':
15+
normalized = snakeCase(input);
16+
break;
17+
case 'startcase':
18+
normalized = startCase(input);
19+
break;
520
case 'uppercase':
6-
return normalized.toUpperCase() === normalized;
21+
normalized = input.toUpperCase();
22+
break;
723
case 'lowercase':
824
default:
9-
return normalized.toLowerCase() === normalized;
25+
normalized = input.toLowerCase();
1026
}
27+
return normalized === input;
1128
};

@commitlint/core/src/rules/scope-case.test.js

+84-2
Original file line numberDiff line numberDiff line change
@@ -6,14 +6,24 @@ const messages = {
66
empty: 'chore: subject',
77
lowercase: 'chore(scope): subject',
88
mixedcase: 'chore(sCoPe): subject',
9-
uppercase: 'chore(SCOPE): subject'
9+
uppercase: 'chore(SCOPE): subject',
10+
camelcase: 'chore(myScope): subject',
11+
kebabcase: 'chore(my-scope): subject',
12+
pascalcase: 'chore(MyScope): subject',
13+
snakecase: 'chore(my_scope): subject',
14+
startcase: 'chore(My Scope): subject'
1015
};
1116

1217
const parsed = {
1318
empty: parse(messages.empty),
1419
lowercase: parse(messages.lowercase),
1520
mixedcase: parse(messages.mixedcase),
16-
uppercase: parse(messages.uppercase)
21+
uppercase: parse(messages.uppercase),
22+
camelcase: parse(messages.camelcase),
23+
kebabcase: parse(messages.kebabcase),
24+
pascalcase: parse(messages.pascalcase),
25+
snakecase: parse(messages.snakecase),
26+
startcase: parse(messages.startcase)
1727
};
1828

1929
test('with empty scope should succeed for "never lowercase"', async t => {
@@ -40,6 +50,66 @@ test('with empty scope should succeed for "always uppercase"', async t => {
4050
t.is(actual, expected);
4151
});
4252

53+
test('with empty scope should succeed for "never camelcase"', async t => {
54+
const [actual] = scopeCase(await parsed.empty, 'never', 'camelcase');
55+
const expected = true;
56+
t.is(actual, expected);
57+
});
58+
59+
test('with empty scope should succeed for "always camelcase"', async t => {
60+
const [actual] = scopeCase(await parsed.empty, 'never', 'camelcase');
61+
const expected = true;
62+
t.is(actual, expected);
63+
});
64+
65+
test('with empty scope should succeed for "never kebabcase"', async t => {
66+
const [actual] = scopeCase(await parsed.empty, 'never', 'kebabcase');
67+
const expected = true;
68+
t.is(actual, expected);
69+
});
70+
71+
test('with empty scope should succeed for "always kebabcase"', async t => {
72+
const [actual] = scopeCase(await parsed.empty, 'never', 'kebabcase');
73+
const expected = true;
74+
t.is(actual, expected);
75+
});
76+
77+
test('with empty scope should succeed for "never pascalcase"', async t => {
78+
const [actual] = scopeCase(await parsed.empty, 'never', 'pascalcase');
79+
const expected = true;
80+
t.is(actual, expected);
81+
});
82+
83+
test('with empty scope should succeed for "always pascalcase"', async t => {
84+
const [actual] = scopeCase(await parsed.empty, 'never', 'pascalcase');
85+
const expected = true;
86+
t.is(actual, expected);
87+
});
88+
89+
test('with empty scope should succeed for "never snakecase"', async t => {
90+
const [actual] = scopeCase(await parsed.empty, 'never', 'snakecase');
91+
const expected = true;
92+
t.is(actual, expected);
93+
});
94+
95+
test('with empty scope should succeed for "always snakecase"', async t => {
96+
const [actual] = scopeCase(await parsed.empty, 'never', 'snakecase');
97+
const expected = true;
98+
t.is(actual, expected);
99+
});
100+
101+
test('with empty scope should succeed for "never startcase"', async t => {
102+
const [actual] = scopeCase(await parsed.empty, 'never', 'startcase');
103+
const expected = true;
104+
t.is(actual, expected);
105+
});
106+
107+
test('with empty scope should succeed for "always startcase"', async t => {
108+
const [actual] = scopeCase(await parsed.empty, 'never', 'startcase');
109+
const expected = true;
110+
t.is(actual, expected);
111+
});
112+
43113
test('with lowercase scope should fail for "never lowercase"', async t => {
44114
const [actual] = scopeCase(await parsed.lowercase, 'never', 'lowercase');
45115
const expected = false;
@@ -70,6 +140,18 @@ test('with mixedcase scope should succeed for "never uppercase"', async t => {
70140
t.is(actual, expected);
71141
});
72142

143+
test('with kebabcase scope should succeed for "always lowercase"', async t => {
144+
const [actual] = scopeCase(await parsed.kebabcase, 'always', 'lowercase');
145+
const expected = false;
146+
t.is(actual, expected);
147+
});
148+
149+
test('with camelcase scope should fail for "always lowercase"', async t => {
150+
const [actual] = scopeCase(await parsed.camelcase, 'always', 'lowercase');
151+
const expected = false;
152+
t.is(actual, expected);
153+
});
154+
73155
test('with mixedcase scope should fail for "always uppercase"', async t => {
74156
const [actual] = scopeCase(await parsed.mixedcase, 'always', 'uppercase');
75157
const expected = false;

docs/reference-rules.md

+36
Original file line numberDiff line numberDiff line change
@@ -146,6 +146,18 @@ Rule configurations are either of type `array` residing on a key with the rule's
146146
```js
147147
'lowerCase'
148148
```
149+
* **possible values**
150+
```js
151+
[
152+
'lowercase', // default
153+
'uppercase', // UPPERCASE
154+
'camelcase', // camelCase
155+
'kebabcase', // kebab-case
156+
'pascalcase', // PascalCase
157+
'snakecase', // snake_case
158+
'startcase' // Start Case
159+
]
160+
```
149161

150162
#### scope-empty
151163
* **condition**: `scope` is empty
@@ -173,6 +185,18 @@ Rule configurations are either of type `array` residing on a key with the rule's
173185
```js
174186
'lowerCase'
175187
```
188+
* **possible values**
189+
```js
190+
[
191+
'lowercase', // default
192+
'uppercase', // UPPERCASE
193+
'camelcase', // camelCase
194+
'kebabcase', // kebab-case
195+
'pascalcase', // PascalCase
196+
'snakecase', // snake_case
197+
'startcase' // Start Case
198+
]
199+
```
176200

177201
#### subject-empty
178202
* **condition**: `subject` is empty
@@ -243,6 +267,18 @@ Rule configurations are either of type `array` residing on a key with the rule's
243267
```js
244268
'lowerCase'
245269
```
270+
* **possible values**
271+
```js
272+
[
273+
'lowercase', // default
274+
'uppercase', // UPPERCASE
275+
'camelcase', // camelCase
276+
'kebabcase', // kebab-case
277+
'pascalcase', // PascalCase
278+
'snakecase', // snake_case
279+
'startcase' // Start Case
280+
]
281+
```
246282

247283
#### type-empty
248284
* **condition**: `type` is empty

package.json

+3
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,9 @@
5656
"name": "Mario Nebl",
5757
"email": "[email protected]"
5858
},
59+
"dependencies": {
60+
"lodash": "^4.17.4"
61+
},
5962
"devDependencies": {
6063
"docsify-cli": "^4.1.8",
6164
"eslint-config-prettier": "^2.3.0",

0 commit comments

Comments
 (0)