Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/copilot-instructions.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,6 @@ Node-API Conformance Test Suite: A pure ECMAScript test suite for Node-API imple
- **Process Isolation**: The built-in runner for Node.js, run each test in isolation to prevent crashes from aborting entire test suite.

## Development Focus
- Port existing tests from `nodejs/node/test/js-native-api` into `tests/engine/` and `nodejs/node/test/node-api` into `tests/runtime/`, removing dependencies on Node.js runtime APIs while preserving test coverage
- Port existing tests from `nodejs/node/test/js-native-api` into `tests/js-native-api/` and `nodejs/node/test/node-api` into `tests/node-api/`, removing dependencies on Node.js runtime APIs while preserving test coverage
- Structure tests for easy integration by external implementors
- Consider following patterns from [web-platform-tests](https://web-platform-tests.org/) and [WebGPU CTS](https://github.com/gpuweb/cts) projects where applicable.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
node_modules/
/node/
47 changes: 47 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

13 changes: 13 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
{
"name": "node-api-cts",
"version": "0.1.0",
"private": true,
"type": "module",
"scripts": {
"shallow-checkout-nodejs": "node ./tools/shallow-checkout-nodejs.ts"
},
"devDependencies": {
"@types/node": "^24.10.1",
"typescript": "^5.9.3"
}
}
95 changes: 95 additions & 0 deletions tools/shallow-checkout-nodejs.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
#!/usr/bin/env node
import assert from "node:assert/strict";
import {
spawnSync,
type SpawnSyncOptionsWithStringEncoding,
} from "node:child_process";
import { cpSync, mkdtempSync, mkdirSync, rmSync } from "node:fs";
import path from "node:path";
import { tmpdir } from "node:os";

const PATHS = ["test/js-native-api", "test/node-api", "doc/api/n-api.md"];
const NODE_REPO_URL = "https://github.com/nodejs/node.git";
const ROOT_PATH = path.resolve(import.meta.dirname, "..");
const NODE_ROOT_PATH = path.join(ROOT_PATH, "node");

function getOptionsFromArgs([ref = "main"]: string[]) {
return { ref };
}

function runGit(
args: string[],
options: Partial<SpawnSyncOptionsWithStringEncoding> = {}
) {
const result = spawnSync("git", args, {
stdio: options.stdio ?? "inherit",
encoding: options.encoding ?? "utf8",
cwd: options.cwd,
});

assert(!result.error, result.error);
assert.equal(
result.status,
0,
`git ${args.join(" ")} exited with ${result.status ?? "unknown"}`
);

return result;
}

function ensureGitAvailable() {
return runGit(["--version"], { stdio: "pipe" }).stdout.trim();
}

function copyPath(source: string, destination: string) {
rmSync(destination, { recursive: true, force: true });

mkdirSync(path.dirname(destination), { recursive: true });
cpSync(source, destination, { recursive: true });
}

function main() {
const { ref } = getOptionsFromArgs(process.argv.slice(2));
mkdirSync(NODE_ROOT_PATH, { recursive: true });

const gitVersion = ensureGitAvailable();
console.log(`Using ${gitVersion}`);

const tempDir = mkdtempSync(path.join(tmpdir(), "node-tests-"));
console.log(`Cloning ${NODE_REPO_URL} @ ${ref} into ${tempDir}`);

try {
runGit([
"clone",
"--depth=1",
"--filter=blob:none",
"--sparse",
"--branch",
ref,
NODE_REPO_URL,
tempDir,
]);

runGit(["sparse-checkout", "set", "--no-cone", ...PATHS], {
cwd: tempDir,
});

for (const sourcePath of PATHS) {
const source = path.join(tempDir, sourcePath);
const destination = path.join(NODE_ROOT_PATH, sourcePath);
console.log(`Updating ${destination}`);
copyPath(source, destination);
}
} finally {
rmSync(tempDir, { recursive: true, force: true });
}

console.log("Node.js tests and docs checkout complete.");
}

try {
main();
} catch (error) {
console.error(error instanceof Error ? error.message : error);
process.exitCode = 1;
}
14 changes: 14 additions & 0 deletions tools/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"compilerOptions": {
"target": "ES2022",
"module": "NodeNext",
"moduleResolution": "NodeNext",
"strict": true,
"types": ["node"],
"esModuleInterop": true,
"forceConsistentCasingInFileNames": true,
"skipLibCheck": true,
"noEmit": true
},
"include": ["**/*.ts"]
}