@configjs/cli 1.0.0
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.
- package/LICENSE +22 -0
- package/README.md +431 -0
- package/dist/check-JF56SNQC.js +126 -0
- package/dist/chunk-5T664O5A.js +8402 -0
- package/dist/chunk-PQLKGF6I.js +224 -0
- package/dist/cli.d.ts +1 -0
- package/dist/cli.js +41 -0
- package/dist/install-X7G2IXXX.js +1127 -0
- package/dist/list-J4E7JFII.js +75 -0
- package/package.json +95 -0
|
@@ -0,0 +1,224 @@
|
|
|
1
|
+
import {
|
|
2
|
+
logger
|
|
3
|
+
} from "./chunk-5T664O5A.js";
|
|
4
|
+
|
|
5
|
+
// src/core/validator.ts
|
|
6
|
+
var CompatibilityValidator = class {
|
|
7
|
+
/**
|
|
8
|
+
* @param rules - Règles de compatibilité à appliquer
|
|
9
|
+
*/
|
|
10
|
+
constructor(rules) {
|
|
11
|
+
this.rules = rules;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Valide la compatibilité d'un ensemble de plugins
|
|
15
|
+
*
|
|
16
|
+
* @param plugins - Liste des plugins à valider
|
|
17
|
+
* @returns Résultat de la validation avec erreurs, warnings et suggestions
|
|
18
|
+
*
|
|
19
|
+
* @example
|
|
20
|
+
* ```typescript
|
|
21
|
+
* const result = validator.validate([plugin1, plugin2, plugin3])
|
|
22
|
+
* if (!result.valid) {
|
|
23
|
+
* // Gérer les erreurs
|
|
24
|
+
* }
|
|
25
|
+
* ```
|
|
26
|
+
*/
|
|
27
|
+
validate(plugins) {
|
|
28
|
+
logger.debug(`Validating ${plugins.length} plugin(s)`);
|
|
29
|
+
const pluginNames = new Set(plugins.map((p) => p.name));
|
|
30
|
+
const allConflicts = this.checkConflicts(plugins, pluginNames);
|
|
31
|
+
const conflictErrors = [];
|
|
32
|
+
const conflictWarnings = [];
|
|
33
|
+
for (const conflict of allConflicts) {
|
|
34
|
+
const rule = this.rules.find(
|
|
35
|
+
(r) => r.type === "CONFLICT" && r.plugins?.every((p) => conflict.plugins?.includes(p))
|
|
36
|
+
);
|
|
37
|
+
if (rule?.severity === "error") {
|
|
38
|
+
conflictErrors.push(conflict);
|
|
39
|
+
} else {
|
|
40
|
+
conflictWarnings.push(conflict);
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
const errors = [
|
|
44
|
+
...this.checkExclusivity(plugins, pluginNames),
|
|
45
|
+
...conflictErrors,
|
|
46
|
+
...this.checkDependencies(plugins, pluginNames)
|
|
47
|
+
];
|
|
48
|
+
const warnings = conflictWarnings;
|
|
49
|
+
const suggestions = this.checkRecommendations(plugins, pluginNames);
|
|
50
|
+
const valid = errors.length === 0;
|
|
51
|
+
logger.debug(`Validation result: ${valid ? "valid" : "invalid"}`, {
|
|
52
|
+
errors: errors.length,
|
|
53
|
+
warnings: warnings.length,
|
|
54
|
+
suggestions: suggestions.length
|
|
55
|
+
});
|
|
56
|
+
return {
|
|
57
|
+
valid,
|
|
58
|
+
errors,
|
|
59
|
+
warnings,
|
|
60
|
+
suggestions
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* Vérifie les règles d'exclusivité (EXCLUSIVE)
|
|
65
|
+
*
|
|
66
|
+
* @param _plugins - Liste des plugins (non utilisée, conservée pour cohérence)
|
|
67
|
+
* @param pluginNames - Set des noms de plugins pour lookup rapide
|
|
68
|
+
* @returns Liste des erreurs d'exclusivité
|
|
69
|
+
*
|
|
70
|
+
* @internal
|
|
71
|
+
*/
|
|
72
|
+
checkExclusivity(_plugins, pluginNames) {
|
|
73
|
+
const errors = [];
|
|
74
|
+
for (const rule of this.rules) {
|
|
75
|
+
if (rule.type !== "EXCLUSIVE" || !rule.plugins) {
|
|
76
|
+
continue;
|
|
77
|
+
}
|
|
78
|
+
const selectedExclusivePlugins = rule.plugins.filter(
|
|
79
|
+
(pluginName) => pluginNames.has(pluginName)
|
|
80
|
+
);
|
|
81
|
+
if (selectedExclusivePlugins.length > 1) {
|
|
82
|
+
errors.push({
|
|
83
|
+
type: "EXCLUSIVE",
|
|
84
|
+
plugins: selectedExclusivePlugins,
|
|
85
|
+
message: rule.reason,
|
|
86
|
+
canOverride: rule.allowOverride ?? false
|
|
87
|
+
});
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
return errors;
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* Vérifie les conflits entre plugins (CONFLICT)
|
|
94
|
+
*
|
|
95
|
+
* @param _plugins - Liste des plugins (non utilisée, conservée pour cohérence)
|
|
96
|
+
* @param pluginNames - Set des noms de plugins pour lookup rapide
|
|
97
|
+
* @returns Liste des warnings/erreurs de conflit
|
|
98
|
+
*
|
|
99
|
+
* @internal
|
|
100
|
+
*/
|
|
101
|
+
checkConflicts(_plugins, pluginNames) {
|
|
102
|
+
const conflicts = [];
|
|
103
|
+
for (const rule of this.rules) {
|
|
104
|
+
if (rule.type !== "CONFLICT" || !rule.plugins) {
|
|
105
|
+
continue;
|
|
106
|
+
}
|
|
107
|
+
const conflictingPlugins = rule.plugins.filter(
|
|
108
|
+
(pluginName) => pluginNames.has(pluginName)
|
|
109
|
+
);
|
|
110
|
+
if (conflictingPlugins.length > 1) {
|
|
111
|
+
conflicts.push({
|
|
112
|
+
type: "CONFLICT",
|
|
113
|
+
plugins: conflictingPlugins,
|
|
114
|
+
message: rule.reason,
|
|
115
|
+
canOverride: rule.allowOverride ?? true
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
return conflicts;
|
|
120
|
+
}
|
|
121
|
+
/**
|
|
122
|
+
* Vérifie les dépendances requises (REQUIRES)
|
|
123
|
+
*
|
|
124
|
+
* @param _plugins - Liste des plugins (non utilisée, conservée pour cohérence)
|
|
125
|
+
* @param pluginNames - Set des noms de plugins pour lookup rapide
|
|
126
|
+
* @returns Liste des erreurs de dépendances manquantes
|
|
127
|
+
*
|
|
128
|
+
* @internal
|
|
129
|
+
*/
|
|
130
|
+
checkDependencies(_plugins, pluginNames) {
|
|
131
|
+
const errors = [];
|
|
132
|
+
for (const rule of this.rules) {
|
|
133
|
+
if (rule.type !== "REQUIRES" || !rule.plugin || !rule.requires) {
|
|
134
|
+
continue;
|
|
135
|
+
}
|
|
136
|
+
if (!pluginNames.has(rule.plugin)) {
|
|
137
|
+
continue;
|
|
138
|
+
}
|
|
139
|
+
const missingDependencies = rule.requires.filter(
|
|
140
|
+
(dep) => !pluginNames.has(dep)
|
|
141
|
+
);
|
|
142
|
+
if (missingDependencies.length > 0) {
|
|
143
|
+
errors.push({
|
|
144
|
+
type: "REQUIRES",
|
|
145
|
+
plugin: rule.plugin,
|
|
146
|
+
required: missingDependencies.join(", "),
|
|
147
|
+
message: `${rule.plugin} requires: ${missingDependencies.join(", ")}. ${rule.reason}`,
|
|
148
|
+
canOverride: rule.allowOverride ?? false
|
|
149
|
+
});
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
return errors;
|
|
153
|
+
}
|
|
154
|
+
/**
|
|
155
|
+
* Vérifie les recommandations (RECOMMENDS)
|
|
156
|
+
*
|
|
157
|
+
* @param _plugins - Liste des plugins (non utilisée, conservée pour cohérence)
|
|
158
|
+
* @param pluginNames - Set des noms de plugins pour lookup rapide
|
|
159
|
+
* @returns Liste des suggestions de plugins recommandés
|
|
160
|
+
*
|
|
161
|
+
* @internal
|
|
162
|
+
*/
|
|
163
|
+
checkRecommendations(_plugins, pluginNames) {
|
|
164
|
+
const suggestions = [];
|
|
165
|
+
for (const rule of this.rules) {
|
|
166
|
+
if (rule.type !== "RECOMMENDS" || !rule.plugin || !rule.recommends) {
|
|
167
|
+
continue;
|
|
168
|
+
}
|
|
169
|
+
if (!pluginNames.has(rule.plugin)) {
|
|
170
|
+
continue;
|
|
171
|
+
}
|
|
172
|
+
const missingRecommendations = rule.recommends.filter(
|
|
173
|
+
(rec) => !pluginNames.has(rec)
|
|
174
|
+
);
|
|
175
|
+
if (missingRecommendations.length > 0) {
|
|
176
|
+
suggestions.push(
|
|
177
|
+
`${rule.plugin} recommends: ${missingRecommendations.join(", ")}. ${rule.reason}`
|
|
178
|
+
);
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
return suggestions;
|
|
182
|
+
}
|
|
183
|
+
};
|
|
184
|
+
var compatibilityRules = [
|
|
185
|
+
// Exclusivités - State Management
|
|
186
|
+
{
|
|
187
|
+
type: "EXCLUSIVE",
|
|
188
|
+
plugins: ["@reduxjs/toolkit", "zustand", "jotai"],
|
|
189
|
+
reason: "Une seule solution de state management est recommand\xE9e",
|
|
190
|
+
severity: "error",
|
|
191
|
+
allowOverride: false
|
|
192
|
+
},
|
|
193
|
+
// Conflits - CSS Frameworks
|
|
194
|
+
{
|
|
195
|
+
type: "CONFLICT",
|
|
196
|
+
plugins: ["tailwindcss", "bootstrap"],
|
|
197
|
+
reason: "Approches CSS potentiellement conflictuelles",
|
|
198
|
+
severity: "warning",
|
|
199
|
+
allowOverride: true
|
|
200
|
+
},
|
|
201
|
+
// Dépendances - TailwindCSS
|
|
202
|
+
{
|
|
203
|
+
type: "REQUIRES",
|
|
204
|
+
plugin: "tailwindcss",
|
|
205
|
+
requires: ["postcss", "autoprefixer"],
|
|
206
|
+
reason: "PostCSS et Autoprefixer sont n\xE9cessaires pour TailwindCSS",
|
|
207
|
+
severity: "error",
|
|
208
|
+
autoInstall: true,
|
|
209
|
+
allowOverride: false
|
|
210
|
+
},
|
|
211
|
+
// Recommandations - React Router
|
|
212
|
+
{
|
|
213
|
+
type: "RECOMMENDS",
|
|
214
|
+
plugin: "react-router-dom",
|
|
215
|
+
recommends: ["@types/react-router-dom"],
|
|
216
|
+
reason: "Types TypeScript recommand\xE9s pour une meilleure exp\xE9rience de d\xE9veloppement",
|
|
217
|
+
severity: "info"
|
|
218
|
+
}
|
|
219
|
+
];
|
|
220
|
+
|
|
221
|
+
export {
|
|
222
|
+
CompatibilityValidator,
|
|
223
|
+
compatibilityRules
|
|
224
|
+
};
|
package/dist/cli.d.ts
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
package/dist/cli.js
ADDED
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
// src/cli.ts
|
|
4
|
+
import { Command } from "commander";
|
|
5
|
+
|
|
6
|
+
// package.json
|
|
7
|
+
var version = "1.0.0";
|
|
8
|
+
|
|
9
|
+
// src/cli.ts
|
|
10
|
+
var program = new Command();
|
|
11
|
+
program.name("confjs").description("Configure your frontend stack, instantly").version(version);
|
|
12
|
+
program.command("react").description("Configure a React project").option("-y, --yes", "Accept all defaults").option("-d, --dry-run", "Simulate without writing to disk").option("-s, --silent", "Non-interactive mode").option("--debug", "Enable debug logs").option("-c, --config <file>", "Use configuration file").option("-f, --force", "Force installation (overwrite configs)").option("--no-install", "Generate configs only, skip package installation").action(
|
|
13
|
+
async (options) => {
|
|
14
|
+
try {
|
|
15
|
+
const { installReact } = await import("./install-X7G2IXXX.js");
|
|
16
|
+
await installReact(options);
|
|
17
|
+
} catch (error) {
|
|
18
|
+
console.error("Error:", error);
|
|
19
|
+
process.exit(1);
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
);
|
|
23
|
+
program.command("list").description("List available libraries").option("-c, --category <category>", "Filter by category").action(async (options) => {
|
|
24
|
+
try {
|
|
25
|
+
const { listLibraries } = await import("./list-J4E7JFII.js");
|
|
26
|
+
listLibraries(options);
|
|
27
|
+
} catch (error) {
|
|
28
|
+
console.error("Error:", error);
|
|
29
|
+
process.exit(1);
|
|
30
|
+
}
|
|
31
|
+
});
|
|
32
|
+
program.command("check").description("Check compatibility without installing").option("-c, --config <file>", "Configuration file to check").action(async (options) => {
|
|
33
|
+
try {
|
|
34
|
+
const { checkCompatibility } = await import("./check-JF56SNQC.js");
|
|
35
|
+
await checkCompatibility(options);
|
|
36
|
+
} catch (error) {
|
|
37
|
+
console.error("Error:", error);
|
|
38
|
+
process.exit(1);
|
|
39
|
+
}
|
|
40
|
+
});
|
|
41
|
+
program.parse(process.argv);
|