Skip to content

A foreign key's implicit index breaks dropping its column after introspection #7481

Description

@morozov
Q A
Version 4.4.x

Table fabricates an implicit index to back a foreign key and records its name in $implicitIndexNames. On a constructed table the index is implicit, so dropping the foreign key drops it too. A round-trip through the database breaks that in two steps:

  1. Create-and-introspect loses the index's implicitness. The database has no notion of an implicit index, so introspection brings it back as an explicit one.
  2. Dropping the foreign key does not automatically drop the no longer implicit index. Dropping its column then leaves an index over a column that doesn't exist, so the table is invalid.

Given child(id PK, parent_id) with a foreign key child_parent on parent_id referencing parent(id), where the invalid table is caught depends on how it's edited:

  • The mutable Table API has no build-time check, so the invalid table reaches the database on drop-and-create:

    $child = $schemaManager->introspectTableByUnquotedName('child');
    $child->removeForeignKey('child_parent');
    $child->dropColumn('parent_id');
    $schemaManager->dropTable('child');
    $schemaManager->createTable($child);
    // DriverException: SQLSTATE[HY000]: General error: 1 no such column: parent_id
  • The editor rejects it earlier, when create() builds the object:

    $child = $schemaManager->introspectTableByUnquotedName('child');
    $child->edit()
        ->dropColumnByUnquotedName('parent_id')
        ->dropForeignKeyConstraintByUnquotedName('child_parent')
        ->create();
    // ColumnDoesNotExist: There is no column with name "parent_id" on table child.

Metadata

Metadata

Assignees

No one assigned

    Type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions