Skip to main content

运行时警告

客户端警告

assignment_value_stale

对 `%property%` 属性 (%location%) 的赋值将计算右侧,而不是赋值后 `%property%` 的值。这可能导致意外行为。

考虑这样一个情况...

<script>
	let object = $state({ array: null });

	function add() {
		(object.array ??= []).push(object.array.length);
	}
</script>

<button onclick={add}>添加</button>
<p>项目: {JSON.stringify(object.items)}</p>

...当按钮第一次被点击时,正在推送到的数组是赋值右侧的 [],但 object.array 的最终值是一个空的状态代理。因此,被推送的值将被丢弃。

你可以通过将其分为两个语句来修复此问题:

function function add(): voidadd() {
	
let object: {
    array: number[];
}
object
.array: number[]array ??= [];
let object: {
    array: number[];
}
object
.array: number[]array.Array<number>.push(...items: number[]): number

Appends new elements to the end of an array, and returns the new length of the array.

@paramitems New elements to add to the array.
push
(
let object: {
    array: number[];
}
object
.array: number[]array.Array<number>.length: number

Gets or sets the length of the array. This is a number one higher than the highest index in the array.

length
);
}

binding_property_non_reactive

`%binding%` 绑定到非响应式属性
`%binding%` (%location%) 绑定到非响应式属性

console_log_state

你的 `console.%method%` 包含了 `$state` 代理。考虑使用 `$inspect(...)` 或 `$state.snapshot(...)` 代替

在记录一个 代理 时,浏览器开发工具将记录代理本身,而不是它所表示的值。在 Svelte 中,$state 代理的“目标”可能与其当前值不符,这可能会造成混淆。

记录一个值随着时间变化的最简单方法是使用 $inspect 符文。或者,为了临时记录某些事情(例如,在事件处理程序内部)你可以使用 $state.snapshot 来获取当前值的快照。

event_handler_invalid

%handler% 应该是一个函数。你是想 %suggestion% 吗?

hydration_attribute_changed

在服务器和客户端渲染之间,`%html%` 上的 `%attribute%` 属性更改了其值。客户端值 `%value%` 将被忽略,以服务器值为准

某些属性(如<img> 元素上的 src)在水合期间不会被修复,即服务器值将被保留。这是因为更新这些属性可能导致图像被重新获取(或者在 <iframe> 的情况下,框架被重新加载),即使它们解析到相同的资源。

要解决此问题,可以用 svelte-ignore 注释来静默此警告,或者确保在服务器和客户端之间值保持不变。如果你确实需要在水合时更改值,可以像这样强制更新:

<script>
	let { src } = $props();

	if (typeof window !== 'undefined') {
		// 储存该值...
		const initial = src;

		// 取消设置...
		src = undefined;

		$effect(() => {
			// ...在我们挂载之后重置
			src = initial;
		});
	}
</script>

<img {src} />

hydration_html_changed

`{@html ...}` 块在服务器和客户端渲染之间的值发生更改。客户端值将被忽略,以服务器值为准
`{@html ...}` 块 %location% 在服务器和客户端渲染之间的值发生更改。客户端值将被忽略,以服务器值为准

如果 {@html ...} 的值在服务器和客户端之间发生变化,它将在水合期间不会被修复,即服务器值将被保留。这是因为在水合期间的变更检测成本高昂且通常是不必要的。

要解决此问题,可以用 svelte-ignore 注释来静默此警告,或者确保在服务器和客户端之间值保持不变。如果你确实需要在水合时更改值,可以像这样强制更新:

<script>
	let { markup } = $props();

	if (typeof window !== 'undefined') {
		// 储存该值...
		const initial = markup;

		// 取消设置...
		markup = undefined;

		$effect(() => {
			// ...在我们挂载之后重置
			markup = initial;
		});
	}
</script>

{@html markup}

hydration_mismatch

水合失败,因为初始 UI 与服务器上渲染的内容不匹配
水合失败,因为初始 UI 与服务器上渲染的内容不匹配。错误发生在 %location% 附近

当 Svelte 在水合来自服务器的 HTML 时遇到错误时,会抛出此警告。在水合期间,Svelte 遍历 DOM,期望特定结构。如果该结构不同(例如,因为无效 HTML 导致 HTML 被 DOM 修复),那么 Svelte 将遇到问题,从而导致此警告。

在开发过程中,此错误通常会伴随一个 console.error,详细说明需要修复的 HTML。

invalid_raw_snippet_render

传递给 `createRawSnippet` 的 `render` 函数应该返回单个元素的 HTML

legacy_recursive_reactive_block

检测到在 `%filename%` 中迁移的 `$:` 响应式块,该块同时访问和更新同一响应式值。这可能会在转换为 `$effect` 时导致递归更新。

lifecycle_double_unmount

尝试卸载未挂载的组件

ownership_invalid_binding

%parent% 用 `bind:` 向 %child% 传递了一个值,但该值由 %owner% 所拥有。考虑在 %owner% 和 %parent% 之间创建一个绑定

考虑三个组件 GrandParentParentChild。如果你做 <GrandParent bind:value>,在 GrandParent 内通过 <Parent {value} /> (注意缺少 bind:)传递变量,然后在 Parent 内做 <Child bind:value>,就会抛出此警告。

要解决它,应该 bind: 该值,而不是仅仅传递一个属性(即在这个例子中做 <Parent bind:value />)。

ownership_invalid_mutation

在创建它的组件之外修改一个值是强烈不建议的。考虑使用 `bind:` 向子组件传递值,或使用回调
%component% 修改了由 %owner% 所拥有的值。这是强烈不建议的。考虑使用 `bind:` 向子组件传递值,或使用回调

考虑以下代码:

App
<script>
	import Child from './Child.svelte';
	let person = $state({ name: 'Florida', surname: 'Man' });
</script>

<Child {person} />
<script lang="ts">
	import Child from './Child.svelte';
	let person = $state({ name: 'Florida', surname: 'Man' });
</script>

<Child {person} />
Child
<script>
	let { person } = $props();
</script>

<input bind:value={person.name}>
<input bind:value={person.surname}>
<script lang="ts">
	let { person } = $props();
</script>

<input bind:value={person.name}>
<input bind:value={person.surname}>

Child 正在修改由 App 所拥有的 person,而没有被明确“允许”这样做。这是强烈不建议的,因为这可能会导致难以进行推理的代码(“谁修改了这个值?”),因此出现警告。

要解决此问题,可以创建回调属性来传达更改,或将 person 标记为 $bindable

state_proxy_equality_mismatch

响应式 `$state(...)` 代理和它们代理的值具有不同的身份。由于这个原因,与 `%operator%` 的比较将产生意想不到的结果

$state(...) 创建了一个 代理 对它所传递的值。代理和该值具有不同的身份,这意味着相等性检查将始终返回 false

<script>
	let value = { foo: 'bar' };
	let proxy = $state(value);

	value === proxy; // 始终为 false
</script>

为了解决此问题,请确保比较的值都是通过 $state(...) 创建的,或者都不是。请注意,$state.raw(...) 不会创建状态代理。

共享警告

dynamic_void_element_content

`<svelte:element this="%tag%">` 是一个空元素 —— 它不能有内容

<input> 这样的元素不能有内容,传递给这些元素的任何子元素将被忽略。

state_snapshot_uncloneable

值无法通过 `$state.snapshot` 克隆 —— 返回的是原始值
以下属性无法通过 `$state.snapshot` 克隆 —— 返回值包含原始值:

%properties%

$state.snapshot 试图克隆给定值,以返回一个不再变化的引用。某些对象可能不可克隆,在这种情况下,将返回原始值。在以下示例中,property 被克隆,但 window 不被克隆,因为 DOM 元素不可克隆:

const 
const object: {
    property: string;
    window: Window & typeof globalThis;
}
object
=
function $state<{
    property: string;
    window: Window & typeof globalThis;
}>(initial: {
    property: string;
    window: Window & typeof globalThis;
}): {
    property: string;
    window: Window & typeof globalThis;
} (+1 overload)
namespace $state

Declares reactive state.

Example:

let count = $state(0);

https://svelte.dev/docs/svelte/$state

@paraminitial The initial value
$state
({ property: stringproperty: 'this is cloneable', window: Window & typeof globalThiswindow });
const
const snapshot: {
    property: string;
    window: {
        [x: number]: {
 [x: number]: ...;
 readonly clientInformation: {
   readonly clipboard: {
       read: {};
       readText: {};
       write: {};
       writeText: {};
       addEventListener: {};
       dispatchEvent: {};
       removeEventListener: {};
   };
   ... 41 more ...;
   readonly storage: {
       ...;
   };
 };
 ... 207 more ...;
 readonly sessionStorage: {
   ...;
 };
        };
        ... 921 more ...;
        undefined: undefined;
    };
}
snapshot
=
namespace $state
function $state<T>(initial: T): T (+1 overload)

Declares reactive state.

Example:

let count = $state(0);

https://svelte.dev/docs/svelte/$state

@paraminitial The initial value
$state
.
function $state.snapshot<{
    property: string;
    window: Window & typeof globalThis;
}>(state: {
    property: string;
    window: Window & typeof globalThis;
}): {
    property: string;
    window: {
        ...;
    };
}

To take a static snapshot of a deeply reactive $state proxy, use $state.snapshot:

Example:

&#x3C;script>
  let counter = $state({ count: 0 });

  function onclick() {
	// Will log `{ count: ... }` rather than `Proxy { ... }`
	console.log($state.snapshot(counter));
  };
&#x3C;/script>

https://svelte.dev/docs/svelte/$state#$state.snapshot

@paramstate The value to snapshot
snapshot
(
const object: {
    property: string;
    window: Window & typeof globalThis;
}
object
);

在 GitHub 编辑此页面

上一页 下一页