mastra-ai/mastra · error · PlatformApiError

Neon provisioning failed${row.error ? ` — ${row.error}` : ''

Error message

Neon provisioning failed${row.error ? ` — ${row.error}` : ''}

What it means

waitForDatabaseReady polls getDatabaseStatus until the Neon database reaches a terminal state. If the API reports status 'failed', it throws this PlatformApiError (500), appending the server-supplied `row.error` detail when present, so the user sees why provisioning failed.

Source

Thrown at mastracode/mastra-factory/src/platform.ts:257

    signal?.throwIfAborted();
    // Bound each poll by whatever remains of the overall budget so a stuck
    // fetch can't exceed `timeoutMs`.
    const remaining = deadline - Date.now();
    if (remaining <= 0) throw timeoutError();
    const perRequestSignal = composeSignals(signal, AbortSignal.timeout(remaining));
    let row: AttachedDatabase;
    try {
      row = await getDatabaseStatus({ token, orgId, projectId, databaseId, signal: perRequestSignal });
    } catch (err) {
      // Reshape the per-request timeout as the same 504 the deadline branch
      // raises; other errors (network, 5xx) bubble up unchanged.
      if (err instanceof DOMException && err.name === 'TimeoutError') throw timeoutError();
      throw err;
    }
    lastStatus = row.status;
    if (row.status === 'ready') return row;
    if (row.status === 'failed') {
      throw new PlatformApiError(500, `Neon provisioning failed${row.error ? ` — ${row.error}` : ''}`);
    }
    if (Date.now() >= deadline) throw timeoutError();
    await new Promise(resolve => setTimeout(resolve, intervalMs));
  }
}

/**
 * Compose an outer AbortSignal with a per-request timeout signal. Uses
 * `AbortSignal.any` where available (Node ≥20.3); falls back to a manual
 * proxy for older runtimes.
 */
function composeSignals(outer: AbortSignal | undefined, inner: AbortSignal): AbortSignal {
  if (!outer) return inner;
  if (typeof AbortSignal.any === 'function') {
    return AbortSignal.any([outer, inner]);
  }
  const controller = new AbortController();
  const abort = (reason: unknown) => controller.abort(reason);

View on GitHub (pinned to 75dd419e61)

Solutions

  1. Read the detail after the em-dash — it is the upstream Neon error and indicates the fix.
  2. Retry create-factory: many failures (capacity, transient infra) succeed on a second run.
  3. Pick a different regionId if the error suggests regional capacity or unsupported-region issues.
  4. Check Neon org quotas/billing if the error indicates limits, then rerun; verify the name matches [a-zA-Z0-9_-] up to 64 chars.

Example fix

// before
await attachNeonDatabase({ token, orgId, projectId, name: 'production db!', regionId: 'aws-us-east-1' });
// after
await attachNeonDatabase({ token, orgId, projectId, name: 'production-db', regionId: 'aws-us-east-1' });
Defensive patterns

Strategy: try-catch

Validate before calling

if (!/^[a-zA-Z0-9_-]{1,64}$/.test(dbName)) throw new Error('DB name must match [a-zA-Z0-9_-]{1,64}');
if (!supportedNeonRegions.includes(regionId)) throw new Error(`Unsupported region: ${regionId}`);

Try / catch

try {
  const db = await waitForDatabaseReady(opts);
} catch (err) {
  if (err instanceof PlatformApiError && err.message.startsWith('Neon provisioning failed')) {
    console.error('Neon reported a provisioning failure. Detail:', err.message);
    console.error('Retry create-factory, try a different region, or check Neon org quotas/billing.');
    process.exit(1);
  }
  throw err;
}

Prevention

When it happens

Trigger: The platform reports `row.status === 'failed'` during the status polling loop — Neon itself failed to create/attach the database; `row.error` carries the upstream reason.

Common situations: Unsupported or out-of-capacity region; database name violating Neon charset/length rules; quota/billing limits reached on the Neon org; transient Neon infrastructure failure during initial provisioning.

Related errors


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