feat(tstest.classes.runtime.parser): Add support for all runtime token and update docs/tests; regenerate lockfile and add local settings
This commit is contained in:
10
changelog.md
10
changelog.md
@@ -1,5 +1,15 @@
|
||||
# Changelog
|
||||
|
||||
## 2025-10-12 - 2.5.0 - feat(tstest.classes.runtime.parser)
|
||||
Add support for "all" runtime token and update docs/tests; regenerate lockfile and add local settings
|
||||
|
||||
- Add support for the `all` runtime token (expands to node, chromium, deno, bun) in tstest filename parser (tstest.classes.runtime.parser)
|
||||
- Handle `all` with modifiers (e.g. `*.all.nonci.ts`) and mixed tokens (e.g. `node+all`) so it expands to the full runtime set
|
||||
- Add unit tests covering `all` cases in test/test.runtime.parser.node.ts
|
||||
- Update README (examples and tables) to document `.all.ts` and `.all.nonci.ts` usage and include a universal example
|
||||
- Update ts files' parser comments and constants to include ALL_RUNTIMES
|
||||
- Add deno.lock (dependency lockfile) and a local .claude/settings.local.json for project permissions / local settings
|
||||
|
||||
## 2025-10-11 - 2.4.3 - fix(docs)
|
||||
Update documentation: expand README with multi-runtime architecture, add module READMEs, and add local dev settings
|
||||
|
||||
|
17
readme.md
17
readme.md
@@ -61,15 +61,29 @@ Name your test files with runtime specifiers to control where they run:
|
||||
| `*.chromium.ts` | Chromium browser | `test.dom.chromium.ts` |
|
||||
| `*.deno.ts` | Deno runtime | `test.http.deno.ts` |
|
||||
| `*.bun.ts` | Bun runtime | `test.fast.bun.ts` |
|
||||
| `*.all.ts` | All runtimes (Node, Chromium, Deno, Bun) | `test.universal.all.ts` |
|
||||
| `*.node+chromium.ts` | Both Node.js and Chromium | `test.isomorphic.node+chromium.ts` |
|
||||
| `*.node+deno.ts` | Both Node.js and Deno | `test.cross.node+deno.ts` |
|
||||
| `*.deno+bun.ts` | Both Deno and Bun | `test.modern.deno+bun.ts` |
|
||||
| `*.chromium.nonci.ts` | Chromium, skip in CI | `test.visual.chromium.nonci.ts` |
|
||||
| `*.all.nonci.ts` | All runtimes, skip in CI | `test.comprehensive.all.nonci.ts` |
|
||||
|
||||
**Multi-Runtime Examples:**
|
||||
|
||||
```typescript
|
||||
// test.api.node+deno+bun.ts - runs in Node.js, Deno, and Bun
|
||||
// test.api.all.ts - runs in all runtimes (Node, Chromium, Deno, Bun)
|
||||
import { expect, tap } from '@git.zone/tstest/tapbundle';
|
||||
|
||||
tap.test('universal HTTP test', async () => {
|
||||
const response = await fetch('https://api.example.com/test');
|
||||
expect(response.status).toEqual(200);
|
||||
});
|
||||
|
||||
export default tap.start();
|
||||
```
|
||||
|
||||
```typescript
|
||||
// test.api.node+deno+bun.ts - runs in specific runtimes
|
||||
import { expect, tap } from '@git.zone/tstest/tapbundle';
|
||||
|
||||
tap.test('cross-runtime HTTP test', async () => {
|
||||
@@ -915,6 +929,7 @@ tstest test/api/endpoints.test.ts --verbose --timeout 60
|
||||
### Version 2.4.0
|
||||
- 🚀 **Multi-Runtime Architecture** - Support for Deno, Bun, Node.js, and Chromium
|
||||
- 🔀 **New Naming Convention** - Flexible `.runtime1+runtime2.ts` pattern
|
||||
- 🌐 **Universal Testing** - `.all.ts` pattern runs tests on all supported runtimes
|
||||
- 🔄 **Migration Tool** - Easy migration from legacy naming (`.browser.ts`, `.both.ts`)
|
||||
- 🦕 **Deno Support** - Full Deno runtime with Node.js compatibility
|
||||
- 🐰 **Bun Support** - Ultra-fast Bun runtime integration
|
||||
|
@@ -164,4 +164,40 @@ tap.test('parseTestFilename - handles full paths', async () => {
|
||||
expect(parsed.original).toEqual('test.node+chromium.ts');
|
||||
});
|
||||
|
||||
tap.test('parseTestFilename - all keyword expands to all runtimes', async () => {
|
||||
const parsed = parseTestFilename('test.all.ts');
|
||||
expect(parsed.baseName).toEqual('test');
|
||||
expect(parsed.runtimes).toEqual(['node', 'chromium', 'deno', 'bun']);
|
||||
expect(parsed.modifiers).toEqual([]);
|
||||
expect(parsed.extension).toEqual('ts');
|
||||
expect(parsed.isLegacy).toEqual(false);
|
||||
});
|
||||
|
||||
tap.test('parseTestFilename - all keyword with nonci modifier', async () => {
|
||||
const parsed = parseTestFilename('test.all.nonci.ts');
|
||||
expect(parsed.baseName).toEqual('test');
|
||||
expect(parsed.runtimes).toEqual(['node', 'chromium', 'deno', 'bun']);
|
||||
expect(parsed.modifiers).toEqual(['nonci']);
|
||||
expect(parsed.extension).toEqual('ts');
|
||||
expect(parsed.isLegacy).toEqual(false);
|
||||
});
|
||||
|
||||
tap.test('parseTestFilename - all keyword with complex basename', async () => {
|
||||
const parsed = parseTestFilename('test.some.feature.all.ts');
|
||||
expect(parsed.baseName).toEqual('test.some.feature');
|
||||
expect(parsed.runtimes).toEqual(['node', 'chromium', 'deno', 'bun']);
|
||||
expect(parsed.modifiers).toEqual([]);
|
||||
expect(parsed.extension).toEqual('ts');
|
||||
expect(parsed.isLegacy).toEqual(false);
|
||||
});
|
||||
|
||||
tap.test('parseTestFilename - all keyword in chain expands to all runtimes', async () => {
|
||||
const parsed = parseTestFilename('test.node+all.ts');
|
||||
expect(parsed.baseName).toEqual('test');
|
||||
expect(parsed.runtimes).toEqual(['node', 'chromium', 'deno', 'bun']);
|
||||
expect(parsed.modifiers).toEqual([]);
|
||||
expect(parsed.extension).toEqual('ts');
|
||||
expect(parsed.isLegacy).toEqual(false);
|
||||
});
|
||||
|
||||
export default tap.start();
|
||||
|
@@ -3,6 +3,6 @@
|
||||
*/
|
||||
export const commitinfo = {
|
||||
name: '@git.zone/tstest',
|
||||
version: '2.4.3',
|
||||
version: '2.5.0',
|
||||
description: 'a test utility to run tests that match test/**/*.ts'
|
||||
}
|
||||
|
@@ -6,6 +6,7 @@
|
||||
* - test.chromium.ts
|
||||
* - test.node+chromium.ts
|
||||
* - test.deno+bun.ts
|
||||
* - test.all.ts (runs on all runtimes)
|
||||
* - test.chromium.nonci.ts
|
||||
*/
|
||||
|
||||
@@ -29,6 +30,7 @@ export interface ParserConfig {
|
||||
const KNOWN_RUNTIMES: Set<string> = new Set(['node', 'chromium', 'deno', 'bun']);
|
||||
const KNOWN_MODIFIERS: Set<string> = new Set(['nonci']);
|
||||
const VALID_EXTENSIONS: Set<string> = new Set(['ts', 'tsx', 'mts', 'cts']);
|
||||
const ALL_RUNTIMES: Runtime[] = ['node', 'chromium', 'deno', 'bun'];
|
||||
|
||||
// Legacy mappings for backwards compatibility
|
||||
const LEGACY_RUNTIME_MAP: Record<string, Runtime[]> = {
|
||||
@@ -102,9 +104,12 @@ export function parseTestFilename(
|
||||
const runtimeCandidates = token.split('+').map(r => r.trim()).filter(Boolean);
|
||||
const validRuntimes: Runtime[] = [];
|
||||
const invalidRuntimes: string[] = [];
|
||||
let hasAllKeyword = false;
|
||||
|
||||
for (const candidate of runtimeCandidates) {
|
||||
if (KNOWN_RUNTIMES.has(candidate)) {
|
||||
if (candidate === 'all') {
|
||||
hasAllKeyword = true;
|
||||
} else if (KNOWN_RUNTIMES.has(candidate)) {
|
||||
// Dedupe: only add if not already in list
|
||||
if (!validRuntimes.includes(candidate as Runtime)) {
|
||||
validRuntimes.push(candidate as Runtime);
|
||||
@@ -114,11 +119,18 @@ export function parseTestFilename(
|
||||
}
|
||||
}
|
||||
|
||||
// If 'all' keyword is present, expand to all runtimes
|
||||
if (hasAllKeyword) {
|
||||
runtimes = [...ALL_RUNTIMES];
|
||||
runtimeTokenIndex = i;
|
||||
break;
|
||||
}
|
||||
|
||||
if (invalidRuntimes.length > 0) {
|
||||
if (strictUnknownRuntime) {
|
||||
throw new Error(
|
||||
`Unknown runtime(s) in "${fileName}": ${invalidRuntimes.join(', ')}. ` +
|
||||
`Valid runtimes: ${Array.from(KNOWN_RUNTIMES).join(', ')}`
|
||||
`Valid runtimes: ${Array.from(KNOWN_RUNTIMES).join(', ')}, all`
|
||||
);
|
||||
} else {
|
||||
console.warn(
|
||||
@@ -138,6 +150,13 @@ export function parseTestFilename(
|
||||
}
|
||||
}
|
||||
|
||||
// Check if this is the 'all' keyword (expands to all runtimes)
|
||||
if (token === 'all') {
|
||||
runtimes = [...ALL_RUNTIMES];
|
||||
runtimeTokenIndex = i;
|
||||
break;
|
||||
}
|
||||
|
||||
// Check if this is a single runtime token
|
||||
if (KNOWN_RUNTIMES.has(token)) {
|
||||
runtimes = [token as Runtime];
|
||||
|
Reference in New Issue
Block a user