@1agh/maude 0.15.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +166 -0
- package/cli/bin/maude.exe +15 -0
- package/cli/bin/maude.mjs +45 -0
- package/cli/bin/mdcc.exe +10 -0
- package/cli/bin/mdcc.mjs +7 -0
- package/cli/cli-wrapper.cjs +67 -0
- package/cli/commands/config.mjs +94 -0
- package/cli/commands/design.mjs +386 -0
- package/cli/commands/help.mjs +57 -0
- package/cli/commands/init.mjs +178 -0
- package/cli/commands/version.mjs +7 -0
- package/cli/install.cjs +113 -0
- package/cli/lib/argv.mjs +37 -0
- package/cli/lib/argv.test.mjs +46 -0
- package/cli/lib/copy-tree.mjs +78 -0
- package/package.json +94 -0
- package/plugins/design/dev-server/annotations-context-toolbar.tsx +397 -0
- package/plugins/design/dev-server/annotations-layer.tsx +1717 -0
- package/plugins/design/dev-server/api.ts +674 -0
- package/plugins/design/dev-server/bin/_screenshot-playwright.mjs +50 -0
- package/plugins/design/dev-server/bin/bootstrap-check.sh +83 -0
- package/plugins/design/dev-server/bin/canvas-edit.sh +48 -0
- package/plugins/design/dev-server/bin/handoff.sh +27 -0
- package/plugins/design/dev-server/bin/screenshot.sh +232 -0
- package/plugins/design/dev-server/bin/server-up.sh +135 -0
- package/plugins/design/dev-server/bin/slug.sh +22 -0
- package/plugins/design/dev-server/bin/smoke.sh +272 -0
- package/plugins/design/dev-server/build.ts +267 -0
- package/plugins/design/dev-server/canvas-build.ts +219 -0
- package/plugins/design/dev-server/canvas-edit.ts +388 -0
- package/plugins/design/dev-server/canvas-header.ts +165 -0
- package/plugins/design/dev-server/canvas-icons.tsx +131 -0
- package/plugins/design/dev-server/canvas-lib-inline.ts +260 -0
- package/plugins/design/dev-server/canvas-lib-resolver.ts +85 -0
- package/plugins/design/dev-server/canvas-lib.tsx +1995 -0
- package/plugins/design/dev-server/canvas-meta.schema.json +181 -0
- package/plugins/design/dev-server/canvas-pipeline.ts +270 -0
- package/plugins/design/dev-server/canvas-shell.tsx +813 -0
- package/plugins/design/dev-server/client/app.jsx +2027 -0
- package/plugins/design/dev-server/client/hmr.mjs +85 -0
- package/plugins/design/dev-server/client/iframe-lazy.mjs +121 -0
- package/plugins/design/dev-server/client/index.html +15 -0
- package/plugins/design/dev-server/client/styles/0-reset.css +18 -0
- package/plugins/design/dev-server/client/styles/1-tokens.css +297 -0
- package/plugins/design/dev-server/client/styles/2-layout.css +35 -0
- package/plugins/design/dev-server/client/styles/3-shell.css +906 -0
- package/plugins/design/dev-server/client/styles/4-components.css +1268 -0
- package/plugins/design/dev-server/client/styles/5-utilities.css +4 -0
- package/plugins/design/dev-server/client/styles/_index.css +24 -0
- package/plugins/design/dev-server/client/styles.css +1419 -0
- package/plugins/design/dev-server/config.schema.json +147 -0
- package/plugins/design/dev-server/context-menu.tsx +343 -0
- package/plugins/design/dev-server/context.ts +173 -0
- package/plugins/design/dev-server/dist/client.bundle.js +20323 -0
- package/plugins/design/dev-server/dist/styles.css +2875 -0
- package/plugins/design/dev-server/examples/README.md +9 -0
- package/plugins/design/dev-server/examples/perf-100-artboards.tsx +113 -0
- package/plugins/design/dev-server/fs-watch.ts +63 -0
- package/plugins/design/dev-server/handoff.ts +721 -0
- package/plugins/design/dev-server/history.ts +125 -0
- package/plugins/design/dev-server/hmr-broadcast.ts +114 -0
- package/plugins/design/dev-server/http.ts +413 -0
- package/plugins/design/dev-server/input-router.tsx +485 -0
- package/plugins/design/dev-server/inspect.ts +365 -0
- package/plugins/design/dev-server/locator.ts +159 -0
- package/plugins/design/dev-server/mem.ts +97 -0
- package/plugins/design/dev-server/runtime-bundle.ts +235 -0
- package/plugins/design/dev-server/server.mjs +1246 -0
- package/plugins/design/dev-server/server.ts +131 -0
- package/plugins/design/dev-server/test/_helpers.ts +81 -0
- package/plugins/design/dev-server/test/active-state.test.ts +145 -0
- package/plugins/design/dev-server/test/annotations-api.test.ts +146 -0
- package/plugins/design/dev-server/test/annotations-layer.test.ts +419 -0
- package/plugins/design/dev-server/test/binary-smoke.test.ts +47 -0
- package/plugins/design/dev-server/test/bundle-smoke.test.ts +29 -0
- package/plugins/design/dev-server/test/canvas-build.test.ts +78 -0
- package/plugins/design/dev-server/test/canvas-edit.test.ts +139 -0
- package/plugins/design/dev-server/test/canvas-header.test.ts +127 -0
- package/plugins/design/dev-server/test/canvas-lib-inline.test.ts +146 -0
- package/plugins/design/dev-server/test/canvas-lib-resolver.test.ts +112 -0
- package/plugins/design/dev-server/test/canvas-meta-api.test.ts +236 -0
- package/plugins/design/dev-server/test/canvas-pipeline.test.ts +180 -0
- package/plugins/design/dev-server/test/canvas-route.test.ts +176 -0
- package/plugins/design/dev-server/test/fs-watch.test.ts +41 -0
- package/plugins/design/dev-server/test/handoff-static-frames.test.ts +215 -0
- package/plugins/design/dev-server/test/handoff.test.ts +281 -0
- package/plugins/design/dev-server/test/history-rollback.test.ts +62 -0
- package/plugins/design/dev-server/test/hmr-broadcast.test.ts +108 -0
- package/plugins/design/dev-server/test/input-router.test.ts +316 -0
- package/plugins/design/dev-server/test/locator.test.ts +214 -0
- package/plugins/design/dev-server/test/perf-harness.ts +193 -0
- package/plugins/design/dev-server/test/phase-3.6-smoke.test.ts +77 -0
- package/plugins/design/dev-server/test/runtime-bundle.test.ts +69 -0
- package/plugins/design/dev-server/test/server-lifecycle.test.ts +28 -0
- package/plugins/design/dev-server/test/tool-palette.test.tsx +55 -0
- package/plugins/design/dev-server/test/use-annotation-selection.test.tsx +77 -0
- package/plugins/design/dev-server/test/use-artboard-drag.test.ts +325 -0
- package/plugins/design/dev-server/test/use-selection-set.test.tsx +166 -0
- package/plugins/design/dev-server/test/use-snap-guides.test.ts +190 -0
- package/plugins/design/dev-server/test/use-tool-mode.test.tsx +93 -0
- package/plugins/design/dev-server/test/ws-handshake.test.ts +33 -0
- package/plugins/design/dev-server/tool-palette.tsx +278 -0
- package/plugins/design/dev-server/tsconfig.json +26 -0
- package/plugins/design/dev-server/use-annotation-selection.tsx +92 -0
- package/plugins/design/dev-server/use-annotations-visibility.tsx +43 -0
- package/plugins/design/dev-server/use-artboard-drag.tsx +445 -0
- package/plugins/design/dev-server/use-selection-set.tsx +224 -0
- package/plugins/design/dev-server/use-snap-guides.tsx +215 -0
- package/plugins/design/dev-server/use-tool-mode.tsx +114 -0
- package/plugins/design/dev-server/ws.ts +90 -0
- package/plugins/design/templates/_shell.html +177 -0
- package/plugins/design/templates/canvas.tsx.template +54 -0
- package/plugins/design/templates/design-system-inspiration/_MAPPING.md +277 -0
- package/plugins/design/templates/design-system-inspiration/_README.md +71 -0
- package/plugins/design/templates/design-system-inspiration/audience-consumer/components-banner.html +68 -0
- package/plugins/design/templates/design-system-inspiration/audience-consumer/components-empty-state-generous.html +39 -0
- package/plugins/design/templates/design-system-inspiration/audience-consumer/components-feature-grid.html +62 -0
- package/plugins/design/templates/design-system-inspiration/audience-consumer/components-marketing-card.html +63 -0
- package/plugins/design/templates/design-system-inspiration/audience-consumer/components-testimonial.html +80 -0
- package/plugins/design/templates/design-system-inspiration/audience-developer/components-code-block.html +71 -0
- package/plugins/design/templates/design-system-inspiration/audience-developer/components-diff-view.html +65 -0
- package/plugins/design/templates/design-system-inspiration/audience-developer/components-log-stream.html +62 -0
- package/plugins/design/templates/design-system-inspiration/audience-developer/components-monospace-table.html +57 -0
- package/plugins/design/templates/design-system-inspiration/audience-developer/components-terminal-pane.html +67 -0
- package/plugins/design/templates/design-system-inspiration/audience-developer/type-mono.html +57 -0
- package/plugins/design/templates/design-system-inspiration/audience-pro/colors-presence.html +74 -0
- package/plugins/design/templates/design-system-inspiration/audience-pro/components-command-palette.html +90 -0
- package/plugins/design/templates/design-system-inspiration/audience-pro/components-keyboard.html +51 -0
- package/plugins/design/templates/design-system-inspiration/audience-pro/components-list.html +89 -0
- package/plugins/design/templates/design-system-inspiration/audience-pro/components-shortcuts-overlay.html +85 -0
- package/plugins/design/templates/design-system-inspiration/audience-pro/components-toast-menu.html +80 -0
- package/plugins/design/templates/design-system-inspiration/core/INDEX.md.tpl +25 -0
- package/plugins/design/templates/design-system-inspiration/core/README.orchestration.md.tpl +71 -0
- package/plugins/design/templates/design-system-inspiration/core/README.philosophy.md.tpl +77 -0
- package/plugins/design/templates/design-system-inspiration/core/SKILL.md.tpl +50 -0
- package/plugins/design/templates/design-system-inspiration/core/colors_and_type.css.tpl +111 -0
- package/plugins/design/templates/design-system-inspiration/core/config.json.tpl +28 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/_layout.css +113 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/colors-accent.html +48 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/colors-surfaces.html +49 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/colors-text.html +52 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/components-buttons.html +83 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/components-cards.html +79 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/components-inputs.html +82 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/motion.html +66 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/spacing-scale.html +53 -0
- package/plugins/design/templates/design-system-inspiration/core/preview/type-scale.html +62 -0
- package/plugins/design/templates/design-system-inspiration/foundations/borders.html +39 -0
- package/plugins/design/templates/design-system-inspiration/foundations/elevation.html +46 -0
- package/plugins/design/templates/design-system-inspiration/foundations/focus.html +48 -0
- package/plugins/design/templates/design-system-inspiration/foundations/grid.html +51 -0
- package/plugins/design/templates/design-system-inspiration/foundations/iconography.html +73 -0
- package/plugins/design/templates/design-system-inspiration/foundations/opacity.html +45 -0
- package/plugins/design/templates/design-system-inspiration/foundations/radii.html +40 -0
- package/plugins/design/templates/design-system-inspiration/foundations/selection.html +45 -0
- package/plugins/design/templates/design-system-inspiration/meta/accessibility.html +62 -0
- package/plugins/design/templates/design-system-inspiration/meta/i18n.html +73 -0
- package/plugins/design/templates/design-system-inspiration/meta/presence-multiplayer.html +71 -0
- package/plugins/design/templates/design-system-inspiration/meta/tokens-index.html +80 -0
- package/plugins/design/templates/design-system-inspiration/patterns/patterns-auth.html +78 -0
- package/plugins/design/templates/design-system-inspiration/patterns/patterns-data-density.html +61 -0
- package/plugins/design/templates/design-system-inspiration/patterns/patterns-error-pages.html +70 -0
- package/plugins/design/templates/design-system-inspiration/patterns/patterns-form-layouts.html +70 -0
- package/plugins/design/templates/design-system-inspiration/patterns/patterns-onboarding.html +71 -0
- package/plugins/design/templates/design-system-inspiration/patterns/patterns-pricing.html +83 -0
- package/plugins/design/templates/design-system-inspiration/platform-desktop/components-resize-panels.html +63 -0
- package/plugins/design/templates/design-system-inspiration/platform-desktop/ui_kits-desktop-index.html +55 -0
- package/plugins/design/templates/design-system-inspiration/platform-desktop/ui_kits-desktop-showcase.html +302 -0
- package/plugins/design/templates/design-system-inspiration/platform-mobile/components-bottom-sheet.html +63 -0
- package/plugins/design/templates/design-system-inspiration/platform-mobile/components-pull-to-refresh.html +74 -0
- package/plugins/design/templates/design-system-inspiration/platform-mobile/components-segmented-control.html +51 -0
- package/plugins/design/templates/design-system-inspiration/platform-mobile/components-tab-bar.html +57 -0
- package/plugins/design/templates/design-system-inspiration/platform-mobile/ui_kits-mobile-index.html +58 -0
- package/plugins/design/templates/design-system-inspiration/platform-mobile/ui_kits-mobile-showcase.html +237 -0
- package/plugins/design/templates/design-system-inspiration/status/colors-status.html +49 -0
- package/plugins/design/templates/design-system-inspiration/status/components-status.html +63 -0
- package/plugins/design/templates/design-system-inspiration/status/skeletons.html +74 -0
- package/plugins/design/templates/design-system-inspiration/theme-both/colors-themes-side-by-side.html +59 -0
- package/plugins/design/templates/design-system-inspiration/universal/components-callout.html +74 -0
- package/plugins/design/templates/design-system-inspiration/universal/components-dialogs.html +81 -0
- package/plugins/design/templates/design-system-inspiration/universal/components-tables.html +101 -0
- package/plugins/design/templates/design-system-inspiration/universal/components-toggles.html +74 -0
- package/plugins/design/templates/design-system-inspiration/universal/components-tooltips.html +74 -0
- package/plugins/design/templates/design-system-inspiration/universal/empty-state.html.tpl +34 -0
- package/plugins/design/templates/design-system-inspiration/universal/logo.html +42 -0
- package/plugins/design/templates/ds-specimen.tsx.template +59 -0
- package/plugins/flow/.claude-plugin/config.schema.json +398 -0
- package/plugins/flow/README.md +45 -0
- package/plugins/flow/templates/ai-skeleton/INDEX.md +50 -0
- package/plugins/flow/templates/ai-skeleton/README.md +46 -0
- package/plugins/flow/templates/ai-skeleton/browser/har/.gitkeep +0 -0
- package/plugins/flow/templates/ai-skeleton/browser/snapshots/.gitkeep +0 -0
- package/plugins/flow/templates/ai-skeleton/business/README.md +12 -0
- package/plugins/flow/templates/ai-skeleton/context/README.md +12 -0
- package/plugins/flow/templates/ai-skeleton/decisions/README.md +20 -0
- package/plugins/flow/templates/ai-skeleton/design-import/.gitkeep +0 -0
- package/plugins/flow/templates/ai-skeleton/dev-logs/.gitkeep +0 -0
- package/plugins/flow/templates/ai-skeleton/device/.gitkeep +0 -0
- package/plugins/flow/templates/ai-skeleton/docs/README.md +5 -0
- package/plugins/flow/templates/ai-skeleton/logs/.gitkeep +0 -0
- package/plugins/flow/templates/ai-skeleton/logs/README.md +13 -0
- package/plugins/flow/templates/ai-skeleton/plans/README.md +16 -0
- package/plugins/flow/templates/ai-skeleton/plans/archive/.gitkeep +0 -0
- package/plugins/flow/templates/ai-skeleton/release-guide.md +35 -0
- package/plugins/flow/templates/ai-skeleton/reviews/README.md +15 -0
- package/plugins/flow/templates/ai-skeleton/scenarios/README.md +26 -0
- package/plugins/flow/templates/ai-skeleton/scenarios/_lib/.gitkeep +0 -0
- package/plugins/flow/templates/ai-skeleton/state/STATE.md +25 -0
- package/plugins/flow/templates/ai-skeleton/templates/HANDOFF.md +32 -0
- package/plugins/flow/templates/ai-skeleton/workflows.config.json +74 -0
|
@@ -0,0 +1,272 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# smoke.sh — batch-screenshot every UI canvas + preview specimen.
|
|
3
|
+
# Catches "build green ≠ user-visible green" regressions that bypass the
|
|
4
|
+
# per-canvas hooks in /design:edit step 7 / /design:new step 9 — typically
|
|
5
|
+
# dev-server infra changes or bulk multi-canvas migrations. See DDR-021.
|
|
6
|
+
#
|
|
7
|
+
# Usage:
|
|
8
|
+
# smoke.sh [--root <repo>]
|
|
9
|
+
# [--out-dir <dir>]
|
|
10
|
+
# [--include-system 0|1] (default 1)
|
|
11
|
+
# [--timeout <secs>] (default 8)
|
|
12
|
+
# [--engine auto|agent-browser|playwright]
|
|
13
|
+
#
|
|
14
|
+
# Reads:
|
|
15
|
+
# $DESIGN_ROOT/_server.json (must exist — caller runs server-up.sh first)
|
|
16
|
+
# $DESIGN_ROOT/ui/*.tsx (canvases)
|
|
17
|
+
# $DESIGN_ROOT/system/*/preview/*.tsx (specimens, when --include-system 1)
|
|
18
|
+
#
|
|
19
|
+
# Writes:
|
|
20
|
+
# <out-dir>/<slug>.png (one screenshot per canvas)
|
|
21
|
+
# <out-dir>/report.tsv (machine-parseable summary)
|
|
22
|
+
# <out-dir>/report.md (human-readable summary, links every PNG)
|
|
23
|
+
#
|
|
24
|
+
# Stdout: one line per canvas, tab-separated:
|
|
25
|
+
# STATUS \t FILE \t SCREENSHOT \t DETAIL
|
|
26
|
+
# Stderr: diagnostic / progress.
|
|
27
|
+
# Exit: 0 = all green / 3 = at least one blank/error / 1 = missing deps / 2 = bad args.
|
|
28
|
+
|
|
29
|
+
REPO=""
|
|
30
|
+
OUT_DIR=""
|
|
31
|
+
INCLUDE_SYSTEM=1
|
|
32
|
+
TIMEOUT=8
|
|
33
|
+
ENGINE="auto"
|
|
34
|
+
|
|
35
|
+
while [ $# -gt 0 ]; do
|
|
36
|
+
case "$1" in
|
|
37
|
+
--root) REPO="$2"; shift 2 ;;
|
|
38
|
+
--out-dir) OUT_DIR="$2"; shift 2 ;;
|
|
39
|
+
--include-system) INCLUDE_SYSTEM="$2"; shift 2 ;;
|
|
40
|
+
--timeout) TIMEOUT="$2"; shift 2 ;;
|
|
41
|
+
--engine) ENGINE="$2"; shift 2 ;;
|
|
42
|
+
--help|-h)
|
|
43
|
+
sed -n '2,28p' "$0" | sed 's/^# \?//'
|
|
44
|
+
exit 0
|
|
45
|
+
;;
|
|
46
|
+
*)
|
|
47
|
+
echo "smoke.sh: unknown arg '$1' (try --help)" >&2
|
|
48
|
+
exit 2
|
|
49
|
+
;;
|
|
50
|
+
esac
|
|
51
|
+
done
|
|
52
|
+
|
|
53
|
+
# ---------- resolve repo + design root ----------
|
|
54
|
+
if [ -z "$REPO" ]; then
|
|
55
|
+
REPO="${CLAUDE_PROJECT_DIR:-$(git rev-parse --show-toplevel 2>/dev/null || pwd)}"
|
|
56
|
+
fi
|
|
57
|
+
DESIGN_ROOT="$REPO/.design"
|
|
58
|
+
[ -d "$DESIGN_ROOT" ] || { echo "smoke.sh: no .design/ under $REPO" >&2; exit 1; }
|
|
59
|
+
|
|
60
|
+
STATE="$DESIGN_ROOT/_server.json"
|
|
61
|
+
[ -f "$STATE" ] || { echo "smoke.sh: $STATE missing — run server-up.sh first" >&2; exit 1; }
|
|
62
|
+
|
|
63
|
+
if command -v jq >/dev/null 2>&1; then
|
|
64
|
+
PORT=$(jq -r .port "$STATE" 2>/dev/null)
|
|
65
|
+
else
|
|
66
|
+
PORT=$(sed -nE 's/.*"port"[[:space:]]*:[[:space:]]*([0-9]+).*/\1/p' "$STATE" | head -n1)
|
|
67
|
+
fi
|
|
68
|
+
[ -n "$PORT" ] || { echo "smoke.sh: no port in $STATE" >&2; exit 1; }
|
|
69
|
+
|
|
70
|
+
# ---------- resolve out-dir ----------
|
|
71
|
+
if [ -z "$OUT_DIR" ]; then
|
|
72
|
+
TS=$(date +%Y%m%d-%H%M%S)
|
|
73
|
+
OUT_DIR="$DESIGN_ROOT/_history/_smoke/$TS"
|
|
74
|
+
fi
|
|
75
|
+
mkdir -p "$OUT_DIR"
|
|
76
|
+
|
|
77
|
+
# ---------- engine resolution ----------
|
|
78
|
+
if [ "$ENGINE" = "auto" ]; then
|
|
79
|
+
if command -v agent-browser >/dev/null 2>&1; then
|
|
80
|
+
ENGINE="agent-browser"
|
|
81
|
+
else
|
|
82
|
+
ENGINE="playwright"
|
|
83
|
+
fi
|
|
84
|
+
fi
|
|
85
|
+
echo "→ smoke engine: $ENGINE | port: $PORT | out: $OUT_DIR" >&2
|
|
86
|
+
|
|
87
|
+
# ---------- collect canvases ----------
|
|
88
|
+
CANVASES=""
|
|
89
|
+
if [ -d "$DESIGN_ROOT/ui" ]; then
|
|
90
|
+
while IFS= read -r f; do
|
|
91
|
+
base=$(basename "$f")
|
|
92
|
+
case "$base" in _*) continue ;; esac
|
|
93
|
+
CANVASES="$CANVASES$f"$'\n'
|
|
94
|
+
done < <(find "$DESIGN_ROOT/ui" -maxdepth 1 -type f -name '*.tsx' 2>/dev/null | sort)
|
|
95
|
+
fi
|
|
96
|
+
|
|
97
|
+
if [ "$INCLUDE_SYSTEM" = "1" ] && [ -d "$DESIGN_ROOT/system" ]; then
|
|
98
|
+
while IFS= read -r f; do
|
|
99
|
+
base=$(basename "$f")
|
|
100
|
+
case "$base" in _*) continue ;; esac
|
|
101
|
+
CANVASES="$CANVASES$f"$'\n'
|
|
102
|
+
done < <(find "$DESIGN_ROOT/system" -type f -name '*.tsx' -path '*/preview/*' 2>/dev/null | sort)
|
|
103
|
+
fi
|
|
104
|
+
|
|
105
|
+
CANVASES=$(printf '%s' "$CANVASES" | sed '/^$/d')
|
|
106
|
+
COUNT=$(printf '%s' "$CANVASES" | grep -c .)
|
|
107
|
+
[ "$COUNT" -gt 0 ] || { echo "smoke.sh: no canvases found (ui/*.tsx or system/*/preview/*.tsx)" >&2; exit 1; }
|
|
108
|
+
echo "→ found $COUNT canvases" >&2
|
|
109
|
+
|
|
110
|
+
# ---------- helpers ----------
|
|
111
|
+
SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)"
|
|
112
|
+
SLUG_HELPER="$SCRIPT_DIR/slug.sh"
|
|
113
|
+
|
|
114
|
+
urlencode_path() {
|
|
115
|
+
# Encode spaces only — leaves /, ., etc alone. Server resolves these.
|
|
116
|
+
printf '%s' "$1" | sed 's/ /%20/g'
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
# Probe a canvas via agent-browser. Returns three lines on stdout:
|
|
120
|
+
# <status> one of OK / BLANK / ERROR
|
|
121
|
+
# <detail> short summary string
|
|
122
|
+
# <screenshot-path-or-empty>
|
|
123
|
+
probe_agent_browser() {
|
|
124
|
+
local url="$1"
|
|
125
|
+
local out_png="$2"
|
|
126
|
+
|
|
127
|
+
agent-browser open "$url" >/dev/null 2>&1 || { echo "ERROR"; echo "open-failed"; echo ""; return; }
|
|
128
|
+
|
|
129
|
+
# Poll for any DC marker — [data-dc-screen], [data-dc-slot], [data-cd-id].
|
|
130
|
+
# Specimens may not have any of these, so we also accept body innerText > 0.
|
|
131
|
+
local poll=0
|
|
132
|
+
local mounted=0
|
|
133
|
+
while [ $poll -lt "$TIMEOUT" ]; do
|
|
134
|
+
sleep 1
|
|
135
|
+
poll=$((poll + 1))
|
|
136
|
+
local raw
|
|
137
|
+
raw=$(agent-browser eval "document.querySelectorAll('[data-dc-screen],[data-dc-slot],[data-cd-id]').length + (document.body && document.body.innerText.trim().length > 0 ? 1000 : 0)" 2>/dev/null)
|
|
138
|
+
raw=$(printf '%s' "$raw" | tr -d '[:space:]')
|
|
139
|
+
case "$raw" in
|
|
140
|
+
''|*[!0-9]*) continue ;;
|
|
141
|
+
0) continue ;;
|
|
142
|
+
*) mounted=1; break ;;
|
|
143
|
+
esac
|
|
144
|
+
done
|
|
145
|
+
|
|
146
|
+
# Capture screenshot regardless — the PNG is evidence even on failure.
|
|
147
|
+
agent-browser screenshot --full "$out_png" >/dev/null 2>&1 || true
|
|
148
|
+
|
|
149
|
+
if [ $mounted -eq 0 ]; then
|
|
150
|
+
echo "BLANK"
|
|
151
|
+
echo "no-dc-markers-no-text-after-${TIMEOUT}s"
|
|
152
|
+
echo "$out_png"
|
|
153
|
+
return
|
|
154
|
+
fi
|
|
155
|
+
|
|
156
|
+
# Probe for visible error overlays (react-error-overlay, common patterns).
|
|
157
|
+
local err
|
|
158
|
+
err=$(agent-browser eval "(() => {
|
|
159
|
+
const sel = ['#__react-error-overlay', '.react-error-overlay', '[data-error-overlay]', 'pre.error-stack'];
|
|
160
|
+
for (const s of sel) { const el = document.querySelector(s); if (el && el.innerText) return el.innerText.slice(0, 120); }
|
|
161
|
+
const body = document.body && document.body.innerText || '';
|
|
162
|
+
if (body.startsWith('Error:') || body.startsWith('SyntaxError:') || body.startsWith('ReferenceError:')) return body.slice(0, 120);
|
|
163
|
+
return '';
|
|
164
|
+
})()" 2>/dev/null)
|
|
165
|
+
# Strip wrapping quotes that agent-browser eval adds for strings.
|
|
166
|
+
err=$(printf '%s' "$err" | sed 's/^"//; s/"$//; s/^\\n//; s/\\n$//')
|
|
167
|
+
|
|
168
|
+
if [ -n "$err" ] && [ "$err" != "null" ] && [ "$err" != "undefined" ]; then
|
|
169
|
+
echo "ERROR"
|
|
170
|
+
echo "$err"
|
|
171
|
+
echo "$out_png"
|
|
172
|
+
return
|
|
173
|
+
fi
|
|
174
|
+
|
|
175
|
+
# PNG size sanity — < 2 KB usually means blank background only.
|
|
176
|
+
if [ -s "$out_png" ]; then
|
|
177
|
+
local size
|
|
178
|
+
size=$(wc -c < "$out_png" 2>/dev/null | tr -d ' ')
|
|
179
|
+
if [ -n "$size" ] && [ "$size" -lt 2048 ]; then
|
|
180
|
+
echo "BLANK"
|
|
181
|
+
echo "png-${size}B"
|
|
182
|
+
echo "$out_png"
|
|
183
|
+
return
|
|
184
|
+
fi
|
|
185
|
+
fi
|
|
186
|
+
|
|
187
|
+
echo "OK"
|
|
188
|
+
echo "ok"
|
|
189
|
+
echo "$out_png"
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
# ---------- iterate ----------
|
|
193
|
+
TSV="$OUT_DIR/report.tsv"
|
|
194
|
+
MD="$OUT_DIR/report.md"
|
|
195
|
+
printf 'status\tfile\tscreenshot\tdetail\n' > "$TSV"
|
|
196
|
+
{
|
|
197
|
+
echo "# Smoke report — $(date '+%Y-%m-%d %H:%M:%S')"
|
|
198
|
+
echo
|
|
199
|
+
echo "- repo: \`$REPO\`"
|
|
200
|
+
echo "- port: $PORT"
|
|
201
|
+
echo "- canvases: $COUNT"
|
|
202
|
+
echo
|
|
203
|
+
echo "| status | file | screenshot | detail |"
|
|
204
|
+
echo "|---|---|---|---|"
|
|
205
|
+
} > "$MD"
|
|
206
|
+
|
|
207
|
+
FAILED=0
|
|
208
|
+
N=0
|
|
209
|
+
while IFS= read -r CANVAS; do
|
|
210
|
+
[ -z "$CANVAS" ] && continue
|
|
211
|
+
N=$((N + 1))
|
|
212
|
+
REL="${CANVAS#$DESIGN_ROOT/}"
|
|
213
|
+
REL_ENC=$(urlencode_path "$REL")
|
|
214
|
+
URL="http://localhost:$PORT/$REL_ENC"
|
|
215
|
+
SLUG=$(bash "$SLUG_HELPER" "$REL" 2>/dev/null || printf '%s' "$REL" | tr '/ ' '__' | tr '[:upper:]' '[:lower:]')
|
|
216
|
+
OUT_PNG="$OUT_DIR/$SLUG.png"
|
|
217
|
+
|
|
218
|
+
printf ' [%d/%d] %s … ' "$N" "$COUNT" "$REL" >&2
|
|
219
|
+
|
|
220
|
+
if [ "$ENGINE" = "agent-browser" ]; then
|
|
221
|
+
RESULT=$(probe_agent_browser "$URL" "$OUT_PNG")
|
|
222
|
+
else
|
|
223
|
+
# Playwright fallback — coarser: just screenshot, accept any PNG > 2 KB as OK.
|
|
224
|
+
# See _screenshot-playwright.mjs for the underlying tool.
|
|
225
|
+
bash "$SCRIPT_DIR/screenshot.sh" --url "$URL" --full --out "$OUT_PNG" --engine playwright --timeout "$TIMEOUT" >/dev/null 2>&1
|
|
226
|
+
if [ -s "$OUT_PNG" ]; then
|
|
227
|
+
SIZE=$(wc -c < "$OUT_PNG" | tr -d ' ')
|
|
228
|
+
if [ "$SIZE" -lt 2048 ]; then
|
|
229
|
+
RESULT=$'BLANK\npng-'"$SIZE"$'B\n'"$OUT_PNG"
|
|
230
|
+
else
|
|
231
|
+
RESULT=$'OK\nok\n'"$OUT_PNG"
|
|
232
|
+
fi
|
|
233
|
+
else
|
|
234
|
+
RESULT=$'ERROR\nno-png\n'"$OUT_PNG"
|
|
235
|
+
fi
|
|
236
|
+
fi
|
|
237
|
+
|
|
238
|
+
STATUS=$(printf '%s\n' "$RESULT" | sed -n '1p')
|
|
239
|
+
DETAIL=$(printf '%s\n' "$RESULT" | sed -n '2p')
|
|
240
|
+
SHOT=$(printf '%s\n' "$RESULT" | sed -n '3p')
|
|
241
|
+
|
|
242
|
+
case "$STATUS" in
|
|
243
|
+
OK) SYM="✓"; echo "$SYM" >&2 ;;
|
|
244
|
+
BLANK) SYM="✗"; FAILED=$((FAILED + 1)); echo "$SYM blank ($DETAIL)" >&2 ;;
|
|
245
|
+
ERROR) SYM="⚠"; FAILED=$((FAILED + 1)); echo "$SYM error ($DETAIL)" >&2 ;;
|
|
246
|
+
*) SYM="?"; FAILED=$((FAILED + 1)); echo "? unknown ($STATUS)" >&2 ;;
|
|
247
|
+
esac
|
|
248
|
+
|
|
249
|
+
printf '%s\t%s\t%s\t%s\n' "$STATUS" "$REL" "$SHOT" "$DETAIL" >> "$TSV"
|
|
250
|
+
printf '| %s %s | `%s` | [`%s`](%s) | %s |\n' "$SYM" "$STATUS" "$REL" "$(basename "$SHOT")" "$(basename "$SHOT")" "$DETAIL" >> "$MD"
|
|
251
|
+
|
|
252
|
+
printf '%s\t%s\t%s\t%s\n' "$STATUS" "$REL" "$SHOT" "$DETAIL"
|
|
253
|
+
done <<< "$CANVASES"
|
|
254
|
+
|
|
255
|
+
{
|
|
256
|
+
echo
|
|
257
|
+
if [ $FAILED -eq 0 ]; then
|
|
258
|
+
echo "**Result:** ✓ all $COUNT canvases rendered."
|
|
259
|
+
else
|
|
260
|
+
echo "**Result:** ✗ $FAILED / $COUNT canvases failed."
|
|
261
|
+
fi
|
|
262
|
+
} >> "$MD"
|
|
263
|
+
|
|
264
|
+
echo "→ report: $MD" >&2
|
|
265
|
+
echo "→ tsv: $TSV" >&2
|
|
266
|
+
|
|
267
|
+
if [ $FAILED -gt 0 ]; then
|
|
268
|
+
echo "✗ smoke: $FAILED / $COUNT canvases failed" >&2
|
|
269
|
+
exit 3
|
|
270
|
+
fi
|
|
271
|
+
echo "✓ smoke: all $COUNT canvases rendered" >&2
|
|
272
|
+
exit 0
|
|
@@ -0,0 +1,267 @@
|
|
|
1
|
+
#!/usr/bin/env bun
|
|
2
|
+
// Build orchestrator for the dev-server.
|
|
3
|
+
//
|
|
4
|
+
// Three steps (run on demand):
|
|
5
|
+
// (a) Client JSX bundle: client/app.jsx + React 19 -> dist/client.bundle.js (IIFE, tree-shaken).
|
|
6
|
+
// (b) CSS bundle: client/styles/_index.css (Lightning CSS, @layer, OKLCH fallback).
|
|
7
|
+
// (c) Server binary: server.ts -> dist/maude-<platform> (bun build --compile, per-platform).
|
|
8
|
+
//
|
|
9
|
+
// Modes:
|
|
10
|
+
// bun run build.ts -> dev build for current platform (no compile, no minify)
|
|
11
|
+
// bun run build.ts --release -> release build for all platforms in the matrix
|
|
12
|
+
// bun run build.ts --release --target=bun-darwin-arm64
|
|
13
|
+
// bun run build.ts --watch -> watch client + CSS; broadcast over HMR socket
|
|
14
|
+
// bun run build.ts --dry-run -> exit 0 without writing files (smoke for CI / Task 2 validation)
|
|
15
|
+
//
|
|
16
|
+
// Per DDR-009 (Bun runtime authoritative) + DDR-012 (React 19 unified) + DDR-014 (Lightning CSS).
|
|
17
|
+
|
|
18
|
+
import { existsSync, mkdirSync } from 'node:fs';
|
|
19
|
+
import { dirname, join, resolve } from 'node:path';
|
|
20
|
+
import { fileURLToPath } from 'node:url';
|
|
21
|
+
|
|
22
|
+
import { browserslistToTargets, bundle as lcssBundle } from 'lightningcss';
|
|
23
|
+
|
|
24
|
+
const ROOT = dirname(fileURLToPath(import.meta.url));
|
|
25
|
+
const DIST = join(ROOT, 'dist');
|
|
26
|
+
|
|
27
|
+
const ARGS = new Set(process.argv.slice(2));
|
|
28
|
+
const FLAG_TARGET = process.argv.find((a) => a.startsWith('--target='))?.slice('--target='.length);
|
|
29
|
+
const MODE: 'dev' | 'release' | 'dry' = ARGS.has('--dry-run')
|
|
30
|
+
? 'dry'
|
|
31
|
+
: ARGS.has('--release')
|
|
32
|
+
? 'release'
|
|
33
|
+
: 'dev';
|
|
34
|
+
const WATCH = ARGS.has('--watch');
|
|
35
|
+
|
|
36
|
+
const PLATFORM_MATRIX = [
|
|
37
|
+
'bun-darwin-arm64',
|
|
38
|
+
'bun-darwin-x64',
|
|
39
|
+
'bun-linux-x64',
|
|
40
|
+
'bun-linux-arm64',
|
|
41
|
+
'bun-linux-x64-musl',
|
|
42
|
+
'bun-linux-arm64-musl',
|
|
43
|
+
'bun-windows-x64',
|
|
44
|
+
] as const;
|
|
45
|
+
|
|
46
|
+
type PlatformTarget = (typeof PLATFORM_MATRIX)[number];
|
|
47
|
+
|
|
48
|
+
function platformSlug(target: PlatformTarget): string {
|
|
49
|
+
// bun calls Windows "windows"; npm and process.platform call it "win32".
|
|
50
|
+
// Sub-package directories + the build-binaries.yml matrix slug use win32-x64.
|
|
51
|
+
const s = target.replace(/^bun-/, '');
|
|
52
|
+
return s === 'windows-x64' ? 'win32-x64' : s;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
function currentTarget(): PlatformTarget {
|
|
56
|
+
const p = process.platform;
|
|
57
|
+
const a = process.arch;
|
|
58
|
+
if (p === 'darwin') return a === 'arm64' ? 'bun-darwin-arm64' : 'bun-darwin-x64';
|
|
59
|
+
if (p === 'linux') return a === 'arm64' ? 'bun-linux-arm64' : 'bun-linux-x64';
|
|
60
|
+
if (p === 'win32') return 'bun-windows-x64';
|
|
61
|
+
throw new Error(`Unsupported host platform: ${p}-${a}`);
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
function ensureDist() {
|
|
65
|
+
if (!existsSync(DIST)) mkdirSync(DIST, { recursive: true });
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
// ---------- (a) Client JSX bundle ----------
|
|
69
|
+
|
|
70
|
+
async function buildClient(): Promise<{ outBytes: number; outPath: string }> {
|
|
71
|
+
ensureDist();
|
|
72
|
+
const outPath = join(DIST, 'client.bundle.js');
|
|
73
|
+
// Read package.json version at build time for the wordmark sub-line.
|
|
74
|
+
const pkg = JSON.parse(await Bun.file(join(ROOT, '..', '..', '..', 'package.json')).text());
|
|
75
|
+
const result = await Bun.build({
|
|
76
|
+
entrypoints: [join(ROOT, 'client/app.jsx')],
|
|
77
|
+
outdir: DIST,
|
|
78
|
+
target: 'browser',
|
|
79
|
+
// ESM — not IIFE. Bun.build's IIFE + full minify + React 19 hits a TDZ
|
|
80
|
+
// bug (`Cannot access 'VZ' before initialization`) because top-level
|
|
81
|
+
// `const`s get rotated past their declaration. ESM has stable hoisting
|
|
82
|
+
// semantics the minifier respects. Cost: `<script type="module">` in
|
|
83
|
+
// index.html (already set).
|
|
84
|
+
format: 'esm',
|
|
85
|
+
naming: 'client.bundle.js',
|
|
86
|
+
minify: MODE === 'release',
|
|
87
|
+
sourcemap: MODE === 'dev' ? 'inline' : 'none',
|
|
88
|
+
define: {
|
|
89
|
+
'process.env.NODE_ENV': JSON.stringify(MODE === 'release' ? 'production' : 'development'),
|
|
90
|
+
__MDCC_VERSION__: JSON.stringify(pkg.version),
|
|
91
|
+
},
|
|
92
|
+
});
|
|
93
|
+
if (!result.success) {
|
|
94
|
+
const messages = result.logs.map((l) => l.message ?? String(l)).join('\n');
|
|
95
|
+
throw new Error(`Client build failed:\n${messages}`);
|
|
96
|
+
}
|
|
97
|
+
const out = Bun.file(outPath);
|
|
98
|
+
return { outBytes: out.size, outPath };
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
// ---------- (b) CSS bundle (Lightning CSS) ----------
|
|
102
|
+
|
|
103
|
+
async function buildCss(): Promise<{ outBytes: number; outPath: string }> {
|
|
104
|
+
ensureDist();
|
|
105
|
+
const inputPath = join(ROOT, 'client/styles/_index.css');
|
|
106
|
+
const outPath = join(DIST, 'styles.css');
|
|
107
|
+
const { code } = lcssBundle({
|
|
108
|
+
filename: inputPath,
|
|
109
|
+
minify: MODE === 'release',
|
|
110
|
+
sourceMap: false,
|
|
111
|
+
targets: browserslistToTargets([
|
|
112
|
+
'Chrome >= 110',
|
|
113
|
+
'Safari >= 16',
|
|
114
|
+
'Firefox >= 110',
|
|
115
|
+
'Edge >= 110',
|
|
116
|
+
]),
|
|
117
|
+
drafts: { customMedia: true },
|
|
118
|
+
});
|
|
119
|
+
await Bun.write(outPath, code);
|
|
120
|
+
return { outBytes: code.byteLength, outPath };
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
// ---------- (c) Server binary (bun build --compile, per-platform) ----------
|
|
124
|
+
|
|
125
|
+
async function buildServerBinary(target: PlatformTarget): Promise<{ outPath: string }> {
|
|
126
|
+
ensureDist();
|
|
127
|
+
const slug = platformSlug(target);
|
|
128
|
+
const ext = slug.startsWith('win32') ? '.exe' : '';
|
|
129
|
+
const outPath = join(DIST, `maude-${slug}${ext}`);
|
|
130
|
+
const entry = join(ROOT, 'server.ts');
|
|
131
|
+
if (!existsSync(entry)) {
|
|
132
|
+
// T7 not landed yet — fall back to the .mjs entry so this script remains runnable mid-migration.
|
|
133
|
+
const legacy = join(ROOT, 'server.mjs');
|
|
134
|
+
if (!existsSync(legacy)) throw new Error(`Neither server.ts nor server.mjs exists in ${ROOT}`);
|
|
135
|
+
const proc = Bun.spawn(
|
|
136
|
+
[
|
|
137
|
+
'bun',
|
|
138
|
+
'build',
|
|
139
|
+
'--compile',
|
|
140
|
+
`--target=${target}`,
|
|
141
|
+
'--minify',
|
|
142
|
+
'--sourcemap',
|
|
143
|
+
`--outfile=${outPath}`,
|
|
144
|
+
legacy,
|
|
145
|
+
],
|
|
146
|
+
{ cwd: ROOT, stdout: 'inherit', stderr: 'inherit' }
|
|
147
|
+
);
|
|
148
|
+
const code = await proc.exited;
|
|
149
|
+
if (code !== 0)
|
|
150
|
+
throw new Error(`bun build --compile (legacy) failed for ${target} (exit ${code})`);
|
|
151
|
+
return { outPath };
|
|
152
|
+
}
|
|
153
|
+
const proc = Bun.spawn(
|
|
154
|
+
[
|
|
155
|
+
'bun',
|
|
156
|
+
'build',
|
|
157
|
+
'--compile',
|
|
158
|
+
`--target=${target}`,
|
|
159
|
+
'--minify',
|
|
160
|
+
'--sourcemap',
|
|
161
|
+
'--smol',
|
|
162
|
+
`--outfile=${outPath}`,
|
|
163
|
+
entry,
|
|
164
|
+
],
|
|
165
|
+
{ cwd: ROOT, stdout: 'inherit', stderr: 'inherit' }
|
|
166
|
+
);
|
|
167
|
+
const code = await proc.exited;
|
|
168
|
+
if (code !== 0) throw new Error(`bun build --compile failed for ${target} (exit ${code})`);
|
|
169
|
+
return { outPath };
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
// ---------- Watch mode ----------
|
|
173
|
+
|
|
174
|
+
async function watch() {
|
|
175
|
+
await buildClient();
|
|
176
|
+
await buildCss();
|
|
177
|
+
console.log('[build:watch] initial build complete; watching client/ + server source...');
|
|
178
|
+
|
|
179
|
+
// Bun fs.watch is recursive on darwin/linux/win32.
|
|
180
|
+
const fs = await import('node:fs');
|
|
181
|
+
const seen = new Map<string, number>();
|
|
182
|
+
const debounce = 50;
|
|
183
|
+
|
|
184
|
+
const trigger = async (path: string) => {
|
|
185
|
+
const now = Date.now();
|
|
186
|
+
const last = seen.get(path) ?? 0;
|
|
187
|
+
if (now - last < debounce) return;
|
|
188
|
+
seen.set(path, now);
|
|
189
|
+
try {
|
|
190
|
+
if (path.endsWith('.css')) {
|
|
191
|
+
const r = await buildCss();
|
|
192
|
+
console.log(`[build:watch] CSS rebuilt (${r.outBytes} B)`);
|
|
193
|
+
broadcastHmr({ type: 'css-update', path: '/_client/styles.css', hash: now });
|
|
194
|
+
} else if (/\.(jsx|tsx|ts|mjs)$/.test(path)) {
|
|
195
|
+
const r = await buildClient();
|
|
196
|
+
console.log(`[build:watch] client rebuilt (${r.outBytes} B)`);
|
|
197
|
+
broadcastHmr({ type: 'module-update', path: '/_client/client.bundle.js', hash: now });
|
|
198
|
+
}
|
|
199
|
+
} catch (err) {
|
|
200
|
+
console.error('[build:watch] rebuild failed:', err);
|
|
201
|
+
}
|
|
202
|
+
};
|
|
203
|
+
|
|
204
|
+
fs.watch(join(ROOT, 'client'), { recursive: true }, (_, filename) => {
|
|
205
|
+
if (filename) void trigger(filename);
|
|
206
|
+
});
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
// HMR notifications: the dev-server (server.ts) owns the WS endpoint; here we just POST a hint.
|
|
210
|
+
async function broadcastHmr(payload: object) {
|
|
211
|
+
try {
|
|
212
|
+
const port = Bun.env.MDCC_DEV_PORT ?? '4399';
|
|
213
|
+
await fetch(`http://localhost:${port}/_hmr`, {
|
|
214
|
+
method: 'POST',
|
|
215
|
+
headers: { 'content-type': 'application/json' },
|
|
216
|
+
body: JSON.stringify(payload),
|
|
217
|
+
});
|
|
218
|
+
} catch {
|
|
219
|
+
// server may not be running yet; ignore.
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
|
|
223
|
+
// ---------- Orchestrate ----------
|
|
224
|
+
|
|
225
|
+
async function main() {
|
|
226
|
+
if (MODE === 'dry') {
|
|
227
|
+
console.log(`[build] --dry-run OK (mode=dry, target=${FLAG_TARGET ?? currentTarget()})`);
|
|
228
|
+
return;
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
if (WATCH) {
|
|
232
|
+
await watch();
|
|
233
|
+
// Keep alive — fs.watch holds the event loop.
|
|
234
|
+
await new Promise(() => {});
|
|
235
|
+
return;
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
console.log(`[build] mode=${MODE}`);
|
|
239
|
+
|
|
240
|
+
const t0 = performance.now();
|
|
241
|
+
const client = await buildClient();
|
|
242
|
+
const t1 = performance.now();
|
|
243
|
+
console.log(
|
|
244
|
+
`[build] client.bundle.js ${client.outBytes.toLocaleString()} B (${(t1 - t0).toFixed(0)} ms)`
|
|
245
|
+
);
|
|
246
|
+
|
|
247
|
+
const css = await buildCss();
|
|
248
|
+
const t2 = performance.now();
|
|
249
|
+
console.log(
|
|
250
|
+
`[build] styles.css ${css.outBytes.toLocaleString()} B (${(t2 - t1).toFixed(0)} ms)`
|
|
251
|
+
);
|
|
252
|
+
|
|
253
|
+
if (MODE === 'release') {
|
|
254
|
+
const targets: PlatformTarget[] = FLAG_TARGET
|
|
255
|
+
? [FLAG_TARGET as PlatformTarget]
|
|
256
|
+
: [currentTarget()];
|
|
257
|
+
for (const target of targets) {
|
|
258
|
+
const t = performance.now();
|
|
259
|
+
const bin = await buildServerBinary(target);
|
|
260
|
+
console.log(`[build] ${bin.outPath} (${(performance.now() - t).toFixed(0)} ms)`);
|
|
261
|
+
}
|
|
262
|
+
}
|
|
263
|
+
}
|
|
264
|
+
|
|
265
|
+
await main();
|
|
266
|
+
|
|
267
|
+
export { buildClient, buildCss, buildServerBinary, PLATFORM_MATRIX, type PlatformTarget };
|