fix: improve $inspect handling of derived objects (#10584)

* fix: improve $inspect handling of derived objects

* Update packages/svelte/src/internal/client/runtime.js

Co-authored-by: Simon H <5968653+dummdidumm@users.noreply.github.com>

---------

Co-authored-by: Simon H <5968653+dummdidumm@users.noreply.github.com>
pull/10592/head
Dominic Gannaway 4 months ago committed by GitHub
parent 29890bb616
commit 58008479fc
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -0,0 +1,5 @@
---
"svelte": patch
---
fix: improve $inspect handling of derived objects

@ -43,6 +43,7 @@ let is_micro_task_queued = false;
let is_flushing_effect = false;
// Used for $inspect
export let is_batching_effect = false;
let is_inspecting_signal = false;
// Handle effect queues
@ -130,8 +131,15 @@ export function batch_inspect(target, prop, receiver) {
return Reflect.apply(value, this, arguments);
} finally {
is_batching_effect = previously_batching_effect;
if (last_inspected_signal !== null) {
for (const fn of last_inspected_signal.inspect) fn();
if (last_inspected_signal !== null && !is_inspecting_signal) {
is_inspecting_signal = true;
try {
for (const fn of last_inspected_signal.inspect) {
fn();
}
} finally {
is_inspecting_signal = false;
}
last_inspected_signal = null;
}
}

@ -0,0 +1,54 @@
import { flushSync } from 'svelte';
import { test } from '../../test';
/**
* @type {any[]}
*/
let log;
/**
* @type {typeof console.log}}
*/
let original_log;
export default test({
compileOptions: {
dev: true
},
before_test() {
log = [];
original_log = console.log;
console.log = (...v) => {
log.push(...v);
};
},
after_test() {
console.log = original_log;
},
async test({ assert, target }) {
const button = target.querySelector('button');
flushSync(() => {
button?.click();
});
assert.htmlEqual(target.innerHTML, `<button>update</button>\n1`);
assert.deepEqual(log, [
'init',
{
data: {
derived: 0,
list: []
},
derived: []
},
'update',
{
data: {
derived: 0,
list: [1]
},
derived: [1]
}
]);
}
});

@ -0,0 +1,21 @@
<script context="module">
const data = $state({
list: [],
derived: 0
});
const derived = $derived(data.list.filter(() => true));
const state = {
data,
get derived() { return derived }
};
</script>
<script>
data.list.length = 0;
$inspect(state);
</script>
<button onclick={() => (state.data.list.push(1))}>update</button>
{state.data.list}
Loading…
Cancel
Save