remix-run/remix · error · Error

Table "{tableName}" primaryKey must contain at least one col

Error message

Table "{tableName}" primaryKey must contain at least one column

What it means

An explicitly provided primaryKey option must list at least one column. This error is thrown when primaryKey is an empty array (or equivalent), which would leave the table with no primary key at all.

Source

Thrown at packages/data-table/src/lib/table.ts:1104

function normalizePrimaryKey(
  tableName: string,
  columns: TableColumnsDefinition,
  primaryKey?: string | readonly string[],
): string[] {
  if (primaryKey === undefined) {
    if (!Object.prototype.hasOwnProperty.call(columns, 'id')) {
      throw new Error(
        'Table "' + tableName + '" must include an "id" column or an explicit primaryKey',
      )
    }

    return ['id']
  }

  let keys = Array.isArray(primaryKey) ? [...primaryKey] : [primaryKey]

  if (keys.length === 0) {
    throw new Error('Table "' + tableName + '" primaryKey must contain at least one column')
  }

  for (let key of keys) {
    if (!Object.prototype.hasOwnProperty.call(columns, key)) {
      throw new Error('Table "' + tableName + '" primaryKey column "' + key + '" does not exist')
    }
  }

  return keys
}

function normalizeKeySelector<table extends AnyTable>(
  table: table,
  selector: KeySelector<table> | undefined,
  optionName: string,
  defaultValue: readonly string[],
): string[] {
  return normalizeKeysForTable(table, selector, optionName, defaultValue)

View on GitHub (pinned to 9696913134)

Solutions

  1. Provide at least one column name in the primaryKey array
  2. Guard dynamic key lists: fall back to ['id'] when the computed list is empty
  3. Check for accidental spreads like { ...defaults, primaryKey: [] }

Example fix

// before
createTable('t', cols, { primaryKey: computedKeys })
// after
createTable('t', cols, { primaryKey: computedKeys.length > 0 ? computedKeys : ['id'] })
Defensive patterns

Strategy: validation

Validate before calling

if (keys.length === 0) throw new Error('primaryKey must not be empty')

Prevention

When it happens

Trigger: Passing primaryKey: [] programmatically, e.g. when a list of key columns is computed from config or user input and comes back empty.

Common situations: Dynamic schema generation where the key list is derived from data that is empty in some environment; spread defaults that accidentally override a real key list.

Related errors


AI-assisted analysis of remix-run/remix@9696913134 (2026-08-27). Data as JSON: /api/errors/a420f380da62c377. Report an issue: GitHub.