@git.zone/tstest 1.11.5 → 2.2.0

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 (47) hide show
  1. package/dist_ts/00_commitinfo_data.js +2 -2
  2. package/dist_ts/index.js +24 -2
  3. package/dist_ts/tstest.classes.tap.parser.d.ts +10 -5
  4. package/dist_ts/tstest.classes.tap.parser.js +239 -99
  5. package/dist_ts/tstest.classes.tap.parser.old.d.ts +50 -0
  6. package/dist_ts/tstest.classes.tap.parser.old.js +332 -0
  7. package/dist_ts/tstest.classes.tstest.d.ts +1 -0
  8. package/dist_ts/tstest.classes.tstest.js +93 -4
  9. package/dist_ts/tstest.logging.d.ts +4 -0
  10. package/dist_ts/tstest.logging.js +36 -1
  11. package/dist_ts/tstest.plugins.d.ts +2 -1
  12. package/dist_ts/tstest.plugins.js +3 -2
  13. package/dist_ts_tapbundle/index.d.ts +1 -3
  14. package/dist_ts_tapbundle/index.js +3 -5
  15. package/dist_ts_tapbundle/tapbundle.classes.settingsmanager.d.ts +36 -0
  16. package/dist_ts_tapbundle/tapbundle.classes.settingsmanager.js +114 -0
  17. package/dist_ts_tapbundle/tapbundle.classes.tap.d.ts +26 -3
  18. package/dist_ts_tapbundle/tapbundle.classes.tap.js +218 -22
  19. package/dist_ts_tapbundle/tapbundle.classes.taptest.d.ts +5 -0
  20. package/dist_ts_tapbundle/tapbundle.classes.taptest.js +161 -7
  21. package/dist_ts_tapbundle/tapbundle.classes.taptools.d.ts +14 -0
  22. package/dist_ts_tapbundle/tapbundle.classes.taptools.js +24 -1
  23. package/dist_ts_tapbundle/tapbundle.expect.wrapper.d.ts +11 -0
  24. package/dist_ts_tapbundle/tapbundle.expect.wrapper.js +71 -0
  25. package/dist_ts_tapbundle/tapbundle.interfaces.d.ts +27 -0
  26. package/dist_ts_tapbundle/tapbundle.interfaces.js +2 -0
  27. package/dist_ts_tapbundle/tapbundle.utilities.diff.d.ts +5 -0
  28. package/dist_ts_tapbundle/tapbundle.utilities.diff.js +179 -0
  29. package/dist_ts_tapbundle_protocol/index.d.ts +6 -0
  30. package/dist_ts_tapbundle_protocol/index.js +11 -0
  31. package/dist_ts_tapbundle_protocol/protocol.emitter.d.ts +55 -0
  32. package/dist_ts_tapbundle_protocol/protocol.emitter.js +155 -0
  33. package/dist_ts_tapbundle_protocol/protocol.parser.d.ts +79 -0
  34. package/dist_ts_tapbundle_protocol/protocol.parser.js +359 -0
  35. package/dist_ts_tapbundle_protocol/protocol.types.d.ts +111 -0
  36. package/dist_ts_tapbundle_protocol/protocol.types.js +19 -0
  37. package/package.json +2 -1
  38. package/readme.hints.md +166 -5
  39. package/readme.md +134 -3
  40. package/readme.plan.md +145 -56
  41. package/ts/00_commitinfo_data.ts +1 -1
  42. package/ts/index.ts +22 -1
  43. package/ts/tspublish.json +1 -1
  44. package/ts/tstest.classes.tap.parser.ts +271 -110
  45. package/ts/tstest.classes.tstest.ts +112 -5
  46. package/ts/tstest.logging.ts +43 -0
  47. package/ts/tstest.plugins.ts +2 -0
package/readme.hints.md CHANGED
@@ -40,9 +40,17 @@ This project integrates tstest with tapbundle through a modular architecture:
40
40
  - Automatically detects browser environment and only enables in browser context
41
41
 
42
42
  3. **Build System**
43
- - Uses `tsbuild tsfolders` to compile TypeScript
44
- - Maintains separate output directories: `/dist_ts/`, `/dist_ts_tapbundle/`, `/dist_ts_tapbundle_node/`
45
- - Compilation order is resolved automatically based on dependencies
43
+ - Uses `tsbuild tsfolders` to compile TypeScript (invoked by `pnpm build`)
44
+ - Maintains separate output directories: `/dist_ts/`, `/dist_ts_tapbundle/`, `/dist_ts_tapbundle_node/`, `/dist_ts_tapbundle_protocol/`
45
+ - Compilation order is resolved automatically based on dependencies in tspublish.json files
46
+ - Protocol imports use compiled dist directories:
47
+ ```typescript
48
+ // In ts/tstest.classes.tap.parser.ts
49
+ import { ProtocolParser } from '../dist_ts_tapbundle_protocol/index.js';
50
+
51
+ // In ts_tapbundle/tapbundle.classes.tap.ts
52
+ import { ProtocolEmitter } from '../dist_ts_tapbundle_protocol/index.js';
53
+ ```
46
54
 
47
55
  ### Test Scripts
48
56
 
@@ -102,6 +110,159 @@ A new internal protocol is being designed that will:
102
110
  - Use Unicode delimiters `⟦TSTEST:⟧` that won't conflict with test content
103
111
  - Support structured JSON metadata
104
112
  - Allow rich error reporting with stack traces and diffs
105
- - Maintain backwards compatibility during migration
113
+ - Completely replace v1 protocol (no backwards compatibility)
106
114
 
107
- See `readme.protocol.md` for the full specification and `tapbundle.protocols.ts` for the implementation utilities.
115
+ ### ts_tapbundle_protocol Directory
116
+ The protocol v2 implementation is contained in a separate `ts_tapbundle_protocol` directory:
117
+ - **Isomorphic Code**: All protocol code works in both browser and Node.js environments
118
+ - **No Platform Dependencies**: No Node.js-specific imports, ensuring true cross-platform compatibility
119
+ - **Clean Separation**: Protocol logic is isolated from platform-specific code in tstest and tapbundle
120
+ - **Shared Implementation**: Both tstest (parser) and tapbundle (emitter) use the same protocol classes
121
+ - **Build Process**:
122
+ - Compiled by `pnpm build` via tsbuild to `dist_ts_tapbundle_protocol/`
123
+ - Build order managed through tspublish.json files
124
+ - Other modules import from the compiled dist directory, not source
125
+
126
+ This architectural decision ensures the protocol can be used in any JavaScript environment without modification and maintains proper build dependencies.
127
+
128
+ See `readme.protocol.md` for the full specification and `ts_tapbundle_protocol/` for the implementation.
129
+
130
+ ## Protocol V2 Implementation Status
131
+
132
+ The Protocol V2 has been implemented to fix issues with TAP protocol parsing when test descriptions contain special characters like `#`, `###SNAPSHOT###`, or protocol markers like `⟦TSTEST:ERROR⟧`.
133
+
134
+ ### Implementation Details:
135
+
136
+ 1. **Protocol Components**:
137
+ - `ProtocolEmitter` - Generates protocol v2 messages (used by tapbundle)
138
+ - `ProtocolParser` - Parses protocol v2 messages (used by tstest)
139
+ - Uses Unicode markers `⟦TSTEST:` and `⟧` to avoid conflicts with test content
140
+
141
+ 2. **Current Status**:
142
+ - ✅ Basic protocol emission and parsing works
143
+ - ✅ Handles test descriptions with special characters correctly
144
+ - ✅ Supports metadata for timing, tags, errors
145
+ - ⚠️ Protocol messages sometimes appear in console output (parsing not catching all cases)
146
+
147
+ 3. **Key Findings**:
148
+ - `tap.skip.test()` doesn't create actual test objects, just logs and increments counter
149
+ - `tap.todo()` method is not implemented (no `addTodo` method in Tap class)
150
+ - Protocol parser's `isBlockStart` was fixed to only match exact block markers, not partial matches in test descriptions
151
+
152
+ 4. **Import Paths**:
153
+ - tstest imports from: `import { ProtocolParser } from '../dist_ts_tapbundle_protocol/index.js';`
154
+ - tapbundle imports from: `import { ProtocolEmitter } from '../dist_ts_tapbundle_protocol/index.js';`
155
+
156
+ ## Test Configuration System (Phase 2)
157
+
158
+ The Test Configuration System has been implemented to provide global settings and lifecycle hooks for tests.
159
+
160
+ ### Key Features:
161
+
162
+ 1. **00init.ts Discovery**:
163
+ - Automatically detects `00init.ts` files in the same directory as test files
164
+ - Creates a temporary loader file that imports both `00init.ts` and the test file
165
+ - Loader files are cleaned up automatically after test execution
166
+
167
+ 2. **Settings Inheritance**:
168
+ - Global settings from `00init.ts` → File-level settings → Test-level settings
169
+ - Settings include: timeout, retries, retryDelay, bail, concurrency
170
+ - Lifecycle hooks: beforeAll, afterAll, beforeEach, afterEach
171
+
172
+ 3. **Implementation Details**:
173
+ - `SettingsManager` class handles settings inheritance and merging
174
+ - `tap.settings()` API allows configuration at any level
175
+ - Lifecycle hooks are integrated into test execution flow
176
+
177
+ ### Important Development Notes:
178
+
179
+ 1. **Local Development**: When developing tstest itself, use `node cli.js` instead of globally installed `tstest` to test changes
180
+
181
+ 2. **Console Output Buffering**: Console output from tests is buffered and only displayed for failing tests. TAP-compliant comments (lines starting with `#`) are always shown.
182
+
183
+ 3. **TypeScript Warnings**: Fixed async/await warnings in `movePreviousLogFiles()` by using sync versions of file operations
184
+
185
+ ## Enhanced Communication Features (Phase 3)
186
+
187
+ The Enhanced Communication system has been implemented to provide rich, real-time feedback during test execution.
188
+
189
+ ### Key Features:
190
+
191
+ 1. **Event-Based Test Lifecycle Reporting**:
192
+ - `test:queued` - Test is ready to run
193
+ - `test:started` - Test execution begins
194
+ - `test:completed` - Test finishes (with pass/fail status)
195
+ - `suite:started` - Test suite/describe block begins
196
+ - `suite:completed` - Test suite/describe block ends
197
+ - `hook:started` - Lifecycle hook (beforeEach/afterEach) begins
198
+ - `hook:completed` - Lifecycle hook finishes
199
+ - `assertion:failed` - Assertion failure with detailed information
200
+
201
+ 2. **Visual Diff Output for Assertion Failures**:
202
+ - **String Diffs**: Character-by-character comparison with colored output
203
+ - **Object/Array Diffs**: Deep property comparison showing added/removed/changed properties
204
+ - **Primitive Diffs**: Clear display of expected vs actual values
205
+ - **Colorized Output**: Green for expected, red for actual, yellow for differences
206
+ - **Smart Formatting**: Multi-line strings and complex objects are formatted for readability
207
+
208
+ 3. **Real-Time Test Progress API**:
209
+ - Tests emit progress events as they execute
210
+ - tstest parser processes events and updates display in real-time
211
+ - Structured event format carries rich metadata (timing, errors, diffs)
212
+ - Seamless integration with existing TAP protocol via Protocol V2
213
+
214
+ ### Implementation Details:
215
+ - Events are transmitted via Protocol V2's `EVENT` block type
216
+ - Event data is JSON-encoded within protocol markers
217
+ - Parser handles events asynchronously for real-time updates
218
+ - Visual diffs are generated using custom diff algorithms for each data type
219
+
220
+ ## Watch Mode (Phase 4)
221
+
222
+ tstest now supports watch mode for automatic test re-runs on file changes.
223
+
224
+ ### Usage
225
+ ```bash
226
+ tstest test/**/*.ts --watch
227
+ tstest test/specific.ts -w
228
+ ```
229
+
230
+ ### Features
231
+ - **Automatic Re-runs**: Tests re-run when any watched file changes
232
+ - **Debouncing**: Multiple rapid changes are batched (300ms delay)
233
+ - **Clear Output**: Console is cleared before each run for clean results
234
+ - **Status Updates**: Shows which files triggered the re-run
235
+ - **Graceful Exit**: Press Ctrl+C to stop watching
236
+
237
+ ### Options
238
+ - `--watch` or `-w`: Enable watch mode
239
+ - `--watch-ignore`: Comma-separated patterns to ignore (e.g., `--watch-ignore node_modules,dist`)
240
+
241
+ ### Implementation Details
242
+ - Uses `@push.rocks/smartchok` for cross-platform file watching
243
+ - Watches the entire project directory from where tests are run
244
+ - Ignores changes matching the ignore patterns
245
+ - Shows "Waiting for file changes..." between runs
246
+
247
+ ## Fixed Issues
248
+
249
+ ### tap.skip.test(), tap.todo(), and tap.only.test() (Fixed)
250
+
251
+ Previously reported issues with these methods have been resolved:
252
+
253
+ 1. **tap.skip.test()** - Now properly creates test objects that are counted in test results
254
+ - Tests marked with `skip.test()` appear in the test count
255
+ - Shows as passed with skip directive in TAP output
256
+ - `markAsSkipped()` method added to handle pre-test skip marking
257
+
258
+ 2. **tap.todo.test()** - Fully implemented with test object creation
259
+ - Supports both `tap.todo.test('description')` and `tap.todo.test('description', testFunc)`
260
+ - Todo tests are counted and marked with todo directive
261
+ - Both regular and parallel todo tests supported
262
+
263
+ 3. **tap.only.test()** - Works correctly for focused testing
264
+ - When `.only` tests exist, only those tests run
265
+ - Other tests are not executed but still counted
266
+ - Both regular and parallel only tests supported
267
+
268
+ These fixes ensure accurate test counts and proper TAP-compliant output for all test states.
package/readme.md CHANGED
@@ -27,6 +27,12 @@
27
27
  - 🔁 **Retry Logic** - Automatically retry failing tests
28
28
  - 🛠️ **Test Fixtures** - Create reusable test data
29
29
  - 📦 **Browser-Compatible** - Full browser support with embedded tapbundle
30
+ - 👀 **Watch Mode** - Automatically re-run tests on file changes
31
+ - 📊 **Real-time Progress** - Live test execution progress updates
32
+ - 🎨 **Visual Diffs** - Beautiful side-by-side diffs for failed assertions
33
+ - 🔄 **Event-based Reporting** - Real-time test lifecycle events
34
+ - ⚙️ **Test Configuration** - Flexible test settings with .tstest.json files
35
+ - 🚀 **Protocol V2** - Enhanced TAP protocol with Unicode delimiters
30
36
 
31
37
  ## Installation
32
38
 
@@ -73,6 +79,9 @@ tstest "test/unit/*.ts"
73
79
  | `--timeout <seconds>` | Timeout test files after specified seconds |
74
80
  | `--startFrom <n>` | Start running from test file number n |
75
81
  | `--stopAt <n>` | Stop running at test file number n |
82
+ | `--watch`, `-w` | Watch for file changes and re-run tests |
83
+ | `--watch-ignore <patterns>` | Ignore patterns in watch mode (comma-separated) |
84
+ | `--only` | Run only tests marked with .only |
76
85
 
77
86
  ### Example Outputs
78
87
 
@@ -203,9 +212,9 @@ tap.only.test('focus on this', async () => {
203
212
  // Only this test will run
204
213
  });
205
214
 
206
- // Todo test
207
- tap.todo('implement later', async () => {
208
- // Marked as todo
215
+ // Todo test - creates actual test object marked as todo
216
+ tap.todo.test('implement later', async () => {
217
+ // This test will be counted but marked as todo
209
218
  });
210
219
 
211
220
  // Chaining modifiers
@@ -558,6 +567,115 @@ tapWrap.tap.test('wrapped test', async () => {
558
567
 
559
568
  ## Advanced Features
560
569
 
570
+ ### Watch Mode
571
+
572
+ Automatically re-run tests when files change:
573
+
574
+ ```bash
575
+ # Watch all files in the project
576
+ tstest test/ --watch
577
+
578
+ # Watch with custom ignore patterns
579
+ tstest test/ --watch --watch-ignore "dist/**,coverage/**"
580
+
581
+ # Short form
582
+ tstest test/ -w
583
+ ```
584
+
585
+ **Features:**
586
+ - 👀 Shows which files triggered the re-run
587
+ - ⏱️ 300ms debouncing to batch rapid changes
588
+ - 🔄 Clears console between runs for clean output
589
+ - 📁 Intelligently ignores common non-source files
590
+
591
+ ### Real-time Test Progress
592
+
593
+ tstest provides real-time updates during test execution:
594
+
595
+ ```
596
+ ▶️ test/api.test.ts (1/4)
597
+ Runtime: node.js
598
+ ⏳ Running: api endpoint validation...
599
+ ✅ api endpoint validation (145ms)
600
+ ⏳ Running: error handling...
601
+ ✅ error handling (23ms)
602
+ Summary: 2/2 PASSED
603
+ ```
604
+
605
+ ### Visual Diffs for Failed Assertions
606
+
607
+ When assertions fail, tstest shows beautiful side-by-side diffs:
608
+
609
+ ```
610
+ ❌ should return correct user data
611
+
612
+ String Diff:
613
+ - Expected
614
+ + Received
615
+
616
+ - Hello World
617
+ + Hello Universe
618
+
619
+ Object Diff:
620
+ {
621
+ name: "John",
622
+ - age: 30,
623
+ + age: 31,
624
+ email: "john@example.com"
625
+ }
626
+ ```
627
+
628
+ ### Test Configuration (.tstest.json)
629
+
630
+ Configure test behavior with `.tstest.json` files:
631
+
632
+ ```json
633
+ {
634
+ "timeout": 30000,
635
+ "retries": 2,
636
+ "bail": false,
637
+ "parallel": true,
638
+ "tags": ["unit", "fast"],
639
+ "env": {
640
+ "NODE_ENV": "test"
641
+ }
642
+ }
643
+ ```
644
+
645
+ Configuration files are discovered in:
646
+ 1. Test file directory
647
+ 2. Parent directories (up to project root)
648
+ 3. Project root
649
+ 4. Home directory (`~/.tstest.json`)
650
+
651
+ Settings cascade and merge, with closer files taking precedence.
652
+
653
+ ### Event-based Test Reporting
654
+
655
+ tstest emits detailed events during test execution for integration with CI/CD tools:
656
+
657
+ ```json
658
+ {"event":"suite:started","file":"test/api.test.ts","timestamp":"2025-05-26T10:30:00.000Z"}
659
+ {"event":"test:started","name":"api endpoint validation","timestamp":"2025-05-26T10:30:00.100Z"}
660
+ {"event":"test:progress","name":"api endpoint validation","message":"Validating response schema"}
661
+ {"event":"test:completed","name":"api endpoint validation","passed":true,"duration":145}
662
+ {"event":"suite:completed","file":"test/api.test.ts","passed":true,"total":2,"failed":0}
663
+ ```
664
+
665
+ ### Enhanced TAP Protocol (Protocol V2)
666
+
667
+ tstest uses an enhanced TAP protocol with Unicode delimiters for better parsing:
668
+
669
+ ```
670
+ ⟦TSTEST:EVENT:test:started⟧{"name":"my test","timestamp":"2025-05-26T10:30:00.000Z"}
671
+ ok 1 my test
672
+ ⟦TSTEST:EVENT:test:completed⟧{"name":"my test","passed":true,"duration":145}
673
+ ```
674
+
675
+ This prevents conflicts with test output that might contain TAP-like formatting.
676
+
677
+ ## Advanced Features
678
+
561
679
  ### Glob Pattern Support
562
680
 
563
681
  Run specific test patterns:
@@ -731,6 +849,19 @@ tstest test/api/endpoints.test.ts --verbose --timeout 60
731
849
 
732
850
  ## Changelog
733
851
 
852
+ ### Version 1.11.0
853
+ - 👀 Added Watch Mode with `--watch`/`-w` flag for automatic test re-runs
854
+ - 📊 Implemented real-time test progress updates with event streaming
855
+ - 🎨 Added visual diffs for failed assertions with side-by-side comparison
856
+ - 🔄 Enhanced event-based test lifecycle reporting
857
+ - ⚙️ Added test configuration system with `.tstest.json` files
858
+ - 🚀 Implemented Protocol V2 with Unicode delimiters for better TAP parsing
859
+ - 🐛 Fixed `tap.todo()` to create proper test objects
860
+ - 🐛 Fixed `tap.skip.test()` to correctly create and count test objects
861
+ - 🐛 Fixed `tap.only.test()` implementation with `--only` flag support
862
+ - 📁 Added settings inheritance for cascading test configuration
863
+ - ⏱️ Added debouncing for file change events in watch mode
864
+
734
865
  ### Version 1.10.0
735
866
  - ⏱️ Added `--timeout <seconds>` option for test file timeout protection
736
867
  - 🎯 Added `--startFrom <n>` and `--stopAt <n>` options for test file range control
package/readme.plan.md CHANGED
@@ -2,23 +2,38 @@
2
2
 
3
3
  !! FIRST: Reread /home/philkunz/.claude/CLAUDE.md to ensure following all guidelines !!
4
4
 
5
- ## Improved Internal Protocol (NEW - Critical)
6
-
7
- ### Current Issues
8
- - TAP protocol uses `#` for metadata which conflicts with test descriptions containing `#`
9
- - Fragile regex parsing that breaks with special characters
10
- - Limited extensibility for new metadata types
11
-
12
- ### Proposed Solution: Protocol V2
13
- - Use Unicode delimiters `⟦TSTEST:META:{}⟧` that won't appear in test names
14
- - Structured JSON metadata format
15
- - Separate protocol blocks for complex data (errors, snapshots)
16
- - Backwards compatible with gradual migration
17
-
18
- ### Implementation
19
- - Phase 1: Add protocol v2 parser alongside v1
20
- - Phase 2: Generate v2 by default with --legacy flag for v1
21
- - Phase 3: Full migration to v2 in next major version
5
+ ## Improved Internal Protocol (NEW - Critical) ✅ COMPLETED
6
+
7
+ ### Current Issues ✅ RESOLVED
8
+ - TAP protocol uses `#` for metadata which conflicts with test descriptions containing `#`
9
+ - Fragile regex parsing that breaks with special characters
10
+ - Limited extensibility for new metadata types
11
+
12
+ ### Proposed Solution: Protocol V2 ✅ IMPLEMENTED
13
+ - Use Unicode delimiters `⟦TSTEST:META:{}⟧` that won't appear in test names
14
+ - Structured JSON metadata format
15
+ - Separate protocol blocks for complex data (errors, snapshots)
16
+ - Complete replacement of v1 (no backwards compatibility needed)
17
+
18
+ ### Implementation ✅ COMPLETED
19
+ - Phase 1: Create protocol v2 implementation in ts_tapbundle_protocol
20
+ - Phase 2: Replace all v1 code in both tstest and tapbundle with v2
21
+ - Phase 3: Delete all v1 parsing and generation code
22
+
23
+ #### ts_tapbundle_protocol Directory
24
+ The protocol v2 implementation will be contained in the `ts_tapbundle_protocol` directory as isomorphic TypeScript code:
25
+ - **Isomorphic Design**: All code must work in both browser and Node.js environments
26
+ - **No Node.js Imports**: No Node.js-specific modules allowed (no fs, path, child_process, etc.)
27
+ - **Protocol Classes**: Contains classes implementing all sides of the protocol:
28
+ - ✅ `ProtocolEmitter`: For generating protocol v2 messages (used by tapbundle)
29
+ - ✅ `ProtocolParser`: For parsing protocol v2 messages (used by tstest)
30
+ - ✅ `ProtocolMessage`: Base classes for different message types
31
+ - ✅ `ProtocolTypes`: TypeScript interfaces and types for protocol structures
32
+ - **Pure TypeScript**: Only browser-compatible APIs and pure TypeScript/JavaScript code
33
+ - **Build Integration**:
34
+ - Compiled by `pnpm build` (via tsbuild) to `dist_ts_tapbundle_protocol/`
35
+ - Build order defined in tspublish.json files
36
+ - Imported by ts and ts_tapbundle modules from the compiled dist directory
22
37
 
23
38
  See `readme.protocol.md` for detailed specification.
24
39
 
@@ -77,19 +92,19 @@ interface TapSettings {
77
92
  3. **Application**: Apply settings to test execution
78
93
  4. **Advanced**: Parallel execution and snapshot configuration
79
94
 
80
- ## 1. Enhanced Communication Between tapbundle and tstest
95
+ ## 1. Enhanced Communication Between tapbundle and tstest ✅ COMPLETED
81
96
 
82
- ### 1.1 Real-time Test Progress API
83
- - Create a bidirectional communication channel between tapbundle and tstest
84
- - Emit events for test lifecycle stages (start, progress, completion)
85
- - Allow tstest to subscribe to tapbundle events for better progress reporting
86
- - Implement a standardized message format for test metadata
97
+ ### 1.1 Real-time Test Progress API ✅ COMPLETED
98
+ - Create a bidirectional communication channel between tapbundle and tstest
99
+ - Emit events for test lifecycle stages (start, progress, completion)
100
+ - Allow tstest to subscribe to tapbundle events for better progress reporting
101
+ - Implement a standardized message format for test metadata
87
102
 
88
- ### 1.2 Rich Error Reporting
89
- - Pass structured error objects from tapbundle to tstest
90
- - Include stack traces, code snippets, and contextual information
91
- - Support for error categorization (assertion failures, timeouts, uncaught exceptions)
92
- - Visual diff output for failed assertions
103
+ ### 1.2 Rich Error Reporting ✅ COMPLETED
104
+ - Pass structured error objects from tapbundle to tstest
105
+ - Include stack traces, code snippets, and contextual information
106
+ - Support for error categorization (assertion failures, timeouts, uncaught exceptions)
107
+ - Visual diff output for failed assertions
93
108
 
94
109
  ## 2. Enhanced toolsArg Functionality
95
110
 
@@ -134,13 +149,15 @@ tap.test('performance test', async (toolsArg) => {
134
149
  ## 5. Test Execution Improvements
135
150
 
136
151
 
137
- ### 5.2 Watch Mode
152
+ ### 5.2 Watch Mode ✅ COMPLETED
138
153
  - Automatically re-run tests on file changes
139
- - Intelligent test selection based on changed files
140
- - Fast feedback loop for development
141
- - Integration with IDE/editor plugins
154
+ - Debounced file change detection (300ms)
155
+ - Clear console output between runs
156
+ - Shows which files triggered re-runs
157
+ - Graceful exit with Ctrl+C
158
+ - `--watch-ignore` option for excluding patterns
142
159
 
143
- ### 5.3 Advanced Test Filtering (Partial)
160
+ ### 5.3 Advanced Test Filtering (Partial) ⚠️
144
161
  ```typescript
145
162
  // Exclude tests by pattern (not yet implemented)
146
163
  tstest --exclude "**/slow/**"
@@ -182,30 +199,38 @@ tstest --changed
182
199
 
183
200
  ## Implementation Phases
184
201
 
185
- ### Phase 1: Improved Internal Protocol (Priority: Critical) (NEW)
186
- 1. Implement Protocol V2 parser in tstest
187
- 2. Add protocol version negotiation
188
- 3. Update tapbundle to generate V2 format with feature flag
189
- 4. Test with real-world test suites containing special characters
190
-
191
- ### Phase 2: Test Configuration System (Priority: High)
192
- 1. Implement tap.settings() API with TypeScript interfaces
193
- 2. Add 00init.ts discovery and loading mechanism
194
- 3. Implement settings inheritance and merge logic
195
- 4. Apply settings to test execution (timeouts, retries, etc.)
196
-
197
- ### Phase 3: Enhanced Communication (Priority: High)
198
- 1. Build on Protocol V2 for richer communication
199
- 2. Implement real-time test progress API
200
- 3. Add structured error reporting with diffs and traces
201
-
202
- ### Phase 4: Developer Experience (Priority: Medium)
202
+ ### Phase 1: Improved Internal Protocol (Priority: Critical) ✅ COMPLETED
203
+ 1. Create ts_tapbundle_protocol directory with isomorphic protocol v2 implementation
204
+ - Implement ProtocolEmitter class for message generation
205
+ - Implement ProtocolParser class for message parsing
206
+ - Define ProtocolMessage types and interfaces
207
+ - ✅ Ensure all code is browser and Node.js compatible
208
+ - Add tspublish.json to configure build order
209
+ 2. Update build configuration to compile ts_tapbundle_protocol first
210
+ 3. Replace TAP parser in tstest with Protocol V2 parser importing from dist_ts_tapbundle_protocol
211
+ 4. Replace TAP generation in tapbundle with Protocol V2 emitter importing from dist_ts_tapbundle_protocol
212
+ 5. Delete all v1 TAP parsing code from tstest
213
+ 6. ✅ Delete all v1 TAP generation code from tapbundle
214
+ 7. Test with real-world test suites containing special characters
215
+
216
+ ### Phase 2: Test Configuration System (Priority: High) ✅ COMPLETED
217
+ 1. Implement tap.settings() API with TypeScript interfaces
218
+ 2. ✅ Add 00init.ts discovery and loading mechanism
219
+ 3. Implement settings inheritance and merge logic
220
+ 4. ✅ Apply settings to test execution (timeouts, retries, etc.)
221
+
222
+ ### Phase 3: Enhanced Communication (Priority: High) ✅ COMPLETED
223
+ 1. ✅ Build on Protocol V2 for richer communication
224
+ 2. ✅ Implement real-time test progress API
225
+ 3. ✅ Add structured error reporting with diffs and traces
226
+
227
+ ### Phase 4: Developer Experience (Priority: Medium) ❌ NOT STARTED
203
228
  1. Add watch mode
204
229
  2. Implement custom reporters
205
230
  3. Complete advanced test filtering options
206
231
  4. Add performance benchmarking API
207
232
 
208
- ### Phase 5: Analytics and Performance (Priority: Low)
233
+ ### Phase 5: Analytics and Performance (Priority: Low) ❌ NOT STARTED
209
234
  1. Build test analytics dashboard
210
235
  2. Implement coverage integration
211
236
  3. Create trend analysis tools
@@ -214,10 +239,10 @@ tstest --changed
214
239
  ## Technical Considerations
215
240
 
216
241
  ### API Design Principles
217
- - Maintain backward compatibility
242
+ - Clean, modern API design without legacy constraints
218
243
  - Progressive enhancement approach
219
- - Opt-in features to avoid breaking changes
220
- - Clear migration paths for new features
244
+ - Well-documented features and APIs
245
+ - Clear, simple interfaces
221
246
 
222
247
  ### Performance Goals
223
248
  - Minimal overhead for test execution
@@ -229,4 +254,68 @@ tstest --changed
229
254
  - Clean interfaces between tstest and tapbundle
230
255
  - Extensible plugin architecture
231
256
  - Standard test result format
232
- - Compatible with existing CI/CD tools
257
+ - Compatible with existing CI/CD tools
258
+
259
+ ## Summary of Remaining Work
260
+
261
+ ### ✅ Completed
262
+ - **Protocol V2**: Full implementation with Unicode delimiters, structured metadata, and special character handling
263
+ - **Test Configuration System**: tap.settings() API, 00init.ts discovery, settings inheritance, lifecycle hooks
264
+ - **Enhanced Communication**: Event-based test lifecycle reporting, visual diff output for assertion failures, real-time test progress API
265
+ - **Rich Error Reporting**: Stack traces, error metadata, and visual diffs through protocol
266
+ - **Tags Filtering**: `--tags` option for running specific tagged tests
267
+
268
+ ### ✅ Existing Features (Not in Plan)
269
+ - **Timeout Support**: `--timeout` option and per-test timeouts
270
+ - **Test Retries**: `tap.retry()` for flaky test handling
271
+ - **Parallel Tests**: `.testParallel()` for concurrent execution
272
+ - **Snapshot Testing**: Basic implementation with `toMatchSnapshot()`
273
+ - **Test Lifecycle**: `describe()` blocks with `beforeEach`/`afterEach`
274
+ - **Skip Tests**: `tap.skip.test()` (though it doesn't create test objects)
275
+ - **Log Files**: `--logfile` option saves output to `.nogit/testlogs/`
276
+ - **Test Range**: `--startFrom` and `--stopAt` for partial runs
277
+
278
+ ### ⚠️ Partially Completed
279
+ - **Advanced Test Filtering**: Have `--tags` but missing `--exclude`, `--failed`, `--changed`
280
+
281
+ ### ❌ Not Started
282
+
283
+ #### High Priority
284
+
285
+ #### Medium Priority
286
+ 2. **Developer Experience**
287
+ - Watch mode for file changes
288
+ - Custom reporters (JSON, JUnit, HTML, Markdown)
289
+ - Performance benchmarking API
290
+ - Better error messages with suggestions
291
+
292
+ 3. **Enhanced toolsArg**
293
+ - Test data injection
294
+ - Context sharing between tests
295
+ - Parameterized tests
296
+
297
+ 4. **Test Organization**
298
+ - Hierarchical test suites
299
+ - Nested describe blocks
300
+ - Suite-level lifecycle hooks
301
+
302
+ #### Low Priority
303
+ 5. **Analytics and Performance**
304
+ - Test analytics dashboard
305
+ - Code coverage integration
306
+ - Trend analysis
307
+ - Flaky test detection
308
+
309
+ ### Recently Fixed Issues ✅
310
+ - **tap.todo()**: Now fully implemented with test object creation
311
+ - **tap.skip.test()**: Now creates test objects and maintains accurate test count
312
+ - **tap.only.test()**: Works correctly - when .only tests exist, only those run
313
+
314
+ ### Remaining Minor Issues
315
+ - **Protocol Output**: Some protocol messages still appear in console output
316
+
317
+ ### Next Recommended Steps
318
+ 1. Add Watch Mode (Phase 4) - high developer value for fast feedback
319
+ 2. Implement Custom Reporters - important for CI/CD integration
320
+ 3. Implement performance benchmarking API
321
+ 4. Add better error messages with suggestions
@@ -3,6 +3,6 @@
3
3
  */
4
4
  export const commitinfo = {
5
5
  name: '@git.zone/tstest',
6
- version: '1.11.5',
6
+ version: '2.2.0',
7
7
  description: 'a test utility to run tests that match test/**/*.ts'
8
8
  }
package/ts/index.ts CHANGED
@@ -16,6 +16,8 @@ export const runCli = async () => {
16
16
  let startFromFile: number | null = null;
17
17
  let stopAtFile: number | null = null;
18
18
  let timeoutSeconds: number | null = null;
19
+ let watchMode: boolean = false;
20
+ let watchIgnorePatterns: string[] = [];
19
21
 
20
22
  // Parse options
21
23
  for (let i = 0; i < args.length; i++) {
@@ -84,6 +86,18 @@ export const runCli = async () => {
84
86
  process.exit(1);
85
87
  }
86
88
  break;
89
+ case '--watch':
90
+ case '-w':
91
+ watchMode = true;
92
+ break;
93
+ case '--watch-ignore':
94
+ if (i + 1 < args.length) {
95
+ watchIgnorePatterns = args[++i].split(',');
96
+ } else {
97
+ console.error('Error: --watch-ignore requires a comma-separated list of patterns');
98
+ process.exit(1);
99
+ }
100
+ break;
87
101
  default:
88
102
  if (!arg.startsWith('-')) {
89
103
  testPath = arg;
@@ -110,6 +124,8 @@ export const runCli = async () => {
110
124
  console.error(' --startFrom <n> Start running from test file number n');
111
125
  console.error(' --stopAt <n> Stop running at test file number n');
112
126
  console.error(' --timeout <s> Timeout test files after s seconds');
127
+ console.error(' --watch, -w Watch for file changes and re-run tests');
128
+ console.error(' --watch-ignore Patterns to ignore in watch mode (comma-separated)');
113
129
  process.exit(1);
114
130
  }
115
131
 
@@ -125,7 +141,12 @@ export const runCli = async () => {
125
141
  }
126
142
 
127
143
  const tsTestInstance = new TsTest(process.cwd(), testPath, executionMode, logOptions, tags, startFromFile, stopAtFile, timeoutSeconds);
128
- await tsTestInstance.run();
144
+
145
+ if (watchMode) {
146
+ await tsTestInstance.runWatch(watchIgnorePatterns);
147
+ } else {
148
+ await tsTestInstance.run();
149
+ }
129
150
  };
130
151
 
131
152
  // Execute CLI when this file is run directly
package/ts/tspublish.json CHANGED
@@ -1,3 +1,3 @@
1
1
  {
2
- "order": 2
2
+ "order": 4
3
3
  }