0

从 Angular 2 升级到 Angular 4 后,尝试使用 AOT 进行编译时出现以下错误:

Property 'total' does not exist on type 'Observable<any>'.

这就是我到目前为止使用 observables 的方式......

首先,我分配了一个这样的变量:

public myData: Observable<any>;

然后我打电话给我订阅的服务,如下所示:

this.mySubscription = this.apiService.get('URL-HERE')
                        .subscribe(
                            response => this.myData = response,
                            error => this.feedbackService.displayError(<any>error),
                            () => this.feedbackService.stopLoading()
                        );

这适用于开发模式(ng serve),我可以使用诸如*ngFor迭代结果之类的东西。

收到这些错误后,我尝试添加这样的模型类:

export class MyData {
    total: number;
    count: number;
    data: Array<any> = [];
}
... rest of component here

然后将它与我的 observable 一起使用,如下所示:

public myData: Observable<MyData>;

但是我在尝试编译时仍然遇到错误:

Property 'total' does not exist on type 'Observable<MyData>'.

我究竟做错了什么?

更新

这是服务方法的样子:

return this.http
        .get(apiUrl + apiPath, {headers: headersWithToken})
        .timeoutWith(appSettings.maxTimeHttpCalls, Observable.defer(() => Observable.throw(this.feedbackService.timeout())))
        .map((response: Response) => {
            return response.json();
        })
        .catch((err: Response) => {
            return err.json();
        });

所有值(包括total)都存在于返回的 JSON 中,我可以在我的 HTML 中毫无问题地使用它。

4

3 回答 3

1

让我们在这里添加更多上下文,我认为您的错误实际上是在component.html文件中发生的,对吗?

所以基本上,你有这样的东西:

my-component.component.ts

@Component({
    selector: 'app-my-component',
    templateUrl: './my-component.component.html',
    styleUrls: ['./my-component.component.scss']
})
export class MyComponent implements OnInit {
    data$: Observable< MyType >;

    construct(private myService: MyService) {
        this.data$ = myService.getStuff();
    }
}

让我们假设您的服务my-service.service.ts如下所示:

@Injectable()
export class MyService {
    getStuff(): Observable< MyType > {
        this.http.get('www.example.com/data').map(res => res.json());
    }
}

最后,你有你的my-component.component.html目前它看起来像这样:

<div class="my-data">
    {{data$?.global?.statistics | async}}
</div>

编译时你会得到错误 Property 'global' does not exist on type 'Observable<MyType>'.

这是有充分理由的。我们需要记住,我们使用的对象可以包含可观察对象,但它们本身可能不是可观察对象。上面的 HTML 文件所说的是,data$并且global是对象的一部分,并且statisticsObservable. 所以结构看起来像这样:

data$: {
    global: {
        statistics: Observable< MyType >;
    }
}

但实际上你想要的是:

data$: Observable< MyType >;

所以要解决这个问题,你需要进入你的 HTML 并告诉它这data$Observable而不是其中的对象:

<div class="my-data">
    {{(data$ | async)?.global?.statistics}}
</div>

现在它知道data$对象是对象Observable,它后面的东西是返回对象的一部分,而不是Observable类。

于 2017-09-06T09:25:24.427 回答
1

原来 AOT 不喜欢 Angular 4 中的 elvis 运算符。

我保留了所有组件并包装了所有包含诸如支票内的Observable<any>东西的条目(并删除了?)并且错误消失了。{{myData?.total}}*ngIf

于 2017-03-29T06:12:34.517 回答
0

您所看到的编译器行为变化可能与 aot 的关系不大,而与更新的 typescript 的关系更大(如果您使用的任何东西早于我认为的 angular 2.4.9,那么您必须使用 typescript 2.0 或更低版本,角度 4 需要 2.1 或更高)。

鉴于升级到 typescript,您可能还需要重新访问您的 tsconfig 设置并确保它们仍在执行您想要的操作。

于 2017-03-29T16:08:21.183 回答