@emkodev/emroute 1.8.0 → 1.8.2-beta.2

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 (51) hide show
  1. package/README.md +1 -1
  2. package/core/renderer/html.renderer.ts +1 -1
  3. package/core/renderer/md.renderer.ts +1 -1
  4. package/core/renderer/ssr.renderer.ts +21 -1
  5. package/core/server/emroute.server.ts +45 -52
  6. package/core/util/widget-resolve.util.ts +2 -2
  7. package/core/widget/widget.registry.ts +29 -2
  8. package/dist/core/renderer/html.renderer.js +1 -1
  9. package/dist/core/renderer/html.renderer.js.map +1 -1
  10. package/dist/core/renderer/md.renderer.js +1 -1
  11. package/dist/core/renderer/md.renderer.js.map +1 -1
  12. package/dist/core/renderer/ssr.renderer.d.ts +4 -1
  13. package/dist/core/renderer/ssr.renderer.js +20 -0
  14. package/dist/core/renderer/ssr.renderer.js.map +1 -1
  15. package/dist/core/server/emroute.server.d.ts +0 -2
  16. package/dist/core/server/emroute.server.js +36 -47
  17. package/dist/core/server/emroute.server.js.map +1 -1
  18. package/dist/core/util/widget-resolve.util.d.ts +1 -3
  19. package/dist/core/util/widget-resolve.util.js +2 -2
  20. package/dist/core/util/widget-resolve.util.js.map +1 -1
  21. package/dist/core/widget/widget.registry.d.ts +8 -0
  22. package/dist/core/widget/widget.registry.js +28 -2
  23. package/dist/core/widget/widget.registry.js.map +1 -1
  24. package/dist/emroute.js +227 -66
  25. package/dist/emroute.js.map +13 -13
  26. package/dist/runtime/abstract.runtime.js +7 -3
  27. package/dist/runtime/abstract.runtime.js.map +1 -1
  28. package/dist/runtime/fetch.runtime.js +7 -1
  29. package/dist/runtime/fetch.runtime.js.map +1 -1
  30. package/dist/server/build.util.d.ts +1 -1
  31. package/dist/server/build.util.js +10 -28
  32. package/dist/server/build.util.js.map +1 -1
  33. package/dist/src/element/component.element.d.ts +4 -1
  34. package/dist/src/element/component.element.js +4 -1
  35. package/dist/src/element/component.element.js.map +1 -1
  36. package/dist/src/overlay/mod.d.ts +1 -1
  37. package/dist/src/overlay/overlay.service.js +136 -6
  38. package/dist/src/overlay/overlay.service.js.map +1 -1
  39. package/dist/src/overlay/overlay.type.d.ts +28 -4
  40. package/dist/src/renderer/spa/emroute.app.d.ts +3 -0
  41. package/dist/src/renderer/spa/emroute.app.js +18 -3
  42. package/dist/src/renderer/spa/emroute.app.js.map +1 -1
  43. package/package.json +2 -2
  44. package/runtime/abstract.runtime.ts +11 -5
  45. package/runtime/fetch.runtime.ts +6 -1
  46. package/server/build.util.ts +10 -30
  47. package/src/element/component.element.ts +4 -1
  48. package/src/overlay/mod.ts +1 -1
  49. package/src/overlay/overlay.service.ts +158 -8
  50. package/src/overlay/overlay.type.ts +27 -2
  51. package/src/renderer/spa/emroute.app.ts +20 -3
@@ -7,14 +7,29 @@
7
7
  * programmatic triggers, and complex workflows. dismissAll() is
8
8
  * DOM-aware and closes both programmatic and declarative overlays.
9
9
  */
10
+ export interface ToastHandle {
11
+ id: number;
12
+ dismiss(): void;
13
+ update(opts: {
14
+ message?: string;
15
+ type?: string;
16
+ timeout?: number;
17
+ }): void;
18
+ }
19
+ export type ToastType = 'success' | 'error' | 'warning' | 'info';
20
+ export interface ToastFunction {
21
+ (options: ToastOptions): ToastHandle;
22
+ success(message: string, timeout?: number): ToastHandle;
23
+ error(message: string, timeout?: number): ToastHandle;
24
+ warning(message: string, timeout?: number): ToastHandle;
25
+ info(message: string, timeout?: number): ToastHandle;
26
+ }
10
27
  export interface OverlayService {
11
28
  modal<T = undefined>(options: ModalOptions<T>): Promise<T | undefined>;
12
29
  closeModal<T>(value?: T): void;
13
30
  popover(options: PopoverOptions): void;
14
31
  closePopover(): void;
15
- toast(options: ToastOptions): {
16
- dismiss(): void;
17
- };
32
+ toast: ToastFunction;
18
33
  /** Close all open overlays — programmatic and declarative — and toasts. */
19
34
  dismissAll(): void;
20
35
  }
@@ -27,7 +42,16 @@ export interface PopoverOptions {
27
42
  render(el: HTMLDivElement): void;
28
43
  }
29
44
  export interface ToastOptions {
30
- render(el: HTMLDivElement): void;
45
+ /** Custom render function — escape hatch for full control. */
46
+ render?(el: HTMLDivElement): void;
47
+ /** Text content (alternative to render). */
48
+ message?: string;
49
+ /** Toast type — sets `data-toast-type` attribute. */
50
+ type?: ToastType;
51
+ /** Confirm button label. Shows button, makes toast manual, returns PromiseLike<boolean>. */
52
+ confirm?: string;
53
+ /** Reject button label. */
54
+ reject?: string;
31
55
  /** Auto-dismiss timeout in ms. Default 0 (manual dismiss only). Set to a positive ms value for auto-dismiss via CSS animation. */
32
56
  timeout?: number;
33
57
  }
@@ -7,6 +7,7 @@
7
7
  */
8
8
  import { Emroute } from '../../../core/server/emroute.server.ts';
9
9
  import type { NavigateOptions } from '../../../core/type/route.type.ts';
10
+ import type { ContextProvider } from '../../../core/type/component.type.ts';
10
11
  import { type BasePath } from '../../../core/server/emroute.server.ts';
11
12
  /** Options for `createEmrouteApp`. */
12
13
  export interface EmrouteAppOptions {
@@ -36,6 +37,8 @@ export declare function createEmrouteApp(server: Emroute, options?: EmrouteAppOp
36
37
  export interface BootOptions extends EmrouteAppOptions {
37
38
  /** Override the server origin (defaults to `location.origin`). */
38
39
  origin?: string;
40
+ /** Context provider — enriches every ComponentContext (pages and widgets). */
41
+ extendContext?: ContextProvider;
39
42
  }
40
43
  /**
41
44
  * Boot the browser app from runtime manifests.
@@ -21,9 +21,17 @@ export class EmrouteApp {
21
21
  slot = null;
22
22
  abortController = null;
23
23
  constructor(server, options) {
24
- const bp = options?.basePath ?? DEFAULT_BASE_PATH;
25
24
  this.server = server;
26
- this.appBase = bp.app;
25
+ if (options?.basePath) {
26
+ this.appBase = options.basePath.app;
27
+ }
28
+ else if (typeof document !== 'undefined') {
29
+ const base = document.querySelector('base')?.getAttribute('href');
30
+ this.appBase = base ? base.replace(/\/$/, '') : DEFAULT_BASE_PATH.app;
31
+ }
32
+ else {
33
+ this.appBase = DEFAULT_BASE_PATH.app;
34
+ }
27
35
  }
28
36
  async initialize(slotSelector = 'router-slot') {
29
37
  this.slot = document.querySelector(slotSelector);
@@ -179,9 +187,11 @@ export async function bootEmrouteApp(options) {
179
187
  : [];
180
188
  // Build lazy module loaders for all route + widget + element modules
181
189
  const moduleLoaders = buildLazyLoaders(routeTree, widgetEntries, elementEntries, runtime);
182
- // Register widgets eagerly (tag defined immediately, module loads on connectedCallback)
190
+ // Register widgets: lazy in registry (loaded on demand during render),
191
+ // lazy in DOM (module loads on connectedCallback for hydration).
183
192
  const widgets = new WidgetRegistry();
184
193
  for (const entry of widgetEntries) {
194
+ widgets.addLazy(entry.name, entry.modulePath);
185
195
  ComponentElement.registerLazy(entry.name, moduleLoaders[entry.modulePath]);
186
196
  }
187
197
  // Register custom elements — import all modules, define when loaded
@@ -198,6 +208,10 @@ export async function bootEmrouteApp(options) {
198
208
  });
199
209
  }
200
210
  }
211
+ // Wire context provider for both pages (Pipeline) and widgets (ComponentElement)
212
+ if (options?.extendContext) {
213
+ ComponentElement.setContextProvider(options.extendContext);
214
+ }
201
215
  // Create Emroute instance (same class as SSR)
202
216
  const mdRenderer = MarkdownElement.getConfiguredRenderer();
203
217
  const server = await Emroute.create({
@@ -205,6 +219,7 @@ export async function bootEmrouteApp(options) {
205
219
  widgets,
206
220
  moduleLoaders,
207
221
  ...(mdRenderer ? { markdownRenderer: mdRenderer } : {}),
222
+ ...(options?.extendContext ? { extendContext: options.extendContext } : {}),
208
223
  }, runtime);
209
224
  return createEmrouteApp(server, options);
210
225
  }
@@ -1 +1 @@
1
- {"version":3,"file":"emroute.app.js","sourceRoot":"","sources":["../../../../src/renderer/spa/emroute.app.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"emroute.app.js","sourceRoot":"","sources":["../../../../src/renderer/spa/emroute.app.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@emkodev/emroute",
3
- "version": "1.8.0",
3
+ "version": "1.8.2-beta.2",
4
4
  "description": "File-based (but storage-agnostic) router with triple rendering (SPA, SSR HTML, SSR Markdown). Zero dependencies.",
5
5
  "license": "BSD-3-Clause",
6
6
  "author": "emko.dev",
@@ -99,7 +99,7 @@
99
99
  }
100
100
  },
101
101
  "devDependencies": {
102
- "@emkodev/emkoma": "^0.1.0",
102
+ "@emkodev/emkoma": "^0.1.2",
103
103
  "@eslint/js": "^10.0.1",
104
104
  "@types/bun": "^1.3.9",
105
105
  "eslint": "^10.0.2",
@@ -769,11 +769,17 @@ export abstract class Runtime {
769
769
 
770
770
  const files: { html?: string; md?: string; css?: string } = {};
771
771
  let hasFiles = false;
772
- for (const ext of COMPANION_EXTENSIONS) {
773
- const companionFile = `${name}.widget.${ext}`;
774
- const companionPath = `${trailingDir}${name}/${companionFile}`;
775
- if ((await this.query(companionPath)).status !== 404) {
776
- files[ext] = `${prefix}${name}/${companionFile}`;
772
+ const companionResults = await Promise.all(
773
+ COMPANION_EXTENSIONS.map(async (ext) => {
774
+ const companionFile = `${name}.widget.${ext}`;
775
+ const companionPath = `${trailingDir}${name}/${companionFile}`;
776
+ const exists = (await this.query(companionPath)).status !== 404;
777
+ return { ext, exists, path: `${prefix}${name}/${companionFile}` };
778
+ }),
779
+ );
780
+ for (const { ext, exists, path } of companionResults) {
781
+ if (exists) {
782
+ files[ext] = path;
777
783
  hasFiles = true;
778
784
  }
779
785
  }
@@ -59,7 +59,12 @@ export class FetchRuntime extends Runtime {
59
59
  const response = await fetch(url);
60
60
  const js = await response.text();
61
61
  const blob = new Blob([js], { type: 'application/javascript' });
62
- return import(URL.createObjectURL(blob));
62
+ const objectUrl = URL.createObjectURL(blob);
63
+ try {
64
+ return await import(objectUrl);
65
+ } finally {
66
+ URL.revokeObjectURL(objectUrl);
67
+ }
63
68
  }
64
69
 
65
70
  private toUrl(resource: FetchParams[0]): string {
@@ -60,17 +60,17 @@ const DEFAULT_BUNDLE_PATHS = { emroute: '/emroute.js', app: '/app.js' };
60
60
  * - Updated manifests — route tree and widget manifest reference .js paths
61
61
  * - emroute.js — pre-built from dist/ (copied into runtime)
62
62
  * - app.js — consumer entry point (transpiled from .ts, no bundler)
63
- * - index.htmlshell with import map + script tags (if not already present)
63
+ * - importmap.jsonmerged import map (emroute externals + consumer entries)
64
64
  */
65
65
  export async function buildClientBundles(options: BuildOptions): Promise<void> {
66
66
  const { runtime, root, spa, entryPoint } = options;
67
- if (spa === 'none') return;
68
-
69
67
  const paths = options.bundlePaths ?? DEFAULT_BUNDLE_PATHS;
70
68
 
71
69
  // Merge .ts modules → .js with inlined companions, update manifests
72
70
  await mergeModules(runtime);
73
71
 
72
+ if (spa === 'none') return;
73
+
74
74
  // Copy pre-built emroute.js from the package dist/
75
75
  const consumerRequire = createRequire(root + '/');
76
76
  const emrouteJsPath = resolvePrebuiltBundle(consumerRequire);
@@ -100,8 +100,8 @@ export async function buildClientBundles(options: BuildOptions): Promise<void> {
100
100
  } catch { /* no main.css on disk — fine */ }
101
101
  }
102
102
 
103
- // Write shell (index.html) if not already present
104
- await writeShell(runtime, paths);
103
+ // Write merged import map server reads this when generating the shell
104
+ await writeImportMap(runtime, paths);
105
105
  }
106
106
 
107
107
  /**
@@ -122,15 +122,12 @@ function resolvePrebuiltBundle(require: NodeRequire): string {
122
122
  return resolve(process.cwd(), 'dist/emroute.js');
123
123
  }
124
124
 
125
- // ── Shell generation ──────────────────────────────────────────────────
125
+ // ── Import map ───────────────────────────────────────────────────────
126
126
 
127
- async function writeShell(
127
+ async function writeImportMap(
128
128
  runtime: Runtime,
129
129
  paths: { emroute: string; app: string },
130
130
  ): Promise<void> {
131
- if ((await runtime.query('/index.html')).status !== 404) return;
132
-
133
- // Base emroute imports
134
131
  const imports: Record<string, string> = {};
135
132
  for (const pkg of EMROUTE_EXTERNALS) {
136
133
  imports[pkg] = paths.emroute;
@@ -147,26 +144,9 @@ async function writeShell(
147
144
  }
148
145
  }
149
146
 
150
- const importMap = JSON.stringify({ imports }, null, 2);
151
-
152
- const html = `<!DOCTYPE html>
153
- <html>
154
- <head>
155
- <meta charset="utf-8">
156
- <meta name="viewport" content="width=device-width, initial-scale=1">
157
- <title>emroute</title>
158
- <style>@view-transition { navigation: auto; } router-slot { display: contents; }</style>
159
- </head>
160
- <body>
161
- <router-slot></router-slot>
162
- <script type="importmap">
163
- ${importMap}
164
- </script>
165
- <script type="module" src="${paths.app}"></script>
166
- </body>
167
- </html>`;
168
-
169
- await runtime.command('/index.html', { body: html });
147
+ await runtime.command('/importmap.json', {
148
+ body: JSON.stringify({ imports }, null, 2),
149
+ });
170
150
  }
171
151
 
172
152
  // ── Module merging ───────────────────────────────────────────────────
@@ -39,7 +39,10 @@ export class ComponentElement<TParams, TData> extends HTMLElementBase {
39
39
  /** App-level context provider set once during router initialization. */
40
40
  private static extendContext: ContextProvider | undefined;
41
41
 
42
- /** Register (or clear) the context provider that enriches every widget's ComponentContext. */
42
+ /**
43
+ * Register (or clear) the context provider that enriches every widget's ComponentContext.
44
+ * @deprecated Use `bootEmrouteApp({ extendContext })` instead — it wires both pages and widgets.
45
+ */
43
46
  static setContextProvider(provider: ContextProvider | undefined): void {
44
47
  ComponentElement.extendContext = provider;
45
48
  }
@@ -6,5 +6,5 @@
6
6
  * dismissAll() closes both programmatic and declarative overlays.
7
7
  */
8
8
 
9
- export type { ModalOptions, OverlayService, PopoverOptions, ToastOptions } from './overlay.type.ts';
9
+ export type { ModalOptions, OverlayService, PopoverOptions, ToastHandle, ToastOptions } from './overlay.type.ts';
10
10
  export { createOverlayService } from './overlay.service.ts';
@@ -11,7 +11,7 @@
11
11
  * via DOM queries.
12
12
  */
13
13
 
14
- import type { ModalOptions, OverlayService, PopoverOptions, ToastOptions } from './overlay.type.ts';
14
+ import type { ModalOptions, OverlayService, PopoverOptions, ToastFunction, ToastHandle, ToastOptions } from './overlay.type.ts';
15
15
  import { overlayCSS } from './overlay.css.ts';
16
16
 
17
17
  const ANIMATION_SAFETY_TIMEOUT = 300;
@@ -35,6 +35,86 @@ function animateDismiss(el: HTMLElement, onDone: () => void): void {
35
35
  setTimeout(finish, ANIMATION_SAFETY_TIMEOUT);
36
36
  }
37
37
 
38
+ /**
39
+ * Populate a toast element from a cloned template.
40
+ * Sets `[data-toast-message]` textContent, `data-toast-type` attribute,
41
+ * and unhides confirm/reject buttons when labels are provided.
42
+ */
43
+ function fillTemplate(
44
+ el: HTMLElement,
45
+ options: ToastOptions,
46
+ onConfirm?: () => void,
47
+ onReject?: () => void,
48
+ ): void {
49
+ const msgEl = el.querySelector('[data-toast-message]');
50
+ if (msgEl && options.message) {
51
+ msgEl.textContent = options.message;
52
+ }
53
+
54
+ if (options.type) {
55
+ el.setAttribute('data-toast-type', options.type);
56
+ }
57
+
58
+ const confirmBtn = el.querySelector('[data-toast-confirm]') as HTMLElement | null;
59
+ if (confirmBtn) {
60
+ if (options.confirm) {
61
+ confirmBtn.textContent = options.confirm;
62
+ confirmBtn.hidden = false;
63
+ if (onConfirm) confirmBtn.addEventListener('click', onConfirm, { once: true });
64
+ } else {
65
+ confirmBtn.hidden = true;
66
+ }
67
+ }
68
+
69
+ const rejectBtn = el.querySelector('[data-toast-reject]') as HTMLElement | null;
70
+ if (rejectBtn) {
71
+ if (options.reject) {
72
+ rejectBtn.textContent = options.reject;
73
+ rejectBtn.hidden = false;
74
+ if (onReject) rejectBtn.addEventListener('click', onReject, { once: true });
75
+ } else {
76
+ rejectBtn.hidden = true;
77
+ }
78
+ }
79
+ }
80
+
81
+ /**
82
+ * Build toast inner content when no `<template id="overlay-toast">` exists.
83
+ * Creates a `<span>` with the message text, plus confirm/reject buttons
84
+ * if labels are provided.
85
+ */
86
+ function buildFallback(
87
+ el: HTMLElement,
88
+ options: ToastOptions,
89
+ onConfirm?: () => void,
90
+ onReject?: () => void,
91
+ ): void {
92
+ if (options.type) {
93
+ el.setAttribute('data-toast-type', options.type);
94
+ }
95
+
96
+ const span = document.createElement('span');
97
+ span.setAttribute('data-toast-message', '');
98
+ span.textContent = options.message ?? '';
99
+ el.appendChild(span);
100
+
101
+ if (options.confirm) {
102
+ const btn = document.createElement('button');
103
+ btn.setAttribute('data-toast-confirm', '');
104
+ btn.textContent = options.confirm;
105
+ if (onConfirm) btn.addEventListener('click', onConfirm, { once: true });
106
+ el.appendChild(btn);
107
+ }
108
+
109
+ if (options.reject) {
110
+ const btn = document.createElement('button');
111
+ btn.setAttribute('data-toast-reject', '');
112
+ btn.textContent = options.reject;
113
+ if (onReject) btn.addEventListener('click', onReject, { once: true });
114
+ el.appendChild(btn);
115
+ }
116
+ }
117
+
38
118
  export function createOverlayService(): OverlayService {
39
119
  let styleInjected = false;
40
120
 
@@ -167,7 +247,7 @@ export function createOverlayService(): OverlayService {
167
247
  }
168
248
  }
169
249
 
170
- function toast(options: ToastOptions): { dismiss(): void } {
250
+ function toast(options: ToastOptions): ToastHandle {
171
251
  const container = ensureToastContainer();
172
252
 
173
253
  // Clean up dead toasts before adding a new one
@@ -176,26 +256,96 @@ export function createOverlayService(): OverlayService {
176
256
  const el = document.createElement('div');
177
257
  el.setAttribute('data-overlay-toast', '');
178
258
 
179
- const timeout = options.timeout ?? 0;
259
+ const isConfirmation = !!(options.confirm || options.reject);
260
+ const timeout = isConfirmation ? 0 : (options.timeout ?? 0);
180
261
  if (timeout === 0) {
181
262
  el.setAttribute('data-toast-manual', '');
182
263
  } else {
183
264
  el.style.setProperty('--overlay-toast-duration', `${timeout}ms`);
184
265
  }
185
266
 
186
- options.render(el);
267
+ // Confirmation promise plumbing
268
+ let confirmResolve: ((value: boolean) => void) | undefined;
269
+ let confirmPromise: Promise<boolean> | undefined;
270
+ if (isConfirmation) {
271
+ const resolvers = Promise.withResolvers<boolean>();
272
+ confirmResolve = resolvers.resolve;
273
+ confirmPromise = resolvers.promise;
274
+ }
275
+
276
+ const onConfirm = confirmResolve
277
+ ? () => { confirmResolve!(true); dismiss(); }
278
+ : undefined;
279
+ const onReject = confirmResolve
280
+ ? () => { confirmResolve!(false); dismiss(); }
281
+ : undefined;
282
+
283
+ // Render content
284
+ if (options.render) {
285
+ // Escape hatch: caller takes full control
286
+ options.render(el);
287
+ } else {
288
+ // Template-based or fallback
289
+ const template = document.querySelector<HTMLTemplateElement>('#overlay-toast');
290
+ if (template) {
291
+ const clone = template.content.cloneNode(true) as DocumentFragment;
292
+ el.appendChild(clone);
293
+ fillTemplate(el, options, onConfirm, onReject);
294
+ } else {
295
+ buildFallback(el, options, onConfirm, onReject);
296
+ }
297
+ }
298
+
187
299
  container.appendChild(el);
188
300
 
301
+ const id = performance.now();
189
302
  let dismissed = false;
190
- const dismiss = () => {
303
+
304
+ function dismiss(): void {
191
305
  if (dismissed) return;
192
306
  dismissed = true;
193
307
  el.setAttribute('data-dismissing', '');
194
- };
308
+ }
309
+
310
+ function update(opts: { message?: string; type?: string; timeout?: number }): void {
311
+ if (opts.message !== undefined) {
312
+ const msgEl = el.querySelector('[data-toast-message]');
313
+ if (msgEl) msgEl.textContent = opts.message;
314
+ }
315
+ if (opts.type !== undefined) {
316
+ el.setAttribute('data-toast-type', opts.type);
317
+ }
318
+ if (opts.timeout !== undefined) {
319
+ el.style.setProperty('--overlay-toast-duration', `${opts.timeout}ms`);
320
+ // Restart animation by removing and re-adding the manual flag
321
+ if (opts.timeout === 0) {
322
+ el.setAttribute('data-toast-manual', '');
323
+ } else {
324
+ el.removeAttribute('data-toast-manual');
325
+ }
326
+ }
327
+ }
328
+
329
+ const handle: ToastHandle = { id, dismiss, update };
195
330
 
196
- return { dismiss };
331
+ // For confirmation toasts, return a handle that is also PromiseLike<boolean>
332
+ if (confirmPromise) {
333
+ (handle as ToastHandle & PromiseLike<boolean>).then = confirmPromise.then.bind(confirmPromise);
334
+ }
335
+
336
+ return handle;
197
337
  }
198
338
 
339
+ // Attach convenience methods
340
+ toast.success = (message: string, timeout?: number): ToastHandle =>
341
+ toast({ message, type: 'success', timeout: timeout ?? 5000 });
342
+ toast.error = (message: string, timeout?: number): ToastHandle =>
343
+ toast({ message, type: 'error', timeout: timeout ?? 5000 });
344
+ toast.warning = (message: string, timeout?: number): ToastHandle =>
345
+ toast({ message, type: 'warning', timeout: timeout ?? 5000 });
346
+ toast.info = (message: string, timeout?: number): ToastHandle =>
347
+ toast({ message, type: 'info', timeout: timeout ?? 5000 });
348
+
199
349
  // --- Popover ---
200
350
 
201
351
  function popover(options: PopoverOptions): void {
@@ -340,7 +490,7 @@ export function createOverlayService(): OverlayService {
340
490
  return {
341
491
  modal,
342
492
  closeModal,
343
- toast,
493
+ toast: toast as ToastFunction,
344
494
  popover,
345
495
  closePopover,
346
496
  dismissAll,
@@ -8,6 +8,22 @@
8
8
  * DOM-aware and closes both programmatic and declarative overlays.
9
9
  */
10
10
 
11
+ export interface ToastHandle {
12
+ id: number;
13
+ dismiss(): void;
14
+ update(opts: { message?: string; type?: string; timeout?: number }): void;
15
+ }
16
+
17
+ export type ToastType = 'success' | 'error' | 'warning' | 'info';
18
+
19
+ export interface ToastFunction {
20
+ (options: ToastOptions): ToastHandle;
21
+ success(message: string, timeout?: number): ToastHandle;
22
+ error(message: string, timeout?: number): ToastHandle;
23
+ warning(message: string, timeout?: number): ToastHandle;
24
+ info(message: string, timeout?: number): ToastHandle;
25
+ }
26
+
11
27
  export interface OverlayService {
12
28
  modal<T = undefined>(options: ModalOptions<T>): Promise<T | undefined>;
13
29
  closeModal<T>(value?: T): void;
@@ -15,7 +31,7 @@ export interface OverlayService {
15
31
  popover(options: PopoverOptions): void;
16
32
  closePopover(): void;
17
33
 
18
- toast(options: ToastOptions): { dismiss(): void };
34
+ toast: ToastFunction;
19
35
 
20
36
  /** Close all open overlays — programmatic and declarative — and toasts. */
21
37
  dismissAll(): void;
@@ -32,7 +48,16 @@ export interface PopoverOptions {
32
48
  }
33
49
 
34
50
  export interface ToastOptions {
35
- render(el: HTMLDivElement): void;
51
+ /** Custom render function — escape hatch for full control. */
52
+ render?(el: HTMLDivElement): void;
53
+ /** Text content (alternative to render). */
54
+ message?: string;
55
+ /** Toast type — sets `data-toast-type` attribute. */
56
+ type?: ToastType;
57
+ /** Confirm button label. Shows button, makes toast manual, returns PromiseLike<boolean>. */
58
+ confirm?: string;
59
+ /** Reject button label. */
60
+ reject?: string;
36
61
  /** Auto-dismiss timeout in ms. Default 0 (manual dismiss only). Set to a positive ms value for auto-dismiss via CSS animation. */
37
62
  timeout?: number;
38
63
  }
@@ -15,6 +15,7 @@ import type { RouteNode } from '../../../core/type/route-tree.type.ts';
15
15
  import type { NavigateOptions } from '../../../core/type/route.type.ts';
16
16
  import type { WidgetManifestEntry } from '../../../core/type/widget.type.ts';
17
17
  import type { ElementManifestEntry } from '../../../core/type/element.type.ts';
18
+ import type { ContextProvider } from '../../../core/type/component.type.ts';
18
19
  import { type BasePath, DEFAULT_BASE_PATH } from '../../../core/server/emroute.server.ts';
19
20
  import { assertSafeRedirect, escapeHtml } from '../../../core/util/html.util.ts';
20
21
  import { ComponentElement } from '../../element/component.element.ts';
@@ -34,9 +35,15 @@ export class EmrouteApp {
34
35
  private abortController: AbortController | null = null;
35
36
 
36
37
  constructor(server: Emroute, options?: EmrouteAppOptions) {
37
- const bp = options?.basePath ?? DEFAULT_BASE_PATH;
38
38
  this.server = server;
39
- this.appBase = bp.app;
39
+ if (options?.basePath) {
40
+ this.appBase = options.basePath.app;
41
+ } else if (typeof document !== 'undefined') {
42
+ const base = document.querySelector('base')?.getAttribute('href');
43
+ this.appBase = base ? base.replace(/\/$/, '') : DEFAULT_BASE_PATH.app;
44
+ } else {
45
+ this.appBase = DEFAULT_BASE_PATH.app;
46
+ }
40
47
  }
41
48
 
42
49
  async initialize(slotSelector = 'router-slot'): Promise<void> {
@@ -178,6 +185,8 @@ export async function createEmrouteApp(
178
185
  export interface BootOptions extends EmrouteAppOptions {
179
186
  /** Override the server origin (defaults to `location.origin`). */
180
187
  origin?: string;
188
+ /** Context provider — enriches every ComponentContext (pages and widgets). */
189
+ extendContext?: ContextProvider;
181
190
  }
182
191
 
183
192
  /**
@@ -216,9 +225,11 @@ export async function bootEmrouteApp(options?: BootOptions): Promise<EmrouteApp>
216
225
  // Build lazy module loaders for all route + widget + element modules
217
226
  const moduleLoaders = buildLazyLoaders(routeTree, widgetEntries, elementEntries, runtime);
218
227
 
219
- // Register widgets eagerly (tag defined immediately, module loads on connectedCallback)
228
+ // Register widgets: lazy in registry (loaded on demand during render),
229
+ // lazy in DOM (module loads on connectedCallback for hydration).
220
230
  const widgets = new WidgetRegistry();
221
231
  for (const entry of widgetEntries) {
232
+ widgets.addLazy(entry.name, entry.modulePath);
222
233
  ComponentElement.registerLazy(entry.name, moduleLoaders[entry.modulePath]!);
223
234
  }
224
235
 
@@ -237,6 +248,11 @@ export async function bootEmrouteApp(options?: BootOptions): Promise<EmrouteApp>
237
248
  }
238
249
  }
239
250
 
251
+ // Wire context provider for both pages (Pipeline) and widgets (ComponentElement)
252
+ if (options?.extendContext) {
253
+ ComponentElement.setContextProvider(options.extendContext);
254
+ }
255
+
240
256
  // Create Emroute instance (same class as SSR)
241
257
  const mdRenderer = MarkdownElement.getConfiguredRenderer();
242
258
  const server = await Emroute.create({
@@ -244,6 +260,7 @@ export async function bootEmrouteApp(options?: BootOptions): Promise<EmrouteApp>
244
260
  widgets,
245
261
  moduleLoaders,
246
262
  ...(mdRenderer ? { markdownRenderer: mdRenderer } : {}),
263
+ ...(options?.extendContext ? { extendContext: options.extendContext } : {}),
247
264
  }, runtime);
248
265
 
249
266
  return createEmrouteApp(server, options);