2

LoopBack我已经Angular4使用angular-cli. 我的 LoopBack 项目在端口提供 html 文件,3000而我的 Angular4 项目在4200.

现在我需要知道我是否可以在 3000 上提供这个 Angular 应用程序,就像从 LoopBack 目录提供静态文件一样?

我想问的是是否可以使用 LoopBack 服务器来为 Angular4 应用程序提供服务,就像它为 Angularjs 应用程序提供服务一样?

谢谢

4

3 回答 3

14

如果您使用 ng serve 使用 angular-cli 提供 Angular,则 Angular 仅在端口 4200 上运行。

您必须将您的 angular middleware.json 文件选项指向您的 angular2 应用程序的dist目录,或者将您的 dist 目录内容复制到您的环回“客户端”文件夹中。

所以它看起来像这样:

中间件.json

   .
   .
    "files": {
        "loopback#static": {
          "params": "$!../client/"
        }
      }
   .
   .

dist目录是运行时 Angular 输出文件的位置

ng build

确保您的环回引导文件夹中没有router.js文件。这通常包含一些路由代码以将根 url 重定向到您的 api 的状态输出,因此 / 将带您进入您的 api 状态,而不是您的 Angular 应用程序的 index.html。

Loopback 为 Angular 应用程序提供服务,但是,当您尝试直接访问链接时,例如 /blog/:id 换句话说,例如 /blog/f24382f3y23f9832 那么它将失败,因为 loopback 不知道如何处理这些链接,即使 loopback客户端指向角度,直接查询这些链接时,角度尚未“引导”。

要解决此问题,您必须添加自定义中间件以将环回重定向到您的角度索引,以便角度的路由器可以从那里获取它。

因此,在您的middleware.json文件中,更改以下内容:

"final": {
    "./middleware/custom404": {}
    }

然后在 /server/middleware/ 中添加一个文件 custom404.js ,以便完整路径为 /server/middleware/custom404.js 。如果中间件目录不存在,则创建它。

然后在custom404.js文件中:

'use strict';
module.exports = function () {
    var path = require('path');
    return function urlNotFound(req, res, next) {
        let angular_index = path.resolve('client/index.html');
        res.sendFile(angular_index, function (err) {
            if (err) {
                console.error(err);
                res.status(err.status).end();
            }
        });
    };
};

这将重定向回您的 Angular 应用程序,并且 Angular 的路由器将正确路由 url,同时仍由环回提供服务。

我使用path.resolve的是首先根据我们的网络路径而不是当前目录解析链接,否则将被视为恶意调用,您将收到 403 错误。

我已经阅读了 angular.io 文档,这是实现这一点的正确方法。请参阅此处angular.io 文档。阅读标题为“路由应用程序必须回退到 index.html”的部分

我在这里发表了自己的帖子Rewrite requests from loopback to angular2 (Refused to execute script because its MIME type ('text/html') is not executable)我遇到了类似的问题。

于 2017-05-30T15:40:49.670 回答
0

我花了整整一天的时间来解决这个问题。实际上你只需要做两件事。

  1. 在您的节点应用程序的 middleware.json 文件中添加以下对象。

    “文件”:{“loopback#static”:{“参数”:“$!../client/”}}

注意:您还可以提供“dist”文件夹的路径而不是“client”文件夹。

  1. 删除或注释节点应用程序启动文件夹中的 root.js 文件的代码。
于 2020-03-18T08:42:00.793 回答
0

我假设您正在询问生产环境。我当前的 Angular 设置包括html5Mode启用的 ui-router,因此为了让 Loopback 提供静态内容(并避免引入 Nginx 实例或类似的东西),我必须从middleware.json"loopback#static"键下的所有内容)中删除静态中间件并有选择地进行环回将请求传递给它的 Api 或使用相应的文件进行响应,server/server.js假设我的客户端是在client-dist项目的根目录下构建的:

const staticRoot = path.resolve(__dirname, '..', 'client-dist');

app.all('/*', function(req, res, next) {
    // Everything starting with /api passes through
    if (req.url.startsWith('/api')) {
        return next();
    }

    let isAsset = req.url.match(/\/(.*\.(js|css|map|png|svg|jpg|xlsx))\??/);
    if (isAsset) {
        return res.sendFile(isAsset[1], {root: staticRoot });
    }
    // Just send the index.html for other files to support HTML5Mode
    res.sendFile('index.html', { root: staticRoot });
});

如果您不想使用html5Mode,只需loopback#static指向构建客户端的目录,正如https://loopback.io/doc/en/lb3/Add-a-static-web-page.html中所述.

对于我的开发环境,我只是告诉 Loopback SDK 使用localhost:3000

.config(function(LoopBackResourceProvider, $windowProvider) {
    'ngInject';
    var $window = $windowProvider.$get();
    if ([4200].includes(parseInt($window.location.port, 10))) {
        LoopBackResourceProvider.setUrlBase(
            'http://' + $window.location.hostname + ':3000/api'
        );
    }
})
于 2017-05-23T18:47:02.290 回答