使用 Express 时未加载 Javascript (Angular)

Posted

技术标签:

【中文标题】使用 Express 时未加载 Javascript (Angular)【英文标题】:Javascript (Angular) not loading when using Express 【发布时间】:2014-07-14 15:30:10 【问题描述】:

我正在尝试使用 node.js、express.js 和 Heroku(或 Modulus.io)将我的应用程序部署到公共域。

在开发环境中一切正常。但是当我尝试将它部署到 Heroku 或 Modulus 时,我遇到了很多关于 PORT 和 Express 的问题。现在我正在尝试部署到 Heroku。

该项目是基于 angular-seed 构建的,我对 package.json 以及服务器的启动方式进行了一些更改,以便它可以与 Heroku 一起使用。

现在,本地服务器 (localhost:5000) 加载了一个静态 html 页面(index.html 工作正常),但没有任何 CSS 或 javascript 加载到该页面。在 Heroku 上部署的应用也是如此。

这是我对 package.json 所做的更改(来自 angular-seed 中提供的更改):

...
"scripts": 
  "start": "node web.js",
  ...
"main": "web.js",
...

这是 web.js 的样子:

var express = require("express");
var logfmt = require("logfmt");
var app = express();

app.use(logfmt.requestLogger());

app.use(express.static(__dirname + '/app'));


app.get('/', function(req, res) 
  //res.send('Hello World!');
  res.sendfile('./app/index.html');
);

var port = Number(process.env.PORT || 5000);
app.listen(port, function() 
  console.log("Listening on " + port);
);

在 HTML 索引文件中,

<!doctype html>
<html lang="en" ng-app="myApp">
<head>
  <meta charset="utf-8">
  <title>Title</title>
  <link rel="stylesheet" href="css/app.css"/>
</head>

<body> 
... 
  <script src="../bower_components/angular/angular.js"></script>
  <script src="../bower_components/angular-route/angular-route.js"></script>
  <script src="../bower_components/angular-sanitize/angular-sanitize.js"></script>
  <script src="../bower_components/angular-animate/angular-animate.js"></script>
  <script src="js/app.js"></script>
  <script src="js/services.js"></script>
  <script src="js/controllers.js"></script>
  <script src="js/filters.js"></script>
  <script src="js/directives.js"></script>
</body>
</html>

我在命令提示符中使用“foreman start”启动服务器,它使用纯 HTML 加载本地服务器就可以了。我也尝试过使用:

app.configure(function() 
    app.use(express.static(__dirname + '/public')); 
    app.use(express.logger('dev')); 
    app.use(express.bodyParser());  
);

在 web.js 中,但是当我启动服务器时,我收到一条错误消息,指出“TypeError: undefined is not a function”指向“app.configure”的句点。

控制台中的错误提示:

GET http://localhost:5000/bower_components/angular/angular.js 404 (Not Found) localhost/:22
GET http://localhost:5000/bower_components/angular-route/angular-route.js 404 (Not Found) localhost/:23
GET http://localhost:5000/bower_components/angular-sanitize/angular-sanitize.js 404 (Not Found) localhost/:24
GET http://localhost:5000/bower_components/angular-animate/angular-animate.js 404 (Not Found) localhost/:25
Uncaught ReferenceError: angular is not defined 
... etc

我一直在尝试在 Google 上找到一个解决方案,但其中大多数是一年前的,似乎不再有效。任何帮助表示赞赏。谢谢!


跟进错误: 现在我无法将它推送到 Heroku。不过,在本地一切正常。 这是我尝试将其推送到 Heroku 时的终端输出:

Counting objects: 5, done.
Delta compression using up to 8 threads.
Compressing objects: 100% (3/3), done.
Writing objects: 100% (3/3), 285 bytes | 0 bytes/s, done.
Total 3 (delta 2), reused 0 (delta 0)
To ssh://git@github.com/[...]
   a655423..98d78e4  master -> master
user@ubuntu:~/directory$ git push heroku
warning: push.default is unset; its implicit value is changing in
Git 2.0 from 'matching' to 'simple'. To squelch this message
and maintain the current behavior after the default changes, use:

  git config --global push.default matching

To squelch this message and adopt the new behavior now, use:

  git config --global push.default simple

See 'git help config' and search for 'push.default' for further information.
(the 'simple' mode was introduced in Git 1.7.11. Use the similar mode
'current' instead of 'simple' if you sometimes use older versions of Git)

Fetching repository, done.
Counting objects: 5, done.
Delta compression using up to 8 threads.
Compressing objects: 100% (3/3), done.
Writing objects: 100% (3/3), 285 bytes | 0 bytes/s, done.
Total 3 (delta 2), reused 0 (delta 0)

-----> Node.js app detected

       PRO TIP: Specify a node version in package.json
       See https://devcenter.heroku.com/articles/nodejs-support

-----> Defaulting to latest stable node: 0.10.21
-----> Downloading and installing node
-----> Restoring node_modules directory from cache
-----> Pruning cached dependencies not specified in package.json
-----> Node version changed since last build; rebuilding dependencies

       > ws@0.4.31 install /tmp/build_f31706d9-b302-4cdd-ae3e-cce981c1bf51/node_modules/karma/node_modules/socket.io/node_modules/socket.io-client/node_modules/ws
       > (node-gyp rebuild 2> builderror.log) || (exit 0)

       make: Entering directory `/tmp/build_f31706d9-b302-4cdd-ae3e-cce981c1bf51/node_modules/karma/node_modules/socket.io/node_modules/socket.io-client/node_modules/ws/build'
         CXX(target) Release/obj.target/bufferutil/src/bufferutil.o
         SOLINK_MODULE(target) Release/obj.target/bufferutil.node
         SOLINK_MODULE(target) Release/obj.target/bufferutil.node: Finished
         COPY Release/bufferutil.node
         CXX(target) Release/obj.target/validation/src/validation.o
         SOLINK_MODULE(target) Release/obj.target/validation.node
         SOLINK_MODULE(target) Release/obj.target/validation.node: Finished
         COPY Release/validation.node
       make: Leaving directory `/tmp/build_f31706d9-b302-4cdd-ae3e-cce981c1bf51/node_modules/karma/node_modules/socket.io/node_modules/socket.io-client/node_modules/ws/build'

       > phantomjs@1.9.7-5 install /tmp/build_f31706d9-b302-4cdd-ae3e-cce981c1bf51/node_modules/karma-phantomjs-launcher/node_modules/phantomjs
       > node install.js

       Downloading http://cdn.bitbucket.org/ariya/phantomjs/downloads/phantomjs-1.9.7-linux-x86_64.tar.bz2
       Saving to /tmp/phantomjs/phantomjs-1.9.7-linux-x86_64.tar.bz2
       Receiving...
       Error requesting archive.
       Status: 403
       Request options: 
         "protocol": "http:",
         "slashes": true,
         "auth": null,
         "host": "cdn.bitbucket.org",
         "port": null,
         "hostname": "cdn.bitbucket.org",
         "hash": null,
         "search": null,
         "query": null,
         "pathname": "/ariya/phantomjs/downloads/phantomjs-1.9.7-linux-x86_64.tar.bz2",
         "path": "/ariya/phantomjs/downloads/phantomjs-1.9.7-linux-x86_64.tar.bz2",
         "href": "http://cdn.bitbucket.org/ariya/phantomjs/downloads/phantomjs-1.9.7-linux-x86_64.tar.bz2"
       
       Response headers: 
         "content-type": "text/html",
         "content-length": "14134",
         "connection": "keep-alive",
         "date": "Sat, 24 May 2014 00:28:20 GMT",
         "last-modified": "Sat, 24 May 2014 00:08:24 GMT",
         "etag": "\"999f4f548bfffe25245dc29e49c57e9c\"",
         "accept-ranges": "bytes",
         "server": "AmazonS3",
         "age": "49096",
         "x-cache": "Hit from cloudfront",
         "via": "1.1 7718496b82dfc64dff52dbb3d7f07f3b.cloudfront.net (CloudFront)",
         "x-amz-cf-id": "kA4IYvDWX-l2HNW8EzztjY9STY96Ns0vsZDWTUaloDmJTnwJakcDIg=="
       
       Make sure your network and proxy settings are correct.
       npm ERR! weird error 1
       npm ERR! not ok code 0

 !     Push rejected, failed to compile Node.js app

跟进错误 2: 好的,这解决了无法推送到 Heroku 的问题。所以现在我可以将更改推送到 Heroku,但是 AngularJS 和 CSS 仍然没有显示在 Heroku 域上。我检查了域上的控制台,上面写着:

GET http://myapp.herokuapp.com/bower_components/angular-sanitize/angular-sanitize.js 404 (Not Found) lit-inlet-8601.herokuapp.com/:24
GET http://myapp.herokuapp.com/bower_components/angular-animate/angular-animate.js 404 (Not Found) lit-inlet-8601.herokuapp.com/:25
Uncaught Error: [$injector:modulerr] Failed to instantiate module myApp due to:
Error: [$injector:modulerr] Failed to instantiate module ngAnimate due to:
Error: [$injector:nomod] Module 'ngAnimate' is not available! You either misspelled the modul...<omitted>...1) angular.js:78

这很奇怪,因为它在本地运行良好。在检查元素 Sources 选项卡上,它似乎缺少一些目录(即 angular-animate 和 angular-sanitize)。我尝试在终端中同时运行“heroku run bower install angular-sanitize”和“heroku run bower install angular-animate”,但它没有解决问题。

“foreman start”和“npm start”都在本地启动服务器,一切都按原样显示。

我的 index.html 文件位于 app_name/app/ 目录下,而 web.js 位于 app_name 目录下。我没有更改任何脚本来在 index.html 文件中加载 Angular,所以它看起来仍然如上所示。

位于 app_name/app/js 中的 app.js 文件应该正确列出了依赖项:

angular.module('myApp', [
  'ngAnimate',
  'ngSanitize',
  'ngRoute',
  'myApp.filters',
  'myApp.services',
  'myApp.directives',
  'myApp.controllers'
])...

我不确定是什么原因造成的。任何帮助表示赞赏。谢谢!

【问题讨论】:

app.configure() 在 Express 4 中被删除,除了express.static 之外的所有中间件(它们现在都是单独的模块)。你的目录结构是什么样的(项目和公共)? 【参考方案1】:

您是否考虑过将 bower_components 文件夹置于版本和控制之下,如果是,您是否检查过 .gitignore?我刚刚遇到了一个类似的问题,即在部署后未加载某些 Bower 安装的依赖项。原来我忽略了所有 dist/ 文件夹。

【讨论】:

您的 dist 文件夹绝对应该被忽略。而且你的 bower_components 文件夹几乎肯定也最好被忽略。这两个都是在构建时生成的,所以它们不应该从源代码管理中拉出来【参考方案2】:

你需要另一个静态目录路由:

app.use(express.static(__dirname + '/app'));
//add this so the browser can GET the bower files
app.use('/bower_components', express.static(__dirname + '/bower_components'));

为了在 heroku 上进行部署,您需要在您的 package.json 文件中设置一个 postinstall 脚本,以便 heroku 将为您运行 bower install

Here's a blog post describing that.

"scripts": 
    "postinstall": "./node_modules/bower/bin/bower install"

由于当前bower install没有运行,所以实际需要的angularjs文件不存在,导致浏览器控制台出现这些错误,导致ReferenceError about angular未定义。

GET http://localhost:5000/bower_components/angular/angular.js 404 (Not Found) localhost/:22
GET http://localhost:5000/bower_components/angular-route/angular-route.js 404 (Not Found) localhost/:23
GET http://localhost:5000/bower_components/angular-sanitize/angular-sanitize.js 404 (Not Found) localhost/:24
GET http://localhost:5000/bower_components/angular-animate/angular-animate.js 404 (Not Found) localhost/:25
Uncaught ReferenceError: angular is not defined

一步一步来。首先,确保文件在本地和 heroku 上都正确安装。然后确保它们正确加载到浏览器中。然后确保您的实际 javascript 代码对于您的应用程序是正确的。


下一个问题

Followup Error 2:好的,这解决了无法 推到 Heroku。所以现在我可以将更改推送到 Heroku,但是 AngularJS 并且 CSS 仍然没有显示在 Heroku 域上。我检查了 域上的控制台,上面写着:

GET http://myapp.herokuapp.com/bower_components/angular-sanitize/angular-sanitize.js 404 (Not Found) lit-inlet-8601.herokuapp.com/:24
GET http://myapp.herokuapp.com/bower_components/angular-animate/angular-animate.js 404 (Not Found) lit-inlet-8601.herokuapp.com/:25
Uncaught Error: [$injector:modulerr] Failed to instantiate module myApp due to:
Error: [$injector:modulerr] Failed to instantiate module ngAnimate due to:
Error: [$injector:nomod] Module 'ngAnimate' is not available! You either misspelled the modul...<omitted>...1) angular.js:78

因此,heroku 中缺少 angular-sanitize 和 angular-animate,这意味着 bower install 没有安装它们。验证您确实在 bower.json 文件中正确引用了它们。

【讨论】:

此行修复了本地页面上的 Javascript 和 CSS 加载。但现在我似乎无法将其推送到 Heroku。我测试了它有和没有和线,它肯定似乎来自那个添加。我编辑了原始问题以包含输出任何想法如何解决? 感谢您迄今为止的所有帮助。我越来越接近我的目标,但现在似乎还有另一个问题(他们只是永远不会停止)。我已经更新了原始问题以包含新错误。如果您能对此有所了解,我将不胜感激。谢谢! @PeterLyons 感谢一百万次......你救了我的命。

以上是关于使用 Express 时未加载 Javascript (Angular)的主要内容,如果未能解决你的问题,请参考以下文章

NodeJS Express req[user] 在多次刷新时未定义

最终确定令牌过期时未命中 http 拦截器

尝试使用 dlopen 加载库时未定义的符号

使用控件时未加载 UserControl 中的外部图像

使用 ajax 加载模板时未呈现脚本

打字稿。导入“模块/子目录”npm 包时未找到环境声明