Angular2:无法阅读财产'来电'未定义的(引导时)

时间:2017-01-09 14:14:15

标签: angular typescript service dependency-injection webpack

检查底部的更新!

我有一个服务在应用程序引导时抛出错误。 Cannot read property 'call' of undefined。我使用的是ng2 2.4.2和angular-cli 1.0.0-beta.24。

ERROR

  

未捕获的TypeError:无法读取属性' call'在webpack_require(bootstrap 81b10f8 ...:52)的webpack_require(environment.ts:8)处于webpack_require(bootstrap 81b10f8 ...:52)处于webpack_require(bootstrap 81b10f8 ...:52)处于Object.450(src async:7)处未定义at object.1057(util.service.ts:35)at webpack_require(bootstrap 81b10f8 ...:52)at webpackJsonpCallback(bootstrap 81b10f8 ...:23)at main.bundle.js:1

正如您所看到的那样,util服务存在问题 - 如下所示:

import { Injectable } from '@angular/core';
import { Router } from '@angular/router';
import { Project } from '../datatypes/';
import { Response } from '@angular/http';


@Injectable()
export class UtilService {
    constructor(private router: Router) {}

    public redirectToProject(project: Project) {
        let query = project.ProjectName.split(' ')
            .join('-')
            .concat('-' + project.Id)
            .toLowerCase();
        this.router.navigate(['/project', query]);
    }

    public extractData(res: Response) {
        let body = res.json();
        return body || {};
    }
}

奇怪:在使用chrome检查源文件时,它没有语法突出显示,这表明语法错误 - 在我看来,但是没有。

2017年1月20日更新

我更新到ng2.4.4和angular-cli 1.0.0-beta26。问题仍然存在。 在玩游戏时,Arjan发现它与beta 21一起使用。必须检查更改。现在问题不在上面的服务中,而是在environment.ts文件中(具有所有默认值)。

6 个答案:

答案 0 :(得分:14)

我认为在运行时更改模块导入会发生这种情况。

使用 ng serve再次运行应用程序,它为我解决了该问题。

当您在加载惰性模块或类似情况之前尝试在其他模块中使用延迟加载的模块的组件时,也会发生这种情况。

答案 1 :(得分:9)

对我来说,这是因为使用我们自己的客户端JavaScript来动态加载webpack生成的bundle。这很容易在我们自己的加载器脚本中修复。

使用webpack时,常规Angular 2 index.html不包含任何<style><script>元素,只包含<app-root></app-root>。运行ng serveng build时,文件会增强服务器端,以便在文件末尾添加以下内容:

<script type="text/javascript" src="inline.bundle.js"></script>
<script type="text/javascript" src="polyfills.bundle.js"></script>
<script type="text/javascript" src="styles.bundle.js"></script>
<script type="text/javascript" src="vendor.bundle.js"></script>
<script type="text/javascript" src="main.bundle.js"></script>

...或者,对于ng build --prod

<link href="styles.d41d8cd98f00b204e980.bundle.css" rel="stylesheet"/>
...
<script type="text/javascript" src="inline.66e3ead788094772ecc4.bundle.js"></script>
<script type="text/javascript" src="polyfills.477266e3ead78809ecc4.bundle.js"></script>
<script type="text/javascript" src="vendor.18c581546c015d1bfc6e.bundle.js"></script>
<script type="text/javascript" src="main.9a5c1002f220245829cd.bundle.js"></script>

生成的服务器端HTML文件将发送到浏览器。浏览器将按照遇到的顺序运行HTML中已存在的<script>个元素。

但是在运行时动态添加<script>元素客户端时会有所不同,默认情况下会异步执行。{请参阅&#34;解析器插入的脚本&#34;和#34;脚本插入的脚本&#34; on MDN's script页。

在我们的案例中,我们将Angular 2应用程序包含在CMS的页面中。为了避免在我们发布新版本时更改CMS页面(这将更改生成的包的名称中的哈希值),我们使用自己的JavaScript代码添加包。对于浏览器,这些是&#34;脚本插入的脚本&#34;。要确保以正确的顺序执行这些操作,只需将async设置为false(设置defer对我来说不起作用):

var script = document.createElement('script');
script.async = false;
script.src = ...

或者,在使用document.write时,请确保其中包含async="false"属性:

document.write(unescape('%3Cscript async="false" src="..." %3E%3C/script%3E'));

(有趣的是:请注意Chrome 55及更高版本might skip these blocking scripts on slow connections,如果它们托管在其他域中。)

如果没有这个,最常见的事情是angular-cli 1.0.0-beta.21,尽管我们确实看到了偶然的&#34;找不到变量:webpackJsonp&#34; < / em>的。对于更高版本,可能会显示不同的错误,具体取决于首先执行的脚本以及使用的浏览器。像:

Cannot read property 'call' of undefined
TypeError: modules[moduleId] is undefined
ReferenceError: Can't find variable: webpackJsonp
TypeError: undefined is not an object (evaluating modules[moduleId].call')
Unable to get property 'call' of undefined or null reference

另请注意,旧版本中未使用vendor.bundle.jspolyfills.bundle.js。并且可能需要将脚本插入到下面 <app-root>元素的位置。

答案 2 :(得分:1)

最后我找到了答案 - 与<script type="text/javascript" src="inline.bundle.js"></script> <script type="text/javascript" src="scripts.bundle.js"></script> <script type="text/javascript" src="styles.bundle.js"></script> <script type="text/javascript" src="vendor.bundle.js"></script> <script type="text/javascript" src="main.bundle.js"></script> 一起使用。我们必须使用这些文件:

beta.29

更新本地全局包也很重要。 全局更新在their github page上有详细描述。 本地更新也很简单 - 只需更新package.json中的依赖项。

重要提示:由于@angular/cli angular cli是包 angular-cli ,而不是 {{1}} ..

答案 3 :(得分:0)

我有类似的问题。我更新到@ angular-cli(1.0.0-rc.2)和@ angular / core(2.4.9)并遵循Sandrooco的解决方案。但是,还需要一个额外的文件polyfills.bundle.js。

public int countYZ(String str) {
    String[] words = str.split("\\W");
    int tally = 0;

    for (String w : words)
        tally += (w.endsWith("y") || w.endsWith("z")) ? 1 : 0;

    return tally;
}

我希望它有所帮助。

答案 4 :(得分:0)

在我的情况下,我需要确保我的脚本标签顺序正确。

  <script type="text/javascript" src="inline.bundle.js"></script>
  <script type="text/javascript" src="polyfills.bundle.js"></script>
  <script type="text/javascript" src="styles.bundle.js"></script>
  <script type="text/javascript" src="scripts.bundle.js"></script>
  <script type="text/javascript" src="vendor.bundle.js"></script>
  <script type="text/javascript" src="main.bundle.js"></script>

答案 5 :(得分:0)

由于某种原因更改端口对我来说ng serve --port 4300