@voltx/server 0.4.2 → 0.4.4

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 ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 Promptly AI Team
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/dist/index.cjs CHANGED
@@ -40,7 +40,8 @@ __export(index_exports, {
40
40
  filePathToUrlPath: () => filePathToUrlPath,
41
41
  registerSSR: () => registerSSR,
42
42
  registerStaticFiles: () => registerStaticFiles,
43
- scanAndRegisterRoutes: () => scanAndRegisterRoutes
43
+ scanAndRegisterRoutes: () => scanAndRegisterRoutes,
44
+ voltxRouter: () => voltxRouter
44
45
  });
45
46
  module.exports = __toCommonJS(index_exports);
46
47
 
@@ -309,6 +310,86 @@ function createViteDevConfig(options = {}) {
309
310
  };
310
311
  }
311
312
 
313
+ // src/vite-plugin.ts
314
+ function voltxRouter(options = {}) {
315
+ const pagesDir = options.pagesDir ?? "src/pages";
316
+ const virtualModuleId = "virtual:voltx-routes";
317
+ const resolvedVirtualModuleId = "\0" + virtualModuleId;
318
+ return {
319
+ name: "voltx-router",
320
+ enforce: "pre",
321
+ config() {
322
+ return {
323
+ ssr: {
324
+ // react-router ships CJS — force Vite to bundle its .mjs for SSR
325
+ noExternal: ["react-router"]
326
+ }
327
+ };
328
+ },
329
+ resolveId(id) {
330
+ if (id === virtualModuleId) {
331
+ return resolvedVirtualModuleId;
332
+ }
333
+ },
334
+ load(id) {
335
+ if (id === resolvedVirtualModuleId) {
336
+ return `
337
+ import { createElement } from "react";
338
+ import { Routes, Route } from "react-router";
339
+
340
+ const pages = import.meta.glob("/${pagesDir}/**/*.tsx", { eager: true });
341
+
342
+ function buildRoutes() {
343
+ const routes = [];
344
+ for (const [filePath, mod] of Object.entries(pages)) {
345
+ const Component = mod.default;
346
+ if (!Component) continue;
347
+
348
+ let routePath = filePath
349
+ .replace("/${pagesDir}", "")
350
+ .replace(/\\.tsx$/, "")
351
+ .replace(/\\/index$/, "/")
352
+ .replace(/\\[([^\\]]+)\\]/g, ":$1");
353
+
354
+ if (!routePath.startsWith("/")) routePath = "/" + routePath;
355
+ if (routePath !== "/" && routePath.endsWith("/")) {
356
+ routePath = routePath.slice(0, -1);
357
+ }
358
+
359
+ routes.push({ path: routePath, Component });
360
+ }
361
+ return routes;
362
+ }
363
+
364
+ const routes = buildRoutes();
365
+
366
+ export function VoltxRoutes() {
367
+ return createElement(
368
+ Routes,
369
+ null,
370
+ routes.map(({ path, Component }) =>
371
+ createElement(Route, { key: path, path, element: createElement(Component) })
372
+ )
373
+ );
374
+ }
375
+
376
+ export { routes };
377
+ `;
378
+ }
379
+ },
380
+ // HMR: when a file in src/pages/ is added/removed, invalidate the virtual module
381
+ handleHotUpdate({ file, server }) {
382
+ if (file.includes(pagesDir.replace(/\//g, "/"))) {
383
+ const mod = server.moduleGraph.getModuleById(resolvedVirtualModuleId);
384
+ if (mod) {
385
+ server.moduleGraph.invalidateModule(mod);
386
+ server.ws.send({ type: "full-reload" });
387
+ }
388
+ }
389
+ }
390
+ };
391
+ }
392
+
312
393
  // src/ssr.ts
313
394
  var import_node_path3 = require("path");
314
395
  var import_node_fs = require("fs");
@@ -364,9 +445,8 @@ function registerSSR(app, vite, options = {}) {
364
445
  try {
365
446
  const { createServer: createViteServer } = await import("vite");
366
447
  const devServer = await createViteServer({
367
- server: { middlewareMode: true },
368
- appType: "custom",
369
- optimizeDeps: { disabled: true }
448
+ server: { middlewareMode: true, hmr: false },
449
+ appType: "custom"
370
450
  });
371
451
  const mod = await devServer.ssrLoadModule(entryServer);
372
452
  render = mod.render;
@@ -450,7 +530,7 @@ ${cssLinks}
450
530
  }
451
531
 
452
532
  // src/index.ts
453
- var VERSION = "0.4.2";
533
+ var VERSION = "0.4.4";
454
534
  // Annotate the CommonJS export names for ESM import in node:
455
535
  0 && (module.exports = {
456
536
  Hono,
@@ -463,5 +543,6 @@ var VERSION = "0.4.2";
463
543
  filePathToUrlPath,
464
544
  registerSSR,
465
545
  registerStaticFiles,
466
- scanAndRegisterRoutes
546
+ scanAndRegisterRoutes,
547
+ voltxRouter
467
548
  });
package/dist/index.d.cts CHANGED
@@ -1,6 +1,7 @@
1
1
  import * as hono from 'hono';
2
2
  import { Context, Hono } from 'hono';
3
3
  export { Context, Hono } from 'hono';
4
+ import { Plugin } from 'vite';
4
5
 
5
6
  interface ServerConfig {
6
7
  /** Port to listen on (default: 3000) */
@@ -176,6 +177,24 @@ declare function createViteDevConfig(options?: ViteDevOptions): {
176
177
  entry: string;
177
178
  };
178
179
 
180
+ interface VoltxRouterOptions {
181
+ /** Directory to scan for page files (default: "src/pages") */
182
+ pagesDir?: string;
183
+ }
184
+ /**
185
+ * VoltX file-based router plugin for Vite.
186
+ *
187
+ * Scans `src/pages/` and generates a virtual module that maps
188
+ * file paths to routes — just like Next.js.
189
+ *
190
+ * Convention:
191
+ * src/pages/index.tsx → /
192
+ * src/pages/about.tsx → /about
193
+ * src/pages/blog/index.tsx → /blog
194
+ * src/pages/blog/[slug].tsx → /blog/:slug
195
+ */
196
+ declare function voltxRouter(options?: VoltxRouterOptions): Plugin;
197
+
179
198
  interface SSROptions {
180
199
  /** Path to entry-server module (default: src/entry-server.tsx) */
181
200
  entryServer?: string;
@@ -223,6 +242,6 @@ interface ViteDevServer {
223
242
  */
224
243
  declare function registerSSR(app: Hono, vite: ViteDevServer | null, options?: SSROptions): void;
225
244
 
226
- declare const VERSION = "0.4.2";
245
+ declare const VERSION = "0.4.4";
227
246
 
228
- export { type CorsConfig, type HttpMethod, type MiddlewareHandler, type RouteEntry, type RouteHandler, type RouteModule, type SSROptions, type ServerConfig, type ServerInfo, VERSION, type ViteDevOptions, type VoltxServer, createCorsMiddleware, createErrorHandler, createLoggerMiddleware, createServer, createViteDevConfig, filePathToUrlPath, registerSSR, registerStaticFiles, scanAndRegisterRoutes };
247
+ export { type CorsConfig, type HttpMethod, type MiddlewareHandler, type RouteEntry, type RouteHandler, type RouteModule, type SSROptions, type ServerConfig, type ServerInfo, VERSION, type ViteDevOptions, type VoltxRouterOptions, type VoltxServer, createCorsMiddleware, createErrorHandler, createLoggerMiddleware, createServer, createViteDevConfig, filePathToUrlPath, registerSSR, registerStaticFiles, scanAndRegisterRoutes, voltxRouter };
package/dist/index.d.ts CHANGED
@@ -1,6 +1,7 @@
1
1
  import * as hono from 'hono';
2
2
  import { Context, Hono } from 'hono';
3
3
  export { Context, Hono } from 'hono';
4
+ import { Plugin } from 'vite';
4
5
 
5
6
  interface ServerConfig {
6
7
  /** Port to listen on (default: 3000) */
@@ -176,6 +177,24 @@ declare function createViteDevConfig(options?: ViteDevOptions): {
176
177
  entry: string;
177
178
  };
178
179
 
180
+ interface VoltxRouterOptions {
181
+ /** Directory to scan for page files (default: "src/pages") */
182
+ pagesDir?: string;
183
+ }
184
+ /**
185
+ * VoltX file-based router plugin for Vite.
186
+ *
187
+ * Scans `src/pages/` and generates a virtual module that maps
188
+ * file paths to routes — just like Next.js.
189
+ *
190
+ * Convention:
191
+ * src/pages/index.tsx → /
192
+ * src/pages/about.tsx → /about
193
+ * src/pages/blog/index.tsx → /blog
194
+ * src/pages/blog/[slug].tsx → /blog/:slug
195
+ */
196
+ declare function voltxRouter(options?: VoltxRouterOptions): Plugin;
197
+
179
198
  interface SSROptions {
180
199
  /** Path to entry-server module (default: src/entry-server.tsx) */
181
200
  entryServer?: string;
@@ -223,6 +242,6 @@ interface ViteDevServer {
223
242
  */
224
243
  declare function registerSSR(app: Hono, vite: ViteDevServer | null, options?: SSROptions): void;
225
244
 
226
- declare const VERSION = "0.4.2";
245
+ declare const VERSION = "0.4.4";
227
246
 
228
- export { type CorsConfig, type HttpMethod, type MiddlewareHandler, type RouteEntry, type RouteHandler, type RouteModule, type SSROptions, type ServerConfig, type ServerInfo, VERSION, type ViteDevOptions, type VoltxServer, createCorsMiddleware, createErrorHandler, createLoggerMiddleware, createServer, createViteDevConfig, filePathToUrlPath, registerSSR, registerStaticFiles, scanAndRegisterRoutes };
247
+ export { type CorsConfig, type HttpMethod, type MiddlewareHandler, type RouteEntry, type RouteHandler, type RouteModule, type SSROptions, type ServerConfig, type ServerInfo, VERSION, type ViteDevOptions, type VoltxRouterOptions, type VoltxServer, createCorsMiddleware, createErrorHandler, createLoggerMiddleware, createServer, createViteDevConfig, filePathToUrlPath, registerSSR, registerStaticFiles, scanAndRegisterRoutes, voltxRouter };
package/dist/index.js CHANGED
@@ -263,6 +263,86 @@ function createViteDevConfig(options = {}) {
263
263
  };
264
264
  }
265
265
 
266
+ // src/vite-plugin.ts
267
+ function voltxRouter(options = {}) {
268
+ const pagesDir = options.pagesDir ?? "src/pages";
269
+ const virtualModuleId = "virtual:voltx-routes";
270
+ const resolvedVirtualModuleId = "\0" + virtualModuleId;
271
+ return {
272
+ name: "voltx-router",
273
+ enforce: "pre",
274
+ config() {
275
+ return {
276
+ ssr: {
277
+ // react-router ships CJS — force Vite to bundle its .mjs for SSR
278
+ noExternal: ["react-router"]
279
+ }
280
+ };
281
+ },
282
+ resolveId(id) {
283
+ if (id === virtualModuleId) {
284
+ return resolvedVirtualModuleId;
285
+ }
286
+ },
287
+ load(id) {
288
+ if (id === resolvedVirtualModuleId) {
289
+ return `
290
+ import { createElement } from "react";
291
+ import { Routes, Route } from "react-router";
292
+
293
+ const pages = import.meta.glob("/${pagesDir}/**/*.tsx", { eager: true });
294
+
295
+ function buildRoutes() {
296
+ const routes = [];
297
+ for (const [filePath, mod] of Object.entries(pages)) {
298
+ const Component = mod.default;
299
+ if (!Component) continue;
300
+
301
+ let routePath = filePath
302
+ .replace("/${pagesDir}", "")
303
+ .replace(/\\.tsx$/, "")
304
+ .replace(/\\/index$/, "/")
305
+ .replace(/\\[([^\\]]+)\\]/g, ":$1");
306
+
307
+ if (!routePath.startsWith("/")) routePath = "/" + routePath;
308
+ if (routePath !== "/" && routePath.endsWith("/")) {
309
+ routePath = routePath.slice(0, -1);
310
+ }
311
+
312
+ routes.push({ path: routePath, Component });
313
+ }
314
+ return routes;
315
+ }
316
+
317
+ const routes = buildRoutes();
318
+
319
+ export function VoltxRoutes() {
320
+ return createElement(
321
+ Routes,
322
+ null,
323
+ routes.map(({ path, Component }) =>
324
+ createElement(Route, { key: path, path, element: createElement(Component) })
325
+ )
326
+ );
327
+ }
328
+
329
+ export { routes };
330
+ `;
331
+ }
332
+ },
333
+ // HMR: when a file in src/pages/ is added/removed, invalidate the virtual module
334
+ handleHotUpdate({ file, server }) {
335
+ if (file.includes(pagesDir.replace(/\//g, "/"))) {
336
+ const mod = server.moduleGraph.getModuleById(resolvedVirtualModuleId);
337
+ if (mod) {
338
+ server.moduleGraph.invalidateModule(mod);
339
+ server.ws.send({ type: "full-reload" });
340
+ }
341
+ }
342
+ }
343
+ };
344
+ }
345
+
266
346
  // src/ssr.ts
267
347
  import { resolve as resolve2 } from "path";
268
348
  import { readFileSync, existsSync } from "fs";
@@ -318,9 +398,8 @@ function registerSSR(app, vite, options = {}) {
318
398
  try {
319
399
  const { createServer: createViteServer } = await import("vite");
320
400
  const devServer = await createViteServer({
321
- server: { middlewareMode: true },
322
- appType: "custom",
323
- optimizeDeps: { disabled: true }
401
+ server: { middlewareMode: true, hmr: false },
402
+ appType: "custom"
324
403
  });
325
404
  const mod = await devServer.ssrLoadModule(entryServer);
326
405
  render = mod.render;
@@ -404,7 +483,7 @@ ${cssLinks}
404
483
  }
405
484
 
406
485
  // src/index.ts
407
- var VERSION = "0.4.2";
486
+ var VERSION = "0.4.4";
408
487
  export {
409
488
  Hono2 as Hono,
410
489
  VERSION,
@@ -416,5 +495,6 @@ export {
416
495
  filePathToUrlPath,
417
496
  registerSSR,
418
497
  registerStaticFiles,
419
- scanAndRegisterRoutes
498
+ scanAndRegisterRoutes,
499
+ voltxRouter
420
500
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@voltx/server",
3
- "version": "0.4.2",
3
+ "version": "0.4.4",
4
4
  "description": "VoltX Server — Hono-based HTTP server with file-based routing, SSE streaming, and static file serving",
5
5
  "type": "module",
6
6
  "main": "./dist/index.cjs",
@@ -13,31 +13,47 @@
13
13
  "require": "./dist/index.cjs"
14
14
  }
15
15
  },
16
- "files": ["dist"],
17
- "scripts": {
18
- "build": "tsup src/index.ts --format cjs,esm --dts --clean",
19
- "dev": "tsup src/index.ts --format cjs,esm --dts --watch",
20
- "clean": "rm -rf dist"
21
- },
16
+ "files": [
17
+ "dist"
18
+ ],
22
19
  "dependencies": {
23
- "hono": "^4.7.0",
24
- "@hono/node-server": "^1.14.0"
20
+ "@hono/node-server": "^1.14.0",
21
+ "hono": "^4.7.0"
25
22
  },
26
23
  "peerDependencies": {
27
24
  "react": ">=18.0.0",
28
- "react-dom": ">=18.0.0"
25
+ "react-dom": ">=18.0.0",
26
+ "vite": ">=5.0.0"
29
27
  },
30
28
  "peerDependenciesMeta": {
31
- "react": { "optional": true },
32
- "react-dom": { "optional": true }
29
+ "react": {
30
+ "optional": true
31
+ },
32
+ "react-dom": {
33
+ "optional": true
34
+ },
35
+ "vite": {
36
+ "optional": true
37
+ }
33
38
  },
34
39
  "devDependencies": {
40
+ "@types/react": "^19.0.0",
41
+ "@types/react-dom": "^19.0.0",
35
42
  "tsup": "^8.0.0",
36
43
  "typescript": "^5.7.0",
37
- "@types/react": "^19.0.0",
38
- "@types/react-dom": "^19.0.0"
44
+ "vite": "^8.0.1"
39
45
  },
40
- "keywords": ["voltx", "server", "hono", "http", "routing", "file-based", "sse", "streaming", "middleware"],
46
+ "keywords": [
47
+ "voltx",
48
+ "server",
49
+ "hono",
50
+ "http",
51
+ "routing",
52
+ "file-based",
53
+ "sse",
54
+ "streaming",
55
+ "middleware"
56
+ ],
41
57
  "license": "MIT",
42
58
  "repository": {
43
59
  "type": "git",
@@ -45,5 +61,10 @@
45
61
  "directory": "packages/server"
46
62
  },
47
63
  "homepage": "https://voltx.co.in",
48
- "author": "Promptly AI Team"
49
- }
64
+ "author": "Promptly AI Team",
65
+ "scripts": {
66
+ "build": "tsup src/index.ts --format cjs,esm --dts --clean --external vite",
67
+ "dev": "tsup src/index.ts --format cjs,esm --dts --watch",
68
+ "clean": "rm -rf dist"
69
+ }
70
+ }