Skip to content

Instantly share code, notes, and snippets.

@lukemelia
Created December 22, 2015 04:10
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save lukemelia/9b40a71394a4ff3ce611 to your computer and use it in GitHub Desktop.
Save lukemelia/9b40a71394a4ff3ce611 to your computer and use it in GitHub Desktop.
Sketch of ember-cli-deploy for Tom's fastboot deploy
module.exports = function(deployTarget) {
var ENV = {};
if (deployTarget === 'production') {
ENV.plugins = [
'build', // perform the browser build
's3:browser-s3', // upload the browser build to S3
'gzip', // gzip the browser build assets
'manifest', // avoid redundant uploads
'fastboot', // perform the fastboot build, and merge in browser build details, zip and fingerprint the results
's3:fastboot-s3', // upload the fastboot build to S3
];
ENV['fastboot-s3'] = {
bucket: process.env.FASTBOOT_S3_BUCKET,
prefix: 'fastboot/',
filePattern: function(context) {
return context.fastbootHashedZip;
},
distFiles: function(context) {
return [context.fastbootHashedZip];
},
distDir: ''
};
}
return ENV;
}
/* jshint node: true */
'use strict';
var Promise = require('ember-cli/lib/ext/promise');
var glob = require('glob');
var DeployPluginBase = require('ember-cli-deploy-plugin');
var path = require('path');
var RSVP = require('rsvp');
var exec = RSVP.denodeify(require('child_process').exec);
var crypto = require('crypto');
var fs = require('fs-promise');
module.exports = {
name: 'ember-cli-deploy-build',
createDeployPlugin: function(options) {
var DeployPlugin = DeployPluginBase.extend({
name: options.name,
defaultConfig: {
environment: 'production',
outputPath: 'tmp' + path.sep + 'fastboot-dist'
},
build: function(context) {
var self = this;
var outputPath = this.readConfig('outputPath');
var buildEnv = this.readConfig('environment');
process.env.EMBER_CLI_FASTBOOT = true;
var Builder = this.project.require('ember-cli/lib/models/builder');
var builder = new Builder({
ui: this.ui,
outputPath: outputPath,
environment: buildEnv,
project: this.project
});
this.log('building fastboot app to `' + outputPath + '` using buildEnv `' + buildEnv + '`...', { verbose: true });
return builder.build()
.finally(function() {
return builder.cleanup();
})
.then(this._logSuccess.bind(this, outputPath))
.then(function(files) {
files = files || [];
return {
fastbootDistDir: outputPath,
fastbootDistFiles: files
};
})
.catch(function(error) {
self.log('build failed', { color: 'red' });
return Promise.reject(error);
})
.finally(function(){
process.env.EMBER_CLI_FASTBOOT = false;
});
},
didBuild: function(context) {
// Rewrite FastBoot index.html assets
var browserAssetMap = JSON.parse(fs.readFileSync(context.distDir + '/assets/assetMap.json'));
var fastBootAssetMap = JSON.parse(fs.readFileSync(context.fastbootDistDir + '/assets/assetMap.json'));
var prepend = browserAssetMap.prepend;
var indexHTML = fs.readFileSync(context.fastbootDistDir + '/index.html').toString();
var newAssets = browserAssetMap.assets;
var oldAssets = fastBootAssetMap.assets;
for (var key in oldAssets) {
var value = oldAssets[key];
indexHTML = indexHTML.replace(prepend + value, prepend + newAssets[key]);
}
fs.writeFileSync(context.fastbootDistDir + '/index.html', indexHTML);
},
willUpload: function(context){
// zip and fingerprint the fastboot code
return exec("zip -r fastboot-dist.zip " + context.fastBootDistDir).then(function(){
var zipBuf = fs.readFileSync('fastboot-dist.zip');
var hash = md5Hash(zipBuf);
var hashedZip = 'fastboot-dist-' + hash + '.zip';
context.fastbootHashedZip = hashedZip;
return fs.rename('fastboot-dist.zip', hashedZip)
.then(function() {
log("Created " + hashedZip);
return hashedZip;
});
});
},
function md5Hash(buf) {
var md5 = crypto.createHash('md5');
md5.update(buf);
return md5.digest('hex');
},
_logSuccess: function(outputPath) {
var self = this;
var files = glob.sync('**/**/*', { nonull: false, nodir: true, cwd: outputPath });
if (files && files.length) {
files.forEach(function(path) {
self.log('✔ ' + path, { verbose: true });
});
}
self.log('fastboot build ok', { verbose: true });
return Promise.resolve(files);
}
});
return new DeployPlugin();
}
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment