Skip to content

deep: deleting a nested property does not notify (objProxyHandler lacks a deleteProperty trap) #102

Description

@nj-reve

In deep.ts, objProxyHandler implements get/has/ownKeys/set traps but no deleteProperty, so delete obj.nested.key on a deep-proxied object updates the target without notifying dependents — computeds/reactions tracking that key (or its parent's key collection via Object.keys/spread) stay stale until an unrelated tracked write. (Correction after further verification: this applies at every depth including the root — see the comment below; our initial 'root works' observation came from a wrapper of our own.)

Repro sketch:

const state = deepSignal({ nested: { a: 1, b: 2 } });
// effect/computed reading state.nested.a or Object.keys(state.nested)
delete state.nested.a; // no notification — stale reads
state.nested.b = 3;    // now the delete becomes visible too

We hit this in production code (a keyed override map inside a deep-signal draft: deleting a cleared key left a memoized computed stale). Fix that worked for us — a deleteProperty trap mirroring set's notification order:

deleteProperty(target, prop) {
  updateStorage(target, prop);
  dirtyCollection(target);
  return Reflect.deleteProperty(target, prop);
},

(With set's equals: () => false storage semantics, this also notifies on absent-key deletes, consistent with unchanged-value sets.) arrayProxyHandler may want the same treatment for completeness. Happy to send this as a PR if useful.

Tested against signal-utils 0.21.1.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions