zero-query 0.8.6 → 0.8.8
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/README.md +4 -5
- package/cli/commands/bundle.js +20 -28
- package/cli/commands/dev/devtools/panel.html +1 -1
- package/cli/commands/dev/overlay.js +132 -44
- package/dist/zquery.dist.zip +0 -0
- package/dist/zquery.js +12 -110
- package/dist/zquery.min.js +2 -2
- package/index.d.ts +1 -3
- package/package.json +1 -1
- package/src/component.js +8 -106
- package/src/router.js +1 -1
- package/src/ssr.js +1 -1
- package/types/component.d.ts +3 -34
package/src/component.js
CHANGED
|
@@ -15,7 +15,7 @@
|
|
|
15
15
|
* - Scoped styles (inline or via styleUrl)
|
|
16
16
|
* - External templates via templateUrl (with {{expression}} interpolation)
|
|
17
17
|
* - External styles via styleUrl (fetched & scoped automatically)
|
|
18
|
-
* - Relative path resolution — templateUrl
|
|
18
|
+
* - Relative path resolution — templateUrl and styleUrl
|
|
19
19
|
* resolve relative to the component file automatically
|
|
20
20
|
*/
|
|
21
21
|
|
|
@@ -86,16 +86,6 @@ function _fetchResource(url) {
|
|
|
86
86
|
return promise;
|
|
87
87
|
}
|
|
88
88
|
|
|
89
|
-
/**
|
|
90
|
-
* Convert a kebab-case id to Title Case.
|
|
91
|
-
* 'getting-started' → 'Getting Started'
|
|
92
|
-
* @param {string} id
|
|
93
|
-
* @returns {string}
|
|
94
|
-
*/
|
|
95
|
-
function _titleCase(id) {
|
|
96
|
-
return id.replace(/-/g, ' ').replace(/\b\w/g, c => c.toUpperCase());
|
|
97
|
-
}
|
|
98
|
-
|
|
99
89
|
/**
|
|
100
90
|
* Resolve a relative URL against a base.
|
|
101
91
|
*
|
|
@@ -314,47 +304,10 @@ class Component {
|
|
|
314
304
|
// - string → single stylesheet
|
|
315
305
|
// - string[] → array of URLs → all fetched & concatenated
|
|
316
306
|
//
|
|
317
|
-
// pages config (shorthand for multi-template + route-param page switching):
|
|
318
|
-
// pages: {
|
|
319
|
-
// dir: 'pages', // relative to component file (or base)
|
|
320
|
-
// param: 'section', // route param name → this.activePage
|
|
321
|
-
// default: 'getting-started', // fallback when param is absent
|
|
322
|
-
// ext: '.html', // file extension (default '.html')
|
|
323
|
-
// items: ['page-a', { id: 'page-b', label: 'Page B' }, ...]
|
|
324
|
-
// }
|
|
325
|
-
// Exposes this.pages (array of {id,label}), this.activePage (current id)
|
|
326
|
-
// Pages are lazy-loaded: only the active page is fetched on first render,
|
|
327
|
-
// remaining pages are prefetched in the background for instant navigation.
|
|
328
|
-
//
|
|
329
307
|
async _loadExternals() {
|
|
330
308
|
const def = this._def;
|
|
331
309
|
const base = def._base; // auto-detected or explicit
|
|
332
310
|
|
|
333
|
-
// -- Pages config ---------------------------------------------
|
|
334
|
-
if (def.pages && !def._pagesNormalized) {
|
|
335
|
-
const p = def.pages;
|
|
336
|
-
const ext = p.ext || '.html';
|
|
337
|
-
const dir = _resolveUrl((p.dir || '').replace(/\/+$/, ''), base);
|
|
338
|
-
|
|
339
|
-
// Normalize items → [{id, label}, …]
|
|
340
|
-
def._pages = (p.items || []).map(item => {
|
|
341
|
-
if (typeof item === 'string') return { id: item, label: _titleCase(item) };
|
|
342
|
-
return { ...item, label: item.label || _titleCase(item.id) };
|
|
343
|
-
});
|
|
344
|
-
|
|
345
|
-
// Build URL map for lazy per-page loading.
|
|
346
|
-
// Pages are fetched on demand (active page first, rest prefetched in
|
|
347
|
-
// the background) so the component renders as soon as the visible
|
|
348
|
-
// page is ready instead of waiting for every page to download.
|
|
349
|
-
def._pageUrls = {};
|
|
350
|
-
for (const { id } of def._pages) {
|
|
351
|
-
def._pageUrls[id] = `${dir}/${id}${ext}`;
|
|
352
|
-
}
|
|
353
|
-
if (!def._externalTemplates) def._externalTemplates = {};
|
|
354
|
-
|
|
355
|
-
def._pagesNormalized = true;
|
|
356
|
-
}
|
|
357
|
-
|
|
358
311
|
// -- External templates --------------------------------------
|
|
359
312
|
if (def.templateUrl && !def._templateLoaded) {
|
|
360
313
|
const tu = def.templateUrl;
|
|
@@ -367,9 +320,8 @@ class Component {
|
|
|
367
320
|
results.forEach((html, i) => { def._externalTemplates[i] = html; });
|
|
368
321
|
} else if (typeof tu === 'object') {
|
|
369
322
|
const entries = Object.entries(tu);
|
|
370
|
-
// Pages config already resolved; plain objects still need resolving
|
|
371
323
|
const results = await Promise.all(
|
|
372
|
-
entries.map(([, url]) => _fetchResource(
|
|
324
|
+
entries.map(([, url]) => _fetchResource(_resolveUrl(url, base)))
|
|
373
325
|
);
|
|
374
326
|
def._externalTemplates = {};
|
|
375
327
|
entries.forEach(([key], i) => { def._externalTemplates[key] = results[i]; });
|
|
@@ -398,8 +350,7 @@ class Component {
|
|
|
398
350
|
_render() {
|
|
399
351
|
// If externals haven't loaded yet, trigger async load then re-render
|
|
400
352
|
if ((this._def.templateUrl && !this._def._templateLoaded) ||
|
|
401
|
-
(this._def.styleUrl && !this._def._styleLoaded)
|
|
402
|
-
(this._def.pages && !this._def._pagesNormalized)) {
|
|
353
|
+
(this._def.styleUrl && !this._def._styleLoaded)) {
|
|
403
354
|
this._loadExternals().then(() => {
|
|
404
355
|
if (!this._destroyed) this._render();
|
|
405
356
|
});
|
|
@@ -411,43 +362,6 @@ class Component {
|
|
|
411
362
|
this.templates = this._def._externalTemplates;
|
|
412
363
|
}
|
|
413
364
|
|
|
414
|
-
// Expose pages metadata and active page (derived from route param)
|
|
415
|
-
if (this._def._pages) {
|
|
416
|
-
this.pages = this._def._pages;
|
|
417
|
-
const pc = this._def.pages;
|
|
418
|
-
let active = (pc.param && this.props.$params?.[pc.param]) || pc.default || this._def._pages[0]?.id || '';
|
|
419
|
-
|
|
420
|
-
// Fall back to default if the param doesn't match any known page
|
|
421
|
-
if (this._def._pageUrls && !(active in this._def._pageUrls)) {
|
|
422
|
-
active = pc.default || this._def._pages[0]?.id || '';
|
|
423
|
-
}
|
|
424
|
-
this.activePage = active;
|
|
425
|
-
|
|
426
|
-
// Lazy-load: fetch only the active page's template on demand
|
|
427
|
-
if (this._def._pageUrls && !(active in this._def._externalTemplates)) {
|
|
428
|
-
const url = this._def._pageUrls[active];
|
|
429
|
-
if (url) {
|
|
430
|
-
_fetchResource(url).then(html => {
|
|
431
|
-
this._def._externalTemplates[active] = html;
|
|
432
|
-
if (!this._destroyed) this._render();
|
|
433
|
-
});
|
|
434
|
-
return; // Wait for active page before rendering
|
|
435
|
-
}
|
|
436
|
-
}
|
|
437
|
-
|
|
438
|
-
// Prefetch remaining pages in background (once, after active page is ready)
|
|
439
|
-
if (this._def._pageUrls && !this._def._pagesPrefetched) {
|
|
440
|
-
this._def._pagesPrefetched = true;
|
|
441
|
-
for (const [id, url] of Object.entries(this._def._pageUrls)) {
|
|
442
|
-
if (!(id in this._def._externalTemplates)) {
|
|
443
|
-
_fetchResource(url).then(html => {
|
|
444
|
-
this._def._externalTemplates[id] = html;
|
|
445
|
-
});
|
|
446
|
-
}
|
|
447
|
-
}
|
|
448
|
-
}
|
|
449
|
-
}
|
|
450
|
-
|
|
451
365
|
// Determine HTML content
|
|
452
366
|
let html;
|
|
453
367
|
if (this._def.render) {
|
|
@@ -1150,7 +1064,7 @@ class Component {
|
|
|
1150
1064
|
// Reserved definition keys (not user methods)
|
|
1151
1065
|
const _reservedKeys = new Set([
|
|
1152
1066
|
'state', 'render', 'styles', 'init', 'mounted', 'updated', 'destroyed', 'props',
|
|
1153
|
-
'templateUrl', 'styleUrl', 'templates', '
|
|
1067
|
+
'templateUrl', 'styleUrl', 'templates', 'base',
|
|
1154
1068
|
'computed', 'watch'
|
|
1155
1069
|
]);
|
|
1156
1070
|
|
|
@@ -1173,8 +1087,8 @@ export function component(name, definition) {
|
|
|
1173
1087
|
}
|
|
1174
1088
|
definition._name = name;
|
|
1175
1089
|
|
|
1176
|
-
// Auto-detect the calling module's URL so that relative templateUrl
|
|
1177
|
-
//
|
|
1090
|
+
// Auto-detect the calling module's URL so that relative templateUrl
|
|
1091
|
+
// and styleUrl paths resolve relative to the component file.
|
|
1178
1092
|
// An explicit `base` string on the definition overrides auto-detection.
|
|
1179
1093
|
if (definition.base !== undefined) {
|
|
1180
1094
|
definition._base = definition.base; // explicit override
|
|
@@ -1301,23 +1215,11 @@ export async function prefetch(name) {
|
|
|
1301
1215
|
const def = _registry.get(name);
|
|
1302
1216
|
if (!def) return;
|
|
1303
1217
|
|
|
1304
|
-
// Load templateUrl
|
|
1218
|
+
// Load templateUrl and styleUrl if not already loaded.
|
|
1305
1219
|
if ((def.templateUrl && !def._templateLoaded) ||
|
|
1306
|
-
(def.styleUrl && !def._styleLoaded)
|
|
1307
|
-
(def.pages && !def._pagesNormalized)) {
|
|
1220
|
+
(def.styleUrl && !def._styleLoaded)) {
|
|
1308
1221
|
await Component.prototype._loadExternals.call({ _def: def });
|
|
1309
1222
|
}
|
|
1310
|
-
|
|
1311
|
-
// For pages-based components, prefetch ALL page templates so any
|
|
1312
|
-
// active page renders instantly on mount.
|
|
1313
|
-
if (def._pageUrls && def._externalTemplates) {
|
|
1314
|
-
const missing = Object.entries(def._pageUrls)
|
|
1315
|
-
.filter(([id]) => !(id in def._externalTemplates));
|
|
1316
|
-
if (missing.length) {
|
|
1317
|
-
const results = await Promise.all(missing.map(([, url]) => _fetchResource(url)));
|
|
1318
|
-
missing.forEach(([id], i) => { def._externalTemplates[id] = results[i]; });
|
|
1319
|
-
}
|
|
1320
|
-
}
|
|
1321
1223
|
}
|
|
1322
1224
|
|
|
1323
1225
|
|
package/src/router.js
CHANGED
|
@@ -138,7 +138,7 @@ class Router {
|
|
|
138
138
|
|
|
139
139
|
// Per-route fallback: register an alias path for the same component.
|
|
140
140
|
// e.g. { path: '/docs/:section', fallback: '/docs', component: 'docs-page' }
|
|
141
|
-
// When matched via fallback, missing params are undefined
|
|
141
|
+
// When matched via fallback, missing params are undefined.
|
|
142
142
|
if (route.fallback) {
|
|
143
143
|
const fbKeys = [];
|
|
144
144
|
const fbPattern = route.fallback
|
package/src/ssr.js
CHANGED
|
@@ -94,7 +94,7 @@ class SSRComponent {
|
|
|
94
94
|
|
|
95
95
|
const SSR_RESERVED = new Set([
|
|
96
96
|
'state', 'render', 'styles', 'init', 'mounted', 'updated', 'destroyed',
|
|
97
|
-
'props', 'templateUrl', 'styleUrl', 'templates',
|
|
97
|
+
'props', 'templateUrl', 'styleUrl', 'templates',
|
|
98
98
|
'base', 'computed', 'watch'
|
|
99
99
|
]);
|
|
100
100
|
|
package/types/component.d.ts
CHANGED
|
@@ -7,28 +7,6 @@
|
|
|
7
7
|
import type { ReactiveProxy } from './reactive';
|
|
8
8
|
import type { NavigationContext } from './router';
|
|
9
9
|
|
|
10
|
-
/** Item in a `pages` config — either a string id or an `{ id, label }` object. */
|
|
11
|
-
export type PageItem = string | { id: string; label?: string };
|
|
12
|
-
|
|
13
|
-
/**
|
|
14
|
-
* Declarative multi-page configuration for a component.
|
|
15
|
-
*
|
|
16
|
-
* Pages are **lazy-loaded**: only the active page is fetched on first render.
|
|
17
|
-
* Remaining pages are prefetched in the background for instant navigation.
|
|
18
|
-
*/
|
|
19
|
-
export interface PagesConfig {
|
|
20
|
-
/** Directory containing the page HTML files (resolved relative to `base`). */
|
|
21
|
-
dir?: string;
|
|
22
|
-
/** Route parameter name to read (e.g. `'section'` for `/docs/:section`). */
|
|
23
|
-
param?: string;
|
|
24
|
-
/** Default page id when the param is absent. */
|
|
25
|
-
default?: string;
|
|
26
|
-
/** File extension appended to each page id (default `'.html'`). */
|
|
27
|
-
ext?: string;
|
|
28
|
-
/** List of page ids and/or `{ id, label }` objects. */
|
|
29
|
-
items?: PageItem[];
|
|
30
|
-
}
|
|
31
|
-
|
|
32
10
|
/** The object passed to `$.component()` to define a component. */
|
|
33
11
|
export interface ComponentDefinition {
|
|
34
12
|
/**
|
|
@@ -58,12 +36,9 @@ export interface ComponentDefinition {
|
|
|
58
36
|
*/
|
|
59
37
|
styleUrl?: string | string[];
|
|
60
38
|
|
|
61
|
-
/** High-level multi-page configuration shorthand. */
|
|
62
|
-
pages?: PagesConfig;
|
|
63
|
-
|
|
64
39
|
/**
|
|
65
|
-
* Override the base path for resolving relative `templateUrl
|
|
66
|
-
*
|
|
40
|
+
* Override the base path for resolving relative `templateUrl` and `styleUrl`
|
|
41
|
+
* paths. Normally auto-detected from the calling file.
|
|
67
42
|
*/
|
|
68
43
|
base?: string;
|
|
69
44
|
|
|
@@ -121,15 +96,9 @@ export interface ComponentInstance {
|
|
|
121
96
|
/** Map of `z-ref` name → DOM element. Populated after each render. */
|
|
122
97
|
refs: Record<string, Element>;
|
|
123
98
|
|
|
124
|
-
/** Keyed template map (when using multi-`templateUrl`
|
|
99
|
+
/** Keyed template map (when using multi-`templateUrl`). */
|
|
125
100
|
templates: Record<string, string>;
|
|
126
101
|
|
|
127
|
-
/** Normalized page metadata (when using `pages` config). */
|
|
128
|
-
pages: Array<{ id: string; label: string }>;
|
|
129
|
-
|
|
130
|
-
/** Active page id derived from route param (when using `pages` config). */
|
|
131
|
-
activePage: string;
|
|
132
|
-
|
|
133
102
|
/**
|
|
134
103
|
* Computed properties — lazy getters derived from state.
|
|
135
104
|
* Defined via `computed` in the component definition.
|