Module: Hibiki::Observer

Included in:
Derived, Effect
Defined in:
lib/hibiki/tracking.rb

Overview

---- shared observer behaviour ---------------------------------------------- The reverse edges of Trackable: what an observer read on its last run, and the value each one had when it read it.

Instance Method Summary collapse

Instance Method Details

#add_source(source, seen) ⇒ Object



107
# File 'lib/hibiki/tracking.rb', line 107

def add_source(source, seen) = sources[source] = seen

#clear_sourcesObject

Solid clears deps before rerun (cleanNode); we mirror that, so stale branches of dynamic deps (flag ? a : b) stop invalidating us.



111
112
113
114
# File 'lib/hibiki/tracking.rb', line 111

def clear_sources
  sources.each_key { |source| source.unsubscribe(self) }
  sources.clear
end

#sourcesObject

source => the value we saw for it. A Hash rather than a Set because the remembered value is what makes the equality gate possible; last read in a run wins, which is the value the run actually acted on.



106
# File 'lib/hibiki/tracking.rb', line 106

def sources = (@sources ||= {})

#sources_changed?Boolean

The equality gate, asked at flush time (see Effect#invalidate): did any value we read actually change? Svelte's $derived compares; we compare on the observer's side instead of the producer's, because Derived#invalidate has already notified downstream by the time it knows its new value. The comparison itself is delegated to each source (changed_from?), so a per-signal equals: is honored here too.

changed_from?'s peek resolves a dirty source without subscribing us to it — no untrack needed, since a Derived#recompute makes itself the observer. any? short-circuits in the useful direction: sources are in read order, so a changed first source spares the rest a validation recompute, and the run recomputes them only if it reads them this time.

Returns:

  • (Boolean)


128
129
130
# File 'lib/hibiki/tracking.rb', line 128

def sources_changed?
  sources.any? { |source, seen| source.changed_from?(seen) }
end