Spun off from #2781 audit.
`TableDefinition.cfc::primaryKey()` uses `required string name` for the column-name argument:
```cfm
public any function primaryKey(
required string name,
string type = "integer",
...
)
```
Every sibling column helper in the same file (`bigInteger`, `binary`, `boolean`, `date`, `datetime`, `decimal`, `float`, `integer`, `string`, `text`, `uniqueidentifier`, `time`, `timestamp`, `char`) accepts `columnNames` (or singular `columnName` via `$combineArguments`). `primaryKey` is the lone outlier — users and AI tooling that learn the convention from one helper consistently mis-call `primaryKey` with `columnName=...` and get a "required argument missing" error.
Defense for keeping it
The primary key IS the row's identity, not a payload column. Calling it `name` is more semantic than calling it `columnName`. The argument has been `name` since the 2017 dbmigrate merge.
Defense for changing it
Predictability beats cleverness. Every other column-shaped helper in the file uses `columnNames`/`columnName`; one outlier costs more attention than the semantic distinction earns. Same fix as #2781 worked for `t.references()`: accept the conventional alias via `$combineArguments`, keep the legacy name working.
Suggested fix
```cfm
public any function primaryKey(
string name,
string columnName,
string columnNames,
...
) {
$combineArguments(args = arguments, combine = "name,columnName", required = false);
$combineArguments(args = arguments, combine = "name,columnNames", required = true);
// ...
}
```
Three-way alias: `name` (legacy), `columnName` (singular convention), `columnNames` (plural convention). All resolve to `arguments.name` internally so the existing body stays unchanged.
Confidence
Low-priority cleanup. Issue is purely cosmetic — `primaryKey` works fine, just doesn't match the surrounding pattern. No downstream bugs.
Good first issue for someone wanting to touch the migrator without a deep dive.
Spun off from #2781 audit.
`TableDefinition.cfc::primaryKey()` uses `required string name` for the column-name argument:
```cfm
public any function primaryKey(
required string name,
string type = "integer",
...
)
```
Every sibling column helper in the same file (`bigInteger`, `binary`, `boolean`, `date`, `datetime`, `decimal`, `float`, `integer`, `string`, `text`, `uniqueidentifier`, `time`, `timestamp`, `char`) accepts `columnNames` (or singular `columnName` via `$combineArguments`). `primaryKey` is the lone outlier — users and AI tooling that learn the convention from one helper consistently mis-call `primaryKey` with `columnName=...` and get a "required argument missing" error.
Defense for keeping it
The primary key IS the row's identity, not a payload column. Calling it `name` is more semantic than calling it `columnName`. The argument has been `name` since the 2017 dbmigrate merge.
Defense for changing it
Predictability beats cleverness. Every other column-shaped helper in the file uses `columnNames`/`columnName`; one outlier costs more attention than the semantic distinction earns. Same fix as #2781 worked for `t.references()`: accept the conventional alias via `$combineArguments`, keep the legacy name working.
Suggested fix
```cfm
public any function primaryKey(
string name,
string columnName,
string columnNames,
...
) {
$combineArguments(args = arguments, combine = "name,columnName", required = false);
$combineArguments(args = arguments, combine = "name,columnNames", required = true);
// ...
}
```
Three-way alias: `name` (legacy), `columnName` (singular convention), `columnNames` (plural convention). All resolve to `arguments.name` internally so the existing body stays unchanged.
Confidence
Low-priority cleanup. Issue is purely cosmetic — `primaryKey` works fine, just doesn't match the surrounding pattern. No downstream bugs.
Good first issue for someone wanting to touch the migrator without a deep dive.