我目前真的很困惑,因为我得到了 ERROR TypeError: "_this.device.addKeysToObj is not a function"
。但是我实现了这个函数,所以我不知道是什么问题或者为什么它不可调用。我已经尝试了 Firefox 和 chrome 的代码,都出现了同样的错误。
错误在 this.device.addKeysToObj(this.result.results[0]);
这是我的课:
export class Device {
id: number;
deviceID: string;
name: string;
location: string;
deviceType: string;
subType: string;
valueNamingMap: Object;
addKeysToObj(deviceValues: object): void {
for (let key of Object.keys(deviceValues).map((key) => { return key })) {
if (!this.valueNamingMap.hasOwnProperty(key)) {
this.valueNamingMap[key] = '';
}
}
console.log(this, deviceValues);
}
}
这就是电话:
export class BatterieSensorComponent implements OnInit {
@Input() device: Device;
public result: Page<Value> = new Page<Value>();
//[..]
ngOnInit() {
this.valueService.list('', this.device).subscribe(
res => {
console.log(this.device); // NEW edit 1
this.result = res;
if (this.result.count > 0)
{
this.device.addKeysToObj(this.result.results[0]);
}
}
)
}
}
编辑 1
记录 this.device
见上面代码中的注释:
{
deviceID: "000000001"
deviceType: "sensor"
id: 5
location: "-"
name: "Batteries"
subType: "sensor"
valueNamingMap:
Object { v0: "vehicle battery", v1: "Living area battery" }
<prototype>: Object { … }
}
编辑 2
部分 device.service 代码:
list(url?: string, deviceType?: string, subType?: string): Observable<Page<Device>> {
if(!url) url = `${this.url}/devices/`;
if(deviceType) url+= '?deviceType=' + deviceType;
if(subType) url+= '&subType=' + subType;
return this.httpClient.get<Page<Device>>(url, { headers: this.headers })
.pipe(
catchError(this.handleError('LIST devices', new Page<Device>()))
);
}
父组件中的调用:
ngOnInit() {
this.deviceService.list('', 'sensor', ).subscribe(
res => {
this.devices = res.results;
}
)
}
模板:
<div class="mdl-grid">
<div class="mdl-cell mdl-cell--6-col mdl-cell--6-col-tablet" *ngFor="let device of devices">
<app-batterie-sensor [device]="device"></app-batterie-sensor>
</div>
</div>
原文由 Max 发布,翻译遵循 CC BY-SA 4.0 许可协议
原始答案
这是 Typescript 的一个常见问题,你说
device
是Device
类型,但事实并非如此。它具有与Device
相同的所有属性,但由于它不是Device
它没有预期的方法。您需要确保为
Device
中的每个条目实例化Page
,可能在父组件的ngOnInit
中:我不知道
Page
的结构,但如果它是一个数组,请尝试以下操作。进一步说明
让我们尝试一个打字稿示例,因为这种行为与 Angular 没有任何关系。我们将使用
localStorage
来表示来自外部源的数据,但这与 HTTP 相同。效果很好,太棒了。 typescript 接口纯粹是一种编译时结构,与类不同,它在 JavaScript 中没有等价物——它只是开发人员的提示。但这也意味着,如果您为外部值创建一个接口,例如上面的
SimpleValue
并且 _弄错了_,那么编译器仍然会相信您知道您在说什么,它不能可能在编译时验证这一点。从外部源加载一个类怎么样?它有什么不同?如果我们采用上面的示例并将
SimpleValue
更改为一个类而不更改任何其他内容,那么它仍然可以工作。但是有区别。与接口不同,类被转译成它们的 JavaScript 等价物,换句话说,它们存在于编译点之后。在我们上面的示例中,这不会导致问题,所以让我们尝试一个确实会导致问题的示例。加载的值有我们期望的属性,但没有方法,呃哦!问题是在调用
new SimpleClass
时会创建方法。当我们创建valueToSave
我们确实实例化了这个类,但是我们把它变成了一个 JSON 字符串并发送到其他地方,而 JSON 没有方法的概念,所以信息丢失了。当我们在loadFromStorage
中加载数据时,我们 没有 调用new SimpleClass
,我们只是相信调用者知道存储的类型是什么。我们如何处理这个问题?让我们暂时回到 Angular 并考虑一个常见的用例:日期。 JSON 没有 Date 类型,JavaScript 有,那么我们如何从服务器检索日期并将其作为日期工作?这是我喜欢使用的模式。
也许有点冗长,但它是我用来处理来自扁平后端合约的丰富前端模型的最强大和最灵活的模式。