{"record":{"id":"878890474ec56551","repo":"phalcon/cphalcon","slug":"foreign-key-columns-are-required","errorCode":null,"errorMessage":"Foreign key columns are required","messagePattern":"Foreign key columns are required","errorType":"exception","errorClass":"Phalcon\\Db\\Exceptions\\ForeignKeyColumnsRequired","httpStatus":null,"severity":"error","filePath":"phalcon/Db/Reference.zep","lineNumber":114,"sourceCode":"\n    /**\n     * Phalcon\\Db\\Reference constructor\n     */\n    public function __construct( string name,  array definition)\n    {\n        var columns, schema, referencedTable, referencedSchema,\n            referencedColumns, onDelete, onUpdate;\n\n        let this->name = name;\n\n        if unlikely !fetch referencedTable, definition[\"referencedTable\"] {\n            throw new ReferencedTableRequired();\n        }\n\n        let this->referencedTable = referencedTable;\n\n        if unlikely !fetch columns, definition[\"columns\"] {\n            throw new ForeignKeyColumnsRequired();\n        }\n\n        let this->columns = columns;\n\n        if unlikely !fetch referencedColumns, definition[\"referencedColumns\"] {\n            throw new ReferencedColumnsRequired();\n        }\n\n        let this->referencedColumns = referencedColumns;\n\n        if fetch schema, definition[\"schema\"] {\n            let this->schemaName = schema;\n        }\n\n        if fetch referencedSchema, definition[\"referencedSchema\"] {\n            let this->referencedSchema = referencedSchema;\n        }\n","sourceCodeStart":96,"sourceCodeEnd":132,"githubUrl":"https://github.com/phalcon/cphalcon/blob/b7419de9cd0a8a3f48441ead84c9f8415d463e25/phalcon/Db/Reference.zep#L96-L132","documentation":"The second required-key check in Phalcon\\Db\\Reference::__construct(): after 'referencedTable', the definition must contain 'columns' listing the local foreign-key columns. If it is missing, ForeignKeyColumnsRequired is thrown because the constraint has no local side to apply.","triggerScenarios":"new Reference('fk_posts_user', ['referencedTable' => 'users', 'referencedColumns' => ['id']]) without 'columns'; the local columns key dropped during refactoring or lost when definitions were copied from config.","commonSituations":"Migration definitions hand-written from memory (only the target side specified); generators that emit referencedTable/referencedColumns but skip local columns; key renamed to 'localColumns'.","solutions":["Add 'columns' => ['user_id'] naming the local column(s)","Validate all three required keys with one isset() guard before constructing","Check the migration/config source that produced the definition"],"exampleFix":"// before\nnew Reference('fk_posts_user', [\n    'referencedTable' => 'users',\n    'referencedColumns' => ['id'],\n]);\n\n// after\nnew Reference('fk_posts_user', [\n    'columns' => ['user_id'],\n    'referencedTable' => 'users',\n    'referencedColumns' => ['id'],\n]);","handlingStrategy":"validation","validationCode":"if (!isset($definition['referencedTable'], $definition['columns'], $definition['referencedColumns'])) {\n    throw new InvalidArgumentException(\n        'Reference definition requires referencedTable, columns and referencedColumns'\n    );\n}\n$reference = new \\Phalcon\\Db\\Reference('fk_posts_user', $definition);","typeGuard":"function isCompleteReferenceDefinition(array $definition): bool\n{\n    return isset($definition['referencedTable'], $definition['columns'], $definition['referencedColumns']);\n}","tryCatchPattern":"try {\n    $reference = new \\Phalcon\\Db\\Reference('fk_posts_user', $definition);\n} catch (\\Phalcon\\Db\\Exceptions\\ForeignKeyColumnsRequired $e) {\n    throw new InvalidArgumentException('Foreign key definition is missing local columns', 0, $e);\n}","preventionTips":["The local 'columns' key is as mandatory as the referenced side — always define both","Validate both column lists with one isset() guard before constructing","Test migration generators against all required Reference keys"],"tags":["phalcon-db","foreign-key","reference","schema-definition","migrations"],"backgroundTag":"missing-definition-key","analyzedSha":"b7419de9cd0a8a3f48441ead84c9f8415d463e25","analyzedAt":"2026-08-21T06:21:18.811Z","schemaVersion":2},"datasetVersion":"2026-08-21T11:28:35.574Z"}