bug: DBML Ref delete/update actions ignored — all FKs emitted as ON DELETE NO ACTION #2
Reference in New Issue
Block a user
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Summary
When converting a multi-file DBML schema to PostgreSQL DDL, relspecgo ignores the
[delete: ...]and[update: ...]action modifiers onRef:declarations. Every generated foreign key constraint is emitted asON DELETE NO ACTION ON UPDATE NO ACTIONregardless of what is specified in the source DBML.Environment
relspec(relspecgo)dbmlpgsqlReproduction
Input — cross-file
Ref:declarations (bottom ofschema/files.dbml)Input — inline column
[ref: ...]with delete action (same-file,schema/core.dbml)Original migration had
ON DELETE CASCADEforthought_links.from_idandthought_links.to_id.Top-level
Ref:declarations with explicit delete actions (fromschema/skills.dbml):And from
schema/meta.dbml:Generated output (from
migrations/020_generated_schema.sql)Every single FK in the output is:
No FK in the entire 4400-line generated file has anything other than
NO ACTION, regardless of whether the Ref specifiescascade,set null, orrestrict.Expected Behaviour
The pgsql writer should honour the
[delete: ...]/[update: ...]action modifiers from DBMLRef:declarations and emit the appropriateON DELETE/ON UPDATEclauses:[delete: cascade]ON DELETE CASCADE[delete: set null]ON DELETE SET NULL[delete: restrict]ON DELETE RESTRICT[delete: no action]ON DELETE NO ACTION[update: cascade]ON UPDATE CASCADEActual Behaviour
All FKs are emitted as
ON DELETE NO ACTION ON UPDATE NO ACTIONunconditionally.Areas to Investigate
pkg/readers/dbml/) — is the[delete: ...]modifier being parsed and stored on theRelationstruct, or silently dropped?Relation/ForeignKeystruct have a field for delete/update actions? If not, it needs one.pkg/writers/pgsql/) — even if the action is parsed and stored, is the writer reading it and emitting the correctON DELETEclause, or always defaulting toNO ACTION?[ref: > ...]on a column vs a top-levelRef:block) both carry delete actions through to the writer, or only one of them.Workaround
None currently. The generated SQL must be manually edited after generation to add correct
ON DELETE/ON UPDATEclauses, which defeats the purpose of schema-as-code.Related
Summary: The DBML parser only recognized ondelete: / onupdate: prefixes, but the standard DBML spec uses delete: and update:. Fixed by adding delete: / update: as the primary recognized prefixes (while retaining ondelete: / onupdate:
for backward compatibility). Updated the test data (complex.dbml) to use standard DBML syntax so the existing tests now verify the correct behavior.