-
-
Notifications
You must be signed in to change notification settings - Fork 28
Description
I believe it's time to discuss our policies around experimental features in the project. Features like --experimental-network-import
are challenging to assess and maintain, especially when there is no active champion or creator overseeing them.
Proposal
I propose that when the creator or champion of an experimental feature becomes inactive, we should:
- Re-evaluate the benefits of the feature.
- Decide whether to remove the feature entirely or delegate its maintenance to a team.
This approach will help us set clear expectations, assess and review vulnerabilities, and ensure better maintenance of our experimental features.
Recent Example
We recently dropped the --experimental-policy
feature because:
- We were receiving reports about it.
- The documentation did not clearly define its boundaries and security expectations, making it difficult to assess.
Actionable Steps
To facilitate this discussion, I have written a simple script to list all experimental APIs from nodejs/node/docs/api/**
. You can find it here.
Can we evaluate these experimental features either asynchronously or through a dedicated call?
File | API | Group Header | Re-Evaluated |
---|---|---|---|
doc/api/async_context.md | AsyncLocalStorage.bind(fn) |
AsyncLocalStorage | ⬜ |
doc/api/async_context.md | AsyncLocalStorage.snapshot() |
AsyncLocalStorage | ⬜ |
doc/api/async_context.md | asyncLocalStorage.disable() |
AsyncLocalStorage | ⬜ |
doc/api/async_context.md | asyncLocalStorage.enterWith(store) |
AsyncLocalStorage | ⬜ |
doc/api/async_context.md | asyncLocalStorage.exit(callback[, ...args]) |
AsyncLocalStorage | ⬜ |
doc/api/async_hooks.md | AsyncHooks |
Async hooks | ⬜ |
doc/api/buffer.md | buffer.resolveObjectURL(id) |
Buffer | ⬜ |
doc/api/child_process.md | subprocess[Symbol.dispose]() |
Child Process | ⬜ |
doc/api/cli.md | --allow-addons |
Permission Model | ✅ |
doc/api/cli.md | --allow-child-process |
Permission Model | ✅ |
doc/api/cli.md | --allow-fs-read |
Permission Model | ✅ |
doc/api/cli.md | --allow-fs-write |
Permission Model | ✅ |
doc/api/cli.md | --allow-wasi |
Permission Model | ✅ |
doc/api/cli.md | --allow-worker |
Permission Model | ✅ |
doc/api/cli.md | --build-snapshot |
Startup Snapshot | ⬜ |
doc/api/cli.md | --build-snapshot-config |
Startup Snapshot | ⬜ |
doc/api/cli.md | -C condition , --conditions=condition |
Conditional Exports | ⬜ |
doc/api/cli.md | --cpu-prof |
⬜ | |
doc/api/cli.md | --cpu-prof-dir |
⬜ | |
doc/api/cli.md | --cpu-prof-interval |
⬜ | |
doc/api/cli.md | --cpu-prof-name |
⬜ | |
doc/api/cli.md | --disable-warning=code-or-type |
⬜ | |
doc/api/cli.md | --expose-gc |
⬜ | |
doc/api/cli.md | --env-file=config |
Node Env | ⬜ |
doc/api/cli.md | --experimental-default-type=type |
Loaders | ⬜ |
doc/api/cli.md | --experimental-detect-module |
Loaders | ⬜ |
doc/api/cli.md | --experimental-network-imports |
Loaders | ⬜ |
doc/api/cli.md | --experimental-permission |
Permission Model | ✅ |
doc/api/cli.md | --experimental-require-module |
Loaders | ⬜ |
doc/api/cli.md | --experimental-sea-config |
SEA | ⬜ |
doc/api/cli.md | --experimental-shadow-realm |
⬜ | |
doc/api/cli.md | --experimental-test-module-mocks |
Test Runner | ⬜ |
doc/api/cli.md | --experimental-test-snapshots |
Test Runner | ⬜ |
doc/api/cli.md | --frozen-intrinsics |
⬜ | |
doc/api/cli.md | --heap-prof |
⬜ | |
doc/api/cli.md | --heap-prof-dir |
⬜ | |
doc/api/cli.md | --heap-prof-interval |
⬜ | |
doc/api/cli.md | --heap-prof-name |
⬜ | |
doc/api/cli.md | --heapsnapshot-near-heap-limit=max_count |
⬜ | |
doc/api/cli.md | --import=module |
Loaders | ⬜ |
doc/api/cli.md | --jitless |
⬜ | |
doc/api/cli.md | --no-experimental-global-navigator |
⬜ | |
doc/api/cli.md | --run |
✅ | |
doc/api/cli.md | --snapshot-blob=path |
Startup Snapshot | ⬜ |
doc/api/cli.md | --test-update-snapshots |
⬜ | |
doc/api/cli.md | NODE_COMPILE_CACHE=dir |
⬜ | |
doc/api/cli.md | Source map cache | ⬜ | |
doc/api/corepack.md | Corepack | Corepack | ⬜ |
doc/api/crypto.md | crypto.hash(algorithm, data[, outputEncoding]) |
Crypto | ⬜ |
doc/api/dgram.md | socket[Symbol.asyncDispose]() |
⬜ | |
doc/api/diagnostics_channel.md | diagnostics_channel.tracingChannel(nameOrChannels) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | channel.bindStore(store[, transform]) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | channel.unbindStore(store) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | channel.runStores(context, fn[, thisArg[, ...args]]) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | Class: TracingChannel |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | tracingChannel.subscribe(subscribers) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | tracingChannel.unsubscribe(subscribers) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | tracingChannel.traceSync(fn[, context[, thisArg[, ...args]]]) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | tracingChannel.tracePromise(fn[, context[, thisArg[, ...args]]]) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | tracingChannel.traceCallback(fn, position, context, thisArg, ...args) |
Diagnostics | ⬜ |
doc/api/diagnostics_channel.md | Built-in Channels | ⬜ | |
doc/api/errors.md | ERR_INPUT_TYPE_NOT_ALLOWED |
⬜ | |
doc/api/errors.md | ERR_REQUIRE_CYCLE_MODULE |
⬜ | |
doc/api/errors.md | ERR_REQUIRE_ASYNC_MODULE |
⬜ | |
doc/api/errors.md | ERR_REQUIRE_ESM |
⬜ | |
doc/api/errors.md | ERR_UNKNOWN_FILE_EXTENSION |
⬜ | |
doc/api/errors.md | ERR_UNKNOWN_MODULE_FORMAT |
⬜ | |
doc/api/errors.md | ERR_USE_AFTER_CLOSE |
⬜ | |
doc/api/errors.md | ERR_NETWORK_IMPORT_BAD_RESPONSE |
⬜ | |
doc/api/errors.md | ERR_NETWORK_IMPORT_DISALLOWED |
⬜ | |
doc/api/esm.md | import.meta.dirname |
⬜ | |
doc/api/esm.md | import.meta.filename |
⬜ | |
doc/api/esm.md | import.meta.resolve(specifier) |
⬜ | |
doc/api/esm.md | JSON modules | ESM | ⬜ |
doc/api/esm.md | Wasm modules | ESM | ⬜ |
doc/api/esm.md | HTTPS and HTTP imports | ESM | ⬜ |
doc/api/events.md | events.addAbortListener(signal, listener) |
Events | ⬜ |
doc/api/fs.md | filehandle.readableWebStream([options]) |
File System | ⬜ |
doc/api/fs.md | filehandle[Symbol.asyncDispose]() |
File System | ⬜ |
doc/api/fs.md | fsPromises.glob(pattern[, options]) |
File System | ⬜ |
doc/api/fs.md | fs.glob(pattern[, options], callback) |
File System | ⬜ |
doc/api/fs.md | fs.openAsBlob(path[, options]) |
File System | ⬜ |
doc/api/fs.md | fs.globSync(pattern[, options]) |
File System | ⬜ |
doc/api/fs.md | dirent.parentPath |
File System | ⬜ |
doc/api/globals.md | Class: ByteLengthQueuingStrategy |
⬜ | |
doc/api/globals.md | Class: CompressionStream |
⬜ | |
doc/api/globals.md | Class: CountQueuingStrategy |
⬜ | |
doc/api/globals.md | Crypto |
Crypto | ⬜ |
doc/api/globals.md | CryptoKey |
Crypto | ⬜ |
doc/api/globals.md | CustomEvent |
⬜ | |
doc/api/globals.md | Class: DecompressionStream |
⬜ | |
doc/api/globals.md | Navigator |
⬜ | |
doc/api/globals.md | Class: ReadableByteStreamController |
⬜ | |
doc/api/globals.md | Class: ReadableStream |
⬜ | |
doc/api/globals.md | Class: ReadableStreamBYOBReader |
⬜ | |
doc/api/globals.md | Class: ReadableStreamBYOBRequest |
⬜ | |
doc/api/globals.md | Class: ReadableStreamDefaultController |
⬜ | |
doc/api/globals.md | Class: ReadableStreamDefaultReader |
⬜ | |
doc/api/globals.md | SubtleCrypto |
⬜ | |
doc/api/globals.md | Class: TextDecoderStream |
⬜ | |
doc/api/globals.md | Class: TextEncoderStream |
⬜ | |
doc/api/globals.md | TransformStream | TransformStream | ⬜ |
doc/api/globals.md | TransformStreamDefaultController | TransformStreamDefaultController | ⬜ |
doc/api/globals.md | WebSocket | globals.md | ⬜ |
doc/api/globals.md | WritableStream | WritableStream | ⬜ |
doc/api/globals.md | WritableStreamDefaultController | WritableStreamDefaultController | ⬜ |
doc/api/globals.md | WritableStreamDefaultWriter | WritableStreamDefaultWriter | ⬜ |
doc/api/http.md | serverSymbol.asyncDispose | http.md | ⬜ |
doc/api/http2.md | serverSymbol.asyncDispose | http2.md | ⬜ |
doc/api/https.md | serverSymbol.asyncDispose | https.md | ⬜ |
doc/api/inspector.md | Promises API | inspector.md | ⬜ |
doc/api/module.md | module.register(specifier[, parentURL][, options]) | module.md | ⬜ |
doc/api/module.md | Customization Hooks | module.md | ⬜ |
doc/api/module.md | initialize() | module.md | ⬜ |
doc/api/module.md | resolve(specifier, context, nextResolve) | module.md | ⬜ |
doc/api/module.md | load(url, context, nextLoad) | module.md | ⬜ |
doc/api/module.md | Source map v3 support | module.md | ⬜ |
doc/api/n-api.md | node_api_nogc_env | n-api.md | ⬜ |
doc/api/n-api.md | node_api_nogc_finalize | n-api.md | ⬜ |
doc/api/n-api.md | node_api_create_external_string_latin1 | n-api.md | ⬜ |
doc/api/n-api.md | node_api_create_external_string_utf16 | n-api.md | ⬜ |
doc/api/n-api.md | node_api_create_property_key_utf16 | n-api.md | ⬜ |
doc/api/n-api.md | node_api_post_finalizer | n-api.md | ⬜ |
doc/api/net.md | serverSymbol.asyncDispose | net.md | ⬜ |
doc/api/packages.md | Determining package manager | packages.md | ⬜ |
doc/api/packages.md | "packageManager" | packages.md | ⬜ |
doc/api/process.md | process.constrainedMemory() | process.md | ⬜ |
doc/api/process.md | process.availableMemory() | process.md | ⬜ |
doc/api/process.md | process.getActiveResourcesInfo() | process.md | ⬜ |
doc/api/process.md | process.loadEnvFile(path) | process.md | ⬜ |
doc/api/process.md | process.setSourceMapsEnabled(val) | process.md | ⬜ |
doc/api/process.md | process.sourceMapsEnabled | process.md | ⬜ |
doc/api/readline.md | Promises API | readline.md | ⬜ |
doc/api/single-executable-applications.md | Single executable applications | single-executable-applications.md | ⬜ |
doc/api/stream.md | writable.writableAborted | stream.md | ⬜ |
doc/api/stream.md | readable.readableAborted | stream.md | ⬜ |
doc/api/stream.md | readable.readableDidRead | stream.md | ⬜ |
doc/api/stream.md | readableSymbol.asyncDispose | stream.md | ⬜ |
doc/api/stream.md | readable.compose(stream[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.iterator([options]) | stream.md | ⬜ |
doc/api/stream.md | readable.map(fn[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.filter(fn[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.forEach(fn[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.toArray([options]) | stream.md | ⬜ |
doc/api/stream.md | readable.some(fn[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.find(fn[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.every(fn[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.flatMap(fn[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.drop(limit[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.take(limit[, options]) | stream.md | ⬜ |
doc/api/stream.md | readable.reduce(fn[, initial[, options]]) | stream.md | ⬜ |
doc/api/stream.md | stream.compose(...streams) | stream.md | ⬜ |
doc/api/stream.md | stream.Readable.fromWeb(readableStream[, options]) | stream.md | ⬜ |
doc/api/stream.md | stream.Readable.isDisturbed(stream) | stream.md | ⬜ |
doc/api/stream.md | stream.isErrored(stream) | stream.md | ⬜ |
doc/api/stream.md | stream.isReadable(stream) | stream.md | ⬜ |
doc/api/stream.md | stream.Readable.toWeb(streamReadable[, options]) | stream.md | ⬜ |
doc/api/stream.md | stream.Writable.fromWeb(writableStream[, options]) | stream.md | ⬜ |
doc/api/stream.md | stream.Writable.toWeb(streamWritable) | stream.md | ⬜ |
doc/api/stream.md | stream.Duplex.fromWeb(pair[, options]) | stream.md | ⬜ |
doc/api/stream.md | stream.Duplex.toWeb(streamDuplex) | stream.md | ⬜ |
doc/api/test.md | Watch mode | test.md | ⬜ |
doc/api/test.md | Collecting code coverage | test.md | ⬜ |
doc/api/test.md | Snapshot testing | test.md | ⬜ |
doc/api/test.md | snapshot | test.md | ⬜ |
doc/api/test.md | snapshot.setDefaultSnapshotSerializers(serializers) | test.md | ⬜ |
doc/api/test.md | snapshot.setResolveSnapshotPath(fn) | test.md | ⬜ |
doc/api/test.md | MockModuleContext | test.md | ⬜ |
doc/api/test.md | mock.module(specifier[, options]) | test.md | ⬜ |
doc/api/test.md | MockTimers | test.md | ⬜ |
doc/api/test.md | context.assert.snapshot(value[, options]) | test.md | ⬜ |
doc/api/test.md | context.plan(count) | test.md | ⬜ |
doc/api/timers.md | immediateSymbol.dispose | timers.md | ⬜ |
doc/api/timers.md | timeoutSymbol.dispose | timers.md | ⬜ |
doc/api/timers.md | timersPromises.scheduler.wait(delay[, options]) | timers.md | ⬜ |
doc/api/timers.md | timersPromises.scheduler.yield() | timers.md | ⬜ |
doc/api/tracing.md | Trace events | tracing.md | ⬜ |
doc/api/url.md | URL.createObjectURL(blob) | url.md | ⬜ |
doc/api/url.md | URL.revokeObjectURL(id) | url.md | ⬜ |
doc/api/util.md | util.MIMEType | util.MIMEType | ⬜ |
doc/api/util.md | util.parseEnv(content) | util.md | ⬜ |
doc/api/util.md | util.styleText(format, text) | util.md | ⬜ |
doc/api/util.md | util.transferableAbortController() | util.md | ⬜ |
doc/api/util.md | util.transferableAbortSignal(signal) | util.md | ⬜ |
doc/api/util.md | util.aborted(signal, resource) | util.md | ⬜ |
doc/api/v8.md | v8.queryObjects(ctor[, options]) | v8.md | ⬜ |
doc/api/v8.md | v8.setHeapSnapshotNearHeapLimit(limit) | v8.md | ⬜ |
doc/api/v8.md | Startup Snapshot API | v8.md | ⬜ |
doc/api/vm.md | vm.Module | vm.Module | ⬜ |
doc/api/vm.md | vm.SourceTextModule | vm.SourceTextModule | ⬜ |
doc/api/vm.md | vm.SyntheticModule | vm.SyntheticModule | ⬜ |
doc/api/vm.md | vm.constants.USE_MAIN_CONTEXT_DEFAULT_LOADER | vm.md | ⬜ |
doc/api/vm.md | vm.measureMemory([options]) | vm.md | ⬜ |
doc/api/wasi.md | WebAssembly System Interface (WASI) | wasi.md | ⬜ |
doc/api/webcrypto.md | Ed25519/Ed448/X25519/X448 key pairs | webcrypto.md | ⬜ |
doc/api/worker_threads.md | port.hasRef() | worker_threads.md | ⬜ |
(Feel free to edit this table)