forgeos 0.1.0-alpha.13 → 0.1.0-alpha.14
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/AGENTS.md +6 -5
- package/CHANGELOG.md +12 -0
- package/adapters/java/README.md +68 -0
- package/adapters/java/pom.xml +34 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Auth.java +20 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Diagnostic.java +16 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Entry.java +38 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/EntryKind.java +16 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/ErrorInfo.java +4 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Forge.java +94 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/ForgeCall.java +12 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/ForgeContext.java +11 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/ForgeHandler.java +8 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/ForgeHttpHandler.java +179 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/ForgeRegistry.java +121 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Json.java +14 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Manifest.java +14 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/RequestEnvelope.java +6 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/ResponseEnvelope.java +25 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Risk.java +18 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Schemas.java +36 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/Service.java +65 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/TransactionMode.java +18 -0
- package/adapters/java/src/main/java/dev/forgeos/adapter/TypedForgeHandler.java +6 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Auth.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Diagnostic.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Entry.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/EntryKind.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ErrorInfo.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Forge.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ForgeCall.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ForgeContext.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ForgeHandler.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ForgeHttpHandler.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ForgeRegistry$EntryOption.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ForgeRegistry$RegisteredEntry.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ForgeRegistry$RegistryOption.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ForgeRegistry.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Json.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Manifest.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/RequestEnvelope.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/ResponseEnvelope.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Risk.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Schemas.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/Service.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/TransactionMode.class +0 -0
- package/adapters/java/target/classes/dev/forgeos/adapter/TypedForgeHandler.class +0 -0
- package/adapters/java/target/forge-java-adapter-0.1.0-alpha.11.jar +0 -0
- package/adapters/java/target/maven-archiver/pom.properties +3 -0
- package/adapters/java/target/maven-status/maven-compiler-plugin/compile/default-compile/createdFiles.lst +23 -0
- package/adapters/java/target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst +20 -0
- package/adapters/java-spring-boot-starter/README.md +32 -0
- package/adapters/java-spring-boot-starter/pom.xml +36 -0
- package/adapters/java-spring-boot-starter/src/main/java/dev/forgeos/adapter/spring/ForgeCommand.java +22 -0
- package/adapters/java-spring-boot-starter/src/main/java/dev/forgeos/adapter/spring/ForgeExternalService.java +15 -0
- package/adapters/java-spring-boot-starter/src/main/java/dev/forgeos/adapter/spring/ForgeQuery.java +16 -0
- package/adapters/java-spring-boot-starter/src/main/java/dev/forgeos/adapter/spring/ForgeServiceBeanCondition.java +18 -0
- package/adapters/java-spring-boot-starter/src/main/java/dev/forgeos/adapter/spring/ForgeSpringAutoConfiguration.java +16 -0
- package/adapters/java-spring-boot-starter/src/main/java/dev/forgeos/adapter/spring/ForgeSpringRuntime.java +104 -0
- package/adapters/java-spring-boot-starter/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports +1 -0
- package/adapters/java-spring-boot-starter/target/classes/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports +1 -0
- package/adapters/java-spring-boot-starter/target/classes/dev/forgeos/adapter/spring/ForgeCommand.class +0 -0
- package/adapters/java-spring-boot-starter/target/classes/dev/forgeos/adapter/spring/ForgeExternalService.class +0 -0
- package/adapters/java-spring-boot-starter/target/classes/dev/forgeos/adapter/spring/ForgeQuery.class +0 -0
- package/adapters/java-spring-boot-starter/target/classes/dev/forgeos/adapter/spring/ForgeServiceBeanCondition.class +0 -0
- package/adapters/java-spring-boot-starter/target/classes/dev/forgeos/adapter/spring/ForgeSpringAutoConfiguration.class +0 -0
- package/adapters/java-spring-boot-starter/target/classes/dev/forgeos/adapter/spring/ForgeSpringRuntime.class +0 -0
- package/adapters/java-spring-boot-starter/target/forge-java-spring-boot-starter-0.1.0-alpha.11.jar +0 -0
- package/adapters/java-spring-boot-starter/target/maven-archiver/pom.properties +3 -0
- package/adapters/java-spring-boot-starter/target/maven-status/maven-compiler-plugin/compile/default-compile/createdFiles.lst +6 -0
- package/adapters/java-spring-boot-starter/target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst +6 -0
- package/docs/forge-protocol.md +33 -0
- package/examples/java-billing/pom.xml +52 -0
- package/examples/java-billing/src/main/java/dev/forgeos/examples/billing/CreateInvoiceInput.java +4 -0
- package/examples/java-billing/src/main/java/dev/forgeos/examples/billing/Invoice.java +11 -0
- package/examples/java-billing/src/main/java/dev/forgeos/examples/billing/Main.java +127 -0
- package/examples/java-billing/target/classes/dev/forgeos/examples/billing/CreateInvoiceInput.class +0 -0
- package/examples/java-billing/target/classes/dev/forgeos/examples/billing/Invoice.class +0 -0
- package/examples/java-billing/target/classes/dev/forgeos/examples/billing/Main$EmptyInput.class +0 -0
- package/examples/java-billing/target/classes/dev/forgeos/examples/billing/Main$Options.class +0 -0
- package/examples/java-billing/target/classes/dev/forgeos/examples/billing/Main.class +0 -0
- package/examples/java-billing/target/java-billing-0.1.0-alpha.11-all.jar +0 -0
- package/examples/java-billing/target/java-billing-0.1.0-alpha.11.jar +0 -0
- package/examples/java-billing/target/maven-archiver/pom.properties +3 -0
- package/examples/java-billing/target/maven-status/maven-compiler-plugin/compile/default-compile/createdFiles.lst +5 -0
- package/examples/java-billing/target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst +3 -0
- package/package.json +4 -1
- package/src/forge/_generated/actionSubscriptions.json +1 -1
- package/src/forge/_generated/actionSubscriptions.ts +3 -3
- package/src/forge/_generated/agentAdapterManifest.json +1 -1
- package/src/forge/_generated/agentAdapterManifest.ts +3 -3
- package/src/forge/_generated/agentContract.json +1 -1
- package/src/forge/_generated/agentContract.ts +1274 -7
- package/src/forge/_generated/agentQuickstart.md +1 -1
- package/src/forge/_generated/agentTools.json +1 -1
- package/src/forge/_generated/agentTools.md +1 -1
- package/src/forge/_generated/agentTools.ts +2 -2
- package/src/forge/_generated/aiContext.ts +1 -1
- package/src/forge/_generated/aiModels.ts +1 -1
- package/src/forge/_generated/aiProviders.ts +1 -1
- package/src/forge/_generated/aiRegistry.json +1 -1
- package/src/forge/_generated/aiRegistry.ts +3 -3
- package/src/forge/_generated/api.json +1 -1
- package/src/forge/_generated/api.ts +1 -1
- package/src/forge/_generated/appGraph.json +1 -1
- package/src/forge/_generated/appGraph.ts +107 -78
- package/src/forge/_generated/appMap.md +1 -1
- package/src/forge/_generated/artifactManifest.json +1 -1
- package/src/forge/_generated/artifactManifest.ts +2 -2
- package/src/forge/_generated/authClaims.ts +1 -1
- package/src/forge/_generated/authConfig.ts +1 -1
- package/src/forge/_generated/authContext.ts +1 -1
- package/src/forge/_generated/authRegistry.ts +1 -1
- package/src/forge/_generated/buildInfo.json +1 -1
- package/src/forge/_generated/buildInfo.ts +4 -4
- package/src/forge/_generated/capabilityMap.json +1 -1
- package/src/forge/_generated/capabilityMap.md +1 -1
- package/src/forge/_generated/capabilityMap.ts +2 -2
- package/src/forge/_generated/client.ts +1 -1
- package/src/forge/_generated/clientApi.ts +1 -1
- package/src/forge/_generated/clientManifest.json +1 -1
- package/src/forge/_generated/clientManifest.ts +14 -3
- package/src/forge/_generated/clientTypes.ts +1 -1
- package/src/forge/_generated/configRegistry.ts +1 -1
- package/src/forge/_generated/dataGraph.json +1 -1
- package/src/forge/_generated/dataGraph.ts +3 -3
- package/src/forge/_generated/db.ts +1 -1
- package/src/forge/_generated/dbSecurityManifest.ts +1 -1
- package/src/forge/_generated/dbSessionContext.ts +1 -1
- package/src/forge/_generated/deployManifest.json +1 -1
- package/src/forge/_generated/deployManifest.ts +7 -7
- package/src/forge/_generated/devManifest.json +1 -1
- package/src/forge/_generated/devManifest.ts +3 -3
- package/src/forge/_generated/envSchema.ts +1 -1
- package/src/forge/_generated/externalServices.ts +1 -1
- package/src/forge/_generated/frontendGraph.ts +1 -1
- package/src/forge/_generated/importGuards.json +1 -1
- package/src/forge/_generated/importGuards.ts +35 -1
- package/src/forge/_generated/index.ts +3 -1
- package/src/forge/_generated/liveProductionManifest.ts +1 -1
- package/src/forge/_generated/liveProtocol.ts +1 -1
- package/src/forge/_generated/liveQueryRegistry.json +1 -1
- package/src/forge/_generated/liveQueryRegistry.ts +3 -3
- package/src/forge/_generated/liveTransportConfig.ts +1 -1
- package/src/forge/_generated/makeRegistry.json +1 -1
- package/src/forge/_generated/makeRegistry.ts +8 -8
- package/src/forge/_generated/makeTemplates.json +1 -1
- package/src/forge/_generated/makeTemplates.ts +2 -2
- package/src/forge/_generated/mockMap.ts +1 -1
- package/src/forge/_generated/operationPlaybooks.md +6 -6
- package/src/forge/_generated/packageGraph.json +1 -1
- package/src/forge/_generated/packageGraph.ts +52412 -2
- package/src/forge/_generated/packageUpgradeRegistry.json +1 -1
- package/src/forge/_generated/packageUpgradeRegistry.ts +2 -2
- package/src/forge/_generated/permissionMatrix.json +1 -1
- package/src/forge/_generated/permissionMatrix.ts +3 -3
- package/src/forge/_generated/policyRegistry.json +1 -1
- package/src/forge/_generated/policyRegistry.ts +3 -3
- package/src/forge/_generated/queryRegistry.json +1 -1
- package/src/forge/_generated/queryRegistry.ts +3 -3
- package/src/forge/_generated/react.d.ts +1 -1
- package/src/forge/_generated/react.ts +1 -1
- package/src/forge/_generated/reactManifest.json +1 -1
- package/src/forge/_generated/reactManifest.ts +3 -3
- package/src/forge/_generated/releaseManifest.json +1 -1
- package/src/forge/_generated/releaseManifest.ts +3 -3
- package/src/forge/_generated/rlsPolicies.sql +1 -1
- package/src/forge/_generated/rlsPolicies.ts +1 -1
- package/src/forge/_generated/runtimeGraph.json +1 -1
- package/src/forge/_generated/runtimeGraph.ts +3 -3
- package/src/forge/_generated/runtimeMatrix.json +1 -1
- package/src/forge/_generated/runtimeMatrix.ts +70357 -1
- package/src/forge/_generated/runtimeRegistry.ts +1 -1
- package/src/forge/_generated/runtimeRules.md +1 -1
- package/src/forge/_generated/secretRegistry.ts +1 -1
- package/src/forge/_generated/secretsContext.ts +1 -1
- package/src/forge/_generated/serverApi.ts +1 -1
- package/src/forge/_generated/sourceMapManifest.json +1 -1
- package/src/forge/_generated/sourceMapManifest.ts +2 -2
- package/src/forge/_generated/sqlPlan.ts +1 -1
- package/src/forge/_generated/subscriptionManifest.json +1 -1
- package/src/forge/_generated/subscriptionManifest.ts +3 -3
- package/src/forge/_generated/symbolicationManifest.json +1 -1
- package/src/forge/_generated/symbolicationManifest.ts +2 -2
- package/src/forge/_generated/telemetryRegistry.json +1 -1
- package/src/forge/_generated/telemetryRegistry.ts +3 -3
- package/src/forge/_generated/telemetrySinks.json +1 -1
- package/src/forge/_generated/telemetrySinks.ts +2 -2
- package/src/forge/_generated/tenantScope.json +1 -1
- package/src/forge/_generated/tenantScope.ts +3 -3
- package/src/forge/_generated/testGraph.json +1 -1
- package/src/forge/_generated/testGraph.ts +71 -5
- package/src/forge/_generated/testPlanRegistry.json +1 -1
- package/src/forge/_generated/testPlanRegistry.ts +2 -2
- package/src/forge/_generated/uiRoutes.ts +1 -1
- package/src/forge/_generated/uiScenarios.ts +1 -1
- package/src/forge/_generated/uiTestManifest.json +1 -1
- package/src/forge/_generated/uiTestManifest.ts +2 -2
- package/src/forge/_generated/vue.d.ts +25 -0
- package/src/forge/_generated/vue.ts +30 -0
- package/src/forge/_generated/vueManifest.json +1 -0
- package/src/forge/_generated/vueManifest.ts +19 -0
- package/src/forge/_generated/workflowRegistry.json +1 -1
- package/src/forge/_generated/workflowRegistry.ts +3 -3
- package/src/forge/_generated/workflowSubscriptions.json +1 -1
- package/src/forge/_generated/workflowSubscriptions.ts +3 -3
- package/src/forge/agent-adapters/index.ts +1 -1
- package/src/forge/cli/parse.ts +1 -1
- package/src/forge/cli/verify.ts +2 -0
- package/src/forge/compiler/agent-contract/build.ts +10 -9
- package/src/forge/compiler/client-sdk/build-manifest.ts +55 -0
- package/src/forge/compiler/client-sdk/render-client.ts +66 -1
- package/src/forge/compiler/diagnostics/create.ts +6 -1
- package/src/forge/compiler/emitter/barrel.ts +3 -0
- package/src/forge/compiler/frontend-graph/build.ts +85 -13
- package/src/forge/compiler/make-registry/build.ts +6 -7
- package/src/forge/compiler/orchestrator/plan.ts +13 -0
- package/src/forge/compiler/orchestrator/serialize.ts +6 -0
- package/src/forge/compiler/types/frontend-graph.ts +2 -2
- package/src/forge/intent/index.ts +11 -6
- package/src/forge/make/index.ts +23 -3
- package/src/forge/make/templates.ts +153 -0
- package/src/forge/make/types.ts +2 -1
- package/src/forge/version.ts +1 -1
- package/src/forge/vue/index.ts +407 -0
|
@@ -13,6 +13,7 @@ import { createDiagnostic } from "../diagnostics/create.ts";
|
|
|
13
13
|
|
|
14
14
|
const WEB_ROOT = "web";
|
|
15
15
|
const API_URL_ENV = "NEXT_PUBLIC_FORGE_URL";
|
|
16
|
+
const NUXT_API_URL_ENV = "NUXT_PUBLIC_FORGE_URL";
|
|
16
17
|
const VITE_API_URL_ENV = "VITE_FORGE_URL";
|
|
17
18
|
|
|
18
19
|
function toPosix(path: string): string {
|
|
@@ -43,7 +44,7 @@ function walkFiles(root: string): string[] {
|
|
|
43
44
|
for (const entry of nodeFileSystem.readDir(dir)) {
|
|
44
45
|
const absolute = join(dir, entry.name);
|
|
45
46
|
if (entry.isDirectory) {
|
|
46
|
-
if (entry.name === "node_modules" || entry.name === ".next" || entry.name === "dist") {
|
|
47
|
+
if (entry.name === "node_modules" || entry.name === ".next" || entry.name === ".nuxt" || entry.name === "dist" || entry.name === ".output") {
|
|
47
48
|
continue;
|
|
48
49
|
}
|
|
49
50
|
walk(absolute);
|
|
@@ -71,6 +72,14 @@ function detectFramework(webRoot: string): FrontendGraph["framework"] {
|
|
|
71
72
|
if (deps.next || nodeFileSystem.exists(join(webRoot, "next.config.ts"))) {
|
|
72
73
|
return "next";
|
|
73
74
|
}
|
|
75
|
+
if (
|
|
76
|
+
deps.nuxt ||
|
|
77
|
+
nodeFileSystem.exists(join(webRoot, "nuxt.config.ts")) ||
|
|
78
|
+
nodeFileSystem.exists(join(webRoot, "nuxt.config.js")) ||
|
|
79
|
+
nodeFileSystem.exists(join(webRoot, "nuxt.config.mjs"))
|
|
80
|
+
) {
|
|
81
|
+
return "nuxt";
|
|
82
|
+
}
|
|
74
83
|
if (deps.vite || nodeFileSystem.exists(join(webRoot, "vite.config.ts"))) {
|
|
75
84
|
return "vite";
|
|
76
85
|
}
|
|
@@ -105,6 +114,27 @@ function routePathForFile(webRoot: string, file: string): string | null {
|
|
|
105
114
|
if (rel === "app/page.tsx" || rel === "app/page.ts" || rel === "app/page.jsx" || rel === "app/page.js") {
|
|
106
115
|
return "/";
|
|
107
116
|
}
|
|
117
|
+
if (rel === "app.vue") {
|
|
118
|
+
return "/";
|
|
119
|
+
}
|
|
120
|
+
if (rel === "pages/index.vue") {
|
|
121
|
+
return "/";
|
|
122
|
+
}
|
|
123
|
+
const vueRoute = rel.match(/^pages\/(.+)\.vue$/);
|
|
124
|
+
if (vueRoute) {
|
|
125
|
+
const route = vueRoute[1]
|
|
126
|
+
.split("/")
|
|
127
|
+
.map((segment) => {
|
|
128
|
+
if (segment === "index") {
|
|
129
|
+
return "";
|
|
130
|
+
}
|
|
131
|
+
const dynamic = segment.match(/^\[([A-Za-z0-9_]+)\]$/);
|
|
132
|
+
return dynamic ? `:${dynamic[1]}` : segment;
|
|
133
|
+
})
|
|
134
|
+
.filter(Boolean)
|
|
135
|
+
.join("/");
|
|
136
|
+
return `/${route}`;
|
|
137
|
+
}
|
|
108
138
|
const match = rel.match(/^app\/(.+)\/page\.(tsx|ts|jsx|js)$/);
|
|
109
139
|
if (match) {
|
|
110
140
|
const route = match[1]
|
|
@@ -117,7 +147,7 @@ function routePathForFile(webRoot: string, file: string): string | null {
|
|
|
117
147
|
}
|
|
118
148
|
|
|
119
149
|
function componentNameForFile(file: string): string {
|
|
120
|
-
return basename(file).replace(/\.(tsx|ts|jsx|js)$/, "");
|
|
150
|
+
return basename(file).replace(/\.(tsx|ts|jsx|js|vue)$/, "");
|
|
121
151
|
}
|
|
122
152
|
|
|
123
153
|
function componentNameForText(file: string, text: string): string {
|
|
@@ -134,6 +164,14 @@ function componentNameForText(file: string, text: string): string {
|
|
|
134
164
|
|
|
135
165
|
function isComponentFile(webRoot: string, file: string, text: string): boolean {
|
|
136
166
|
const rel = toPosix(relative(webRoot, file));
|
|
167
|
+
if (file.endsWith(".vue")) {
|
|
168
|
+
return (
|
|
169
|
+
rel === "app.vue" ||
|
|
170
|
+
rel.startsWith("components/") ||
|
|
171
|
+
rel.startsWith("src/components/") ||
|
|
172
|
+
rel.startsWith("pages/")
|
|
173
|
+
);
|
|
174
|
+
}
|
|
137
175
|
if (!/\.(tsx|jsx)$/.test(file)) {
|
|
138
176
|
return false;
|
|
139
177
|
}
|
|
@@ -206,6 +244,9 @@ function devCommandFor(webRoot: string, framework: FrontendGraph["framework"]):
|
|
|
206
244
|
}
|
|
207
245
|
|
|
208
246
|
function apiEnvFor(framework: FrontendGraph["framework"]): string {
|
|
247
|
+
if (framework === "nuxt") {
|
|
248
|
+
return NUXT_API_URL_ENV;
|
|
249
|
+
}
|
|
209
250
|
return framework === "vite" || framework === "static" ? VITE_API_URL_ENV : API_URL_ENV;
|
|
210
251
|
}
|
|
211
252
|
|
|
@@ -224,7 +265,7 @@ function stringProp(text: string, prop: "userId" | "tenantId" | "role"): string
|
|
|
224
265
|
}
|
|
225
266
|
|
|
226
267
|
function defaultWebPort(framework: FrontendGraph["framework"]): number {
|
|
227
|
-
return framework === "next" ? 3000 : 5173;
|
|
268
|
+
return framework === "next" || framework === "nuxt" ? 3000 : 5173;
|
|
228
269
|
}
|
|
229
270
|
|
|
230
271
|
function componentNamesInText(text: string, components: FrontendComponentInfo[]): string[] {
|
|
@@ -299,7 +340,7 @@ export function buildFrontendGraph(input: {
|
|
|
299
340
|
const defaultApiUrl = `http://127.0.0.1:${input.apiPort ?? 3765}`;
|
|
300
341
|
const devUrl = `http://127.0.0.1:${input.webPort ?? defaultWebPort(framework)}`;
|
|
301
342
|
const files = walkFiles(webRoot);
|
|
302
|
-
const sourceFiles = files.filter((file) => /\.(tsx|ts|jsx|js|html)$/.test(file));
|
|
343
|
+
const sourceFiles = files.filter((file) => /\.(tsx|ts|jsx|js|vue|html)$/.test(file));
|
|
303
344
|
const routes: FrontendRouteInfo[] = [];
|
|
304
345
|
const components: FrontendComponentInfo[] = [];
|
|
305
346
|
const providers: FrontendProviderInfo[] = [];
|
|
@@ -314,7 +355,9 @@ export function buildFrontendGraph(input: {
|
|
|
314
355
|
rel === "web/lib/forge.ts" ||
|
|
315
356
|
rel === "web/lib/forge.tsx" ||
|
|
316
357
|
rel === "web/src/lib/forge.ts" ||
|
|
317
|
-
rel === "web/src/lib/forge.tsx"
|
|
358
|
+
rel === "web/src/lib/forge.tsx" ||
|
|
359
|
+
rel === "web/composables/forge.ts" ||
|
|
360
|
+
rel === "web/plugins/forge.ts";
|
|
318
361
|
textByRel.set(rel, text);
|
|
319
362
|
const uses = detectUses(text, input.clientManifest);
|
|
320
363
|
if (isComponentFile(webRoot, file, text)) {
|
|
@@ -335,11 +378,32 @@ export function buildFrontendGraph(input: {
|
|
|
335
378
|
...(devAuth && stringProp(text, "role") ? { devAuthRole: stringProp(text, "role") } : {}),
|
|
336
379
|
});
|
|
337
380
|
}
|
|
381
|
+
if (
|
|
382
|
+
text.includes("provideForge({") ||
|
|
383
|
+
text.includes("vueApp.use(ForgeVuePlugin") ||
|
|
384
|
+
text.includes("app.use(ForgeVuePlugin")
|
|
385
|
+
) {
|
|
386
|
+
const devAuth =
|
|
387
|
+
text.includes("devAuth") ||
|
|
388
|
+
(text.includes("userId") && text.includes("tenantId") && text.includes("role"));
|
|
389
|
+
providers.push({
|
|
390
|
+
name: framework === "nuxt" ? "ForgeNuxtPlugin" : "ForgeVueProvider",
|
|
391
|
+
file: rel,
|
|
392
|
+
...(text.includes(NUXT_API_URL_ENV) ? { apiUrlEnv: NUXT_API_URL_ENV } : {}),
|
|
393
|
+
...(text.includes(VITE_API_URL_ENV) ? { apiUrlEnv: VITE_API_URL_ENV } : {}),
|
|
394
|
+
devAuth,
|
|
395
|
+
...(devAuth && stringProp(text, "userId") ? { devAuthUserId: stringProp(text, "userId") } : {}),
|
|
396
|
+
...(devAuth && stringProp(text, "tenantId") ? { devAuthTenantId: stringProp(text, "tenantId") } : {}),
|
|
397
|
+
...(devAuth && stringProp(text, "role") ? { devAuthRole: stringProp(text, "role") } : {}),
|
|
398
|
+
});
|
|
399
|
+
}
|
|
338
400
|
if (
|
|
339
401
|
rel === "web/lib/forge.ts" ||
|
|
340
402
|
rel === "web/lib/forge.tsx" ||
|
|
341
403
|
rel === "web/src/lib/forge.ts" ||
|
|
342
|
-
rel === "web/src/lib/forge.tsx"
|
|
404
|
+
rel === "web/src/lib/forge.tsx" ||
|
|
405
|
+
rel === "web/composables/forge.ts" ||
|
|
406
|
+
rel === "web/plugins/forge.ts"
|
|
343
407
|
) {
|
|
344
408
|
bridgeFiles.push(rel);
|
|
345
409
|
}
|
|
@@ -350,7 +414,7 @@ export function buildFrontendGraph(input: {
|
|
|
350
414
|
message: "frontend imports generated files directly; prefer the local web/lib/forge bridge",
|
|
351
415
|
file: rel,
|
|
352
416
|
fixHint: "Import generated client APIs through web/lib/forge.ts so agents and humans have one stable frontend bridge.",
|
|
353
|
-
suggestedCommands: ["forge inspect frontend --json",
|
|
417
|
+
suggestedCommands: ["forge inspect frontend --json", `forge make ui --framework ${framework === "nuxt" ? "nuxt" : "vite"} --dry-run --json`],
|
|
354
418
|
docs: ["src/forge/_generated/frontendGraph.json", "src/forge/_generated/appMap.md"],
|
|
355
419
|
}));
|
|
356
420
|
}
|
|
@@ -401,9 +465,13 @@ export function buildFrontendGraph(input: {
|
|
|
401
465
|
diagnostics.push(createDiagnostic({
|
|
402
466
|
severity: "warning",
|
|
403
467
|
code: "FORGE_FRONTEND_PROVIDER_MISSING",
|
|
404
|
-
message:
|
|
405
|
-
|
|
406
|
-
|
|
468
|
+
message: framework === "nuxt"
|
|
469
|
+
? "Nuxt app does not expose a Forge plugin; generated composables may not be wired"
|
|
470
|
+
: "web app does not expose a ForgeProvider; generated hooks may not be wired",
|
|
471
|
+
fixHint: framework === "nuxt"
|
|
472
|
+
? "Create web/plugins/forge.ts and call provideForge with runtimeConfig.public.forgeUrl and devAuth for local development."
|
|
473
|
+
: "Mount ForgeProvider once in the web app root/provider layer and pass devAuth for local development.",
|
|
474
|
+
suggestedCommands: ["forge inspect frontend --json", `forge make ui --framework ${framework === "nuxt" ? "nuxt" : "vite"} --dry-run --json`],
|
|
407
475
|
docs: ["src/forge/_generated/frontendGraph.json", "AGENTS.md"],
|
|
408
476
|
}));
|
|
409
477
|
}
|
|
@@ -411,9 +479,13 @@ export function buildFrontendGraph(input: {
|
|
|
411
479
|
diagnostics.push(createDiagnostic({
|
|
412
480
|
severity: "warning",
|
|
413
481
|
code: "FORGE_FRONTEND_BRIDGE_MISSING",
|
|
414
|
-
message:
|
|
415
|
-
|
|
416
|
-
|
|
482
|
+
message: framework === "nuxt"
|
|
483
|
+
? "web/composables/forge.ts bridge is missing; agents may use fragile generated import paths"
|
|
484
|
+
: "web/**/lib/forge.ts bridge is missing; agents may use fragile generated import paths",
|
|
485
|
+
fixHint: framework === "nuxt"
|
|
486
|
+
? "Create web/composables/forge.ts and re-export api plus generated Forge Vue composables from src/forge/_generated."
|
|
487
|
+
: "Create web/lib/forge.ts or web/src/lib/forge.ts and re-export api, client, ForgeProvider, and generated hooks from src/forge/_generated.",
|
|
488
|
+
suggestedCommands: [`forge make ui --framework ${framework === "nuxt" ? "nuxt" : "vite"} --dry-run --json`, "forge generate"],
|
|
417
489
|
docs: ["src/forge/_generated/frontendGraph.json", "AGENTS.md"],
|
|
418
490
|
}));
|
|
419
491
|
}
|
|
@@ -34,6 +34,7 @@ export function buildMakeRegistry(generatorVersion: string): MakeRegistryArtifac
|
|
|
34
34
|
"forge make list --json",
|
|
35
35
|
"forge make explain <primitive> --json",
|
|
36
36
|
"forge make ui --framework vite --dry-run --json",
|
|
37
|
+
"forge make ui --framework nuxt --dry-run --json",
|
|
37
38
|
"forge make ai-chat support --dry-run --json",
|
|
38
39
|
"forge make resource <name> --fields title:text,status:enum(open,closed) --dry-run --json",
|
|
39
40
|
"forge make resource <name> --fields title:text --with-ui --yes",
|
|
@@ -113,16 +114,14 @@ export function buildMakeRegistry(generatorVersion: string): MakeRegistryArtifac
|
|
|
113
114
|
},
|
|
114
115
|
{
|
|
115
116
|
name: "ui",
|
|
116
|
-
summary: "Add a Vite React frontend shell with
|
|
117
|
+
summary: "Add a Vite React or Nuxt Vue frontend shell with generated Forge client bindings.",
|
|
117
118
|
creates: [
|
|
118
119
|
"web/package.json",
|
|
119
|
-
"web/
|
|
120
|
-
"web/src/
|
|
121
|
-
"web/src/main.tsx",
|
|
122
|
-
"web/src/App.tsx",
|
|
120
|
+
"web/src/lib/forge.ts or web/composables/forge.ts",
|
|
121
|
+
"web/src/main.tsx or web/app.vue",
|
|
123
122
|
],
|
|
124
123
|
modifies: [],
|
|
125
|
-
examples: ["forge make ui --framework vite --yes"],
|
|
124
|
+
examples: ["forge make ui --framework vite --yes", "forge make ui --framework nuxt --yes"],
|
|
126
125
|
},
|
|
127
126
|
{
|
|
128
127
|
name: "ai-chat",
|
|
@@ -166,7 +165,7 @@ export function buildMakeTemplates(): MakeTemplateArtifact {
|
|
|
166
165
|
{ name: "workflow", sourceKind: "runtime", outputPattern: "src/workflows/<name>.ts" },
|
|
167
166
|
{ name: "component", sourceKind: "frontend", outputPattern: "web/components/<name>.tsx" },
|
|
168
167
|
{ name: "page", sourceKind: "frontend", outputPattern: "web/app/<route>/page.tsx" },
|
|
169
|
-
{ name: "ui", sourceKind: "frontend", outputPattern: "web/src/App.tsx" },
|
|
168
|
+
{ name: "ui", sourceKind: "frontend", outputPattern: "web/src/App.tsx or web/app.vue" },
|
|
170
169
|
{ name: "ai-chat", sourceKind: "frontend", outputPattern: "web/components/<name>AiChat.tsx" },
|
|
171
170
|
{ name: "placeholder-test", sourceKind: "test", outputPattern: "tests/make-generated/<name>.test.ts" },
|
|
172
171
|
],
|
|
@@ -35,6 +35,7 @@ import {
|
|
|
35
35
|
import {
|
|
36
36
|
buildClientManifest,
|
|
37
37
|
buildReactManifest,
|
|
38
|
+
buildVueManifest,
|
|
38
39
|
} from "../client-sdk/build-manifest.ts";
|
|
39
40
|
import {
|
|
40
41
|
buildFrontendGraph,
|
|
@@ -48,6 +49,9 @@ import {
|
|
|
48
49
|
renderReactDts,
|
|
49
50
|
renderReactManifestTs,
|
|
50
51
|
renderReactTs,
|
|
52
|
+
renderVueDts,
|
|
53
|
+
renderVueManifestTs,
|
|
54
|
+
renderVueTs,
|
|
51
55
|
} from "../client-sdk/render-client.ts";
|
|
52
56
|
import { buildSqlPlan } from "../data-graph/sql/ddl.ts";
|
|
53
57
|
import { buildRlsArtifacts } from "../data-graph/rls/build.ts";
|
|
@@ -204,6 +208,7 @@ import {
|
|
|
204
208
|
serializeClientApiTsExport,
|
|
205
209
|
serializeClientManifestJson,
|
|
206
210
|
serializeReactManifestJson,
|
|
211
|
+
serializeVueManifestJson,
|
|
207
212
|
buildMockMapEntries,
|
|
208
213
|
} from "./serialize.ts";
|
|
209
214
|
import { buildDefaultAuthRegistry, AUTH_ENV } from "../../runtime/auth/config.ts";
|
|
@@ -334,6 +339,7 @@ export function plan(input: PlanInput): EmitPlan {
|
|
|
334
339
|
);
|
|
335
340
|
const clientManifest = buildClientManifest(apiSurface, input.classified);
|
|
336
341
|
const reactManifest = buildReactManifest(clientManifest);
|
|
342
|
+
const vueManifest = buildVueManifest(clientManifest);
|
|
337
343
|
const frontendGraph = buildFrontendGraph({
|
|
338
344
|
workspaceRoot: input.ctx.workspaceRoot,
|
|
339
345
|
clientManifest,
|
|
@@ -884,6 +890,13 @@ export function plan(input: PlanInput): EmitPlan {
|
|
|
884
890
|
`${GENERATED_DIR}/reactManifest.json`,
|
|
885
891
|
serializeReactManifestJson(reactManifest),
|
|
886
892
|
),
|
|
893
|
+
makeEmitFile(`${GENERATED_DIR}/vue.ts`, renderVueTs()),
|
|
894
|
+
makeEmitFile(`${GENERATED_DIR}/vue.d.ts`, renderVueDts()),
|
|
895
|
+
makeEmitFile(`${GENERATED_DIR}/vueManifest.ts`, renderVueManifestTs(vueManifest)),
|
|
896
|
+
makeEmitFile(
|
|
897
|
+
`${GENERATED_DIR}/vueManifest.json`,
|
|
898
|
+
serializeVueManifestJson(vueManifest),
|
|
899
|
+
),
|
|
887
900
|
];
|
|
888
901
|
const fileRenderMs = performance.now() - checkpoint;
|
|
889
902
|
checkpoint = performance.now();
|
|
@@ -940,6 +940,12 @@ export function serializeReactManifestJson(
|
|
|
940
940
|
return serializeCanonical(manifest);
|
|
941
941
|
}
|
|
942
942
|
|
|
943
|
+
export function serializeVueManifestJson(
|
|
944
|
+
manifest: import("../client-sdk/build-manifest.ts").VueManifest,
|
|
945
|
+
): string {
|
|
946
|
+
return serializeCanonical(manifest);
|
|
947
|
+
}
|
|
948
|
+
|
|
943
949
|
export function serializeTestGraphJson(graph: TestGraph): string {
|
|
944
950
|
return serializeCanonical(graph);
|
|
945
951
|
}
|
|
@@ -31,7 +31,7 @@ export interface FrontendProviderInfo {
|
|
|
31
31
|
|
|
32
32
|
export interface FrontendWebManifest {
|
|
33
33
|
present: boolean;
|
|
34
|
-
framework: "next" | "vite" | "static" | "unknown" | "none";
|
|
34
|
+
framework: "next" | "nuxt" | "vite" | "static" | "unknown" | "none";
|
|
35
35
|
root?: string;
|
|
36
36
|
packageManager?: "bun" | "npm" | "pnpm" | "yarn" | "unknown";
|
|
37
37
|
scripts: {
|
|
@@ -63,7 +63,7 @@ export interface FrontendClientBindingInfo {
|
|
|
63
63
|
export interface FrontendGraph {
|
|
64
64
|
schemaVersion: "0.1.0";
|
|
65
65
|
present: boolean;
|
|
66
|
-
framework: "next" | "vite" | "static" | "unknown" | "none";
|
|
66
|
+
framework: "next" | "nuxt" | "vite" | "static" | "unknown" | "none";
|
|
67
67
|
root?: string;
|
|
68
68
|
dev?: {
|
|
69
69
|
command: string;
|
|
@@ -231,7 +231,7 @@ function planFor(input: {
|
|
|
231
231
|
}
|
|
232
232
|
case "connect-ui":
|
|
233
233
|
return {
|
|
234
|
-
summary: "Inspect and repair the web app bridge, provider, routes, and generated
|
|
234
|
+
summary: "Inspect and repair the web app bridge, provider/plugin, routes, and generated binding usage.",
|
|
235
235
|
plan: [
|
|
236
236
|
step(
|
|
237
237
|
"Read frontend graph",
|
|
@@ -242,20 +242,25 @@ function planFor(input: {
|
|
|
242
242
|
),
|
|
243
243
|
step(
|
|
244
244
|
"Create or repair UI bridge",
|
|
245
|
-
"Forge frontends should use the local bridge and hooks instead of fragile direct runtime fetches.",
|
|
246
|
-
[
|
|
247
|
-
|
|
248
|
-
|
|
245
|
+
"Forge frontends should use the local bridge and generated hooks/composables instead of fragile direct runtime fetches.",
|
|
246
|
+
[
|
|
247
|
+
"forge make ui --framework vite --dry-run --json",
|
|
248
|
+
"forge make ui --framework nuxt --dry-run --json",
|
|
249
|
+
"forge repair diagnose --diagnostic FORGE_FRONTEND_DIRECT_RUNTIME_FETCH --json",
|
|
250
|
+
],
|
|
251
|
+
["web/src/lib/forge.ts", "web/composables/forge.ts", "web/src/App.tsx", "web/app.vue", `${GENERATED_DIR}/frontendGraph.json`],
|
|
252
|
+
["ForgeProvider or Nuxt plugin is mounted when framework needs it", "generated hooks/composables replace raw endpoint fetches"],
|
|
249
253
|
),
|
|
250
254
|
],
|
|
251
255
|
commands: [
|
|
252
256
|
intentCommand("forge inspect frontend --json", "Inspect frontend wiring"),
|
|
253
257
|
intentCommand("forge dev --once --json", "Run the central diagnostic loop"),
|
|
254
258
|
intentCommand("forge make ui --framework vite --dry-run --json", "Preview adding a Forge-ready UI bridge", "after-review"),
|
|
259
|
+
intentCommand("forge make ui --framework nuxt --dry-run --json", "Preview adding a Forge-ready Nuxt UI bridge", "after-review"),
|
|
255
260
|
intentCommand("forge generate", "Refresh frontendGraph and agentContract", "after-editing"),
|
|
256
261
|
],
|
|
257
262
|
filesToInspect: files,
|
|
258
|
-
filesToChange: uniqueSorted(["web", "web/src/lib/forge.ts", "web/src/App.tsx"]),
|
|
263
|
+
filesToChange: uniqueSorted(["web", "web/src/lib/forge.ts", "web/composables/forge.ts", "web/src/App.tsx", "web/app.vue"]),
|
|
259
264
|
risks: [
|
|
260
265
|
risk("medium", "UI can appear to work while bypassing generated hooks.", "Treat frontendGraph diagnostics as blocking for agent handoff."),
|
|
261
266
|
],
|
package/src/forge/make/index.ts
CHANGED
|
@@ -21,6 +21,13 @@ import {
|
|
|
21
21
|
renderListQuery,
|
|
22
22
|
renderLiveQuery,
|
|
23
23
|
renderNextAiPackage,
|
|
24
|
+
renderNuxtApp,
|
|
25
|
+
renderNuxtConfig,
|
|
26
|
+
renderNuxtForgeComposable,
|
|
27
|
+
renderNuxtForgePlugin,
|
|
28
|
+
renderNuxtPackage,
|
|
29
|
+
renderNuxtStatusComponent,
|
|
30
|
+
renderNuxtTsconfig,
|
|
24
31
|
renderPage,
|
|
25
32
|
renderPlaceholderTest,
|
|
26
33
|
renderPolicyFile,
|
|
@@ -107,7 +114,7 @@ const EXPLANATIONS: Record<MakeIntent["kind"], string> = {
|
|
|
107
114
|
page:
|
|
108
115
|
"Adds a minimal app page under web/app/<route>/page.tsx.",
|
|
109
116
|
ui:
|
|
110
|
-
"Adds a minimal Vite React web app with
|
|
117
|
+
"Adds a minimal Vite React or Nuxt Vue web app with generated Forge client bindings.",
|
|
111
118
|
"ai-chat":
|
|
112
119
|
"Adds a Forge AI agent definition and a React chat component that calls the Forge /ai/agents/run runtime endpoint.",
|
|
113
120
|
resource:
|
|
@@ -513,7 +520,7 @@ function buildIntent(options: MakeCommandOptions): {
|
|
|
513
520
|
const kind = options.primitive as MakeIntent["kind"];
|
|
514
521
|
const fieldOptions = parseFieldOptions(options);
|
|
515
522
|
const diagnostics = [...fieldOptions.diagnostics];
|
|
516
|
-
if (options.framework && !["vite", "next"].includes(options.framework)) {
|
|
523
|
+
if (options.framework && !["vite", "next", "nuxt"].includes(options.framework)) {
|
|
517
524
|
diagnostics.push(
|
|
518
525
|
diagnostic("error", "FORGE_MAKE_PATCH_UNSAFE", `unsupported frontend framework '${options.framework}'`),
|
|
519
526
|
);
|
|
@@ -523,7 +530,7 @@ function buildIntent(options: MakeCommandOptions): {
|
|
|
523
530
|
diagnostic(
|
|
524
531
|
"warning",
|
|
525
532
|
"FORGE_MAKE_UI_FRAMEWORK_EXPERIMENTAL",
|
|
526
|
-
"forge make ui currently generates
|
|
533
|
+
"forge make ui currently generates Vite React and Nuxt Vue bridges; Next support should use the b2b-support-web template",
|
|
527
534
|
),
|
|
528
535
|
);
|
|
529
536
|
}
|
|
@@ -574,6 +581,7 @@ function buildIntent(options: MakeCommandOptions): {
|
|
|
574
581
|
trigger: options.trigger ?? options.event ?? (table ? `${singular}.created` : undefined),
|
|
575
582
|
component: options.component,
|
|
576
583
|
route: options.name ? kebabCase(options.name) : undefined,
|
|
584
|
+
framework: options.framework,
|
|
577
585
|
withAi: options.withAi || kind === "ai-chat",
|
|
578
586
|
withCreateForm: options.withCreateForm || kind === "resource",
|
|
579
587
|
},
|
|
@@ -794,6 +802,18 @@ function addFrontendFiles(plan: MakePlan, workspaceRoot: string, intent: MakeInt
|
|
|
794
802
|
return;
|
|
795
803
|
}
|
|
796
804
|
if (intent.kind === "ui") {
|
|
805
|
+
if (intent.framework === "nuxt") {
|
|
806
|
+
plan.filesToCreate.push(
|
|
807
|
+
createFile(workspaceRoot, "web/package.json", "Add Nuxt web package", renderNuxtPackage(intent.name)),
|
|
808
|
+
createFile(workspaceRoot, "web/nuxt.config.ts", "Add Nuxt runtime config", renderNuxtConfig()),
|
|
809
|
+
createFile(workspaceRoot, "web/tsconfig.json", "Add Nuxt TypeScript config", renderNuxtTsconfig()),
|
|
810
|
+
createFile(workspaceRoot, "web/composables/forge.ts", "Add Forge Vue composable bridge", renderNuxtForgeComposable()),
|
|
811
|
+
createFile(workspaceRoot, "web/plugins/forge.ts", "Add Forge Nuxt plugin", renderNuxtForgePlugin()),
|
|
812
|
+
createFile(workspaceRoot, "web/app.vue", "Add Nuxt app shell", renderNuxtApp()),
|
|
813
|
+
createFile(workspaceRoot, "web/components/ForgeStatus.vue", "Add Forge status component", renderNuxtStatusComponent()),
|
|
814
|
+
);
|
|
815
|
+
return;
|
|
816
|
+
}
|
|
797
817
|
plan.filesToCreate.push(
|
|
798
818
|
createFile(workspaceRoot, "web/package.json", "Add Vite React web package", renderVitePackage(intent.name)),
|
|
799
819
|
createFile(workspaceRoot, "web/tsconfig.json", "Add web TypeScript config", renderViteTsconfig()),
|
|
@@ -652,6 +652,159 @@ export function renderVitePackage(appName: string): string {
|
|
|
652
652
|
`;
|
|
653
653
|
}
|
|
654
654
|
|
|
655
|
+
export function renderNuxtPackage(appName: string): string {
|
|
656
|
+
return `{
|
|
657
|
+
"name": "${kebabCase(appName)}-web",
|
|
658
|
+
"private": true,
|
|
659
|
+
"type": "module",
|
|
660
|
+
"scripts": {
|
|
661
|
+
"dev": "nuxt dev --host 127.0.0.1",
|
|
662
|
+
"build": "nuxt build",
|
|
663
|
+
"typecheck": "nuxt typecheck"
|
|
664
|
+
},
|
|
665
|
+
"dependencies": {
|
|
666
|
+
"nuxt": "^4.0.0",
|
|
667
|
+
"vue": "^3.5.38"
|
|
668
|
+
},
|
|
669
|
+
"devDependencies": {
|
|
670
|
+
"typescript": "^5.7.3"
|
|
671
|
+
}
|
|
672
|
+
}
|
|
673
|
+
`;
|
|
674
|
+
}
|
|
675
|
+
|
|
676
|
+
export function renderNuxtConfig(): string {
|
|
677
|
+
return `export default defineNuxtConfig({
|
|
678
|
+
compatibilityDate: "2026-06-18",
|
|
679
|
+
runtimeConfig: {
|
|
680
|
+
public: {
|
|
681
|
+
forgeUrl: process.env.NUXT_PUBLIC_FORGE_URL ?? "http://127.0.0.1:3765",
|
|
682
|
+
},
|
|
683
|
+
},
|
|
684
|
+
typescript: {
|
|
685
|
+
strict: true,
|
|
686
|
+
},
|
|
687
|
+
});
|
|
688
|
+
`;
|
|
689
|
+
}
|
|
690
|
+
|
|
691
|
+
export function renderNuxtTsconfig(): string {
|
|
692
|
+
return `{
|
|
693
|
+
"extends": "./.nuxt/tsconfig.json"
|
|
694
|
+
}
|
|
695
|
+
`;
|
|
696
|
+
}
|
|
697
|
+
|
|
698
|
+
export function renderNuxtForgeComposable(): string {
|
|
699
|
+
return `export const forgeUrl = "http://127.0.0.1:3765";
|
|
700
|
+
|
|
701
|
+
export { api } from "../../src/forge/_generated/api";
|
|
702
|
+
export { createForgeClient, ForgeError } from "../../src/forge/_generated/client";
|
|
703
|
+
export {
|
|
704
|
+
ForgeVuePlugin,
|
|
705
|
+
provideForge,
|
|
706
|
+
useForgeAuth,
|
|
707
|
+
useForgeClient,
|
|
708
|
+
useForgeCommand,
|
|
709
|
+
useForgeLiveQuery,
|
|
710
|
+
useForgeQuery,
|
|
711
|
+
} from "../../src/forge/_generated/vue";
|
|
712
|
+
`;
|
|
713
|
+
}
|
|
714
|
+
|
|
715
|
+
export function renderNuxtForgePlugin(): string {
|
|
716
|
+
return `import { ForgeVuePlugin } from "../composables/forge";
|
|
717
|
+
|
|
718
|
+
export default defineNuxtPlugin((nuxtApp) => {
|
|
719
|
+
const config = useRuntimeConfig();
|
|
720
|
+
|
|
721
|
+
nuxtApp.vueApp.use(ForgeVuePlugin, {
|
|
722
|
+
url: String(config.public.forgeUrl),
|
|
723
|
+
devAuth: true,
|
|
724
|
+
});
|
|
725
|
+
});
|
|
726
|
+
`;
|
|
727
|
+
}
|
|
728
|
+
|
|
729
|
+
export function renderNuxtApp(): string {
|
|
730
|
+
return `<script setup lang="ts">
|
|
731
|
+
import ForgeStatus from "./components/ForgeStatus.vue";
|
|
732
|
+
</script>
|
|
733
|
+
|
|
734
|
+
<template>
|
|
735
|
+
<main class="shell">
|
|
736
|
+
<p class="eyebrow">ForgeOS Nuxt app</p>
|
|
737
|
+
<h1>Full-stack loop ready</h1>
|
|
738
|
+
<ForgeStatus />
|
|
739
|
+
</main>
|
|
740
|
+
</template>
|
|
741
|
+
|
|
742
|
+
<style scoped>
|
|
743
|
+
.shell {
|
|
744
|
+
width: min(760px, calc(100vw - 32px));
|
|
745
|
+
margin: 0 auto;
|
|
746
|
+
padding: 48px 0;
|
|
747
|
+
}
|
|
748
|
+
|
|
749
|
+
.eyebrow {
|
|
750
|
+
color: #58655f;
|
|
751
|
+
font-size: 0.82rem;
|
|
752
|
+
font-weight: 800;
|
|
753
|
+
text-transform: uppercase;
|
|
754
|
+
}
|
|
755
|
+
|
|
756
|
+
h1 {
|
|
757
|
+
margin: 0 0 12px;
|
|
758
|
+
color: #17211d;
|
|
759
|
+
font-size: 2.2rem;
|
|
760
|
+
}
|
|
761
|
+
</style>
|
|
762
|
+
`;
|
|
763
|
+
}
|
|
764
|
+
|
|
765
|
+
export function renderNuxtStatusComponent(): string {
|
|
766
|
+
return `<script setup lang="ts">
|
|
767
|
+
import { computed } from "vue";
|
|
768
|
+
import { useForgeAuth } from "../composables/forge";
|
|
769
|
+
|
|
770
|
+
const auth = useForgeAuth();
|
|
771
|
+
const tenantLabel = computed(() => auth?.tenantId ?? "dev-tenant");
|
|
772
|
+
const roleLabel = computed(() => auth?.role ?? "owner");
|
|
773
|
+
</script>
|
|
774
|
+
|
|
775
|
+
<template>
|
|
776
|
+
<section class="status-panel">
|
|
777
|
+
<span class="status-dot" aria-hidden="true" />
|
|
778
|
+
<p>
|
|
779
|
+
Connected as <strong>{{ roleLabel }}</strong> on
|
|
780
|
+
<strong>{{ tenantLabel }}</strong>.
|
|
781
|
+
</p>
|
|
782
|
+
</section>
|
|
783
|
+
</template>
|
|
784
|
+
|
|
785
|
+
<style scoped>
|
|
786
|
+
.status-panel {
|
|
787
|
+
display: flex;
|
|
788
|
+
align-items: center;
|
|
789
|
+
gap: 10px;
|
|
790
|
+
margin-top: 24px;
|
|
791
|
+
color: #26332d;
|
|
792
|
+
}
|
|
793
|
+
|
|
794
|
+
.status-dot {
|
|
795
|
+
width: 10px;
|
|
796
|
+
height: 10px;
|
|
797
|
+
border-radius: 999px;
|
|
798
|
+
background: #1f9d55;
|
|
799
|
+
}
|
|
800
|
+
|
|
801
|
+
p {
|
|
802
|
+
margin: 0;
|
|
803
|
+
}
|
|
804
|
+
</style>
|
|
805
|
+
`;
|
|
806
|
+
}
|
|
807
|
+
|
|
655
808
|
export function renderNextAiPackage(appName: string): string {
|
|
656
809
|
return `{
|
|
657
810
|
"name": "${kebabCase(appName)}-web",
|
package/src/forge/make/types.ts
CHANGED
|
@@ -61,6 +61,7 @@ export interface MakeIntent {
|
|
|
61
61
|
trigger?: string;
|
|
62
62
|
component?: string;
|
|
63
63
|
route?: string;
|
|
64
|
+
framework?: "vite" | "next" | "nuxt";
|
|
64
65
|
withAi: boolean;
|
|
65
66
|
withCreateForm: boolean;
|
|
66
67
|
}
|
|
@@ -130,7 +131,7 @@ export interface MakeCommandOptions {
|
|
|
130
131
|
event?: string;
|
|
131
132
|
trigger?: string;
|
|
132
133
|
component?: string;
|
|
133
|
-
framework?: "vite" | "next";
|
|
134
|
+
framework?: "vite" | "next" | "nuxt";
|
|
134
135
|
withAi: boolean;
|
|
135
136
|
withCrud: boolean;
|
|
136
137
|
withLiveQuery: boolean;
|
package/src/forge/version.ts
CHANGED