@mandujs/core 0.12.2 โ 0.13.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/README.ko.md +304 -304
- package/README.md +653 -653
- package/package.json +1 -1
- package/src/brain/architecture/analyzer.ts +28 -26
- package/src/brain/doctor/analyzer.ts +1 -1
- package/src/bundler/build.ts +91 -91
- package/src/bundler/css.ts +302 -302
- package/src/bundler/dev.ts +0 -1
- package/src/change/history.ts +3 -3
- package/src/change/snapshot.ts +10 -9
- package/src/change/transaction.ts +2 -2
- package/src/client/Link.tsx +227 -227
- package/src/client/globals.ts +44 -44
- package/src/client/hooks.ts +267 -267
- package/src/client/index.ts +5 -5
- package/src/client/island.ts +8 -8
- package/src/client/router.ts +435 -435
- package/src/client/runtime.ts +23 -23
- package/src/client/serialize.ts +404 -404
- package/src/client/window-state.ts +101 -101
- package/src/config/mandu.ts +94 -96
- package/src/config/validate.ts +213 -215
- package/src/config/watcher.ts +311 -311
- package/src/constants.ts +40 -40
- package/src/content/content-layer.ts +314 -314
- package/src/content/content.test.ts +433 -433
- package/src/content/data-store.ts +245 -245
- package/src/content/digest.ts +133 -133
- package/src/content/index.ts +164 -164
- package/src/content/loader-context.ts +172 -172
- package/src/content/loaders/api.ts +216 -216
- package/src/content/loaders/file.ts +169 -169
- package/src/content/loaders/glob.ts +252 -252
- package/src/content/loaders/index.ts +34 -34
- package/src/content/loaders/types.ts +137 -137
- package/src/content/meta-store.ts +209 -209
- package/src/content/types.ts +282 -282
- package/src/content/watcher.ts +135 -135
- package/src/contract/client-safe.test.ts +42 -42
- package/src/contract/client-safe.ts +114 -114
- package/src/contract/client.ts +16 -16
- package/src/contract/define.ts +459 -459
- package/src/contract/handler.ts +10 -10
- package/src/contract/normalize.test.ts +276 -276
- package/src/contract/normalize.ts +404 -404
- package/src/contract/registry.test.ts +206 -206
- package/src/contract/registry.ts +568 -568
- package/src/contract/schema.ts +48 -48
- package/src/contract/types.ts +58 -58
- package/src/contract/validator.ts +32 -32
- package/src/devtools/ai/context-builder.ts +375 -375
- package/src/devtools/ai/index.ts +25 -25
- package/src/devtools/ai/mcp-connector.ts +465 -465
- package/src/devtools/client/catchers/error-catcher.ts +327 -327
- package/src/devtools/client/catchers/index.ts +18 -18
- package/src/devtools/client/catchers/network-proxy.ts +363 -363
- package/src/devtools/client/components/index.ts +39 -39
- package/src/devtools/client/components/kitchen-root.tsx +362 -362
- package/src/devtools/client/components/mandu-character.tsx +241 -241
- package/src/devtools/client/components/overlay.tsx +368 -368
- package/src/devtools/client/components/panel/errors-panel.tsx +259 -259
- package/src/devtools/client/components/panel/guard-panel.tsx +244 -244
- package/src/devtools/client/components/panel/index.ts +32 -32
- package/src/devtools/client/components/panel/islands-panel.tsx +304 -304
- package/src/devtools/client/components/panel/network-panel.tsx +292 -292
- package/src/devtools/client/components/panel/panel-container.tsx +259 -259
- package/src/devtools/client/filters/context-filters.ts +282 -282
- package/src/devtools/client/filters/index.ts +16 -16
- package/src/devtools/client/index.ts +63 -63
- package/src/devtools/client/persistence.ts +335 -335
- package/src/devtools/client/state-manager.ts +478 -478
- package/src/devtools/design-tokens.ts +263 -263
- package/src/devtools/hook/create-hook.ts +207 -207
- package/src/devtools/hook/index.ts +13 -13
- package/src/devtools/index.ts +439 -439
- package/src/devtools/init.ts +266 -266
- package/src/devtools/protocol.ts +237 -237
- package/src/devtools/server/index.ts +17 -17
- package/src/devtools/server/source-context.ts +444 -444
- package/src/devtools/types.ts +319 -319
- package/src/devtools/worker/index.ts +25 -25
- package/src/devtools/worker/redaction-worker.ts +222 -222
- package/src/devtools/worker/worker-manager.ts +409 -409
- package/src/error/classifier.ts +2 -2
- package/src/error/domains.ts +265 -265
- package/src/error/formatter.ts +32 -32
- package/src/error/result.ts +46 -46
- package/src/error/stack-analyzer.ts +5 -0
- package/src/error/types.ts +6 -6
- package/src/errors/extractor.ts +409 -409
- package/src/errors/index.ts +19 -19
- package/src/filling/auth.ts +308 -308
- package/src/filling/context.ts +569 -569
- package/src/filling/deps.ts +238 -238
- package/src/generator/contract-glue.ts +2 -1
- package/src/generator/generate.ts +12 -10
- package/src/generator/index.ts +3 -3
- package/src/generator/templates.ts +80 -79
- package/src/guard/analyzer.ts +360 -360
- package/src/guard/ast-analyzer.ts +806 -806
- package/src/guard/auto-correct.ts +1 -1
- package/src/guard/check.ts +128 -128
- package/src/guard/contract-guard.ts +9 -9
- package/src/guard/file-type.test.ts +24 -24
- package/src/guard/presets/atomic.ts +70 -70
- package/src/guard/presets/clean.ts +77 -77
- package/src/guard/presets/cqrs.test.ts +35 -14
- package/src/guard/presets/fsd.ts +79 -79
- package/src/guard/presets/hexagonal.ts +68 -68
- package/src/guard/presets/index.ts +291 -291
- package/src/guard/reporter.ts +445 -445
- package/src/guard/rules.ts +12 -12
- package/src/guard/statistics.ts +578 -578
- package/src/guard/suggestions.ts +358 -358
- package/src/guard/types.ts +348 -348
- package/src/guard/validator.ts +834 -834
- package/src/guard/watcher.ts +404 -404
- package/src/index.ts +1 -0
- package/src/intent/index.ts +310 -310
- package/src/island/index.ts +304 -304
- package/src/logging/index.ts +22 -22
- package/src/logging/transports.ts +365 -365
- package/src/paths.test.ts +47 -0
- package/src/paths.ts +47 -0
- package/src/plugins/index.ts +38 -38
- package/src/plugins/registry.ts +377 -377
- package/src/plugins/types.ts +363 -363
- package/src/report/build.ts +1 -1
- package/src/report/index.ts +1 -1
- package/src/router/fs-patterns.ts +387 -387
- package/src/router/fs-routes.ts +344 -401
- package/src/router/fs-scanner.ts +497 -497
- package/src/router/fs-types.ts +270 -278
- package/src/router/index.ts +81 -81
- package/src/runtime/boundary.tsx +232 -232
- package/src/runtime/compose.ts +222 -222
- package/src/runtime/lifecycle.ts +381 -381
- package/src/runtime/logger.test.ts +345 -345
- package/src/runtime/logger.ts +677 -677
- package/src/runtime/router.test.ts +476 -476
- package/src/runtime/router.ts +105 -105
- package/src/runtime/security.ts +155 -155
- package/src/runtime/server.ts +24 -24
- package/src/runtime/session-key.ts +328 -328
- package/src/runtime/ssr.ts +367 -367
- package/src/runtime/streaming-ssr.ts +1245 -1245
- package/src/runtime/trace.ts +144 -144
- package/src/seo/index.ts +214 -214
- package/src/seo/integration/ssr.ts +307 -307
- package/src/seo/render/basic.ts +427 -427
- package/src/seo/render/index.ts +143 -143
- package/src/seo/render/jsonld.ts +539 -539
- package/src/seo/render/opengraph.ts +191 -191
- package/src/seo/render/robots.ts +116 -116
- package/src/seo/render/sitemap.ts +137 -137
- package/src/seo/render/twitter.ts +126 -126
- package/src/seo/resolve/index.ts +353 -353
- package/src/seo/resolve/opengraph.ts +143 -143
- package/src/seo/resolve/robots.ts +73 -73
- package/src/seo/resolve/title.ts +94 -94
- package/src/seo/resolve/twitter.ts +73 -73
- package/src/seo/resolve/url.ts +97 -97
- package/src/seo/routes/index.ts +290 -290
- package/src/seo/types.ts +575 -575
- package/src/slot/validator.ts +39 -39
- package/src/spec/index.ts +3 -3
- package/src/spec/load.ts +76 -76
- package/src/spec/lock.ts +56 -56
- package/src/utils/bun.ts +8 -8
- package/src/utils/lru-cache.ts +75 -75
- package/src/utils/safe-io.ts +188 -188
- package/src/utils/string-safe.ts +298 -298
- package/src/watcher/rules.ts +5 -5
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import type { RouteSpec } from "../spec/schema";
|
|
2
|
+
import { GENERATED_RELATIVE_PATHS } from "../paths";
|
|
2
3
|
|
|
3
4
|
export function generateApiHandler(route: RouteSpec): string {
|
|
4
5
|
// contractModule + slotModule์ด ์์ผ๋ฉด contract ๊ฒ์ฆ ๋ฒ์ ์์ฑ
|
|
@@ -29,7 +30,7 @@ export default function handler(req: Request, params: Record<string, string>): R
|
|
|
29
30
|
}
|
|
30
31
|
|
|
31
32
|
export function generateApiHandlerWithSlot(route: RouteSpec): string {
|
|
32
|
-
const slotImportPath = computeSlotImportPath(route.slotModule!,
|
|
33
|
+
const slotImportPath = computeSlotImportPath(route.slotModule!, GENERATED_RELATIVE_PATHS.serverRoutes);
|
|
33
34
|
|
|
34
35
|
return `// Generated by Mandu - DO NOT EDIT DIRECTLY
|
|
35
36
|
// Route ID: ${route.id}
|
|
@@ -49,8 +50,8 @@ export default async function handler(
|
|
|
49
50
|
}
|
|
50
51
|
|
|
51
52
|
export function generateApiHandlerWithContract(route: RouteSpec): string {
|
|
52
|
-
const slotImportPath = computeSlotImportPath(route.slotModule!,
|
|
53
|
-
const contractImportPath = computeSlotImportPath(route.contractModule!,
|
|
53
|
+
const slotImportPath = computeSlotImportPath(route.slotModule!, GENERATED_RELATIVE_PATHS.serverRoutes);
|
|
54
|
+
const contractImportPath = computeSlotImportPath(route.contractModule!, GENERATED_RELATIVE_PATHS.serverRoutes);
|
|
54
55
|
|
|
55
56
|
return `// Generated by Mandu - DO NOT EDIT DIRECTLY
|
|
56
57
|
// Route ID: ${route.id}
|
|
@@ -110,14 +111,14 @@ export default async function handler(
|
|
|
110
111
|
`;
|
|
111
112
|
}
|
|
112
113
|
|
|
113
|
-
export function generateSlotLogic(route: RouteSpec): string {
|
|
114
|
-
if (route.contractModule) {
|
|
115
|
-
return generateSlotLogicWithContract(route);
|
|
116
|
-
}
|
|
117
|
-
|
|
118
|
-
return `// ๐ฅ Mandu Filling - ${route.id}
|
|
119
|
-
// Pattern: ${route.pattern}
|
|
120
|
-
// ์ด ํ์ผ์์ ๋น์ฆ๋์ค ๋ก์ง์ ๊ตฌํํ์ธ์.
|
|
114
|
+
export function generateSlotLogic(route: RouteSpec): string {
|
|
115
|
+
if (route.contractModule) {
|
|
116
|
+
return generateSlotLogicWithContract(route);
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
return `// ๐ฅ Mandu Filling - ${route.id}
|
|
120
|
+
// Pattern: ${route.pattern}
|
|
121
|
+
// ์ด ํ์ผ์์ ๋น์ฆ๋์ค ๋ก์ง์ ๊ตฌํํ์ธ์.
|
|
121
122
|
|
|
122
123
|
import { Mandu } from "@mandujs/core";
|
|
123
124
|
|
|
@@ -149,67 +150,67 @@ export default Mandu.filling()
|
|
|
149
150
|
// ๐ก Context (ctx) API:
|
|
150
151
|
// ctx.query - Query parameters { name: 'value' }
|
|
151
152
|
// ctx.params - Path parameters { id: '123' }
|
|
152
|
-
// ctx.body() - Request body (์๋ ํ์ฑ)
|
|
153
|
-
// ctx.body(zodSchema) - Body with validation
|
|
154
|
-
// ctx.headers - Request headers
|
|
155
|
-
// ctx.ok(data) - 200 OK
|
|
156
|
-
// ctx.created(data) - 201 Created
|
|
157
|
-
// ctx.error(msg) - 400 Bad Request
|
|
158
|
-
// ctx.notFound(msg) - 404 Not Found
|
|
159
|
-
// ctx.set(key, value) - Guard์์ Handler๋ก ๋ฐ์ดํฐ ์ ๋ฌ
|
|
160
|
-
// ctx.get(key) - Guard์์ ์ค์ ํ ๋ฐ์ดํฐ ์ฝ๊ธฐ
|
|
161
|
-
`;
|
|
162
|
-
}
|
|
163
|
-
|
|
164
|
-
export function generateSlotLogicWithContract(route: RouteSpec): string {
|
|
165
|
-
const contractImportPath = computeSlotImportPath(
|
|
166
|
-
route.contractModule!,
|
|
167
|
-
pathDirname(route.slotModule ?? "spec/slots")
|
|
168
|
-
);
|
|
169
|
-
|
|
170
|
-
return `// ๐ฅ Mandu Filling - ${route.id}
|
|
171
|
-
// Pattern: ${route.pattern}
|
|
172
|
-
// Contract Module: ${route.contractModule}
|
|
173
|
-
// ์ด ํ์ผ์์ ๋น์ฆ๋์ค ๋ก์ง์ ๊ตฌํํ์ธ์.
|
|
174
|
-
|
|
175
|
-
import { Mandu } from "@mandujs/core";
|
|
176
|
-
import contract from "${contractImportPath}";
|
|
177
|
-
|
|
178
|
-
export default Mandu.filling()
|
|
179
|
-
// ๐ GET ${route.pattern}
|
|
180
|
-
.get(async (ctx) => {
|
|
181
|
-
const input = await ctx.input(contract, "GET", ctx.params);
|
|
182
|
-
// TODO: ๊ณ์ฝ์ ์๋ต ์ฝ๋์ ๋ง๊ฒ status๋ฅผ ์กฐ์ ํ์ธ์
|
|
183
|
-
return ctx.output(contract, 200, {
|
|
184
|
-
message: "Hello from ${route.id}!",
|
|
185
|
-
input,
|
|
186
|
-
timestamp: new Date().toISOString(),
|
|
187
|
-
});
|
|
188
|
-
})
|
|
189
|
-
|
|
190
|
-
// โ POST ${route.pattern}
|
|
191
|
-
.post(async (ctx) => {
|
|
192
|
-
const input = await ctx.input(contract, "POST", ctx.params);
|
|
193
|
-
// TODO: ๊ณ์ฝ์ ์๋ต ์ฝ๋์ ๋ง๊ฒ status๋ฅผ ์กฐ์ ํ์ธ์
|
|
194
|
-
return ctx.output(contract, 201, {
|
|
195
|
-
message: "Created!",
|
|
196
|
-
input,
|
|
197
|
-
timestamp: new Date().toISOString(),
|
|
198
|
-
});
|
|
199
|
-
});
|
|
200
|
-
|
|
201
|
-
// ๐ก Contract ๊ธฐ๋ฐ ์ฌ์ฉ๋ฒ:
|
|
202
|
-
// ctx.input(contract, "GET") - Contract๋ก ์์ฒญ ๊ฒ์ฆ + ์ ๊ทํ
|
|
203
|
-
// ctx.output(contract, 200, data) - Contract๋ก ์๋ต ๊ฒ์ฆ
|
|
204
|
-
// ctx.okContract(contract, data) - 200 OK (Contract ๊ฒ์ฆ)
|
|
205
|
-
// ctx.createdContract(contract, data) - 201 Created (Contract ๊ฒ์ฆ)
|
|
206
|
-
`;
|
|
207
|
-
}
|
|
153
|
+
// ctx.body() - Request body (์๋ ํ์ฑ)
|
|
154
|
+
// ctx.body(zodSchema) - Body with validation
|
|
155
|
+
// ctx.headers - Request headers
|
|
156
|
+
// ctx.ok(data) - 200 OK
|
|
157
|
+
// ctx.created(data) - 201 Created
|
|
158
|
+
// ctx.error(msg) - 400 Bad Request
|
|
159
|
+
// ctx.notFound(msg) - 404 Not Found
|
|
160
|
+
// ctx.set(key, value) - Guard์์ Handler๋ก ๋ฐ์ดํฐ ์ ๋ฌ
|
|
161
|
+
// ctx.get(key) - Guard์์ ์ค์ ํ ๋ฐ์ดํฐ ์ฝ๊ธฐ
|
|
162
|
+
`;
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
export function generateSlotLogicWithContract(route: RouteSpec): string {
|
|
166
|
+
const contractImportPath = computeSlotImportPath(
|
|
167
|
+
route.contractModule!,
|
|
168
|
+
pathDirname(route.slotModule ?? "spec/slots")
|
|
169
|
+
);
|
|
170
|
+
|
|
171
|
+
return `// ๐ฅ Mandu Filling - ${route.id}
|
|
172
|
+
// Pattern: ${route.pattern}
|
|
173
|
+
// Contract Module: ${route.contractModule}
|
|
174
|
+
// ์ด ํ์ผ์์ ๋น์ฆ๋์ค ๋ก์ง์ ๊ตฌํํ์ธ์.
|
|
175
|
+
|
|
176
|
+
import { Mandu } from "@mandujs/core";
|
|
177
|
+
import contract from "${contractImportPath}";
|
|
178
|
+
|
|
179
|
+
export default Mandu.filling()
|
|
180
|
+
// ๐ GET ${route.pattern}
|
|
181
|
+
.get(async (ctx) => {
|
|
182
|
+
const input = await ctx.input(contract, "GET", ctx.params);
|
|
183
|
+
// TODO: ๊ณ์ฝ์ ์๋ต ์ฝ๋์ ๋ง๊ฒ status๋ฅผ ์กฐ์ ํ์ธ์
|
|
184
|
+
return ctx.output(contract, 200, {
|
|
185
|
+
message: "Hello from ${route.id}!",
|
|
186
|
+
input,
|
|
187
|
+
timestamp: new Date().toISOString(),
|
|
188
|
+
});
|
|
189
|
+
})
|
|
190
|
+
|
|
191
|
+
// โ POST ${route.pattern}
|
|
192
|
+
.post(async (ctx) => {
|
|
193
|
+
const input = await ctx.input(contract, "POST", ctx.params);
|
|
194
|
+
// TODO: ๊ณ์ฝ์ ์๋ต ์ฝ๋์ ๋ง๊ฒ status๋ฅผ ์กฐ์ ํ์ธ์
|
|
195
|
+
return ctx.output(contract, 201, {
|
|
196
|
+
message: "Created!",
|
|
197
|
+
input,
|
|
198
|
+
timestamp: new Date().toISOString(),
|
|
199
|
+
});
|
|
200
|
+
});
|
|
201
|
+
|
|
202
|
+
// ๐ก Contract ๊ธฐ๋ฐ ์ฌ์ฉ๋ฒ:
|
|
203
|
+
// ctx.input(contract, "GET") - Contract๋ก ์์ฒญ ๊ฒ์ฆ + ์ ๊ทํ
|
|
204
|
+
// ctx.output(contract, 200, data) - Contract๋ก ์๋ต ๊ฒ์ฆ
|
|
205
|
+
// ctx.okContract(contract, data) - 200 OK (Contract ๊ฒ์ฆ)
|
|
206
|
+
// ctx.createdContract(contract, data) - 201 Created (Contract ๊ฒ์ฆ)
|
|
207
|
+
`;
|
|
208
|
+
}
|
|
208
209
|
|
|
209
210
|
function computeSlotImportPath(slotModule: string, fromDir: string): string {
|
|
210
|
-
// slotModule: "
|
|
211
|
-
// fromDir: "
|
|
212
|
-
// result: "
|
|
211
|
+
// slotModule: "spec/slots/users.slot.ts"
|
|
212
|
+
// fromDir: ".mandu/generated/server/routes"
|
|
213
|
+
// result: "../../../../spec/slots/users.slot"
|
|
213
214
|
|
|
214
215
|
const slotParts = slotModule.replace(/\\/g, "/").split("/");
|
|
215
216
|
const fromParts = fromDir.replace(/\\/g, "/").split("/");
|
|
@@ -280,11 +281,11 @@ export default function ${pageName}Page({ params }: Props): React.ReactElement {
|
|
|
280
281
|
*/
|
|
281
282
|
export function generatePageComponentWithIsland(route: RouteSpec): string {
|
|
282
283
|
const pageName = toPascalCase(route.id);
|
|
283
|
-
const clientImportPath = computeSlotImportPath(route.clientModule!,
|
|
284
|
+
const clientImportPath = computeSlotImportPath(route.clientModule!, GENERATED_RELATIVE_PATHS.webRoutes);
|
|
284
285
|
|
|
285
286
|
// clientModule + slotModule โ PageRegistration ํ์
|
|
286
287
|
if (route.slotModule) {
|
|
287
|
-
const slotImportPath = computeSlotImportPath(route.slotModule!,
|
|
288
|
+
const slotImportPath = computeSlotImportPath(route.slotModule!, GENERATED_RELATIVE_PATHS.webRoutes);
|
|
288
289
|
|
|
289
290
|
return `// Generated by Mandu - DO NOT EDIT DIRECTLY
|
|
290
291
|
// Island-First Rendering + Slot Module
|
|
@@ -346,7 +347,7 @@ export default function ${pageName}Page({ params, loaderData }: Props): React.Re
|
|
|
346
347
|
*/
|
|
347
348
|
export function generatePageHandlerWithSlot(route: RouteSpec): string {
|
|
348
349
|
const pageName = toPascalCase(route.id);
|
|
349
|
-
const slotImportPath = computeSlotImportPath(route.slotModule!,
|
|
350
|
+
const slotImportPath = computeSlotImportPath(route.slotModule!, GENERATED_RELATIVE_PATHS.serverRoutes);
|
|
350
351
|
|
|
351
352
|
return `// Generated by Mandu - DO NOT EDIT DIRECTLY
|
|
352
353
|
// Route ID: ${route.id}
|
|
@@ -383,13 +384,13 @@ export default {
|
|
|
383
384
|
* "todo-page" โ "TodoPage"
|
|
384
385
|
* "user_profile" โ "UserProfile"
|
|
385
386
|
*/
|
|
386
|
-
function toPascalCase(str: string): string {
|
|
387
|
+
function toPascalCase(str: string): string {
|
|
387
388
|
return str
|
|
388
389
|
.split(/[-_]/)
|
|
389
390
|
.map((part) => part.charAt(0).toUpperCase() + part.slice(1))
|
|
390
391
|
.join("");
|
|
391
|
-
}
|
|
392
|
-
|
|
393
|
-
function pathDirname(filePath: string): string {
|
|
394
|
-
return filePath.replace(/\\/g, "/").split("/").slice(0, -1).join("/");
|
|
395
|
-
}
|
|
392
|
+
}
|
|
393
|
+
|
|
394
|
+
function pathDirname(filePath: string): string {
|
|
395
|
+
return filePath.replace(/\\/g, "/").split("/").slice(0, -1).join("/");
|
|
396
|
+
}
|