简体   繁体   English

这是@cached 用于自动跟踪 Ember Octane 的有效用法吗?

[英]Is this a valid usage of @cached for autotracking of Ember Octane?

Recently I encountered an use case of @cached from tracked-toolbox when writing a Glimmer component with autotracking.最近我在编写带有自动跟踪功能的 Glimmer 组件时遇到了一个来自tracked-toolbox@cached用例。 Here is an example code snippet:这是一个示例代码片段:

import Component from '@glimmer/component';

/**
 * Example usage
 * <PersonInfo
 *  @a={{this.objA}}
 *  @b={{this.stringB}}
 *  @c={{this.intC}}
 * />
 * Where objA can be a large object
 */

export default class PersonInfo extends Component {

  /**
   * I hope @cached here can help avoid re-running output getter in each
   * of the other getters, e.g. this.msg, this.link, this.name
   * But whenever any input args changes it triggers update 
   * (i.e. parent run this.objA = newObj)
   */
  get output() {
    return someExpensiveLogic(this.args.a, this.args.b, this.args.c);
  }

  get msg() {
    return translate(this.output.msg);
  }

  get link() {
    return convert(this.output.link);
  }

  get name() {
    return change(this.output.name);
  }
}
{{!-- In the template --}}
<div>
  {{this.name}}
  {{this.msg}}
  {{this.link}}
</div>

Without using @cached , the above code will execute the output getter 3 times when rendering, once for each of msg , link and name .在不使用@cached ,上面的代码在渲染时会执行 3 次output getter,分别对msglinkname

I also thought about building my own cache for output , but it requires me to manually keep track of which state is used and hash them, which could be expensive and hard to maintain.我还考虑过为output构建自己的缓存,但它需要我手动跟踪使用了哪个状态并对它们进行哈希处理,这可能很昂贵且难以维护。

From my understanding, what @cached provides is an access to the "global tag" in the auto tracking system, so I can rely on that tag to determine when the cache needs refresh.根据我的理解, @cached提供的是对自动跟踪系统中“全局标签”的访问,因此我可以依靠该标签来确定缓存何时需要刷新。

Since this is not supported in a company project I work on for now, I hope this usage it can encourage us to add such support later.由于我目前从事的公司项目不支持此功能,我希望这种用法可以鼓励我们以后添加此类支持。

Note: I found that @cached is convenient wrapper of注意:我发现@cached是方便的包装器

import { createCache, getValue } from '@glimmer/tracking/primitives/cache';

So fundamentally what I need is @glimmer/tracking/primitives/cache .所以基本上我需要的是@glimmer/tracking/primitives/cache

Posting a follow up here based on an offline discussion.根据离线讨论在此处发布跟进。

This is a valid usage of the @cached utility from tracked-toolbox .这是tracked-toolbox 中@cached实用程序的有效用法。 The narrow use case meets the below requirements:狭义用例满足以下要求:

  1. The output getter is expensive. output吸气剂很贵。
  2. The result of output is used multiple times in other getters in JS. output的结果在 JS 中的其他 getter 中多次使用。 (If this.output is only used directly in the template, it will already have exactly the same semantics around rerunning as it does with @cache .) (如果this.output仅直接在模板中使用,它在重新运行时已经具有与@cache完全相同的语义。)
  3. Compared to an explicit cache of the values used in the output getter, using @cache will not evaluate changes of the arguments' values, which means if this.args.b is set to the same value as before, the output getter will still rerun.output getter 中使用的的显式缓存相比,使用@cache不会评估参数值的更改,这意味着如果this.args.b设置为与以前相同的值, output getter 仍将重新运行. This is not a concern in this use case, because I know the parent will not set the same value in input args.在这个用例中这不是问题,因为我知道父级不会在输入参数中设置相同的值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM