-
Notifications
You must be signed in to change notification settings - Fork 37
Expand file tree
/
Copy pathcommitlint.config.test.js
More file actions
192 lines (160 loc) · 6.51 KB
/
Copy pathcommitlint.config.test.js
File metadata and controls
192 lines (160 loc) · 6.51 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
const { default: lint } = require('@commitlint/lint');
const config = require('./commitlint.config');
// Use the conventional-commits parser opts that support the ! breaking marker.
// In production, commitlint loads these from @commitlint/config-conventional.
const parserOpts = {
headerPattern: /^(\w*)(?:\((.*)\))?!?: (.*)$/,
headerCorrespondence: ['type', 'scope', 'subject'],
};
const lintMessage = (message) =>
lint(message, config.rules, { plugins: config.plugins, parserOpts });
describe('commitlint scope-full-name-for-versioning', () => {
describe('valid commits', () => {
it('feat with full project name', async () => {
const result = await lintMessage(
'feat(@redhat-cloud-services/rbac-client): add endpoint'
);
expect(result.valid).toBe(true);
});
it('fix with full project name', async () => {
const result = await lintMessage(
'fix(@redhat-cloud-services/scheduler-client): handle error'
);
expect(result.valid).toBe(true);
});
it('breaking with full project name (! marker)', async () => {
const result = await lintMessage(
'feat(@redhat-cloud-services/rbac-client)!: remove v1'
);
expect(result.valid).toBe(true);
});
it('breaking with full project name (BREAKING CHANGE footer)', async () => {
const result = await lintMessage(
'feat(@redhat-cloud-services/rbac-client): remove v1\n\nBREAKING CHANGE: removes v1 API'
);
expect(result.valid).toBe(true);
});
it('multiple scopes comma-separated', async () => {
const result = await lintMessage(
'feat(@redhat-cloud-services/rbac-client,@redhat-cloud-services/scheduler-client): shared change'
);
expect(result.valid).toBe(true);
});
it('chore with short scope (no version impact)', async () => {
const result = await lintMessage('chore(rbac): update docs');
expect(result.valid).toBe(true);
});
it('docs with short scope (no version impact)', async () => {
const result = await lintMessage('docs(readme): add examples');
expect(result.valid).toBe(true);
});
it('chore with area scope (deps)', async () => {
const result = await lintMessage('chore(deps): add new dep');
expect(result.valid).toBe(true);
});
it('chore with area scope (ci)', async () => {
const result = await lintMessage('chore(ci): update workflow');
expect(result.valid).toBe(true);
});
it('breaking with BREAKING CHANGE footer (BREAKING CHANGE footer)', async () => {
const result = await lintMessage(
'feat(@redhat-cloud-services/rbac-client): remove v1\n\nBREAKING CHANGE: removes v1 API'
);
expect(result.valid).toBe(true);
});
it('chore with no scope', async () => {
const result = await lintMessage('chore: maintenance');
expect(result.valid).toBe(true);
});
it('build-utils project name (non-client package)', async () => {
const result = await lintMessage(
'feat(@redhat-cloud-services/build-utils): add executor'
);
expect(result.valid).toBe(true);
});
it('shared project name', async () => {
const result = await lintMessage(
'fix(@redhat-cloud-services/javascript-clients-shared): fix interceptor'
);
expect(result.valid).toBe(true);
});
it('fix with short scope (allowed)', async () => {
const result = await lintMessage('fix(scheduler): handle error');
expect(result.valid).toBe(true);
});
it('fix with no scope (allowed)', async () => {
const result = await lintMessage('fix: global change');
expect(result.valid).toBe(true);
});
it('fix with deps scope (dependabot)', async () => {
const result = await lintMessage('fix(deps): bump axios to 1.18.0');
expect(result.valid).toBe(true);
});
it('fix with deps-dev scope (dependabot)', async () => {
const result = await lintMessage('fix(deps-dev): bump webpack to 5.1.0');
expect(result.valid).toBe(true);
});
});
describe('invalid commits', () => {
it('feat with short scope', async () => {
const result = await lintMessage('feat(rbac): add endpoint');
expect(result.valid).toBe(false);
expect(result.errors[0].message).toContain(
'must be a full Nx project name'
);
expect(result.errors[0].message).toContain('Use full project name like');
});
it('breaking chore with short scope (! marker)', async () => {
const result = await lintMessage('chore(rbac)!: breaking change');
expect(result.valid).toBe(false);
});
it('breaking chore with short scope (BREAKING CHANGE footer)', async () => {
const result = await lintMessage(
'chore(rbac): breaking change\n\nBREAKING CHANGE: removes old API'
);
expect(result.valid).toBe(false);
});
it('breaking type! with short scope', async () => {
const result = await lintMessage('fix(rbac)!: breaking fix');
expect(result.valid).toBe(false);
});
it('comma-separated with one invalid scope', async () => {
const result = await lintMessage(
'feat(@redhat-cloud-services/rbac-client,scheduler): mixed scopes'
);
expect(result.valid).toBe(false);
});
it('feat with invented project name', async () => {
const result = await lintMessage(
'feat(@redhat-cloud-services/nonexistent-client): add feature'
);
expect(result.valid).toBe(false);
expect(result.errors[0].message).toContain('Project');
expect(result.errors[0].message).toContain('not found');
});
it('feat with no scope', async () => {
const result = await lintMessage('feat: global change');
expect(result.valid).toBe(false);
expect(result.errors[0].message).toContain('Scope required');
});
it('breaking with no scope', async () => {
const result = await lintMessage('fix!: breaking fix');
expect(result.valid).toBe(false);
expect(result.errors[0].message).toContain('Scope required');
});
it('feat with area scope (deps)', async () => {
const result = await lintMessage('feat(deps): add new dep');
expect(result.valid).toBe(false);
expect(result.errors[0].message).toContain(
'must be a full Nx project name'
);
});
it('feat with area scope (ci)', async () => {
const result = await lintMessage('feat(ci): update workflow');
expect(result.valid).toBe(false);
expect(result.errors[0].message).toContain(
'must be a full Nx project name'
);
});
});
});