tkeron 4.5.0 → 5.0.1

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
@@ -82,8 +82,8 @@ document.getElementById("quote").textContent = data.content;
82
82
 
83
83
  ```bash
84
84
  tk init <name> # Initialize new project
85
- tk build [src] [out] # Build project (default: websrc → web)
86
- tk dev [src] [out] # Dev server with hot reload (port 3000)
85
+ tk build # Build project (websrc → web)
86
+ tk dev [port] [host] # Dev server with hot reload (default: localhost:3000)
87
87
  ```
88
88
 
89
89
  **Aliases:** `tk i`, `tk b`, `tk d`
package/changelog.md CHANGED
@@ -1,3 +1,56 @@
1
+ # v5.0.1
2
+
3
+ ## Documentation fixes and dependency updates
4
+
5
+ - Fix: `tk build` and `tk dev` CLI signatures corrected in README (removed wrong `[src] [out]` args, aligned with v5.0 breaking change)
6
+ - Fix: Component resolution docs updated to reflect actual glob search behavior (not limited to root `websrc/`)
7
+ - Fix: Build process docs updated to include `.com.md` processing step and iterative loop (up to 10 iterations)
8
+ - Fix: `tsconfig.json` example corrected to match real config (`lib: ["ESNext", "DOM"]`, removed `types: ["bun-types"]`)
9
+ - Fix: TypeScript compilation docs clarified — Bun transpiler does NOT type-check, only transpiles
10
+ - Fix: Broken link `tkeron.dev/docs` → `tkeron.com`
11
+ - Fix: `components-html.md` quick start used `<button>` (reserved HTML tag, no hyphen) — replaced with `<my-button>`
12
+ - Fix: `best-practices.md` Summary had orphaned/corrupted code fragment — removed
13
+ - Fix: Added `.com.md` to all feature lists, tables, and build process diagrams across all docs
14
+ - Fix: `package.json` description updated to reflect actual purpose
15
+ - Deps: `bun update --latest` — updated all dependencies
16
+
17
+ ---
18
+
19
+ # v5.0.0
20
+
21
+ ## Breaking: sourceDir and targetDir removed as CLI arguments
22
+
23
+ - `tk build` and `tk dev` no longer accept positional directory arguments
24
+ - Fixed convention: source in `websrc/`, output in `web/`
25
+ - To migrate: rename your source directory to `websrc/` (`mv your-dir websrc`)
26
+ - Output is always `web/` (sibling of `websrc/`) — no longer configurable via CLI
27
+ - `port` and `host` remain as positional arguments for `tk dev`
28
+
29
+ ## Fix: pre-rendering module resolution in projects without node_modules
30
+
31
+ - `processPre.ts` now injects the absolute resolved path of `@tkeron/html-parser` instead of the bare specifier
32
+ - Fixes failure when the user's project lives inside a workspace root with a `node_modules/` that doesn't include `@tkeron` dependencies
33
+
34
+ ### Migration
35
+
36
+ ```bash
37
+ # Before (v4.x)
38
+ tk build src dist
39
+ tk dev src dist 8080
40
+
41
+ # After (v5.0)
42
+ tk build
43
+ tk dev 8080
44
+ ```
45
+
46
+ ### What changed
47
+
48
+ - `buildWrapper` no longer forwards `sourceDir`/`targetDir` to `build()`
49
+ - CLI positioned arguments for directories removed from `build` and `develop` commands
50
+ - Documentation updated (cli-reference, getting-started)
51
+
52
+ ---
53
+
1
54
  # v4.5.0
2
55
 
3
56
  ## tsconfig.json Generation on Init
@@ -231,23 +231,20 @@ document.getElementById("stars").textContent = data.public_repos;
231
231
 
232
232
  - HTML components: static markup
233
233
  - TypeScript components: dynamic generation
234
+ - Markdown components: content in Markdown
234
235
  - Pre-rendering: DOM manipulation at build time
235
236
  - Browser code: regular TypeScript/JavaScript
236
237
  - No bundling of npm packages
237
238
  - No type checking (use `tsc --noEmit`)
238
239
  - Powered by Bun
239
- document.querySelectorAll('.my-button').forEach(btn => {
240
- btn.addEventListener('click', handleClick);
241
- });
242
- });
243
240
 
244
- ````
241
+ ---
245
242
 
246
243
  ```typescript
247
244
  // ❌ Don't try to maintain state
248
245
  let count = 0; // This is meaningless
249
246
  com.innerHTML = `<button>Count: ${count}</button>`;
250
- ````
247
+ ```
251
248
 
252
249
  **Solution:** Use client-side JavaScript for stateful UI.
253
250
 
@@ -52,30 +52,22 @@ Build your project by processing source files into static output.
52
52
  **Usage:**
53
53
 
54
54
  ```bash
55
- tk build [sourceDir] [targetDir]
55
+ tk build
56
56
  ```
57
57
 
58
- **Arguments:**
58
+ **Convention:**
59
59
 
60
- | Argument | Type | Default | Description |
61
- | ----------- | ------ | -------- | ---------------------------------------------- |
62
- | `sourceDir` | string | `websrc` | Source directory containing your project files |
63
- | `targetDir` | string | `web` | Output directory for built files |
60
+ - Source directory: `websrc/` (relative to current directory)
61
+ - Output directory: `web/` (sibling of `websrc/`)
64
62
 
65
63
  **Examples:**
66
64
 
67
65
  ```bash
68
- # Build with defaults (websrc → web)
66
+ # Build the project
69
67
  tk build
70
68
 
71
- # Build with custom source directory
72
- tk build src web
73
-
74
- # Build to custom output directory
75
- tk build websrc dist
76
-
77
- # Build with both custom
78
- tk build source output
69
+ # Using alias
70
+ tk b
79
71
  ```
80
72
 
81
73
  **Build Process:**
@@ -83,16 +75,20 @@ tk build source output
83
75
  1. Creates temporary directory as sibling to source
84
76
  2. Copies source to temp directory
85
77
  3. Runs `.pre.ts` files (pre-rendering)
86
- 4. Processes `.com.ts` components (TypeScript components)
87
- 5. Processes `.com.html` components (HTML components)
88
- 6. Compiles TypeScript to JavaScript
89
- 7. Copies result to target directory
90
- 8. Cleans up temporary directory
78
+ 4. Iterative component processing (up to 10 iterations):
79
+ - Processes `.com.ts` components (TypeScript components)
80
+ - Processes `.com.html` components (HTML components)
81
+ - Processes `.com.md` components (Markdown components)
82
+ - Repeats until no changes are detected
83
+ 5. Compiles TypeScript to JavaScript
84
+ 6. Copies result to target directory
85
+ 7. Cleans up temporary directory
91
86
 
92
87
  **Files Excluded from Output:**
93
88
 
94
89
  - `*.com.html` - HTML components (inlined)
95
90
  - `*.com.ts` - TypeScript components (inlined)
91
+ - `*.com.md` - Markdown components (inlined)
96
92
  - `*.pre.ts` - Pre-rendering scripts (executed)
97
93
 
98
94
  **Exit Codes:**
@@ -120,17 +116,20 @@ Start a development server with hot reload.
120
116
  **Usage:**
121
117
 
122
118
  ```bash
123
- tk develop [sourceDir] [outputDir] [port] [host]
119
+ tk develop [port] [host]
124
120
  ```
125
121
 
126
122
  **Arguments:**
127
123
 
128
- | Argument | Type | Default | Description |
129
- | ----------- | ------ | ----------- | --------------------------- |
130
- | `sourceDir` | string | `websrc` | Source directory to watch |
131
- | `outputDir` | string | `web` | Output directory for builds |
132
- | `port` | number | `3000` | Port for development server |
133
- | `host` | string | `localhost` | Host to bind server to |
124
+ | Argument | Type | Default | Description |
125
+ | -------- | ------ | ----------- | --------------------------- |
126
+ | `port` | number | `3000` | Port for development server |
127
+ | `host` | string | `localhost` | Host to bind server to |
128
+
129
+ **Convention:**
130
+
131
+ - Source directory: `websrc/` (relative to current directory)
132
+ - Output directory: `web/` (sibling of `websrc/`)
134
133
 
135
134
  **Examples:**
136
135
 
@@ -138,17 +137,14 @@ tk develop [sourceDir] [outputDir] [port] [host]
138
137
  # Start with defaults
139
138
  tk dev
140
139
 
141
- # Custom source and output
142
- tk dev src dist
143
-
144
140
  # Custom port
145
- tk dev websrc web 8080
141
+ tk dev 8080
146
142
 
147
143
  # Bind to all interfaces
148
- tk dev websrc web 3000 0.0.0.0
144
+ tk dev 3000 0.0.0.0
149
145
 
150
146
  # Complete custom configuration
151
- tk develop source output 8080 0.0.0.0
147
+ tk develop 8080 0.0.0.0
152
148
  ```
153
149
 
154
150
  **What It Does:**
@@ -317,7 +313,7 @@ tk init . --force
317
313
  cd my-website
318
314
 
319
315
  # Start development server
320
- tk dev websrc
316
+ tk dev
321
317
 
322
318
  # Open http://localhost:3000
323
319
  ```
@@ -356,7 +352,7 @@ Quick reference for command shortcuts:
356
352
  ```bash
357
353
  tk b # Same as: tk build
358
354
  tk d # Same as: tk develop
359
- tk dev websrc web 8080 # Same as: tk develop websrc web 8080
355
+ tk dev 8080 # Same as: tk develop 8080
360
356
  tk i my-site # Same as: tk init my-site
361
357
  ```
362
358
 
@@ -430,22 +426,19 @@ Tkeron uses **convention over configuration**. There are no configuration files.
430
426
 
431
427
  **Project Structure Convention:**
432
428
 
433
- - Source directory: `websrc/` (default)
434
- - Output directory: `web/` (default)
429
+ - Source directory: `websrc/` (fixed)
430
+ - Output directory: `web/` (fixed)
435
431
  - Component files: `*.com.html` and `*.com.ts`
436
432
  - Pre-render files: `*.pre.ts`
437
433
  - Type definitions: `tkeron.d.ts`
438
434
 
439
435
  **Customization:**
440
436
 
441
- All customization is done via command-line arguments:
437
+ Server configuration is done via command-line arguments:
442
438
 
443
439
  ```bash
444
- # Custom directories
445
- tk build src dist
446
-
447
440
  # Custom server config
448
- tk dev src dist 8080 0.0.0.0
441
+ tk dev 8080 0.0.0.0
449
442
  ```
450
443
 
451
444
  ---
@@ -459,8 +452,8 @@ Tkeron doesn't require a `tsconfig.json`, but you can add one for editor support
459
452
  "compilerOptions": {
460
453
  "target": "ESNext",
461
454
  "module": "ESNext",
455
+ "lib": ["ESNext", "DOM"],
462
456
  "moduleResolution": "bundler",
463
- "types": ["bun-types"],
464
457
  "strict": true,
465
458
  "skipLibCheck": true
466
459
  },
@@ -580,7 +573,7 @@ Error: Port 3000 is already in use
580
573
 
581
574
  ```bash
582
575
  # Use different port
583
- tk dev websrc web 3001
576
+ tk dev 3001
584
577
  ```
585
578
 
586
579
  ### Source Directory Not Found
@@ -597,8 +590,8 @@ tk dev websrc web 3001
597
590
  # Create directory
598
591
  mkdir websrc
599
592
 
600
- # Or use correct path
601
- tk build src web
593
+ # Or initialize a new project
594
+ tk init .
602
595
  ```
603
596
 
604
597
  ### Permission Denied
@@ -646,7 +639,7 @@ tk
646
639
  This document! Also available at:
647
640
 
648
641
  - [GitHub Repository](https://github.com/tkeron/tkeron)
649
- - [Documentation Site](https://tkeron.dev/docs)
642
+ - [Documentation Site](https://tkeron.com)
650
643
 
651
644
  ### Report Issues
652
645
 
@@ -668,11 +661,8 @@ tk dev
668
661
  # Build for production
669
662
  NODE_ENV=production tk build
670
663
 
671
- # Build to custom directory
672
- tk build websrc dist
673
-
674
664
  # Development on port 8080
675
- tk dev websrc web 8080
665
+ tk dev 8080
676
666
 
677
667
  # Initialize in current directory
678
668
  tk init .
@@ -125,9 +125,9 @@ blog-post.com.ts → <blog-post>
125
125
 
126
126
  ## TypeScript Compilation
127
127
 
128
- ### Issue: TypeScript Errors Prevent Build
128
+ ### Issue: TypeScript Errors in Source
129
129
 
130
- **Problem:** Type errors block compilation
130
+ **Problem:** TypeScript code has type errors
131
131
 
132
132
  ```typescript
133
133
  // ❌ WRONG
@@ -135,18 +135,24 @@ const user = { name: "Alice" };
135
135
  user.age = 30; // Error: Property 'age' does not exist
136
136
  ```
137
137
 
138
- **Why this happens:**
138
+ **Why this matters:**
139
139
 
140
- - Tkeron uses Bun's TypeScript transpiler
141
- - Type errors can prevent successful builds
142
- - Missing types for global variables
140
+ - Tkeron uses Bun's TypeScript transpiler, which **does NOT type-check** — it only transpiles
141
+ - Type errors won't prevent the build from running
142
+ - However, type errors may indicate real bugs in your code
143
+ - Missing types for global variables can confuse your IDE
143
144
 
144
145
  **Solution:**
145
146
 
147
+ - Run `tsc --noEmit` separately to catch type errors before building
146
148
  - Use `tkeron.d.ts` for global type declarations
147
- - Fix type errors before building
148
149
  - Use `any` strategically if types are complex
149
150
 
151
+ ```bash
152
+ # Check types, then build
153
+ tsc --noEmit && tk build
154
+ ```
155
+
150
156
  ```typescript
151
157
  // ✅ CORRECT
152
158
  const user: { name: string; age?: number } = { name: "Alice" };
@@ -166,16 +172,17 @@ user.age = 30; // OK
166
172
 
167
173
  **Why this happens:**
168
174
 
169
- - Tkeron searches in 2 locations only:
175
+ - Tkeron searches in 2 ways:
170
176
  1. Same directory as HTML file
171
- 2. Root directory (`websrc/`)
172
- - Not in subdirectories or parent directories (except root)
177
+ 2. Glob search across the entire source tree
178
+ - If no match is found in either, the element remains unchanged
173
179
 
174
180
  **Solution:**
175
- Either place component:
181
+ Place the component file anywhere in the source tree — Tkeron will find it via glob search. For clarity, common locations:
176
182
 
177
- - In `blog/user-card.com.html` (next to `post.html`)
178
- - Or in `websrc/user-card.com.html` (root, available everywhere)
183
+ - In `blog/user-card.com.html` (next to `post.html` — higher priority)
184
+ - In `websrc/user-card.com.html` (root)
185
+ - In `websrc/components/user-card.com.html` (organized in a subfolder)
179
186
 
180
187
  ## Build Performance
181
188
 
@@ -7,7 +7,7 @@ HTML components (`.com.html` files) are the simplest way to create reusable piec
7
7
  Create a file named with `.com.html` extension:
8
8
 
9
9
  ```html
10
- <!-- button.com.html -->
10
+ <!-- my-button.com.html -->
11
11
  <button class="btn">Click me</button>
12
12
  ```
13
13
 
@@ -15,7 +15,7 @@ Use it with a matching custom element:
15
15
 
16
16
  ```html
17
17
  <!-- index.html -->
18
- <button></button>
18
+ <my-button></my-button>
19
19
  ```
20
20
 
21
21
  Build, and the custom element is replaced with the component's content.
@@ -36,7 +36,7 @@ Component filenames must:
36
36
  | -------------------- | -------------- | ------------------------- |
37
37
  | `user-card.com.html` | `<user-card>` | ✅ Yes |
38
38
  | `nav-menu.com.html` | `<nav-menu>` | ✅ Yes |
39
- | `header.com.html` | `<header>` | ❌ No (no hyphen) |
39
+ | `card.com.html` | `<card>` | ❌ No (no hyphen) |
40
40
  | `UserCard.com.html` | `<user-card>` | ✅ Yes (case-insensitive) |
41
41
 
42
42
  ### 2. Component Resolution
@@ -44,23 +44,25 @@ Component filenames must:
44
44
  Tkeron looks for components in this order:
45
45
 
46
46
  1. **Same directory** as the file using it
47
- 2. **Root directory** (`websrc/`)
47
+ 2. **Any directory** in the source tree (via glob search)
48
48
 
49
49
  **Example structure:**
50
50
 
51
51
  ```
52
52
  websrc/
53
53
  ├── index.html
54
- ├── header.com.html # Available to all files
54
+ ├── site-header.com.html # Available to all files
55
+ ├── components/
56
+ │ └── blog-comment.com.html # Also available to all files
55
57
  ├── blog/
56
58
  │ ├── post.html
57
- │ └── comment.com.html # Available only to blog/post.html
59
+ │ └── blog-comment.com.html # Takes priority for blog/post.html
58
60
  ```
59
61
 
60
62
  In `blog/post.html`:
61
63
 
62
- - `<comment>` → Finds `blog/comment.com.html` first
63
- - `<header>` → Falls back to `websrc/header.com.html`
64
+ - `<blog-comment>` → Finds `blog/blog-comment.com.html` first (same directory)
65
+ - `<site-header>` → Found via glob search in the source tree
64
66
 
65
67
  ### 3. Build Process
66
68
 
@@ -50,23 +50,23 @@ Component filenames must:
50
50
  Tkeron looks for components in this order:
51
51
 
52
52
  1. **Same directory** as the file using it
53
- 2. **Root directory** (`websrc/`)
53
+ 2. **Any directory** in the source tree (via glob search)
54
54
 
55
55
  **Example structure:**
56
56
 
57
57
  ```
58
58
  websrc/
59
59
  ├── index.html
60
- ├── site-intro.com.md # Available to all files
60
+ ├── site-intro.com.md # Available to all files
61
61
  ├── blog/
62
62
  │ ├── post.html
63
- │ └── post-footer.com.md # Available only to blog/post.html
63
+ │ └── post-footer.com.md # Takes priority for blog/post.html
64
64
  ```
65
65
 
66
66
  In `blog/post.html`:
67
67
 
68
- - `<post-footer>` → Finds `blog/post-footer.com.md` first
69
- - `<site-intro>` → Falls back to `websrc/site-intro.com.md`
68
+ - `<post-footer>` → Finds `blog/post-footer.com.md` first (same directory)
69
+ - `<site-intro>` → Found via glob search in the source tree
70
70
 
71
71
  ### 3. Component Priority
72
72
 
@@ -84,7 +84,7 @@ Custom elements in HTML must contain at least one hyphen to distinguish them fro
84
84
  Same as HTML components:
85
85
 
86
86
  1. **Same directory** as the file using it
87
- 2. **Root directory** (`websrc/`)
87
+ 2. **Any directory** in the source tree (via glob search)
88
88
 
89
89
  ### IDE Support & IntelliSense
90
90
 
@@ -65,22 +65,20 @@ tk init my-website --force
65
65
  Build your project to compile it into static files:
66
66
 
67
67
  ```bash
68
- tk build websrc web
68
+ tk build
69
69
  ```
70
70
 
71
- **Parameters:**
71
+ **Convention:**
72
72
 
73
- - First argument: source directory (default: `websrc`)
74
- - Second argument: output directory (default: `web`)
73
+ - Source: `websrc/` (relative to current directory)
74
+ - Output: `web/` (sibling of `websrc/`)
75
75
 
76
- **Shorthand:**
76
+ **Using alias:**
77
77
 
78
78
  ```bash
79
- tk build
79
+ tk b
80
80
  ```
81
81
 
82
- This uses the defaults: `websrc` → `web`
83
-
84
82
  **Output structure:**
85
83
 
86
84
  ```
@@ -90,7 +88,7 @@ web/
90
88
  └── ... # Other processed files
91
89
  ```
92
90
 
93
- Notice that `.com.html`, `.com.ts`, and `.pre.ts` files are **not** copied to output - they're processed and inlined.
91
+ Notice that `.com.html`, `.com.ts`, `.com.md`, and `.pre.ts` files are **not** copied to output - they're processed and inlined.
94
92
 
95
93
  ## Start Development Server
96
94
 
@@ -110,20 +108,18 @@ This will:
110
108
  **Custom configuration:**
111
109
 
112
110
  ```bash
113
- tk dev websrc web 8080 0.0.0.0
111
+ tk dev 8080 0.0.0.0
114
112
  ```
115
113
 
116
114
  **Parameters:**
117
115
 
118
- - Source directory (default: `websrc`)
119
- - Output directory (default: `web`)
120
116
  - Port (default: `3000`)
121
117
  - Host (default: `localhost`)
122
118
 
123
119
  **Example with custom port:**
124
120
 
125
121
  ```bash
126
- tk dev websrc web 8080
122
+ tk dev 8080
127
123
  ```
128
124
 
129
125
  Visit `http://localhost:8080` in your browser.
@@ -202,6 +198,7 @@ Open `web/index.html` in your browser. You'll see the greeting component inlined
202
198
  | `.ts` / `.js` | Scripts for pages | ✅ Yes (compiled) |
203
199
  | `.com.html` | HTML components | ❌ No (inlined) |
204
200
  | `.com.ts` | TypeScript components | ❌ No (inlined) |
201
+ | `.com.md` | Markdown components | ❌ No (inlined) |
205
202
  | `.pre.ts` | Pre-rendering scripts | ❌ No (executed) |
206
203
  | `.css` | Stylesheets | ✅ Yes |
207
204
  | Images, fonts, etc. | Static assets | ✅ Yes |
@@ -212,17 +209,14 @@ Open `web/index.html` in your browser. You'll see the greeting component inlined
212
209
  # Show help
213
210
  tk
214
211
 
215
- # Build with defaults
212
+ # Build the project
216
213
  tk build
217
214
 
218
- # Build with custom directories
219
- tk build src dist
220
-
221
215
  # Start dev server
222
216
  tk dev
223
217
 
224
218
  # Start dev server on port 8080
225
- tk dev websrc web 8080
219
+ tk dev 8080
226
220
 
227
221
  # Initialize new project
228
222
  tk init my-project
@@ -248,14 +242,14 @@ Now that you have a basic understanding:
248
242
 
249
243
  ### "Source directory does not exist"
250
244
 
251
- Make sure you're running commands from the right directory:
245
+ Make sure you're running commands from the right directory and that `websrc/` exists:
252
246
 
253
247
  ```bash
254
248
  # Check if websrc exists
255
249
  ls websrc
256
250
 
257
- # Or specify the correct path
258
- tk build path/to/websrc path/to/web
251
+ # Or run tk init to create a new project
252
+ tk init .
259
253
  ```
260
254
 
261
255
  ### "Command not found: tk"
@@ -271,11 +265,11 @@ bun install -g tkeron
271
265
  Use a different port:
272
266
 
273
267
  ```bash
274
- tk dev websrc web 3001
268
+ tk dev 3001
275
269
  ```
276
270
 
277
271
  ### Components not working
278
272
 
279
273
  - Component names **must** contain a hyphen: `user-card`, not `usercard`
280
274
  - File must be named exactly: `user-card.com.html`
281
- - Component files must be in `websrc/` or the same directory as the page using them
275
+ - Component files can be anywhere in the source tree — Tkeron searches the same directory first, then the entire source via glob
package/docs/overview.md CHANGED
@@ -11,6 +11,7 @@ Powered by [Bun](https://bun.sh).
11
11
  - Compiles TypeScript to JavaScript
12
12
  - Inlines HTML components (`.com.html`)
13
13
  - Executes TypeScript components (`.com.ts`) at build time
14
+ - Renders Markdown components (`.com.md`) at build time
14
15
  - Runs pre-rendering scripts (`.pre.ts`)
15
16
  - Copies assets
16
17
  - Dev server with hot reload
@@ -107,11 +108,12 @@ websrc/ Build Steps web/
107
108
  ├── index.html → 1. .pre.ts → ├── index.html
108
109
  ├── index.ts 2. .com.ts ├── index.js
109
110
  ├── index.pre.ts 3. .com.html
110
- ├── nav.com.html 4. TypeScript
111
- └── card.com.ts 5. Assets
111
+ ├── nav.com.html 4. .com.md
112
+ ├── card.com.ts 5. TypeScript
113
+ └── info.com.md 6. Assets
112
114
  ```
113
115
 
114
- Component files (`.com.html`, `.com.ts`, `.pre.ts`) are not copied to output.
116
+ Component files (`.com.html`, `.com.ts`, `.com.md`, `.pre.ts`) are not copied to output.
115
117
 
116
118
  ---
117
119
 
@@ -71,10 +71,13 @@ This is the parsed DOM from the corresponding `.html` file.
71
71
 
72
72
  ```
73
73
  1. Run .pre.ts files → Modify HTML documents
74
- 2. Process .com.ts → Replace TypeScript components
75
- 3. Process .com.html → Replace HTML components
76
- 4. Compile .ts to .js TypeScript compilation
77
- 5. Copy to output Final build
74
+ 2. Iterative component processing (up to 10 iterations):
75
+ a. Process .com.ts → Replace TypeScript components
76
+ b. Process .com.htmlReplace HTML components
77
+ c. Process .com.md Replace Markdown components
78
+ d. Repeat until no changes
79
+ 3. Compile .ts to .js → TypeScript compilation
80
+ 4. Copy to output → Final build
78
81
  ```
79
82
 
80
83
  Pre-rendering happens **first**, so you can inject components dynamically.
@@ -1,13 +1 @@
1
- // Augment global scope for .pre.ts files
2
- declare module "*.pre.ts" {
3
- global {
4
- const document: Document;
5
- }
6
- }
7
-
8
- // Augment global scope for .com.ts files
9
- declare module "*.com.ts" {
10
- global {
11
- const com: HTMLElement;
12
- }
13
- }
1
+ declare const com: HTMLElement;
package/index.ts CHANGED
@@ -15,8 +15,6 @@ getCommands("tkeron", packageJson.version)
15
15
  .addCommand("build")
16
16
  .addAlias("b")
17
17
  .addDescription("Build the project")
18
- .addPositionedArgument("sourceDir")
19
- .addPositionedArgument("targetDir")
20
18
  .setCallback(buildWrapper)
21
19
 
22
20
  .commands()
@@ -25,8 +23,6 @@ getCommands("tkeron", packageJson.version)
25
23
  .addAlias("dev")
26
24
  .addAlias("d")
27
25
  .addDescription("Start development server")
28
- .addPositionedArgument("sourceDir")
29
- .addPositionedArgument("targetDir")
30
26
  .addPositionedArgument("port")
31
27
  .addPositionedArgument("host")
32
28
  .setCallback(develop)
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "tkeron",
3
- "version": "4.5.0",
4
- "description": "CLI tool for backend-driven frontend development with TypeScript.",
3
+ "version": "5.0.1",
4
+ "description": "CLI build tool for vanilla web development with TypeScript.",
5
5
  "type": "module",
6
6
  "main": "./src/index.ts",
7
7
  "exports": {
@@ -3,8 +3,6 @@ import type { Logger } from "@tkeron/tools";
3
3
  import { logger as defaultLogger } from "@tkeron/tools";
4
4
 
5
5
  export interface BuildWrapperOptions {
6
- sourceDir?: string;
7
- targetDir?: string;
8
6
  logger?: Logger;
9
7
  [key: string]: any;
10
8
  }
@@ -13,7 +11,7 @@ export const buildWrapper = async (options: BuildWrapperOptions) => {
13
11
  const log = options?.logger || defaultLogger;
14
12
 
15
13
  try {
16
- await build({ ...options, logger: log });
14
+ await build({ logger: log });
17
15
  } catch (error: any) {
18
16
  log.error(`\n❌ Build failed: ${error.message}\n`);
19
17
  process.exit(1);
@@ -0,0 +1,68 @@
1
+ import { existsSync, readFileSync, writeFileSync } from "fs";
2
+ import { join } from "path";
3
+
4
+ const REQUIRED_INCLUDES = ["websrc/**/*", "tkeron.d.ts"];
5
+
6
+ const DEFAULT_COMPILER_OPTIONS = {
7
+ target: "ESNext",
8
+ module: "ESNext",
9
+ lib: ["ESNext", "DOM"],
10
+ moduleResolution: "bundler",
11
+ strict: true,
12
+ skipLibCheck: true,
13
+ };
14
+
15
+ const createFreshTsconfig = () => ({
16
+ compilerOptions: { ...DEFAULT_COMPILER_OPTIONS },
17
+ include: [...REQUIRED_INCLUDES],
18
+ });
19
+
20
+ const mergeIncludes = (existing: string[]): string[] => {
21
+ const merged = [...existing];
22
+ for (const entry of REQUIRED_INCLUDES) {
23
+ if (!merged.includes(entry)) {
24
+ merged.push(entry);
25
+ }
26
+ }
27
+ return merged;
28
+ };
29
+
30
+ export const ensureTsconfig = (
31
+ targetPath: string,
32
+ previousTsconfig?: Record<string, unknown>,
33
+ ) => {
34
+ const tsconfigPath = join(targetPath, "tsconfig.json");
35
+
36
+ if (previousTsconfig) {
37
+ const existingIncludes = Array.isArray(previousTsconfig.include)
38
+ ? (previousTsconfig.include as string[])
39
+ : [];
40
+ const merged = {
41
+ ...previousTsconfig,
42
+ include: mergeIncludes(existingIncludes),
43
+ };
44
+ writeFileSync(tsconfigPath, JSON.stringify(merged, null, 2));
45
+ return;
46
+ }
47
+
48
+ if (existsSync(tsconfigPath)) {
49
+ try {
50
+ const content = readFileSync(tsconfigPath, "utf-8");
51
+ const parsed = JSON.parse(content);
52
+ const existingIncludes = Array.isArray(parsed.include)
53
+ ? (parsed.include as string[])
54
+ : [];
55
+ const merged = { ...parsed, include: mergeIncludes(existingIncludes) };
56
+ writeFileSync(tsconfigPath, JSON.stringify(merged, null, 2));
57
+ return;
58
+ } catch {
59
+ writeFileSync(
60
+ tsconfigPath,
61
+ JSON.stringify(createFreshTsconfig(), null, 2),
62
+ );
63
+ return;
64
+ }
65
+ }
66
+
67
+ writeFileSync(tsconfigPath, JSON.stringify(createFreshTsconfig(), null, 2));
68
+ };
package/src/init.ts CHANGED
@@ -4,7 +4,6 @@ import {
4
4
  mkdirSync,
5
5
  copyFileSync,
6
6
  readFileSync,
7
- writeFileSync,
8
7
  readdirSync,
9
8
  rmSync,
10
9
  } from "fs";
@@ -12,6 +11,7 @@ import { join, resolve, basename } from "path";
12
11
  import type { Logger } from "@tkeron/tools";
13
12
  import { silentLogger } from "@tkeron/tools";
14
13
  import { promptUser } from "./promptUser";
14
+ import { ensureTsconfig } from "./ensureTsconfig";
15
15
 
16
16
  export interface InitOptions {
17
17
  projectName: string;
@@ -30,6 +30,8 @@ export const init = async (options: InitOptions) => {
30
30
  const targetPath = resolve(process.cwd(), projectName);
31
31
  const isCurrentDir = projectName === "." || targetPath === process.cwd();
32
32
 
33
+ let skipWebsrc = false;
34
+
33
35
  if (existsSync(targetPath)) {
34
36
  if (!isCurrentDir) {
35
37
  if (!force) {
@@ -57,18 +59,22 @@ export const init = async (options: InitOptions) => {
57
59
  "\nDo you want to overwrite them? (y/N): ",
58
60
  );
59
61
 
60
- if (!shouldContinue) {
61
- log.log("\n❌ Operation cancelled.");
62
- return;
62
+ if (shouldContinue) {
63
+ existingTkeronFiles.forEach((file) => {
64
+ const filePath = join(targetPath, file);
65
+ rmSync(filePath, { recursive: true, force: true });
66
+ });
67
+ log.log("✓ Cleaned existing tkeron files");
68
+ } else {
69
+ skipWebsrc = existingTkeronFiles.includes("websrc");
63
70
  }
71
+ } else {
72
+ existingTkeronFiles.forEach((file) => {
73
+ const filePath = join(targetPath, file);
74
+ rmSync(filePath, { recursive: true, force: true });
75
+ });
76
+ log.log("✓ Cleaned existing tkeron files");
64
77
  }
65
-
66
- existingTkeronFiles.forEach((file) => {
67
- const filePath = join(targetPath, file);
68
- rmSync(filePath, { recursive: true, force: true });
69
- });
70
-
71
- log.log("✓ Cleaned existing tkeron files");
72
78
  }
73
79
  }
74
80
  }
@@ -91,36 +97,27 @@ export const init = async (options: InitOptions) => {
91
97
  }
92
98
 
93
99
  const tsconfigPath = join(targetPath, "tsconfig.json");
94
- let existingTsconfig: Record<string, unknown> | null = null;
95
- if (isCurrentDir && existsSync(tsconfigPath)) {
100
+ let previousTsconfig: Record<string, unknown> | undefined;
101
+ if (existsSync(tsconfigPath)) {
96
102
  try {
97
- existingTsconfig = JSON.parse(readFileSync(tsconfigPath, "utf-8"));
103
+ previousTsconfig = JSON.parse(readFileSync(tsconfigPath, "utf-8"));
98
104
  } catch {
99
- existingTsconfig = null;
105
+ previousTsconfig = undefined;
100
106
  }
101
107
  }
102
108
 
103
109
  mkdirSync(targetPath, { recursive: true });
104
- cpSync(templatePath, targetPath, { recursive: true });
110
+ const websrcInTemplate = join(templatePath, "websrc");
111
+ cpSync(templatePath, targetPath, {
112
+ recursive: true,
113
+ filter: skipWebsrc
114
+ ? (src: string) =>
115
+ src !== websrcInTemplate && !src.startsWith(websrcInTemplate + "/")
116
+ : undefined,
117
+ });
105
118
  copyFileSync(tkeronDtsPath, join(targetPath, "tkeron.d.ts"));
106
119
 
107
- if (existingTsconfig !== null) {
108
- const templateTsconfig = JSON.parse(readFileSync(tsconfigPath, "utf-8"));
109
- const requiredIncludes: string[] = Array.isArray(templateTsconfig.include)
110
- ? (templateTsconfig.include as string[])
111
- : [];
112
- const existingIncludes: string[] = Array.isArray(existingTsconfig.include)
113
- ? (existingTsconfig.include as string[])
114
- : [];
115
- const mergedIncludes = [...existingIncludes];
116
- for (const entry of requiredIncludes) {
117
- if (!mergedIncludes.includes(entry)) {
118
- mergedIncludes.push(entry);
119
- }
120
- }
121
- const merged = { ...existingTsconfig, include: mergedIncludes };
122
- writeFileSync(tsconfigPath, JSON.stringify(merged, null, 2));
123
- }
120
+ ensureTsconfig(targetPath, previousTsconfig);
124
121
 
125
122
  const projectDisplayName = isCurrentDir ? basename(targetPath) : projectName;
126
123
  log.log(`✓ Created project "${projectDisplayName}"`);
@@ -137,7 +137,9 @@ const processComponentsTs = async (
137
137
 
138
138
  const elementHTML = (child as any).outerHTML;
139
139
 
140
- log.info(`Processing component <${tagName}> from ${componentPath}`);
140
+ log.info(
141
+ `Processing component <${tagName}> from ${componentPath.replace(rootDir, ".")}`,
142
+ );
141
143
 
142
144
  const tempDoc = parseHTML(
143
145
  "<html><body>" + elementHTML + "</body></html>",
@@ -199,7 +201,9 @@ ${codeWithoutImports}
199
201
  await executeComponent(com);
200
202
  }
201
203
  } catch (execError: any) {
202
- log.error(`\n❌ Error executing component <${tagName}>:`);
204
+ log.error(
205
+ `\n❌ Error executing component <${tagName}>: ${componentPath.replace(rootDir, ".")}`,
206
+ );
203
207
  log.error(` ${execError.message}`);
204
208
  throw execError;
205
209
  }
package/src/processPre.ts CHANGED
@@ -7,6 +7,8 @@ const packageJsonPath = join(import.meta.dir, "..", "package.json");
7
7
  const packageJson = await Bun.file(packageJsonPath).json();
8
8
  const TKERON_VERSION = packageJson.version;
9
9
 
10
+ const HTML_PARSER_PATH = import.meta.resolve("@tkeron/html-parser");
11
+
10
12
  const DEFAULT_HTML = `<!DOCTYPE html>
11
13
  <html lang="en">
12
14
  <head>
@@ -48,7 +50,7 @@ export const processPre = async (
48
50
  : DEFAULT_HTML;
49
51
 
50
52
  const modifiedCode = `
51
- import { parseHTML } from "@tkeron/html-parser";
53
+ import { parseHTML } from ${JSON.stringify(HTML_PARSER_PATH)};
52
54
 
53
55
  const htmlPath = ${JSON.stringify(htmlFile)};
54
56
  const htmlContent = ${JSON.stringify(htmlContent)};
package/tkeron.d.ts CHANGED
@@ -1,13 +1 @@
1
- // Augment global scope for .pre.ts files
2
- declare module "*.pre.ts" {
3
- global {
4
- const document: Document;
5
- }
6
- }
7
-
8
- // Augment global scope for .com.ts files
9
- declare module "*.com.ts" {
10
- global {
11
- const com: HTMLElement;
12
- }
13
- }
1
+ declare const com: HTMLElement;