Skip to content

Commit fd49aad

Browse files
committed
Replace Value_Node.get_value with a data-driven union approach
1 parent bd8383e commit fd49aad

File tree

3 files changed

+52
-23
lines changed

3 files changed

+52
-23
lines changed

packages/debugger/src/inspector/index.ts

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,8 @@ export function createInspector(props: {
3737
For the extension for inspecting values through `inspect()`
3838
*/
3939
function getValue(id: ValueItemID): unknown {
40-
return valueMap.get(id)?.get_value?.()
40+
let node = valueMap.get(id)
41+
return node ? inspector.value_data_get_value(node.data) : undefined
4142
}
4243
window[GLOBAL_GET_VALUE] = getValue
4344

@@ -56,11 +57,11 @@ export function createInspector(props: {
5657
// Value Nodes (signals, props, and owner value)
5758
for (const [id, toggleChange] of valueUpdates) {
5859
const node = valueMap.get(id)
59-
if (!node || !node.get_value) continue
60+
if (!node) continue
6061
// TODO shouldn't the previous stores be unsubscribed here? after update, they might no longer be here
6162
const selected = inspector.value_node_is_selected(node)
6263
const encoded = encodeValue(
63-
node.get_value(),
64+
inspector.value_data_get_value(node.data),
6465
selected,
6566
setup.eli,
6667
selected &&

packages/debugger/src/inspector/inspector.ts

Lines changed: 47 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -9,10 +9,21 @@ import {UNOWNED_ROOT} from '../main/roots.ts'
99
import {encodeValue} from './serialize.ts'
1010
import {type InspectorUpdateMap, PropGetterState} from './types.ts'
1111

12+
export enum Value_Kind {
13+
Observed_Getter,
14+
Value,
15+
Value_Obj,
16+
}
17+
18+
export type Value_Data =
19+
| {kind: Value_Kind.Observed_Getter; data: Observed_Prop_Data}
20+
| {kind: Value_Kind.Value; value: unknown}
21+
| {kind: Value_Kind.Value_Obj; obj: {value?: unknown}}
22+
1223
export type Value_Node = {
1324
tracked_stores: (() => void)[]
1425
selected: boolean
15-
get_value: (() => unknown) | undefined
26+
data: Value_Data
1627
}
1728

1829
export type Value_Node_Map = Map<ValueItemID, Value_Node>
@@ -31,7 +42,12 @@ export type Observed_Props = {
3142
props: Solid.Props
3243
on_prop_state_change?: On_Prop_State_Change | undefined
3344
on_value_update?: On_Value_Update | undefined
34-
observed_getters: Record<string, {v: unknown | typeof $NOT_SET; n: number}>
45+
observed_getters: Record<string, Observed_Prop_Data>
46+
}
47+
48+
export type Observed_Prop_Data = {
49+
v: unknown | typeof $NOT_SET
50+
n: number // number of listeners
3551
}
3652

3753
export type Inspector_Context<TEl extends object> = {
@@ -50,14 +66,30 @@ export type Collect_Details_Config<TEl extends object> = {
5066
const $INSPECTOR = Symbol('inspector')
5167
const $NOT_SET = Symbol('not-set')
5268

69+
export function value_data_get_value(data: Value_Data): unknown {
70+
switch (data.kind) {
71+
case Value_Kind.Observed_Getter: return data.data.v
72+
case Value_Kind.Value: return data.value
73+
case Value_Kind.Value_Obj: return data.obj.value
74+
}
75+
}
5376

54-
export function value_node_make(get_value: (() => unknown) | undefined): Value_Node {
77+
export function value_node_make(data: Value_Data): Value_Node {
5578
return {
5679
tracked_stores: [],
5780
selected: false,
58-
get_value: get_value,
81+
data: data,
5982
}
6083
}
84+
export function value_node_make_obj(obj: {value?: unknown}): Value_Node {
85+
return value_node_make({kind: Value_Kind.Value_Obj, obj})
86+
}
87+
export function value_node_make_value(value: unknown): Value_Node {
88+
return value_node_make({kind: Value_Kind.Value, value})
89+
}
90+
export function value_node_make_observed_getter(data: Observed_Prop_Data): Value_Node {
91+
return value_node_make({kind: Value_Kind.Observed_Getter, data})
92+
}
6193

6294
export function value_node_add_store_observer(node: Value_Node, unsub: () => void): void {
6395
node.tracked_stores.push(unsub)
@@ -91,7 +123,7 @@ export function observed_props_make(props: Solid.Props): Observed_Props {
91123
props: props,
92124
on_prop_state_change: undefined,
93125
on_value_update: undefined,
94-
observed_getters: {} as Record<string, {v: unknown | typeof $NOT_SET; n: number}>
126+
observed_getters: {} as Record<string, Observed_Prop_Data>
95127
}
96128
}
97129

@@ -100,16 +132,13 @@ export function observed_props_observe_prop(
100132
key: string,
101133
id: ValueItemID,
102134
get: () => unknown,
103-
): {get_value: () => unknown | typeof $NOT_SET; is_stale: boolean} {
135+
): {data: Observed_Prop_Data; is_stale: boolean} {
104136
if (observed.observed_getters[key]) {
105137
let o = observed.observed_getters[key]
106-
return {get_value: () => o.v, is_stale: o.n === 0}
138+
return {data: o, is_stale: o.n === 0}
107139
}
108140

109-
let o: (typeof observed.observed_getters)[string] = (observed.observed_getters[key] = {
110-
v: $NOT_SET,
111-
n: 0,
112-
})
141+
let o: Observed_Prop_Data = (observed.observed_getters[key] = {v: $NOT_SET, n: 0})
113142

114143
// monkey patch the getter to track when it is accessed and when it is no longer accessed.
115144
// and to track when the value changes.
@@ -128,7 +157,7 @@ export function observed_props_observe_prop(
128157
enumerable: true,
129158
})
130159

131-
return {get_value: () => o.v, is_stale: true}
160+
return {data: o, is_stale: true}
132161
}
133162

134163
function compare_proxy_prop_keys(
@@ -193,7 +222,7 @@ function map_source_value<TEl extends object>(
193222
return null
194223
}
195224

196-
ctx.value_map.set(`${ValueItemType.Signal}:${id}`, value_node_make(() => node_raw.value))
225+
ctx.value_map.set(`${ValueItemType.Signal}:${id}`, value_node_make_obj(node_raw))
197226

198227
if (node.kind === NodeType.Memo ||
199228
node.kind === NodeType.Signal
@@ -264,12 +293,11 @@ function map_props<TEl extends object>(
264293
let id: ValueItemID = `prop:${key}`
265294
// GETTER
266295
if (desc.get) {
267-
let {get_value, is_stale} = observed_props_observe_prop(observed, key, id, desc.get)
268-
ctx.value_map.set(id, value_node_make(get_value))
269-
let last_value = get_value()
296+
let {data, is_stale} = observed_props_observe_prop(observed, key, id, desc.get)
297+
ctx.value_map.set(id, value_node_make_observed_getter(data))
270298
record[key] = {
271299
getter: is_stale ? PropGetterState.Stale : PropGetterState.Live,
272-
value: last_value !== $NOT_SET ? encodeValue(get_value(), false, ctx.config.eli) : null,
300+
value: data.v !== $NOT_SET ? encodeValue(data.v, false, ctx.config.eli) : null,
273301
}
274302
}
275303
// VALUE
@@ -280,7 +308,7 @@ function map_props<TEl extends object>(
280308
}
281309
// non-object props cannot be inspected (won't ever change and aren't deep)
282310
if (Array.isArray(desc.value) || misc.is_plain_object(desc.value)) {
283-
ctx.value_map.set(id, value_node_make(() => desc.value))
311+
ctx.value_map.set(id, value_node_make_value(desc.value))
284312
}
285313
}
286314
}
@@ -389,7 +417,7 @@ export function collect_owner_details<TEl extends object>(
389417
}
390418
}
391419

392-
ctx.value_map.set(ValueItemType.Value, value_node_make(get_value))
420+
ctx.value_map.set(ValueItemType.Value, value_node_make_obj(owner))
393421

394422
return {
395423
details: details,

packages/debugger/src/inspector/store.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ setup.store.hooks.onStoreNodeUpdate = (node, property, value, prev) => {
4848
}
4949
}
5050

51-
export function observeStoreNode(rootNode: Solid.StoreNode): VoidFunction {
51+
export function observeStoreNode(rootNode: Solid.StoreNode): () => void {
5252
// might still pass in a proxy
5353
rootNode = setup.store.unwrap(rootNode)
5454
const symbol = Symbol('inspect-store')

0 commit comments

Comments
 (0)