@mauroandre/velojs 0.0.36 → 0.0.38

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 (32) hide show
  1. package/README.md +20 -10
  2. package/agent/AGENTS.md +143 -0
  3. package/agent/skills/velojs-actions/SKILL.md +192 -0
  4. package/agent/skills/velojs-components/SKILL.md +99 -0
  5. package/agent/skills/velojs-endpoints/SKILL.md +187 -0
  6. package/agent/skills/velojs-event-streams/SKILL.md +705 -0
  7. package/agent/skills/velojs-getting-started/SKILL.md +191 -0
  8. package/agent/skills/velojs-hooks/SKILL.md +103 -0
  9. package/agent/skills/velojs-link-component/SKILL.md +67 -0
  10. package/agent/skills/velojs-loaders/SKILL.md +134 -0
  11. package/agent/skills/velojs-middlewares/SKILL.md +143 -0
  12. package/agent/skills/velojs-production-deploy/SKILL.md +96 -0
  13. package/agent/skills/velojs-routes/SKILL.md +209 -0
  14. package/agent/skills/velojs-scripts-component/SKILL.md +62 -0
  15. package/agent/skills/velojs-server-api/SKILL.md +155 -0
  16. package/agent/skills/velojs-sockets/SKILL.md +303 -0
  17. package/agent/skills/velojs-static-generation/SKILL.md +148 -0
  18. package/agent/skills/velojs-testing/SKILL.md +472 -0
  19. package/agent/skills/velojs-type-reference/SKILL.md +142 -0
  20. package/agent/skills/velojs-vite-plugin/SKILL.md +71 -0
  21. package/dist/client.js +58 -47
  22. package/dist/components.js +18 -16
  23. package/dist/hooks.d.ts +3 -2
  24. package/dist/hooks.js +107 -110
  25. package/dist/loader-store.d.ts +49 -0
  26. package/dist/loader-store.js +103 -0
  27. package/dist/server.js +11 -11
  28. package/dist/testing/createTestApp.d.ts +1 -1
  29. package/dist/testing/index.d.ts +1 -1
  30. package/dist/testing/types.d.ts +7 -3
  31. package/dist/vite.js +276 -277
  32. package/package.json +6 -2
@@ -0,0 +1,103 @@
1
+ import { signal as f } from "@preact/signals";
2
+ const p = f(!1), c = /* @__PURE__ */ new Map(), l = /* @__PURE__ */ new Map(), d = /* @__PURE__ */ new Map(), _ = /* @__PURE__ */ new Map(), s = /* @__PURE__ */ new Map(), h = /* @__PURE__ */ new WeakSet();
3
+ let u = !1;
4
+ function S(t) {
5
+ y();
6
+ let e = c.get(t);
7
+ return e || (e = f(null), c.set(t, e)), e;
8
+ }
9
+ function w(t) {
10
+ let e = l.get(t);
11
+ return e || (e = f(!1), l.set(t, e)), e;
12
+ }
13
+ function y() {
14
+ if (u || typeof window > "u") return;
15
+ u = !0;
16
+ const t = window.__PAGE_DATA__;
17
+ if (t)
18
+ for (const e of Object.keys(t)) {
19
+ if (e.startsWith("__")) continue;
20
+ let n = c.get(e);
21
+ n || (n = f(null), c.set(e, n)), n.value = t[e];
22
+ }
23
+ }
24
+ function O(t) {
25
+ if (h.has(t)) return;
26
+ h.add(t);
27
+ const e = (n) => {
28
+ for (const o of n) {
29
+ const i = o.module?.metadata;
30
+ i?.moduleId && i.fullPath !== void 0 && d.set(i.moduleId, i.fullPath), o.children && e(o.children);
31
+ }
32
+ };
33
+ if (e(t), typeof window < "u") {
34
+ y();
35
+ for (const n of c.keys()) v(n, window.location.pathname);
36
+ }
37
+ }
38
+ const k = (t) => t.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
39
+ function E(t, e) {
40
+ const n = [], o = t.split("/").map((r) => r.startsWith(":") ? (n.push(r.slice(1)), "([^/]+)") : k(r)).join("/"), i = e.match(new RegExp(`^${o}(?:/.*)?$`));
41
+ if (!i) return null;
42
+ const a = {};
43
+ return n.forEach((r, L) => {
44
+ a[r] = i[L + 1];
45
+ }), a;
46
+ }
47
+ function g(t, e) {
48
+ const n = d.get(t);
49
+ if (n === void 0) return null;
50
+ const o = E(n, e);
51
+ return o === null ? null : JSON.stringify(o);
52
+ }
53
+ function v(t, e) {
54
+ const n = g(t, e);
55
+ n !== null && _.set(t, n);
56
+ }
57
+ function P(t) {
58
+ if (typeof __VELO_STATIC__ < "u" && __VELO_STATIC__) return `${t === "/" ? "" : t}/index.json`;
59
+ const n = new URLSearchParams(window.location.search);
60
+ return n.set("_data", "1"), `${t}?${n.toString()}`;
61
+ }
62
+ async function m(t, e, n) {
63
+ if (typeof window > "u" || t.length === 0) return;
64
+ const o = P(e);
65
+ for (const a of t) w(a).value = !0;
66
+ let i = n ? s.get(o) : void 0;
67
+ i || (i = fetch(o, { cache: "no-cache" }).then((a) => a.json()), n && (s.set(o, i), i.catch(() => {
68
+ }).then(() => s.delete(o))));
69
+ try {
70
+ const a = await i;
71
+ typeof __VELO_BUILD_HASH__ < "u" && a.__buildHash && a.__buildHash !== __VELO_BUILD_HASH__ && (p.value = !0);
72
+ for (const r of t)
73
+ r in a && (S(r).value = a[r], v(r, e));
74
+ } catch {
75
+ } finally {
76
+ for (const a of t) w(a).value = !1;
77
+ }
78
+ }
79
+ function $(t) {
80
+ if (typeof window > "u") return;
81
+ const e = [];
82
+ for (const n of c.keys()) {
83
+ const o = g(n, t);
84
+ o !== null && _.get(n) !== o && e.push(n);
85
+ }
86
+ m(e, t, !0);
87
+ }
88
+ function H(t) {
89
+ typeof window > "u" || m([t], window.location.pathname, !1);
90
+ }
91
+ function M() {
92
+ c.clear(), l.clear(), d.clear(), _.clear(), s.clear(), u = !1, p.value = !1;
93
+ }
94
+ export {
95
+ M as __resetLoaderStore,
96
+ p as __veloUpdatePending,
97
+ E as extractParams,
98
+ S as loaderEntry,
99
+ w as loaderLoading,
100
+ H as refetchModule,
101
+ O as registerRoutePatterns,
102
+ $ as syncLocation
103
+ };
package/dist/server.js CHANGED
@@ -5,27 +5,27 @@ import { trimTrailingSlash as j } from "hono/trailing-slash";
5
5
  import { render as A } from "preact-render-to-string";
6
6
  import { Router as C } from "wouter-preact";
7
7
  import { AsyncLocalStorage as k } from "node:async_hooks";
8
- import { getAppContext as v } from "./app-context.js";
8
+ import { getAppContext as w } from "./app-context.js";
9
9
  import { flushPendingStreamRoutes as $, registerStreamHandler as D } from "./events.js";
10
10
  import { registerSocketRoutes as I, injectWebSocketServer as y } from "./sockets.js";
11
11
  const S = new k();
12
12
  globalThis.__veloServerData = S;
13
- let w = null;
13
+ let v = null;
14
14
  function Y(e) {
15
- if (w) {
16
- e(w);
15
+ if (v) {
16
+ e(v);
17
17
  return;
18
18
  }
19
- v().serverCallbacks.push(e);
19
+ w().serverCallbacks.push(e);
20
20
  }
21
21
  function P(e) {
22
- w = e;
23
- const t = v();
22
+ v = e;
23
+ const t = w();
24
24
  for (const s of t.serverCallbacks) s(e);
25
25
  t.serverCallbacks.length = 0;
26
26
  }
27
27
  function Z(e) {
28
- v().pendingRoutes.push(e);
28
+ w().pendingRoutes.push(e);
29
29
  }
30
30
  const N = (e, t, s, r) => {
31
31
  if (r && r !== 200 && e.status(r), e.req.query("_data") === "1") {
@@ -208,7 +208,7 @@ const N = (e, t, s, r) => {
208
208
  ), l && c && !n.module) {
209
209
  const h = n.method;
210
210
  h === "GET" && s.has(a) && console.warn(
211
- `[velojs] path "${a}" has both a page GET and an endpoint GET; endpoint will win. Consider renaming one.`
211
+ `[velojs] path "${a}" has both a page GET and an endpoint GET; the page wins and the endpoint is unreachable. Consider renaming one.`
212
212
  );
213
213
  const d = n.handler, m = async (f) => await d({
214
214
  c: f,
@@ -228,12 +228,12 @@ const N = (e, t, s, r) => {
228
228
  }, W = async (e) => {
229
229
  const t = new R();
230
230
  t.use(j()), process.env.NODE_ENV !== "production" && t.use("*", T());
231
- const r = v().pendingRoutes.splice(0);
231
+ const r = w().pendingRoutes.splice(0);
232
232
  for (const n of r)
233
233
  await n(t);
234
234
  _(t, e), b(t, e), await H(t, e);
235
235
  const o = V(e);
236
- if (q(t, e, o), await I(t, e), $(t), process.env.NODE_ENV !== "production" && !w) {
236
+ if (q(t, e, o), await I(t, e), $(t), process.env.NODE_ENV !== "production" && !v) {
237
237
  const n = globalThis.__veloDevServer;
238
238
  n && (P(n), await y(t, n));
239
239
  }
@@ -11,7 +11,7 @@ import type { TestApp, CreateTestAppOptions } from "./types.js";
11
11
  *
12
12
  * ```typescript
13
13
  * import { createTestApp } from "@mauroandre/velojs/testing";
14
- * import { routes } from "../app/routes.js";
14
+ * import routes from "../app/routes.js";
15
15
  *
16
16
  * const app = await createTestApp({
17
17
  * routes,
@@ -8,7 +8,7 @@
8
8
  * @example
9
9
  * ```typescript
10
10
  * import { createTestApp } from "@mauroandre/velojs/testing";
11
- * import { routes } from "../app/routes.js";
11
+ * import routes from "../app/routes.js";
12
12
  *
13
13
  * const app = await createTestApp({ routes });
14
14
  * const res = await app.get("/api/health");
@@ -10,7 +10,7 @@ export type Headers = Record<string, string>;
10
10
  export type Query = Record<string, string | string[]>;
11
11
  export type Params = Record<string, string>;
12
12
  export interface CreateTestAppOptions {
13
- /** App routes — typically `import { routes } from "./app/routes.js"`. */
13
+ /** App routes — typically `import routes from "./app/routes.js"` (the default export of `routes.tsx`). */
14
14
  routes: AppRoutes;
15
15
  /**
16
16
  * Optional setup that runs once before the app is created.
@@ -129,8 +129,12 @@ export interface TestApp {
129
129
  /**
130
130
  * Invoke a `loader` server function. By default unwraps the response data:
131
131
  * - Resolved normally → returns the loader's return value
132
- * - Threw → re-throws
133
- * - Redirected → returns a `TestResponse` for status inspection
132
+ * - Redirected (3xx) → returns a `TestResponse` for status inspection
133
+ * - Non-2xx (a `c.status()` set by the loader, or a 500 from a thrown
134
+ * error) → returns a `TestResponse`. Nothing is re-thrown: the loader
135
+ * runs inside a Hono handler, which catches and turns the throw into a
136
+ * 500 response, so `hono.fetch` resolves. Assert on `res.status`, not
137
+ * with `rejects.toThrow()`.
134
138
  */
135
139
  loader<T = any>(fn: Function | string, opts?: LoaderRequestOptions): Promise<T | TestResponse>;
136
140
  subscribe<TEvent = any, TSnapshot = any>(stream: EventStream<TEvent, TSnapshot> | string, opts?: SubscribeOptions): Promise<TestSubscription<TEvent, TSnapshot>>;