reports icon indicating copy to clipboard operation
reports copied to clipboard

FB17585928: Bug with PersistentModel's Identifiable conformance

Open malhal opened this issue 7 months ago • 0 comments

Submission Date

2025-05-12

Status

Open

Area

SwiftData

Operating System Version

macOS 15.4.1

Type

Incorrect/Unexpected Behavior

Description

I'd like to report a bug in PersistentModel's implementation of id property for Identifiable conformance. I.e. our @Model classes.

The interface states PersistentModel conforms to Identifiable, e.g.

    public protocol PersistentModel : AnyObject, Observable, Hashable, Identifiable {

And the implementation of Identifiable is declared in this extension:

    extension PersistentModel {
             public var id: PersistentIdentifier { get }

However the documentation for Identifiable states that the id must be a stable identifier and PersistentIdentifier is not. E.g. when a new model instance is inserted it has a temporary PersistentIdentifier and after save it changes to one that represents the model in the database. This mistake results in many bugs, e.g. if .sheet(item:) is being used to display the newly inserted model, if there is an auto save (e.g. 15 secs after the insert) and the id changes then the sheet is dismissed and presented again. Also if the newly inserted model causes a @Query to update a List, then after the save the row view is needlessly recreated for the same object.

All of this can be fixed if the id is changed to the usual ObjectIdentifier that we use for classes, e.g.

    extension PersistentModel {
             public var id: ObjectIdentifier {
                 ObjectIdentifier(self)
             }
    }

I discovered this problem while working on this StackOverflow answer to someone who had the sheet problem.

Keywords

No response

Prerequisites

  • [x] The title follows the format FB<number>: <title>
  • [x] I will keep this issue updated with Apple's responses

malhal avatar May 12 '25 16:05 malhal