Angular2@Inputs是公开的,还是我们可以/应该通过将其设为私有来制定更严格的API



我正在使用带有Typescript的Angular2

假设我在应用程序组件的模板中有以下内容:

... 
<coffee-cup [coffee]=""
...

我的coffee-cup组件:

@Component({
  selector: 'coffee-cup',
  ...
})
export class CoffeeCup {
  @Input() 
  public coffee = 0;
}

我目前不确定我的输入应该是什么样子。它可能看起来像这样:

@Input()
public coffee = 0;

@Input()
private coffee = 0;

我目前倾向于将会员可变咖啡设为私人咖啡。

  • 我想为组件定义一个清晰的公共API
  • 我只想通过模板公开设置咖啡属性
  • 我目前没有任何理由允许直接从父组件读取或设置咖啡。如果需要,我可以删除私有修饰符

我查看组件的方式是有两个单独的API与之交互:

  1. 模板API,由@Inputs@Outputs组成
  2. 由所有公共属性和方法组成的Typescript API

我还没有检查在以下情况下会发生什么,然而,它可能会改变答案:

  • 假设咖啡会员是公众。如果我的appComponent使用@ViewChild访问CoffeeCup并设置咖啡成员,那么生命周期挂钩(如ngOnChange)会启动吗

重申这个问题:Angular2 @Input应该是公共的,还是我们可以/应该通过将其设为私有来制定更严格的API

首先,从API设计的角度来看,@Input意味着公共。从角度来看也是如此,这些装饰器描述了与组件交互的接口。

angular使用@Input装饰器或任何其他元装饰器,让angular了解您的意图,更好地理解模板及其与组件类的关系。

在某些情况下,变更检测引擎也会使用它。例如,@Input是一个由更改检测跟踪的字段,它向CD引擎提示应该监视此属性。

具有带有@Input装饰器的私有属性在运行时不应该有任何影响。这个修饰符是虚拟的,它在TypeScript到JavaScript编译之后就消失了。

然而,根据您的环境可能会产生一些影响:

一般来说,拥有TypeScript和元数据的一大好处是拥有一个智能IDE,这意味着IDE可以在编写代码时为您提供帮助。根据每个IDE的实现,拥有私有属性可能会也可能不会影响这一点。当您为某个组件编写HTML标记时,在属性上设置@Input将导致IDE在intellisense窗口上显示该属性。

另一个风险因素是将来支持typescript中的缩小/放大。顾名思义,私有属性在类内部使用,而不是在其他地方。这种特性意味着编译器可以更改私有属性的名称,使它们占用更少的字节,这也使它们"更私有",因为标识符可能会随着构建的不同而变化。例如:缩小后的private mySpecialProperty: string将是p1,编译器将更改类中对此标识符的所有引用以匹配p1。因此,今天这样做是可行的,但在未来它可能会限制构建功能。

需要考虑的另一点是,虽然angular不关心修改器,但编译器会关心,因此动态组件的创建将受到限制。换句话说,在html标记中创建组件不会有任何问题,但使用ComponentResolver -> ComponentFactor动态创建组件将受到限制,因为您无法使用代码将这些输入分配给组件的实例。如果你不打算这么做,那你很好。

如果您正在构建供其他人使用的组件,public修饰符对于@Input/@Output是必需的。你的组件的用户应该能够动态地创建你的组件。

这也回答了访问父/子组件上的这些属性以获得对咖啡组件的引用的问题。只能通过模板标记进行绑定。例如,您将无法手动注册到在咖啡组件上注册的EventEmitter。这有时是必需的,请将This场景作为一个示例。

至于生命周期挂钩,它不应该有任何影响,因为angular不检查类型,而是检查存在性。

所以,总而言之,在大多数用例中,你不应该有任何问题,但随着应用程序的进展,你可能会解决一些问题,或者不解决。你可能还必须在未来选择退出高级缩小功能。。。

相关内容

  • 没有找到相关文章

最新更新