Guide
响应式系统
TSone 的响应式系统允许您创建响应式状态,并在状态变化时自动更新 UI。
核心概念
响应式对象
响应式对象由 reactive 创建,会在属性访问和修改时自动追踪依赖。
副作用函数
副作用函数通过 effect 创建,会在依赖变化时重新执行。
依赖追踪
框架会在 effect 运行期间记录访问过的响应式属性。
核心 API
reactive
import { reactive } from '@geektech/tsone';
const state = reactive({
count: 0,
user: { name: 'John', age: 30 },
});
console.log(state.count);
state.count = 1;effect
import { effect, reactive } from '@geektech/tsone';
const state = reactive({ count: 0 });
effect(() => {
console.log(`Count: ${state.count}`);
});
state.count = 1;
state.count = 2;computed
import { computed, reactive } from '@geektech/tsone';
const state = reactive({ count: 0 });
const doubleCount = computed(() => state.count * 2);
console.log(doubleCount.value);
state.count = 1;
console.log(doubleCount.value);readonly
import { reactive, readonly } from '@geektech/tsone';
const original = reactive({ count: 0 });
const readOnlyState = readonly(original);
console.log(readOnlyState.count);
original.count = 1;ref
import { effect, ref } from '@geektech/tsone';
const count = ref(0);
effect(() => {
console.log(`Count: ${count.value}`);
});
count.value += 1;响应式原理
TSone 基于 JavaScript Proxy 拦截 get/set 来完成依赖收集和派发更新。
依赖追踪过程
- 执行 effect,并将其标记为当前活动副作用
- 在 effect 内部读取 reactive 或 ref 的值
- 记录依赖关系
- 当值变化时重新调度对应 effect
高级用法
嵌套响应式对象
const state = reactive({
user: { name: 'John', address: { city: 'New York' } },
});
effect(() => {
console.log(`${state.user.name} lives in ${state.user.address.city}`);
});
state.user.address.city = 'Los Angeles';数组响应式
const state = reactive({ items: ['Item 1', 'Item 2'] });
effect(() => {
console.log(state.items.join(', '));
});
state.items.push('Item 3');
state.items[0] = 'Updated Item 1';条件依赖
const state = reactive({ showCount: true, count: 0, message: 'Hello' });
effect(() => {
if (state.showCount) {
console.log(`Count: ${state.count}`);
} else {
console.log(state.message);
}
});清除副作用
import { effect, reactive, stop } from '@geektech/tsone';
const state = reactive({ count: 0 });
const runner = effect(() => {
console.log(`Count: ${state.count}`);
});
stop(runner);watch 侦听器
watch(source, callback, options) 侦听响应式源(getter 或 ref)的变化并执行回调,返回停止侦听的函数。回调收到新值、旧值和一个注册清理函数的 onCleanup 参数;默认随调度器批处理,同一批变化只回调一次。
import { reactive, ref, watch } from '@geektech/tsone';
const count = ref(0);
const stop = watch(count, (value, oldValue) => {
console.log(`count: ${oldValue} -> ${value}`);
});
const state = reactive({ profile: { name: 'John' } });
watch(() => state.profile.name, (name) => {
console.log('name changed to', name);
}, { deep: true });
stop();immediate: 建立后立即执行一次回调(此时 oldValue 为 undefined)deep: 深度追踪 getter 返回值嵌套属性的变化sync: 变化发生时同步回调(默认随调度器批处理)
最佳实践
状态设计
- 只把需要驱动 UI 的数据放进响应式对象
- 根据业务模块组织状态,避免无意义的深层嵌套
- 对复杂派生值优先使用 computed
性能优化
- 为昂贵计算使用 computed 缓存
- 避免在 effect 中执行重计算或副作用链式写入
- 对不应该被写入的数据使用 readonly
常见陷阱
- 不要直接替换整个 reactive 对象
- 不要在 effect 内部无条件修改依赖状态
- 嵌套对象会自动响应化,无需手动再次 reactive
与组件系统集成
class CounterComponent extends Component<object, { count: number }> {
protected initState() {
return { count: 0 };
}
protected initStyles(): void {}
protected render(): VNode {
return {
tag: 'button',
children: ['Count: '],
listeners: { click: () => this.state.count++ },
};
}
}总结
通过 reactive、effect、computed、readonly、ref 和 stop,TSone 为组件状态和独立数据模型提供了统一的响应式基础。