sparkle-design-cli 2.3.0 → 2.3.1
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/lib/load-plugins.js +42 -15
- package/package.json +1 -1
package/lib/load-plugins.js
CHANGED
|
@@ -61,7 +61,12 @@ function extractPluginEntry(pkg) {
|
|
|
61
61
|
}
|
|
62
62
|
|
|
63
63
|
/**
|
|
64
|
-
* Discover and load anti-pattern plugins from the consumer's package.json deps
|
|
64
|
+
* Discover and load anti-pattern plugins from the consumer's package.json deps, plus
|
|
65
|
+
* a self-reference path: if the consumer's own package.json declares
|
|
66
|
+
* `sparkleCli.antiPatterns`, that entry is loaded too (packageName is recorded as the
|
|
67
|
+
* consumer's own `name`, or `"(self)"` if unnamed). This lets a library check its own
|
|
68
|
+
* source against the anti-patterns it defines for its consumers, without needing to
|
|
69
|
+
* list itself in its own dependencies.
|
|
65
70
|
*
|
|
66
71
|
* Returns an object of the shape:
|
|
67
72
|
* {
|
|
@@ -92,18 +97,8 @@ export async function loadAntiPatternPlugins({ cwd = process.cwd() } = {}) {
|
|
|
92
97
|
const groups = [];
|
|
93
98
|
const reminders = [];
|
|
94
99
|
|
|
95
|
-
|
|
96
|
-
const
|
|
97
|
-
if (!depPkgPath) continue;
|
|
98
|
-
|
|
99
|
-
const depPkg = readJsonSafe(depPkgPath);
|
|
100
|
-
if (!depPkg) continue;
|
|
101
|
-
|
|
102
|
-
const entry = extractPluginEntry(depPkg);
|
|
103
|
-
if (!entry) continue;
|
|
104
|
-
|
|
105
|
-
const resolvedFile = path.resolve(path.dirname(depPkgPath), entry);
|
|
106
|
-
const record = { packageName: depName, entry, resolvedFile, status: 'loaded' };
|
|
100
|
+
const loadEntry = async (packageName, entry, resolvedFile) => {
|
|
101
|
+
const record = { packageName, entry, resolvedFile, status: 'loaded' };
|
|
107
102
|
|
|
108
103
|
try {
|
|
109
104
|
if (!fs.existsSync(resolvedFile)) {
|
|
@@ -115,7 +110,7 @@ export async function loadAntiPatternPlugins({ cwd = process.cwd() } = {}) {
|
|
|
115
110
|
// plain object を export する plugin にも同じ厳しさを適用したい。
|
|
116
111
|
// en: Share shape validation with `defineAntiPatternPlugin` so plugins that skip
|
|
117
112
|
// the helper are still rejected at load time.
|
|
118
|
-
validatePluginShape(candidate, `${
|
|
113
|
+
validatePluginShape(candidate, `${packageName} (${entry})`);
|
|
119
114
|
groups.push(...candidate.groups);
|
|
120
115
|
record.groupIds = candidate.groups.map((group) => group.id);
|
|
121
116
|
if (Array.isArray(candidate.manualReviewReminders)) {
|
|
@@ -125,11 +120,43 @@ export async function loadAntiPatternPlugins({ cwd = process.cwd() } = {}) {
|
|
|
125
120
|
record.status = 'error';
|
|
126
121
|
record.error = error?.message ?? String(error);
|
|
127
122
|
console.warn(
|
|
128
|
-
`⚠️ sparkle-design-cli: failed to load anti-pattern plugin from ${
|
|
123
|
+
`⚠️ sparkle-design-cli: failed to load anti-pattern plugin from ${packageName} (entry: ${entry}, error: ${record.error})`
|
|
129
124
|
);
|
|
130
125
|
}
|
|
131
126
|
|
|
132
127
|
discovered.push(record);
|
|
128
|
+
};
|
|
129
|
+
|
|
130
|
+
// 自己参照パス: consumer 自身が sparkleCli.antiPatterns を宣言しているケース
|
|
131
|
+
// (自分自身のソースに対して check を実行する場合、自分自身は自分の dependencies には
|
|
132
|
+
// 現れないため、依存パッケージ経由の discovery だけでは見つからない)。
|
|
133
|
+
// en: Self-reference path — a package checking its own source won't list itself in
|
|
134
|
+
// its own dependencies, so dependency-based discovery alone would miss it.
|
|
135
|
+
const selfEntry = extractPluginEntry(consumerPkg);
|
|
136
|
+
if (selfEntry) {
|
|
137
|
+
const resolvedFile = path.resolve(cwd, selfEntry);
|
|
138
|
+
await loadEntry(consumerPkg.name || '(self)', selfEntry, resolvedFile);
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
for (const depName of depNames) {
|
|
142
|
+
// 自分自身の名前を自分の dependencies に含むケース(workspace の self-link 等)では、
|
|
143
|
+
// 上の自己参照パスと重複してロードされてしまうためスキップする。
|
|
144
|
+
// en: Skip the consumer's own name if it also appears in its own dependencies (e.g. a
|
|
145
|
+
// workspace self-link) — otherwise the self-reference path above and this loop would
|
|
146
|
+
// load the same plugin entry twice.
|
|
147
|
+
if (depName === consumerPkg.name) continue;
|
|
148
|
+
|
|
149
|
+
const depPkgPath = resolvePluginPackageJson(depName, cwd);
|
|
150
|
+
if (!depPkgPath) continue;
|
|
151
|
+
|
|
152
|
+
const depPkg = readJsonSafe(depPkgPath);
|
|
153
|
+
if (!depPkg) continue;
|
|
154
|
+
|
|
155
|
+
const entry = extractPluginEntry(depPkg);
|
|
156
|
+
if (!entry) continue;
|
|
157
|
+
|
|
158
|
+
const resolvedFile = path.resolve(path.dirname(depPkgPath), entry);
|
|
159
|
+
await loadEntry(depName, entry, resolvedFile);
|
|
133
160
|
}
|
|
134
161
|
|
|
135
162
|
return { groups, reminders, discovered };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "sparkle-design-cli",
|
|
3
|
-
"version": "2.3.
|
|
3
|
+
"version": "2.3.1",
|
|
4
4
|
"description": "Sparkle Design CLI — プロジェクトセットアップ、CSS・フォント生成、アンチパターン検査、AI エージェント(Claude Code / Cursor / Codex)向けのガードと hook 設定まで一括で行う sparkle-design 公式 CLI。",
|
|
5
5
|
"publishConfig": {
|
|
6
6
|
"registry": "https://registry.npmjs.org",
|