装饰器速查表
本库导出了以下装饰器,可直接从 @kaokei/use-vue-service 导入使用:
@kaokei/di透传装饰器:@Injectable、@Inject、@PostConstruct、@PreDestroy、@Self、@SkipSelf、@Optional、@LazyInject— 详细说明请参阅 @kaokei/di 装饰器文档- 本库专属装饰器:
@autobind、@Computed、@Raw、@RunInScope— 下方有完整说明
| 装饰器 | 无括号调用 | 有括号调用 | 依赖 @Injectable | 依赖 @Inject | 支持 decorate() |
|---|---|---|---|---|---|
@Computed(getter) | ✓ | ✓ | ✗ | ✗ | ✓ |
@Raw(field) | ✓ | ✓ | ✗ | ✗ | ✗ |
@Raw(accessor) | ✓ | ✓ | ✗ | ✗ | ✓ |
@Raw(class) | ✓ | ✓ | ✓ | ✗ | ✓ |
@RunInScope(method) | ✓ | ✓ | ✗ | ✗ | ✓ |
@autobind(method) | ✓ | ✗ | ✗ | ✗ | ✗ |
说明:
- 无括号调用:直接写
@Computed,装饰器本身作为装饰器使用。 - 有括号调用:写成
@Computed(),装饰器作为工厂函数调用后返回真正的装饰器。 @Raw(field)不可在decorate()中使用:field 形式内部使用了addInitializer,而decorate()不支持该机制。@Raw(class)依赖@Injectable:类形式通过context.metadata写入标记,元数据机制由@Injectable激活,因此必须配合使用。
@Computed
ts
// 用法一:不带括号
@Computed
public get doubleCount() { return this.count * 2; }
// 用法二:带括号
@Computed()
public get doubleCount() { return this.count * 2; }getter 装饰器,将 class 的 getter 属性转换为 Vue 的 computed 响应式计算属性。支持只读和可写(writable)两种形式。如果原型链上存在同名 setter,则自动创建 computed({ get, set })。
@Raw
field / accessor / 类装饰器,标记属性或整个类不参与 Vue 响应式追踪。装饰属性时,赋值时自动调用 markRaw;装饰整个类时,实例不会被 reactive() 包裹。
field 装饰器(不带括号)
ts
@Raw
public chartInstance = {};field 装饰器(带括号)
ts
@Raw()
public chartInstance = {};WARNING
field 形式内部使用了 addInitializer,不能在 decorate() 中使用。
accessor 装饰器(不带括号)
ts
@Raw
accessor chartInstance = {};accessor 装饰器(带括号)
ts
@Raw()
accessor chartInstance = {};类装饰器(不带括号)
ts
@Injectable()
@Raw
class RawService {
public data = {};
}类装饰器(带括号)
ts
@Injectable()
@Raw()
class RawService {
public data = {};
}WARNING
类形式通过 context.metadata 写入标记,元数据机制由 @Injectable 激活,因此必须配合 @Injectable() 使用。
@RunInScope
ts
// 用法一:不带括号
@RunInScope
public setup() { watchEffect(() => { /* ... */ }); }
// 用法二:带括号
@RunInScope()
public setup() { watchEffect(() => { /* ... */ }); }方法装饰器,将方法体包裹在一个新的 Vue EffectScope 中执行,并返回该 EffectScope。方法内的 watchEffect、watch、computed 等副作用统一由该 scope 管理。不会自动调用被装饰的方法,需要用户主动调用。
@autobind
ts
// 用法:不带括号
@autobind
public handleClick() { /* this 始终指向 reactive proxy */ }方法装饰器,将方法绑定到 reactive(this) 上,确保 this 始终指向 Vue 响应式 proxy 对象。适用于 setTimeout、Promise.then、事件回调等需要保持 this 绑定的场景。
关键特性:
- 内部使用
value.bind(reactive(this))绑定,利用 Vue 3reactive()幂等性,不会破坏 Vue 响应式追踪 - 兼容
@Raw装饰器:检测context.metadata[RAW_CLASS_KEY],在@Raw类中回退为普通bind(this)绑定 - 仅支持无括号调用(
@autobind),不支持工厂形式(@autobind()) - 不依赖
@Injectable或@Inject - 不支持
decorate()函数(内部使用addInitializer)
使用场景(详见 autobind 的必要性分析):
| 场景 | 是否需要 @autobind |
|---|---|
Vue SFC 模板 @click="service.method" | ❌ 不需要(编译器自动包裹箭头函数) |
JS 中解构方法 const { method } = service | ✅ 需要 |
回调传递 setTimeout(service.method, 0) | ✅ 需要 |
Promise.then(service.method) | ✅ 需要 |