mastra-ai/mastra · error · Error

${name}: id must be provided and cannot be empty.

Error message

${name}: id must be provided and cannot be empty.

What it means

MastraCompositeStore requires a non-empty string `id` in its config. The constructor validates it immediately and throws if it is missing, not a string, or whitespace-only. This guarantees every composite store has a stable identifier.

Source

Thrown at packages/core/src/storage/base.ts:375

   * `prune()`. Undefined means nothing is pruned (keep forever).
   */
  protected retention?: RetentionConfig;

  /**
   * Retained references to the parent stores supplied via composition. `init()`
   * delegates to these so the parent's own `init()` logic (pragmas, ordered
   * DDL, init coalescing, etc.) runs instead of being bypassed by the
   * composite iterating the inner domains in parallel — which was the cause
   * of the SQLITE_BUSY / "no such table" races reported in issue #16782.
   */
  protected parentDefault?: MastraCompositeStore;
  protected parentEditor?: MastraCompositeStore;

  constructor(config: MastraCompositeStoreConfig) {
    const name = config.name ?? 'MastraCompositeStore';

    if (!config.id || typeof config.id !== 'string' || config.id.trim() === '') {
      throw new Error(`${name}: id must be provided and cannot be empty.`);
    }

    super({
      component: 'STORAGE',
      name,
    });

    this.id = config.id;
    this.disableInit = config.disableInit ?? false;
    this.retention = config.retention;

    // If composition config is provided (default, editor, or domains), compose the stores
    if (config.default || config.editor || config.domains) {
      const defaultStores = config.default?.stores;
      const editorStores = config.editor?.stores;
      const domainOverrides = config.domains ?? {};

      // Retain the parent store refs so init() can delegate to their own

View on GitHub (pinned to 75dd419e61)

Solutions

  1. Pass a non-empty string `id` in the MastraCompositeStore config
  2. If the ID comes from user input or env, trim it and check truthiness before constructing
  3. Check for property-name typos (e.g. `Id`, `key`) so the real `id` field isn't left undefined

Example fix

// before
new MastraCompositeStore({ name: 'MyStore' });
// after
new MastraCompositeStore({ name: 'MyStore', id: 'my-store' });
Defensive patterns

Strategy: validation

Validate before calling

function assertValidStoreId(id: unknown): asserts id is string {
  if (typeof id !== 'string' || id.trim() === '') {
    throw new Error('MastraCompositeStore id must be a non-empty string');
  }
}
assertValidStoreId(config.id);

Type guard

function hasStoreId(config: { id?: unknown }): config is { id: string } {
  return typeof config.id === 'string' && config.id.trim() !== '';
}

Try / catch

try {
  const store = new MastraCompositeStore(config);
} catch (e) {
  if (e instanceof Error && e.message.includes('id must be provided')) {
    throw new Error(`Invalid store config: ${config.name ?? 'unnamed'} is missing a non-empty id`);
  }
  throw e;
}

Prevention

When it happens

Trigger: Calling `new MastraCompositeStore({ name })` or any subclass constructor without `config.id`, passing `id: ''`, a non-string (number, undefined), or a string of only whitespace like `' '`.

Common situations: Migrating from older store configs where `id` was optional; building the config object dynamically and leaving `id` unset; trimming user-supplied IDs that turn out to be empty; typos like `Id` vs `id`.

Related errors


AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30). Data as JSON: /api/errors/bceb6377cd8d8b11. Report an issue: GitHub.