build(broccoli): convert traceur and broccoli-dest-copy plugins to use tree-differ

Also adding symlink-or-copy to our npm dependencies since our plugins now use it.
This commit is contained in:
Igor Minar 2015-04-24 11:00:15 -07:00
parent bdf6af9bd6
commit 7740fc071c
7 changed files with 2557 additions and 2546 deletions

View File

@ -1332,14 +1332,6 @@
"version": "0.0.8"
}
}
},
"symlink-or-copy": {
"version": "1.0.1",
"dependencies": {
"copy-dereference": {
"version": "1.0.0"
}
}
}
}
},
@ -1374,14 +1366,6 @@
}
}
},
"symlink-or-copy": {
"version": "1.0.1",
"dependencies": {
"copy-dereference": {
"version": "1.0.0"
}
}
},
"underscore": {
"version": "1.8.3"
}
@ -1399,14 +1383,6 @@
"version": "3.0.18"
}
}
},
"symlink-or-copy": {
"version": "1.0.1",
"dependencies": {
"copy-dereference": {
"version": "1.0.0"
}
}
}
}
},
@ -1513,14 +1489,6 @@
},
"rimraf": {
"version": "2.3.2"
},
"symlink-or-copy": {
"version": "1.0.1",
"dependencies": {
"copy-dereference": {
"version": "1.0.0"
}
}
}
}
},
@ -4808,14 +4776,6 @@
}
}
},
"minijasminenode2": {
"version": "1.0.0",
"dependencies": {
"jasmine-core": {
"version": "2.0.0"
}
}
},
"require-uncached": {
"version": "1.0.2",
"dependencies": {
@ -7978,6 +7938,14 @@
"merge": {
"version": "1.2.0"
},
"minijasminenode2": {
"version": "1.0.0",
"dependencies": {
"jasmine-core": {
"version": "2.0.0"
}
}
},
"minimatch": {
"version": "2.0.4",
"dependencies": {
@ -8296,6 +8264,14 @@
"sprintf-js": {
"version": "1.0.2"
},
"symlink-or-copy": {
"version": "1.0.1",
"dependencies": {
"copy-dereference": {
"version": "1.0.0"
}
}
},
"systemjs": {
"version": "0.9.3"
},
@ -8955,5 +8931,5 @@
}
},
"name": "angular",
"version": "2.0.0-alpha.19"
"version": "2.0.0-alpha.20"
}

4844
npm-shrinkwrap.json generated

File diff suppressed because it is too large Load Diff

View File

@ -94,6 +94,7 @@
"sorted-object": "^1.0.0",
"source-map": "^0.3.0",
"sprintf-js": "1.0.*",
"symlink-or-copy": "^1.0.1",
"systemjs-builder": "^0.10.3",
"temp": "^0.8.1",
"ternary-stream": "^1.2.3",

View File

@ -1,33 +1,63 @@
/// <reference path="./broccoli-filter.d.ts" />
/// <reference path="./broccoli.d.ts" />
/// <reference path="../typings/node/node.d.ts" />
/// <reference path="../typings/fs-extra/fs-extra.d.ts" />
import Filter = require('broccoli-filter');
import fs = require('fs');
import fse = require('fs-extra');
import path = require('path');
import TreeDiffer = require('./tree-differ');
/**
* Intercepts each file as it is copied to the destination tempdir,
* and tees a copy to the given path outside the tmp dir.
*/
class DestCopy extends Filter {
constructor(private inputTree, private outputRoot: string) { super(inputTree); }
export = function destCopy(inputTree, outputRoot) { return new DestCopy(inputTree, outputRoot); }
getDestFilePath(relativePath: string): string { return relativePath; }
processString(content: string, relativePath: string): string { return content; }
class DestCopy implements BroccoliTree {
treeDirtyChecker: TreeDiffer;
initialized = false;
processFile(srcDir, destDir, relativePath): Promise<any> {
return super.processFile(srcDir, destDir, relativePath)
.then(x => {
var destFile = path.join(this.outputRoot, this.getDestFilePath(relativePath));
var dir = path.dirname(destFile);
fse.mkdirsSync(dir);
fse.copySync(path.join(srcDir, relativePath), destFile);
});
// props monkey-patched by broccoli builder:
inputPath = null;
cachePath = null;
outputPath = null;
constructor(public inputTree: BroccoliTree, public outputRoot: string) {}
rebuild() {
let firstRun = !this.initialized;
this.init();
let diffResult = this.treeDirtyChecker.diffTree();
diffResult.log(!firstRun);
diffResult.changedPaths.forEach((changedFilePath) => {
var destFilePath = path.join(this.outputRoot, changedFilePath);
var destDirPath = path.dirname(destFilePath);
fse.mkdirsSync(destDirPath);
fse.copySync(path.join(this.inputPath, changedFilePath), destFilePath);
});
diffResult.removedPaths.forEach((removedFilePath) => {
var destFilePath = path.join(this.outputRoot, removedFilePath);
// TODO: what about obsolete directories? we are not cleaning those up yet
fs.unlinkSync(destFilePath);
});
}
}
export = function destCopy(inputTree, outputRoot) {
return new DestCopy(inputTree, outputRoot);
private init() {
if (!this.initialized) {
this.initialized = true;
this.treeDirtyChecker = new TreeDiffer(this.inputPath);
}
}
cleanup() {}
}

View File

@ -1,55 +1,95 @@
/// <reference path="../broccoli.d.ts" />
/// <reference path="../broccoli-writer.d.ts" />
/// <reference path="../../typings/fs-extra/fs-extra.d.ts" />
/// <reference path="../../typings/node/node.d.ts" />
import fs = require('fs');
import fse = require('fs-extra');
import path = require('path');
var traceur = require('../../../tools/transpiler');
var walkSync = require('walk-sync');
import TreeDiffer = require('../tree-differ');
import Writer = require('broccoli-writer');
var xtend = require('xtend');
class TraceurFilter extends Writer {
static RUNTIME_PATH = traceur.RUNTIME_PATH;
let traceur = require('../../../tools/transpiler');
let symlinkOrCopy = require('symlink-or-copy');
let xtend = require('xtend');
constructor(private inputTree, private destExtension: string,
private destSourceMapExtension: string, private options = {}) {
super();
}
write(readTree, destDir) {
return readTree(this.inputTree)
.then(srcDir => {
walkSync(srcDir)
.filter(filepath =>
{
var extension = path.extname(filepath).toLowerCase();
return extension === '.js' || extension === '.es6' || extension === '.cjs';
})
.map(filepath => {
var options = xtend({filename: filepath}, this.options);
export = traceurCompiler;
var fsOpts = {encoding: 'utf-8'};
var sourcecode = fs.readFileSync(path.join(srcDir, filepath), fsOpts);
var result = traceur.compile(options, filepath, sourcecode);
// TODO: we should fix the sourceMappingURL written by Traceur instead of overriding
// (but we might switch to typescript first)
var mapFilepath = filepath.replace(/\.\w+$/, '') + this.destSourceMapExtension;
result.js = result.js + '\n//# sourceMappingURL=./' + path.basename(mapFilepath);
var destFilepath = filepath.replace(/\.\w+$/, this.destExtension);
var destFile = path.join(destDir, destFilepath);
fse.mkdirsSync(path.dirname(destFile));
fs.writeFileSync(destFile, result.js, fsOpts);
var destMap = path.join(destDir, mapFilepath);
result.sourceMap.file = destFilepath;
fs.writeFileSync(destMap, JSON.stringify(result.sourceMap), fsOpts);
});
});
}
function traceurCompiler(inputTree, destExtension, destSourceMapExtension, options) {
return new TraceurCompiler(inputTree, destExtension, destSourceMapExtension, options);
}
module.exports = TraceurFilter;
traceurCompiler['RUNTIME_PATH'] = traceur.RUNTIME_PATH;
class TraceurCompiler implements BroccoliTree {
treeDiffer: TreeDiffer;
initialized = false;
// props monkey-patched by broccoli builder:
inputPath = null;
cachePath = null;
outputPath = null;
constructor(public inputTree: BroccoliTree, private destExtension: string,
private destSourceMapExtension: string, private options: {[key: string]: any}) {}
rebuild() {
let firstRun = !this.initialized;
this.init();
let diffResult = this.treeDiffer.diffTree();
diffResult.log(!firstRun);
diffResult.changedPaths.forEach((changedFilePath) => {
var extension = path.extname(changedFilePath).toLowerCase();
if (extension === '.js' || extension === '.es6' || extension === '.cjs') {
var options = xtend({filename: changedFilePath}, this.options);
var fsOpts = {encoding: 'utf-8'};
var absoluteInputFilePath = path.join(this.inputPath, changedFilePath);
var sourcecode = fs.readFileSync(absoluteInputFilePath, fsOpts);
var result = traceur.compile(options, changedFilePath, sourcecode);
// TODO: we should fix the sourceMappingURL written by Traceur instead of overriding
// (but we might switch to typescript first)
var mapFilepath = changedFilePath.replace(/\.\w+$/, '') + this.destSourceMapExtension;
result.js = result.js + '\n//# sourceMappingURL=./' + path.basename(mapFilepath);
var destFilepath = changedFilePath.replace(/\.\w+$/, this.destExtension);
var destFile = path.join(this.cachePath, destFilepath);
fse.mkdirsSync(path.dirname(destFile));
fs.writeFileSync(destFile, result.js, fsOpts);
var destMap = path.join(this.cachePath, mapFilepath);
result.sourceMap.file = destFilepath;
fs.writeFileSync(destMap, JSON.stringify(result.sourceMap), fsOpts);
}
});
diffResult.removedPaths.forEach((removedFilePath) => {
var destFilepath = removedFilePath.replace(/\.\w+$/, this.destExtension);
var absoluteOuputFilePath = path.join(this.cachePath, destFilepath);
fs.unlinkSync(absoluteOuputFilePath);
});
// just symlink the cache and output tree
fs.rmdirSync(this.outputPath);
symlinkOrCopy.sync(this.cachePath, this.outputPath);
}
private init() {
if (!this.initialized) {
this.initialized = true;
this.treeDiffer = new TreeDiffer(this.inputPath);
}
}
cleanup() {}
}

View File

@ -8,7 +8,7 @@ var path = require('path');
var replace = require('broccoli-replace');
var stew = require('broccoli-stew');
var ts2dart = require('../broccoli-ts2dart');
var TraceurCompiler = require('../traceur');
var traceurCompiler = require('../traceur');
var projectRootDir = path.normalize(path.join(__dirname, '..', '..', '..'));
@ -19,7 +19,7 @@ module.exports = function makeBrowserTree(options) {
{include: ['**/**'], exclude: ['**/*.cjs', 'benchmarks/e2e_test/**'], destDir: '/'});
// Use Traceur to transpile original sources to ES6
var es6Tree = new TraceurCompiler(modulesTree, '.es6', '.map', {
var es6Tree = traceurCompiler(modulesTree, '.es6', '.map', {
sourceMaps: true,
annotations: true, // parse annotations
types: true, // parse types
@ -34,7 +34,7 @@ module.exports = function makeBrowserTree(options) {
// Call Traceur again to lower the ES6 build tree to ES5
var es5Tree =
new TraceurCompiler(es6Tree, '.js', '.js.map', {modules: 'instantiate', sourceMaps: true});
traceurCompiler(es6Tree, '.js', '.js.map', {modules: 'instantiate', sourceMaps: true});
// Now we add a few more files to the es6 tree that Traceur should not see
['angular2', 'rtts_assert'].forEach(function(destDir) {
@ -53,7 +53,7 @@ module.exports = function makeBrowserTree(options) {
'node_modules/systemjs/lib/extension-cjs.js',
'node_modules/rx/dist/rx.all.js',
'tools/build/snippets/runtime_paths.js',
path.relative(projectRootDir, TraceurCompiler.RUNTIME_PATH)
path.relative(projectRootDir, traceurCompiler.RUNTIME_PATH)
]
}));
var vendorScripts_benchmark =

View File

@ -7,7 +7,7 @@ var renderLodashTemplate = require('broccoli-lodash');
var replace = require('broccoli-replace');
var stew = require('broccoli-stew');
var ts2dart = require('../broccoli-ts2dart');
var TraceurCompiler = require('../traceur');
var traceurCompiler = require('../traceur');
var TypescriptCompiler = require('../typescript');
var projectRootDir = path.normalize(path.join(__dirname, '..', '..', '..'));
@ -29,7 +29,7 @@ module.exports = function makeNodeTree() {
]
});
var nodeTree = new TraceurCompiler(modulesTree, '.js', '.map', {
var nodeTree = traceurCompiler(modulesTree, '.js', '.map', {
sourceMaps: true,
annotations: true, // parse annotations
types: true, // parse types