Skip to content
This repository was archived by the owner on May 1, 2020. It is now read-only.

Commit 99922ce

Browse files
committed
feat(build): replace --dev flag with --prod and add flags --aot, --minifyJs, --minifyCss, --optimizeJs
1 parent 899e02f commit 99922ce

10 files changed

+142
-157
lines changed

src/build.ts

+7-64
Original file line numberDiff line numberDiff line change
@@ -48,13 +48,7 @@ function buildWorker(context: BuildContext) {
4848
// load any 100% required files to ensure they exist
4949
return validateRequiredFilesExist();
5050
}).then(() => {
51-
if (context.isProd) {
52-
// production build
53-
return buildProd(context);
54-
}
55-
56-
// dev build
57-
return buildDev(context);
51+
return buildProject(context);
5852
});
5953
}
6054

@@ -64,86 +58,35 @@ function validateRequiredFilesExist() {
6458
return readFileAsync(process.env.IONIC_APP_ENTRY_POINT_PATH);
6559
}
6660

67-
function buildProd(context: BuildContext) {
68-
// sync empty the www/build directory
69-
clean(context);
70-
71-
buildId++;
72-
73-
// async tasks
74-
// these can happen all while other tasks are running
75-
const copyPromise = copy(context);
61+
function buildProject(context: BuildContext) {
62+
var compilePromise = (context.runAot) ? ngc(context) : transpile(context);
7663

77-
// kick off ngc to run the Ahead of Time compiler
78-
return ngc(context)
64+
return compilePromise
7965
.then(() => {
80-
// ngc has finished, now let's bundle it all together
8166
return bundle(context);
8267
})
8368
.then(() => {
84-
// js minify can kick off right away
85-
const jsPromise = minifyJs(context);
86-
87-
// sass needs to finish, then css minify can run when sass is done
69+
const minPromise = (context.runMinifyJs) ? minifyJs(context) : Promise.resolve();
8870
const sassPromise = sass(context)
8971
.then(() => {
90-
return minifyCss(context);
72+
return (context.runMinifyCss) ? minifyCss(context) : Promise.resolve()
9173
});
9274

9375
return Promise.all([
94-
jsPromise,
76+
minPromise,
9577
sassPromise
9678
]);
9779
})
9880
.then(() => {
9981
// kick off the tslint after everything else
10082
// nothing needs to wait on its completion
10183
lint(context);
102-
103-
// ensure the async tasks have fully completed before resolving
104-
return Promise.all([
105-
copyPromise
106-
]);
10784
})
10885
.catch(err => {
10986
throw new BuildError(err);
11087
});
11188
}
11289

113-
114-
function buildDev(context: BuildContext) {
115-
// sync empty the www/build directory
116-
clean(context);
117-
118-
buildId++;
119-
120-
// async tasks
121-
// these can happen all while other tasks are running
122-
const copyPromise = copy(context);
123-
124-
// just bundle, and if that passes then do the rest at the same time
125-
return transpile(context)
126-
.then(() => {
127-
return bundle(context);
128-
})
129-
.then(() => {
130-
return Promise.all([
131-
sass(context),
132-
copyPromise
133-
]);
134-
})
135-
.then(() => {
136-
// kick off the tslint after everything else
137-
// nothing needs to wait on its completion
138-
lint(context);
139-
return Promise.resolve();
140-
})
141-
.catch(err => {
142-
throw new BuildError(err);
143-
});
144-
}
145-
146-
14790
export function buildUpdate(changedFiles: ChangedFile[], context: BuildContext) {
14891
return new Promise(resolve => {
14992
const logger = new Logger('build');

src/rollup/ionic-rollup-resolver-plugin.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ export function ionicRollupResolverPlugin(context: BuildContext) {
5757
}
5858

5959
// remove decorators if prod build
60-
if (context.isProd) {
60+
if (context.optimizeJs) {
6161
file.content = optimizeJavascript(jsSourcePath, file.content);
6262
}
6363

src/spec/build.spec.ts

+70
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
import { BuildContext } from '../util/interfaces';
2+
3+
import * as build from '../build';
4+
import * as bundle from '../bundle';
5+
import * as copy from '../copy';
6+
import * as minify from '../minify';
7+
import * as lint from '../lint';
8+
import * as ngc from '../ngc';
9+
import * as sass from '../sass';
10+
import * as transpile from '../transpile';
11+
12+
describe('build', () => {
13+
beforeEach(() => {
14+
spyOn(copy, 'copy').and.returnValue(Promise.resolve());
15+
spyOn(ngc, 'ngc').and.returnValue(Promise.resolve());
16+
spyOn(bundle, 'bundle').and.returnValue(Promise.resolve());
17+
spyOn(minify, 'minifyJs').and.returnValue(Promise.resolve());
18+
spyOn(sass, 'sass').and.returnValue(Promise.resolve());
19+
spyOn(minify, 'minifyCss').and.returnValue(Promise.resolve());
20+
spyOn(lint, 'lint').and.returnValue(Promise.resolve());
21+
spyOn(transpile, 'transpile').and.returnValue(Promise.resolve());
22+
});
23+
24+
describe('build', () => {
25+
it('isProd', () => {
26+
let context: BuildContext = {
27+
isProd: true,
28+
optimizeJs: true,
29+
runMinifyJs: true,
30+
runMinifyCss: true,
31+
runAot: true
32+
};
33+
34+
build.build(context).then(() => {
35+
expect(copy.copy).toHaveBeenCalled();
36+
expect(ngc.ngc).toHaveBeenCalled();
37+
expect(bundle.bundle).toHaveBeenCalled();
38+
expect(minify.minifyJs).toHaveBeenCalled();
39+
expect(sass.sass).toHaveBeenCalled();
40+
expect(minify.minifyCss).toHaveBeenCalled();
41+
expect(lint.lint).toHaveBeenCalled();
42+
43+
expect(transpile.transpile).not.toHaveBeenCalled();
44+
});
45+
});
46+
47+
it('isDev', () => {
48+
let context: BuildContext = {
49+
isProd: false,
50+
optimizeJs: false,
51+
runMinifyJs: false,
52+
runMinifyCss: false,
53+
runAot: false
54+
};
55+
56+
build.build(context).then(() => {
57+
expect(copy.copy).toHaveBeenCalled();
58+
expect(transpile.transpile).toHaveBeenCalled();
59+
expect(bundle.bundle).toHaveBeenCalled();
60+
expect(sass.sass).toHaveBeenCalled();
61+
expect(lint.lint).toHaveBeenCalled();
62+
63+
expect(ngc.ngc).not.toHaveBeenCalled();
64+
expect(minify.minifyJs).not.toHaveBeenCalled();
65+
expect(minify.minifyCss).not.toHaveBeenCalled();
66+
});
67+
});
68+
});
69+
70+
});

src/spec/config.spec.ts

+20-45
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import { BuildContext } from '../util/interfaces';
2-
import { bundlerStrategy, generateContext, getConfigValue, getUserConfigFile, getIsProd, replacePathVars } from '../util/config';
2+
import { bundlerStrategy, generateContext, getConfigValue, getUserConfigFile, replacePathVars } from '../util/config';
33
import { addArgv, setAppPackageJsonData, setProcessEnvVar, setProcessArgs, setProcessEnv, setCwd } from '../util/config';
44
import { resolve } from 'path';
55

@@ -39,60 +39,35 @@ describe('config', () => {
3939

4040
it('should set isProd by default', () => {
4141
const context = generateContext();
42-
expect(context.isProd).toEqual(true);
42+
expect(context.isProd).toEqual(false);
4343
});
4444

4545
it('should create an object when passed nothing', () => {
4646
const context = generateContext();
4747
expect(context).toBeDefined();
4848
});
4949

50-
});
51-
52-
describe('getIsProd', () => {
53-
54-
it('should set isProd false with env var', () => {
55-
context = {};
56-
setProcessEnvVar('IONIC_DEV', 'true');
57-
expect(getIsProd(context)).toEqual(false);
58-
});
59-
60-
it('should set isProd false with package.json string config', () => {
61-
context = {};
62-
setAppPackageJsonData({ config: { ionic_dev: 'true' }});
63-
expect(getIsProd(context)).toEqual(false);
64-
});
65-
66-
it('should set isProd false with package.json config', () => {
67-
context = {};
68-
setAppPackageJsonData({ config: { ionic_dev: true }});
69-
expect(getIsProd(context)).toEqual(false);
70-
});
71-
72-
it('should not reassign isProd when already set', () => {
73-
context = {};
74-
context.isProd = true;
75-
addArgv('--dev');
76-
expect(getIsProd(context)).toEqual(true);
77-
});
78-
79-
it('should set isProd false with short --d arg', () => {
80-
context = {};
81-
addArgv('-d');
82-
expect(getIsProd(context)).toEqual(false);
83-
});
84-
85-
it('should set isProd false with full --dev arg', () => {
86-
context = {};
87-
addArgv('--dev');
88-
expect(getIsProd(context)).toEqual(false);
50+
it('should set default prod specific build flag defaults to false', () => {
51+
const context = generateContext({
52+
isProd: false
53+
});
54+
expect(context.isProd).toEqual(false);
55+
expect(context.runAot).toEqual(false);
56+
expect(context.runMinifyJs).toEqual(false);
57+
expect(context.runMinifyCss).toEqual(false);
58+
expect(context.optimizeJs).toEqual(false);
8959
});
9060

91-
it('should default to isProd true', () => {
92-
context = {};
93-
expect(getIsProd(context)).toEqual(true);
61+
it('should set default prod specific build flags to true when isProd is true', () => {
62+
const context = generateContext({
63+
isProd: true
64+
});
65+
expect(context.isProd).toEqual(true);
66+
expect(context.runAot).toEqual(true);
67+
expect(context.runMinifyJs).toEqual(true);
68+
expect(context.runMinifyCss).toEqual(true);
69+
expect(context.optimizeJs).toEqual(true);
9470
});
95-
9671
});
9772

9873
describe('replacePathVars', () => {

src/transpile-worker.ts

-1
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@ const context: BuildContext = {};
77
process.on('message', (incomingMsg: TranspileWorkerMessage) => {
88
context.rootDir = incomingMsg.rootDir;
99
context.buildDir = incomingMsg.buildDir;
10-
context.isProd = incomingMsg.isProd;
1110

1211
const workerConfig: TranspileWorkerConfig = {
1312
configFile: incomingMsg.configFile,

src/transpile.ts

+1-4
Original file line numberDiff line numberDiff line change
@@ -246,7 +246,6 @@ function runDiagnosticsWorker(context: BuildContext) {
246246
const msg: TranspileWorkerMessage = {
247247
rootDir: context.rootDir,
248248
buildDir: context.buildDir,
249-
isProd: context.isProd,
250249
configFile: getTsConfigPath(context)
251250
};
252251
diagnosticsWorker.send(msg);
@@ -256,16 +255,14 @@ function runDiagnosticsWorker(context: BuildContext) {
256255
export interface TranspileWorkerMessage {
257256
rootDir?: string;
258257
buildDir?: string;
259-
isProd?: boolean;
260258
configFile?: string;
261259
transpileSuccess?: boolean;
262260
}
263261

264262

265263
function cleanFileNames(context: BuildContext, fileNames: string[]) {
266264
// make sure we're not transpiling the prod when dev and stuff
267-
const removeFileName = (context.isProd) ? 'main.dev.ts' : 'main.prod.ts';
268-
return fileNames.filter(f => (f.indexOf(removeFileName) === -1));
265+
return fileNames;
269266
}
270267

271268
function writeSourceFiles(fileCache: FileCache, sourceFiles: ts.SourceFile[]) {

src/util/config.ts

+25-38
Original file line numberDiff line numberDiff line change
@@ -61,8 +61,31 @@ export function generateContext(context?: BuildContext): BuildContext {
6161
context.bundler = bundlerStrategy(context);
6262
}
6363

64-
context.isProd = getIsProd(context);
65-
setIonicEnvironment(context.isProd);
64+
context.isProd = [
65+
context.isProd,
66+
hasArg('--prod')
67+
].find(val => typeof val === 'boolean');
68+
69+
// If context is prod then the following flags must be set to true
70+
context.runAot = [
71+
context.runAot,
72+
context.isProd || hasArg('--aot'),
73+
].find(val => typeof val === 'boolean');
74+
75+
context.runMinifyJs = [
76+
context.runMinifyJs,
77+
context.isProd || hasArg('--minifyJs')
78+
].find(val => typeof val === 'boolean');
79+
80+
context.runMinifyCss = [
81+
context.runMinifyCss,
82+
context.isProd || hasArg('--minifyCss')
83+
].find(val => typeof val === 'boolean');
84+
85+
context.optimizeJs = [
86+
context.optimizeJs,
87+
context.isProd || hasArg('--optimizeJs')
88+
].find(val => typeof val === 'boolean');
6689

6790
if (typeof context.isWatch !== 'boolean') {
6891
context.isWatch = hasArg('--watch');
@@ -75,31 +98,6 @@ export function generateContext(context?: BuildContext): BuildContext {
7598
return context;
7699
}
77100

78-
79-
export function getIsProd(context: BuildContext) {
80-
// only check if isProd hasn't already been manually set
81-
if (typeof context.isProd === 'boolean') {
82-
return context.isProd;
83-
}
84-
if (hasArg('--dev', '-d')) {
85-
// not production: has a --dev or -d cmd line arg
86-
return false;
87-
}
88-
89-
let val = getPackageJsonConfig(context, ENV_VAR_IONIC_DEV.toLowerCase());
90-
if (typeof val === 'boolean') {
91-
return !val;
92-
}
93-
94-
val = getProcessEnvVar(ENV_VAR_IONIC_DEV);
95-
if (typeof val === 'boolean') {
96-
return !val;
97-
}
98-
99-
return true;
100-
}
101-
102-
103101
export function getUserConfigFile(context: BuildContext, task: TaskInfo, userConfigFile: string) {
104102
if (userConfigFile) {
105103
return resolve(userConfigFile);
@@ -311,12 +309,6 @@ export function isDebugMode() {
311309
return (processEnv.ionic_debug_mode === 'true');
312310
}
313311

314-
315-
export function setIonicEnvironment(isProd: boolean) {
316-
setProcessEnvVar(ENV_VAR_IONIC_ENV, (isProd ? ENV_VAR_PROD : ENV_VAR_DEV));
317-
}
318-
319-
320312
let processArgv: string[];
321313
export function setProcessArgs(argv: string[]) {
322314
processArgv = argv;
@@ -401,11 +393,6 @@ const TMP_DIR = '.tmp';
401393
const WWW_DIR = 'www';
402394
const WWW_INDEX_FILENAME = 'index.html';
403395

404-
const ENV_VAR_PROD = 'prod';
405-
const ENV_VAR_DEV = 'dev';
406-
407-
const ENV_VAR_IONIC_ENV = 'IONIC_ENV';
408-
const ENV_VAR_IONIC_DEV = 'IONIC_DEV';
409396
const ENV_VAR_ROOT_DIR = 'IONIC_ROOT_DIR';
410397
const ENV_VAR_TMP_DIR = 'IONIC_TMP_DIR';
411398
const ENV_VAR_SRC_DIR = 'IONIC_SRC_DIR';

0 commit comments

Comments
 (0)