diff --git a/.gitignore b/.gitignore index 9812c3c4..2f41fd03 100644 --- a/.gitignore +++ b/.gitignore @@ -35,7 +35,7 @@ Obj/ .vs/ /wwwroot/dist/ -/Client/dist/ +/ClientApp/dist/ # MSTest test Results [Tt]est[Rr]esult*/ @@ -187,6 +187,7 @@ BundleArtifacts/ !*.[Cc]ache/ # Others +*.db ClientBin/ ~$* *~ @@ -259,3 +260,6 @@ _Pvt_Extensions # Jest Code Coverage report coverage/ + +.DS_Store +package-lock.json diff --git a/.vscode/launch.json b/.vscode/launch.json index c3669663..08d4edf9 100644 --- a/.vscode/launch.json +++ b/.vscode/launch.json @@ -20,7 +20,7 @@ "type": "coreclr", "request": "launch", "preLaunchTask": "build", - "program": "${workspaceRoot}/bin/Debug/netcoreapp1.1/Asp2017.dll", + "program": "${workspaceRoot}/bin/Debug/netcoreapp2.0/Asp2017.dll", "args": [], "cwd": "${workspaceRoot}", "stopAtEntry": false, @@ -51,7 +51,7 @@ "type": "coreclr", "request": "launch", "preLaunchTask": "build", - "program": "${workspaceRoot}/bin/Debug/netcoreapp1.1/Asp2017.dll", + "program": "${workspaceRoot}/bin/Debug/netcoreapp2.0/Asp2017.dll", "args": [], "cwd": "${workspaceRoot}", "stopAtEntry": false, @@ -82,7 +82,7 @@ "type": "coreclr", "request": "launch", "preLaunchTask": "build", - "program": "${workspaceRoot}/bin/Debug/netcoreapp1.1/Asp2017.dll", + "program": "${workspaceRoot}/bin/Debug/netcoreapp2.0/Asp2017.dll", "args": [], "cwd": "${workspaceRoot}", "stopAtEntry": false, diff --git a/Asp2017.csproj b/Asp2017.csproj index 712d1b94..e373e9ae 100644 --- a/Asp2017.csproj +++ b/Asp2017.csproj @@ -1,51 +1,68 @@  + - netcoreapp2.0 + netcoreapp2.0 + TargetFrameworkOverride true + Latest false - - + + + + + + + + + + - - - - - - - - + + + - - - + + - + + + + + + + + + + + + + + + + + - - + + + - + %(DistFiles.Identity) PreserveNewest - - - - - - - + diff --git a/Client/main.server.aot.ts b/Client/main.server.aot.ts deleted file mode 100644 index eb4f0699..00000000 --- a/Client/main.server.aot.ts +++ /dev/null @@ -1,41 +0,0 @@ -import 'zone.js/dist/zone-node'; -import './polyfills/server.polyfills'; -import { enableProdMode } from '@angular/core'; -import { INITIAL_CONFIG } from '@angular/platform-server'; -import { APP_BASE_HREF } from '@angular/common'; -import { createServerRenderer, RenderResult } from 'aspnet-prerendering'; - -import { ORIGIN_URL } from './app/shared/constants/baseurl.constants'; -// Grab the (Node) server-specific NgModule -import { ServerAppModuleNgFactory } from './ngfactory/app/server-app.module.ngfactory'; -// Temporary * the engine will be on npm soon (`@universal/ng-aspnetcore-engine`) -import { ngAspnetCoreEngine, IEngineOptions, createTransferScript } from './polyfills/temporary-aspnetcore-engine'; - -enableProdMode(); - -export default createServerRenderer(params => { - - // Platform-server provider configuration - const setupOptions: IEngineOptions = { - appSelector: '', - ngModule: ServerAppModuleNgFactory, - request: params, - providers: [ - // Optional - Any other Server providers you want to pass (remember you'll have to provide them for the Browser as well) - ] - }; - - return ngAspnetCoreEngine(setupOptions).then(response => { - // Apply your transferData to response.globals - response.globals.transferData = createTransferScript({ - someData: 'Transfer this to the client on the window.TRANSFER_CACHE {} object' - }); - - return ({ - html: response.html, - globals: response.globals - }); - }); -}); - -/* -------- THIS FILE IS TEMPORARY and will be gone when @ngtools/webpack can handle dual files (w server) ---------- */ diff --git a/Client/tsconfig.browser.json b/Client/tsconfig.browser.json deleted file mode 100644 index d04b9e60..00000000 --- a/Client/tsconfig.browser.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "../tsconfig.json", - "angularCompilerOptions": { - "entryModule": "./app/browser-app.module#BrowserAppModule" - }, - "exclude": [ - "./main.server.aot.ts" - ] -} diff --git a/Client/tsconfig.server.aot.json b/Client/tsconfig.server.aot.json deleted file mode 100644 index 2407460a..00000000 --- a/Client/tsconfig.server.aot.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "extends": "./tsconfig.server.json", - "angularCompilerOptions": { - "genDir": "ngfactory", - "entryModule": "./app/server-app.module#ServerAppModule" - }, - "exclude": [] -} diff --git a/Client/tsconfig.server.json b/Client/tsconfig.server.json deleted file mode 100644 index 6fecd055..00000000 --- a/Client/tsconfig.server.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "../tsconfig.json", - "angularCompilerOptions": { - "entryModule": "./app/server-app.module#ServerAppModule" - }, - "exclude": [ - "./main.server.aot.ts" - ] -} diff --git a/Client/app/app.component.html b/ClientApp/app/app.component.html similarity index 94% rename from Client/app/app.component.html rename to ClientApp/app/app.component.html index 12a962a5..a3e3bf9b 100644 --- a/Client/app/app.component.html +++ b/ClientApp/app/app.component.html @@ -3,4 +3,4 @@
-
\ No newline at end of file + diff --git a/Client/app/app.component.scss b/ClientApp/app/app.component.scss similarity index 100% rename from Client/app/app.component.scss rename to ClientApp/app/app.component.scss diff --git a/Client/app/app.component.ts b/ClientApp/app/app.component.ts similarity index 100% rename from Client/app/app.component.ts rename to ClientApp/app/app.component.ts diff --git a/Client/app/browser-app.module.ts b/ClientApp/app/app.module.browser.ts similarity index 94% rename from Client/app/browser-app.module.ts rename to ClientApp/app/app.module.browser.ts index 0150d22c..0af291d4 100644 --- a/Client/app/browser-app.module.ts +++ b/ClientApp/app/app.module.browser.ts @@ -6,7 +6,7 @@ import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; import { SignalRModule, SignalRConfiguration } from 'ng2-signalr'; import { ORIGIN_URL } from './shared/constants/baseurl.constants'; -import { AppModule } from './app.module'; +import { AppModuleShared } from './app.module'; import { AppComponent } from './app.component'; import { REQUEST } from './shared/constants/request'; import { BrowserTransferStateModule } from '../modules/transfer-state/browser-transfer-state.module'; @@ -41,7 +41,7 @@ export function getRequest() { BrowserTransferStateModule, // Our Common AppModule - AppModule, + AppModuleShared, SignalRModule.forRoot(createConfig) ], @@ -58,5 +58,4 @@ export function getRequest() { } ] }) -export class BrowserAppModule { -} +export class AppModule { } diff --git a/Client/app/server-app.module.ts b/ClientApp/app/app.module.server.ts similarity index 90% rename from Client/app/server-app.module.ts rename to ClientApp/app/app.module.server.ts index ac91990a..9ccbfb52 100644 --- a/Client/app/server-app.module.ts +++ b/ClientApp/app/app.module.server.ts @@ -3,7 +3,7 @@ import { ServerModule } from '@angular/platform-server'; import { BrowserModule } from '@angular/platform-browser'; import { NoopAnimationsModule } from '@angular/platform-browser/animations'; -import { AppModule } from './app.module'; +import { AppModuleShared } from './app.module'; import { AppComponent } from './app.component'; import { ServerTransferStateModule } from '../modules/transfer-state/server-transfer-state.module'; import { TransferState } from '../modules/transfer-state/transfer-state'; @@ -20,10 +20,10 @@ import { TransferState } from '../modules/transfer-state/transfer-state'; ServerTransferStateModule, // Our Common AppModule - AppModule + AppModuleShared ] }) -export class ServerAppModule { +export class AppModule { constructor(private transferState: TransferState) { } diff --git a/Client/app/app.module.ts b/ClientApp/app/app.module.ts similarity index 96% rename from Client/app/app.module.ts rename to ClientApp/app/app.module.ts index 753aed35..57498bb8 100644 --- a/Client/app/app.module.ts +++ b/ClientApp/app/app.module.ts @@ -1,5 +1,5 @@ import { NgModule, Inject } from '@angular/core'; -import { RouterModule } from '@angular/router'; +import { RouterModule, PreloadAllModules } from '@angular/router'; import { CommonModule, APP_BASE_HREF } from '@angular/common'; import { HttpModule, Http } from '@angular/http'; import { FormsModule } from '@angular/forms'; @@ -134,9 +134,9 @@ export function createTranslateLoader(http: Http, baseHref) { ] } }, - + { path: 'lazy', loadChildren: './containers/lazy/lazy.module#LazyModule'}, - + { path: '**', component: NotFoundComponent, data: { @@ -148,7 +148,12 @@ export function createTranslateLoader(http: Http, baseHref) { ] } } - ]) + ], { + // Router options + useHash: false, + preloadingStrategy: PreloadAllModules, + initialNavigation: 'enabled' + }) ], providers: [ LinkService, @@ -157,5 +162,5 @@ export function createTranslateLoader(http: Http, baseHref) { TranslateModule ] }) -export class AppModule { +export class AppModuleShared { } diff --git a/Client/app/components/navmenu/navmenu.component.css b/ClientApp/app/components/navmenu/navmenu.component.css similarity index 100% rename from Client/app/components/navmenu/navmenu.component.css rename to ClientApp/app/components/navmenu/navmenu.component.css diff --git a/Client/app/components/navmenu/navmenu.component.html b/ClientApp/app/components/navmenu/navmenu.component.html similarity index 100% rename from Client/app/components/navmenu/navmenu.component.html rename to ClientApp/app/components/navmenu/navmenu.component.html diff --git a/Client/app/components/navmenu/navmenu.component.ts b/ClientApp/app/components/navmenu/navmenu.component.ts similarity index 100% rename from Client/app/components/navmenu/navmenu.component.ts rename to ClientApp/app/components/navmenu/navmenu.component.ts diff --git a/Client/app/components/user-detail/user-detail.component.html b/ClientApp/app/components/user-detail/user-detail.component.html similarity index 100% rename from Client/app/components/user-detail/user-detail.component.html rename to ClientApp/app/components/user-detail/user-detail.component.html diff --git a/Client/app/components/user-detail/user-detail.component.ts b/ClientApp/app/components/user-detail/user-detail.component.ts similarity index 100% rename from Client/app/components/user-detail/user-detail.component.ts rename to ClientApp/app/components/user-detail/user-detail.component.ts diff --git a/Client/app/containers/chat/chat.component.html b/ClientApp/app/containers/chat/chat.component.html similarity index 100% rename from Client/app/containers/chat/chat.component.html rename to ClientApp/app/containers/chat/chat.component.html diff --git a/Client/app/containers/chat/chat.component.css b/ClientApp/app/containers/chat/chat.component.scss similarity index 100% rename from Client/app/containers/chat/chat.component.css rename to ClientApp/app/containers/chat/chat.component.scss diff --git a/Client/app/containers/chat/chat.component.ts b/ClientApp/app/containers/chat/chat.component.ts similarity index 97% rename from Client/app/containers/chat/chat.component.ts rename to ClientApp/app/containers/chat/chat.component.ts index ca9dc8ea..8bbd9ed9 100644 --- a/Client/app/containers/chat/chat.component.ts +++ b/ClientApp/app/containers/chat/chat.component.ts @@ -11,7 +11,7 @@ export class ChatMessage { @Component({ selector: 'chat', templateUrl: './chat.component.html', - styleUrls: ['./chat.component.css'] + styleUrls: ['./chat.component.scss'] }) export class ChatComponent implements OnInit { diff --git a/Client/app/containers/counter/counter.component.html b/ClientApp/app/containers/counter/counter.component.html similarity index 100% rename from Client/app/containers/counter/counter.component.html rename to ClientApp/app/containers/counter/counter.component.html diff --git a/Client/app/containers/counter/counter.component.spec.ts b/ClientApp/app/containers/counter/counter.component.spec.ts similarity index 100% rename from Client/app/containers/counter/counter.component.spec.ts rename to ClientApp/app/containers/counter/counter.component.spec.ts diff --git a/Client/app/containers/counter/counter.component.ts b/ClientApp/app/containers/counter/counter.component.ts similarity index 100% rename from Client/app/containers/counter/counter.component.ts rename to ClientApp/app/containers/counter/counter.component.ts diff --git a/Client/app/containers/home/home.component.html b/ClientApp/app/containers/home/home.component.html similarity index 90% rename from Client/app/containers/home/home.component.html rename to ClientApp/app/containers/home/home.component.html index 3f872f90..06d801e7 100644 --- a/Client/app/containers/home/home.component.html +++ b/ClientApp/app/containers/home/home.component.html @@ -1,23 +1,20 @@ -

- {{ title }}

+

{{ title }}

Enjoy the latest features from .NET Core & Angular 4.0!
For more info check the repo here: AspNetCore-Angular2-Universal repo -

-

{{ 'HOME_FEATURE_LIST_TITLE' | translate }}

diff --git a/Client/app/containers/home/home.component.ts b/ClientApp/app/containers/home/home.component.ts similarity index 78% rename from Client/app/containers/home/home.component.ts rename to ClientApp/app/containers/home/home.component.ts index ed7e6f0a..3065c0b1 100644 --- a/Client/app/containers/home/home.component.ts +++ b/ClientApp/app/containers/home/home.component.ts @@ -8,10 +8,12 @@ import { TranslateService } from '@ngx-translate/core'; }) export class HomeComponent implements OnInit { - title: string = 'Angular 4.0 Universal & ASP.NET Core advanced starter-kit'; + title: string = 'Angular 4.0 Universal & ASP.NET Core 2.0 advanced starter-kit'; // Use "constructor"s only for dependency injection - constructor(public translate: TranslateService) { } + constructor( + public translate: TranslateService + ) { } // Here you want to handle anything with @Input()'s @Output()'s // Data retrieval / etc - this is when the Component is "ready" and wired up diff --git a/Client/app/containers/lazy/lazy.component.ts b/ClientApp/app/containers/lazy/lazy.component.ts similarity index 100% rename from Client/app/containers/lazy/lazy.component.ts rename to ClientApp/app/containers/lazy/lazy.component.ts diff --git a/Client/app/containers/lazy/lazy.module.ts b/ClientApp/app/containers/lazy/lazy.module.ts similarity index 100% rename from Client/app/containers/lazy/lazy.module.ts rename to ClientApp/app/containers/lazy/lazy.module.ts diff --git a/Client/app/containers/ngx-bootstrap-demo/ngx-bootstrap.component.html b/ClientApp/app/containers/ngx-bootstrap-demo/ngx-bootstrap.component.html similarity index 100% rename from Client/app/containers/ngx-bootstrap-demo/ngx-bootstrap.component.html rename to ClientApp/app/containers/ngx-bootstrap-demo/ngx-bootstrap.component.html diff --git a/Client/app/containers/ngx-bootstrap-demo/ngx-bootstrap.component.ts b/ClientApp/app/containers/ngx-bootstrap-demo/ngx-bootstrap.component.ts similarity index 100% rename from Client/app/containers/ngx-bootstrap-demo/ngx-bootstrap.component.ts rename to ClientApp/app/containers/ngx-bootstrap-demo/ngx-bootstrap.component.ts diff --git a/Client/app/containers/not-found/not-found.component.html b/ClientApp/app/containers/not-found/not-found.component.html similarity index 100% rename from Client/app/containers/not-found/not-found.component.html rename to ClientApp/app/containers/not-found/not-found.component.html diff --git a/Client/app/containers/not-found/not-found.component.ts b/ClientApp/app/containers/not-found/not-found.component.ts similarity index 100% rename from Client/app/containers/not-found/not-found.component.ts rename to ClientApp/app/containers/not-found/not-found.component.ts diff --git a/Client/app/containers/users/users.component.css b/ClientApp/app/containers/users/users.component.css similarity index 100% rename from Client/app/containers/users/users.component.css rename to ClientApp/app/containers/users/users.component.css diff --git a/Client/app/containers/users/users.component.html b/ClientApp/app/containers/users/users.component.html similarity index 100% rename from Client/app/containers/users/users.component.html rename to ClientApp/app/containers/users/users.component.html diff --git a/Client/app/containers/users/users.component.ts b/ClientApp/app/containers/users/users.component.ts similarity index 100% rename from Client/app/containers/users/users.component.ts rename to ClientApp/app/containers/users/users.component.ts diff --git a/Client/app/models/User.ts b/ClientApp/app/models/User.ts similarity index 100% rename from Client/app/models/User.ts rename to ClientApp/app/models/User.ts diff --git a/Client/app/shared/constants/baseurl.constants.ts b/ClientApp/app/shared/constants/baseurl.constants.ts similarity index 100% rename from Client/app/shared/constants/baseurl.constants.ts rename to ClientApp/app/shared/constants/baseurl.constants.ts diff --git a/Client/app/shared/constants/request.ts b/ClientApp/app/shared/constants/request.ts similarity index 100% rename from Client/app/shared/constants/request.ts rename to ClientApp/app/shared/constants/request.ts diff --git a/Client/app/shared/link.service.ts b/ClientApp/app/shared/link.service.ts similarity index 100% rename from Client/app/shared/link.service.ts rename to ClientApp/app/shared/link.service.ts diff --git a/Client/app/shared/route.resolver.ts b/ClientApp/app/shared/route.resolver.ts similarity index 100% rename from Client/app/shared/route.resolver.ts rename to ClientApp/app/shared/route.resolver.ts diff --git a/Client/app/shared/user.service.ts b/ClientApp/app/shared/user.service.ts similarity index 100% rename from Client/app/shared/user.service.ts rename to ClientApp/app/shared/user.service.ts diff --git a/Client/main.browser.ts b/ClientApp/boot.browser.ts similarity index 77% rename from Client/main.browser.ts rename to ClientApp/boot.browser.ts index 01723608..a7830543 100644 --- a/Client/main.browser.ts +++ b/ClientApp/boot.browser.ts @@ -1,7 +1,7 @@ import './polyfills/browser.polyfills'; import { enableProdMode } from '@angular/core'; import { platformBrowserDynamic } from '@angular/platform-browser-dynamic'; -import { BrowserAppModule } from './app/browser-app.module'; +import { AppModule } from './app/app.module.browser'; const rootElemTagName = 'app'; // Update this if you change your root component selector @@ -15,4 +15,4 @@ if (module['hot']) { enableProdMode(); } -const modulePromise = platformBrowserDynamic().bootstrapModule(BrowserAppModule); +const modulePromise = platformBrowserDynamic().bootstrapModule(AppModule); diff --git a/Client/main.server.ts b/ClientApp/boot.server.ts similarity index 94% rename from Client/main.server.ts rename to ClientApp/boot.server.ts index e20e4f9f..d93a4f56 100644 --- a/Client/main.server.ts +++ b/ClientApp/boot.server.ts @@ -7,7 +7,7 @@ import { createServerRenderer, RenderResult } from 'aspnet-prerendering'; import { ORIGIN_URL } from './app/shared/constants/baseurl.constants'; // Grab the (Node) server-specific NgModule -import { ServerAppModule } from './app/server-app.module'; +import { AppModule } from './app/app.module.server'; // Temporary * the engine will be on npm soon (`@universal/ng-aspnetcore-engine`) import { ngAspnetCoreEngine, IEngineOptions, createTransferScript } from './polyfills/temporary-aspnetcore-engine'; @@ -18,7 +18,7 @@ export default createServerRenderer((params: BootFuncParams) => { // Platform-server provider configuration const setupOptions: IEngineOptions = { appSelector: '', - ngModule: ServerAppModule, + ngModule: AppModule, request: params, providers: [ // Optional - Any other Server providers you want to pass (remember you'll have to provide them for the Browser as well) diff --git a/Client/modules/transfer-http/transfer-http.module.ts b/ClientApp/modules/transfer-http/transfer-http.module.ts similarity index 100% rename from Client/modules/transfer-http/transfer-http.module.ts rename to ClientApp/modules/transfer-http/transfer-http.module.ts diff --git a/Client/modules/transfer-http/transfer-http.ts b/ClientApp/modules/transfer-http/transfer-http.ts similarity index 100% rename from Client/modules/transfer-http/transfer-http.ts rename to ClientApp/modules/transfer-http/transfer-http.ts diff --git a/Client/modules/transfer-state/browser-transfer-state.module.ts b/ClientApp/modules/transfer-state/browser-transfer-state.module.ts similarity index 100% rename from Client/modules/transfer-state/browser-transfer-state.module.ts rename to ClientApp/modules/transfer-state/browser-transfer-state.module.ts diff --git a/Client/modules/transfer-state/server-transfer-state.module.ts b/ClientApp/modules/transfer-state/server-transfer-state.module.ts similarity index 100% rename from Client/modules/transfer-state/server-transfer-state.module.ts rename to ClientApp/modules/transfer-state/server-transfer-state.module.ts diff --git a/Client/modules/transfer-state/server-transfer-state.ts b/ClientApp/modules/transfer-state/server-transfer-state.ts similarity index 100% rename from Client/modules/transfer-state/server-transfer-state.ts rename to ClientApp/modules/transfer-state/server-transfer-state.ts diff --git a/Client/modules/transfer-state/transfer-state.ts b/ClientApp/modules/transfer-state/transfer-state.ts similarity index 100% rename from Client/modules/transfer-state/transfer-state.ts rename to ClientApp/modules/transfer-state/transfer-state.ts diff --git a/Client/polyfills/browser.polyfills.ts b/ClientApp/polyfills/browser.polyfills.ts similarity index 100% rename from Client/polyfills/browser.polyfills.ts rename to ClientApp/polyfills/browser.polyfills.ts diff --git a/Client/polyfills/polyfills.ts b/ClientApp/polyfills/polyfills.ts similarity index 100% rename from Client/polyfills/polyfills.ts rename to ClientApp/polyfills/polyfills.ts diff --git a/Client/polyfills/rx-imports.ts b/ClientApp/polyfills/rx-imports.ts similarity index 100% rename from Client/polyfills/rx-imports.ts rename to ClientApp/polyfills/rx-imports.ts diff --git a/Client/polyfills/server.polyfills.ts b/ClientApp/polyfills/server.polyfills.ts similarity index 100% rename from Client/polyfills/server.polyfills.ts rename to ClientApp/polyfills/server.polyfills.ts diff --git a/Client/polyfills/temporary-aspnetcore-engine.ts b/ClientApp/polyfills/temporary-aspnetcore-engine.ts similarity index 100% rename from Client/polyfills/temporary-aspnetcore-engine.ts rename to ClientApp/polyfills/temporary-aspnetcore-engine.ts diff --git a/Client/test/jestGlobalMocks.ts b/ClientApp/test/jestGlobalMocks.ts similarity index 100% rename from Client/test/jestGlobalMocks.ts rename to ClientApp/test/jestGlobalMocks.ts diff --git a/Client/test/setupJest.ts b/ClientApp/test/setupJest.ts similarity index 100% rename from Client/test/setupJest.ts rename to ClientApp/test/setupJest.ts diff --git a/Client/tsconfig.spec.json b/ClientApp/tsconfig.spec.json similarity index 100% rename from Client/tsconfig.spec.json rename to ClientApp/tsconfig.spec.json diff --git a/Client/typings.d.ts b/ClientApp/typings.d.ts similarity index 100% rename from Client/typings.d.ts rename to ClientApp/typings.d.ts diff --git a/README.md b/README.md index 183ab0b0..040dc0e0 100644 --- a/README.md +++ b/README.md @@ -118,7 +118,7 @@ npm install && npm run build:dev && dotnet restore # or yarn install ``` -If you're running the project from command line with `dotnet run` make sure you set your environment variables to Development (otherwise things like HMR won't work). +If you're running the project from command line with `dotnet run` make sure you set your environment variables to Development (otherwise things like HMR might not work). ```bash # on Windows: @@ -129,7 +129,6 @@ export ASPNETCORE_ENVIRONMENT=Development # Upcoming Features: -- **Fix and update Webpack build / Vendor chunking and overall compilation speed.** ( important ) - Update to use npm [ngAspnetCoreEngine](https://github.com/angular/universal/pull/682) (still need to tweak a few things there) - Potractor e2e testing - Add basic Redux State store (Will also hold state durijg HMR builds) diff --git a/Server/Controllers/HomeController.cs b/Server/Controllers/HomeController.cs index 3f19192d..87b41ff2 100644 --- a/Server/Controllers/HomeController.cs +++ b/Server/Controllers/HomeController.cs @@ -43,7 +43,7 @@ public async Task Index() "/", nodeServices, cancelToken, - new JavaScriptModuleExport(applicationBasePath + "/Client/dist/main-server"), + new JavaScriptModuleExport(applicationBasePath + "/ClientApp/dist/main-server"), unencodedAbsoluteUrl, unencodedPathAndQuery, transferData, // Our simplified Request object & any other CustommData you want to send! diff --git a/Startup.cs b/Startup.cs index 00fc9291..7736f9e9 100644 --- a/Startup.cs +++ b/Startup.cs @@ -73,7 +73,8 @@ public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerF app.UseDeveloperExceptionPage(); app.UseWebpackDevMiddleware(new WebpackDevMiddlewareOptions { - HotModuleReplacement = true + HotModuleReplacement = true, + HotModuleReplacementEndpoint = "/dist/__webpack_hmr" }); app.UseSwagger(); app.UseSwaggerUI(c => diff --git a/Views/Home/Index.cshtml b/Views/Home/Index.cshtml index 418bb1fd..b0796562 100644 --- a/Views/Home/Index.cshtml +++ b/Views/Home/Index.cshtml @@ -1,6 +1,7 @@ @Html.Raw(ViewData["SpaHtml"]) + @section scripts { - + } diff --git a/Views/Shared/_Layout.cshtml b/Views/Shared/_Layout.cshtml index 8d8fb071..509c52db 100644 --- a/Views/Shared/_Layout.cshtml +++ b/Views/Shared/_Layout.cshtml @@ -1,32 +1,33 @@  - - - @ViewData["Title"] + + + @ViewData["Title"] - - - @Html.Raw(ViewData["Meta"]) - @Html.Raw(ViewData["Links"]) + + + @Html.Raw(ViewData["Meta"]) + @Html.Raw(ViewData["Links"]) - + + - @Html.Raw(ViewData["Styles"]) + @Html.Raw(ViewData["Styles"]) - - - @RenderBody() + + + @RenderBody() - - + + - + - - @Html.Raw(ViewData["TransferData"]) + + @Html.Raw(ViewData["TransferData"]) - @RenderSection("scripts", required: false) - + @RenderSection("scripts", required: false) + diff --git a/package.json b/package.json index 3d0e18c9..f3b00472 100644 --- a/package.json +++ b/package.json @@ -6,40 +6,44 @@ "test:watch": "npm run test -- --watch", "test:ci": "npm run test -- --runInBand", "test:coverage": "npm run test -- --coverage", - "build:dev": "webpack --progress --color", - "build:aot": "webpack --env.aot --env.client & webpack --env.aot --env.server" + "build:dev": "npm run build:vendor && npm run build:webpack", + "build:webpack": "webpack --progress --color", + "build:prod": "npm run build:vendor -- --env.prod && npm run build:dev -- --env.prod", + "build:vendor": "webpack --config webpack.config.vendor.js --progress --color" }, "jest": { "preset": "jest-preset-angular", - "setupTestFrameworkScriptFile": "./Client/test/setupJest.ts", + "setupTestFrameworkScriptFile": "./ClientApp/test/setupJest.ts", "globals": { - "__TS_CONFIG__": "Client/tsconfig.spec.json", + "__TS_CONFIG__": "ClientApp/tsconfig.spec.json", "__TRANSFORM_HTML__": true }, "coveragePathIgnorePatterns": [ "/node_modules/", - "/Client/test/.*.ts" + "/ClientApp/test/.*.ts" ], "coverageDirectory": "coverage" }, "dependencies": { - "@angular/animations": "^4.0.0", - "@angular/common": "^4.0.0", - "@angular/compiler": "^4.0.0", - "@angular/compiler-cli": "^4.0.0", - "@angular/core": "^4.0.0", - "@angular/forms": "^4.0.0", - "@angular/http": "^4.0.0", - "@angular/platform-browser": "^4.0.0", - "@angular/platform-browser-dynamic": "^4.0.0", - "@angular/platform-server": "^4.0.0", - "@angular/router": "^4.0.0", + "@angular/animations": "^4.3.0", + "@angular/common": "^4.3.0", + "@angular/compiler": "^4.3.0", + "@angular/compiler-cli": "^4.3.0", + "@angular/core": "^4.3.0", + "@angular/forms": "^4.3.0", + "@angular/http": "^4.3.0", + "@angular/platform-browser": "^4.3.0", + "@angular/platform-browser-dynamic": "^4.3.0", + "@angular/platform-server": "^4.3.0", + "@angular/router": "^4.3.0", + "@nguniversal/aspnetcore-engine": "^1.0.0-beta.2", "@ngx-translate/core": "^6.0.1", "@ngx-translate/http-loader": "0.0.3", "@types/node": "^7.0.12", + "angular2-router-loader": "^0.3.4", "angular2-template-loader": "0.6.0", "aspnet-prerendering": "2.0.3", - "aspnet-webpack": "^1.0.17", + "aspnet-webpack": "^2.0.1", "awesome-typescript-loader": "^3.0.0", "bootstrap": "^3.3.7", "bootstrap-sass": "^3.3.7", @@ -55,7 +59,7 @@ "jquery": "^2.2.1", "json-loader": "^0.5.4", "ng2-signalr": "2.0.4", - "ngx-bootstrap": "^1.7.1", + "ngx-bootstrap": "^2.0.0-beta.2", "node-sass": "^4.5.2", "preboot": "^4.5.2", "raw-loader": "^0.5.1", @@ -78,7 +82,8 @@ "@types/jasmine": "^2.5.37", "@types/jest": "^19.2.3", "chai": "^3.5.0", - "codelyzer": "^3.0.0-beta.4", + "codelyzer": "^3.0.0", + "tslint": "^5.0.0", "jasmine-core": "^2.5.2", "jest": "^20.0.0", "jest-preset-angular": "^2.0.1" diff --git a/tsconfig.json b/tsconfig.json index 8728ffab..0e68aae4 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -4,10 +4,11 @@ "module": "es2015", "target": "es5", "noImplicitAny": false, - "sourceMap": false, + "sourceMap": true, "experimentalDecorators": true, "emitDecoratorMetadata": true, - "noStrictGenericChecks": true, + "skipDefaultLibCheck": true, + "skipLibCheck": true, "lib": [ "es2016", "dom" @@ -15,6 +16,6 @@ "types": [ "node" ] }, "include": [ - "Client" + "ClientApp" ] } diff --git a/webpack.additions.js b/webpack.additions.js new file mode 100644 index 00000000..62bf4bb3 --- /dev/null +++ b/webpack.additions.js @@ -0,0 +1,18 @@ +/* [ Webpack Additions ] + * + * This file contains ADD-ONS we are adding on-top of the traditional JavaScriptServices repo + * We do this so that those already using JavaScriptServices can easily figure out how to combine this repo into it. + */ + +// Shared rules[] we need to add +const sharedModuleRules = [ + // sass + { test: /\.scss$/, loaders: ['to-string-loader', 'css-loader', 'sass-loader'] }, + // font-awesome + { test: /\.(woff2?|ttf|eot|svg)$/, loader: 'url-loader?limit=10000' } +]; + + +module.exports = { + sharedModuleRules +}; diff --git a/webpack.config.js b/webpack.config.js index 76980b9c..06435301 100644 --- a/webpack.config.js +++ b/webpack.config.js @@ -1,46 +1,97 @@ -const path = require('path'); -const webpackMerge = require('webpack-merge'); -const commonPartial = require('./webpack/webpack.common'); -const clientPartial = require('./webpack/webpack.client'); -const serverPartial = require('./webpack/webpack.server'); -const prodPartial = require('./webpack/webpack.prod'); -const { getAotPlugin } = require('./webpack/webpack.aot'); +/* + * Webpack (JavaScriptServices) with a few changes & updates + * - This is to keep us inline with JSServices, and help those using that template to add things from this one + * + * Things updated or changed: + * module -> rules [] + * .ts$ test : Added 'angular2-router-loader' for lazy-loading in development + * added ...sharedModuleRules (for scss & font-awesome loaders) + */ -module.exports = function (options, webpackOptions) { - options = options || {}; - webpackOptions = webpackOptions || {}; +const path = require('path'); +const webpack = require('webpack'); +const merge = require('webpack-merge'); +const AotPlugin = require('@ngtools/webpack').AotPlugin; +const CheckerPlugin = require('awesome-typescript-loader').CheckerPlugin; - if (options.aot) { - console.log(`Running build for ${options.client ? 'client' : 'server'} with AoT Compilation`) - } +const { sharedModuleRules } = require('./webpack.additions'); - const serverConfig = webpackMerge({}, commonPartial, serverPartial, { - entry: options.aot ? { 'main-server' : './Client/main.server.aot.ts' } : serverPartial.entry, // Temporary +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$/, use: isDevBuild ? ['awesome-typescript-loader?silent=true', 'angular2-template-loader', 'angular2-router-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' }, + ...sharedModuleRules + ] + }, + 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: [ - getAotPlugin('server', !!options.aot) - ] + 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 AotPlugin({ + tsConfigPath: './tsconfig.json', + entryModule: path.join(__dirname, 'ClientApp/app/app.module.browser#AppModule'), + exclude: ['./**/*.server.ts'] + }) + ]) }); - let clientConfig = webpackMerge({}, commonPartial, clientPartial, { + // 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: [ - getAotPlugin('client', !!options.aot) - ] + 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 AotPlugin({ + 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' }); - if (webpackOptions.prod) { - clientConfig = webpackMerge({}, clientConfig, prodPartial); - } - - const configs = []; - if (!options.aot) { - configs.push(clientConfig, serverConfig); - - } else if (options.client) { - configs.push(clientConfig); - - } else if (options.server) { - configs.push(serverConfig); - } - - return configs; -} + return [clientBundleConfig, serverBundleConfig]; +}; diff --git a/webpack.config.vendor.js b/webpack.config.vendor.js new file mode 100644 index 00000000..7ae8a6d2 --- /dev/null +++ b/webpack.config.vendor.js @@ -0,0 +1,97 @@ +const path = require('path'); +const webpack = require('webpack'); +const ExtractTextPlugin = require('extract-text-webpack-plugin'); +const merge = require('webpack-merge'); +const treeShakableModules = [ + '@angular/animations', + '@angular/common', + '@angular/compiler', + '@angular/core', + '@angular/forms', + '@angular/http', + '@angular/platform-browser', + '@angular/platform-browser-dynamic', + '@angular/router', + 'ngx-bootstrap', + 'zone.js', +]; +const nonTreeShakableModules = [ + 'bootstrap', + 'bootstrap/dist/css/bootstrap.css', + 'core-js', + // 'es6-promise', + // 'es6-shim', + 'event-source-polyfill', + // 'jquery', +]; +const allModules = treeShakableModules.concat(nonTreeShakableModules); + +module.exports = (env) => { + console.log(`env = ${JSON.stringify(env)}`) + const extractCSS = new ExtractTextPlugin('vendor.css'); + const isDevBuild = !(env && env.prod); + const sharedConfig = { + stats: { modules: false }, + resolve: { extensions: [ '.js' ] }, + module: { + rules: [ + { test: /\.(png|woff|woff2|eot|ttf|svg)(\?|$)/, use: 'url-loader?limit=100000' } + ] + }, + output: { + publicPath: 'dist/', + filename: '[name].js', + library: '[name]_[hash]' + }, + plugins: [ + // new webpack.ProvidePlugin({ $: 'jquery', jQuery: 'jquery' }), // Maps these identifiers to the jQuery package (because Bootstrap expects it to be a global variable) + new webpack.ContextReplacementPlugin(/\@angular\b.*\b(bundles|linker)/, path.join(__dirname, './ClientApp')), // Workaround for https://github.com/angular/angular/issues/11580 + new webpack.ContextReplacementPlugin(/angular(\\|\/)core(\\|\/)@angular/, path.join(__dirname, './ClientApp')), // Workaround for https://github.com/angular/angular/issues/14898 + new webpack.IgnorePlugin(/^vertx$/) // Workaround for https://github.com/stefanpenner/es6-promise/issues/100 + ] + }; + + const clientBundleConfig = merge(sharedConfig, { + entry: { + // To keep development builds fast, include all vendor dependencies in the vendor bundle. + // But for production builds, leave the tree-shakable ones out so the AOT compiler can produce a smaller bundle. + vendor: isDevBuild ? allModules : nonTreeShakableModules + }, + output: { path: path.join(__dirname, 'wwwroot', 'dist') }, + module: { + rules: [ + { test: /\.css(\?|$)/, use: extractCSS.extract({ use: isDevBuild ? 'css-loader' : 'css-loader?minimize' }) } + ] + }, + plugins: [ + extractCSS, + new webpack.DllPlugin({ + path: path.join(__dirname, 'wwwroot', 'dist', '[name]-manifest.json'), + name: '[name]_[hash]' + }) + ].concat(isDevBuild ? [] : [ + new webpack.optimize.UglifyJsPlugin() + ]) + }); + + const serverBundleConfig = merge(sharedConfig, { + target: 'node', + resolve: { mainFields: ['main'] }, + entry: { vendor: allModules.concat(['aspnet-prerendering']) }, + output: { + path: path.join(__dirname, 'ClientApp', 'dist'), + libraryTarget: 'commonjs2', + }, + module: { + rules: [ { test: /\.css(\?|$)/, use: ['to-string-loader', isDevBuild ? 'css-loader' : 'css-loader?minimize' ] } ] + }, + plugins: [ + new webpack.DllPlugin({ + path: path.join(__dirname, 'ClientApp', 'dist', '[name]-manifest.json'), + name: '[name]_[hash]' + }) + ] + }); + + return [clientBundleConfig, serverBundleConfig]; +}