Skip to content

Commit c01cd43

Browse files
committed
perf(core): avoid unnecessary calls to setState
1 parent ccf81ed commit c01cd43

File tree

1 file changed

+15
-14
lines changed

1 file changed

+15
-14
lines changed

packages/core/src/internal/useObservable.ts

Lines changed: 15 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { useEffect, useState } from "react"
1+
import { useEffect, useState, useRef } from "react"
22
import { SUSPENSE } from "../SUSPENSE"
33
import { EMPTY_VALUE } from "./empty-value"
44
import { Observable } from "rxjs"
@@ -8,31 +8,32 @@ export const useObservable = <O>(
88
getValue: () => O,
99
): Exclude<O, typeof SUSPENSE> => {
1010
const [state, setState] = useState(getValue)
11+
const prevStateRef = useRef<O | (() => O)>(state)
1112

1213
useEffect(() => {
13-
let prevVal: O | typeof SUSPENSE = EMPTY_VALUE
1414
let err: any = EMPTY_VALUE
15-
16-
const onNext = (value: O | typeof SUSPENSE) => {
17-
if (value === SUSPENSE) {
18-
setState(getValue)
19-
} else if (!Object.is(value, prevVal)) {
20-
setState(value)
21-
}
22-
prevVal = value
23-
}
15+
let syncVal: O | typeof SUSPENSE = EMPTY_VALUE
2416
const onError = (error: any) => {
2517
err = error
2618
setState(() => {
2719
throw error
2820
})
2921
}
3022

31-
let subscription = source$.subscribe(onNext, onError)
23+
let subscription = source$.subscribe((val) => (syncVal = val), onError)
3224
if (err !== EMPTY_VALUE) return
33-
if (prevVal === EMPTY_VALUE) onNext(SUSPENSE)
25+
26+
const set = (val: O | (() => O)) => {
27+
if (!Object.is(val, prevStateRef.current)) {
28+
setState((prevStateRef.current = val))
29+
}
30+
}
31+
32+
if (syncVal === EMPTY_VALUE) set(getValue)
3433
const t = subscription
35-
subscription = source$.subscribe(onNext, onError)
34+
subscription = source$.subscribe((value: O | typeof SUSPENSE) => {
35+
set(value === SUSPENSE ? getValue : value)
36+
}, onError)
3637
t.unsubscribe()
3738

3839
return () => subscription.unsubscribe()

0 commit comments

Comments
 (0)