@w5s/mrm-preset 3.5.7 → 3.5.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (46) hide show
  1. package/.turbo/turbo-build.log +1 -1
  2. package/.turbo/turbo-lint.log +12 -14
  3. package/.turbo/turbo-test.log +23 -258
  4. package/CHANGELOG.md +4 -0
  5. package/asdf/{index.js → index.cjs} +1 -1
  6. package/bootstrap/{index.js → index.cjs} +11 -10
  7. package/ci/_gitlab/Renovate.gitlab-ci.yml +1 -1
  8. package/ci/{github.js → github.cjs} +10 -10
  9. package/ci/{gitlab.js → gitlab.cjs} +1 -2
  10. package/ci/{index.js → index.cjs} +4 -4
  11. package/commitlint/{index.js → index.cjs} +3 -3
  12. package/core/{commitlint.js → commitlint.cjs} +5 -5
  13. package/core/{cspell.js → cspell.cjs} +5 -4
  14. package/core/{eslint.js → eslint.cjs} +5 -4
  15. package/core/{git.js → git.cjs} +4 -3
  16. package/core/{githooks.js → githooks.cjs} +3 -3
  17. package/core/{jest.js → jest.cjs} +11 -10
  18. package/core/{jsonFile.js → jsonFile.cjs} +1 -1
  19. package/core/{lintStaged.js → lintStaged.cjs} +4 -4
  20. package/core/{npm.js → npm.cjs} +204 -205
  21. package/core/{pkg.js → pkg.cjs} +70 -69
  22. package/core/{semanticRelease.js → semanticRelease.cjs} +7 -7
  23. package/core/{turbo.js → turbo.cjs} +5 -4
  24. package/core/{typedoc.js → typedoc.cjs} +9 -8
  25. package/core/{vitest.js → vitest.cjs} +8 -7
  26. package/core/{vscode.js → vscode.cjs} +1 -1
  27. package/cspell/{index.js → index.cjs} +7 -7
  28. package/editorconfig/{index.js → index.cjs} +4 -3
  29. package/eslint/{index.js → index.cjs} +10 -9
  30. package/githooks/{index.js → index.cjs} +12 -11
  31. package/gitignore/{index.js → index.cjs} +1 -1
  32. package/lang/{index.js → index.cjs} +4 -4
  33. package/licenses/{index.js → index.cjs} +5 -4
  34. package/package.json +4 -4
  35. package/package.json.backup +9 -9
  36. package/post-configure/{index.js → index.cjs} +5 -4
  37. package/project/{index.js → index.cjs} +64 -63
  38. package/release/{index.js → index.cjs} +6 -5
  39. package/renovate/{index.js → index.cjs} +3 -2
  40. package/vitest/{index.js → index.cjs} +1 -1
  41. package/contributing/{index.js → index.cjs} +1 -1
  42. package/core/{asdf.js → asdf.cjs} +0 -0
  43. package/core/{git.ignore.js → git.ignore.cjs} +27 -27
  44. package/core/{githubCI.js → githubCI.cjs} +2 -2
  45. package/core/{gitlabCI.js → gitlabCI.cjs} +0 -0
  46. package/core/{project.js → project.cjs} +8 -8
@@ -1,7 +1,8 @@
1
1
  const { packageJson } = require('mrm-core');
2
- const pkg = require('./pkg.js');
3
- const npm = require('./npm.js');
4
- const project = require('./project.js');
2
+
3
+ const npm = require('./npm.cjs');
4
+ const pkg = require('./pkg.cjs');
5
+ const project = require('./project.cjs');
5
6
 
6
7
  /**
7
8
  * @param {{
@@ -17,6 +18,8 @@ function jest({ state }) {
17
18
  const ignorePatterns = ['/node_modules/', '/docs/', '/lib/', '/dist/', '/build/', '/.cache/', '/public/'];
18
19
 
19
20
  pkg.value(packageFile, {
21
+ // @ts-ignore
22
+ default: {},
20
23
  path: 'jest',
21
24
  state: hasJest ? 'present' : 'absent',
22
25
  update: hasWorkspaces
@@ -28,24 +31,22 @@ function jest({ state }) {
28
31
  })
29
32
  : (config) => ({
30
33
  ...config,
31
- preset: 'es-jest',
32
34
  coveragePathIgnorePatterns: ignorePatterns,
35
+ preset: 'es-jest',
33
36
  testPathIgnorePatterns: ignorePatterns,
34
37
  }),
35
- // @ts-ignore
36
- default: {},
37
38
  });
38
39
  pkg.script(packageFile, {
40
+ default: undefined, // pkg.emptyScript,
39
41
  name: `${project.coverage}:root`,
40
- update: (/** @type {string|undefined} */ _) => (hasWorkspaces ? _ : 'jest --coverage'),
41
42
  state: 'present',
42
- default: undefined, // pkg.emptyScript,
43
+ update: (/** @type {string|undefined} */ _) => (hasWorkspaces ? _ : 'jest --coverage'),
43
44
  });
44
45
  pkg.script(packageFile, {
46
+ default: undefined, // pkg.emptyScript,
45
47
  name: `${project.test}:root`,
46
- update: (/** @type {string|undefined} */ _) => (hasWorkspaces ? _ : 'jest'),
47
48
  state: 'present',
48
- default: undefined, // pkg.emptyScript,
49
+ update: (/** @type {string|undefined} */ _) => (hasWorkspaces ? _ : 'jest'),
49
50
  });
50
51
  });
51
52
 
@@ -39,7 +39,7 @@ function setValue(jsonFile, path, pathValue) {
39
39
  * default?: T | (() => T)
40
40
  * }} options
41
41
  */
42
- function value(jsonFile, { state, path, default: defaultValue, update: nextValue }) {
42
+ function value(jsonFile, { default: defaultValue, path, state, update: nextValue }) {
43
43
  if (state === 'present') {
44
44
  let currentValue = getValue(jsonFile, path);
45
45
 
@@ -1,5 +1,5 @@
1
- const pkg = require('./pkg.js');
2
- const jsonFile = require('./jsonFile.js');
1
+ const jsonFile = require('./jsonFile.cjs');
2
+ const pkg = require('./pkg.cjs');
3
3
 
4
4
  /**
5
5
  * @typedef {Record<string, string|string[]>} LintStagedConfig
@@ -14,11 +14,11 @@ const jsonFile = require('./jsonFile.js');
14
14
  function lintStaged({ state, update }) {
15
15
  pkg.withPackageJson((packageFile) => {
16
16
  jsonFile.value(packageFile, {
17
+ /** @type {LintStagedConfig} */
18
+ default: {},
17
19
  path: 'lint-staged',
18
20
  state,
19
21
  update,
20
- /** @type {LintStagedConfig} */
21
- default: {},
22
22
  });
23
23
  });
24
24
 
@@ -1,29 +1,28 @@
1
1
  /* eslint-disable no-param-reassign */
2
2
  /* eslint-disable consistent-return */
3
3
  /* eslint-disable default-param-last */
4
- const { yarnVersion, yarnConfig } = require('@w5s/configurator-core');
5
-
4
+ const { yarnConfig, yarnVersion } = require('@w5s/configurator-core');
6
5
  /* cSpell: disable */
7
6
  // @ts-check
8
7
  // @ts-ignore
9
8
  const fs = require('fs-extra');
10
9
  // @ts-ignore
10
+ const listify = require('listify');
11
+ // @ts-ignore
11
12
  const _ = require('lodash');
13
+ const { json, yaml } = require('mrm-core');
12
14
  // @ts-ignore
13
- const semver = require('semver');
15
+ const MrmError = require('mrm-core/src/error');
14
16
  // @ts-ignore
15
- const listify = require('listify');
17
+ const packageJson = require('mrm-core/src/files/packageJson');
16
18
  // @ts-ignore
17
- const validateNpmPackageName = require('validate-npm-package-name');
19
+ const execCommand = require('mrm-core/src/util/execCommand');
18
20
  // @ts-ignore
19
21
  const log = require('mrm-core/src/util/log');
20
22
  // @ts-ignore
21
- const execCommand = require('mrm-core/src/util/execCommand');
22
- // @ts-ignore
23
- const packageJson = require('mrm-core/src/files/packageJson');
23
+ const semver = require('semver');
24
24
  // @ts-ignore
25
- const MrmError = require('mrm-core/src/error');
26
- const { yaml, json } = require('mrm-core');
25
+ const validateNpmPackageName = require('validate-npm-package-name');
27
26
 
28
27
  /**
29
28
  * @typedef {{
@@ -44,146 +43,83 @@ const { yaml, json } = require('mrm-core');
44
43
  */
45
44
 
46
45
  /**
47
- * Install or update given npm packages if needed
48
- *
49
- * @param {Record<string, string> | string[] | string} deps
50
- * @param {Options} [options]
51
- * @param {Function=} exec
46
+ * @param {'npm'|'pnpm'|`yarn@${'classic'|'berry'}`} defaultPackageManager
52
47
  */
53
- function install(deps, options = {}, exec) {
54
- const dev = options.dev !== false;
55
- const manager = options.yarn ? 'yarn' : options.pnpm ? 'pnpm' : detectPackageManager();
56
- const run = manager === 'yarn' ? runYarn : manager === 'pnpm' ? runPnpm : runNpm;
57
-
58
- // options.versions is a min versions mapping,
59
- // the list of packages to install will be taken from deps
60
- let versions = options.versions || {};
61
-
62
- /** @type string[] */
63
- let dependencies = [];
48
+ async function bootstrap(defaultPackageManager) {
49
+ const packageFile = json(`./package.json`);
50
+ const isYarn = isUsingYarn() || defaultPackageManager.startsWith('yarn@');
51
+ const isPnpm = isUsingPnpm() || defaultPackageManager === 'pnpm';
64
52
 
65
- if (typeof deps === 'string') {
66
- dependencies = [deps];
67
- } else if (Array.isArray(deps)) {
68
- dependencies = deps;
69
- } else if (typeof deps === 'object' && deps !== null) {
70
- // deps is an object with required versions
71
- // prettier-ignore
72
- versions = deps;
73
- dependencies = Object.keys(deps);
53
+ if (!packageFile.get('packageManager') && isYarn) {
54
+ // Downgrade
55
+ if (defaultPackageManager.endsWith('@classic')) {
56
+ await yarnVersion({
57
+ state: 'present',
58
+ update: () => 'classic',
59
+ });
60
+ } else {
61
+ await yarnVersion({
62
+ state: 'present',
63
+ update: () => 'berry',
64
+ });
65
+ await yarnConfig({
66
+ key: 'nodeLinker',
67
+ state: 'present',
68
+ update: () => 'node-modules',
69
+ });
70
+ }
71
+ } else if (!packageFile.get('packageManager') && isPnpm) {
72
+ packageFile.set('packageManager', 'pnpm@latest');
73
+ packageFile.save();
74
74
  }
75
75
 
76
- const newDeps = getUnsatisfiedDeps(dependencies, versions, { dev });
77
- if (newDeps.length === 0) {
78
- return;
76
+ // lock files
77
+ if (isYarn && !fs.existsSync('yarn.lock')) {
78
+ execCommand(undefined, 'yarn', ['install']);
79
79
  }
80
-
81
- log.info(`Installing ${listify(newDeps)}...`);
82
- const versionedDeps = newDeps.map((dep) => getVersionedDep(dep, versions));
83
-
84
- return run(versionedDeps, { dev }, exec);
85
- }
86
-
87
- /**
88
- * Uninstall given npm packages
89
- *
90
- * @param {string[] | string} deps
91
- * @param {Options} [options]
92
- * @param {Function=} exec
93
- */
94
- function uninstall(deps, options = {}, exec) {
95
- deps = _.castArray(deps);
96
- const dev = options.dev !== false;
97
- const manager = options.yarn ? 'yarn' : options.pnpm ? 'pnpm' : detectPackageManager();
98
- const run = manager === 'yarn' ? runYarn : manager === 'pnpm' ? runPnpm : runNpm;
99
-
100
- const installed = getOwnDependencies({ dev });
101
-
102
- // @ts-ignore
103
- const newDeps = deps.filter((dep) => installed[dep]);
104
-
105
- if (newDeps.length === 0) {
106
- return;
80
+ if (isPnpm && !fs.existsSync('pnpm-lock.yaml')) {
81
+ execCommand(undefined, 'pnpm', ['install']);
82
+ }
83
+ if (!isYarn && !isPnpm && !fs.existsSync('package-lock.json')) {
84
+ execCommand(undefined, 'npm', ['install']);
107
85
  }
108
-
109
- log.info(`Uninstalling ${listify(newDeps)}...`);
110
-
111
- return run(newDeps, { dev, remove: true }, exec);
112
- }
113
-
114
- /**
115
- * Install given npm packages
116
- *
117
- * @param {string[]} deps
118
- * @param {RunOptions} [options]
119
- * @param {Function} [exec]
120
- */
121
- function runNpm(deps, options = {}, exec) {
122
- const args = [options.remove ? 'uninstall' : 'install', options.dev ? '--save-dev' : '--save', ...deps];
123
-
124
- return execCommand(exec, 'npm', args, {
125
- cwd: options.cwd,
126
- stdio: options.stdio === undefined ? 'inherit' : options.stdio,
127
- });
128
86
  }
129
87
 
130
88
  /**
131
- * Install given Yarn packages
132
- *
133
- * @param {string[]} deps
134
- * @param {RunOptions} [options]
135
- * @param {Function} [exec]
89
+ * @param {{
90
+ * name: string|string[]|Record<string, string>,
91
+ * state: 'present'|'absent',
92
+ * dev?: boolean,
93
+ * yarn?: boolean,
94
+ * pnpm?: boolean,
95
+ * }} options
136
96
  */
137
- function runYarn(deps, options = {}, exec) {
138
- const add = options.dev ? ['add', '--dev'] : ['add'];
139
- const remove = ['remove'];
140
- // eslint-disable-next-line unicorn/prefer-spread
141
- const args = (options.remove ? remove : add).concat(isUsingWorkspaces() && !isYarnBerry() ? ['-W'] : []).concat(deps);
142
-
143
- return execCommand(exec, 'yarn', args, {
144
- cwd: options.cwd,
145
- stdio: options.stdio === undefined ? 'inherit' : options.stdio,
146
- });
97
+ function dependency({ name, state, ...options }) {
98
+ if (state === 'present') {
99
+ install(name, options);
100
+ } else {
101
+ uninstall(typeof name === 'string' || Array.isArray(name) ? name : Object.keys(name));
102
+ }
147
103
  }
148
104
 
149
- /**
150
- * Install given PNPM packages
151
- *
152
- * @param {string[]} deps
153
- * @param {RunOptions} [options]
154
- * @param {Function} [exec]
155
- */
156
- function runPnpm(deps, options = {}, exec) {
157
- const add = options.dev ? ['add', '--save-dev'] : ['add'];
158
- const remove = ['remove'];
159
- const args = [...(options.remove ? remove : add), ...(isUsingWorkspaces() ? ['--workspace-root'] : []), ...deps];
160
-
161
- return execCommand(exec, 'pnpm', args, {
162
- cwd: options.cwd,
163
- stdio: options.stdio === undefined ? 'inherit' : options.stdio,
164
- });
105
+ function detectPackageManager() {
106
+ if (isUsingYarn()) {
107
+ return 'yarn';
108
+ }
109
+ if (isUsingPnpm()) {
110
+ return 'pnpm';
111
+ }
112
+ return 'npm';
165
113
  }
166
114
 
167
115
  /**
168
- * Add version or latest to package name
116
+ * Return version of installed npm package
169
117
  *
170
- * @param {string} dep
171
- * @param {Record<string, string>} versions
118
+ * @param {string} name
119
+ * @returns {string} - version
172
120
  */
173
- function getVersionedDep(dep, versions) {
174
- // Handle non-registry packages (Github, bitbucket, etc.)
175
- if (!validateNpmPackageName(dep).validForNewPackages) {
176
- // If we were explicitly passed a version, attempt to
177
- // load it via the `#semver:<semver>` syntax.
178
- if (versions[dep]) {
179
- return `${dep}#semver:${versions[dep]}`;
180
- }
181
-
182
- return dep;
183
- }
184
- const version = versions[dep] || 'latest';
185
-
186
- return `${dep}@${version}`;
121
+ function getInstalledVersion(name) {
122
+ return json(`./node_modules/${name}/package.json`).get('version');
187
123
  }
188
124
 
189
125
  /**
@@ -200,16 +136,6 @@ function getOwnDependencies(options) {
200
136
  return pkg.get(options.dev ? 'devDependencies' : 'dependencies') || {};
201
137
  }
202
138
 
203
- /**
204
- * Return version of installed npm package
205
- *
206
- * @param {string} name
207
- * @returns {string} - version
208
- */
209
- function getInstalledVersion(name) {
210
- return json(`./node_modules/${name}/package.json`).get('version');
211
- }
212
-
213
139
  /**
214
140
  * Return only not installed dependencies, or dependencies which installed
215
141
  * version doesn't satisfy range.
@@ -259,94 +185,167 @@ function getUnsatisfiedDeps(deps, versions, options) {
259
185
  });
260
186
  }
261
187
 
262
- /*
263
- * Is project using Yarn?
188
+ /**
189
+ * Add version or latest to package name
190
+ *
191
+ * @param {string} dep
192
+ * @param {Record<string, string>} versions
264
193
  */
265
- function isUsingYarn() {
266
- return fs.existsSync('yarn.lock');
267
- }
194
+ function getVersionedDep(dep, versions) {
195
+ // Handle non-registry packages (Github, bitbucket, etc.)
196
+ if (!validateNpmPackageName(dep).validForNewPackages) {
197
+ // If we were explicitly passed a version, attempt to
198
+ // load it via the `#semver:<semver>` syntax.
199
+ if (versions[dep]) {
200
+ return `${dep}#semver:${versions[dep]}`;
201
+ }
268
202
 
269
- function isUsingPnpm() {
270
- return fs.existsSync('pnpm-lock.yaml');
203
+ return dep;
204
+ }
205
+ const version = versions[dep] || 'latest';
206
+
207
+ return `${dep}@${version}`;
271
208
  }
272
209
 
273
- function detectPackageManager() {
274
- if (isUsingYarn()) {
275
- return 'yarn';
210
+ /**
211
+ * Install or update given npm packages if needed
212
+ *
213
+ * @param {Record<string, string> | string[] | string} deps
214
+ * @param {Options} [options]
215
+ * @param {Function=} exec
216
+ */
217
+ function install(deps, options = {}, exec) {
218
+ const dev = options.dev !== false;
219
+ const manager = options.yarn ? 'yarn' : options.pnpm ? 'pnpm' : detectPackageManager();
220
+ const run = manager === 'yarn' ? runYarn : manager === 'pnpm' ? runPnpm : runNpm;
221
+
222
+ // options.versions is a min versions mapping,
223
+ // the list of packages to install will be taken from deps
224
+ let versions = options.versions || {};
225
+
226
+ /** @type string[] */
227
+ let dependencies = [];
228
+
229
+ if (typeof deps === 'string') {
230
+ dependencies = [deps];
231
+ } else if (Array.isArray(deps)) {
232
+ dependencies = deps;
233
+ } else if (typeof deps === 'object' && deps !== null) {
234
+ // deps is an object with required versions
235
+ // prettier-ignore
236
+ versions = deps;
237
+ dependencies = Object.keys(deps);
276
238
  }
277
- if (isUsingPnpm()) {
278
- return 'pnpm';
239
+
240
+ const newDeps = getUnsatisfiedDeps(dependencies, versions, { dev });
241
+ if (newDeps.length === 0) {
242
+ return;
279
243
  }
280
- return 'npm';
244
+
245
+ log.info(`Installing ${listify(newDeps)}...`);
246
+ const versionedDeps = newDeps.map((dep) => getVersionedDep(dep, versions));
247
+
248
+ return run(versionedDeps, { dev }, exec);
249
+ }
250
+
251
+ function isUsingPnpm() {
252
+ return fs.existsSync('pnpm-lock.yaml');
281
253
  }
282
254
 
283
255
  function isUsingWorkspaces() {
284
256
  return Boolean(packageJson().get('workspaces'));
285
257
  }
286
258
 
259
+ /*
260
+ * Is project using Yarn?
261
+ */
262
+ function isUsingYarn() {
263
+ return fs.existsSync('yarn.lock');
264
+ }
265
+
287
266
  function isYarnBerry() {
288
267
  const yamlRC = yaml('.yarnrc.yml');
289
268
  return yamlRC.exists() && !(yamlRC.get('yarnPath') || '').includes('.yarn/releases/yarn-1.');
290
269
  }
291
270
 
292
271
  /**
293
- * @param {'npm'|'pnpm'|`yarn@${'classic'|'berry'}`} defaultPackageManager
272
+ * Install given npm packages
273
+ *
274
+ * @param {string[]} deps
275
+ * @param {RunOptions} [options]
276
+ * @param {Function} [exec]
294
277
  */
295
- async function bootstrap(defaultPackageManager) {
296
- const packageFile = json(`./package.json`);
297
- const isYarn = isUsingYarn() || defaultPackageManager.startsWith('yarn@');
298
- const isPnpm = isUsingPnpm() || defaultPackageManager === 'pnpm';
278
+ function runNpm(deps, options = {}, exec) {
279
+ const args = [options.remove ? 'uninstall' : 'install', options.dev ? '--save-dev' : '--save', ...deps];
299
280
 
300
- if (!packageFile.get('packageManager') && isYarn) {
301
- // Downgrade
302
- if (defaultPackageManager.endsWith('@classic')) {
303
- await yarnVersion({
304
- state: 'present',
305
- update: () => 'classic',
306
- });
307
- } else {
308
- await yarnVersion({
309
- state: 'present',
310
- update: () => 'berry',
311
- });
312
- await yarnConfig({
313
- key: 'nodeLinker',
314
- state: 'present',
315
- update: () => 'node-modules',
316
- });
317
- }
318
- } else if (!packageFile.get('packageManager') && isPnpm) {
319
- packageFile.set('packageManager', 'pnpm@latest');
320
- packageFile.save();
321
- }
281
+ return execCommand(exec, 'npm', args, {
282
+ cwd: options.cwd,
283
+ stdio: options.stdio === undefined ? 'inherit' : options.stdio,
284
+ });
285
+ }
322
286
 
323
- // lock files
324
- if (isYarn && !fs.existsSync('yarn.lock')) {
325
- execCommand(undefined, 'yarn', ['install']);
326
- }
327
- if (isPnpm && !fs.existsSync('pnpm-lock.yaml')) {
328
- execCommand(undefined, 'pnpm', ['install']);
329
- }
330
- if (!isYarn && !isPnpm && !fs.existsSync('package-lock.json')) {
331
- execCommand(undefined, 'npm', ['install']);
332
- }
287
+ /**
288
+ * Install given PNPM packages
289
+ *
290
+ * @param {string[]} deps
291
+ * @param {RunOptions} [options]
292
+ * @param {Function} [exec]
293
+ */
294
+ function runPnpm(deps, options = {}, exec) {
295
+ const add = options.dev ? ['add', '--save-dev'] : ['add'];
296
+ const remove = ['remove'];
297
+ const args = [...(options.remove ? remove : add), ...(isUsingWorkspaces() ? ['--workspace-root'] : []), ...deps];
298
+
299
+ return execCommand(exec, 'pnpm', args, {
300
+ cwd: options.cwd,
301
+ stdio: options.stdio === undefined ? 'inherit' : options.stdio,
302
+ });
333
303
  }
334
304
 
335
305
  /**
336
- * @param {{
337
- * name: string|string[]|Record<string, string>,
338
- * state: 'present'|'absent',
339
- * dev?: boolean,
340
- * yarn?: boolean,
341
- * pnpm?: boolean,
342
- * }} options
306
+ * Install given Yarn packages
307
+ *
308
+ * @param {string[]} deps
309
+ * @param {RunOptions} [options]
310
+ * @param {Function} [exec]
343
311
  */
344
- function dependency({ name, state, ...options }) {
345
- if (state === 'present') {
346
- install(name, options);
347
- } else {
348
- uninstall(typeof name === 'string' || Array.isArray(name) ? name : Object.keys(name));
312
+ function runYarn(deps, options = {}, exec) {
313
+ const add = options.dev ? ['add', '--dev'] : ['add'];
314
+ const remove = ['remove'];
315
+
316
+ const args = (options.remove ? remove : add).concat(isUsingWorkspaces() && !isYarnBerry() ? ['-W'] : []).concat(deps);
317
+
318
+ return execCommand(exec, 'yarn', args, {
319
+ cwd: options.cwd,
320
+ stdio: options.stdio === undefined ? 'inherit' : options.stdio,
321
+ });
322
+ }
323
+
324
+ /**
325
+ * Uninstall given npm packages
326
+ *
327
+ * @param {string[] | string} deps
328
+ * @param {Options} [options]
329
+ * @param {Function=} exec
330
+ */
331
+ function uninstall(deps, options = {}, exec) {
332
+ deps = _.castArray(deps);
333
+ const dev = options.dev !== false;
334
+ const manager = options.yarn ? 'yarn' : options.pnpm ? 'pnpm' : detectPackageManager();
335
+ const run = manager === 'yarn' ? runYarn : manager === 'pnpm' ? runPnpm : runNpm;
336
+
337
+ const installed = getOwnDependencies({ dev });
338
+
339
+ // @ts-ignore
340
+ const newDeps = deps.filter((dep) => installed[dep]);
341
+
342
+ if (newDeps.length === 0) {
343
+ return;
349
344
  }
345
+
346
+ log.info(`Uninstalling ${listify(newDeps)}...`);
347
+
348
+ return run(newDeps, { dev, remove: true }, exec);
350
349
  }
351
350
 
352
351
  module.exports = {