Breaking changes in bold.
For versions v0.11.0 and up, see laminar.dev/blog
- New:
ConcurrentStreamStrategy
- New:
EventStream.periodic
andPeriodicEventStream
- New:
EventStream.fromJsPromise
andSignal.fromJsPromise
News:
- New video: Laminar – Smooth UI Development with Scala.js
- Also talks about observables and Airstream specifically
- You can now sponsor Airstream development on github!
- Naming:
fold
->foldLeft
,foldRecover
->foldLeftRecover
,FoldSignal
->FoldLeftSignal
- Naming:
composeChangesAndInitial
->composeAll
- New:
splitOne
andsplitOneIntoSignals
methods- Works just like
split
andsplitIntoSignals
but operates on observables ofA
, notM[A]
, so this way you can split observables of individual records rather than observables of (e.g.) lists of records.
- Works just like
- Fix: EventBus.emit signature overly restrictive
- Fix: throttle operator behaved more like debounce, it was not emitting until the parent stopped emitting for
intervalMillis
. It behaves as advertised now. (#34) - New:
Observer.combine(observer1, observer2, ...)
factory - New:
observer.contracollect { case Foo => bar }
operator - New:
EventBus.emit
andEventBus.emitTry
- Just convenience wrappers over
WriteBus
methods
- Just convenience wrappers over
- Build: Upgrade to scala-js-dom 1.0.0
- Does not affect Airstream itself, just be aware that it's not compatible with scala-js-dom v0.9.8
- API:
debugLog
operator now prints withprintln
instead ofdom.console.log
- New:
debugLogJs
operator that prints withdom.console.log
- New: Dynamic Ownership
- Flagship feature of this release. Dynamic ownership makes it easier to build complex Laminar-style ownership lifetimes with the ability to re-activate subscriptions after they were deactivated. If you're building a DOM manipulation library this will be very handy. See how Laminar v0.8 uses this feature for inspiration.
- This feature builds on top of regular Ownership so it's not a breaking change in itself, except for the incidental breaking changes listed below.
- API: Merge
Owned
intoSubscription
- Several API changes including new
cleanup
param instead of anonKilled
method (yay composition) – see howEventBusSource
uses it. Also moveSubscription
intoownership
package Subscription
constructor is now public- Migration: Replace usages of
Owned
withSubscription
and adapt to the slightly different API.
- Several API changes including new
- API: Eliminate
EventBusSource
, replace bySubscription
- API: Privatize EventBusStream constructor
- API: Trying to kill an already dead Subscription now throws an exception
- New:
OptionSplittable
– you can nowsplit
observables ofOption[A]
as if it's a list of zero-to-one items - New:
WriteBus.emit
andWriteBus.emitTry
methods to send events to multiple WriteBus-es in a single transaction (essentially,Var.set
but for streams) - New:
EventStream.empty
, a stream that never emits any events - Build: Note that this release is version
0.8.0
, not0.8
as I would have named it before
- Build: Scala 2.13 Support – thanks, @megri!
- API: Simplify
combineWith
type signature (return EventStream / Signal types instead of more specific subtypes)- Note: very small chance of breakage: this will affect you if you relied on the return type of these methods being unnecessarily specific (
CombineSignal2
/CombineEventStream2
). This is unlikely because these internal types don't offer you any functionality.
- Note: very small chance of breakage: this will affect you if you relied on the return type of these methods being unnecessarily specific (
- API: Move
mapTo
andmapToValue
methods fromEventStream
toObservable
- New:
WriteBus.contracomposeWriter
– thanks, @vic! - New: Add
startWith*
aliases fortoSignal*
methods onEventStream
- New:
unsafeRethrowErrorCallback
anddelayedRethrowErrorCallback
for error handling
- API:
fromValue
,fromSeq
, andfromTry
event streams now requireemitOnce
param - API:
toSignal
,toSignalWithTry
arguments are now passed by name- This means that these values will now be evaluated only if / when the resulting Signal is started for the first time.
- API: Move debugging operators from
Debug
object intoObservable
trait - API: Change param name of
delay
operator fromintervalMillis
toms
- New:
delaySync
operator to control the relative order of streams emission within the same transaction - New:
flatMap
(#20) – thanks, @yurique!- API: FlattenObservable type params changed, might break your custom implementations – see diff
- New:
SwitchSignalStrategy
to flatten signals of signals - New:
split
andsplitIntoSignals
operators- Powerful operators letting you split any observable into multiple streams or signals. Provide an easier way to efficiently render children nodes in Laminar.
- New:
composeChanges
andcomposeChangesAndInitial
operators forSignal
- New: Report failures of unhandled error callbacks
- Skipping this version to align versions with Laminar
- API: Make
Val
aStrictSignal
(it already behaved like one)
- API: Make
FutureSignal
aStrictSignal
(it already behaved like one)
- API: Eliminate the whole concept of State #13
State
andStateVar
are no more. RIP- Merge
MemoryObservable
intoSignal
- Merge
LazyObservable
intoObservable
- Remove
toLazy
method as all observables are now lazy - Migration guide
- Use
Signal
instead ofState
andMemoryObservable
. This is NOT a drop in replacement as State was not lazy. Make sure you have observers (internal or external) on all Signals that would be replacing State, or else they won't run. Consult the updated documentation for a reminder on Signal semantics. - For
Signal
alternatives toState
'snow()
/tryNow()
methods, see the Getting Signal's current value section in the new docs. - Use
Observable
instead ofLazyObservable
. - Use
Var
instead ofStateVar
. - Use
toSignal
instead oftoState
. - Remove invocations of
toLazy
method, they are not needed anymore.
- Use
- API: Make Var and its signal strict (not lazy)
- Var does not provide a WriteBus anymore, only an Observer
- Var now exposes
now
andtryNow
methods, as does its signal - See Var docs for details
- API: Make SignalViewer a Signal itself
- A StrictSignal, to be precise
- API: Remove flatMap method
- Use map(...).flatten
- I don't have time to sort out type inference and other stuff needed to get
flatMap
to work nicely.
- New: Update Vars using (currentValue => nextValue) functions
- New methods on Var instances:
set
,setTry
,update
,tryUpdate
- New methods on Var instances:
- New: Batch update Vars in a single transaction
- Companion object methods:
Var.set
,Var.setTry
,Var.update
,Var.tryUpdate
- See new Var docs for details
- Companion object methods:
- Fix: NPE from errors unhandled by
recover
partial function
- New: Error Handling – see whole new section in docs
- API: a few breaking changes for those who extend Airstream classes
- A bunch of class / trait member fields are now
Try[A]
instead ofA
- Split
fire
intofireValue
&fireError
, etc. - By and large this does not affect existing Airstream usage, just customization by subclassing
- A bunch of class / trait member fields are now
- API:
Observable.removeObserver
andTransaction.removeExternalObserver
are now private (#10) - Build: Drop Scala 2.11 support
- New:
SignalViewer
- This serves as a warning about my intention to deprecate and eventually remove the entirety of the
State
type in Airstream. Its strictness has not proved useful, and yet has plenty of drawbacks. See Laminar#37 for details. If you want to speak up against that, now is the time.
- This serves as a warning about my intention to deprecate and eventually remove the entirety of the
- New:
Ref
performance util (experimental)
- Naming: Observer.map -> Observer.contramap
- Naming: WriteBus.mapWriter -> WriteBus.contramapWriter
- API:
EventStream.mapTo
now acceptsvalue
by name; previous behaviour available usingmapToValue
method - API:
Observable.flatten
now needs aFlattenStrategy
except forSwitchEventStream
which is provided implicitly as a default - New: Integration with Futures.
EventStream.fromFuture
,Signal.fromFuture
,State.fromFuture
,SwitchFutureStrategy
,ConcurrentFutureStrategy
,OverwriteFutureStrategy
- New:
LazyObservable.flatMap
(available via implicits) - New:
LazyObservable.map
returns a more specific type
- API: Signal only fires if
nextValue != prevValue
- Naming: Var -> StateVar
- New: Make
Val.now()
public - New: signal.Var
- Fix: Ensure Signal's initialValue has been evaluated onStart
Initial release. First version extracted from Laminar repo.