// Generated on 2015-04-28 using
// generator-webapp 0.5.1
'use strict';
// # Globbing
// for performance reasons we're only matching one level down:
// 'test/spec/{,*/}*.js'
// If you want to recursively match all subfolders, use:
// 'test/spec/**/*.js'
module.exports = function (grunt) {
// Time how long tasks take. Can help when optimizing build times
require('time-grunt')(grunt);
// Load grunt tasks automatically
require('load-grunt-tasks')(grunt);
// Configurable paths
var config = {
app: 'app',
appModuleName: 'sdcApp',
dist: 'app/dist'
};
// Define the configuration for all the tasks
grunt.initConfig({
// Project settings
config: config,
// Watches files for changes and runs tasks based on the changed files
watch: {
html: {
files: ['<%= config.app %>/scripts/**/*.html'],
tasks: ['ngtemplates:app']
},
less: {
files: ['<%= config.app %>/**/*.less'],
tasks: ['less:all']
},
ts: {
files: ['<%= config.app %>/scripts/**/*.ts'],
tasks: ['ts:all']
},
bower: {
files: ['bower.json'],
tasks: ['wiredep']
},
gruntfile: {
files: ['Gruntfile.js']
},
livereload: {
options: {
livereload: '<%= connect.options.livereload %>'
},
files: [
'<%= config.app %>/{,*/}*.html',
'<%= config.app %>/scripts/**/*.html',
'<%= config.app %>/scripts/**/*.css',
'.tmp/styles/{,*/}*.css',
'<%= config.app %>/images/{,*/}*'
]
},
configurations: {
files: [
'configurations/*.json'
],
tasks: ['ngconstant']
}
},
ngconstant: {
options: {
dest: 'app/scripts/modules/configurations.js',
name: 'Sdc.Config'
},
main: {
constants: {
sdcConfig: grunt.file.readJSON(grunt.option('env') ? 'configurations/' + grunt.option('env') + '.json' : 'configurations/prod.json'),
sdcMenu: grunt.file.readJSON('configurations/menu.json')
}
}
},
express: {
options: {
port: process.env.PORT || 9000
},
mock: {
options: {
script: 'server-mock/mock-server.js'
}
}
},
ts: {
all: {
src: [
'app/scripts/**/*.ts',
'typings/**/*.ts'
],
reference: 'app/scripts/references.ts'
},
single: {
src: []
}
},
ngtemplates: {
app: {
options: {
module: '<%= config.appModuleName %>',
prefix: '/'
},
src: [
'<%= config.app %>/scripts/**/*.html',
'!index.html'
],
dest: '<%= config.app %>/scripts/templates.js'
}
},
less: {
all: {
options: {
paths: ['<%= config.app %>/scripts',
'<%= config.app %>/styles']
},
files: {
'<%= config.app %>/styles/app.css': '<%= config.app %>/styles/app.less'
}
},
single: {
paths: ['<%= config.app %>/scripts',
'<%= config.app %>/styles'],
files: []
}
},
injector: {
options: {},
// Inject application script files into index.html (doesn't include bower)
scripts_models: {
options: {
transform: function (filePath) {
filePath = filePath.replace('/app/', '');
return '';
},
starttag: '',
endtag: ''
},
files: {
'<%= config.app %>/index.html': [
[
'<%= config.app %>/scripts/models/**/*.js',
'!<%= config.app %>/scripts/models/**/*-tests.js'
]
]
}
},
scripts_utils: {
options: {
transform: function (filePath) {
filePath = filePath.replace('/app/', '');
return '';
},
starttag: '',
endtag: ''
},
files: {
'<%= config.app %>/index.html': [
[
'<%= config.app %>/scripts/utils/**/*.js',
'!<%= config.app %>/scripts/models/**/*-tests.js'
]
]
}
},
scripts_filters: {
options: {
transform: function (filePath) {
filePath = filePath.replace('/app/', '');
return '';
},
starttag: '',
endtag: ''
},
files: {
'<%= config.app %>/index.html': [
['<%= config.app %>/scripts/filters/**/*.js',
'!<%= config.app %>/scripts/filters/**/*-tests.js'
]
]
}
},
scripts_directives: {
options: {
transform: function (filePath) {
filePath = filePath.replace('/app/', '');
return '';
},
starttag: '',
endtag: ''
},
files: {
'<%= config.app %>/index.html': [
['<%= config.app %>/scripts/directives/**/*.js',
'!<%= config.app %>/scripts/directives/**/*-tests.js'
]
]
}
},
scripts_services: {
options: {
transform: function (filePath) {
filePath = filePath.replace('/app/', '');
return '';
},
starttag: '',
endtag: ''
},
files: {
'<%= config.app %>/index.html': [
['<%= config.app %>/scripts/services/**/*.js',
'!<%= config.app %>/scripts/services/**/*-tests.js'
]
]
}
},
scripts_view_models: {
options: {
transform: function (filePath) {
filePath = filePath.replace('/app/', '');
return '';
},
starttag: '',
endtag: ''
},
files: {
'<%= config.app %>/index.html': [
['<%= config.app %>/scripts/view-models/**/*.js',
'!<%= config.app %>/scripts/view-models/**/*-tests.js']
]
}
},
// Inject component less into app.less
less: {
options: {
transform: function (filePath) {
filePath = filePath.replace('/app/scripts/', '../scripts/');
filePath = filePath.replace('/app/styles/', '');
return '@import \'' + filePath + '\';';
},
starttag: '// injector:less',
endtag: '// endinjector:less'
},
files: {
'<%= config.app %>/styles/app.less': [
'<%= config.app %>/styles/**/*.less',
'<%= config.app %>/scripts/**/*.less',
'!<%= config.app %>/styles/app.less'
]
}
},
// Inject component css into index.html
css: {
options: {
transform: function (filePath) {
filePath = filePath.replace('/app/', '');
filePath = filePath.replace('/.tmp/', '');
return '';
},
starttag: '',
endtag: ''
},
files: {
'<%= config.app %>/index.html': [
'<%= config.app %>/scripts/**/*.css',
'<%= config.app %>/styles/**/*.css',
'!<%= config.app %>/styles/app.css'
]
}
}
},
// The actual grunt server settings
connect: {
options: {
port: 9000,
open: true,
livereload: 35729,
// Change this to '0.0.0.0' to access the server from outside
hostname: 'localhost'
},
livereload: {
options: {
middleware: function (connect) {
return [
connect().use(function (req, res, next) {
var mockApis = require('./configurations/mock.json').sdcConfig;
var userType;
switch (grunt.option('role')) {
case "admin":
userType = mockApis.userTypes.admin;
break;
case "tester":
userType = mockApis.userTypes.tester;
break;
case "governor":
userType = mockApis.userTypes.governor;
break;
case "ops":
userType = mockApis.userTypes.ops;
break;
case "designer":
userType = mockApis.userTypes.designer;
break;
case "product_strategist":
userType = mockApis.userTypes.product_strategist;
break;
case "product_manager":
userType = mockApis.userTypes.product_manager;
break;
default:
userType = mockApis.userTypes.designer;
}
res.cookie(mockApis.cookie.userIdSuffix, req.headers[mockApis.cookie.userIdSuffix] || userType.userId);
res.cookie(mockApis.cookie.userEmail, req.headers[mockApis.cookie.userEmail] || userType.email);
res.cookie(mockApis.cookie.userFirstName, req.headers[mockApis.cookie.userFirstName] || userType.firstName);
res.cookie(mockApis.cookie.userLastName, req.headers[mockApis.cookie.userLastName] || userType.lastName);
next();
}),
connect().use(require('http-proxy-middleware')(['/onboarding', '/onboarding-api'], {
target: 'http://feHost:8181/',
changeOrigin: true,
secure: false
})),
connect().use('/bower_components', connect.static('./bower_components')),
connect().use('/non_bower_components', connect.static('./non_bower_components')),
connect.static(config.app)
];
}
}
},
dist: {
options: {
base: '<%= config.dist %>',
livereload: false
}
}
},
// Empties folders to start fresh
clean: {
generated: {
files: [{
dot: true,
src: [
'<%= config.app %>/scripts/**/*.js',
'<%= config.app %>/scripts/**/*.css',
'!<%= config.app %>/scripts/**/welcome/styles/*.css',
'<%= config.app %>/styles/**/*.css',
'<%= config.app %>/scripts/**/*.js.map'
]
}]
},
dist: {
files: [{
dot: true,
src: [
'.tmp',
'<%= config.dist %>/*',
'!<%= config.dist %>/.git*'
]
}]
},
server: '.tmp'
},
// Add vendor prefixed styles
autoprefixer: {
options: {
browsers: ['> 1%', 'last 2 versions', 'Firefox ESR', 'Opera 12.1']
},
dist: {
files: [{
expand: true,
cwd: '.tmp/css/',
src: '{,*/**/}*.css',
dest: '.tmp/css/'
}]
}
},
// Automatically inject Bower components into the HTML file
wiredep: {
app: {
ignorePath: /^\/|\.\.\//,
src: ['<%= config.app %>/index.html']
}
},
// Renames files for browser caching purposes
rev: {
dist: {
files: {
src: [
'<%= config.dist %>/scripts/{,*/}*.js',
'<%= config.dist %>/styles/{,*/}*.css',
'<%= config.dist %>/images/{,*/}*.*',
'!<%= config.dist %>/images/resource-icons/{,*/}*.*',
'!<%= config.dist %>/images/service-icons/{,*/}*.*',
'!<%= config.dist %>/images/relationship-icons/{,*/}*.*',
'<%= config.dist %>/*.{ico,png}'
]
}
}
},
// Reads HTML for usemin blocks to enable smart builds that automatically
// concat, minify and revision files. Creates configurations in memory so
// additional tasks can operate on them
useminPrepare: {
options: {
dest: '<%= config.dist %>'
},
sdc: {
src: ['<%= config.app %>/index.html']
},
html: '<%= config.app %>/index.html'
},
// Performs rewrites based on rev and the useminPrepare configuration
usemin: {
options: {
assetsDirs: [
'<%= config.dist %>',
'<%= config.dist %>/images',
'<%= config.dist %>/styles'
],
// This is so we update image references in our ng-templates
patterns: {
js: [
[/(assets\/images\/.*?\.(?:gif|jpeg|jpg|png|webp|svg))/gm, 'Update the JS to reference our revved images']
]
}
},
html: ['<%= config.dist %>/{,*/}*.html'],
css: ['<%= config.dist %>/styles/{,*/}*.css'],
js: ['<%= config.dist %>/public/{,*/}*.js']
},
// The following *-min tasks produce minified files in the dist folder
imagemin: {
dist: {
files: [{
expand: true,
cwd: '<%= config.app %>/images',
src: '<%= config.app %>/**/*.{gif,jpeg,jpg,png}',
dest: '<%= config.dist %>/images'
}]
}
},
svgmin: {
dist: {
files: [{
expand: true,
cwd: '<%= config.app %>/images',
src: '{,*/}*.svg',
dest: '<%= config.dist %>/images'
}]
}
},
htmlmin: {
dist: {
options: {
collapseBooleanAttributes: true,
collapseWhitespace: true,
conservativeCollapse: true,
removeAttributeQuotes: true,
removeCommentsFromCDATA: true,
removeEmptyAttributes: true,
removeOptionalTags: true,
removeRedundantAttributes: true,
useShortDoctype: true
},
files: [{
expand: true,
cwd: '<%= config.dist %>',
src: '{,*/}*.html',
dest: '<%= config.dist %>'
}]
}
},
// By default, your `index.html`'s will take care
// of minification. These next options are pre-configured if you do not
// wish to use the Usemin blocks.
cssmin: {
dist: {
files: {
'<%= config.dist %>/styles/main.css': [
'.tmp/css/{,*/**/}*.css',
'<%= config.app %>/scripts/{,*/**/}*.css',
'<%= config.app %>/styles/app.css'
]
}
}
},
uglify: {
dist: {
files: {
'<%= config.dist %>/scripts/scripts.js': [
'<%= config.dist %>/scripts/scripts.js'
]
}
}
},
replace: {
cssReplace: {
src: ['<%= config.app %>/scripts/{,*/**/}*.css',
'<%= config.app %>/styles/{,*/**/}*.css'],
overwrite: true,
replacements: [
{
from: '../../../images/',
to: '../images/'
},
{
from: '../../images/',
to: '../images/'
},
{
from: '../../../fonts/',
to: '../fonts/'
},
{
from: '../../fonts/',
to: '../fonts/'
},
{
from: '../../../styles/images/',
to: 'images/'
}
]
},
},
concat: {
dist: {
options: {
separator: ';\n'
},
src: ['<%= config.app %>/scripts/{,*/**/}*.js'],
dest: '.tmp/concat/scripts/scripts.js'
},
generated: {
options: {
separator: '\n'
}
}
},
// Copies remaining files to places other tasks can use
copy: {
dist: {
files: [{
expand: true,
dot: true,
cwd: '<%= config.app %>',
dest: '<%= config.dist %>',
src: [
'*.{ico,png,txt}',
'.htaccess',
// 'bower_components/**/*',
'styles/images/**/*',
'styles/fonts/**/*',
'languages/**/*',
'index.html'
]
}, {
src: 'node_modules/apache-server-configs/dist/.htaccess',
dest: '<%= config.dist %>/.htaccess'
},
{
expand: true,
cwd: '.tmp/images',
dest: '<%= config.dist %>/images',
src: ['generated/*']
},
//TODO to remove this section after integration onboard finished
{
expand: true,
cwd: '<%= config.app %>/third-party',
dest: '<%= config.dist %>/third-party',
src: ['onboard_bundle_full.js']
},
{
expand: true,
dest: '<%= config.dist %>',
src: [
'package.json'
]
}
]
},
styles: {
expand: true,
cwd: '<%= config.app %>/styles',
dest: '.tmp/css/',
src: '{,*/**/}*.css'
}
},
// Run some tasks in parallel to speed up build process
concurrent: {
server: ['copy:styles'],
test: ['copy:styles'],
dist: [
'copy:styles',
'imagemin'
]
},
// Test settings
karma: {
dev: {
configFile: "tests/karma.unit.conf.js",
singleRun: true,
options: {
browsers: ['Chrome'],
coverageReporter: {
type: 'html',
dir: 'tests/Coverage'
}
}
},
debug: {
configFile: "tests/karma.unit.conf.js",
singleRun: false,
//comment out this line if you want to cancel the watch and see the UT log
background: true,
options: {
browsers: ['Chrome'],
reporters: [
'junit',
'dots',
'progress'
]
}
},
jenkins: {
configFile: "tests/karma.unit.conf.js",
singleRun: true,
options: {
browsers: ['PhantomJS'],
coverageReporter: {
type: 'text-summary',
dir: 'tests/Coverage',
file: 'coverage.txt'
}
}
}
},
tslint: {
options: {
configuration: 'tslint.json'
},
files: {
src: ['<%= config.app %>/**/*.ts']
}
}
});
grunt.registerTask('serve', 'start the server and preview your app, --allow-remote for remote access', function (target) {
var env = grunt.option('env');
if (grunt.option('allow-remote')) {
grunt.config.set('connect.options.hostname', '0.0.0.0');
}
if (target === 'dist') {
return grunt.task.run(['build', 'connect:dist:keepalive']);
}
if (env === 'mock') {
grunt.task.run([
'express:mock',
'clean:generated',
'ts:all',
'ngtemplates:app',
'injector',
'less:all',
'ngconstant',
'wiredep',
'concurrent:server',
'autoprefixer',
'connect:livereload',
'watch:html',
'watch:less'
]);
}
grunt.task.run([
'clean:generated',
'ts:all',
'ngtemplates:app',
'injector',
'less:all',
'ngconstant',
'wiredep',
'concurrent:server',
'autoprefixer',
'connect:livereload',
'watch'
]);
});
grunt.registerTask('build', [
'clean:generated',
'less:all',
'ts:all',
'ngconstant',
'ngtemplates:app',
'wiredep',
'replace',
'clean:dist',
'useminPrepare:sdc',
'concurrent:dist',
'autoprefixer:dist',
'concat',
'copy:dist',
'cssmin',
'uglify',
'rev',
'usemin'
]);
grunt.registerTask("test", function (target) {
if (!(target === 'debug' || target === 'dev' || target === 'jenkins')) {
throw new Error("target available for test are ");
}
var tasks = [
// "tslint:karma",
// "ngconstant",
//// "concurrent:test",
// "servicesIconConstants",
// "autoprefixer",
// "ngtemplates:testsTemplates",
// "connect:test"
];
tasks.push('karma:' + target);
if (target === 'debug') {
if (grunt.config.get('watch.ts')) {
tasks.push("watch:ts");
} else {
throw new Error("target watch:ts is not available, verify that it exists in your Gruntfile");
}
}
grunt.task.run(tasks);
});
var lessSingleTask = function (filePath) {
var lessSingleFiles = [{
expand: true,
src: [filePath.replace(/\\/g, '/')],
ext: '.css'
}];
grunt.config('less.single.files', lessSingleFiles);
grunt.config('watch.less.tasks', 'less:single');
};
var tsSingleTask = function (filePath) {
var tsSingleData = {
src: [filePath.replace(/\\/g, '/')]
};
// grunt.config('ts.single', tsSingleData);
};
var singleTaskByTaskName = {
//less: lessSingleTask,
ts: tsSingleTask
};
var onGruntWatchEvent = function (action, filepath, target) {
if (singleTaskByTaskName[target]) {
singleTaskByTaskName[target].call(undefined, filepath);
}
};
grunt.event.on('watch', onGruntWatchEvent);
};