├── .angular-cli.json
├── .editorconfig
├── .gitignore
├── README.md
├── app1.server.ts
├── app2.server.ts
├── e2e
├── app1
│ ├── app.e2e-spec.ts
│ ├── app.po.ts
│ └── tsconfig.e2e.json
└── app2
│ ├── app.e2e-spec.ts
│ ├── app.po.ts
│ └── tsconfig.e2e.json
├── karma.conf.js
├── package-lock.json
├── package.json
├── protractor.conf.js
├── scripts
├── update.js
├── verify.js
└── versions
│ └── 1.3.2.json
├── src
├── app1.test.ts
├── app1
│ ├── app
│ │ ├── app.component.css
│ │ ├── app.component.html
│ │ ├── app.component.ts
│ │ ├── app.module.ts
│ │ ├── app.server.module.ts
│ │ └── views
│ │ │ └── default
│ │ │ ├── default.component.css
│ │ │ ├── default.component.html
│ │ │ ├── default.component.spec.ts
│ │ │ ├── default.component.ts
│ │ │ └── default.module.ts
│ ├── assets
│ │ └── .gitkeep
│ ├── environments
│ │ ├── environment.prod.ts
│ │ └── environment.ts
│ ├── favicon.ico
│ ├── index.html
│ ├── main.server.ts
│ ├── main.ts
│ └── styles.scss
├── app2.test.ts
├── app2
│ ├── app
│ │ ├── app.component.css
│ │ ├── app.component.html
│ │ ├── app.component.ts
│ │ ├── app.module.ts
│ │ ├── app.server.module.ts
│ │ └── views
│ │ │ └── default
│ │ │ ├── default.component.css
│ │ │ ├── default.component.html
│ │ │ ├── default.component.spec.ts
│ │ │ ├── default.component.ts
│ │ │ └── default.module.ts
│ ├── environments
│ │ ├── environment.prod.ts
│ │ └── environment.ts
│ ├── favicon.ico
│ ├── index.html
│ ├── main.server.ts
│ ├── main.ts
│ └── styles.scss
├── shared
│ ├── assets
│ │ └── .gitkeep
│ ├── components
│ │ ├── angular-cli
│ │ │ ├── angular-cli.css
│ │ │ ├── angular-cli.html
│ │ │ ├── angular-cli.module.ts
│ │ │ ├── angular-cli.spec.ts
│ │ │ └── angular-cli.ts
│ │ ├── example1
│ │ │ ├── example1.css
│ │ │ ├── example1.html
│ │ │ ├── example1.module.ts
│ │ │ ├── example1.spec.ts
│ │ │ └── example1.ts
│ │ └── example2
│ │ │ ├── example2.css
│ │ │ ├── example2.html
│ │ │ ├── example2.module.ts
│ │ │ ├── example2.spec.ts
│ │ │ └── example2.ts
│ ├── other
│ │ ├── polyfills.ts
│ │ └── styles.scss
│ └── package.json
├── test.ts
├── tsconfig.app1.json
├── tsconfig.app1.server.json
├── tsconfig.app2.json
├── tsconfig.app2.server.json
├── tsconfig.spec.json
└── typings.d.ts
├── tsconfig.json
├── tslint.json
├── webpack.app1.server.config.js
└── webpack.app2.server.config.js
/.angular-cli.json:
--------------------------------------------------------------------------------
1 | {
2 | "$schema": "./node_modules/@angular/cli/lib/config/schema.json",
3 | "project": {
4 | "name": "angular-cli-library"
5 | },
6 | "apps": [
7 | {
8 | "name": "app1-browser",
9 | "root": "src",
10 | "outDir": "dist/app1-browser",
11 | "assets": [
12 | { "glob": "**/*", "input": "app1/assets/", "output": "./assets/" },
13 | { "glob": "favicon.ico", "input": "app1/", "output": "./" },
14 | { "glob": "**/*", "input": "shared/assets", "output": "./assets/" }
15 | ],
16 | "index": "app1/index.html",
17 | "deployUrl": "./",
18 | "platform": "browser",
19 | "main": "app1/main.ts",
20 | "polyfills": "shared/other/polyfills.ts",
21 | "test": "app1.test.ts",
22 | "tsconfig": "tsconfig.app1.json",
23 | "testTsconfig": "tsconfig.spec.json",
24 | "prefix": "app1",
25 | "styles": [
26 | "app1/styles.scss",
27 | "shared/other/styles.scss"
28 | ],
29 | "scripts": [],
30 | "environmentSource": "app1/environments/environment.ts",
31 | "environments": {
32 | "dev": "app1/environments/environment.ts",
33 | "prod": "app1/environments/environment.prod.ts"
34 | }
35 | },{
36 | "name": "app1-server",
37 | "root": "src",
38 | "outDir": "dist/app1-server",
39 | "assets": [
40 | { "glob": "**/*", "input": "app1/assets/", "output": "./assets/" },
41 | { "glob": "favicon.ico", "input": "app1/", "output": "./" },
42 | { "glob": "**/*", "input": "shared/assets", "output": "./assets/" }
43 | ],
44 | "index": "app1/index.html",
45 | "deployUrl": "./",
46 | "platform": "server",
47 | "main": "app1/main.server.ts",
48 | "test": "app1.test.ts",
49 | "tsconfig": "tsconfig.app1.server.json",
50 | "testTsconfig": "tsconfig.spec.json",
51 | "prefix": "app1",
52 | "styles": [
53 | "app1/styles.scss",
54 | "shared/other/styles.scss"
55 | ],
56 | "scripts": [],
57 | "environmentSource": "app1/environments/environment.ts",
58 | "environments": {
59 | "dev": "app1/environments/environment.ts",
60 | "prod": "app1/environments/environment.prod.ts"
61 | }
62 | },
63 | {
64 | "name": "app2-browser",
65 | "root": "src",
66 | "outDir": "dist/app2-browser",
67 | "assets": [
68 | { "glob": "**/*", "input": "app2/assets/", "output": "./assets/" },
69 | { "glob": "favicon.ico", "input": "app2/", "output": "./" },
70 | { "glob": "**/*", "input": "../node_modules/angular-cli-library/assets", "output": "./assets/" }
71 | ],
72 | "index": "app2/index.html",
73 | "deployUrl": "./",
74 | "platform": "browser",
75 | "main": "app2/main.ts",
76 | "polyfills": "../node_modules/angular-cli-library/other/polyfills.ts",
77 | "test": "app2.test.ts",
78 | "tsconfig": "tsconfig.app2.json",
79 | "testTsconfig": "tsconfig.spec.json",
80 | "prefix": "app2",
81 | "styles": [
82 | "app2/styles.scss",
83 | "../node_modules/angular-cli-library/other/styles.scss"
84 | ],
85 | "scripts": [],
86 | "environmentSource": "app2/environments/environment.ts",
87 | "environments": {
88 | "dev": "app2/environments/environment.ts",
89 | "prod": "app2/environments/environment.prod.ts"
90 | }
91 | },{
92 | "name": "app2-server",
93 | "root": "src",
94 | "outDir": "dist/app2-server",
95 | "assets": [
96 | { "glob": "**/*", "input": "app2/assets/", "output": "./assets/" },
97 | { "glob": "favicon.ico", "input": "app2/", "output": "./" },
98 | { "glob": "**/*", "input": "../node_modules/angular-cli-library/assets", "output": "./assets/" }
99 | ],
100 | "index": "app2/index.html",
101 | "deployUrl": "./",
102 | "platform": "server",
103 | "main": "app2/main.server.ts",
104 | "test": "app2.test.ts",
105 | "tsconfig": "tsconfig.app2.server.json",
106 | "testTsconfig": "tsconfig.spec.json",
107 | "prefix": "app2",
108 | "styles": [
109 | "app2/styles.scss",
110 | "../node_modules/angular-cli-library/other/styles.scss"
111 | ],
112 | "scripts": [],
113 | "environmentSource": "app2/environments/environment.ts",
114 | "environments": {
115 | "dev": "app2/environments/environment.ts",
116 | "prod": "app2/environments/environment.prod.ts"
117 | }
118 | }
119 | ],
120 | "e2e": {
121 | "protractor": {
122 | "config": "./protractor.conf.js"
123 | }
124 | },
125 | "lint": [
126 | {
127 | "project": "src/tsconfig.app.json",
128 | "exclude": "**/node_modules/**"
129 | },
130 | {
131 | "project": "src/tsconfig.spec.json",
132 | "exclude": "**/node_modules/**"
133 | },
134 | {
135 | "project": "e2e/tsconfig.e2e.json",
136 | "exclude": "**/node_modules/**"
137 | }
138 | ],
139 | "test": {
140 | "karma": {
141 | "config": "./karma.conf.js"
142 | }
143 | },
144 | "defaults": {
145 | "styleExt": "css",
146 | "component": {}
147 | }
148 | }
149 |
--------------------------------------------------------------------------------
/.editorconfig:
--------------------------------------------------------------------------------
1 | # Editor configuration, see http://editorconfig.org
2 | root = true
3 |
4 | [*]
5 | charset = utf-8
6 | indent_style = space
7 | indent_size = 2
8 | insert_final_newline = true
9 | trim_trailing_whitespace = true
10 |
11 | [*.md]
12 | max_line_length = off
13 | trim_trailing_whitespace = false
14 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # See http://help.github.com/ignore-files/ for more about ignoring files.
2 |
3 | # compiled output
4 | /dist
5 | /tmp
6 | /out-tsc
7 |
8 | # dependencies
9 | /node_modules
10 |
11 | # IDEs and editors
12 | /.idea
13 | .project
14 | .classpath
15 | .c9/
16 | *.launch
17 | .settings/
18 | *.sublime-workspace
19 |
20 | # IDE - VSCode
21 | .vscode/*
22 | !.vscode/settings.json
23 | !.vscode/tasks.json
24 | !.vscode/launch.json
25 | !.vscode/extensions.json
26 |
27 | # misc
28 | /.sass-cache
29 | /connect.lock
30 | /coverage
31 | /libpeerconnection.log
32 | npm-debug.log
33 | testem.log
34 | /typings
35 | yarn-error.log
36 |
37 | # e2e
38 | /e2e/*.js
39 | /e2e/*.map
40 |
41 | # System Files
42 | .DS_Store
43 | Thumbs.db
44 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Angular CLI with Library support (1.5.4)
2 |
3 | This project was generated with [Angular CLI](https://github.com/angular/angular-cli). It is an extended version of a new app generated with ng new. It adds Library support for multiple apps in a mono-repo.
4 |
5 | This starter is a result of many workarounds in order to make angular-cli work with a shared library of components/services/modules etc.
6 |
7 | Currently supports:
8 |
9 | * Library can be published and imported from npm registry (supports lazy loading and aot, Example2)
10 | * Serving multiple apps at the same time
11 | * Production build of multiple apps (with AOT)
12 | * Shared Library of components/modules ( can be shared between each app with `@shared/` )
13 | * Shared assets folder and polyfills. ( can be shared between each app )
14 | * Shared SCSS. ( can be shared between each app )
15 | * lazy loading of Shared modules
16 | * Shared modules can lazy load other Shared modules ( with/without routes )
17 | * Unit tests for each app
18 | * E2E tests for each app
19 | * Custom commands to make your life easier
20 | * Universal Integration for multiple apps (need to install webpack for local serve `npm install -g webpack`)
21 |
22 | and everything else you would normally be able to do with an app generated with ng new.
23 |
24 | Feel free to ask questions, provide feedback, submit ideas, requests or create an issue.
25 |
26 | Star and support this project if you like it, to help it stay alive and maybe even be added as a boilerplate/starter to angular-cli (e.x. ng new app-name --template library).
27 |
28 | ## Versioning
29 |
30 | Versioning of this project will follow the same with Angular-cli. There will be a separate branch that will be working for each version (starting with 1.2.7)
31 |
32 | ## How to use this Starter
33 |
34 | Just git clone this repo and start using it (run `npm install` after). The result would be the same if you had created a new app with Angular-CLI (ng new) having made all the necessary changes so that you can use multiple apps with a shared Library of components and have extra functionality.
35 |
36 | ## Examples
37 |
38 | The repo also includes examples of some use cases to help you out:
39 |
40 | 0. AngularCLI: `AngularCLI` module is lazy loaded from the shared Libary (@shared) as a component/module of the default view/route.
41 | 1. Example1: In example 1 `Example1` module is lazy loaded from the shared Libary (@shared) as a view/route.
42 | 2. Example2: In example 2, the lazy loaded shared module `Example1` lazy loads another shared module `Example2`. Also `AngularCLI` module is lazily loaded and imported from the angular-cli-library (npm registry)
43 |
44 | ## Commands
45 |
46 | #### Development server
47 |
48 | * Run `npm run app1` to serve app1 (runs `ng serve --app app1 --port 4200`)
49 | * Run `npm run app2` to serve app2 etc. (runs `ng serve --app app2 --port 4201`)
50 |
51 | Names can change if you want (package.json). You can have multiple apps running in your browser as each app is launched on a different port. Navigate to `http://localhost:4200/` or `http://localhost:4201/` for example. Each app will automatically reload if you change any of the source files (if you edit your shared library both apps will reload if they are using it).
52 |
53 | #### Library
54 |
55 | * Run `npm run library:publish` to publish your library to npm registry. It is the same as running `npm publish` in `src/shared` folder.
56 |
57 | #### Build
58 |
59 | * Run `npm run app1:build` to build app1. (runs `ng build --app app1 --prod --build-optimizer`)
60 | * Run `npm run app2:build` to build app2 etc. (runs `ng build --app app2 --prod --build-optimizer`)
61 |
62 | The build artifacts will be stored in the `dist/app1` or `dist/app2` directory. All builds are for production ( --prod ).
63 |
64 | #### Code scaffolding
65 |
66 | Run `ng generate component component-name` to generate a new component. To add a component to app1 specify app.module as in the following example: `ng g component default --module ../app.module.ts`. You can also use `ng generate directive|pipe|service|class|guard|interface|enum|module`.
67 |
68 | #### Running unit tests
69 |
70 | * Run `npm run app1:test` to run *.spec.ts tests in app1 folder. (runs `ng test --app app1`)
71 | * Run `npm run app2:test` to run *.spec.ts tests in app2 folder. (runs `ng test --app app2`)
72 |
73 | #### Running end-to-end tests
74 |
75 | * Run `npm run app1:e2e` to run e2e tests from e2e/app1 folder. (runs `ng e2e --app app1`)
76 | * Run `npm run app2:e2e` to run e2e tests from e2e/app2 folder. (runs `ng e2e --app app2`)
77 |
78 | #### Further help
79 |
80 | To get more help on the Angular CLI use `ng help` or go check out the [Angular CLI README](https://github.com/angular/angular-cli/blob/master/README.md).
81 |
--------------------------------------------------------------------------------
/app1.server.ts:
--------------------------------------------------------------------------------
1 | // These are important and needed before anything else
2 | import 'zone.js/dist/zone-node';
3 | import 'reflect-metadata';
4 |
5 | import { renderModuleFactory } from '@angular/platform-server';
6 | import { enableProdMode } from '@angular/core';
7 |
8 | import * as express from 'express';
9 | import { join } from 'path';
10 | import { readFileSync } from 'fs';
11 |
12 | // Faster server renders w/ Prod mode (dev mode never needed)
13 | enableProdMode();
14 |
15 | // Express server
16 | const app = express();
17 |
18 | const PORT = process.env.PORT || 4000;
19 | const DIST_FOLDER = join(process.cwd(), './dist');
20 |
21 | // Our index.html we'll use as our template
22 | const template = readFileSync(join(DIST_FOLDER, 'app1-browser', 'index.html')).toString();
23 |
24 | // * NOTE :: leave this as require() since this file is built Dynamically from webpack
25 | const { AppServerModuleNgFactory, LAZY_MODULE_MAP } = require('./dist/app1-server/main.bundle');
26 |
27 | const { provideModuleMap } = require('@nguniversal/module-map-ngfactory-loader');
28 |
29 | app.engine('html', (_, options, callback) => {
30 | renderModuleFactory(AppServerModuleNgFactory, {
31 | // Our index.html
32 | document: template,
33 | url: options.req.url,
34 | // DI so that we can get lazy-loading to work differently (since we need it to just instantly render it)
35 | extraProviders: [
36 | provideModuleMap(LAZY_MODULE_MAP)
37 | ]
38 | }).then(html => {
39 | callback(null, html);
40 | });
41 | });
42 |
43 | app.set('view engine', 'html');
44 | app.set('views', join(DIST_FOLDER, 'app1-browser'));
45 |
46 | // Server static files from /browser
47 | app.get('*.*', express.static(join(DIST_FOLDER, 'app1-browser')));
48 |
49 | // All regular routes use the Universal engine
50 | app.get('*', (req, res) => {
51 | res.render(join(DIST_FOLDER, 'app1-browser', 'index.html'), { req });
52 | });
53 |
54 | // Start up the Node server
55 | app.listen(PORT, () => {
56 | console.log(`Node server listening on http://localhost:${PORT}`);
57 | });
--------------------------------------------------------------------------------
/app2.server.ts:
--------------------------------------------------------------------------------
1 | // These are important and needed before anything else
2 | import 'zone.js/dist/zone-node';
3 | import 'reflect-metadata';
4 |
5 | import { renderModuleFactory } from '@angular/platform-server';
6 | import { enableProdMode } from '@angular/core';
7 |
8 | import * as express from 'express';
9 | import { join } from 'path';
10 | import { readFileSync } from 'fs';
11 |
12 | // Faster server renders w/ Prod mode (dev mode never needed)
13 | enableProdMode();
14 |
15 | // Express server
16 | const app = express();
17 |
18 | const PORT = process.env.PORT || 4000;
19 | const DIST_FOLDER = join(process.cwd(), './dist');
20 |
21 | // Our index.html we'll use as our template
22 | const template = readFileSync(join(DIST_FOLDER, 'app2-browser', 'index.html')).toString();
23 |
24 | // * NOTE :: leave this as require() since this file is built Dynamically from webpack
25 | const { AppServerModuleNgFactory, LAZY_MODULE_MAP } = require('./dist/app2-server/main.bundle');
26 |
27 | const { provideModuleMap } = require('@nguniversal/module-map-ngfactory-loader');
28 |
29 | app.engine('html', (_, options, callback) => {
30 | renderModuleFactory(AppServerModuleNgFactory, {
31 | // Our index.html
32 | document: template,
33 | url: options.req.url,
34 | // DI so that we can get lazy-loading to work differently (since we need it to just instantly render it)
35 | extraProviders: [
36 | provideModuleMap(LAZY_MODULE_MAP)
37 | ]
38 | }).then(html => {
39 | callback(null, html);
40 | });
41 | });
42 |
43 | app.set('view engine', 'html');
44 | app.set('views', join(DIST_FOLDER, 'app2-browser'));
45 |
46 | // Server static files from /browser
47 | app.get('*.*', express.static(join(DIST_FOLDER, 'app2-browser')));
48 |
49 | // All regular routes use the Universal engine
50 | app.get('*', (req, res) => {
51 | res.render(join(DIST_FOLDER, 'app2-browser', 'index.html'), { req });
52 | });
53 |
54 | // Start up the Node server
55 | app.listen(PORT, () => {
56 | console.log(`Node server listening on http://localhost:${PORT}`);
57 | });
--------------------------------------------------------------------------------
/e2e/app1/app.e2e-spec.ts:
--------------------------------------------------------------------------------
1 | import { AngularCliLibraryPage } from './app.po';
2 |
3 | describe('App1 ', () => {
4 | let page: AngularCliLibraryPage;
5 |
6 | beforeEach(() => {
7 | page = new AngularCliLibraryPage();
8 | });
9 |
10 | it('should display welcome message', () => {
11 | page.navigateTo();
12 | expect(page.getParagraphText()).toEqual('Welcome to an extended version of a new app generated with ng new! This example uses a shared component/module between multiple apps!!');
13 | });
14 | });
15 |
--------------------------------------------------------------------------------
/e2e/app1/app.po.ts:
--------------------------------------------------------------------------------
1 | import { browser, by, element } from 'protractor';
2 |
3 | export class AngularCliLibraryPage {
4 | navigateTo() {
5 | return browser.get('/');
6 | }
7 |
8 | getParagraphText() {
9 | return element(by.css('app-root h1')).getText();
10 | }
11 | }
12 |
--------------------------------------------------------------------------------
/e2e/app1/tsconfig.e2e.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "../../tsconfig.json",
3 | "compilerOptions": {
4 | "outDir": "../../out-tsc/e2e",
5 | "baseUrl": ".",
6 | "module": "commonjs",
7 | "target": "es5",
8 | "types": [
9 | "jasmine",
10 | "jasminewd2",
11 | "node"
12 | ]
13 | }
14 | }
15 |
--------------------------------------------------------------------------------
/e2e/app2/app.e2e-spec.ts:
--------------------------------------------------------------------------------
1 | import { AngularCliLibraryPage } from './app.po';
2 |
3 | describe('App2 ', () => {
4 | let page: AngularCliLibraryPage;
5 |
6 | beforeEach(() => {
7 | page = new AngularCliLibraryPage();
8 | });
9 |
10 | it('should display welcome message', () => {
11 | page.navigateTo();
12 | expect(page.getParagraphText()).toEqual('Welcome to an extended version of a new app generated with ng new! This example uses a shared component/module between multiple apps!!');
13 | });
14 | });
15 |
--------------------------------------------------------------------------------
/e2e/app2/app.po.ts:
--------------------------------------------------------------------------------
1 | import { browser, by, element } from 'protractor';
2 |
3 | export class AngularCliLibraryPage {
4 | navigateTo() {
5 | return browser.get('/');
6 | }
7 |
8 | getParagraphText() {
9 | return element(by.css('app-root h1')).getText();
10 | }
11 | }
12 |
--------------------------------------------------------------------------------
/e2e/app2/tsconfig.e2e.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "../../tsconfig.json",
3 | "compilerOptions": {
4 | "outDir": "../../out-tsc/e2e",
5 | "baseUrl": ".",
6 | "module": "commonjs",
7 | "target": "es5",
8 | "types": [
9 | "jasmine",
10 | "jasminewd2",
11 | "node"
12 | ]
13 | }
14 | }
15 |
--------------------------------------------------------------------------------
/karma.conf.js:
--------------------------------------------------------------------------------
1 | // Karma configuration file, see link for more information
2 | // https://karma-runner.github.io/0.13/config/configuration-file.html
3 |
4 | module.exports = function (config) {
5 | config.set({
6 | basePath: '',
7 | frameworks: ['jasmine', '@angular/cli'],
8 | plugins: [
9 | require('karma-jasmine'),
10 | require('karma-chrome-launcher'),
11 | require('karma-jasmine-html-reporter'),
12 | require('karma-coverage-istanbul-reporter'),
13 | require('@angular/cli/plugins/karma')
14 | ],
15 | client:{
16 | clearContext: false // leave Jasmine Spec Runner output visible in browser
17 | },
18 | coverageIstanbulReporter: {
19 | reports: [ 'html', 'lcovonly' ],
20 | fixWebpackSourcePaths: true
21 | },
22 | angularCli: {
23 | environment: 'dev'
24 | },
25 | reporters: ['progress', 'kjhtml'],
26 | port: 9876,
27 | colors: true,
28 | logLevel: config.LOG_INFO,
29 | autoWatch: true,
30 | browsers: ['Chrome'],
31 | singleRun: false
32 | });
33 | };
34 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "angular-cli-library",
3 | "version": "1.5.4",
4 | "license": "MIT",
5 | "scripts": {
6 | "ng": "ng",
7 | "start": "ng serve",
8 | "build": "ng build",
9 | "test": "ng test",
10 | "lint": "ng lint",
11 | "e2e": "ng e2e",
12 | "library:publish": "npm publish src/shared",
13 | "update": "node scripts/update.js",
14 | "verify": "node scripts/verify.js",
15 | "app1": "ng serve --app app1-browser --port 4200",
16 | "app2": "ng serve --app app2-browser --port 4201",
17 | "app1:build": "ng build --app app1-browser --prod --build-optimizer",
18 | "app2:build": "ng build --app app2-browser --prod --build-optimizer",
19 | "app1:ssr": "npm run app1:build && npm run app1:ssr:build && webpack --config webpack.app1.server.config.js --progress --colors && node dist/app1-server/server.js",
20 | "app2:ssr": "npm run app2:build && npm run app2:ssr:build && webpack --config webpack.app2.server.config.js --progress --colors && node dist/app2-server/server.js",
21 | "app1:ssr:build": "ng build --app app1-server --prod --output-hashing=false",
22 | "app2:ssr:build": "ng build --app app2-server --prod --output-hashing=false",
23 | "app1:test": "ng test --app app1",
24 | "app2:test": "ng test --app app2",
25 | "app1:e2e": "ng e2e --app app1",
26 | "app2:e2e": "ng e2e --app app2"
27 | },
28 | "private": true,
29 | "dependencies": {
30 | "@angular/animations": "5.0.3",
31 | "@angular/common": "5.0.3",
32 | "@angular/compiler": "5.0.3",
33 | "@angular/core": "5.0.3",
34 | "@angular/forms": "5.0.3",
35 | "@angular/http": "5.0.3",
36 | "@angular/platform-browser": "5.0.3",
37 | "@angular/platform-browser-dynamic": "5.0.3",
38 | "@angular/platform-server": "5.0.3",
39 | "@angular/router": "5.0.3",
40 | "@nguniversal/module-map-ngfactory-loader": "5.0.0-beta.5",
41 | "angular-cli-library": "1.3.2",
42 | "core-js": "2.5.1",
43 | "rxjs": "5.5.2",
44 | "ts-loader": "3.1.1",
45 | "@types/node": "8.0.53",
46 | "zone.js": "0.8.18"
47 | },
48 | "devDependencies": {
49 | "@angular/cli": "1.5.4",
50 | "@angular/compiler-cli": "5.0.3",
51 | "@angular/language-service": "5.0.3",
52 | "@types/jasmine": "2.8.2",
53 | "@types/jasminewd2": "2.0.3",
54 | "@types/node": "8.0.53",
55 | "codelyzer": "4.0.1",
56 | "jasmine-core": "2.8.0",
57 | "jasmine-spec-reporter": "4.2.1",
58 | "karma": "1.7.1",
59 | "karma-chrome-launcher": "2.2.0",
60 | "karma-cli": "1.0.1",
61 | "karma-coverage-istanbul-reporter": "1.3.0",
62 | "karma-jasmine": "1.1.0",
63 | "karma-jasmine-html-reporter": "0.2.2",
64 | "protractor": "5.2.0",
65 | "ts-node": "3.3.0",
66 | "tslint": "5.8.0",
67 | "typescript": "2.4.2"
68 | }
69 | }
70 |
--------------------------------------------------------------------------------
/protractor.conf.js:
--------------------------------------------------------------------------------
1 | // Protractor configuration file, see link for more information
2 | // https://github.com/angular/protractor/blob/master/lib/config.ts
3 |
4 | const { SpecReporter } = require('jasmine-spec-reporter');
5 |
6 | var argv = require('minimist')(process.argv.slice(2));
7 | var path = './e2e/';
8 | if(argv.app){
9 | path += argv.app;
10 | }
11 |
12 | exports.config = {
13 | allScriptsTimeout: 11000,
14 | specs: [
15 | path + '/**/*.e2e-spec.ts'
16 | ],
17 | capabilities: {
18 | 'browserName': 'chrome'
19 | },
20 | directConnect: true,
21 | baseUrl: 'http://localhost:4200/',
22 | framework: 'jasmine',
23 | jasmineNodeOpts: {
24 | showColors: true,
25 | defaultTimeoutInterval: 30000,
26 | print: function() {}
27 | },
28 | onPrepare() {
29 | console.log(path);
30 | require('ts-node').register({
31 | project: path + '/tsconfig.e2e.json'
32 | });
33 | jasmine.getEnv().addReporter(new SpecReporter({ spec: { displayStacktrace: true } }));
34 | }
35 | };
36 |
--------------------------------------------------------------------------------
/scripts/update.js:
--------------------------------------------------------------------------------
1 |
2 | var latest_version = '1.3.2'
3 |
4 | var readline = require('readline');
5 |
6 | var rl = readline.createInterface({
7 | input: process.stdin,
8 | output: process.stdout
9 | });
10 | console.log('Latest version is:' + latest_version);
11 | rl.question('Upgrade to latest version? (y/n) ', function(answer) {
12 | if(answer == 'y' || answer == 'Y'){
13 | console.log('Updating project to latest version...');
14 | } else {
15 |
16 | }
17 | rl.close();
18 | });
--------------------------------------------------------------------------------
/scripts/verify.js:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/scripts/verify.js
--------------------------------------------------------------------------------
/scripts/versions/1.3.2.json:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/scripts/versions/1.3.2.json
--------------------------------------------------------------------------------
/src/app1.test.ts:
--------------------------------------------------------------------------------
1 | // This file is required by karma.conf.js and loads recursively all the .spec and framework files
2 |
3 | import 'zone.js/dist/long-stack-trace-zone';
4 | import 'zone.js/dist/proxy.js';
5 | import 'zone.js/dist/sync-test';
6 | import 'zone.js/dist/jasmine-patch';
7 | import 'zone.js/dist/async-test';
8 | import 'zone.js/dist/fake-async-test';
9 | import { getTestBed } from '@angular/core/testing';
10 | import {
11 | BrowserDynamicTestingModule,
12 | platformBrowserDynamicTesting
13 | } from '@angular/platform-browser-dynamic/testing';
14 |
15 | // Unfortunately there's no typing for the `__karma__` variable. Just declare it as any.
16 | declare const __karma__: any;
17 | declare const require: any;
18 |
19 | // Prevent Karma from running prematurely.
20 | __karma__.loaded = function () {};
21 |
22 | // First, initialize the Angular testing environment.
23 | getTestBed().initTestEnvironment(
24 | BrowserDynamicTestingModule,
25 | platformBrowserDynamicTesting()
26 | );
27 | // Then we find all the tests.
28 | const context = require.context('./app1', true, /\.spec\.ts$/);
29 | // And load the modules.
30 | context.keys().map(context);
31 | // Finally, start Karma to run the tests.
32 | __karma__.start();
33 |
--------------------------------------------------------------------------------
/src/app1/app/app.component.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/app1/app/app.component.css
--------------------------------------------------------------------------------
/src/app1/app/app.component.html:
--------------------------------------------------------------------------------
1 |
2 |
--------------------------------------------------------------------------------
/src/app1/app/app.component.ts:
--------------------------------------------------------------------------------
1 | import { Component } from '@angular/core';
2 |
3 | @Component({
4 | selector: 'app-root',
5 | templateUrl: './app.component.html',
6 | styleUrls: ['./app.component.css']
7 | })
8 | export class AppComponent {
9 | title = 'app';
10 | }
11 |
--------------------------------------------------------------------------------
/src/app1/app/app.module.ts:
--------------------------------------------------------------------------------
1 | import { RouterModule } from '@angular/router';
2 | import { BrowserModule } from '@angular/platform-browser';
3 | import { NgModule } from '@angular/core';
4 |
5 | import { AppComponent } from './app.component';
6 |
7 | @NgModule({
8 | declarations: [
9 | AppComponent
10 | ],
11 | imports: [
12 | BrowserModule.withServerTransition({appId: 'app1'}),
13 | RouterModule.forRoot([
14 | { path: '', loadChildren:'./views/default/default.module#DefaultModule'},
15 | { path: 'example1', loadChildren:'@shared/components/example1/example1.module#Example1Module'},
16 | ])
17 | ],
18 | providers: [],
19 | bootstrap: [AppComponent]
20 | })
21 | export class AppModule { }
22 |
--------------------------------------------------------------------------------
/src/app1/app/app.server.module.ts:
--------------------------------------------------------------------------------
1 | import { NgModule } from '@angular/core';
2 | import { ServerModule } from '@angular/platform-server';
3 |
4 | import { AppModule } from './app.module';
5 | import { AppComponent } from './app.component';
6 | import { ModuleMapLoaderModule } from '@nguniversal/module-map-ngfactory-loader';
7 |
8 | @NgModule({
9 | imports: [
10 | // The AppServerModule should import your AppModule followed
11 | // by the ServerModule from @angular/platform-server.
12 | AppModule,
13 | ServerModule,
14 | ModuleMapLoaderModule
15 | ],
16 | // Since the bootstrapped component is not inherited from your
17 | // imported AppModule, it needs to be repeated here.
18 | bootstrap: [AppComponent]
19 | })
20 | export class AppServerModule {}
--------------------------------------------------------------------------------
/src/app1/app/views/default/default.component.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/app1/app/views/default/default.component.css
--------------------------------------------------------------------------------
/src/app1/app/views/default/default.component.html:
--------------------------------------------------------------------------------
1 |
2 |
--------------------------------------------------------------------------------
/src/app1/app/views/default/default.component.spec.ts:
--------------------------------------------------------------------------------
1 | import { AngularCLIModule } from '@shared/components/angular-cli/angular-cli.module';
2 | import { async, ComponentFixture, TestBed } from '@angular/core/testing';
3 |
4 | import { DefaultComponent } from './default.component';
5 |
6 | describe('Default view of app1 ', () => {
7 | let component: DefaultComponent;
8 | let fixture: ComponentFixture;
9 |
10 | beforeEach(() => {
11 | TestBed.configureTestingModule({
12 | imports: [AngularCLIModule],
13 | declarations: [ DefaultComponent ]
14 | })
15 | .compileComponents();
16 |
17 | fixture = TestBed.createComponent(DefaultComponent);
18 | component = fixture.componentInstance;
19 | fixture.detectChanges();
20 | });
21 |
22 | it('should be created', () => {
23 | expect(component).toBeTruthy();
24 | });
25 | });
26 |
--------------------------------------------------------------------------------
/src/app1/app/views/default/default.component.ts:
--------------------------------------------------------------------------------
1 | import { Component, OnInit } from '@angular/core';
2 |
3 | @Component({
4 | selector: 'app1-default',
5 | templateUrl: './default.component.html',
6 | styleUrls: ['./default.component.css']
7 | })
8 | export class DefaultComponent implements OnInit {
9 |
10 | constructor() { }
11 |
12 | ngOnInit() {
13 | }
14 |
15 | }
16 |
--------------------------------------------------------------------------------
/src/app1/app/views/default/default.module.ts:
--------------------------------------------------------------------------------
1 | import { RouterModule } from '@angular/router';
2 | import { CommonModule } from '@angular/common';
3 | import { NgModule } from '@angular/core';
4 |
5 | import { DefaultComponent } from './default.component';
6 | import { AngularCLIModule } from "@shared/components/angular-cli/angular-cli.module";
7 |
8 | @NgModule({
9 | declarations: [
10 | DefaultComponent
11 | ],
12 | imports: [
13 | CommonModule,
14 | AngularCLIModule,
15 | RouterModule.forChild([
16 | { path: '', component:DefaultComponent},
17 | ])
18 | ]
19 | })
20 | export class DefaultModule { }
21 |
--------------------------------------------------------------------------------
/src/app1/assets/.gitkeep:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/app1/assets/.gitkeep
--------------------------------------------------------------------------------
/src/app1/environments/environment.prod.ts:
--------------------------------------------------------------------------------
1 | export const environment = {
2 | production: true
3 | };
4 |
--------------------------------------------------------------------------------
/src/app1/environments/environment.ts:
--------------------------------------------------------------------------------
1 | // The file contents for the current environment will overwrite these during build.
2 | // The build system defaults to the dev environment which uses `environment.ts`, but if you do
3 | // `ng build --env=prod` then `environment.prod.ts` will be used instead.
4 | // The list of which env maps to which file can be found in `.angular-cli.json`.
5 |
6 | export const environment = {
7 | production: false
8 | };
9 |
--------------------------------------------------------------------------------
/src/app1/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/app1/favicon.ico
--------------------------------------------------------------------------------
/src/app1/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Angular CLI with Library (app1)
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/src/app1/main.server.ts:
--------------------------------------------------------------------------------
1 | export { AppServerModule } from './app/app.server.module';
--------------------------------------------------------------------------------
/src/app1/main.ts:
--------------------------------------------------------------------------------
1 | import { enableProdMode } from '@angular/core';
2 | import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
3 |
4 | import { AppModule } from './app/app.module';
5 | import { environment } from './environments/environment';
6 |
7 | if (environment.production) {
8 | enableProdMode();
9 | }
10 |
11 | platformBrowserDynamic().bootstrapModule(AppModule);
12 |
--------------------------------------------------------------------------------
/src/app1/styles.scss:
--------------------------------------------------------------------------------
1 | /* You can add global styles to this file, and also import other style files */
2 |
--------------------------------------------------------------------------------
/src/app2.test.ts:
--------------------------------------------------------------------------------
1 | // This file is required by karma.conf.js and loads recursively all the .spec and framework files
2 |
3 | import 'zone.js/dist/long-stack-trace-zone';
4 | import 'zone.js/dist/proxy.js';
5 | import 'zone.js/dist/sync-test';
6 | import 'zone.js/dist/jasmine-patch';
7 | import 'zone.js/dist/async-test';
8 | import 'zone.js/dist/fake-async-test';
9 | import { getTestBed } from '@angular/core/testing';
10 | import {
11 | BrowserDynamicTestingModule,
12 | platformBrowserDynamicTesting
13 | } from '@angular/platform-browser-dynamic/testing';
14 |
15 | // Unfortunately there's no typing for the `__karma__` variable. Just declare it as any.
16 | declare const __karma__: any;
17 | declare const require: any;
18 |
19 | // Prevent Karma from running prematurely.
20 | __karma__.loaded = function () {};
21 |
22 | // First, initialize the Angular testing environment.
23 | getTestBed().initTestEnvironment(
24 | BrowserDynamicTestingModule,
25 | platformBrowserDynamicTesting()
26 | );
27 | // Then we find all the tests.
28 | const context = require.context('./app2', true, /\.spec\.ts$/);
29 | // And load the modules.
30 | context.keys().map(context);
31 | // Finally, start Karma to run the tests.
32 | __karma__.start();
33 |
--------------------------------------------------------------------------------
/src/app2/app/app.component.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/app2/app/app.component.css
--------------------------------------------------------------------------------
/src/app2/app/app.component.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
--------------------------------------------------------------------------------
/src/app2/app/app.component.ts:
--------------------------------------------------------------------------------
1 | import { Component } from '@angular/core';
2 |
3 | @Component({
4 | selector: 'app-root',
5 | templateUrl: './app.component.html',
6 | styleUrls: ['./app.component.css']
7 | })
8 | export class AppComponent {
9 |
10 | }
11 |
--------------------------------------------------------------------------------
/src/app2/app/app.module.ts:
--------------------------------------------------------------------------------
1 | import { RouterModule } from '@angular/router';
2 | import { BrowserModule } from '@angular/platform-browser';
3 | import { NgModule } from '@angular/core';
4 |
5 | import { AppComponent } from './app.component';
6 |
7 | @NgModule({
8 | declarations: [
9 | AppComponent
10 | ],
11 | imports: [
12 | BrowserModule.withServerTransition({appId: 'app2'}),
13 | RouterModule.forRoot([
14 | { path: '', loadChildren:'./views/default/default.module#DefaultModule'},
15 | { path: 'example1', loadChildren:'@angular-cli-library/components/example1/example1.module#Example1Module'},
16 | ])
17 | ],
18 | providers: [],
19 | bootstrap: [AppComponent]
20 | })
21 | export class AppModule { }
22 |
--------------------------------------------------------------------------------
/src/app2/app/app.server.module.ts:
--------------------------------------------------------------------------------
1 | import { NgModule } from '@angular/core';
2 | import { ServerModule } from '@angular/platform-server';
3 |
4 | import { AppModule } from './app.module';
5 | import { AppComponent } from './app.component';
6 | import { ModuleMapLoaderModule } from '@nguniversal/module-map-ngfactory-loader';
7 |
8 | @NgModule({
9 | imports: [
10 | // The AppServerModule should import your AppModule followed
11 | // by the ServerModule from @angular/platform-server.
12 | AppModule,
13 | ServerModule,
14 | ModuleMapLoaderModule
15 | ],
16 | // Since the bootstrapped component is not inherited from your
17 | // imported AppModule, it needs to be repeated here.
18 | bootstrap: [AppComponent]
19 | })
20 | export class AppServerModule {}
--------------------------------------------------------------------------------
/src/app2/app/views/default/default.component.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/app2/app/views/default/default.component.css
--------------------------------------------------------------------------------
/src/app2/app/views/default/default.component.html:
--------------------------------------------------------------------------------
1 |
2 |
--------------------------------------------------------------------------------
/src/app2/app/views/default/default.component.spec.ts:
--------------------------------------------------------------------------------
1 | import { AngularCLIModule } from '@shared/components/angular-cli/angular-cli.module';
2 | import { async, ComponentFixture, TestBed } from '@angular/core/testing';
3 |
4 | import { DefaultComponent } from './default.component';
5 |
6 | describe('Default view of app2 ', () => {
7 | let component: DefaultComponent;
8 | let fixture: ComponentFixture;
9 |
10 | beforeEach(() => {
11 | TestBed.configureTestingModule({
12 | imports: [AngularCLIModule],
13 | declarations: [ DefaultComponent ]
14 | })
15 | .compileComponents();
16 |
17 | fixture = TestBed.createComponent(DefaultComponent);
18 | component = fixture.componentInstance;
19 | fixture.detectChanges();
20 | });
21 |
22 | it('should be created', () => {
23 | expect(component).toBeTruthy();
24 | });
25 | });
26 |
--------------------------------------------------------------------------------
/src/app2/app/views/default/default.component.ts:
--------------------------------------------------------------------------------
1 | import { Component, OnInit } from '@angular/core';
2 |
3 | @Component({
4 | selector: 'app2-default',
5 | templateUrl: './default.component.html',
6 | styleUrls: ['./default.component.css']
7 | })
8 | export class DefaultComponent implements OnInit {
9 |
10 | constructor() { }
11 |
12 | ngOnInit() {
13 | }
14 |
15 | }
16 |
--------------------------------------------------------------------------------
/src/app2/app/views/default/default.module.ts:
--------------------------------------------------------------------------------
1 | import { CommonModule } from '@angular/common';
2 | import { NgModule } from '@angular/core';
3 | import { AngularCLIModule } from "@angular-cli-library/components/angular-cli/angular-cli.module";
4 | import { DefaultComponent } from './default.component';
5 | import { RouterModule } from '@angular/router';
6 |
7 | @NgModule({
8 | declarations:[DefaultComponent],
9 | imports: [
10 | CommonModule,
11 | AngularCLIModule,
12 | RouterModule.forChild([
13 | { path: '', component:DefaultComponent},
14 | ])
15 | ]
16 | })
17 | export class DefaultModule { }
18 |
--------------------------------------------------------------------------------
/src/app2/environments/environment.prod.ts:
--------------------------------------------------------------------------------
1 | export const environment = {
2 | production: true
3 | };
4 |
--------------------------------------------------------------------------------
/src/app2/environments/environment.ts:
--------------------------------------------------------------------------------
1 | // The file contents for the current environment will overwrite these during build.
2 | // The build system defaults to the dev environment which uses `environment.ts`, but if you do
3 | // `ng build --env=prod` then `environment.prod.ts` will be used instead.
4 | // The list of which env maps to which file can be found in `.angular-cli.json`.
5 |
6 | export const environment = {
7 | production: false
8 | };
9 |
--------------------------------------------------------------------------------
/src/app2/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/app2/favicon.ico
--------------------------------------------------------------------------------
/src/app2/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Angular CLI with Library (app2)
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
--------------------------------------------------------------------------------
/src/app2/main.server.ts:
--------------------------------------------------------------------------------
1 | export { AppServerModule } from './app/app.server.module';
--------------------------------------------------------------------------------
/src/app2/main.ts:
--------------------------------------------------------------------------------
1 | import { enableProdMode } from '@angular/core';
2 | import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
3 |
4 | import { AppModule } from './app/app.module';
5 | import { environment } from './environments/environment';
6 |
7 | if (environment.production) {
8 | enableProdMode();
9 | }
10 |
11 | platformBrowserDynamic().bootstrapModule(AppModule);
12 |
--------------------------------------------------------------------------------
/src/app2/styles.scss:
--------------------------------------------------------------------------------
1 | /* You can add global styles to this file, and also import other style files */
2 |
--------------------------------------------------------------------------------
/src/shared/assets/.gitkeep:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/shared/assets/.gitkeep
--------------------------------------------------------------------------------
/src/shared/components/angular-cli/angular-cli.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/shared/components/angular-cli/angular-cli.css
--------------------------------------------------------------------------------
/src/shared/components/angular-cli/angular-cli.html:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 | Welcome to {{ title }}!!
9 |
10 |

11 |
12 | Here are some links to help you start:
13 |
14 | -
15 |
16 |
17 | -
18 |
19 |
20 | -
21 |
22 |
23 |
--------------------------------------------------------------------------------
/src/shared/components/angular-cli/angular-cli.module.ts:
--------------------------------------------------------------------------------
1 | import { CommonModule } from '@angular/common';
2 | import { NgModule } from '@angular/core';
3 |
4 | import { AngularCLI } from './angular-cli';
5 |
6 | @NgModule({
7 | declarations: [
8 | AngularCLI
9 | ],
10 | entryComponents:[
11 | AngularCLI
12 | ],
13 | imports: [
14 | CommonModule
15 | ],
16 | exports:[
17 | AngularCLI
18 | ]
19 | })
20 | export class AngularCLIModule { }
21 |
--------------------------------------------------------------------------------
/src/shared/components/angular-cli/angular-cli.spec.ts:
--------------------------------------------------------------------------------
1 | import { async, ComponentFixture, TestBed } from '@angular/core/testing';
2 |
3 | import { AngularCLI } from './angular-cli';
4 |
5 | describe('Shared Angular CLI component/module', () => {
6 | let component: AngularCLI;
7 | let fixture: ComponentFixture;
8 |
9 | beforeEach(async(() => {
10 | TestBed.configureTestingModule({
11 | declarations: [ AngularCLI ]
12 | })
13 | .compileComponents();
14 | }));
15 |
16 | beforeEach(() => {
17 | fixture = TestBed.createComponent(AngularCLI);
18 | component = fixture.componentInstance;
19 | fixture.detectChanges();
20 | });
21 |
22 | it('should be created', () => {
23 | expect(component).toBeTruthy();
24 | });
25 | });
26 |
--------------------------------------------------------------------------------
/src/shared/components/angular-cli/angular-cli.ts:
--------------------------------------------------------------------------------
1 | import { Component, OnInit } from '@angular/core';
2 |
3 | @Component({
4 | selector: 'angular-cli',
5 | templateUrl: './angular-cli.html',
6 | styleUrls: ['./angular-cli.css']
7 | })
8 | export class AngularCLI implements OnInit {
9 | title = 'an extended version of a new app generated with ng new with Library suppport for multiple apps!'
10 |
11 | constructor() { }
12 |
13 | ngOnInit() {
14 | }
15 |
16 | }
17 |
--------------------------------------------------------------------------------
/src/shared/components/example1/example1.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/shared/components/example1/example1.css
--------------------------------------------------------------------------------
/src/shared/components/example1/example1.html:
--------------------------------------------------------------------------------
1 |
2 | {{title}}
3 |
4 |
--------------------------------------------------------------------------------
/src/shared/components/example1/example1.module.ts:
--------------------------------------------------------------------------------
1 | import { RouterModule } from '@angular/router';
2 | import { Example1Component } from './example1';
3 | import { CommonModule } from '@angular/common';
4 | import { NgModule } from '@angular/core';
5 |
6 |
7 | @NgModule({
8 | declarations: [
9 | Example1Component,
10 | ],
11 | imports: [
12 | CommonModule,
13 | RouterModule.forChild([
14 | { path: '', component:Example1Component},
15 | { path: 'example2', loadChildren:'../example2/example2.module#Example2Module'},
16 | ])
17 | ],
18 | exports:[
19 | Example1Component
20 | ]
21 | })
22 | export class Example1Module { }
23 |
--------------------------------------------------------------------------------
/src/shared/components/example1/example1.spec.ts:
--------------------------------------------------------------------------------
1 | import { async, ComponentFixture, TestBed } from '@angular/core/testing';
2 |
3 | import { AngularCLI } from './angular-cli';
4 |
5 | describe('Shared Angular CLI component/module', () => {
6 | let component: AngularCLI;
7 | let fixture: ComponentFixture;
8 |
9 | beforeEach(async(() => {
10 | TestBed.configureTestingModule({
11 | declarations: [ AngularCLI ]
12 | })
13 | .compileComponents();
14 | }));
15 |
16 | beforeEach(() => {
17 | fixture = TestBed.createComponent(AngularCLI);
18 | component = fixture.componentInstance;
19 | fixture.detectChanges();
20 | });
21 |
22 | it('should be created', () => {
23 | expect(component).toBeTruthy();
24 | });
25 | });
26 |
--------------------------------------------------------------------------------
/src/shared/components/example1/example1.ts:
--------------------------------------------------------------------------------
1 | import { Component, OnInit } from '@angular/core';
2 |
3 | @Component({
4 | selector: 'example1',
5 | templateUrl: './example1.html',
6 | styleUrls: ['./example1.css']
7 | })
8 | export class Example1Component implements OnInit {
9 | title = 'Example1: This component/module was lazy loaded from a Shared Library';
10 |
11 | constructor() { }
12 |
13 | ngOnInit() {
14 | }
15 |
16 | }
17 |
--------------------------------------------------------------------------------
/src/shared/components/example2/example2.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nekkon/angular-cli-library/c61f240ba6b241fa652fab904580d75b3c7985e1/src/shared/components/example2/example2.css
--------------------------------------------------------------------------------
/src/shared/components/example2/example2.html:
--------------------------------------------------------------------------------
1 |
2 | {{title}}
3 |
4 |
--------------------------------------------------------------------------------
/src/shared/components/example2/example2.module.ts:
--------------------------------------------------------------------------------
1 | import { RouterModule } from '@angular/router';
2 | import { CommonModule } from '@angular/common';
3 | import { NgModule } from '@angular/core';
4 | import { Example2Component } from "./example2";
5 |
6 | @NgModule({
7 | declarations: [
8 | Example2Component
9 | ],
10 | imports: [
11 | CommonModule,
12 | RouterModule.forChild([
13 | { path: '', component:Example2Component }
14 | ])
15 | ],
16 | exports:[
17 | Example2Component
18 | ]
19 | })
20 | export class Example2Module { }
21 |
--------------------------------------------------------------------------------
/src/shared/components/example2/example2.spec.ts:
--------------------------------------------------------------------------------
1 | import { async, ComponentFixture, TestBed } from '@angular/core/testing';
2 |
3 | import { AngularCLI } from './angular-cli';
4 |
5 | describe('Shared Angular CLI component/module', () => {
6 | let component: AngularCLI;
7 | let fixture: ComponentFixture;
8 |
9 | beforeEach(async(() => {
10 | TestBed.configureTestingModule({
11 | declarations: [ AngularCLI ]
12 | })
13 | .compileComponents();
14 | }));
15 |
16 | beforeEach(() => {
17 | fixture = TestBed.createComponent(AngularCLI);
18 | component = fixture.componentInstance;
19 | fixture.detectChanges();
20 | });
21 |
22 | it('should be created', () => {
23 | expect(component).toBeTruthy();
24 | });
25 | });
26 |
--------------------------------------------------------------------------------
/src/shared/components/example2/example2.ts:
--------------------------------------------------------------------------------
1 | import { Component, OnInit } from '@angular/core';
2 |
3 | @Component({
4 | selector: 'example2',
5 | templateUrl: './example2.html',
6 | styleUrls: ['./example2.css']
7 | })
8 | export class Example2Component implements OnInit {
9 | title = 'Example2: This Shared module/component was lazily loaded from another Shared lazy loaded module/component!';
10 |
11 | constructor() { }
12 |
13 | ngOnInit() {
14 | }
15 |
16 | }
17 |
--------------------------------------------------------------------------------
/src/shared/other/polyfills.ts:
--------------------------------------------------------------------------------
1 | /**
2 | * This file includes polyfills needed by Angular and is loaded before the app.
3 | * You can add your own extra polyfills to this file.
4 | *
5 | * This file is divided into 2 sections:
6 | * 1. Browser polyfills. These are applied before loading ZoneJS and are sorted by browsers.
7 | * 2. Application imports. Files imported after ZoneJS that should be loaded before your main
8 | * file.
9 | *
10 | * The current setup is for so-called "evergreen" browsers; the last versions of browsers that
11 | * automatically update themselves. This includes Safari >= 10, Chrome >= 55 (including Opera),
12 | * Edge >= 13 on the desktop, and iOS 10 and Chrome on mobile.
13 | *
14 | * Learn more in https://angular.io/docs/ts/latest/guide/browser-support.html
15 | */
16 |
17 | /***************************************************************************************************
18 | * BROWSER POLYFILLS
19 | */
20 |
21 | /** IE9, IE10 and IE11 requires all of the following polyfills. **/
22 | // import 'core-js/es6/symbol';
23 | // import 'core-js/es6/object';
24 | // import 'core-js/es6/function';
25 | // import 'core-js/es6/parse-int';
26 | // import 'core-js/es6/parse-float';
27 | // import 'core-js/es6/number';
28 | // import 'core-js/es6/math';
29 | // import 'core-js/es6/string';
30 | // import 'core-js/es6/date';
31 | // import 'core-js/es6/array';
32 | // import 'core-js/es6/regexp';
33 | // import 'core-js/es6/map';
34 | // import 'core-js/es6/weak-map';
35 | // import 'core-js/es6/set';
36 |
37 | /** IE10 and IE11 requires the following for NgClass support on SVG elements */
38 | // import 'classlist.js'; // Run `npm install --save classlist.js`.
39 |
40 | /** Evergreen browsers require these. **/
41 | import 'core-js/es6/reflect';
42 | import 'core-js/es7/reflect';
43 |
44 |
45 | /**
46 | * Required to support Web Animations `@angular/animation`.
47 | * Needed for: All but Chrome, Firefox and Opera. http://caniuse.com/#feat=web-animation
48 | **/
49 | // import 'web-animations-js'; // Run `npm install --save web-animations-js`.
50 |
51 |
52 |
53 | /***************************************************************************************************
54 | * Zone JS is required by Angular itself.
55 | */
56 | import 'zone.js/dist/zone'; // Included with Angular CLI.
57 |
58 |
59 |
60 | /***************************************************************************************************
61 | * APPLICATION IMPORTS
62 | */
63 |
64 | /**
65 | * Date, currency, decimal and percent pipes.
66 | * Needed for: All but Chrome, Firefox, Edge, IE11 and Safari 10
67 | */
68 | // import 'intl'; // Run `npm install --save intl`.
69 | /**
70 | * Need to import at least one locale-data with intl.
71 | */
72 | // import 'intl/locale-data/jsonp/en';
73 |
--------------------------------------------------------------------------------
/src/shared/other/styles.scss:
--------------------------------------------------------------------------------
1 | /* Styles in this file can be shared between apps */
2 |
--------------------------------------------------------------------------------
/src/shared/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "angular-cli-library",
3 | "version": "1.3.2",
4 | "description": "npm package showcasing angular-cli-library by nekkon",
5 | "main": "index.ts",
6 | "scripts": {
7 | "test": "ng test"
8 | },
9 | "repository": {
10 | "type": "git",
11 | "url": "git+https://github.com/nekkon/angular-cli-library.git"
12 | },
13 | "keywords": [
14 | "angular-cli",
15 | "angular",
16 | "typescript",
17 | "library",
18 | "mono-repo",
19 | "multiple-apps"
20 | ],
21 | "author": "nekkon",
22 | "license": "MIT",
23 | "bugs": {
24 | "url": "https://github.com/nekkon/angular-cli-library/issues"
25 | },
26 | "homepage": "https://github.com/nekkon/angular-cli-library#readme"
27 | }
28 |
--------------------------------------------------------------------------------
/src/test.ts:
--------------------------------------------------------------------------------
1 | // This file is required by karma.conf.js and loads recursively all the .spec and framework files
2 |
3 | import 'zone.js/dist/long-stack-trace-zone';
4 | import 'zone.js/dist/proxy.js';
5 | import 'zone.js/dist/sync-test';
6 | import 'zone.js/dist/jasmine-patch';
7 | import 'zone.js/dist/async-test';
8 | import 'zone.js/dist/fake-async-test';
9 | import { getTestBed } from '@angular/core/testing';
10 | import {
11 | BrowserDynamicTestingModule,
12 | platformBrowserDynamicTesting
13 | } from '@angular/platform-browser-dynamic/testing';
14 |
15 | // Unfortunately there's no typing for the `__karma__` variable. Just declare it as any.
16 | declare const __karma__: any;
17 | declare const require: any;
18 |
19 | // Prevent Karma from running prematurely.
20 | __karma__.loaded = function () {};
21 |
22 | // First, initialize the Angular testing environment.
23 | getTestBed().initTestEnvironment(
24 | BrowserDynamicTestingModule,
25 | platformBrowserDynamicTesting()
26 | );
27 | // Then we find all the tests.
28 | const context = require.context('./', true, /\.spec\.ts$/);
29 | // And load the modules.
30 | context.keys().map(context);
31 | // Finally, start Karma to run the tests.
32 | __karma__.start();
33 |
--------------------------------------------------------------------------------
/src/tsconfig.app1.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "../tsconfig.json",
3 | "compilerOptions": {
4 | "paths": {
5 | "@shared/*": ["shared/*"]
6 | },
7 | "outDir": "../out-tsc/app",
8 | "baseUrl": ".",
9 | "module": "es2015",
10 | "types": []
11 | },
12 | "include": [
13 | "app1/**/*",
14 | "shared/**/*"
15 | ],
16 | "exclude":[
17 | "**/*.spec.ts"
18 | ]
19 | }
20 |
--------------------------------------------------------------------------------
/src/tsconfig.app1.server.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "../tsconfig.json",
3 | "compilerOptions": {
4 | "paths": {
5 | "@shared/*": ["shared/*"]
6 | },
7 | "outDir": "../out-tsc/app",
8 | "baseUrl": ".",
9 | "module": "commonjs"
10 | },
11 | "include": [
12 | "app1/**/*",
13 | "shared/**/*"
14 | ],
15 | "exclude":[
16 | "**/*.spec.ts"
17 | ],
18 | "angularCompilerOptions": {
19 | "entryModule": "app1/app/app.server.module#AppServerModule"
20 | }
21 | }
22 |
--------------------------------------------------------------------------------
/src/tsconfig.app2.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "../tsconfig.json",
3 | "compilerOptions": {
4 | "paths": {
5 | "@angular-cli-library/*": ["../node_modules/angular-cli-library/*"]
6 | },
7 | "outDir": "../out-tsc/app",
8 | "baseUrl": ".",
9 | "module": "es2015",
10 | "types": []
11 | },
12 | "include": [
13 | "app2/**/*",
14 | "../node_modules/angular-cli-library/**/*"
15 | ],
16 | "exclude":[
17 | "../**/*.spec.ts"
18 | ]
19 | }
20 |
--------------------------------------------------------------------------------
/src/tsconfig.app2.server.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "../tsconfig.json",
3 | "compilerOptions": {
4 | "paths": {
5 | "@angular-cli-library/*": ["../node_modules/angular-cli-library/*"]
6 | },
7 | "outDir": "../out-tsc/app",
8 | "baseUrl": ".",
9 | "module": "commonjs",
10 | "types": []
11 | },
12 | "include": [
13 | "app2/**/*",
14 | "../node_modules/angular-cli-library/**/*"
15 | ],
16 | "exclude":[
17 | "../**/*.spec.ts"
18 | ],
19 | "angularCompilerOptions": {
20 | "entryModule": "app2/app/app.server.module#AppServerModule"
21 | }
22 | }
23 |
--------------------------------------------------------------------------------
/src/tsconfig.spec.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "../tsconfig.json",
3 | "compilerOptions": {
4 | "paths": {
5 | "@shared/*": ["shared/*"]
6 | },
7 | "outDir": "../out-tsc/app",
8 | "baseUrl": ".",
9 | "module": "es2015",
10 | "types": ["jasmine"]
11 | },
12 | "include": [
13 | "**/*.spec.ts"
14 | ]
15 | }
16 |
--------------------------------------------------------------------------------
/src/typings.d.ts:
--------------------------------------------------------------------------------
1 | /* SystemJS module definition */
2 | declare var module: NodeModule;
3 | interface NodeModule {
4 | id: string;
5 | }
6 |
--------------------------------------------------------------------------------
/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compileOnSave": false,
3 | "compilerOptions": {
4 | "paths": {
5 | "@shared/*": ["src/shared/*"]
6 | },
7 | "outDir": "./dist/out-tsc",
8 | "baseUrl": ".",
9 | "sourceMap": true,
10 | "declaration": false,
11 | "moduleResolution": "node",
12 | "emitDecoratorMetadata": true,
13 | "experimentalDecorators": true,
14 | "target": "es5",
15 | "typeRoots": [
16 | "node_modules/@types"
17 | ],
18 | "lib": [
19 | "es2017",
20 | "dom"
21 | ]
22 | }
23 | }
24 |
--------------------------------------------------------------------------------
/tslint.json:
--------------------------------------------------------------------------------
1 | {
2 | "rulesDirectory": [
3 | "node_modules/codelyzer"
4 | ],
5 | "rules": {
6 | "arrow-return-shorthand": true,
7 | "callable-types": true,
8 | "class-name": true,
9 | "comment-format": [
10 | true,
11 | "check-space"
12 | ],
13 | "curly": true,
14 | "eofline": true,
15 | "forin": true,
16 | "import-blacklist": [
17 | true,
18 | "rxjs"
19 | ],
20 | "import-spacing": true,
21 | "indent": [
22 | true,
23 | "spaces"
24 | ],
25 | "interface-over-type-literal": true,
26 | "label-position": true,
27 | "max-line-length": [
28 | true,
29 | 140
30 | ],
31 | "member-access": false,
32 | "member-ordering": [
33 | true,
34 | {
35 | "order": [
36 | "static-field",
37 | "instance-field",
38 | "static-method",
39 | "instance-method"
40 | ]
41 | }
42 | ],
43 | "no-arg": true,
44 | "no-bitwise": true,
45 | "no-console": [
46 | true,
47 | "debug",
48 | "info",
49 | "time",
50 | "timeEnd",
51 | "trace"
52 | ],
53 | "no-construct": true,
54 | "no-debugger": true,
55 | "no-duplicate-super": true,
56 | "no-empty": false,
57 | "no-empty-interface": true,
58 | "no-eval": true,
59 | "no-inferrable-types": [
60 | true,
61 | "ignore-params"
62 | ],
63 | "no-misused-new": true,
64 | "no-non-null-assertion": true,
65 | "no-shadowed-variable": true,
66 | "no-string-literal": false,
67 | "no-string-throw": true,
68 | "no-switch-case-fall-through": true,
69 | "no-trailing-whitespace": true,
70 | "no-unnecessary-initializer": true,
71 | "no-unused-expression": true,
72 | "no-use-before-declare": true,
73 | "no-var-keyword": true,
74 | "object-literal-sort-keys": false,
75 | "one-line": [
76 | true,
77 | "check-open-brace",
78 | "check-catch",
79 | "check-else",
80 | "check-whitespace"
81 | ],
82 | "prefer-const": true,
83 | "quotemark": [
84 | true,
85 | "single"
86 | ],
87 | "radix": true,
88 | "semicolon": [
89 | true,
90 | "always"
91 | ],
92 | "triple-equals": [
93 | true,
94 | "allow-null-check"
95 | ],
96 | "typedef-whitespace": [
97 | true,
98 | {
99 | "call-signature": "nospace",
100 | "index-signature": "nospace",
101 | "parameter": "nospace",
102 | "property-declaration": "nospace",
103 | "variable-declaration": "nospace"
104 | }
105 | ],
106 | "typeof-compare": true,
107 | "unified-signatures": true,
108 | "variable-name": false,
109 | "whitespace": [
110 | true,
111 | "check-branch",
112 | "check-decl",
113 | "check-operator",
114 | "check-separator",
115 | "check-type"
116 | ],
117 | "directive-selector": [
118 | true,
119 | "attribute",
120 | "app",
121 | "camelCase"
122 | ],
123 | "component-selector": [
124 | true,
125 | "element",
126 | "app",
127 | "kebab-case"
128 | ],
129 | "use-input-property-decorator": true,
130 | "use-output-property-decorator": true,
131 | "use-host-property-decorator": true,
132 | "no-input-rename": true,
133 | "no-output-rename": true,
134 | "use-life-cycle-interface": true,
135 | "use-pipe-transform-interface": true,
136 | "component-class-suffix": true,
137 | "directive-class-suffix": true,
138 | "no-access-missing-member": true,
139 | "templates-use-public": true,
140 | "invoke-injectable": true
141 | }
142 | }
143 |
--------------------------------------------------------------------------------
/webpack.app1.server.config.js:
--------------------------------------------------------------------------------
1 | const path = require('path');
2 | const webpack = require('webpack');
3 |
4 | module.exports = {
5 | entry: { server: './app1.server.ts' },
6 | resolve: { extensions: ['.js', '.ts'] },
7 | target: 'node',
8 | // this makes sure we include node_modules and other 3rd party libraries
9 | externals: [/(node_modules|main\..*\.js)/],
10 | output: {
11 | path: path.join(__dirname, './dist/app1-server'),
12 | filename: '[name].js'
13 | },
14 | module: {
15 | rules: [
16 | {
17 | test: /\.ts$/,
18 | loader: 'ts-loader?configFile=src/tsconfig.app1.server.json'
19 | }
20 | ]
21 | },
22 | plugins: [
23 | // Temporary Fix for issue: https://github.com/angular/angular/issues/11580
24 | // for "WARNING Critical dependency: the request of a dependency is an expression"
25 | new webpack.ContextReplacementPlugin(
26 | /(.+)?angular(\\|\/)core(.+)?/,
27 | path.join(__dirname, './src/app1'), // location of your src
28 | {} // a map of your routes
29 | ),
30 | new webpack.ContextReplacementPlugin(
31 | /(.+)?express(\\|\/)(.+)?/,
32 | path.join(__dirname, './src/app1'),
33 | {}
34 | )
35 | ]
36 | }
--------------------------------------------------------------------------------
/webpack.app2.server.config.js:
--------------------------------------------------------------------------------
1 | const path = require('path');
2 | const webpack = require('webpack');
3 |
4 | module.exports = {
5 | entry: { server: './app2.server.ts' },
6 | resolve: { extensions: ['.js', '.ts'] },
7 | target: 'node',
8 | // this makes sure we include node_modules and other 3rd party libraries
9 | externals: [/(node_modules|main\..*\.js)/],
10 | output: {
11 | path: path.join(__dirname, './dist/app1-server'),
12 | filename: '[name].js'
13 | },
14 | module: {
15 | rules: [
16 | {
17 | test: /\.ts$/,
18 | loader: 'ts-loader?configFile=src/tsconfig.app1.server.json'
19 | }
20 | ]
21 | },
22 | plugins: [
23 | // Temporary Fix for issue: https://github.com/angular/angular/issues/11580
24 | // for "WARNING Critical dependency: the request of a dependency is an expression"
25 | new webpack.ContextReplacementPlugin(
26 | /(.+)?angular(\\|\/)core(.+)?/,
27 | path.join(__dirname, './src/app1'), // location of your src
28 | {} // a map of your routes
29 | ),
30 | new webpack.ContextReplacementPlugin(
31 | /(.+)?express(\\|\/)(.+)?/,
32 | path.join(__dirname, './src/app1'),
33 | {}
34 | )
35 | ]
36 | }
--------------------------------------------------------------------------------