Angular 5 lazy loading Error: Cannot find module
Angular 5 lazy loading Error: Cannot find module
我想使用延迟加载,但我不明白为什么它不起作用,它给我错误 "Cannot find module"。
这是我的环境:
- Angular 5.2.1
- .NET 核心 2
- 网络包 3.10.0
- angular-router-loader 0.8.2
- @angular/cli 1.6.5
我在 loadChildren 中尝试了不同的路径,但始终没有成功,我还暂时禁用了所有守卫和 children 路由。我做错什么了?
文件夹
ClientApp
app
components
users
users-routing.module.ts
users.module.ts
app-routing.module.ts
app.module.shared.ts
app-routing.module.ts
const appRoutes: Routes = [
{
path: 'users',
loadChildren: './components/users/users.module#UsersModule'/* ,
canLoad: [AuthGuard] */
},
{
path: '',
redirectTo: '/login',
pathMatch: 'full'
},
{
path: '**',
redirectTo: '/login'
}
];
@NgModule({
imports: [
RouterModule.forRoot(
appRoutes,
{ enableTracing: false }
)
],
exports: [
RouterModule
],
providers: [
CanDeactivateGuard
]
})
export class AppRoutingModule { }
users-routing.module.ts
const usersRoutes: Routes = [
{
path: '',
component: UsersComponent/* ,
//canActivate: [AuthGuard],
children: [
{
path: 'detail',
canActivateChild: [AuthGuard],
children: [
{
path: ':id',
component: UserViewComponent
},
{
path: 'edit/:id',
component: UserFormComponent,
canDeactivate: [CanDeactivateGuard],
resolve: {
user: UsersResolver
}
},
{
path: '',
component: UserFormComponent,
canDeactivate: [CanDeactivateGuard]
}
]
},
{
path: '',
component: UsersListComponent
}
] */
}
];
@NgModule({
imports: [
RouterModule.forChild(
usersRoutes
)
],
exports: [
RouterModule
]
})
export class UsersRoutingModule { }
用户。module.ts
@NgModule({
imports: [
CommonModule,
FormsModule,
UsersRoutingModule,
RouterModule
],
declarations: [
UsersComponent,
UserFormComponent,
UsersListComponent,
UserViewComponent
],
providers: [
UsersResolver,
RouterModule
]
})
export class UsersModule { }
webpack.config.js
const path = require('path');
const webpack = require('webpack');
const merge = require('webpack-merge');
const AngularCompilerPlugin = require('@ngtools/webpack').AngularCompilerPlugin;
const CheckerPlugin = require('awesome-typescript-loader').CheckerPlugin;
module.exports = (env) => {
// Configuration in common to both client-side and server-side bundles
const isDevBuild = !(env && env.prod);
const sharedConfig = {
stats: {
modules: false
},
context: __dirname,
resolve: {
extensions: ['.js', '.ts']
},
output: {
filename: '[name].js',
publicPath: 'dist/' // Webpack dev middleware, if enabled, handles requests for this URL prefix
},
module: {
rules: [{
test: /\.ts$/,
include: /ClientApp/,
use: isDevBuild ? ['awesome-typescript-loader?silent=true', 'angular2-template-loader'] : '@ngtools/webpack'
},
{
test: /\.html$/,
use: 'html-loader?minimize=false'
},
{
test: /\.css$/,
use: ['to-string-loader', isDevBuild ? 'css-loader' : 'css-loader?minimize']
},
{
test: /\.(png|jpg|jpeg|gif|svg)$/,
use: 'url-loader?limit=25000'
}
],
loaders: [
{
test: /\.ts$/,
loaders: [
'awesome-typescript-loader'
]
},
{
test: /\.(ts|js)$/,
loaders: [
'angular-router-loader'
]
}
]
},
plugins: [new CheckerPlugin()]
};
// Configuration for client-side bundle suitable for running in browsers
const clientBundleOutputDir = './wwwroot/dist';
const clientBundleConfig = merge(sharedConfig, {
entry: {
'main-client': './ClientApp/boot.browser.ts'
},
output: {
path: path.join(__dirname, clientBundleOutputDir)
},
plugins: [
new webpack.DllReferencePlugin({
context: __dirname,
manifest: require('./wwwroot/dist/vendor-manifest.json')
})
].concat(isDevBuild ? [
// Plugins that apply in development builds only
new webpack.SourceMapDevToolPlugin({
filename: '[file].map', // Remove this line if you prefer inline source maps
moduleFilenameTemplate: path.relative(clientBundleOutputDir, '[resourcePath]') // Point sourcemap entries to the original file locations on disk
})
] : [
// Plugins that apply in production builds only
new webpack.optimize.UglifyJsPlugin(),
new AngularCompilerPlugin({
tsConfigPath: './tsconfig.json',
entryModule: path.join(__dirname, 'ClientApp/app/app.module.browser#AppModule'),
exclude: ['./**/*.server.ts']
})
])
});
// Configuration for server-side (prerendering) bundle suitable for running in Node
const serverBundleConfig = merge(sharedConfig, {
resolve: {
mainFields: ['main']
},
entry: {
'main-server': './ClientApp/boot.server.ts'
},
plugins: [
new webpack.DllReferencePlugin({
context: __dirname,
manifest: require('./ClientApp/dist/vendor-manifest.json'),
sourceType: 'commonjs2',
name: './vendor'
})
].concat(isDevBuild ? [] : [
// Plugins that apply in production builds only
new AngularCompilerPlugin({
tsConfigPath: './tsconfig.json',
entryModule: path.join(__dirname, 'ClientApp/app/app.module.server#AppModule'),
exclude: ['./**/*.browser.ts']
})
]),
output: {
libraryTarget: 'commonjs',
path: path.join(__dirname, './ClientApp/dist')
},
target: 'node',
devtool: 'inline-source-map'
});
return [clientBundleConfig, serverBundleConfig];
};
tsconfig.json
{
"compilerOptions": {
"module": "es2015",
"moduleResolution": "node",
"target": "es5",
"sourceMap": true,
"experimentalDecorators": true,
"emitDecoratorMetadata": true,
"skipDefaultLibCheck": true,
"skipLibCheck": true, // Workaround for https://github.com/angular/angular/issues/17863. Remove this if you upgrade to a fixed version of Angular.
"strict": true,
"lib": [ "es6", "dom" ],
"types": [ "webpack-env" ],
"typeRoots": [
"node_modules/@types"
]
},
"exclude": [ "bin", "node_modules" ],
"atom": { "rewriteTsconfig": false }
}
错误信息
Unhandled Promise rejection: Cannot find module
'./ClientApp/app/components/users/users.module'. ; Zone: angular ;
Task: Promise.then ; Value: Error: Cannot find module
'./ClientApp/app/components/users/users.module'.
at vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:34015
at ZoneDelegate.invoke (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117428)
at Object.onInvoke (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:5604)
at ZoneDelegate.invoke (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117427)
at Zone.run (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117178)
at vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117898
at ZoneDelegate.invokeTask (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117461)
at Object.onInvokeTask (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:5595)
at ZoneDelegate.invokeTask (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117460)
at Zone.runTask (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117228)
Error: Cannot find module
'./ClientApp/app/components/users/users.module'.
at http://localhost:5000/dist/vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:34015:9 ... [truncated]
编辑
它的拼写错误文件夹名称是 Users
而不是 users
:
改变
'./components/users/users.module#UsersModule'
到
'./components/Users/users.module#UsersModule'
尝试在你的 user.module.ts 中做:
import {UserRoutes } from './User.routing'
@NgModule({
imports: [
CommonModule,
FormsModule,
UsersRoutingModule.forChild(UserRoutes), //<-- for child
RouterModule
],
declarations: [
UsersComponent,
UserFormComponent,
UsersListComponent,
UserViewComponent
],
providers: [
UsersResolver,
RouterModule
]
})
export class UsersModule { }
我找到了两个解决方案(通过编辑通过 OP):
引用模块,在它已经用导入语句解析后:
从'./components/users/users.module'导入{UsersModule};
然后这样引用:
{
path: 'users',
loadChildren: () => UsersModule,
canLoad: [AuthGuard]
}
我已将 ng-router-loader
添加到应用程序 (npm install ng-router-loader --save-dev
) 并且我这样设置 Webpack:
rules: [{
test: /\.ts$/,
include: /ClientApp/,
//use: isDevBuild ? ['awesome-typescript-loader?silent=true', 'angular2-template-loader'] : '@ngtools/webpack'
use: isDevBuild ? [{ loader: 'ng-router-loader' }, 'awesome-typescript-loader?silent=true', 'angular2-template-loader'] : '@ngtools/webpack'
},
{
test: /\.html$/,
use: 'html-loader?minimize=false'
},
{
test: /\.css$/,
use: ['to-string-loader', isDevBuild ? 'css-loader' : 'css-loader?minimize']
},
{
test: /\.(png|jpg|jpeg|gif|svg)$/,
use: 'url-loader?limit=25000'
}
],
然后通过路径引用模块:
{
path: 'users',
loadChildren: './components/users/users.module#UsersModule',
canLoad: [AuthGuard]
}
一般是路径错误。更改路径。
例如,这个解决方案对我有用::
loadChildren: '../changelog/changelog.module#ChangelogModule'
./folder
或 ../folder
或 folder
目前接受的答案建议将 loadChildren 的值从字符串交换为函数,从而消除了在进行生产构建时进行 AOT 编译的可能性。
对我有用的是
1)使用绝对路径
2) 在 projects > 'projectname' > architect > build > options > lazyModules 下的 angular.json 中将延迟加载模块作为字符串数组添加。路径应与 loadChildren 下定义的路径相同。
因此,对于您的情况,我认为这应该适用于您的路由模块:
loadChildren: 'app/components/users/users.module#UsersModule'
并在 angular.json 中,在上面指定的位置添加:
lazyModules: ["app/components/users/users.module"]
假设这是处理延迟加载的 AppModule,并且您的系统的功能与它是同一棵树:
routes: Routes = [
{
path: 'files-pannel',
loadChildren: () => import('./module-folder/module-name.module').then(m => m.ModuleName)
}
];
你可以这样使用:
const rootRoutes: Routes = [
{ path: 'your-path', loadChildren: () => UsersModule }
];
我在加载我的模块时也遇到了同样的问题,我收到了这个错误
错误:找不到模块 'app/users/users.module'
然后在弄清楚它是与路径相关的错误之后
这个解决方案对我有用希望它能帮助任何人
在路由中添加这条路径
{
path: 'users',
loadChildren: '../app/users/users.module#UsersModule'
}
确定模块文件夹的路径,例如 folder 或 ./folder 或 ../folder
编码愉快!!
我想使用延迟加载,但我不明白为什么它不起作用,它给我错误 "Cannot find module"。
这是我的环境:
- Angular 5.2.1
- .NET 核心 2
- 网络包 3.10.0
- angular-router-loader 0.8.2
- @angular/cli 1.6.5
我在 loadChildren 中尝试了不同的路径,但始终没有成功,我还暂时禁用了所有守卫和 children 路由。我做错什么了?
文件夹
ClientApp
app
components
users
users-routing.module.ts
users.module.ts
app-routing.module.ts
app.module.shared.ts
app-routing.module.ts
const appRoutes: Routes = [
{
path: 'users',
loadChildren: './components/users/users.module#UsersModule'/* ,
canLoad: [AuthGuard] */
},
{
path: '',
redirectTo: '/login',
pathMatch: 'full'
},
{
path: '**',
redirectTo: '/login'
}
];
@NgModule({
imports: [
RouterModule.forRoot(
appRoutes,
{ enableTracing: false }
)
],
exports: [
RouterModule
],
providers: [
CanDeactivateGuard
]
})
export class AppRoutingModule { }
users-routing.module.ts
const usersRoutes: Routes = [
{
path: '',
component: UsersComponent/* ,
//canActivate: [AuthGuard],
children: [
{
path: 'detail',
canActivateChild: [AuthGuard],
children: [
{
path: ':id',
component: UserViewComponent
},
{
path: 'edit/:id',
component: UserFormComponent,
canDeactivate: [CanDeactivateGuard],
resolve: {
user: UsersResolver
}
},
{
path: '',
component: UserFormComponent,
canDeactivate: [CanDeactivateGuard]
}
]
},
{
path: '',
component: UsersListComponent
}
] */
}
];
@NgModule({
imports: [
RouterModule.forChild(
usersRoutes
)
],
exports: [
RouterModule
]
})
export class UsersRoutingModule { }
用户。module.ts
@NgModule({
imports: [
CommonModule,
FormsModule,
UsersRoutingModule,
RouterModule
],
declarations: [
UsersComponent,
UserFormComponent,
UsersListComponent,
UserViewComponent
],
providers: [
UsersResolver,
RouterModule
]
})
export class UsersModule { }
webpack.config.js
const path = require('path');
const webpack = require('webpack');
const merge = require('webpack-merge');
const AngularCompilerPlugin = require('@ngtools/webpack').AngularCompilerPlugin;
const CheckerPlugin = require('awesome-typescript-loader').CheckerPlugin;
module.exports = (env) => {
// Configuration in common to both client-side and server-side bundles
const isDevBuild = !(env && env.prod);
const sharedConfig = {
stats: {
modules: false
},
context: __dirname,
resolve: {
extensions: ['.js', '.ts']
},
output: {
filename: '[name].js',
publicPath: 'dist/' // Webpack dev middleware, if enabled, handles requests for this URL prefix
},
module: {
rules: [{
test: /\.ts$/,
include: /ClientApp/,
use: isDevBuild ? ['awesome-typescript-loader?silent=true', 'angular2-template-loader'] : '@ngtools/webpack'
},
{
test: /\.html$/,
use: 'html-loader?minimize=false'
},
{
test: /\.css$/,
use: ['to-string-loader', isDevBuild ? 'css-loader' : 'css-loader?minimize']
},
{
test: /\.(png|jpg|jpeg|gif|svg)$/,
use: 'url-loader?limit=25000'
}
],
loaders: [
{
test: /\.ts$/,
loaders: [
'awesome-typescript-loader'
]
},
{
test: /\.(ts|js)$/,
loaders: [
'angular-router-loader'
]
}
]
},
plugins: [new CheckerPlugin()]
};
// Configuration for client-side bundle suitable for running in browsers
const clientBundleOutputDir = './wwwroot/dist';
const clientBundleConfig = merge(sharedConfig, {
entry: {
'main-client': './ClientApp/boot.browser.ts'
},
output: {
path: path.join(__dirname, clientBundleOutputDir)
},
plugins: [
new webpack.DllReferencePlugin({
context: __dirname,
manifest: require('./wwwroot/dist/vendor-manifest.json')
})
].concat(isDevBuild ? [
// Plugins that apply in development builds only
new webpack.SourceMapDevToolPlugin({
filename: '[file].map', // Remove this line if you prefer inline source maps
moduleFilenameTemplate: path.relative(clientBundleOutputDir, '[resourcePath]') // Point sourcemap entries to the original file locations on disk
})
] : [
// Plugins that apply in production builds only
new webpack.optimize.UglifyJsPlugin(),
new AngularCompilerPlugin({
tsConfigPath: './tsconfig.json',
entryModule: path.join(__dirname, 'ClientApp/app/app.module.browser#AppModule'),
exclude: ['./**/*.server.ts']
})
])
});
// Configuration for server-side (prerendering) bundle suitable for running in Node
const serverBundleConfig = merge(sharedConfig, {
resolve: {
mainFields: ['main']
},
entry: {
'main-server': './ClientApp/boot.server.ts'
},
plugins: [
new webpack.DllReferencePlugin({
context: __dirname,
manifest: require('./ClientApp/dist/vendor-manifest.json'),
sourceType: 'commonjs2',
name: './vendor'
})
].concat(isDevBuild ? [] : [
// Plugins that apply in production builds only
new AngularCompilerPlugin({
tsConfigPath: './tsconfig.json',
entryModule: path.join(__dirname, 'ClientApp/app/app.module.server#AppModule'),
exclude: ['./**/*.browser.ts']
})
]),
output: {
libraryTarget: 'commonjs',
path: path.join(__dirname, './ClientApp/dist')
},
target: 'node',
devtool: 'inline-source-map'
});
return [clientBundleConfig, serverBundleConfig];
};
tsconfig.json
{
"compilerOptions": {
"module": "es2015",
"moduleResolution": "node",
"target": "es5",
"sourceMap": true,
"experimentalDecorators": true,
"emitDecoratorMetadata": true,
"skipDefaultLibCheck": true,
"skipLibCheck": true, // Workaround for https://github.com/angular/angular/issues/17863. Remove this if you upgrade to a fixed version of Angular.
"strict": true,
"lib": [ "es6", "dom" ],
"types": [ "webpack-env" ],
"typeRoots": [
"node_modules/@types"
]
},
"exclude": [ "bin", "node_modules" ],
"atom": { "rewriteTsconfig": false }
}
错误信息
Unhandled Promise rejection: Cannot find module './ClientApp/app/components/users/users.module'. ; Zone: angular ; Task: Promise.then ; Value: Error: Cannot find module './ClientApp/app/components/users/users.module'. at vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:34015 at ZoneDelegate.invoke (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117428) at Object.onInvoke (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:5604) at ZoneDelegate.invoke (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117427) at Zone.run (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117178) at vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117898 at ZoneDelegate.invokeTask (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117461) at Object.onInvokeTask (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:5595) at ZoneDelegate.invokeTask (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117460) at Zone.runTask (vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:117228) Error: Cannot find module './ClientApp/app/components/users/users.module'. at http://localhost:5000/dist/vendor.js?v=AdjSBPSITyauSY4VQBBoZmJ6NdWqor7MEuHgdi2Dgko:34015:9 ... [truncated]
编辑
它的拼写错误文件夹名称是 Users
而不是 users
:
改变
'./components/users/users.module#UsersModule'
到
'./components/Users/users.module#UsersModule'
尝试在你的 user.module.ts 中做:
import {UserRoutes } from './User.routing'
@NgModule({
imports: [
CommonModule,
FormsModule,
UsersRoutingModule.forChild(UserRoutes), //<-- for child
RouterModule
],
declarations: [
UsersComponent,
UserFormComponent,
UsersListComponent,
UserViewComponent
],
providers: [
UsersResolver,
RouterModule
]
})
export class UsersModule { }
我找到了两个解决方案(通过编辑通过 OP):
引用模块,在它已经用导入语句解析后:
从'./components/users/users.module'导入{UsersModule};
然后这样引用:
{
path: 'users',
loadChildren: () => UsersModule,
canLoad: [AuthGuard]
}
我已将
ng-router-loader
添加到应用程序 (npm install ng-router-loader --save-dev
) 并且我这样设置 Webpack:rules: [{ test: /\.ts$/, include: /ClientApp/, //use: isDevBuild ? ['awesome-typescript-loader?silent=true', 'angular2-template-loader'] : '@ngtools/webpack' use: isDevBuild ? [{ loader: 'ng-router-loader' }, 'awesome-typescript-loader?silent=true', 'angular2-template-loader'] : '@ngtools/webpack' }, { test: /\.html$/, use: 'html-loader?minimize=false' }, { test: /\.css$/, use: ['to-string-loader', isDevBuild ? 'css-loader' : 'css-loader?minimize'] }, { test: /\.(png|jpg|jpeg|gif|svg)$/, use: 'url-loader?limit=25000' } ],
然后通过路径引用模块:
{
path: 'users',
loadChildren: './components/users/users.module#UsersModule',
canLoad: [AuthGuard]
}
一般是路径错误。更改路径。
例如,这个解决方案对我有用::
loadChildren: '../changelog/changelog.module#ChangelogModule'
./folder
或 ../folder
或 folder
目前接受的答案建议将 loadChildren 的值从字符串交换为函数,从而消除了在进行生产构建时进行 AOT 编译的可能性。
对我有用的是 1)使用绝对路径 2) 在 projects > 'projectname' > architect > build > options > lazyModules 下的 angular.json 中将延迟加载模块作为字符串数组添加。路径应与 loadChildren 下定义的路径相同。
因此,对于您的情况,我认为这应该适用于您的路由模块:
loadChildren: 'app/components/users/users.module#UsersModule'
并在 angular.json 中,在上面指定的位置添加:
lazyModules: ["app/components/users/users.module"]
假设这是处理延迟加载的 AppModule,并且您的系统的功能与它是同一棵树:
routes: Routes = [
{
path: 'files-pannel',
loadChildren: () => import('./module-folder/module-name.module').then(m => m.ModuleName)
}
];
你可以这样使用:
const rootRoutes: Routes = [
{ path: 'your-path', loadChildren: () => UsersModule }
];
我在加载我的模块时也遇到了同样的问题,我收到了这个错误 错误:找不到模块 'app/users/users.module' 然后在弄清楚它是与路径相关的错误之后 这个解决方案对我有用希望它能帮助任何人 在路由中添加这条路径
{
path: 'users',
loadChildren: '../app/users/users.module#UsersModule'
}
确定模块文件夹的路径,例如 folder 或 ./folder 或 ../folder
编码愉快!!