【问题标题】:ngtemplate-loader issue ReferenceError: window is not definedngtemplate-loader 问题 ReferenceError:未定义窗口
【发布时间】:2018-02-22 08:39:29
【问题描述】:

我正在尝试将我的 Angular 1.5.3 应用程序切换为使用 Webpack 3.10.0 进行捆绑,并使用 ngtemplate-loader 使 Angular 模板工作。 非常感谢任何帮助,因为我已经坚持了很长时间。

我现在遇到的问题是在生成的 html 文件中包含 <html></html> 标签的奇怪文本:

生成的 wdist/index.html:

var path = 'C:/source/kjopslosning-smb/ksmb-frontend/app/index-webpack.html';
var html = <!DOCTYPE html>
<html lang="no" class="no-js" ng-app="ksmbApp">
     <head>.....</head>
     <body>.....</body>
</html>
;
window.angular.module('ng').run(['$templateCache', function(c) { c.put(path, html) }]);
module.exports = path;

项目结构

+app
+--fonts
+--images
+--styles
+--scripts
+------app.js
+------entry.js
+------controllers
+------sevices
+------directives
+--views (here are all the templates)
+--index-webpack.html
+webpack.config.js
+package.json

webpack.config.js

var webpack = require('webpack');
const CleanWebpackPlugin = require('clean-webpack-plugin');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const ExtractTextPlugin = require("extract-text-webpack-plugin");
const path = require('path');

const extractLess = new ExtractTextPlugin({
  filename: "wbpk-bundle.css",
});


const modules = {
  rules: [
    {
      test: /\.html$/,
      exclude: /node_modules/,
      use: [

        {
          loader: 'html-loader',
          options: {
            root: path.resolve(__dirname, './app/images'),
            attrs: ['img:src', 'link:href']
          }
        },
        {
          loader: 'ngtemplate-loader?relativeTo=' + __dirname + '/app/views',
          options: {
            exclude: path.resolve(__dirname, './app/index-webpack.html'),
          }
        },
      ]
    },
    {
      test: /\.(png|svg|jpg|gif|ico)$/,
      use: [
        {
          loader: 'file-loader',
        }
      ]
    },
    {
      test: /\.less$/,
      use: extractLess.extract({
        use: [{
          loader: "css-loader"
        }, {
          loader: "less-loader",
        }],
        // use style-loader in development
        fallback: "style-loader"
      })
    },
    {
      test: /\.(woff|woff2|eot|ttf|otf)$/,
      use: [
        'file-loader'
      ]
    }
  ]
};

module.exports = {
  entry: path.resolve(__dirname, './app/scripts/entry.js'),
  output: {
    path: __dirname + '/wdist',
    // filename: 'app.bundle.js',
    filename: '[name].bundle.js',
    publicPath: '/ksmb/app'
  },
  devtool: 'inline-source-map',
  module: modules,
  devServer: {
    port: 9000,
    contentBase: './wdist',
    openPage: 'ksmb/app',
    hot: false
  },
  plugins: [
    new CleanWebpackPlugin(['wdist']),
    new HtmlWebpackPlugin({
      filename: 'index.html',
      template: path.resolve(__dirname, './app/index-webpack.html'),
    }),
    extractLess
  ],
};

模板以两种方式注入: 要么使用 ng-include &lt;div ng-include="require('../views/header.html')"&gt;&lt;/div&gt;,要么像这样:

// in app.js

 $routeProvider
     .when('/about', {
      template: require('../views/about.html'),
      controller: 'AboutCtrl',
      controllerAs: 'aboutCtrl',
      title: 'Selskapsinformasjon',
      resolve: {
        initComplete: initComplete
      }
    })
});

生成的 main.bundle.js 似乎有 srtingified 模板:

.............................................
/***/ }),
/* 27 */
/***/ (function(module, exports) {

module.exports = "var path = 'C:/source/kjopslosning-smb/ksmb-frontend/app/views/about.html';\nvar html = <section class=\"ffe-section-wrapper\" mg-controller=\"AboutCtrl as aboutCtrl\">\r\n  <div class=\"ffe-content-container ffe-content-container--lg ffe-content-container--text-left\">\r\n    <a href=\"\" class=\"ffe-link-text ksmb-to-previous\" ng-click=\"aboutCtrl.back()\" ng-bind-html=\"::texts['common.back']\"></a>\r\n  </div>\r\n</section>\r\n<section>\r\n  <div class=\"ffe-content-container ffe-content-container--text-left content-wrapper\">\r\n    <h1 class=\"ffe-h2\" ng-bind-html=\"::texts['about.title']\"></h1>\r\n    <p class=\"ffe-body-paragraph\" ng-bind-html=\"::texts['about.insurance.body']\"></p>\r\n    <p class=\"ffe-body-paragraph\" ng-bind-html=\"::texts['about.damageinsurance.body']\"></p>\r\n  </div>\r\n</section>\r\n;\nwindow.angular.module('ng').run(['$templateCache', function(c) { c.put(path, html) }]);\nmodule.exports = path;";

/***/ }),
/* 28 */
/***/ (function(module, exports) {

module.exports = "var path = 'C:/source/kjopslosning-smb/ksmb-frontend/app/views/terms.html';\nvar html = <section class=\"ffe-section-wrapper\" mg-controller=\"TermsCtrl as termsCtrl\">\r\n  <div class=\"ffe-content-container ffe-content-container--lg ffe-content-container--text-left\">\r\n    <a href=\"\" class=\"ffe-link-text ksmb-to-previous\" ng-click=\"termsCtrl.back()\" ng-bind-html=\"::texts['common.back']\"></a>\r\n  </div>\r\n</section>\r\n<section>\r\n  <div class=\"ffe-content-container ffe-content-container--text-left content-wrapper\">\r\n    <h1 class=\"ffe-h2\" ng-bind-html=\"::texts['terms.title']\"></h1>\r\n    <div ng-bind-html=\"::texts['terms.body']\"></div>\r\n  </div>\r\n</section>\r\n;\nwindow.angular.module('ng').run(['$templateCache', function(c) { c.put(path, html) }]);\nmodule.exports = path;";

/***/ }),
...............................................

所以当 webpack-server 启动时页面是这样的:

Generated wdist/index.html on webpack-server


由于 Generated index.html 越来越

var path = 'C:/source/kjopslosning-smb/ksmb-frontend/app/index-webpack.html';
var html = <!DOCTYPE html>........</html>
    ;
    window.angular.module('ng').run(['$templateCache', function(c) { c.put(path, html) }]);
    module.exports = path;

这是否意味着index-webpack.html 不会从ngtemplate-loader 中排除?


更新

更改加载程序的顺序后(ngtemplate-loader 然后是 html-loader)我收到错误:

ERROR in   Error: C:\source\kjopslosning-smb\ksmb-frontend\app\index-webpack.html:73
  window.angular.module('ng').run(['$templateCache', function(c) { c.put(path, html) }]);
  ^
  ReferenceError: window is not defined

我认为这是由于 index-webpack.html 没有从 ngtemplate-loader 中排除,尽管 我确实有排除了这个加载器的内部选项。

有什么想法吗?

【问题讨论】:

    标签: angularjs webpack


    【解决方案1】:

    最终将 ngtemplate-loader 的配置更改为如下内容:

    {
      test: /\.html$/,
      exclude: [path.resolve(__dirname, './node_modules'), path.resolve(__dirname, './app/index-webpack.html')],
      use: [
        {
          loader: 'ngtemplate-loader',
          options: {
            relativeTo: path.resolve(__dirname + '/app/views'),
          }
        },
        {
          loader: 'html-loader',
          options: {
            root: path.resolve(__dirname, './app/images'),
            attrs: ['img:src', 'link:href']
    
          }
        },
      ]
    },
    

    所以 exclude 不起作用,因为它在选项 inside ngtemplate-loader 下,它应该在测试之后。
    此外,?relativeTo=' + __dirname + '/app/views 语法在 Webpack3 中也不起作用。所以将它从加载器定义中移除到加载器的选项中。

    【讨论】:

      猜你喜欢
      • 2021-03-30
      • 2020-10-08
      • 2018-05-27
      • 2020-09-18
      • 2020-11-12
      • 2018-10-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多