Elide runs .ts, .mts, .cts and .tsx files by removing their types; it does not type-check them or read
tsconfig.json.
TypeScript syntax
| Syntax | Status |
|---|---|
Type annotations, interfaces, type, generics, as, satisfies, ! | Removed |
import type, import { type X } | Removed |
enum, const enum | Compiled to objects |
namespace | Compiled |
Constructor parameter properties (constructor(public x: number)) | Compiled |
abstract, declare fields, override, accessor | Supported |
import fs = require("node:fs") | Supported |
| Decorators on classes and methods | Standard decorators: each receives (value, context) |
experimentalDecorators-style decorators | Not supported; they receive standard arguments |
Parameter decorators (constructor(@inject x)) | SyntaxError: … expected BindingIdentifier or BindingPattern |
<string>value type assertions | Precompiler failed with 1 diagnostic(s): … [ERROR] Unexpected token; use value as string |
export = value | SyntaxError: … Expected an operand but found export |
tsconfig.json paths | Ignored: TypeError: Module not found: '@lib/ |
Imports may name the .ts file, a .js extension, or no extension; all three resolve to math.ts:
import { add } from "./src/lib/math.ts";
import { add as add2 } from "./src/lib/math.js";
import { add as add3 } from "./src/lib/math";
console.log(add(1, 2), add2(2, 2), add3(3, 3));3 4 6JSX
.tsx files use the automatic JSX runtime and import react/jsx-runtime. Install React yourself:
// app.tsx
import { renderToString } from "react-dom/server";
function Hello({ name }: { name: string }) {
return <p>hello {name}</p>;
}
console.log(renderToString(<Hello name="elide" />));elide install --ecosystems=npm # react, react-dom in package.json
elide app.tsx<p>hello <!-- -->elide</p>| Input | Result |
|---|---|
/ at the top of a .tsx file | Imports preact/jsx-runtime |
jsxImportSource in tsconfig.json | Ignored; React is used |
/** @jsx h */ | Ignored; React elements are created |
JSX in a .jsx file | SyntaxError: … Expected an operand but found <; rename it to .tsx |
Check types
Install TypeScript and run its compiler through Elide:
{
"scripts": { "typecheck": "tsc --noEmit" },
"devDependencies": { "typescript": "^5.9.0", "@types/node": "^24.0.0" }
}{
"compilerOptions": {
"module": "nodenext",
"target": "esnext",
"strict": true,
"noEmit": true,
"allowImportingTsExtensions": true,
"erasableSyntaxOnly": true,
"verbatimModuleSyntax": true,
"types": ["node"]
}
}elide install --ecosystems=npm
elide run typecheck # or: elide run tscbad-types.ts(1,7): error TS2322: Type 'string' is not assignable to type 'number'.tsc exits 2 on type errors. Pass compiler options after --: elide run tsc -- --version. erasableSyntaxOnly
makes tsc reject enums, namespaces and parameter properties; drop it if you use them.
Elide types
@elide-dev/types declares Elide’s own globals and modules and pulls in @types/node. Add it as a dev
dependency and name it in types:
{
"type": "module",
"scripts": { "typecheck": "tsc --noEmit" },
"devDependencies": { "typescript": "^5.9.0", "@elide-dev/types": "nightly" }
}{
"compilerOptions": {
"module": "nodenext",
"target": "esnext",
"strict": true,
"noEmit": true,
"allowImportingTsExtensions": true,
"types": ["@elide-dev/types"]
}
}// main.ts
import { Database } from "elide:postgres";
import { readFileSync } from "node:fs";
const bytes: number = readFileSync("package.json").length;
console.log(`Elide ${Elide.version}: ${bytes} bytes`);
export const open = (url: string) => Database.connect(url);elide install --ecosystems=npm
elide run typecheck
elide main.tsElide 1.6.0: 149 bytes| API | Declared |
|---|---|
Elide.version, debug, release, buildMode | Yes |
Elide. | Typed as boolean; the value is a string |
Elide.serve() | No: Property 'serve' does not exist |
elide:postgres, elide:mysql | Yes |
elide:sqlite, elide:cel, elide:telemetry | No |
import … from ". | Yes, as any |
node:* modules | Yes, through @types/node |
The nightly tag tracks the newest declarations; latest is older.
ES modules and CommonJS
| File | Module system |
|---|---|
.mjs, .mts | ES module |
.cjs, .cts | CommonJS |
.ts, .tsx | ES module |
.js | ES module when the nearest package.json has "type": "module", else CommonJS |
A .js file with import statements and no "type": "module" fails with SyntaxError: … Expected an operand but found import; add the field or rename the file to .mjs.
| Feature | Behavior |
|---|---|
import lib, { a } from ". | module.exports is the default export, its properties are named exports |
await import(". | Works |
require("./lib.mjs") | Error: require() of ES Module … not supported. (ERR_REQUIRE_ESM); use await import() |
createRequire(import. | Works |
import.meta.url, .filename, .dirname | Work |
import.meta.main, import.meta.resolve | undefined |
__dirname in CommonJS | Works |
__filename in the entry CommonJS file | "unknown"; use module.filename. Required files get the real path. |
__dirname, require in ES modules | Defined, unlike Node; do not rely on them |
JSON
All of these load data.json:
import data from "./data.json" with { type: "json" };
import same from "./data.json";
const viaRequire = require("./data.json"); // CommonJSPackage exports and imports
package.json field | import | require() |
|---|---|---|
exports subpaths ("./feature": …) | Works | Works |
exports for the package root, with main | Works | Uses main |
exports for the package root, no main | Works | Error: Cannot find module 'pkg' |
import and default conditions | Work | — |
A require condition listed before default | Selected instead of default | — |
| Unexported subpath | Package subpath is not defined by "exports" field (no code) | — |
imports ("#internal") | TypeError: Packages imports do not define the specifier: '#internal' | Error: Cannot find module '#internal' |