source: Dev/trunk/Gruntfile.js @ 521

Last change on this file since 521 was 520, checked in by hendrikvanantwerpen, 11 years ago

Updated README and made syncs more resilient.

File size: 10.6 KB
RevLine 
[464]1/** Gruntfile - control build and deploy tasks
[453]2 */
[443]3
[469]4var _ = require('underscore');
5
[443]6module.exports = function(grunt) {
7
[469]8    // TASKS
9
[517]10    // default task
[469]11    grunt.registerTask('default', ['compile']);
[517]12    // development
[518]13    grunt.registerTask('compile',
14                       "Lint all sources and compile Coffee and LESS sources.",
15                       ['path-check:svn'
16                       ,'svn-ignore:compile'
17                       ,'jshint:lint-sources'
18                       ,'htmlhint:lint'
19                       ,'coffeelint:lint'
20                       ,'jsonlint:lint'
21                     //,'tv4:lint'
22                       ,'less:compile'
23                       ,'usebanner:generated-css'
24                       ,'coffee:compile'
25                       ,'usebanner:generated-js'
26                       ,'jshint:lint-generated'
27                     //,'amd-check' // too smart about plugins, r.js can't find them
28                       ]);
29    grunt.registerTask('run',
30                       "Compile and start the server locally with foreman.",
31                       ['path-check:foreman'
32                       ,'compile'
33                       ,'foreman:dev']);
34    grunt.registerTask('build',
35                       "Compile and make a Dojo build of the client (compress sources).",
36                       ['compile'
37                       ,'clean:build'
38                       ,'copy:build'
39                       ,'dojo:build'
40                       ]);
41    grunt.registerTask('run-build',
42                       "Make a build and start server from build locally with foreman.",
43                       ['path-check:foreman'
44                       ,'build'
45                       ,'foreman:build']);
46    grunt.registerTask('deploy',
47                       "Make a build and deploy it to Heroku.",
48                       ['path-check:svn'
49                       ,'path-check:git'
50                       ,'svninfo'
51                       ,'build'
52                       ,'git_deploy:deploy']);
[517]53    // database management
54    grunt.registerTask('db-backup-cloud-to-dated-local',
[518]55                       "Backup the Heroku database to a timestamped local database.",
[517]56                       ['path-check:heroku'
57                       ,'heroku-config'
58                       ,'http:db-backup-cloud-to-dated-local']);
59    grunt.registerTask('db-pull-cloud-to-local',
[518]60                       "Synchronize local database with the Heroku database (pull changes).",
[517]61                       ['path-check:heroku'
62                       ,'heroku-config'
63                       ,'http:db-pull-cloud-to-local']);
64    grunt.registerTask('db-push-local-to-cloud',
[518]65                       "Synchronize the Heroku database with the local database (push changes).",
[517]66                       ['path-check:heroku'
67                       ,'heroku-config'
68                       ,'http:db-push-local-to-cloud']);
[518]69    grunt.registerTask('#',
70                       "---\nTASKS BELOW ARE INTERNAL AND SHOULD NOT USUALLY BE CALLED FROM THE COMMAND-LINE\n---",
71                       []);
[469]72
73    // FILES AND FOLDERS
74   
[464]75    var srcDir   = 'src/';
[463]76    var buildDir = 'build/';
[469]77    var coffeeMap = grunt.file.expandMapping(
78        [ 'client/qed-client/**/*.coffee', 'server/**/*.coffee' ],
79        srcDir,
80        { cwd: srcDir, ext: '.js' });
81    var lessMap = grunt.file.expandMapping(
82        [ 'client/qed-client/css/qed.less' ],
83        srcDir,
84        { cwd: srcDir, ext: '.css' });
[453]85
[519]86    var mode = process.env.QED_ENV || 'dev';
87    var dbNames = {
88        dev: 'qed-dev',
89        production: 'qed'
90    };
91    if ( !( mode in dbNames ) ) {
92        throw new Error("Unknown mode "+mode+" specified.");
93    }
94
[469]95    // TASK CONFIG
[517]96
[443]97    grunt.initConfig({
[517]98        localDbURL: "http://localhost:5984",
[519]99        dbName: dbNames[mode],
[517]100        timestamp: "<%= grunt.template.today(\"UTC:yyyymmdd't'HHMMss'z'\") %>",
101
[469]102        'amd-check': {
103            files: [ srcDir+'client/qed-client/**/*.js' ]
104        },
[458]105        clean: {
[469]106            build: { src: [buildDir] }
[458]107        },
[463]108        coffee: {
[469]109            options: { bare: true },
110            compile: { files: coffeeMap }
[453]111        },
[466]112        coffeelint: {
[469]113            lint: { options: require('./'+srcDir+'.coffeelint.json'),
114                    files: coffeeMap }
[466]115        },
[463]116        copy: {
[469]117            build: { files: [{ expand: true,
118                               cwd: srcDir,
119                               src: ['**', '!client/*/**' ],
120                               dest: buildDir }]}
[458]121        },
[453]122        dojo: {
[469]123            build: { options: { dojo: srcDir+'client/dojo/dojo.js',
124                                profile: srcDir+'client/client.profile.js',
[471]125                                releaseDir: '../../'+buildDir }}
[453]126        },
[517]127        foreman: {
128            dev: {
129                options: {
130                    cwd: srcDir
131                }
132            },
133            build: {
134                options: {
135                    cwd: buildDir
136                }
137            }
138        },
[516]139        git_deploy: {
140            deploy: {
141                options: {
142                    url: 'git@heroku.com:quod-erat.git',
143                    branch: 'master',
144                    message: "Deployment of revision <%= svninfo.rev %> on <%= grunt.template.today() %>."
145                },
146                src: buildDir
147            }
148        },
[517]149        'heroku-config': {
150            options: {
151                app: 'quod-erat',
152                keys: ['CLOUDANT_URL']
153            }
154        },
[453]155        htmlhint: {
[469]156            options: { htmlhintrc: srcDir+".htmlhintrc" },
157            lint: { files: [{ expand: true,
158                              cwd: srcDir,
159                              src: ['client/*.html', 'client/qed-client/**/*.html'] }]}
[443]160        },
[517]161        http: {
162            'db-backup-cloud-to-dated-local': {
163                options: {
164                    url: "<%= localDbURL %>/_replicate",
165                    method: 'POST',
166                    body: {
[519]167                        source: "<%= herokuConfig.CLOUDANT_URL %>/<%= dbName %>",
168                        target: "<%= dbName %>-<%= timestamp %>",
[517]169                        create_target: true
170                    },
171                    json: true
172                }
173            },
174            'db-pull-cloud-to-local': {
175                options: {
176                    url: "<%= localDbURL %>/_replicate",
177                    method: 'POST',
178                    body: {
[519]179                        source: "<%= herokuConfig.CLOUDANT_URL %>/<%= dbName %>",
[520]180                        target: "<%= dbName %>",
181                        create_target: true
[517]182                    },
183                    json: true
184                }
185            },
186            'db-push-local-to-cloud': {
187                options: {
188                    url: "<%= localDbURL %>/_replicate",
189                    method: 'POST',
190                    body: {
[519]191                        source: "<%= dbName %>",
[520]192                        target: "<%= herokuConfig.CLOUDANT_URL %>/<%= dbName %>",
193                        create_target: true
[517]194                    },
195                    json: true
196                }
197            }
198        },
[443]199        jshint: {
[469]200            'lint-sources': { options: { jshintrc: srcDir+".jshintrc" },
[505]201                              files: { src: [ srcDir+'client/qed-client/**/*.js', srcDir+'server/**/*.js' ].concat(exclude(dest(coffeeMap))) } },
[469]202            'lint-generated': { options: { jshintrc: srcDir+".jshintrc-generated" },
[505]203                                files: { src: dest(coffeeMap) } }
[443]204        },
[505]205        jsonlint: {
[516]206            'lint': { files: { src: [ srcDir+'client/qed-client/**/*.json', srcDir+'server/**/*.json' ] } }
[505]207        },
[453]208        less: {
[469]209            options: { strictImports: false,
210                       dumpLineNumbers: "all" },
211            compile: { files: lessMap }
212        },
[516]213        'path-check': {
[517]214            'heroku': {
215                src: ['heroku']
216            },
217            'foreman': {
218                src: ['foreman']
219            },
220            'svn': {
221                src: ['svn']
222            },
223            'git': {
224                src: ['git']
[516]225            }
226        },
[469]227        requirejs: {
228            basePath: srcDir+'client/',
229            packages: [
230                { name: "dojo", location: "dojo" },
231                { name: "dijit", location: "dijit" },
232                { name: "dojox", location: "dojox" },
233                { name: "qed-client", location: "qed-client" }
234            ]
235        },
[474]236        'svn-ignore': {
237            compile: {
238                files: { src: dest(coffeeMap).concat(dest(lessMap)) }
239            }
240        },
241        'svn-ignore-clean': {
242            clean: {
243                files: [{
244                    expand: true,
245                    cwd: srcDir,
246                    src: ['**', '!node_modules/**', '!client/dojo/**', '!client/dijit/**', '!client/dojox/**', '!client/util/**'],
247                    filter: 'isDirectory'
248                }]
249            }
250        },
[487]251        tv4: {
252            lint: {
253                options: {
254                    root: grunt.file.readJSON('json-schema-draft-04.json'),
255                    multi: true
256                },
257                src: [srcDir+'server/config/couchdb-schema.json']
258            }
259        },
[469]260        usebanner: {
261            'generated-css': { options: { position: 'top',
262                                          banner: '/* This CSS file is generated. All edits will be lost on recompile. */'},
263                               files: { src: dest(lessMap) }},
264            'generated-js': { options: { position: 'top',
265                                         banner: '/* This JS file is generated, All edits will be lost on recompile. */'},
266                               files: { src: dest(coffeeMap) }}
[443]267        }
268    });
269
[469]270    // LOAD TASKS
271
272    grunt.loadNpmTasks('grunt-amd-check');
273    grunt.loadNpmTasks('grunt-banner');
[466]274    grunt.loadNpmTasks('grunt-coffeelint');
[458]275    grunt.loadNpmTasks('grunt-contrib-clean');
[463]276    grunt.loadNpmTasks('grunt-contrib-coffee');
[453]277    grunt.loadNpmTasks('grunt-contrib-copy');
278    grunt.loadNpmTasks('grunt-contrib-jshint');
[443]279    grunt.loadNpmTasks('grunt-contrib-less');
[453]280    grunt.loadNpmTasks('grunt-dojo');
[516]281    grunt.loadNpmTasks('grunt-git-deploy');
[443]282    grunt.loadNpmTasks('grunt-htmlhint');
[517]283    grunt.loadNpmTasks('grunt-http');
[505]284    grunt.loadNpmTasks('grunt-jsonlint');
[516]285    grunt.loadNpmTasks('grunt-path-check');
286    grunt.loadNpmTasks('grunt-svninfo');
[487]287    grunt.loadNpmTasks('grunt-tv4');
[469]288    grunt.loadTasks('./grunt-tasks');
[443]289
[469]290    // UTIL FUNCTIONS
[464]291
[469]292    function dest(files) {
293        return _.chain(files)
294            .map(function(item){ return item.dest; })
295            .flatten()
296            .value();
297    }
[464]298
[469]299    function exclude(dest) {
300        return _.map(dest, function(dest){ return '!'+dest; });
301    }
302   
[443]303};
Note: See TracBrowser for help on using the repository browser.