@oh-my-pi/omp-stats 12.7.6 → 12.8.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.
Files changed (2) hide show
  1. package/package.json +4 -3
  2. package/src/server.ts +8 -74
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@oh-my-pi/omp-stats",
3
- "version": "12.7.6",
3
+ "version": "12.8.0",
4
4
  "description": "Local observability dashboard for pi AI usage statistics",
5
5
  "type": "module",
6
6
  "main": "./src/index.ts",
@@ -52,8 +52,9 @@
52
52
  "url": "https://github.com/can1357/oh-my-pi/issues"
53
53
  },
54
54
  "dependencies": {
55
- "@oh-my-pi/pi-ai": "12.7.6",
56
- "@oh-my-pi/pi-utils": "12.7.6",
55
+ "@oh-my-pi/pi-ai": "12.8.0",
56
+ "@oh-my-pi/pi-utils": "12.8.0",
57
+ "@tailwindcss/node": "4",
57
58
  "chart.js": "4.5.1",
58
59
  "date-fns": "^4.1.0",
59
60
  "lucide-react": "^0.564.0",
package/src/server.ts CHANGED
@@ -1,7 +1,7 @@
1
1
  import * as fs from "node:fs/promises";
2
2
  import * as os from "node:os";
3
3
  import * as path from "node:path";
4
- import { compile } from "tailwindcss";
4
+ import { $ } from "bun";
5
5
  import {
6
6
  getDashboardStats,
7
7
  getRecentErrors,
@@ -12,33 +12,6 @@ import {
12
12
  } from "./aggregator";
13
13
  import { EMBEDDED_CLIENT_ARCHIVE_TAR_GZ_BASE64 } from "./embedded-client.generated";
14
14
 
15
- /**
16
- * Extract Tailwind class names from source files by scanning for className attributes.
17
- */
18
- async function extractTailwindClasses(dir: string): Promise<Set<string>> {
19
- const classes = new Set<string>();
20
- const classPattern = /className\s*=\s*["'`]([^"'`]+)["'`]/g;
21
- async function scanDir(currentDir: string): Promise<void> {
22
- const entries = await fs.readdir(currentDir, { withFileTypes: true });
23
- for (const entry of entries) {
24
- const fullPath = path.join(currentDir, entry.name);
25
- if (entry.isDirectory()) {
26
- await scanDir(fullPath);
27
- } else if (entry.isFile() && /\.(tsx|ts|jsx|js)$/.test(entry.name)) {
28
- const content = await Bun.file(fullPath).text();
29
- const matches = content.matchAll(classPattern);
30
- for (const match of matches) {
31
- for (const cls of match[1].split(/\s+/)) {
32
- if (cls) classes.add(cls);
33
- }
34
- }
35
- }
36
- }
37
- }
38
- await scanDir(dir);
39
- return classes;
40
- }
41
-
42
15
  const CLIENT_DIR = path.join(import.meta.dir, "client");
43
16
  const STATIC_DIR = path.join(import.meta.dir, "..", "dist", "client");
44
17
  const IS_BUN_COMPILED =
@@ -99,33 +72,6 @@ async function getCompiledClientDir(): Promise<string> {
99
72
  return compiledClientDirPromise;
100
73
  }
101
74
 
102
- async function buildTailwindCss(inputPath: string, outputPath: string): Promise<void> {
103
- const sourceCss = await Bun.file(inputPath).text();
104
- const clientDir = path.dirname(inputPath);
105
- const candidates = await extractTailwindClasses(clientDir);
106
- const compiler = await compile(sourceCss, {
107
- base: clientDir,
108
- loadStylesheet: async (id: string, base: string) => {
109
- if (id === "tailwindcss/index.css" || id === "tailwindcss") {
110
- const tailwindPath = require.resolve("tailwindcss/index.css", { paths: [base] });
111
- return {
112
- path: tailwindPath,
113
- base: path.dirname(tailwindPath),
114
- content: await Bun.file(tailwindPath).text(),
115
- };
116
- }
117
- const resolved = path.resolve(base, id);
118
- return {
119
- path: resolved,
120
- base: path.dirname(resolved),
121
- content: await Bun.file(resolved).text(),
122
- };
123
- },
124
- });
125
- const result = compiler.build([...candidates]);
126
- await Bun.write(outputPath, result);
127
- }
128
-
129
75
  async function getLatestMtime(dir: string): Promise<number> {
130
76
  let latest = 0;
131
77
  const entries = await fs.readdir(dir, { withFileTypes: true });
@@ -174,25 +120,13 @@ const ensureClientBuild = async () => {
174
120
 
175
121
  await fs.rm(STATIC_DIR, { recursive: true, force: true });
176
122
 
177
- // Build Tailwind CSS with the library API
178
- console.log("Building Tailwind CSS...");
179
- try {
180
- await buildTailwindCss(path.join(CLIENT_DIR, "styles.css"), path.join(STATIC_DIR, "styles.css"));
181
- } catch (error) {
182
- console.error("Tailwind build failed:", error);
183
- }
184
-
185
- console.log("Building React app...");
186
- const result = await Bun.build({
187
- entrypoints: [path.join(CLIENT_DIR, "index.tsx")],
188
- outdir: STATIC_DIR,
189
- minify: true,
190
- naming: "[dir]/[name].[ext]",
191
- });
192
-
193
- if (!result.success) {
194
- const errors = result.logs.map(log => log.message).join("\n");
195
- throw new Error(`Failed to build stats client:\n${errors}`);
123
+ console.log("Building stats client...");
124
+ const packageRoot = path.join(import.meta.dir, "..");
125
+ const buildResult = await $`bun run build.ts`.cwd(packageRoot).quiet().nothrow();
126
+ if (buildResult.exitCode !== 0) {
127
+ const output = buildResult.text().trim();
128
+ const details = output ? `\n${output}` : "";
129
+ throw new Error(`Failed to build stats client (exit ${buildResult.exitCode})${details}`);
196
130
  }
197
131
 
198
132
  const indexHtml = `<!DOCTYPE html>