Skip to content
Merged
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
18 changes: 18 additions & 0 deletions .changeset/26206-driver-memory-default.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
---
'@objectstack/driver-memory': patch
---

fix(driver-memory)!: retire the legacy `default` export, which a CommonJS `require()` could not reach as its types described

The package entry exported a legacy `{ id, version, onEnable }` object as its `default`. It is not a kernel plugin (the kernel contract is `init` / `start` / `destroy`), and the CommonJS build could only put it on `require('@objectstack/driver-memory').default`, while the published declarations said `export default` (`@arethetypeswrong/cli` reported `FalseExportDefault`). It leaves the published entry. Every named export stays. Nothing in this repository imported the default, and no example, scaffold template, doc page or skill names the package as a string entry of a stack's `plugins` array.

Clause-②: no (narrowing)
Metadata-protocol: none

<!-- adr-0087: not-required (runtime-export-retired @objectstack/driver-memory#default) One runtime object leaves a published package entry; no key of any metadata schema, no object definition and no stored shape is added, removed, renamed or re-shaped, so there is nothing for `objectstack migrate meta` to rewrite and no tombstone. A TypeScript consumer meets the break at its own import, and the line below names the door to use instead. -->

**BREAKING** (a runtime export is removed). It ships as `patch` because the metadata protocol does not move. There is no staged window.

- FROM `default` TO `new DriverPlugin(new InMemoryDriver(), 'memory')` from `@objectstack/runtime`, or `new InMemoryDriver()` handed to whatever registers your drivers.

A stack config that names `'@objectstack/driver-memory'` as a string entry of `plugins` loaded that object and registered an `InMemoryDriver` through it. After this change that entry loads the module without a default and registers no driver, so put `new DriverPlugin(new InMemoryDriver(), 'memory')` in the `plugins` array instead.
3 changes: 2 additions & 1 deletion packages/drivers/driver-memory/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -61,14 +61,15 @@ const driver = new InMemoryDriver({

| Export | Kind | Description |
|:---|:---|:---|
| `default` | legacy plugin object | Legacy `onEnable` shape — not a kernel `Plugin`; register through `DriverPlugin`. |
| `InMemoryDriver` | class | Driver instance for direct use. |
| `InMemoryStrategy` | class | Query execution strategy used by ObjectQL. |
| `FileSystemPersistenceAdapter` | class | Node-only persistence. |
| `LocalStoragePersistenceAdapter` | class | Browser-only persistence. |
| `MemoryAnalyticsService` | class | Adds analytics aggregations backed by memory store. |
| `InMemoryDriverConfig`, `PersistenceAdapterInterface`, `MemoryAnalyticsConfig` | types | Configuration shapes. |

The package has no default export. Register the driver with a named export, as in Quick Start above.

## Configuration

| Option | Type | Default | Notes |
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
// Copyright (c) 2026 ObjectStack. Licensed under the Apache-2.0 license.

/**
* The package entry carries no `default` export (ADR-0087
* `runtime-export-retired @objectstack/driver-memory#default`).
*
* The retired object was the legacy `{ id, version, onEnable }` shape, which is
* not a kernel `Plugin`, and the CJS build could only reach it as
* `require(...).default` while the published declarations said `export default`
* (attw `FalseExportDefault`). The named exports are the supported surface.
*
* Pinned both ways: the entry has no `default`, and the named door the
* changeset points readers to still constructs a working driver.
*/

import { describe, it, expect } from 'vitest';
import * as entry from './index.js';

describe('driver-memory entry: the legacy default export is retired', () => {
it('the published entry has no default export', () => {
expect('default' in entry).toBe(false);
});

it('the named exports stay, and InMemoryDriver still constructs a driver', () => {
for (const name of ['InMemoryDriver', 'InMemoryStrategy', 'MemoryAnalyticsService', 'FileSystemPersistenceAdapter', 'LocalStoragePersistenceAdapter']) {
expect(typeof (entry as Record<string, unknown>)[name]).toBe('function');
}
const driver = new entry.InMemoryDriver();
expect(driver.name).toBe('com.objectstack.driver.memory');
});
});
24 changes: 7 additions & 17 deletions packages/drivers/driver-memory/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -61,20 +61,10 @@ export type {
UniqueAwareSchema,
} from './memory-unique-constraint.js';

export default {
id: 'com.objectstack.driver.memory',
version: '1.0.0',

onEnable: async (context: any) => {
const { logger, config, drivers } = context;
logger.info('[Memory Driver] Initializing...');

if (drivers) {
const driver = new InMemoryDriver(config);
drivers.register(driver);
logger.info(`[Memory Driver] Registered driver: ${driver.name}`);
} else {
logger.warn('[Memory Driver] No driver registry found in context.');
}
}
};
// [ADR-0087 runtime-export-retired] This entry has NO default export, on
// purpose. The legacy `{ id, version, onEnable }` object it once carried was not
// a kernel `Plugin` (the contract is init/start/destroy), and the package's CJS
// build could only place it on `require(...).default`, which the published
// `.d.ts` misdescribed (attw `FalseExportDefault`). Register this driver through
// a named export: `new DriverPlugin(new InMemoryDriver(), 'memory')`
// (`@objectstack/runtime`), or construct `InMemoryDriver` directly.
Loading