zero-query 0.3.1 → 0.5.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.
package/README.md CHANGED
@@ -1,5 +1,5 @@
1
1
  <p align="center">
2
- <img src="docs/images/logo.svg" alt="zQuery logo" width="300" height="300">
2
+ <img src=".github/images/logo.svg" alt="zQuery logo" width="300" height="300">
3
3
  </p>
4
4
 
5
5
  <h1 align="center">zQuery</h1>
@@ -15,14 +15,14 @@
15
15
 
16
16
  </p>
17
17
 
18
- > **Lightweight, zero-dependency frontend library that combines jQuery-style DOM manipulation with a modern reactive component system, SPA router, global state management, HTTP client, and utility toolkit — all in a single ~45 KB minified browser bundle. Works out of the box with ES modules — no build step required. An optional CLI bundler is available for single-file distribution.**
18
+ > **Lightweight, zero-dependency frontend library that combines jQuery-style DOM manipulation with a modern reactive component system, SPA router, global state management, HTTP client, and utility toolkit — all in a single ~54 KB minified browser bundle. Works out of the box with ES modules. An optional CLI bundler is available for single-file production builds.**
19
19
 
20
20
  ## Features
21
21
 
22
22
  | Module | Highlights |
23
23
  | --- | --- |
24
24
  | **Core `$()`** | jQuery-like chainable selectors, traversal, DOM manipulation, events, animation |
25
- | **Components** | Reactive state, template literals, `@event` delegation, `z-model` two-way binding, scoped styles, lifecycle hooks |
25
+ | **Components** | Reactive state, template literals, `@event` delegation (8 modifiers), `z-model` two-way binding, directives (`z-if`/`z-else-if`/`z-else`, `z-for`, `z-show`, `z-bind`/`:attr`, `z-class`, `z-style`, `z-text`, `z-html`, `z-ref`, `z-cloak`, `z-pre`), scoped styles, external templates (`templateUrl` / `styleUrl`), lifecycle hooks, auto-injected base styles (`z-cloak` hiding, mobile tap-highlight suppression) |
26
26
  | **Router** | History & hash mode, route params (`:id`), guards, lazy loading, `z-link` navigation |
27
27
  | **Store** | Reactive global state, named actions, computed getters, middleware, subscriptions |
28
28
  | **HTTP** | Fetch wrapper with auto-JSON, interceptors, timeout/abort, base URL |
@@ -46,11 +46,20 @@ Scaffold a new project and start the server:
46
46
 
47
47
  ```bash
48
48
  npx zquery create my-app
49
- cd my-app
50
- npx zquery dev
49
+ npx zquery dev my-app
51
50
  ```
52
51
 
53
- The `create` command generates a ready-to-run project with `index.html`, a router, two components, and styles. The dev server watches for file changes, hot-swaps CSS in-place, full-reloads on other changes, and handles SPA fallback routing.
52
+ > **Tip:** Stay in the project root (where `node_modules` lives) instead of `cd`-ing into `my-app`. This keeps `index.d.ts` accessible to your IDE for full type/intellisense support.
53
+
54
+ The `create` command generates a ready-to-run project with a sidebar layout, router, multiple components (including a folder component with external template and styles), and responsive styles. The dev server watches for file changes, hot-swaps CSS in-place, full-reloads on other changes, and handles SPA fallback routing.
55
+
56
+ #### Error Overlay
57
+
58
+ The dev server includes a **full-screen error overlay** that surfaces errors directly in the browser — similar to Vite or Angular:
59
+
60
+ - **Syntax errors** — JS files are validated on every save *before* the reload is triggered. If a syntax error is found the page stays intact and a dark overlay appears with the error message, file path, line:column, and a code frame pointing to the exact location.
61
+ - **Runtime errors** — uncaught exceptions and unhandled promise rejections are captured and displayed in the same overlay with a cleaned-up stack trace.
62
+ - The overlay **auto-clears** when you fix the error and save. Press `Esc` or click `×` to dismiss manually.
54
63
 
55
64
  ### Alternative: Manual Setup (No npm)
56
65
 
@@ -59,8 +68,8 @@ If you prefer **zero tooling**, download `dist/zQuery.min.js` from the [GitHub r
59
68
  ```bash
60
69
  git clone https://github.com/tonywied17/zero-query.git
61
70
  cd zero-query
62
- node build.js
63
- # → dist/zQuery.min.js (~45 KB)
71
+ npx zquery build
72
+ # → dist/zQuery.min.js (~54 KB)
64
73
  ```
65
74
 
66
75
  ### Include in HTML
@@ -91,6 +100,7 @@ node build.js
91
100
  // scripts/app.js
92
101
  import './components/home.js';
93
102
  import './components/about.js';
103
+ import './components/contacts/contacts.js';
94
104
  import { routes } from './routes.js';
95
105
 
96
106
  $.router({ el: '#app', routes, fallback: 'not-found' });
@@ -131,25 +141,38 @@ my-app/
131
141
  components/
132
142
  home.js
133
143
  counter.js
144
+ todos.js
145
+ api-demo.js
134
146
  about.js
147
+ not-found.js
148
+ contacts/ ← folder component (templateUrl + styleUrl)
149
+ contacts.js
150
+ contacts.html
151
+ contacts.css
152
+ styles/
153
+ styles.css
135
154
  ```
136
155
 
137
156
  - One component per file inside `components/`.
138
157
  - Names **must contain a hyphen** (Web Component convention): `home-page`, `app-counter`, etc.
158
+ - Components with external templates or styles can use a subfolder (e.g. `contacts/contacts.js` + `contacts.html` + `contacts.css`).
139
159
  - `app.js` is the single entry point — import components, create the store, and boot the router.
140
160
 
141
161
  ---
142
162
 
143
163
  ## CLI Bundler
144
164
 
145
- The CLI can compile your entire app — ES modules, the library, external templates, and assets — into a **single bundled file**.
165
+ The CLI compiles your entire app — ES modules, the library, external templates, and assets — into a **single production-ready bundle**. It outputs two builds in one step: a `server/` build for deploying to any web server, and a `local/` build that works straight from disk. No config, no flags — just point it at your app.
146
166
 
147
167
  ```bash
148
- # Auto-detect entry from index.html
168
+ # Auto-detect entry from any .html with a module script
149
169
  npx zquery bundle
150
170
 
151
- # Or specify an entry point
152
- npx zquery bundle path/to/scripts/app.js
171
+ # Or point to an app directory from anywhere
172
+ npx zquery bundle my-app/
173
+
174
+ # Or pass a direct entry file (skips auto-detection)
175
+ npx zquery bundle my-app/scripts/main.js
153
176
  ```
154
177
 
155
178
  Output goes to `dist/` next to your `index.html`:
@@ -172,11 +195,16 @@ dist/
172
195
  | Flag | Short | Description |
173
196
  | --- | --- | --- |
174
197
  | `--out <path>` | `-o` | Custom output directory |
175
- | `--html <file>` | | Use a specific HTML file |
198
+ | `--index <file>` | `-i` | Index HTML file (default: auto-detected) |
199
+ | `--minimal` | `-m` | Only output HTML + bundled JS (skip static assets) |
176
200
 
177
201
  ### What the Bundler Does
178
202
 
179
- 1. Reads `index.html` for the `<script type="module">` entry point
203
+ 1. **Entry detection** a strict precedence order ensures the correct file is chosen:
204
+ 1. **HTML files** — `index.html` is checked first, then other `.html` files (root + one level deep).
205
+ 2. **Module scripts within HTML** — within each HTML file, a `<script type="module">` whose `src` resolves to `app.js` wins; otherwise the first module script tag is used.
206
+ 3. **JS file scan** — if no HTML match, JS files (up to 2 levels deep) are scanned in two passes: first for `$.router(` (the canonical app entry point), then for `$.mount(`, `$.store(`, or `mountAll(`.
207
+ 4. **Convention fallbacks** — `scripts/app.js`, `src/app.js`, `js/app.js`, `app.js`, `main.js`.
180
208
  2. Resolves all `import` statements and topologically sorts dependencies
181
209
  3. Strips `import`/`export` syntax, wraps in an IIFE
182
210
  4. Embeds zQuery library and inlines `templateUrl` / `styleUrl` / `pages` files
@@ -216,7 +244,7 @@ location / {
216
244
  | `$.all()` | Collection selector → `ZQueryCollection` |
217
245
  | `$.id` `$.class` `$.classes` `$.tag` `$.children` | Quick DOM refs |
218
246
  | `$.create` | Element factory |
219
- | `$.ready` `$.on` | DOM ready, global delegation |
247
+ | `$.ready` `$.on` `$.off` | DOM ready, global event delegation & direct listeners |
220
248
  | `$.fn` | Collection prototype (extend it) |
221
249
  | `$.component` `$.mount` `$.mountAll` `$.getInstance` `$.destroy` `$.components` | Component system |
222
250
  | `$.style` | Dynamically load global stylesheet file(s) at runtime |
@@ -231,13 +259,14 @@ location / {
231
259
  | `$.storage` `$.session` | Storage wrappers |
232
260
  | `$.bus` | Event bus |
233
261
  | `$.version` | Library version |
262
+ | `$.meta` | Build metadata (populated by CLI bundler) |
234
263
  | `$.noConflict` | Release `$` global |
235
264
 
236
265
  | CLI Command | Description |
237
266
  | --- | --- |
238
- | `zquery create [dir]` | Scaffold a new project (index.html, scripts, styles) |
239
- | `zquery dev [root]` | Dev server with live-reload (port 3100) |
240
- | `zquery bundle [entry]` | Bundle app into a single IIFE file |
267
+ | `zquery create [dir]` | Scaffold a new project (index.html, components, store, styles) |
268
+ | `zquery dev [root]` | Dev server with live-reload &amp; error overlay (port 3100). `--index` for custom HTML. |
269
+ | `zquery bundle [dir\|file]` | Bundle app into a single IIFE file. Accepts dir or direct entry file. |
241
270
  | `zquery build` | Build the zQuery library (`dist/zQuery.min.js`) |
242
271
  | `zquery --help` | Show CLI usage |
243
272
 
@@ -247,7 +276,7 @@ For full method signatures, options, and examples, see **[API.md](API.md)**.
247
276
 
248
277
  ## Editor Support
249
278
 
250
- The official **[zQuery for VS Code](https://marketplace.visualstudio.com/items?itemName=zQuery.zquery-vs-code)** extension provides autocomplete, hover docs, HTML directive support, and 55+ code snippets for every API method and directive. Install it from the [VS Code Marketplace](https://marketplace.visualstudio.com/items?itemName=zQuery.zquery-vs-code) or search **"zQuery for VS Code"** in Extensions.
279
+ The official **[zQuery for VS Code](https://marketplace.visualstudio.com/items?itemName=zQuery.zquery-vs-code)** extension provides autocomplete, hover docs, HTML directive support, and 140+ code snippets for every API method and directive. Install it from the [VS Code Marketplace](https://marketplace.visualstudio.com/items?itemName=zQuery.zquery-vs-code) or search **"zQuery for VS Code"** in Extensions.
251
280
 
252
281
  ---
253
282
 
package/cli/args.js ADDED
@@ -0,0 +1,33 @@
1
+ /**
2
+ * cli/args.js — CLI argument parsing helpers
3
+ *
4
+ * Provides the raw args array and two helper functions for reading
5
+ * named flags (--verbose, -v) and valued options (--port 8080, -p 8080).
6
+ */
7
+
8
+ 'use strict';
9
+
10
+ const args = process.argv.slice(2);
11
+
12
+ /**
13
+ * Check whether a boolean flag is present.
14
+ * flag('verbose', 'v') → true if --verbose or -v appears
15
+ */
16
+ function flag(name, short) {
17
+ const i = args.indexOf(`--${name}`);
18
+ const j = short ? args.indexOf(`-${short}`) : -1;
19
+ return i !== -1 || j !== -1;
20
+ }
21
+
22
+ /**
23
+ * Read a string-valued option.
24
+ * option('port', 'p', '3100') → the value after --port / -p, or '3100'
25
+ */
26
+ function option(name, short, fallback) {
27
+ let i = args.indexOf(`--${name}`);
28
+ if (i === -1 && short) i = args.indexOf(`-${short}`);
29
+ if (i !== -1 && i + 1 < args.length) return args[i + 1];
30
+ return fallback;
31
+ }
32
+
33
+ module.exports = { args, flag, option };
@@ -0,0 +1,58 @@
1
+ /**
2
+ * cli/commands/build.js — library build command
3
+ *
4
+ * Concatenates the zQuery source modules into dist/zquery.js and
5
+ * dist/zquery.min.js.
6
+ */
7
+
8
+ 'use strict';
9
+
10
+ const fs = require('fs');
11
+ const path = require('path');
12
+ const { minify, sizeKB } = require('../utils');
13
+
14
+ function buildLibrary() {
15
+ const pkg = JSON.parse(fs.readFileSync(path.join(process.cwd(), 'package.json'), 'utf-8'));
16
+ const VERSION = pkg.version;
17
+
18
+ const modules = [
19
+ 'src/reactive.js', 'src/core.js', 'src/component.js',
20
+ 'src/router.js', 'src/store.js', 'src/http.js', 'src/utils.js',
21
+ ];
22
+
23
+ const DIST = path.join(process.cwd(), 'dist');
24
+ const OUT_FILE = path.join(DIST, 'zquery.js');
25
+ const MIN_FILE = path.join(DIST, 'zquery.min.js');
26
+
27
+ const start = Date.now();
28
+ if (!fs.existsSync(DIST)) fs.mkdirSync(DIST, { recursive: true });
29
+
30
+ const parts = modules.map(file => {
31
+ let code = fs.readFileSync(path.join(process.cwd(), file), 'utf-8');
32
+ code = code.replace(/^import\s+[\s\S]*?from\s+['"].*?['"];?\s*$/gm, '');
33
+ code = code.replace(/^export\s+(default\s+)?/gm, '');
34
+ code = code.replace(/^export\s*\{[\s\S]*?\};\s*$/gm, '');
35
+ return `// --- ${file} ${'—'.repeat(60 - file.length)}\n${code.trim()}`;
36
+ });
37
+
38
+ let indexCode = fs.readFileSync(path.join(process.cwd(), 'index.js'), 'utf-8');
39
+ indexCode = indexCode.replace(/^import\s+[\s\S]*?from\s+['"].*?['"];?\s*$/gm, '');
40
+ indexCode = indexCode.replace(/^export\s*\{[\s\S]*?\};\s*$/gm, '');
41
+ indexCode = indexCode.replace(/^export\s+(default\s+)?/gm, '');
42
+
43
+ const banner = `/**\n * zQuery (zeroQuery) v${VERSION}\n * Lightweight Frontend Library\n * https://github.com/tonywied17/zero-query\n * (c) ${new Date().getFullYear()} Anthony Wiedman — MIT License\n */`;
44
+
45
+ const bundle = `${banner}\n(function(global) {\n 'use strict';\n\n${parts.join('\n\n')}\n\n// --- index.js (assembly) ${'—'.repeat(42)}\n${indexCode.trim().replace("'__VERSION__'", `'${VERSION}'`)}\n\n})(typeof window !== 'undefined' ? window : globalThis);\n`;
46
+
47
+ fs.writeFileSync(OUT_FILE, bundle, 'utf-8');
48
+ fs.writeFileSync(MIN_FILE, minify(bundle, banner), 'utf-8');
49
+
50
+ const elapsed = Date.now() - start;
51
+ console.log(` ✓ dist/zquery.js (${sizeKB(fs.readFileSync(OUT_FILE))} KB)`);
52
+ console.log(` ✓ dist/zquery.min.js (${sizeKB(fs.readFileSync(MIN_FILE))} KB)`);
53
+ console.log(` Done in ${elapsed}ms\n`);
54
+
55
+ return { DIST, OUT_FILE, MIN_FILE };
56
+ }
57
+
58
+ module.exports = buildLibrary;