@object-ui/cli 17.3.0 → 17.6.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/CHANGELOG.md +537 -0
- package/README.md +6 -8
- package/dist/{chunk-EV2DCI7W.js → chunk-AP2INOE7.js} +717 -599
- package/dist/chunk-AP2INOE7.js.map +1 -0
- package/dist/cli.js +1018 -299
- package/dist/cli.js.map +1 -1
- package/dist/index.d.ts +2 -0
- package/dist/index.js +1 -1
- package/package.json +11 -9
- package/dist/chunk-EV2DCI7W.js.map +0 -1
package/dist/cli.js
CHANGED
|
@@ -3,10 +3,12 @@ import {
|
|
|
3
3
|
createTempApp,
|
|
4
4
|
createTempAppWithRouting,
|
|
5
5
|
init,
|
|
6
|
-
|
|
7
|
-
|
|
6
|
+
isWorkspaceRoot,
|
|
7
|
+
prepareWorkspaceTempApp,
|
|
8
|
+
reportProjectSource,
|
|
9
|
+
resolveProjectSource,
|
|
8
10
|
serve
|
|
9
|
-
} from "./chunk-
|
|
11
|
+
} from "./chunk-AP2INOE7.js";
|
|
10
12
|
|
|
11
13
|
// src/cli.ts
|
|
12
14
|
import { Command } from "commander";
|
|
@@ -15,87 +17,22 @@ import chalk14 from "chalk";
|
|
|
15
17
|
// src/commands/dev.ts
|
|
16
18
|
import { createServer } from "vite";
|
|
17
19
|
import react from "@vitejs/plugin-react";
|
|
18
|
-
import {
|
|
19
|
-
import { join
|
|
20
|
+
import { mkdirSync } from "fs";
|
|
21
|
+
import { join } from "path";
|
|
20
22
|
import chalk from "chalk";
|
|
21
23
|
import { execSync } from "child_process";
|
|
22
|
-
import { createRequire } from "module";
|
|
23
24
|
async function dev(schemaPath, options) {
|
|
24
25
|
const cwd = process.cwd();
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
let hasPagesDir = false;
|
|
28
|
-
let pagesDir = "";
|
|
29
|
-
let appConfig = null;
|
|
30
|
-
const absoluteSchemaPath = resolve(cwd, schemaPath);
|
|
31
|
-
if (existsSync(absoluteSchemaPath) && statSync(absoluteSchemaPath).isFile()) {
|
|
32
|
-
const fileDir = dirname(absoluteSchemaPath);
|
|
33
|
-
const potentialPagesDir = join(fileDir, "pages");
|
|
34
|
-
if (existsSync(potentialPagesDir)) {
|
|
35
|
-
console.log(chalk.blue(`\u{1F4C2} Detected project structure at ${fileDir}`));
|
|
36
|
-
_projectRoot = fileDir;
|
|
37
|
-
hasPagesDir = true;
|
|
38
|
-
pagesDir = potentialPagesDir;
|
|
39
|
-
try {
|
|
40
|
-
appConfig = parseSchemaFile(absoluteSchemaPath);
|
|
41
|
-
console.log(chalk.blue("\u2699\uFE0F Loaded App Config from app.json"));
|
|
42
|
-
} catch (_e) {
|
|
43
|
-
console.warn("Failed to parse app config");
|
|
44
|
-
}
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
if (!hasPagesDir) {
|
|
48
|
-
const localPagesDir = join(cwd, "pages");
|
|
49
|
-
if (existsSync(localPagesDir)) {
|
|
50
|
-
hasPagesDir = true;
|
|
51
|
-
pagesDir = localPagesDir;
|
|
52
|
-
const appJsonPath = join(cwd, "app.json");
|
|
53
|
-
if (existsSync(appJsonPath)) {
|
|
54
|
-
try {
|
|
55
|
-
appConfig = parseSchemaFile(appJsonPath);
|
|
56
|
-
console.log(chalk.blue("\u2699\uFE0F Loaded App Config from app.json"));
|
|
57
|
-
} catch (_e) {
|
|
58
|
-
console.warn("Failed to parse app.json config");
|
|
59
|
-
}
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
}
|
|
63
|
-
const require2 = createRequire(join(cwd, "package.json"));
|
|
64
|
-
let routes = [];
|
|
65
|
-
let schema = null;
|
|
66
|
-
let useFileSystemRouting = false;
|
|
67
|
-
if (hasPagesDir) {
|
|
68
|
-
console.log(chalk.blue(`\u{1F4C1} Using file-system routing from ${pagesDir}`));
|
|
69
|
-
routes = scanPagesDirectory(pagesDir);
|
|
70
|
-
useFileSystemRouting = true;
|
|
71
|
-
if (routes.length === 0) {
|
|
72
|
-
throw new Error(`No schema files found in ${pagesDir}`);
|
|
73
|
-
}
|
|
74
|
-
console.log(chalk.green(`\u2713 Found ${routes.length} route(s)`));
|
|
75
|
-
routes.forEach((route) => {
|
|
76
|
-
console.log(chalk.dim(` ${route.path} \u2192 ${route.filePath.replace(cwd, ".")}`));
|
|
77
|
-
});
|
|
78
|
-
} else {
|
|
79
|
-
const fullSchemaPath = resolve(cwd, schemaPath);
|
|
80
|
-
if (!existsSync(fullSchemaPath)) {
|
|
81
|
-
throw new Error(`Schema file not found: ${schemaPath}
|
|
82
|
-
Run 'objectui init' to create a sample schema.`);
|
|
83
|
-
}
|
|
84
|
-
console.log(chalk.blue("\u{1F4CB} Loading schema:"), chalk.cyan(schemaPath));
|
|
85
|
-
try {
|
|
86
|
-
schema = parseSchemaFile(fullSchemaPath);
|
|
87
|
-
} catch (error) {
|
|
88
|
-
throw new Error(`Invalid schema file: ${error instanceof Error ? error.message : error}`);
|
|
89
|
-
}
|
|
90
|
-
}
|
|
26
|
+
const source = resolveProjectSource(cwd, schemaPath);
|
|
27
|
+
reportProjectSource(source, cwd);
|
|
91
28
|
const tmpDir = join(cwd, ".objectui-tmp");
|
|
92
29
|
mkdirSync(tmpDir, { recursive: true });
|
|
93
|
-
if (
|
|
94
|
-
createTempAppWithRouting(tmpDir, routes, appConfig);
|
|
30
|
+
if (source.mode === "routes") {
|
|
31
|
+
createTempAppWithRouting(tmpDir, source.routes, source.appConfig);
|
|
95
32
|
} else {
|
|
96
|
-
createTempApp(tmpDir, schema);
|
|
33
|
+
createTempApp(tmpDir, source.schema);
|
|
97
34
|
}
|
|
98
|
-
const isMonorepo =
|
|
35
|
+
const isMonorepo = isWorkspaceRoot(cwd);
|
|
99
36
|
if (isMonorepo) {
|
|
100
37
|
console.log(chalk.blue("\u{1F4E6} Detected monorepo - using root node_modules"));
|
|
101
38
|
} else {
|
|
@@ -113,6 +50,10 @@ Run 'objectui init' to create a sample schema.`);
|
|
|
113
50
|
}
|
|
114
51
|
console.log(chalk.green("\u2713 Schema loaded successfully"));
|
|
115
52
|
console.log(chalk.blue("\u{1F680} Starting development server...\n"));
|
|
53
|
+
if (isMonorepo) {
|
|
54
|
+
console.log(chalk.blue("\u{1F4E6} Detected monorepo - configuring workspace aliases"));
|
|
55
|
+
}
|
|
56
|
+
const workspaceConfig = isMonorepo ? await prepareWorkspaceTempApp(cwd, tmpDir) : {};
|
|
116
57
|
const viteConfig = {
|
|
117
58
|
root: tmpDir,
|
|
118
59
|
server: {
|
|
@@ -124,51 +65,9 @@ Run 'objectui init' to create a sample schema.`);
|
|
|
124
65
|
allow: [cwd]
|
|
125
66
|
}
|
|
126
67
|
},
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
},
|
|
130
|
-
plugins: [react()]
|
|
68
|
+
plugins: [react()],
|
|
69
|
+
...workspaceConfig
|
|
131
70
|
};
|
|
132
|
-
if (isMonorepo) {
|
|
133
|
-
console.log(chalk.blue("\u{1F4E6} Detected monorepo - configuring workspace aliases"));
|
|
134
|
-
const postcssPath = join(tmpDir, "postcss.config.js");
|
|
135
|
-
if (existsSync(postcssPath)) {
|
|
136
|
-
unlinkSync(postcssPath);
|
|
137
|
-
}
|
|
138
|
-
viteConfig.resolve.alias = {
|
|
139
|
-
"@object-ui/react": join(cwd, "packages/react/src/index.ts"),
|
|
140
|
-
"@object-ui/components": join(cwd, "packages/components/src/index.ts"),
|
|
141
|
-
"@object-ui/core": join(cwd, "packages/core/src/index.ts"),
|
|
142
|
-
"@object-ui/types": join(cwd, "packages/types/src/index.ts"),
|
|
143
|
-
"@object-ui/plugin-charts": join(cwd, "packages/plugin-charts/src/index.tsx"),
|
|
144
|
-
"@object-ui/plugin-editor": join(cwd, "packages/plugin-editor/src/index.tsx"),
|
|
145
|
-
"@object-ui/plugin-kanban": join(cwd, "packages/plugin-kanban/src/index.tsx"),
|
|
146
|
-
"@object-ui/plugin-markdown": join(cwd, "packages/plugin-markdown/src/index.tsx"),
|
|
147
|
-
"@object-ui/plugin-form": join(cwd, "packages/plugin-form/src/index.tsx"),
|
|
148
|
-
"@object-ui/plugin-grid": join(cwd, "packages/plugin-grid/src/index.tsx"),
|
|
149
|
-
"@object-ui/plugin-view": join(cwd, "packages/plugin-view/src/index.tsx")
|
|
150
|
-
};
|
|
151
|
-
try {
|
|
152
|
-
const lucidePath = require2.resolve("lucide-react", { paths: [join(cwd, "packages/components")] });
|
|
153
|
-
viteConfig.resolve.alias["lucide-react"] = lucidePath;
|
|
154
|
-
} catch (e) {
|
|
155
|
-
console.warn("\u26A0\uFE0F Could not resolve lucide-react automatically:", e);
|
|
156
|
-
}
|
|
157
|
-
try {
|
|
158
|
-
const tailwindcss = require2("tailwindcss");
|
|
159
|
-
const autoprefixer = require2("autoprefixer");
|
|
160
|
-
viteConfig.css = {
|
|
161
|
-
postcss: {
|
|
162
|
-
plugins: [
|
|
163
|
-
tailwindcss(join(tmpDir, "tailwind.config.js")),
|
|
164
|
-
autoprefixer()
|
|
165
|
-
]
|
|
166
|
-
}
|
|
167
|
-
};
|
|
168
|
-
} catch (_e) {
|
|
169
|
-
console.warn(chalk.yellow("\u26A0\uFE0F Failed to load PostCSS plugins from root node_modules. Styles might not work correctly."));
|
|
170
|
-
}
|
|
171
|
-
}
|
|
172
71
|
const server = await createServer(viteConfig);
|
|
173
72
|
await server.listen();
|
|
174
73
|
const { port, host } = server.config.server;
|
|
@@ -186,62 +85,47 @@ Run 'objectui init' to create a sample schema.`);
|
|
|
186
85
|
// src/commands/build.ts
|
|
187
86
|
import { build as viteBuild } from "vite";
|
|
188
87
|
import react2 from "@vitejs/plugin-react";
|
|
189
|
-
import { existsSync
|
|
190
|
-
import { join as join2, resolve
|
|
88
|
+
import { existsSync, mkdirSync as mkdirSync2, cpSync, rmSync } from "fs";
|
|
89
|
+
import { join as join2, resolve } from "path";
|
|
191
90
|
import chalk2 from "chalk";
|
|
192
91
|
import { execSync as execSync2 } from "child_process";
|
|
193
92
|
async function buildApp(schemaPath, options) {
|
|
194
93
|
const cwd = process.cwd();
|
|
195
94
|
const outDir = options.outDir || "dist";
|
|
196
|
-
const outputPath =
|
|
95
|
+
const outputPath = resolve(cwd, outDir);
|
|
197
96
|
console.log(chalk2.blue("\u{1F528} Building application for production..."));
|
|
198
97
|
console.log();
|
|
199
|
-
const
|
|
200
|
-
|
|
201
|
-
let routes = [];
|
|
202
|
-
let schema = null;
|
|
203
|
-
let useFileSystemRouting = false;
|
|
204
|
-
if (hasPagesDir) {
|
|
205
|
-
console.log(chalk2.blue("\u{1F4C1} Using file-system routing"));
|
|
206
|
-
routes = scanPagesDirectory(pagesDir);
|
|
207
|
-
useFileSystemRouting = true;
|
|
208
|
-
if (routes.length === 0) {
|
|
209
|
-
throw new Error("No schema files found in pages/ directory");
|
|
210
|
-
}
|
|
211
|
-
console.log(chalk2.green(`\u2713 Found ${routes.length} route(s)`));
|
|
212
|
-
} else {
|
|
213
|
-
const fullSchemaPath = resolve2(cwd, schemaPath);
|
|
214
|
-
if (!existsSync2(fullSchemaPath)) {
|
|
215
|
-
throw new Error(`Schema file not found: ${schemaPath}
|
|
216
|
-
Run 'objectui init' to create a sample schema.`);
|
|
217
|
-
}
|
|
218
|
-
console.log(chalk2.blue("\u{1F4CB} Loading schema:"), chalk2.cyan(schemaPath));
|
|
219
|
-
try {
|
|
220
|
-
schema = parseSchemaFile(fullSchemaPath);
|
|
221
|
-
} catch (error) {
|
|
222
|
-
throw new Error(`Invalid schema file: ${error instanceof Error ? error.message : error}`);
|
|
223
|
-
}
|
|
224
|
-
}
|
|
98
|
+
const source = resolveProjectSource(cwd, schemaPath);
|
|
99
|
+
reportProjectSource(source, cwd);
|
|
225
100
|
const tmpDir = join2(cwd, ".objectui-tmp");
|
|
226
101
|
mkdirSync2(tmpDir, { recursive: true });
|
|
227
|
-
if (
|
|
228
|
-
createTempAppWithRouting(tmpDir, routes);
|
|
102
|
+
if (source.mode === "routes") {
|
|
103
|
+
createTempAppWithRouting(tmpDir, source.routes, source.appConfig);
|
|
229
104
|
} else {
|
|
230
|
-
createTempApp(tmpDir, schema);
|
|
105
|
+
createTempApp(tmpDir, source.schema);
|
|
231
106
|
}
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
107
|
+
const isMonorepo = isWorkspaceRoot(cwd);
|
|
108
|
+
if (isMonorepo) {
|
|
109
|
+
console.log(chalk2.blue("\u{1F4E6} Detected monorepo - using root node_modules"));
|
|
110
|
+
} else {
|
|
111
|
+
console.log(chalk2.blue("\u{1F4E6} Installing dependencies..."));
|
|
112
|
+
try {
|
|
113
|
+
execSync2("npm install --silent --prefer-offline", {
|
|
114
|
+
cwd: tmpDir,
|
|
115
|
+
stdio: "pipe"
|
|
116
|
+
});
|
|
117
|
+
console.log(chalk2.green("\u2713 Dependencies installed"));
|
|
118
|
+
} catch {
|
|
119
|
+
throw new Error("Failed to install dependencies. Please check your internet connection and try again.");
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
if (isMonorepo) {
|
|
123
|
+
console.log(chalk2.blue("\u{1F4E6} Detected monorepo - configuring workspace aliases"));
|
|
241
124
|
}
|
|
125
|
+
const workspaceConfig = isMonorepo ? await prepareWorkspaceTempApp(cwd, tmpDir) : {};
|
|
242
126
|
console.log(chalk2.blue("\u2699\uFE0F Building with Vite..."));
|
|
243
127
|
console.log();
|
|
244
|
-
if (options.clean &&
|
|
128
|
+
if (options.clean && existsSync(outputPath)) {
|
|
245
129
|
console.log(chalk2.dim(` Cleaning ${outDir}/ directory...`));
|
|
246
130
|
rmSync(outputPath, { recursive: true, force: true });
|
|
247
131
|
}
|
|
@@ -254,7 +138,8 @@ Run 'objectui init' to create a sample schema.`);
|
|
|
254
138
|
reportCompressedSize: true
|
|
255
139
|
},
|
|
256
140
|
plugins: [react2()],
|
|
257
|
-
logLevel: "info"
|
|
141
|
+
logLevel: "info",
|
|
142
|
+
...workspaceConfig
|
|
258
143
|
});
|
|
259
144
|
mkdirSync2(outputPath, { recursive: true });
|
|
260
145
|
cpSync(join2(tmpDir, "dist"), outputPath, { recursive: true });
|
|
@@ -274,21 +159,21 @@ Run 'objectui init' to create a sample schema.`);
|
|
|
274
159
|
// src/commands/start.ts
|
|
275
160
|
import express from "express";
|
|
276
161
|
import rateLimit from "express-rate-limit";
|
|
277
|
-
import { existsSync as
|
|
278
|
-
import { join as join3, resolve as
|
|
162
|
+
import { existsSync as existsSync2 } from "fs";
|
|
163
|
+
import { join as join3, resolve as resolve2 } from "path";
|
|
279
164
|
import chalk3 from "chalk";
|
|
280
165
|
async function start(options) {
|
|
281
166
|
const cwd = process.cwd();
|
|
282
167
|
const distDir = options.dir || "dist";
|
|
283
|
-
const distPath =
|
|
284
|
-
if (!
|
|
168
|
+
const distPath = resolve2(cwd, distDir);
|
|
169
|
+
if (!existsSync2(distPath)) {
|
|
285
170
|
throw new Error(
|
|
286
171
|
`Build directory not found: ${distDir}
|
|
287
172
|
Run 'objectui build' first to create a production build.`
|
|
288
173
|
);
|
|
289
174
|
}
|
|
290
175
|
const indexPath = join3(distPath, "index.html");
|
|
291
|
-
if (!
|
|
176
|
+
if (!existsSync2(indexPath)) {
|
|
292
177
|
throw new Error(
|
|
293
178
|
`index.html not found in ${distDir}/
|
|
294
179
|
Make sure you have a valid production build.`
|
|
@@ -329,14 +214,14 @@ Make sure you have a valid production build.`
|
|
|
329
214
|
|
|
330
215
|
// src/commands/lint.ts
|
|
331
216
|
import { execSync as execSync3 } from "child_process";
|
|
332
|
-
import { existsSync as
|
|
217
|
+
import { existsSync as existsSync3 } from "fs";
|
|
333
218
|
import { join as join4 } from "path";
|
|
334
219
|
import chalk4 from "chalk";
|
|
335
220
|
async function lint(options) {
|
|
336
221
|
const cwd = process.cwd();
|
|
337
222
|
console.log(chalk4.blue("\u{1F50D} Running linter...\n"));
|
|
338
223
|
const tmpDir = join4(cwd, ".objectui-tmp");
|
|
339
|
-
const hasTempApp =
|
|
224
|
+
const hasTempApp = existsSync3(tmpDir);
|
|
340
225
|
if (!hasTempApp) {
|
|
341
226
|
throw new Error(
|
|
342
227
|
"No Object UI application found. Run 'objectui dev' first to generate the application."
|
|
@@ -344,7 +229,7 @@ async function lint(options) {
|
|
|
344
229
|
}
|
|
345
230
|
const packageJsonPath = join4(tmpDir, "package.json");
|
|
346
231
|
const nodeModulesPath = join4(tmpDir, "node_modules");
|
|
347
|
-
if (!
|
|
232
|
+
if (!existsSync3(packageJsonPath) || !existsSync3(nodeModulesPath)) {
|
|
348
233
|
throw new Error(
|
|
349
234
|
"Dependencies not installed. Run 'objectui dev' first to set up the application."
|
|
350
235
|
);
|
|
@@ -374,14 +259,14 @@ async function lint(options) {
|
|
|
374
259
|
|
|
375
260
|
// src/commands/test.ts
|
|
376
261
|
import { execSync as execSync4 } from "child_process";
|
|
377
|
-
import { existsSync as
|
|
262
|
+
import { existsSync as existsSync4 } from "fs";
|
|
378
263
|
import { join as join5 } from "path";
|
|
379
264
|
import chalk5 from "chalk";
|
|
380
265
|
async function test(options) {
|
|
381
266
|
const cwd = process.cwd();
|
|
382
267
|
console.log(chalk5.blue("\u{1F9EA} Running tests...\n"));
|
|
383
268
|
const tmpDir = join5(cwd, ".objectui-tmp");
|
|
384
|
-
const hasTempApp =
|
|
269
|
+
const hasTempApp = existsSync4(tmpDir);
|
|
385
270
|
if (!hasTempApp) {
|
|
386
271
|
throw new Error(
|
|
387
272
|
"No Object UI application found. Run 'objectui dev' first to generate the application."
|
|
@@ -389,7 +274,7 @@ async function test(options) {
|
|
|
389
274
|
}
|
|
390
275
|
const packageJsonPath = join5(tmpDir, "package.json");
|
|
391
276
|
const nodeModulesPath = join5(tmpDir, "node_modules");
|
|
392
|
-
if (!
|
|
277
|
+
if (!existsSync4(packageJsonPath) || !existsSync4(nodeModulesPath)) {
|
|
393
278
|
throw new Error(
|
|
394
279
|
"Dependencies not installed. Run 'objectui dev' first to set up the application."
|
|
395
280
|
);
|
|
@@ -427,7 +312,7 @@ async function test(options) {
|
|
|
427
312
|
|
|
428
313
|
// src/commands/generate.ts
|
|
429
314
|
import chalk6 from "chalk";
|
|
430
|
-
import { existsSync as
|
|
315
|
+
import { existsSync as existsSync5, mkdirSync as mkdirSync3, writeFileSync } from "fs";
|
|
431
316
|
import { join as join6 } from "path";
|
|
432
317
|
async function generate(type, name) {
|
|
433
318
|
const cwd = process.cwd();
|
|
@@ -450,10 +335,10 @@ async function generate(type, name) {
|
|
|
450
335
|
}
|
|
451
336
|
function generateResource(cwd, name) {
|
|
452
337
|
const dir = join6(cwd, "objects");
|
|
453
|
-
if (!
|
|
338
|
+
if (!existsSync5(dir)) mkdirSync3(dir, { recursive: true });
|
|
454
339
|
const fileName = `${name.toLowerCase()}.json`;
|
|
455
340
|
const filePath = join6(dir, fileName);
|
|
456
|
-
if (
|
|
341
|
+
if (existsSync5(filePath)) {
|
|
457
342
|
console.log(chalk6.yellow(`Object ${name} already exists at ${filePath}`));
|
|
458
343
|
return;
|
|
459
344
|
}
|
|
@@ -468,10 +353,10 @@ function generateResource(cwd, name) {
|
|
|
468
353
|
}
|
|
469
354
|
function generatePage(cwd, name) {
|
|
470
355
|
const dir = join6(cwd, "pages");
|
|
471
|
-
if (!
|
|
356
|
+
if (!existsSync5(dir)) mkdirSync3(dir, { recursive: true });
|
|
472
357
|
const fileName = `${name.toLowerCase()}.json`;
|
|
473
358
|
const filePath = join6(dir, fileName);
|
|
474
|
-
if (
|
|
359
|
+
if (existsSync5(filePath)) {
|
|
475
360
|
console.log(chalk6.yellow(`Page ${name} already exists at ${filePath}`));
|
|
476
361
|
return;
|
|
477
362
|
}
|
|
@@ -490,7 +375,7 @@ function generatePage(cwd, name) {
|
|
|
490
375
|
}
|
|
491
376
|
function generatePlugin(cwd, name) {
|
|
492
377
|
const dir = join6(cwd, "plugins", name);
|
|
493
|
-
if (
|
|
378
|
+
if (existsSync5(dir)) {
|
|
494
379
|
console.log(chalk6.yellow(`Plugin ${name} already exists`));
|
|
495
380
|
return;
|
|
496
381
|
}
|
|
@@ -509,95 +394,223 @@ export const ${name}Plugin = {
|
|
|
509
394
|
|
|
510
395
|
// src/commands/doctor.ts
|
|
511
396
|
import chalk7 from "chalk";
|
|
512
|
-
import { existsSync as
|
|
513
|
-
import { join as join7 } from "path";
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
|
|
397
|
+
import { existsSync as existsSync6, readFileSync } from "fs";
|
|
398
|
+
import { dirname, join as join7, resolve as resolvePath } from "path";
|
|
399
|
+
var CSS_ENTRY_CANDIDATES = [
|
|
400
|
+
"src/index.css",
|
|
401
|
+
"src/main.css",
|
|
402
|
+
"src/styles.css",
|
|
403
|
+
"src/style.css",
|
|
404
|
+
"src/app.css",
|
|
405
|
+
"src/global.css",
|
|
406
|
+
"src/globals.css",
|
|
407
|
+
"app/globals.css",
|
|
408
|
+
"app/global.css",
|
|
409
|
+
"styles/globals.css",
|
|
410
|
+
"index.css",
|
|
411
|
+
"styles.css"
|
|
412
|
+
];
|
|
413
|
+
var TAILWIND_CONFIG_CANDIDATES = [
|
|
414
|
+
"tailwind.config.js",
|
|
415
|
+
"tailwind.config.cjs",
|
|
416
|
+
"tailwind.config.mjs",
|
|
417
|
+
"tailwind.config.ts"
|
|
418
|
+
];
|
|
419
|
+
var POSTCSS_CONFIG_CANDIDATES = [
|
|
420
|
+
"postcss.config.js",
|
|
421
|
+
"postcss.config.cjs",
|
|
422
|
+
"postcss.config.mjs",
|
|
423
|
+
"postcss.config.ts"
|
|
424
|
+
];
|
|
425
|
+
var V4_CSS_IMPORT = /@import\s+["']tailwindcss["']/;
|
|
426
|
+
var V3_CSS_DIRECTIVE = /@tailwind\s+(?:base|components|utilities|screens|variants)\b/;
|
|
427
|
+
var CSS_SOURCE_DIRECTIVE = /@source\s+["']/;
|
|
428
|
+
var CSS_CONFIG_DIRECTIVE = /@config\s+["']/;
|
|
429
|
+
var V4_POSTCSS_PLUGIN = /@tailwindcss\/postcss/;
|
|
430
|
+
var V3_POSTCSS_PLUGIN = /["']tailwindcss["']|(?:^|[{,\s])tailwindcss\s*:/m;
|
|
431
|
+
function readIfExists(path) {
|
|
432
|
+
try {
|
|
433
|
+
return existsSync6(path) ? readFileSync(path, "utf-8") : null;
|
|
434
|
+
} catch {
|
|
435
|
+
return null;
|
|
436
|
+
}
|
|
437
|
+
}
|
|
438
|
+
function findFile(cwd, candidates) {
|
|
439
|
+
for (const rel of candidates) {
|
|
440
|
+
const abs = join7(cwd, rel);
|
|
441
|
+
if (existsSync6(abs)) return abs;
|
|
442
|
+
}
|
|
443
|
+
return null;
|
|
444
|
+
}
|
|
445
|
+
function majorOf(range) {
|
|
446
|
+
const match = /(\d+)/.exec(range);
|
|
447
|
+
if (!match) return null;
|
|
448
|
+
const major = Number.parseInt(match[1], 10);
|
|
449
|
+
return Number.isNaN(major) ? null : major;
|
|
450
|
+
}
|
|
451
|
+
function isInstalledFrom(cwd, specifier) {
|
|
452
|
+
let dir = resolvePath(cwd);
|
|
453
|
+
for (; ; ) {
|
|
454
|
+
if (existsSync6(join7(dir, "node_modules", ...specifier.split("/")))) return true;
|
|
455
|
+
const parent = dirname(dir);
|
|
456
|
+
if (parent === dir) return false;
|
|
457
|
+
dir = parent;
|
|
458
|
+
}
|
|
459
|
+
}
|
|
460
|
+
function runDiagnostics(cwd) {
|
|
461
|
+
const results = [];
|
|
462
|
+
const ok = (id, message) => {
|
|
463
|
+
results.push({ id, level: "ok", message });
|
|
464
|
+
};
|
|
465
|
+
const warn = (id, message) => {
|
|
466
|
+
results.push({ id, level: "warn", message });
|
|
467
|
+
};
|
|
468
|
+
const error = (id, message) => {
|
|
469
|
+
results.push({ id, level: "error", message });
|
|
470
|
+
};
|
|
519
471
|
const pkgPath = join7(cwd, "package.json");
|
|
520
|
-
|
|
472
|
+
const pkgRaw = readIfExists(pkgPath);
|
|
473
|
+
let pkg = null;
|
|
474
|
+
if (pkgRaw === null) {
|
|
475
|
+
error("package-json-missing", "package.json not found");
|
|
476
|
+
} else {
|
|
521
477
|
try {
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
478
|
+
pkg = JSON.parse(pkgRaw);
|
|
479
|
+
} catch {
|
|
480
|
+
error("package-json-unreadable", "Failed to parse package.json");
|
|
481
|
+
}
|
|
482
|
+
}
|
|
483
|
+
const deps = pkg ? { ...pkg.dependencies ?? {}, ...pkg.devDependencies ?? {} } : {};
|
|
484
|
+
if (pkg) {
|
|
485
|
+
if (deps.react) {
|
|
486
|
+
ok("react-installed", "React installed");
|
|
487
|
+
} else {
|
|
488
|
+
warn("react-missing", "React not found in dependencies");
|
|
489
|
+
}
|
|
490
|
+
}
|
|
491
|
+
const tailwindRange = pkg ? deps.tailwindcss : void 0;
|
|
492
|
+
if (pkg && !tailwindRange) {
|
|
493
|
+
warn("tailwind-missing", "Tailwind CSS not found in dependencies");
|
|
494
|
+
}
|
|
495
|
+
if (tailwindRange) {
|
|
496
|
+
const major = majorOf(tailwindRange);
|
|
497
|
+
if (major !== null && major < 4) {
|
|
498
|
+
warn(
|
|
499
|
+
"tailwind-major-legacy",
|
|
500
|
+
`Tailwind CSS ${tailwindRange} detected \u2014 ObjectUI targets Tailwind 4. Upgrade with \`npx @tailwindcss/upgrade\`, then move configuration into your CSS entry (\`@import 'tailwindcss'\`, \`@theme\`, \`@source\`).`
|
|
501
|
+
);
|
|
502
|
+
} else {
|
|
503
|
+
ok("tailwind-installed", `Tailwind CSS ${tailwindRange} installed`);
|
|
504
|
+
}
|
|
505
|
+
if (deps["@tailwindcss/postcss"]) {
|
|
506
|
+
ok("tailwind-postcss-declared", "@tailwindcss/postcss declared");
|
|
507
|
+
} else if (isInstalledFrom(cwd, "@tailwindcss/postcss")) {
|
|
508
|
+
ok(
|
|
509
|
+
"tailwind-postcss-installed",
|
|
510
|
+
"@tailwindcss/postcss installed (provided by the workspace)"
|
|
511
|
+
);
|
|
512
|
+
} else {
|
|
513
|
+
error(
|
|
514
|
+
"tailwind-postcss-missing",
|
|
515
|
+
"Tailwind CSS 4 needs @tailwindcss/postcss, which is neither declared nor installed here. v4 moved the PostCSS plugin out of `tailwindcss` into its own package; without it PostCSS fails to load and no styles are emitted. Install it: `npm i -D @tailwindcss/postcss`."
|
|
516
|
+
);
|
|
517
|
+
}
|
|
518
|
+
const postcssConfigPath = findFile(cwd, POSTCSS_CONFIG_CANDIDATES);
|
|
519
|
+
if (postcssConfigPath) {
|
|
520
|
+
const postcssConfig = readIfExists(postcssConfigPath) ?? "";
|
|
521
|
+
const hasV4Plugin = V4_POSTCSS_PLUGIN.test(postcssConfig);
|
|
522
|
+
const hasV3Plugin = V3_POSTCSS_PLUGIN.test(postcssConfig);
|
|
523
|
+
if (hasV3Plugin) {
|
|
524
|
+
error(
|
|
525
|
+
"postcss-plugin-v3",
|
|
526
|
+
"PostCSS config names `tailwindcss` as a plugin \u2014 the Tailwind 3 spelling. In v4 that entry resolves to a shim whose only job is to throw. Replace it with `'@tailwindcss/postcss': {}`."
|
|
527
|
+
);
|
|
528
|
+
} else if (hasV4Plugin) {
|
|
529
|
+
ok("postcss-plugin-v4", "PostCSS config uses @tailwindcss/postcss");
|
|
526
530
|
} else {
|
|
527
|
-
|
|
528
|
-
|
|
531
|
+
warn(
|
|
532
|
+
"postcss-plugin-absent",
|
|
533
|
+
"PostCSS config does not register a Tailwind plugin. Add `'@tailwindcss/postcss': {}` so Tailwind runs during the build."
|
|
534
|
+
);
|
|
529
535
|
}
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
536
|
+
}
|
|
537
|
+
const cssEntries = CSS_ENTRY_CANDIDATES.map((rel) => ({
|
|
538
|
+
rel,
|
|
539
|
+
content: readIfExists(join7(cwd, rel))
|
|
540
|
+
})).filter((entry) => entry.content !== null);
|
|
541
|
+
const importsTailwind = cssEntries.some((entry) => V4_CSS_IMPORT.test(entry.content));
|
|
542
|
+
const usesV3Directives = cssEntries.some((entry) => V3_CSS_DIRECTIVE.test(entry.content));
|
|
543
|
+
const declaresSource = cssEntries.some((entry) => CSS_SOURCE_DIRECTIVE.test(entry.content));
|
|
544
|
+
const optsIntoJsConfig = cssEntries.some((entry) => CSS_CONFIG_DIRECTIVE.test(entry.content));
|
|
545
|
+
if (cssEntries.length === 0) {
|
|
546
|
+
} else if (importsTailwind) {
|
|
547
|
+
ok("css-entry-v4-import", "CSS entry runs `@import 'tailwindcss'`");
|
|
548
|
+
if (declaresSource) {
|
|
549
|
+
ok("css-entry-source", "CSS entry declares `@source` scanning paths");
|
|
536
550
|
}
|
|
537
|
-
}
|
|
538
|
-
|
|
539
|
-
|
|
551
|
+
} else if (usesV3Directives) {
|
|
552
|
+
error(
|
|
553
|
+
"css-entry-v3-directives",
|
|
554
|
+
"CSS entry still uses the Tailwind 3 `@tailwind base/components/utilities` directives. Tailwind 4 replaces all three with a single `@import 'tailwindcss';`."
|
|
555
|
+
);
|
|
556
|
+
} else {
|
|
557
|
+
warn(
|
|
558
|
+
"css-entry-no-tailwind",
|
|
559
|
+
`No CSS entry runs \`@import 'tailwindcss'\`, so Tailwind never starts. Checked: ${cssEntries.map((entry) => entry.rel).join(", ")}.`
|
|
560
|
+
);
|
|
540
561
|
}
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
548
|
-
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
562
|
+
const tailwindConfigPath = findFile(cwd, TAILWIND_CONFIG_CANDIDATES);
|
|
563
|
+
if (tailwindConfigPath && !optsIntoJsConfig) {
|
|
564
|
+
const rel = tailwindConfigPath.slice(cwd.length + 1);
|
|
565
|
+
warn(
|
|
566
|
+
"tailwind-config-inert",
|
|
567
|
+
`${rel} exists but nothing opts into it \u2014 Tailwind 4 ignores a JS config unless a stylesheet declares \`@config\`. Anything it sets (theme, content/@source paths, plugins) has no effect today. Either delete it and move the settings into your CSS entry, or add \`@config '${rel}';\` there.`
|
|
568
|
+
);
|
|
569
|
+
} else if (tailwindConfigPath) {
|
|
570
|
+
ok("tailwind-config-active", "JS Tailwind config is loaded via `@config`");
|
|
571
|
+
}
|
|
572
|
+
}
|
|
573
|
+
if (existsSync6(join7(cwd, "tsconfig.json"))) {
|
|
574
|
+
ok("tsconfig-found", "tsconfig.json found");
|
|
575
|
+
const tsRange = deps.typescript;
|
|
576
|
+
if (tsRange) {
|
|
577
|
+
const major = majorOf(tsRange);
|
|
578
|
+
if (major !== null && major < 5) {
|
|
579
|
+
warn("typescript-legacy", `TypeScript ${tsRange} detected \u2014 version 5.0+ recommended`);
|
|
555
580
|
} else {
|
|
556
|
-
|
|
557
|
-
issues++;
|
|
581
|
+
ok("typescript-version", `TypeScript ${tsRange} (5.0+ required)`);
|
|
558
582
|
}
|
|
559
|
-
} catch (_e) {
|
|
560
583
|
}
|
|
561
584
|
} else {
|
|
562
|
-
|
|
563
|
-
issues++;
|
|
585
|
+
warn("tsconfig-missing", "tsconfig.json not found");
|
|
564
586
|
}
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
if (tsVer) {
|
|
572
|
-
const majorVer = parseInt(tsVer.replace(/[^0-9.]/g, "").split(".")[0], 10);
|
|
573
|
-
if (majorVer >= 5) {
|
|
574
|
-
console.log(chalk7.green(`\u2713 TypeScript ${tsVer} (5.0+ required)`));
|
|
575
|
-
} else {
|
|
576
|
-
console.log(chalk7.yellow(`\u26A0\uFE0F TypeScript ${tsVer} detected \u2014 version 5.0+ recommended`));
|
|
577
|
-
issues++;
|
|
578
|
-
}
|
|
579
|
-
}
|
|
580
|
-
} catch (_e) {
|
|
587
|
+
if (pkg) {
|
|
588
|
+
if (deps["@object-ui/react"] && !deps.react) {
|
|
589
|
+
warn("peer-react", "@object-ui/react requires react as a peer dependency");
|
|
590
|
+
}
|
|
591
|
+
if (deps["@object-ui/components"] && !deps.tailwindcss) {
|
|
592
|
+
warn("peer-tailwind", "@object-ui/components requires tailwindcss as a peer dependency");
|
|
581
593
|
}
|
|
582
|
-
} else {
|
|
583
|
-
console.log(chalk7.yellow("\u26A0\uFE0F tsconfig.json not found"));
|
|
584
|
-
issues++;
|
|
585
594
|
}
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
}
|
|
598
|
-
}
|
|
595
|
+
return results;
|
|
596
|
+
}
|
|
597
|
+
function countIssues(results) {
|
|
598
|
+
return results.filter((result) => result.level !== "ok").length;
|
|
599
|
+
}
|
|
600
|
+
async function doctor() {
|
|
601
|
+
console.log(chalk7.bold("Object UI Doctor"));
|
|
602
|
+
console.log("Diagnosis in progress...\n");
|
|
603
|
+
const results = runDiagnostics(process.cwd());
|
|
604
|
+
for (const result of results) {
|
|
605
|
+
if (result.level === "ok") {
|
|
606
|
+
console.log(chalk7.green(`\u2713 ${result.message}`));
|
|
607
|
+
} else if (result.level === "warn") {
|
|
608
|
+
console.log(chalk7.yellow(`\u26A0\uFE0F ${result.message}`));
|
|
609
|
+
} else {
|
|
610
|
+
console.log(chalk7.red(`x ${result.message}`));
|
|
599
611
|
}
|
|
600
612
|
}
|
|
613
|
+
const issues = countIssues(results);
|
|
601
614
|
console.log("\nResult:");
|
|
602
615
|
if (issues === 0) {
|
|
603
616
|
console.log(chalk7.green("Everything looks good! \u2728"));
|
|
@@ -617,8 +630,8 @@ async function add(component) {
|
|
|
617
630
|
// src/commands/studio.ts
|
|
618
631
|
import chalk9 from "chalk";
|
|
619
632
|
import { spawn } from "child_process";
|
|
620
|
-
import { existsSync as
|
|
621
|
-
import { join as join8, resolve as
|
|
633
|
+
import { existsSync as existsSync7 } from "fs";
|
|
634
|
+
import { join as join8, resolve as resolve3, dirname as dirname2 } from "path";
|
|
622
635
|
import { fileURLToPath } from "url";
|
|
623
636
|
async function studio() {
|
|
624
637
|
console.log(chalk9.bold("\n\u{1F3A8} Starting ObjectUI Studio...\n"));
|
|
@@ -627,12 +640,12 @@ async function studio() {
|
|
|
627
640
|
const __dirname3 = dirname2(__filename3);
|
|
628
641
|
const candidates = [
|
|
629
642
|
join8(cwd, "apps/console"),
|
|
630
|
-
|
|
631
|
-
|
|
643
|
+
resolve3(__dirname3, "../../apps/console"),
|
|
644
|
+
resolve3(__dirname3, "../../../apps/console")
|
|
632
645
|
];
|
|
633
646
|
let consolePath = null;
|
|
634
647
|
for (const candidate of candidates) {
|
|
635
|
-
if (
|
|
648
|
+
if (existsSync7(join8(candidate, "package.json"))) {
|
|
636
649
|
consolePath = candidate;
|
|
637
650
|
break;
|
|
638
651
|
}
|
|
@@ -664,41 +677,735 @@ import chalk10 from "chalk";
|
|
|
664
677
|
import { globSync } from "glob";
|
|
665
678
|
import { readFileSync as readFileSync2 } from "fs";
|
|
666
679
|
import { join as join9 } from "path";
|
|
667
|
-
|
|
680
|
+
import { parse as parseJsonc, printParseErrorCode } from "jsonc-parser";
|
|
681
|
+
|
|
682
|
+
// src/utils/known-schema-types.ts
|
|
683
|
+
var KNOWN_SCHEMA_TYPES = [
|
|
684
|
+
"a",
|
|
685
|
+
"abbr",
|
|
686
|
+
"accordion",
|
|
687
|
+
"action:bar",
|
|
688
|
+
"action:button",
|
|
689
|
+
"action:group",
|
|
690
|
+
"action:icon",
|
|
691
|
+
"action:menu",
|
|
692
|
+
"address",
|
|
693
|
+
"advanced-chart",
|
|
694
|
+
"ai-form-assist",
|
|
695
|
+
"ai-recommendations",
|
|
696
|
+
"ai:feedback",
|
|
697
|
+
"ai:input",
|
|
698
|
+
"ai:suggestion",
|
|
699
|
+
"alert",
|
|
700
|
+
"alert-dialog",
|
|
701
|
+
"app",
|
|
702
|
+
"app-creation-wizard",
|
|
703
|
+
"app-schema-renderer",
|
|
704
|
+
"app-shell:cloud-connection:panel",
|
|
705
|
+
"app-shell:cloud:ai-model-status",
|
|
706
|
+
"app-shell:cloud:onboarding-next",
|
|
707
|
+
"app-shell:marketplace:installed-list",
|
|
708
|
+
"app-shell:mcp:connect-agent",
|
|
709
|
+
"app:launcher",
|
|
710
|
+
"area-chart",
|
|
711
|
+
"article",
|
|
712
|
+
"aside",
|
|
713
|
+
"aspect-ratio",
|
|
714
|
+
"auto_number",
|
|
715
|
+
"avatar",
|
|
716
|
+
"b",
|
|
717
|
+
"badge",
|
|
718
|
+
"bar-chart",
|
|
719
|
+
"blockquote",
|
|
720
|
+
"boolean",
|
|
721
|
+
"br",
|
|
722
|
+
"branding-editor",
|
|
723
|
+
"breadcrumb",
|
|
724
|
+
"button",
|
|
725
|
+
"button-group",
|
|
726
|
+
"calendar",
|
|
727
|
+
"calendar-view",
|
|
728
|
+
"card",
|
|
729
|
+
"carousel",
|
|
730
|
+
"chart",
|
|
731
|
+
"chart:bar",
|
|
732
|
+
"chatbot",
|
|
733
|
+
"chatbot-enhanced",
|
|
734
|
+
"chatbot-floating",
|
|
735
|
+
"checkbox",
|
|
736
|
+
"checkboxes",
|
|
737
|
+
"cite",
|
|
738
|
+
"cloud-connection:panel",
|
|
739
|
+
"cloud:ai-model-status",
|
|
740
|
+
"cloud:onboarding-next",
|
|
741
|
+
"code",
|
|
742
|
+
"code-editor",
|
|
743
|
+
"collapsible",
|
|
744
|
+
"color",
|
|
745
|
+
"combobox",
|
|
746
|
+
"command",
|
|
747
|
+
"container",
|
|
748
|
+
"context-menu",
|
|
749
|
+
"currency",
|
|
750
|
+
"dashboard",
|
|
751
|
+
"dashboard-editor",
|
|
752
|
+
"dashboard-grid",
|
|
753
|
+
"data-model-designer",
|
|
754
|
+
"data-table",
|
|
755
|
+
"date",
|
|
756
|
+
"date-picker",
|
|
757
|
+
"datetime",
|
|
758
|
+
"dd",
|
|
759
|
+
"del",
|
|
760
|
+
"detail",
|
|
761
|
+
"detail-section",
|
|
762
|
+
"detail-view",
|
|
763
|
+
"dialog",
|
|
764
|
+
"div",
|
|
765
|
+
"dl",
|
|
766
|
+
"donut-chart",
|
|
767
|
+
"drawer",
|
|
768
|
+
"dropdown-menu",
|
|
769
|
+
"dt",
|
|
770
|
+
"element:button",
|
|
771
|
+
"element:definition-list",
|
|
772
|
+
"element:divider",
|
|
773
|
+
"element:image",
|
|
774
|
+
"element:metadata_viewer",
|
|
775
|
+
"element:number",
|
|
776
|
+
"element:record_picker",
|
|
777
|
+
"element:repeater",
|
|
778
|
+
"element:text",
|
|
779
|
+
"element:text_input",
|
|
780
|
+
"em",
|
|
781
|
+
"email",
|
|
782
|
+
"embeddable-form",
|
|
783
|
+
"empty",
|
|
784
|
+
"field-designer",
|
|
785
|
+
"field:address",
|
|
786
|
+
"field:audio",
|
|
787
|
+
"field:auto_number",
|
|
788
|
+
"field:avatar",
|
|
789
|
+
"field:boolean",
|
|
790
|
+
"field:checkboxes",
|
|
791
|
+
"field:code",
|
|
792
|
+
"field:color",
|
|
793
|
+
"field:currency",
|
|
794
|
+
"field:date",
|
|
795
|
+
"field:datetime",
|
|
796
|
+
"field:duration",
|
|
797
|
+
"field:email",
|
|
798
|
+
"field:file",
|
|
799
|
+
"field:filter-condition",
|
|
800
|
+
"field:formula",
|
|
801
|
+
"field:geolocation",
|
|
802
|
+
"field:grid",
|
|
803
|
+
"field:html",
|
|
804
|
+
"field:image",
|
|
805
|
+
"field:json",
|
|
806
|
+
"field:location",
|
|
807
|
+
"field:lookup",
|
|
808
|
+
"field:markdown",
|
|
809
|
+
"field:master_detail",
|
|
810
|
+
"field:multiselect",
|
|
811
|
+
"field:number",
|
|
812
|
+
"field:object",
|
|
813
|
+
"field:object-ref",
|
|
814
|
+
"field:password",
|
|
815
|
+
"field:percent",
|
|
816
|
+
"field:permission-facet-link",
|
|
817
|
+
"field:phone",
|
|
818
|
+
"field:progress",
|
|
819
|
+
"field:qrcode",
|
|
820
|
+
"field:radio",
|
|
821
|
+
"field:rating",
|
|
822
|
+
"field:recipient-picker",
|
|
823
|
+
"field:richtext",
|
|
824
|
+
"field:select",
|
|
825
|
+
"field:signature",
|
|
826
|
+
"field:slider",
|
|
827
|
+
"field:summary",
|
|
828
|
+
"field:tags",
|
|
829
|
+
"field:text",
|
|
830
|
+
"field:textarea",
|
|
831
|
+
"field:time",
|
|
832
|
+
"field:tree",
|
|
833
|
+
"field:url",
|
|
834
|
+
"field:user",
|
|
835
|
+
"field:vector",
|
|
836
|
+
"field:video",
|
|
837
|
+
"figcaption",
|
|
838
|
+
"figure",
|
|
839
|
+
"file",
|
|
840
|
+
"file-upload",
|
|
841
|
+
"filter-builder",
|
|
842
|
+
"filter-ui",
|
|
843
|
+
"flex",
|
|
844
|
+
"footer",
|
|
845
|
+
"form",
|
|
846
|
+
"form-analytics",
|
|
847
|
+
"formula",
|
|
848
|
+
"gantt",
|
|
849
|
+
"geolocation",
|
|
850
|
+
"global:notifications",
|
|
851
|
+
"global:search",
|
|
852
|
+
"grid",
|
|
853
|
+
"h1",
|
|
854
|
+
"h2",
|
|
855
|
+
"h3",
|
|
856
|
+
"h4",
|
|
857
|
+
"h5",
|
|
858
|
+
"h6",
|
|
859
|
+
"header",
|
|
860
|
+
"header-bar",
|
|
861
|
+
"home",
|
|
862
|
+
"hover-card",
|
|
863
|
+
"hr",
|
|
864
|
+
"html",
|
|
865
|
+
"i",
|
|
866
|
+
"icon",
|
|
867
|
+
"image",
|
|
868
|
+
"img",
|
|
869
|
+
"import-wizard",
|
|
870
|
+
"input",
|
|
871
|
+
"input-otp",
|
|
872
|
+
"ins",
|
|
873
|
+
"kanban",
|
|
874
|
+
"kanban-enhanced",
|
|
875
|
+
"kanban-ui",
|
|
876
|
+
"kbd",
|
|
877
|
+
"label",
|
|
878
|
+
"layout:app-schema-renderer",
|
|
879
|
+
"layout:navigation-renderer",
|
|
880
|
+
"layout:page-header",
|
|
881
|
+
"layout:page:card",
|
|
882
|
+
"layout:responsive-grid",
|
|
883
|
+
"li",
|
|
884
|
+
"line-chart",
|
|
885
|
+
"list",
|
|
886
|
+
"list-view",
|
|
887
|
+
"loading",
|
|
888
|
+
"location",
|
|
889
|
+
"lookup",
|
|
890
|
+
"main",
|
|
891
|
+
"map",
|
|
892
|
+
"mark",
|
|
893
|
+
"markdown",
|
|
894
|
+
"marketplace:installed-list",
|
|
895
|
+
"master_detail",
|
|
896
|
+
"mcp:connect-agent",
|
|
897
|
+
"menubar",
|
|
898
|
+
"metric",
|
|
899
|
+
"metric-card",
|
|
900
|
+
"multiselect",
|
|
901
|
+
"nav",
|
|
902
|
+
"nav:breadcrumb",
|
|
903
|
+
"nav:menu",
|
|
904
|
+
"navigation-designer",
|
|
905
|
+
"navigation-menu",
|
|
906
|
+
"navigation-renderer",
|
|
907
|
+
"nl-query",
|
|
908
|
+
"number",
|
|
909
|
+
"object",
|
|
910
|
+
"object-calendar",
|
|
911
|
+
"object-chart",
|
|
912
|
+
"object-data-table",
|
|
913
|
+
"object-form",
|
|
914
|
+
"object-gallery",
|
|
915
|
+
"object-gantt",
|
|
916
|
+
"object-grid",
|
|
917
|
+
"object-kanban",
|
|
918
|
+
"object-manager",
|
|
919
|
+
"object-map",
|
|
920
|
+
"object-master-detail-form",
|
|
921
|
+
"object-metric",
|
|
922
|
+
"object-pivot",
|
|
923
|
+
"object-timeline",
|
|
924
|
+
"object-tree",
|
|
925
|
+
"object-view",
|
|
926
|
+
"ol",
|
|
927
|
+
"p",
|
|
928
|
+
"page",
|
|
929
|
+
"page-designer",
|
|
930
|
+
"page-header",
|
|
931
|
+
"page:accordion",
|
|
932
|
+
"page:card",
|
|
933
|
+
"page:footer",
|
|
934
|
+
"page:header",
|
|
935
|
+
"page:section",
|
|
936
|
+
"page:sidebar",
|
|
937
|
+
"page:tabs",
|
|
938
|
+
"pagination",
|
|
939
|
+
"password",
|
|
940
|
+
"percent",
|
|
941
|
+
"phone",
|
|
942
|
+
"pie-chart",
|
|
943
|
+
"pivot",
|
|
944
|
+
"plugin-calendar:calendar-view",
|
|
945
|
+
"plugin-calendar:object-calendar",
|
|
946
|
+
"plugin-charts:advanced-chart",
|
|
947
|
+
"plugin-charts:area-chart",
|
|
948
|
+
"plugin-charts:bar-chart",
|
|
949
|
+
"plugin-charts:chart",
|
|
950
|
+
"plugin-charts:chart:bar",
|
|
951
|
+
"plugin-charts:donut-chart",
|
|
952
|
+
"plugin-charts:line-chart",
|
|
953
|
+
"plugin-charts:object-chart",
|
|
954
|
+
"plugin-charts:pie-chart",
|
|
955
|
+
"plugin-charts:radar-chart",
|
|
956
|
+
"plugin-charts:scatter-chart",
|
|
957
|
+
"plugin-chatbot:chatbot",
|
|
958
|
+
"plugin-chatbot:chatbot-enhanced",
|
|
959
|
+
"plugin-chatbot:chatbot-floating",
|
|
960
|
+
"plugin-dashboard:dashboard",
|
|
961
|
+
"plugin-dashboard:dashboard-grid",
|
|
962
|
+
"plugin-dashboard:metric",
|
|
963
|
+
"plugin-dashboard:metric-card",
|
|
964
|
+
"plugin-dashboard:object-data-table",
|
|
965
|
+
"plugin-dashboard:object-metric",
|
|
966
|
+
"plugin-dashboard:object-pivot",
|
|
967
|
+
"plugin-dashboard:pivot",
|
|
968
|
+
"plugin-designer:app-creation-wizard",
|
|
969
|
+
"plugin-designer:branding-editor",
|
|
970
|
+
"plugin-designer:dashboard-editor",
|
|
971
|
+
"plugin-designer:data-model-designer",
|
|
972
|
+
"plugin-designer:field-designer",
|
|
973
|
+
"plugin-designer:navigation-designer",
|
|
974
|
+
"plugin-designer:object-manager",
|
|
975
|
+
"plugin-designer:page-designer",
|
|
976
|
+
"plugin-designer:process-designer",
|
|
977
|
+
"plugin-designer:report-designer",
|
|
978
|
+
"plugin-detail:detail-section",
|
|
979
|
+
"plugin-detail:detail-view",
|
|
980
|
+
"plugin-detail:related-list",
|
|
981
|
+
"plugin-editor:code-editor",
|
|
982
|
+
"plugin-form:embeddable-form",
|
|
983
|
+
"plugin-form:form-analytics",
|
|
984
|
+
"plugin-form:object-form",
|
|
985
|
+
"plugin-form:object-master-detail-form",
|
|
986
|
+
"plugin-gantt:object-gantt",
|
|
987
|
+
"plugin-grid:import-wizard",
|
|
988
|
+
"plugin-grid:object-grid",
|
|
989
|
+
"plugin-kanban:kanban-enhanced",
|
|
990
|
+
"plugin-kanban:kanban-ui",
|
|
991
|
+
"plugin-kanban:object-kanban",
|
|
992
|
+
"plugin-list:list-view",
|
|
993
|
+
"plugin-list:object-gallery",
|
|
994
|
+
"plugin-map:object-map",
|
|
995
|
+
"plugin-markdown:markdown",
|
|
996
|
+
"plugin-report:report",
|
|
997
|
+
"plugin-report:report-viewer",
|
|
998
|
+
"plugin-report:spec-report",
|
|
999
|
+
"plugin-timeline:object-timeline",
|
|
1000
|
+
"plugin-timeline:timeline",
|
|
1001
|
+
"plugin-tree:object-tree",
|
|
1002
|
+
"plugin-view:object-view",
|
|
1003
|
+
"plugin-view:view",
|
|
1004
|
+
"plugin-view:view:simple",
|
|
1005
|
+
"popover",
|
|
1006
|
+
"pre",
|
|
1007
|
+
"process-designer",
|
|
1008
|
+
"progress",
|
|
1009
|
+
"protocol-placeholder:ai:feedback",
|
|
1010
|
+
"protocol-placeholder:ai:input",
|
|
1011
|
+
"protocol-placeholder:ai:suggestion",
|
|
1012
|
+
"protocol-placeholder:app:launcher",
|
|
1013
|
+
"protocol-placeholder:field:address",
|
|
1014
|
+
"protocol-placeholder:field:audio",
|
|
1015
|
+
"protocol-placeholder:field:avatar",
|
|
1016
|
+
"protocol-placeholder:field:boolean",
|
|
1017
|
+
"protocol-placeholder:field:checkboxes",
|
|
1018
|
+
"protocol-placeholder:field:code",
|
|
1019
|
+
"protocol-placeholder:field:color",
|
|
1020
|
+
"protocol-placeholder:field:currency",
|
|
1021
|
+
"protocol-placeholder:field:date",
|
|
1022
|
+
"protocol-placeholder:field:datetime",
|
|
1023
|
+
"protocol-placeholder:field:duration",
|
|
1024
|
+
"protocol-placeholder:field:email",
|
|
1025
|
+
"protocol-placeholder:field:file",
|
|
1026
|
+
"protocol-placeholder:field:html",
|
|
1027
|
+
"protocol-placeholder:field:image",
|
|
1028
|
+
"protocol-placeholder:field:json",
|
|
1029
|
+
"protocol-placeholder:field:location",
|
|
1030
|
+
"protocol-placeholder:field:lookup",
|
|
1031
|
+
"protocol-placeholder:field:markdown",
|
|
1032
|
+
"protocol-placeholder:field:master_detail",
|
|
1033
|
+
"protocol-placeholder:field:multiselect",
|
|
1034
|
+
"protocol-placeholder:field:number",
|
|
1035
|
+
"protocol-placeholder:field:password",
|
|
1036
|
+
"protocol-placeholder:field:percent",
|
|
1037
|
+
"protocol-placeholder:field:phone",
|
|
1038
|
+
"protocol-placeholder:field:progress",
|
|
1039
|
+
"protocol-placeholder:field:qrcode",
|
|
1040
|
+
"protocol-placeholder:field:radio",
|
|
1041
|
+
"protocol-placeholder:field:rating",
|
|
1042
|
+
"protocol-placeholder:field:select",
|
|
1043
|
+
"protocol-placeholder:field:signature",
|
|
1044
|
+
"protocol-placeholder:field:slider",
|
|
1045
|
+
"protocol-placeholder:field:text",
|
|
1046
|
+
"protocol-placeholder:field:textarea",
|
|
1047
|
+
"protocol-placeholder:field:time",
|
|
1048
|
+
"protocol-placeholder:field:tree",
|
|
1049
|
+
"protocol-placeholder:field:url",
|
|
1050
|
+
"protocol-placeholder:field:video",
|
|
1051
|
+
"protocol-placeholder:global:notifications",
|
|
1052
|
+
"protocol-placeholder:global:search",
|
|
1053
|
+
"protocol-placeholder:nav:breadcrumb",
|
|
1054
|
+
"protocol-placeholder:nav:menu",
|
|
1055
|
+
"protocol-placeholder:page-header",
|
|
1056
|
+
"protocol-placeholder:page:accordion",
|
|
1057
|
+
"protocol-placeholder:page:card",
|
|
1058
|
+
"protocol-placeholder:page:footer",
|
|
1059
|
+
"protocol-placeholder:page:header",
|
|
1060
|
+
"protocol-placeholder:page:sidebar",
|
|
1061
|
+
"protocol-placeholder:page:tabs",
|
|
1062
|
+
"protocol-placeholder:record:activity",
|
|
1063
|
+
"protocol-placeholder:record:chatter",
|
|
1064
|
+
"protocol-placeholder:record:details",
|
|
1065
|
+
"protocol-placeholder:record:highlights",
|
|
1066
|
+
"protocol-placeholder:record:path",
|
|
1067
|
+
"protocol-placeholder:record:related_list",
|
|
1068
|
+
"protocol-placeholder:user:profile",
|
|
1069
|
+
"protocol-placeholder:view:calendar",
|
|
1070
|
+
"protocol-placeholder:view:drawer",
|
|
1071
|
+
"protocol-placeholder:view:gallery",
|
|
1072
|
+
"protocol-placeholder:view:gantt",
|
|
1073
|
+
"protocol-placeholder:view:grid",
|
|
1074
|
+
"protocol-placeholder:view:kanban",
|
|
1075
|
+
"protocol-placeholder:view:map",
|
|
1076
|
+
"protocol-placeholder:view:modal",
|
|
1077
|
+
"protocol-placeholder:view:simple",
|
|
1078
|
+
"protocol-placeholder:view:split",
|
|
1079
|
+
"protocol-placeholder:view:tabbed",
|
|
1080
|
+
"protocol-placeholder:view:timeline",
|
|
1081
|
+
"protocol-placeholder:view:wizard",
|
|
1082
|
+
"protocol-placeholder:widget:bar",
|
|
1083
|
+
"protocol-placeholder:widget:funnel",
|
|
1084
|
+
"protocol-placeholder:widget:heatmap",
|
|
1085
|
+
"protocol-placeholder:widget:image",
|
|
1086
|
+
"protocol-placeholder:widget:line",
|
|
1087
|
+
"protocol-placeholder:widget:metric",
|
|
1088
|
+
"protocol-placeholder:widget:pie",
|
|
1089
|
+
"protocol-placeholder:widget:pivot",
|
|
1090
|
+
"protocol-placeholder:widget:radar",
|
|
1091
|
+
"protocol-placeholder:widget:scatter",
|
|
1092
|
+
"protocol-placeholder:widget:table",
|
|
1093
|
+
"protocol-placeholder:widget:text",
|
|
1094
|
+
"q",
|
|
1095
|
+
"qrcode",
|
|
1096
|
+
"radar-chart",
|
|
1097
|
+
"radio",
|
|
1098
|
+
"radio-group",
|
|
1099
|
+
"rating",
|
|
1100
|
+
"record",
|
|
1101
|
+
"record:activity",
|
|
1102
|
+
"record:alert",
|
|
1103
|
+
"record:approvals",
|
|
1104
|
+
"record:attachments",
|
|
1105
|
+
"record:chatter",
|
|
1106
|
+
"record:details",
|
|
1107
|
+
"record:discussion",
|
|
1108
|
+
"record:highlights",
|
|
1109
|
+
"record:history",
|
|
1110
|
+
"record:line_items",
|
|
1111
|
+
"record:path",
|
|
1112
|
+
"record:quick_actions",
|
|
1113
|
+
"record:reference_rail",
|
|
1114
|
+
"record:related_list",
|
|
1115
|
+
"related-list",
|
|
1116
|
+
"report",
|
|
1117
|
+
"report-designer",
|
|
1118
|
+
"report-viewer",
|
|
1119
|
+
"report:report",
|
|
1120
|
+
"report:report-viewer",
|
|
1121
|
+
"report:spec-report",
|
|
1122
|
+
"resizable",
|
|
1123
|
+
"responsive-grid",
|
|
1124
|
+
"richtext",
|
|
1125
|
+
"scatter-chart",
|
|
1126
|
+
"scroll-area",
|
|
1127
|
+
"section",
|
|
1128
|
+
"select",
|
|
1129
|
+
"separator",
|
|
1130
|
+
"shared-view-link",
|
|
1131
|
+
"sheet",
|
|
1132
|
+
"sidebar",
|
|
1133
|
+
"sidebar-content",
|
|
1134
|
+
"sidebar-footer",
|
|
1135
|
+
"sidebar-group",
|
|
1136
|
+
"sidebar-header",
|
|
1137
|
+
"sidebar-inset",
|
|
1138
|
+
"sidebar-menu",
|
|
1139
|
+
"sidebar-menu-button",
|
|
1140
|
+
"sidebar-menu-item",
|
|
1141
|
+
"sidebar-provider",
|
|
1142
|
+
"sidebar-trigger",
|
|
1143
|
+
"signature",
|
|
1144
|
+
"skeleton",
|
|
1145
|
+
"slider",
|
|
1146
|
+
"small",
|
|
1147
|
+
"sonner",
|
|
1148
|
+
"sort-ui",
|
|
1149
|
+
"span",
|
|
1150
|
+
"spec-report",
|
|
1151
|
+
"spinner",
|
|
1152
|
+
"stack",
|
|
1153
|
+
"statistic",
|
|
1154
|
+
"strong",
|
|
1155
|
+
"sub",
|
|
1156
|
+
"summary",
|
|
1157
|
+
"sup",
|
|
1158
|
+
"switch",
|
|
1159
|
+
"table",
|
|
1160
|
+
"tabs",
|
|
1161
|
+
"tags",
|
|
1162
|
+
"text",
|
|
1163
|
+
"textarea",
|
|
1164
|
+
"time",
|
|
1165
|
+
"timeline",
|
|
1166
|
+
"toast",
|
|
1167
|
+
"toaster",
|
|
1168
|
+
"toggle",
|
|
1169
|
+
"toggle-group",
|
|
1170
|
+
"tooltip",
|
|
1171
|
+
"tree",
|
|
1172
|
+
"tree-view",
|
|
1173
|
+
"u",
|
|
1174
|
+
"ui:a",
|
|
1175
|
+
"ui:abbr",
|
|
1176
|
+
"ui:accordion",
|
|
1177
|
+
"ui:address",
|
|
1178
|
+
"ui:alert",
|
|
1179
|
+
"ui:alert-dialog",
|
|
1180
|
+
"ui:article",
|
|
1181
|
+
"ui:aside",
|
|
1182
|
+
"ui:aspect-ratio",
|
|
1183
|
+
"ui:avatar",
|
|
1184
|
+
"ui:b",
|
|
1185
|
+
"ui:badge",
|
|
1186
|
+
"ui:blockquote",
|
|
1187
|
+
"ui:br",
|
|
1188
|
+
"ui:breadcrumb",
|
|
1189
|
+
"ui:button",
|
|
1190
|
+
"ui:button-group",
|
|
1191
|
+
"ui:calendar",
|
|
1192
|
+
"ui:card",
|
|
1193
|
+
"ui:carousel",
|
|
1194
|
+
"ui:checkbox",
|
|
1195
|
+
"ui:cite",
|
|
1196
|
+
"ui:collapsible",
|
|
1197
|
+
"ui:combobox",
|
|
1198
|
+
"ui:command",
|
|
1199
|
+
"ui:container",
|
|
1200
|
+
"ui:context-menu",
|
|
1201
|
+
"ui:data-table",
|
|
1202
|
+
"ui:date-picker",
|
|
1203
|
+
"ui:dd",
|
|
1204
|
+
"ui:del",
|
|
1205
|
+
"ui:dialog",
|
|
1206
|
+
"ui:div",
|
|
1207
|
+
"ui:dl",
|
|
1208
|
+
"ui:drawer",
|
|
1209
|
+
"ui:dropdown-menu",
|
|
1210
|
+
"ui:dt",
|
|
1211
|
+
"ui:em",
|
|
1212
|
+
"ui:email",
|
|
1213
|
+
"ui:empty",
|
|
1214
|
+
"ui:figcaption",
|
|
1215
|
+
"ui:figure",
|
|
1216
|
+
"ui:file-upload",
|
|
1217
|
+
"ui:filter-builder",
|
|
1218
|
+
"ui:flex",
|
|
1219
|
+
"ui:footer",
|
|
1220
|
+
"ui:grid",
|
|
1221
|
+
"ui:h1",
|
|
1222
|
+
"ui:h2",
|
|
1223
|
+
"ui:h3",
|
|
1224
|
+
"ui:h4",
|
|
1225
|
+
"ui:h5",
|
|
1226
|
+
"ui:h6",
|
|
1227
|
+
"ui:header",
|
|
1228
|
+
"ui:header-bar",
|
|
1229
|
+
"ui:hover-card",
|
|
1230
|
+
"ui:hr",
|
|
1231
|
+
"ui:html",
|
|
1232
|
+
"ui:i",
|
|
1233
|
+
"ui:icon",
|
|
1234
|
+
"ui:image",
|
|
1235
|
+
"ui:img",
|
|
1236
|
+
"ui:input",
|
|
1237
|
+
"ui:input-otp",
|
|
1238
|
+
"ui:ins",
|
|
1239
|
+
"ui:kbd",
|
|
1240
|
+
"ui:label",
|
|
1241
|
+
"ui:li",
|
|
1242
|
+
"ui:list",
|
|
1243
|
+
"ui:loading",
|
|
1244
|
+
"ui:main",
|
|
1245
|
+
"ui:mark",
|
|
1246
|
+
"ui:menubar",
|
|
1247
|
+
"ui:nav",
|
|
1248
|
+
"ui:navigation-menu",
|
|
1249
|
+
"ui:ol",
|
|
1250
|
+
"ui:p",
|
|
1251
|
+
"ui:pagination",
|
|
1252
|
+
"ui:password",
|
|
1253
|
+
"ui:popover",
|
|
1254
|
+
"ui:pre",
|
|
1255
|
+
"ui:progress",
|
|
1256
|
+
"ui:q",
|
|
1257
|
+
"ui:radio-group",
|
|
1258
|
+
"ui:resizable",
|
|
1259
|
+
"ui:scroll-area",
|
|
1260
|
+
"ui:section",
|
|
1261
|
+
"ui:select",
|
|
1262
|
+
"ui:separator",
|
|
1263
|
+
"ui:sheet",
|
|
1264
|
+
"ui:sidebar",
|
|
1265
|
+
"ui:sidebar-content",
|
|
1266
|
+
"ui:sidebar-footer",
|
|
1267
|
+
"ui:sidebar-group",
|
|
1268
|
+
"ui:sidebar-header",
|
|
1269
|
+
"ui:sidebar-inset",
|
|
1270
|
+
"ui:sidebar-menu",
|
|
1271
|
+
"ui:sidebar-menu-button",
|
|
1272
|
+
"ui:sidebar-menu-item",
|
|
1273
|
+
"ui:sidebar-provider",
|
|
1274
|
+
"ui:sidebar-trigger",
|
|
1275
|
+
"ui:skeleton",
|
|
1276
|
+
"ui:slider",
|
|
1277
|
+
"ui:small",
|
|
1278
|
+
"ui:sonner",
|
|
1279
|
+
"ui:span",
|
|
1280
|
+
"ui:spinner",
|
|
1281
|
+
"ui:stack",
|
|
1282
|
+
"ui:statistic",
|
|
1283
|
+
"ui:strong",
|
|
1284
|
+
"ui:sub",
|
|
1285
|
+
"ui:sup",
|
|
1286
|
+
"ui:switch",
|
|
1287
|
+
"ui:table",
|
|
1288
|
+
"ui:tabs",
|
|
1289
|
+
"ui:text",
|
|
1290
|
+
"ui:textarea",
|
|
1291
|
+
"ui:time",
|
|
1292
|
+
"ui:toast",
|
|
1293
|
+
"ui:toaster",
|
|
1294
|
+
"ui:toggle",
|
|
1295
|
+
"ui:toggle-group",
|
|
1296
|
+
"ui:tooltip",
|
|
1297
|
+
"ui:tree-view",
|
|
1298
|
+
"ui:u",
|
|
1299
|
+
"ui:ul",
|
|
1300
|
+
"ul",
|
|
1301
|
+
"url",
|
|
1302
|
+
"user",
|
|
1303
|
+
"user:profile",
|
|
1304
|
+
"utility",
|
|
1305
|
+
"vector",
|
|
1306
|
+
"view",
|
|
1307
|
+
"view-switcher",
|
|
1308
|
+
"view:calendar",
|
|
1309
|
+
"view:chart",
|
|
1310
|
+
"view:dashboard",
|
|
1311
|
+
"view:detail",
|
|
1312
|
+
"view:drawer",
|
|
1313
|
+
"view:filter-ui",
|
|
1314
|
+
"view:form",
|
|
1315
|
+
"view:gallery",
|
|
1316
|
+
"view:gantt",
|
|
1317
|
+
"view:grid",
|
|
1318
|
+
"view:kanban",
|
|
1319
|
+
"view:list",
|
|
1320
|
+
"view:map",
|
|
1321
|
+
"view:modal",
|
|
1322
|
+
"view:shared-view-link",
|
|
1323
|
+
"view:simple",
|
|
1324
|
+
"view:sort-ui",
|
|
1325
|
+
"view:split",
|
|
1326
|
+
"view:tabbed",
|
|
1327
|
+
"view:timeline",
|
|
1328
|
+
"view:tree",
|
|
1329
|
+
"view:view-switcher",
|
|
1330
|
+
"view:wizard",
|
|
1331
|
+
"widget:bar",
|
|
1332
|
+
"widget:funnel",
|
|
1333
|
+
"widget:heatmap",
|
|
1334
|
+
"widget:image",
|
|
1335
|
+
"widget:line",
|
|
1336
|
+
"widget:metric",
|
|
1337
|
+
"widget:pie",
|
|
1338
|
+
"widget:pivot",
|
|
1339
|
+
"widget:radar",
|
|
1340
|
+
"widget:scatter",
|
|
1341
|
+
"widget:table",
|
|
1342
|
+
"widget:text"
|
|
1343
|
+
];
|
|
1344
|
+
var KNOWN_SCHEMA_TYPE_SET = new Set(KNOWN_SCHEMA_TYPES);
|
|
1345
|
+
function isKnownSchemaType(type) {
|
|
1346
|
+
return KNOWN_SCHEMA_TYPE_SET.has(type);
|
|
1347
|
+
}
|
|
1348
|
+
|
|
1349
|
+
// src/commands/check.ts
|
|
1350
|
+
var OBJECTUI_STRUCTURAL_KEYS = [
|
|
1351
|
+
// Composition — the `children`/`body`-class keys the ruling names.
|
|
1352
|
+
"body",
|
|
1353
|
+
"children",
|
|
1354
|
+
// Presentation.
|
|
1355
|
+
"className",
|
|
1356
|
+
"style",
|
|
1357
|
+
"placeholder",
|
|
1358
|
+
// Conditional rendering and interaction state.
|
|
1359
|
+
"visible",
|
|
1360
|
+
"visibleWhen",
|
|
1361
|
+
"visibleOn",
|
|
1362
|
+
"hidden",
|
|
1363
|
+
"hiddenOn",
|
|
1364
|
+
"disabled",
|
|
1365
|
+
"disabledOn",
|
|
1366
|
+
// Test and accessibility handles.
|
|
1367
|
+
"testId",
|
|
1368
|
+
"ariaLabel"
|
|
1369
|
+
];
|
|
1370
|
+
function isObjectUiSchemaFile(content) {
|
|
1371
|
+
return OBJECTUI_STRUCTURAL_KEYS.some((key) => key in content);
|
|
1372
|
+
}
|
|
1373
|
+
function describeParseError(text, error) {
|
|
1374
|
+
const upTo = text.slice(0, error.offset);
|
|
1375
|
+
const line = upTo.split("\n").length;
|
|
1376
|
+
const column = error.offset - (upTo.lastIndexOf("\n") + 1) + 1;
|
|
1377
|
+
return `${printParseErrorCode(error.error)} at line ${line} column ${column}`;
|
|
1378
|
+
}
|
|
1379
|
+
async function check(cwd = process.cwd()) {
|
|
668
1380
|
console.log(chalk10.bold("Object UI Schema Check"));
|
|
669
|
-
const cwd = process.cwd();
|
|
670
1381
|
const files = globSync("**/*.{json,yaml,yml}", {
|
|
671
1382
|
cwd,
|
|
672
1383
|
ignore: ["node_modules/**", "dist/**", ".git/**"]
|
|
673
1384
|
});
|
|
674
1385
|
console.log(`Analyzing ${files.length} files...`);
|
|
675
1386
|
let errors = 0;
|
|
1387
|
+
let skipped = 0;
|
|
676
1388
|
for (const file of files) {
|
|
677
1389
|
try {
|
|
678
1390
|
if (file.endsWith(".json")) {
|
|
679
|
-
const
|
|
1391
|
+
const text = readFileSync2(join9(cwd, file), "utf-8");
|
|
1392
|
+
const parseErrors = [];
|
|
1393
|
+
const content = parseJsonc(text, parseErrors, { allowTrailingComma: true });
|
|
1394
|
+
if (parseErrors.length > 0) {
|
|
1395
|
+
const [first] = parseErrors;
|
|
1396
|
+
console.log(
|
|
1397
|
+
chalk10.red(`x Invalid JSON in ${file}: ${describeParseError(text, first)}`)
|
|
1398
|
+
);
|
|
1399
|
+
errors++;
|
|
1400
|
+
continue;
|
|
1401
|
+
}
|
|
680
1402
|
if (content && typeof content === "object" && content.type) {
|
|
681
|
-
|
|
682
|
-
|
|
683
|
-
|
|
684
|
-
|
|
685
|
-
|
|
686
|
-
|
|
687
|
-
"calendar",
|
|
688
|
-
"dashboard",
|
|
689
|
-
"chart",
|
|
690
|
-
"detail",
|
|
691
|
-
"list",
|
|
692
|
-
"timeline",
|
|
693
|
-
"gantt",
|
|
694
|
-
"map",
|
|
695
|
-
"gallery",
|
|
696
|
-
"object-view",
|
|
697
|
-
"detail-view",
|
|
698
|
-
"object-chart"
|
|
699
|
-
];
|
|
700
|
-
if (typeof content.type === "string" && !knownTypes.includes(content.type)) {
|
|
701
|
-
console.log(chalk10.yellow(`\u26A0\uFE0F Unknown schema type "${content.type}" in ${file}`));
|
|
1403
|
+
if (typeof content.type === "string") {
|
|
1404
|
+
if (!isObjectUiSchemaFile(content)) {
|
|
1405
|
+
skipped++;
|
|
1406
|
+
} else if (!isKnownSchemaType(content.type)) {
|
|
1407
|
+
console.log(chalk10.yellow(`\u26A0\uFE0F Unknown schema type "${content.type}" in ${file}`));
|
|
1408
|
+
}
|
|
702
1409
|
}
|
|
703
1410
|
}
|
|
704
1411
|
}
|
|
@@ -707,6 +1414,18 @@ async function check() {
|
|
|
707
1414
|
errors++;
|
|
708
1415
|
}
|
|
709
1416
|
}
|
|
1417
|
+
if (skipped > 0) {
|
|
1418
|
+
console.log(
|
|
1419
|
+
chalk10.dim(
|
|
1420
|
+
`Skipped ${skipped} file${skipped === 1 ? "" : "s"} with a root "type" and no ObjectUI schema marker.`
|
|
1421
|
+
)
|
|
1422
|
+
);
|
|
1423
|
+
console.log(
|
|
1424
|
+
chalk10.dim(
|
|
1425
|
+
` A file is checked when its root carries an ObjectUI structural key: ${OBJECTUI_STRUCTURAL_KEYS.join(", ")}.`
|
|
1426
|
+
)
|
|
1427
|
+
);
|
|
1428
|
+
}
|
|
710
1429
|
if (errors === 0) {
|
|
711
1430
|
console.log(chalk10.green("\u2713 All checks passed"));
|
|
712
1431
|
} else {
|
|
@@ -717,8 +1436,8 @@ async function check() {
|
|
|
717
1436
|
|
|
718
1437
|
// src/commands/validate.ts
|
|
719
1438
|
import chalk11 from "chalk";
|
|
720
|
-
import { readFileSync as readFileSync3, existsSync as
|
|
721
|
-
import { resolve as
|
|
1439
|
+
import { readFileSync as readFileSync3, existsSync as existsSync8 } from "fs";
|
|
1440
|
+
import { resolve as resolve4 } from "path";
|
|
722
1441
|
import { load as loadYaml } from "js-yaml";
|
|
723
1442
|
import { safeValidateSchema } from "@object-ui/types/zod";
|
|
724
1443
|
|
|
@@ -754,8 +1473,8 @@ function findSpecVocabularyFormFields(node, path = "") {
|
|
|
754
1473
|
// src/commands/validate.ts
|
|
755
1474
|
async function validate(schemaPath) {
|
|
756
1475
|
console.log(chalk11.blue("\u{1F50D} ObjectUI Schema Validator\n"));
|
|
757
|
-
const resolvedPath =
|
|
758
|
-
if (!
|
|
1476
|
+
const resolvedPath = resolve4(process.cwd(), schemaPath);
|
|
1477
|
+
if (!existsSync8(resolvedPath)) {
|
|
759
1478
|
console.error(chalk11.red(`\u2717 Error: Schema file not found: ${schemaPath}`));
|
|
760
1479
|
process.exit(1);
|
|
761
1480
|
}
|
|
@@ -846,17 +1565,17 @@ ${index + 1}. ${issue.message}`));
|
|
|
846
1565
|
// src/commands/create-plugin.ts
|
|
847
1566
|
import chalk12 from "chalk";
|
|
848
1567
|
import { spawn as spawn2 } from "child_process";
|
|
849
|
-
import { resolve as
|
|
1568
|
+
import { resolve as resolve5, dirname as dirname3 } from "path";
|
|
850
1569
|
import { fileURLToPath as fileURLToPath2 } from "url";
|
|
851
1570
|
var __filename = fileURLToPath2(import.meta.url);
|
|
852
1571
|
var __dirname = dirname3(__filename);
|
|
853
1572
|
async function createPlugin(pluginName) {
|
|
854
1573
|
console.log(chalk12.blue("\u{1F680} Creating ObjectUI plugin...\n"));
|
|
855
|
-
const createPluginScript =
|
|
1574
|
+
const createPluginScript = resolve5(
|
|
856
1575
|
__dirname,
|
|
857
1576
|
"../../../create-plugin/dist/index.js"
|
|
858
1577
|
);
|
|
859
|
-
return new Promise((
|
|
1578
|
+
return new Promise((resolve7, reject) => {
|
|
860
1579
|
const child = spawn2("node", [createPluginScript, pluginName], {
|
|
861
1580
|
stdio: "inherit",
|
|
862
1581
|
shell: true
|
|
@@ -867,7 +1586,7 @@ async function createPlugin(pluginName) {
|
|
|
867
1586
|
});
|
|
868
1587
|
child.on("exit", (code) => {
|
|
869
1588
|
if (code === 0) {
|
|
870
|
-
|
|
1589
|
+
resolve7();
|
|
871
1590
|
} else {
|
|
872
1591
|
reject(new Error(`create-plugin exited with code ${code}`));
|
|
873
1592
|
}
|
|
@@ -877,12 +1596,12 @@ async function createPlugin(pluginName) {
|
|
|
877
1596
|
|
|
878
1597
|
// src/commands/analyze.ts
|
|
879
1598
|
import chalk13 from "chalk";
|
|
880
|
-
import { existsSync as
|
|
881
|
-
import { resolve as
|
|
1599
|
+
import { existsSync as existsSync9, statSync, readdirSync } from "fs";
|
|
1600
|
+
import { resolve as resolve6, join as join10, extname } from "path";
|
|
882
1601
|
async function analyzeBundleSize() {
|
|
883
1602
|
console.log(chalk13.bold("\n\u{1F4E6} Bundle Size Analysis\n"));
|
|
884
|
-
const distDir =
|
|
885
|
-
if (!
|
|
1603
|
+
const distDir = resolve6(process.cwd(), "dist");
|
|
1604
|
+
if (!existsSync9(distDir)) {
|
|
886
1605
|
console.log(chalk13.yellow("\u26A0 No dist directory found. Run build first."));
|
|
887
1606
|
return;
|
|
888
1607
|
}
|
|
@@ -891,7 +1610,7 @@ async function analyzeBundleSize() {
|
|
|
891
1610
|
const items = readdirSync(dir);
|
|
892
1611
|
for (const item of items) {
|
|
893
1612
|
const fullPath = join10(dir, item);
|
|
894
|
-
const stat =
|
|
1613
|
+
const stat = statSync(fullPath);
|
|
895
1614
|
if (stat.isDirectory()) {
|
|
896
1615
|
scanDirectory(fullPath);
|
|
897
1616
|
} else {
|
|
@@ -981,7 +1700,7 @@ var packageJson = JSON.parse(
|
|
|
981
1700
|
);
|
|
982
1701
|
var program = new Command();
|
|
983
1702
|
program.name("objectui").description("CLI tool for Object UI - Build applications from JSON schemas").version(packageJson.version);
|
|
984
|
-
program.command("serve").description("Start a development server with your JSON/YAML schema").argument("[schema]", "Path to JSON/YAML schema file", "app.json").option("-p, --port <port>", "Port to run the server on", "3000").option("-h, --host <host>", "Host to bind the server to", "localhost").action(async (schema, options) => {
|
|
1703
|
+
program.command("serve").description("Start a development server with your JSON/YAML schema").argument("[schema]", "Path to JSON/YAML schema file, or a project / pages directory", "app.json").option("-p, --port <port>", "Port to run the server on", "3000").option("-h, --host <host>", "Host to bind the server to", "localhost").option("--no-open", "Do not open browser automatically").action(async (schema, options) => {
|
|
985
1704
|
try {
|
|
986
1705
|
await serve(schema, options);
|
|
987
1706
|
} catch (error) {
|
|
@@ -989,7 +1708,7 @@ program.command("serve").description("Start a development server with your JSON/
|
|
|
989
1708
|
process.exit(1);
|
|
990
1709
|
}
|
|
991
1710
|
});
|
|
992
|
-
program.command("dev").description("Start development server (alias for serve)").argument("[schema]", "Path to JSON/YAML schema file", "app.json").option("-p, --port <port>", "Port to run the server on", "3000").option("-h, --host <host>", "Host to bind the server to", "localhost").option("--no-open", "Do not open browser automatically").action(async (schema, options) => {
|
|
1711
|
+
program.command("dev").description("Start development server (alias for serve)").argument("[schema]", "Path to JSON/YAML schema file, or a project / pages directory", "app.json").option("-p, --port <port>", "Port to run the server on", "3000").option("-h, --host <host>", "Host to bind the server to", "localhost").option("--no-open", "Do not open browser automatically").action(async (schema, options) => {
|
|
993
1712
|
try {
|
|
994
1713
|
await dev(schema, options);
|
|
995
1714
|
} catch (error) {
|
|
@@ -997,7 +1716,7 @@ program.command("dev").description("Start development server (alias for serve)")
|
|
|
997
1716
|
process.exit(1);
|
|
998
1717
|
}
|
|
999
1718
|
});
|
|
1000
|
-
program.command("build").description("Build application for production").argument("[schema]", "Path to JSON/YAML schema file", "app.json").option("-o, --out-dir <dir>", "Output directory", "dist").option("--clean", "Clean output directory before build", false).action(async (schema, options) => {
|
|
1719
|
+
program.command("build").description("Build application for production").argument("[schema]", "Path to JSON/YAML schema file, or a project / pages directory", "app.json").option("-o, --out-dir <dir>", "Output directory", "dist").option("--clean", "Clean output directory before build", false).action(async (schema, options) => {
|
|
1001
1720
|
try {
|
|
1002
1721
|
await buildApp(schema, options);
|
|
1003
1722
|
} catch (error) {
|