FIX Insert order bug when using TPC - Issue #35978 #38070
Open
andrewraper-Sage wants to merge 2 commits intodotnet:mainfrom
Open
FIX Insert order bug when using TPC - Issue #35978 #38070andrewraper-Sage wants to merge 2 commits intodotnet:mainfrom
andrewraper-Sage wants to merge 2 commits intodotnet:mainfrom
Conversation
Author
@dotnet-policy-service agree company="Sage" |
There was a problem hiding this comment.
Pull request overview
Fixes incorrect SaveChanges command ordering for TPC inheritance when a foreign key’s principal is an abstract TPC type mapped to no table (preventing FK constraint violations by ensuring principals are ordered before dependents on INSERT, and dependents before principals on DELETE).
Changes:
- Update
CommandBatchPreparer.AddForeignKeyEdges()to include the model-level FK dependency path when no mapped table-level FK constraints exist. - Remove
elsegating so model-level FK dependency detection runs alongside the table-level constraint path (withCanCreateDependencypreventing duplicates). - Add regression tests covering INSERT and DELETE ordering for the abstract-TPC-principal scenario.
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated no comments.
| File | Description |
|---|---|
| src/EFCore.Relational/Update/Internal/CommandBatchPreparer.cs | Ensures dependency edges are created via model-level FK logic when table-level constraints are missing, fixing ordering for abstract TPC principals. |
| test/EFCore.Relational.Tests/Update/CommandBatchPreparerTest.cs | Adds regression tests validating correct batching/sort order for Added and Deleted entities under abstract-principal TPC FKs. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
When using TPC inheritance with abstract base types, SaveChanges produces an incorrect INSERT order - child entities are inserted before their parents, causing FK constraint violations.
This happens because CommandBatchPreparer.AddForeignKeyEdges() fails to create dependency edges for FKs whose principal is an abstract TPC type mapped to no table. Since no IForeignKeyConstraint is created for such FKs, the table-level constraint path finds nothing.
The model-level FK fallback path should handle this, but for INSERT ordering it was skipped by a guard that assumed table-level constraints would cover it, and for DELETE ordering it was gated behind command.Table == null (unreachable for concrete TPC entities which always have a table).
The fix ensures the model-level FK path participates in dependency edge creation when no mapped table-level constraint exists: an additional foreignKey.GetMappedConstraints().Any() check on the INSERT principal registration guard, and removing the else gates on both DELETE paths so they always run alongside the table-level path (CanCreateDependency already prevents double-counting for FKs that do have mapped constraints).
Fixes #35978