diff options
| author | yo mama <pepper@scannerjammer.com> | 2014-12-04 12:00:43 -0800 |
|---|---|---|
| committer | yo mama <pepper@scannerjammer.com> | 2014-12-04 12:00:43 -0800 |
| commit | 1c620393cdc8fb953bdc95bdaabcf70ff88fc4b3 (patch) | |
| tree | 729455280af1cd83618801c94fafddf621f13617 /app/express-example | |
| parent | 0dd948fe07e97949d9ba01293cc4aca06ba34829 (diff) | |
Diffstat (limited to 'app/express-example')
46 files changed, 1698 insertions, 0 deletions
diff --git a/app/express-example/index.js b/app/express-example/index.js new file mode 100644 index 0000000..be8812e --- /dev/null +++ b/app/express-example/index.js @@ -0,0 +1,186 @@ +'use strict'; +var util = require('util'); +var path = require('path'); +var yeoman = require('yeoman-generator'); + +function ExpressGenerator(args, options, config) { + yeoman.generators.Base.apply(this, arguments); + + this.on('end', function () { + this.installDependencies({ skipInstall: options['skip-install'] }); + }); + + this.pkg = JSON.parse(this.readFileAsString(path.join(__dirname, '../package.json'))); +} + +util.inherits(ExpressGenerator, yeoman.generators.Base); + +ExpressGenerator.prototype.promptType = function promptType() { + // Short circuit if an option was explicitly specified + if (this.options.mvc || this.options.basic) { + return true; + } + + var done = this.async(); + var prompt = [{ + type: 'list', + name: 'type', + message: 'Select a version to install:', + choices: [ + 'Basic', + 'MVC' + ] + }]; + + this.prompt(prompt, function (responses) { + this.options.mvc = responses.type.match(/^MVC$/i) !== null; + done(); + }.bind(this)); +}; + +ExpressGenerator.prototype.promptViewEngine = function () { + + if (this.options.viewEngine) { + return true; + } + + var done = this.async(); + var prompt = [{ + type: 'list', + name: 'viewEngine', + message: 'Select a view engine to use:', + choices: [ + 'Jade', + 'EJS' + ] + }]; + + this.prompt(prompt, function (response) { + this.options.viewEngine = response.viewEngine.toLowerCase(); + done(); + }.bind(this)); +}; + +ExpressGenerator.prototype.promptCssPreprocessor = function () { + + if (this.options.cssPreprocessor) { + return true; + } + + var done = this.async(); + var prompt = [{ + type: 'list', + name: 'cssPreprocessor', + message: 'Select a css preprocessor to use (Sass Requires Ruby):' , + choices: [ + 'None', + 'Node-Sass', + 'Sass', + 'less' + ] + }]; + + this.prompt(prompt, function (response) { + this.options.cssPreprocessor = response.cssPreprocessor.toLowerCase(); + done(); + }.bind(this)); +}; + +ExpressGenerator.prototype.promptDatabase = function () { + + if (this.options.database || !this.options.mvc) { + return true; + } + + var done = this.async(); + var prompt = [{ + type: 'list', + name: 'database', + message: 'Select a database to use:', + choices: [ + 'None', + 'MongoDB', + 'MySQL', + 'PostgreSQL' + ] + }]; + this.prompt(prompt, function (response) { + this.options.database = response.database.toLowerCase(); + done(); + }.bind(this)); +}; + +ExpressGenerator.prototype.promptBuildTool = function () { + + if (this.options.buildTool) { + return true; + } + + var done = this.async(); + var prompt = [{ + type: 'list', + name: 'buildTool', + message: 'Select a build tool to use:', + choices: [ + 'Grunt', + 'Gulp' + ] + }]; + + this.prompt(prompt, function (response) { + this.options.buildTool = response.buildTool.toLowerCase(); + done(); + }.bind(this)); +}; + +ExpressGenerator.prototype.buildEnv = function buildEnv() { + this.sourceRoot(path.join(__dirname, 'templates', 'common')); + this.expandFiles('**', { cwd: this.sourceRoot() }).map(function (file) { + this.template(file, file.replace(/^_/, '')); + }, this); + + var name = this.options.mvc ? 'mvc' : 'basic'; + var filetype = 'js'; + if (this.options.coffee) { + name += '-coffee'; + filetype = 'coffee'; + } + this.sourceRoot(path.join(__dirname, 'templates', name)); + this.directory('.', '.'); + + var views = this.options.viewEngine; + this.sourceRoot(path.join(__dirname, 'templates', 'views', views)); + if (this.options.mvc) { + this.directory('.', 'app/views'); + } else { + this.directory('.', 'views'); + } + + var stylesheets = this.options.cssPreprocessor; + if (stylesheets === 'sass') { + this.sourceRoot(path.join(__dirname, 'templates', 'css', 'sass')); + } else if (stylesheets === 'node-sass') { + this.sourceRoot(path.join(__dirname, 'templates', 'css', 'sass')); + } else if (stylesheets === 'less') { + this.sourceRoot(path.join(__dirname, 'templates', 'css', 'less')); + } else if (stylesheets === 'none') { + this.sourceRoot(path.join(__dirname, 'templates', 'css', 'css')); + } + this.directory('.', 'public/css'); + + if (this.options.database === 'mysql' || this.options.database === 'postgresql') { + this.copy(path.join(__dirname, 'templates', 'extras', name, 'model-index.' + filetype), 'app/models/index.' + filetype); + } + var buildFile = this.options.buildTool === 'grunt' ? 'Gruntfile.js' : 'gulpfile.js'; + this.copy(path.join(__dirname, 'templates', 'extras', name, buildFile), buildFile); +}; + +ExpressGenerator.prototype.assetsDirs = function assetsDirs() { + this.mkdir('public'); + this.mkdir('public/components'); + this.mkdir('public/js'); + this.mkdir('public/css'); + this.mkdir('public/img'); +}; + +module.exports = ExpressGenerator; diff --git a/app/express-example/templates/basic-coffee/app.js b/app/express-example/templates/basic-coffee/app.js new file mode 100644 index 0000000..14986cb --- /dev/null +++ b/app/express-example/templates/basic-coffee/app.js @@ -0,0 +1,65 @@ +require('coffee-script/register'); + +var express = require('express'); +var path = require('path'); +var favicon = require('serve-favicon'); +var logger = require('morgan'); +var cookieParser = require('cookie-parser'); +var bodyParser = require('body-parser'); + +var routes = require('./routes/index'); +var users = require('./routes/user'); + +var app = express(); + +// view engine setup +app.set('views', path.join(__dirname, 'views')); +app.set('view engine', '<%= options.viewEngine %>'); + +// app.use(favicon(__dirname + '/public/img/favicon.ico')); +app.use(logger('dev')); +app.use(bodyParser.json()); +app.use(bodyParser.urlencoded({ + extended: true +})); +app.use(cookieParser()); +app.use(express.static(path.join(__dirname, 'public'))); + +app.use('/', routes); +app.use('/users', users); + +/// catch 404 and forward to error handler +app.use(function(req, res, next) { + var err = new Error('Not Found'); + err.status = 404; + next(err); +}); + +/// error handlers + +// development error handler +// will print stacktrace +if (app.get('env') === 'development') { + app.use(function(err, req, res, next) { + res.status(err.status || 500); + res.render('error', { + message: err.message, + error: err, + title: 'error' + }); + }); +} + +// production error handler +// no stacktraces leaked to user +app.use(function(err, req, res, next) { + res.status(err.status || 500); + res.render('error', { + message: err.message, + error: {}, + title: 'error' + }); +}); + + +module.exports = app; diff --git a/app/express-example/templates/basic-coffee/bin/www b/app/express-example/templates/basic-coffee/bin/www new file mode 100644 index 0000000..d7f4447 --- /dev/null +++ b/app/express-example/templates/basic-coffee/bin/www @@ -0,0 +1,9 @@ +#!/usr/bin/env node +var debug = require('debug')('expressapp'); +var app = require('../app'); + +app.set('port', process.env.PORT || 3000); + +var server = app.listen(app.get('port'), function() { + debug('Express server listening on port ' + server.address().port); +}); diff --git a/app/express-example/templates/basic-coffee/package.json b/app/express-example/templates/basic-coffee/package.json new file mode 100644 index 0000000..3f6cb15 --- /dev/null +++ b/app/express-example/templates/basic-coffee/package.json @@ -0,0 +1,37 @@ +{ + "name": "<%= _.slugify(appname) %>", + "version": "0.0.1", + "private": true, + "scripts": { + "start": "./bin/www" + }, + "dependencies": { + "express": "~4.4.5", + "static-favicon": "~2.0.0-alpha", + "serve-favicon": "^2.0.1", + "morgan": "~1.1.1", + "cookie-parser": "~1.3.2", + "body-parser": "~1.4.3", + "debug": "~1.0.2"<% if(options.viewEngine == 'jade'){ %>, + "jade": "~1.3.1"<% } %><% if(options.viewEngine == 'ejs'){ %>, + "ejs": "~1.0.0"<% } %> + }, + "devDependencies": {<% if(options.buildTool == 'grunt'){ %> + "grunt": "~0.4.5", + "grunt-develop": "~0.4.0"<% if(options.cssPreprocessor == 'sass'){ %>, + "grunt-contrib-sass": "^0.8.1"<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + "grunt-sass": "^0.16.1"<% } %><% if(options.cssPreprocessor == 'less'){ %>, + "grunt-contrib-less": "^0.12.0"<% } %>, + "grunt-contrib-watch": "~0.6.1", + "request": "~2.36.0", + "time-grunt": "~0.3.2", + "load-grunt-tasks": "~0.6.0", + "coffee-script": "^1.7.1"<% } %><% if(options.buildTool == 'gulp'){ %> + "gulp": "~3.8.8"<% if(options.cssPreprocessor == 'sass'){ %>, + "gulp-ruby-sass": "^0.7.1"<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + "gulp-sass": "^1.2.2"<% } %><% if(options.cssPreprocessor == 'less'){ %>, + "gulp-less": "^1.3.6"<% } %>, + "gulp-nodemon": "~1.0.4", + "gulp-livereload": "~2.1.1"<% } %> + } +} diff --git a/app/express-example/templates/basic-coffee/routes/index.coffee b/app/express-example/templates/basic-coffee/routes/index.coffee new file mode 100644 index 0000000..d7583ce --- /dev/null +++ b/app/express-example/templates/basic-coffee/routes/index.coffee @@ -0,0 +1,8 @@ +express = require 'express' +router = express.Router() + +# GET home page. +router.get '/', (req, res) -> + res.render 'index', { title: 'Express' } + +module.exports = router diff --git a/app/express-example/templates/basic-coffee/routes/user.coffee b/app/express-example/templates/basic-coffee/routes/user.coffee new file mode 100644 index 0000000..832fe87 --- /dev/null +++ b/app/express-example/templates/basic-coffee/routes/user.coffee @@ -0,0 +1,8 @@ +express = require 'express' +router = express.Router() + +# GET users listing. +router.get '/', (req, res) -> + res.send 'respond with a resource' + +module.exports = router diff --git a/app/express-example/templates/basic/app.js b/app/express-example/templates/basic/app.js new file mode 100644 index 0000000..dc4539c --- /dev/null +++ b/app/express-example/templates/basic/app.js @@ -0,0 +1,63 @@ +var express = require('express'); +var path = require('path'); +var favicon = require('serve-favicon'); +var logger = require('morgan'); +var cookieParser = require('cookie-parser'); +var bodyParser = require('body-parser'); + +var routes = require('./routes/index'); +var users = require('./routes/user'); + +var app = express(); + +// view engine setup +app.set('views', path.join(__dirname, 'views')); +app.set('view engine', '<%= options.viewEngine %>'); + +// app.use(favicon(__dirname + '/public/img/favicon.ico')); +app.use(logger('dev')); +app.use(bodyParser.json()); +app.use(bodyParser.urlencoded({ + extended: true +})); +app.use(cookieParser()); +app.use(express.static(path.join(__dirname, 'public'))); + +app.use('/', routes); +app.use('/users', users); + +/// catch 404 and forward to error handler +app.use(function(req, res, next) { + var err = new Error('Not Found'); + err.status = 404; + next(err); +}); + +/// error handlers + +// development error handler +// will print stacktrace +if (app.get('env') === 'development') { + app.use(function(err, req, res, next) { + res.status(err.status || 500); + res.render('error', { + message: err.message, + error: err, + title: 'error' + }); + }); +} + +// production error handler +// no stacktraces leaked to user +app.use(function(err, req, res, next) { + res.status(err.status || 500); + res.render('error', { + message: err.message, + error: {}, + title: 'error' + }); +}); + + +module.exports = app; diff --git a/app/express-example/templates/basic/bin/www b/app/express-example/templates/basic/bin/www new file mode 100644 index 0000000..d7f4447 --- /dev/null +++ b/app/express-example/templates/basic/bin/www @@ -0,0 +1,9 @@ +#!/usr/bin/env node +var debug = require('debug')('expressapp'); +var app = require('../app'); + +app.set('port', process.env.PORT || 3000); + +var server = app.listen(app.get('port'), function() { + debug('Express server listening on port ' + server.address().port); +}); diff --git a/app/express-example/templates/basic/package.json b/app/express-example/templates/basic/package.json new file mode 100644 index 0000000..fd4b113 --- /dev/null +++ b/app/express-example/templates/basic/package.json @@ -0,0 +1,35 @@ +{ + "name": "<%= _.slugify(appname) %>", + "version": "0.0.1", + "private": true, + "scripts": { + "start": "node ./bin/www" + }, + "dependencies": { + "express": "~4.4.5", + "serve-favicon": "~2.0.1", + "morgan": "~1.1.1", + "cookie-parser": "~1.3.2", + "body-parser": "~1.4.3", + "debug": "~1.0.2"<% if(options.viewEngine == 'jade'){ %>, + "jade": "~1.3.1"<% } %><% if(options.viewEngine == 'ejs'){ %>, + "ejs": "~1.0.0"<% } %> + }, + "devDependencies": {<% if(options.buildTool == 'grunt'){ %> + "grunt": "~0.4.5", + "grunt-develop": "~0.4.0"<% if(options.cssPreprocessor == 'sass'){ %>, + "grunt-contrib-sass": "^0.8.1"<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + "grunt-sass": "^0.16.1"<% } %><% if(options.cssPreprocessor == 'less'){ %>, + "grunt-contrib-less": "^0.12.0"<% } %>, + "grunt-contrib-watch": "~0.6.1", + "request": "~2.36.0", + "time-grunt": "~0.3.2", + "load-grunt-tasks": "~0.6.0"<% } %><% if(options.buildTool == 'gulp'){ %> + "gulp": "~3.8.8"<% if(options.cssPreprocessor == 'sass'){ %>, + "gulp-ruby-sass": "^0.7.1"<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + "gulp-sass": "^1.2.2"<% } %><% if(options.cssPreprocessor == 'less'){ %>, + "gulp-less": "^1.3.6"<% } %>, + "gulp-nodemon": "~1.0.4", + "gulp-livereload": "~2.1.1"<% } %> + } +} diff --git a/app/express-example/templates/basic/routes/index.js b/app/express-example/templates/basic/routes/index.js new file mode 100644 index 0000000..896c948 --- /dev/null +++ b/app/express-example/templates/basic/routes/index.js @@ -0,0 +1,9 @@ +var express = require('express'); +var router = express.Router(); + +/* GET home page. */ +router.get('/', function(req, res) { + res.render('index', { title: 'Express' }); +}); + +module.exports = router; diff --git a/app/express-example/templates/basic/routes/user.js b/app/express-example/templates/basic/routes/user.js new file mode 100644 index 0000000..c00d7de --- /dev/null +++ b/app/express-example/templates/basic/routes/user.js @@ -0,0 +1,9 @@ +var express = require('express'); +var router = express.Router(); + +/* GET users listing. */ +router.get('/', function(req, res) { + res.send('respond with a resource'); +}); + +module.exports = router; diff --git a/app/express-example/templates/common/_.bowerrc b/app/express-example/templates/common/_.bowerrc new file mode 100644 index 0000000..2f00fdf --- /dev/null +++ b/app/express-example/templates/common/_.bowerrc @@ -0,0 +1,4 @@ +{ + "directory": "public/components", + "json": "bower.json" +} diff --git a/app/express-example/templates/common/_.gitignore b/app/express-example/templates/common/_.gitignore new file mode 100644 index 0000000..80fcba8 --- /dev/null +++ b/app/express-example/templates/common/_.gitignore @@ -0,0 +1,3 @@ +node_modules/ +public/components +.sass-cache
\ No newline at end of file diff --git a/app/express-example/templates/common/_bower.json b/app/express-example/templates/common/_bower.json new file mode 100644 index 0000000..97fc464 --- /dev/null +++ b/app/express-example/templates/common/_bower.json @@ -0,0 +1,9 @@ +{ + "name": "<%= _.slugify(appname) %>", + "version": "0.0.1", + "ignore": [ + "**/.*", + "node_modules", + "components" + ] +} diff --git a/app/express-example/templates/css/css/style.css b/app/express-example/templates/css/css/style.css new file mode 100644 index 0000000..30e047d --- /dev/null +++ b/app/express-example/templates/css/css/style.css @@ -0,0 +1,8 @@ +body { + padding: 50px; + font: 14px "Lucida Grande", Helvetica, Arial, sans-serif; +} + +a { + color: #00B7FF; +}
\ No newline at end of file diff --git a/app/express-example/templates/css/less/style.less b/app/express-example/templates/css/less/style.less new file mode 100644 index 0000000..9453385 --- /dev/null +++ b/app/express-example/templates/css/less/style.less @@ -0,0 +1,8 @@ +body { + padding: 50px; + font: 14px "Lucida Grande", Helvetica, Arial, sans-serif; +} + +a { + color: #00B7FF; +} diff --git a/app/express-example/templates/css/sass/style.scss b/app/express-example/templates/css/sass/style.scss new file mode 100644 index 0000000..9453385 --- /dev/null +++ b/app/express-example/templates/css/sass/style.scss @@ -0,0 +1,8 @@ +body { + padding: 50px; + font: 14px "Lucida Grande", Helvetica, Arial, sans-serif; +} + +a { + color: #00B7FF; +} diff --git a/app/express-example/templates/extras/basic-coffee/Gruntfile.js b/app/express-example/templates/extras/basic-coffee/Gruntfile.js new file mode 100644 index 0000000..921f04d --- /dev/null +++ b/app/express-example/templates/extras/basic-coffee/Gruntfile.js @@ -0,0 +1,109 @@ +'use strict'; + +var request = require('request'); + +module.exports = function (grunt) { + // show elapsed time at the end + require('time-grunt')(grunt); + // load all grunt tasks + require('load-grunt-tasks')(grunt); + + var reloadPort = 35729, files; + + grunt.initConfig({ + pkg: grunt.file.readJSON('package.json'), + develop: { + server: { + file: 'bin/www' + } + },<% if(options.cssPreprocessor == 'sass'){ %> + sass: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.scss' + } + } + },<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + sass: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.scss' + } + } + },<% } %><% if(options.cssPreprocessor == 'less'){ %> + less: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.less' + } + } + },<% } %> + watch: { + options: { + nospawn: true, + livereload: reloadPort + }, + server: { + files: [ + 'bin/www', + 'app.js', + 'routes/*.coffee' + ], + tasks: ['develop', 'delayed-livereload'] + }, + js: { + files: ['public/js/*.js'], + options: { + livereload: reloadPort + } + }, + css: { + files: [<% if(options.cssPreprocessor == 'none'){ %> + 'public/css/*.css'<% } %><% if(options.cssPreprocessor == 'sass'){ %> + 'public/css/*.scss'<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'public/css/*.scss'<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'public/css/*.less'<% } %> + ],<% if(options.cssPreprocessor == 'sass'){ %> + tasks: ['sass'],<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + tasks: ['sass'],<% } %><% if(options.cssPreprocessor == 'less'){ %> + tasks: ['less'],<% } %> + options: { + livereload: reloadPort + } + }, + views: { + files: ['views/*.<%= options.viewEngine %>'], + options: { + livereload: reloadPort + } + } + } + }); + + grunt.config.requires('watch.server.files'); + files = grunt.config('watch.server.files'); + files = grunt.file.expand(files); + + grunt.registerTask('delayed-livereload', 'Live reload after the node server has restarted.', function () { + var done = this.async(); + setTimeout(function () { + request.get('http://localhost:' + reloadPort + '/changed?files=' + files.join(','), function (err, res) { + var reloaded = !err && res.statusCode === 200; + if (reloaded) { + grunt.log.ok('Delayed live reload successful.'); + } else { + grunt.log.error('Unable to make a delayed live reload.'); + } + done(reloaded); + }); + }, 500); + }); + + grunt.registerTask('default', [<% if(options.cssPreprocessor == 'sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'less',<% } %> + 'develop', + 'watch' + ]); +}; diff --git a/app/express-example/templates/extras/basic-coffee/gulpfile.js b/app/express-example/templates/extras/basic-coffee/gulpfile.js new file mode 100644 index 0000000..5dd34e1 --- /dev/null +++ b/app/express-example/templates/extras/basic-coffee/gulpfile.js @@ -0,0 +1,59 @@ +var gulp = require('gulp'), + nodemon = require('gulp-nodemon'), + livereload = require('gulp-livereload')<% if(options.cssPreprocessor == 'sass'){ %>, + sass = require('gulp-ruby-sass')<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + sass = require('gulp-sass')<% } %><% if(options.cssPreprocessor == 'less'){ %>, + less = require('gulp-less')<% } %>; +<% if(options.cssPreprocessor == 'sass'){ %> +gulp.task('sass', function () { + return gulp.src('./public/css/*.scss') + .pipe(sass()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.scss', ['sass']); +});<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> +gulp.task('sass', function () { + gulp.src('./public/css/*.scss') + .pipe(sass()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.scss', ['sass']); +});<% } %><% if(options.cssPreprocessor == 'less'){ %> +gulp.task('less', function () { + gulp.src('./public/css/*.less') + .pipe(less()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.less', ['less']); +});<% } %> + +gulp.task('develop', function () { + livereload.listen(); + nodemon({ + script: 'bin/www', + ext: 'js coffee <%= options.viewEngine %>', + }).on('restart', function () { + setTimeout(function () { + livereload.changed(); + }, 500); + }); +}); + +gulp.task('default', [<% if(options.cssPreprocessor == 'sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'less',<% } %> + 'develop'<% if(options.cssPreprocessor == 'sass' || + options.cssPreprocessor == 'node-sass' || + options.cssPreprocessor == 'less'){ %>, + 'watch'<% } %> +]); diff --git a/app/express-example/templates/extras/basic/Gruntfile.js b/app/express-example/templates/extras/basic/Gruntfile.js new file mode 100644 index 0000000..ffe4bae --- /dev/null +++ b/app/express-example/templates/extras/basic/Gruntfile.js @@ -0,0 +1,109 @@ +'use strict'; + +var request = require('request'); + +module.exports = function (grunt) { + // show elapsed time at the end + require('time-grunt')(grunt); + // load all grunt tasks + require('load-grunt-tasks')(grunt); + + var reloadPort = 35729, files; + + grunt.initConfig({ + pkg: grunt.file.readJSON('package.json'), + develop: { + server: { + file: 'bin/www' + } + },<% if(options.cssPreprocessor == 'sass'){ %> + sass: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.scss' + } + } + },<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + sass: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.scss' + } + } + },<% } %><% if(options.cssPreprocessor == 'less'){ %> + less: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.less' + } + } + },<% } %> + watch: { + options: { + nospawn: true, + livereload: reloadPort + }, + server: { + files: [ + 'bin/www', + 'app.js', + 'routes/*.js' + ], + tasks: ['develop', 'delayed-livereload'] + }, + js: { + files: ['public/js/*.js'], + options: { + livereload: reloadPort + } + }, + css: { + files: [<% if(options.cssPreprocessor == 'none'){ %> + 'public/css/*.css'<% } %><% if(options.cssPreprocessor == 'sass'){ %> + 'public/css/*.scss'<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'public/css/*.scss'<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'public/css/*.less'<% } %> + ],<% if(options.cssPreprocessor == 'sass'){ %> + tasks: ['sass'],<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + tasks: ['sass'],<% } %><% if(options.cssPreprocessor == 'less'){ %> + tasks: ['less'],<% } %> + options: { + livereload: reloadPort + } + }, + views: { + files: ['views/*.<%= options.viewEngine %>'], + options: { + livereload: reloadPort + } + } + } + }); + + grunt.config.requires('watch.server.files'); + files = grunt.config('watch.server.files'); + files = grunt.file.expand(files); + + grunt.registerTask('delayed-livereload', 'Live reload after the node server has restarted.', function () { + var done = this.async(); + setTimeout(function () { + request.get('http://localhost:' + reloadPort + '/changed?files=' + files.join(','), function (err, res) { + var reloaded = !err && res.statusCode === 200; + if (reloaded) { + grunt.log.ok('Delayed live reload successful.'); + } else { + grunt.log.error('Unable to make a delayed live reload.'); + } + done(reloaded); + }); + }, 500); + }); + + grunt.registerTask('default', [<% if(options.cssPreprocessor == 'sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'less',<% } %> + 'develop', + 'watch' + ]); +}; diff --git a/app/express-example/templates/extras/basic/gulpfile.js b/app/express-example/templates/extras/basic/gulpfile.js new file mode 100644 index 0000000..d73c578 --- /dev/null +++ b/app/express-example/templates/extras/basic/gulpfile.js @@ -0,0 +1,59 @@ +var gulp = require('gulp'), + nodemon = require('gulp-nodemon'), + livereload = require('gulp-livereload')<% if(options.cssPreprocessor == 'sass'){ %>, + sass = require('gulp-ruby-sass')<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + sass = require('gulp-sass')<% } %><% if(options.cssPreprocessor == 'less'){ %>, + less = require('gulp-less')<% } %>; +<% if(options.cssPreprocessor == 'sass'){ %> +gulp.task('sass', function () { + return gulp.src('./public/css/*.scss') + .pipe(sass()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.scss', ['sass']); +});<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> +gulp.task('sass', function () { + gulp.src('./public/css/*.scss') + .pipe(sass()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.scss', ['sass']); +});<% } %><% if(options.cssPreprocessor == 'less'){ %> +gulp.task('less', function () { + gulp.src('./public/css/*.less') + .pipe(less()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.less', ['less']); +});<% } %> + +gulp.task('develop', function () { + livereload.listen(); + nodemon({ + script: 'bin/www', + ext: 'js <%= options.viewEngine %>', + }).on('restart', function () { + setTimeout(function () { + livereload.changed(); + }, 500); + }); +}); + +gulp.task('default', [<% if(options.cssPreprocessor == 'sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'less',<% } %> + 'develop'<% if(options.cssPreprocessor == 'sass' || + options.cssPreprocessor == 'node-sass' || + options.cssPreprocessor == 'less'){ %>, + 'watch'<% } %> +]); diff --git a/app/express-example/templates/extras/mvc-coffee/Gruntfile.js b/app/express-example/templates/extras/mvc-coffee/Gruntfile.js new file mode 100644 index 0000000..57a03df --- /dev/null +++ b/app/express-example/templates/extras/mvc-coffee/Gruntfile.js @@ -0,0 +1,103 @@ +'use strict'; + +var request = require('request'); + +module.exports = function (grunt) { + // show elapsed time at the end + require('time-grunt')(grunt); + // load all grunt tasks + require('load-grunt-tasks')(grunt); + + var reloadPort = 35729, files; + + grunt.initConfig({ + pkg: grunt.file.readJSON('package.json'), + develop: { + server: { + file: 'app.js' + } + },<% if(options.cssPreprocessor == 'sass'){ %> + sass: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.scss' + } + } + },<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + sass: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.scss' + } + } + },<% } %><% if(options.cssPreprocessor == 'less'){ %> + less: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.less' + } + } + },<% } %> + watch: { + options: { + nospawn: true, + livereload: reloadPort + }, + js: { + files: [ + 'app.coffee', + 'app/**/*.coffee', + 'config/*.coffee' + ], + tasks: ['develop', 'delayed-livereload'] + }, + css: { + files: [<% if(options.cssPreprocessor == 'none'){ %> + 'public/css/*.css'<% } %><% if(options.cssPreprocessor == 'sass'){ %> + 'public/css/*.scss'<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'public/css/*.scss'<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'public/css/*.less'<% } %> + ],<% if(options.cssPreprocessor == 'sass'){ %> + tasks: ['sass'],<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + tasks: ['sass'],<% } %><% if(options.cssPreprocessor == 'less'){ %> + tasks: ['less'],<% } %> + options: { + livereload: reloadPort + } + }, + views: { + files: [ + 'app/views/*.<%= options.viewEngine %>', + 'app/views/**/*.<%= options.viewEngine %>' + ], + options: { livereload: reloadPort } + } + } + }); + + grunt.config.requires('watch.js.files'); + files = grunt.config('watch.js.files'); + files = grunt.file.expand(files); + + grunt.registerTask('delayed-livereload', 'Live reload after the node server has restarted.', function () { + var done = this.async(); + setTimeout(function () { + request.get('http://localhost:' + reloadPort + '/changed?files=' + files.join(','), function(err, res) { + var reloaded = !err && res.statusCode === 200; + if (reloaded) + grunt.log.ok('Delayed live reload successful.'); + else + grunt.log.error('Unable to make a delayed live reload.'); + done(reloaded); + }); + }, 500); + }); + + grunt.registerTask('default', [<% if(options.cssPreprocessor == 'sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'less',<% } %> + 'develop', + 'watch' + ]); +}; diff --git a/app/express-example/templates/extras/mvc-coffee/gulpfile.js b/app/express-example/templates/extras/mvc-coffee/gulpfile.js new file mode 100644 index 0000000..0475ad4 --- /dev/null +++ b/app/express-example/templates/extras/mvc-coffee/gulpfile.js @@ -0,0 +1,59 @@ +var gulp = require('gulp'), + nodemon = require('gulp-nodemon'), + livereload = require('gulp-livereload')<% if(options.cssPreprocessor == 'sass'){ %>, + sass = require('gulp-ruby-sass')<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + sass = require('gulp-sass')<% } %><% if(options.cssPreprocessor == 'less'){ %>, + less = require('gulp-less')<% } %>; +<% if(options.cssPreprocessor == 'sass'){ %> +gulp.task('sass', function () { + return gulp.src('./public/css/*.scss') + .pipe(sass()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.scss', ['sass']); +});<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> +gulp.task('sass', function () { + gulp.src('./public/css/*.scss') + .pipe(sass()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.scss', ['sass']); +});<% } %><% if(options.cssPreprocessor == 'less'){ %> +gulp.task('less', function () { + gulp.src('./public/css/*.less') + .pipe(less()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.less', ['less']); +});<% } %> + +gulp.task('develop', function () { + livereload.listen(); + nodemon({ + script: 'app.js', + ext: 'js coffee <%= options.viewEngine %>', + }).on('restart', function () { + setTimeout(function () { + livereload.changed(); + }, 500); + }); +}); + +gulp.task('default', [<% if(options.cssPreprocessor == 'sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'less',<% } %> + 'develop'<% if(options.cssPreprocessor == 'sass' || + options.cssPreprocessor == 'node-sass' || + options.cssPreprocessor == 'less'){ %>, + 'watch'<% } %> +]); diff --git a/app/express-example/templates/extras/mvc-coffee/model-index.coffee b/app/express-example/templates/extras/mvc-coffee/model-index.coffee new file mode 100644 index 0000000..2016c32 --- /dev/null +++ b/app/express-example/templates/extras/mvc-coffee/model-index.coffee @@ -0,0 +1,24 @@ +fs = require('fs') +path = require('path') +Sequelize = require('sequelize') +lodash = require('lodash') +config = require('../../config/config') +db = {} + +sequelize = new Sequelize config.db + +fs.readdirSync(__dirname) + .filter (file) -> + file.indexOf('.') != 0 and file != 'index.coffee' + .forEach (file) -> + model = sequelize.import path.join(__dirname, file) + db[model.name] = model + +Object.keys(db).forEach (modelName) -> + if 'associate' of db[modelName] + db[modelName].associate db + +module.exports = lodash.extend + sequelize: sequelize, + Sequelize: Sequelize +, db diff --git a/app/express-example/templates/extras/mvc/Gruntfile.js b/app/express-example/templates/extras/mvc/Gruntfile.js new file mode 100644 index 0000000..2268bb5 --- /dev/null +++ b/app/express-example/templates/extras/mvc/Gruntfile.js @@ -0,0 +1,103 @@ +'use strict'; + +var request = require('request'); + +module.exports = function (grunt) { + // show elapsed time at the end + require('time-grunt')(grunt); + // load all grunt tasks + require('load-grunt-tasks')(grunt); + + var reloadPort = 35729, files; + + grunt.initConfig({ + pkg: grunt.file.readJSON('package.json'), + develop: { + server: { + file: 'app.js' + } + },<% if(options.cssPreprocessor == 'sass'){ %> + sass: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.scss' + } + } + },<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + sass: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.scss' + } + } + },<% } %><% if(options.cssPreprocessor == 'less'){ %> + less: { + dist: { + files: { + 'public/css/style.css': 'public/css/style.less' + } + } + },<% } %> + watch: { + options: { + nospawn: true, + livereload: reloadPort + }, + js: { + files: [ + 'app.js', + 'app/**/*.js', + 'config/*.js' + ], + tasks: ['develop', 'delayed-livereload'] + }, + css: { + files: [<% if(options.cssPreprocessor == 'none'){ %> + 'public/css/*.css'<% } %><% if(options.cssPreprocessor == 'sass'){ %> + 'public/css/*.scss'<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'public/css/*.scss'<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'public/css/*.less'<% } %> + ],<% if(options.cssPreprocessor == 'sass'){ %> + tasks: ['sass'],<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + tasks: ['sass'],<% } %><% if(options.cssPreprocessor == 'less'){ %> + tasks: ['less'],<% } %> + options: { + livereload: reloadPort + } + }, + views: { + files: [ + 'app/views/*.<%= options.viewEngine %>', + 'app/views/**/*.<%= options.viewEngine %>' + ], + options: { livereload: reloadPort } + } + } + }); + + grunt.config.requires('watch.js.files'); + files = grunt.config('watch.js.files'); + files = grunt.file.expand(files); + + grunt.registerTask('delayed-livereload', 'Live reload after the node server has restarted.', function () { + var done = this.async(); + setTimeout(function () { + request.get('http://localhost:' + reloadPort + '/changed?files=' + files.join(','), function(err, res) { + var reloaded = !err && res.statusCode === 200; + if (reloaded) + grunt.log.ok('Delayed live reload successful.'); + else + grunt.log.error('Unable to make a delayed live reload.'); + done(reloaded); + }); + }, 500); + }); + + grunt.registerTask('default', [<% if(options.cssPreprocessor == 'sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'less',<% } %> + 'develop', + 'watch' + ]); +}; diff --git a/app/express-example/templates/extras/mvc/gulpfile.js b/app/express-example/templates/extras/mvc/gulpfile.js new file mode 100644 index 0000000..5a70d05 --- /dev/null +++ b/app/express-example/templates/extras/mvc/gulpfile.js @@ -0,0 +1,59 @@ +var gulp = require('gulp'), + nodemon = require('gulp-nodemon'), + livereload = require('gulp-livereload')<% if(options.cssPreprocessor == 'sass'){ %>, + sass = require('gulp-ruby-sass')<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + sass = require('gulp-sass')<% } %><% if(options.cssPreprocessor == 'less'){ %>, + less = require('gulp-less')<% } %>; +<% if(options.cssPreprocessor == 'sass'){ %> +gulp.task('sass', function () { + return gulp.src('./public/css/*.scss') + .pipe(sass()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.scss', ['sass']); +});<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> +gulp.task('sass', function () { + gulp.src('./public/css/*.scss') + .pipe(sass()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.scss', ['sass']); +});<% } %><% if(options.cssPreprocessor == 'less'){ %> +gulp.task('less', function () { + gulp.src('./public/css/*.less') + .pipe(less()) + .pipe(gulp.dest('./public/css')) + .pipe(livereload()); +}); + +gulp.task('watch', function() { + gulp.watch('./public/css/*.less', ['less']); +});<% } %> + +gulp.task('develop', function () { + livereload.listen(); + nodemon({ + script: 'app.js', + ext: 'js <%= options.viewEngine %>', + }).on('restart', function () { + setTimeout(function () { + livereload.changed(); + }, 500); + }); +}); + +gulp.task('default', [<% if(options.cssPreprocessor == 'sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'node-sass'){ %> + 'sass',<% } %><% if(options.cssPreprocessor == 'less'){ %> + 'less',<% } %> + 'develop'<% if(options.cssPreprocessor == 'sass' || + options.cssPreprocessor == 'node-sass' || + options.cssPreprocessor == 'less'){ %>, + 'watch'<% } %> +]); diff --git a/app/express-example/templates/extras/mvc/model-index.js b/app/express-example/templates/extras/mvc/model-index.js new file mode 100644 index 0000000..7cb2ec7 --- /dev/null +++ b/app/express-example/templates/extras/mvc/model-index.js @@ -0,0 +1,26 @@ +var fs = require('fs'), + path = require('path'), + Sequelize = require('sequelize'), + lodash = require('lodash'), + config = require('../../config/config'), + db = {}; + +var sequelize = new Sequelize(config.db); + +fs.readdirSync(__dirname).filter(function (file) { + return (file.indexOf('.') !== 0) && (file !== 'index.js'); +}).forEach(function (file) { + var model = sequelize.import(path.join(__dirname, file)); + db[model.name] = model; +}); + +Object.keys(db).forEach(function (modelName) { + if ('associate' in db[modelName]) { + db[modelName].associate(db); + } +}); + +module.exports = lodash.extend({ + sequelize: sequelize, + Sequelize: Sequelize +}, db); diff --git a/app/express-example/templates/mvc-coffee/app.js b/app/express-example/templates/mvc-coffee/app.js new file mode 100644 index 0000000..f256f81 --- /dev/null +++ b/app/express-example/templates/mvc-coffee/app.js @@ -0,0 +1,34 @@ +require('coffee-script/register'); + +var express = require('express'), + config = require('./config/config')<% if(options.database == 'none'){ %>;<% } %><% if(options.database == 'mongodb'){ %>, + glob = require('glob'), + mongoose = require('mongoose');<% } %><% if(options.database == 'mysql' || options.database == 'postgresql'){ %>, + db = require('./app/models');<% } %> +<% if(options.database == 'mongodb'){ %> +mongoose.connect(config.db); +var db = mongoose.connection; +db.on('error', function () { + throw new Error('unable to connect to database at ' + config.db); +}); + +var models = glob.sync(config.root + '/app/models/*.coffee'); +models.forEach(function (model) { + require(model); +});<% } %> +var app = express(); + +require('./config/express')(app, config); +<% if(options.database == 'mysql' || options.database == 'postgresql'){ %> +db.sequelize + .sync() + .complete(function (err) { + if(err){ + throw err[0]; + }else{ + app.listen(config.port); + } + }); +<% } else { %> +app.listen(config.port); +<% } %> diff --git a/app/express-example/templates/mvc-coffee/app/controllers/home.coffee b/app/express-example/templates/mvc-coffee/app/controllers/home.coffee new file mode 100644 index 0000000..b8767e8 --- /dev/null +++ b/app/express-example/templates/mvc-coffee/app/controllers/home.coffee @@ -0,0 +1,17 @@ +express = require 'express' +router = express.Router()<% if(options.database == 'mongodb'){ %> +mongoose = require 'mongoose' +Article = mongoose.model 'Article'<% } %><% if(options.database == 'mysql' || options.database == 'postgresql'){ %> +db = require '../models'<% } %> + +module.exports = (app) -> + app.use '/', router + +router.get '/', (req, res, next) -> +<% if(options.database == 'mongodb'){ %> + Article.find (err, articles) -> + return next(err) if err<% } %><% if(options.database == 'mysql' || options.database == 'postgresql'){ %> + db.Article.findAll().success (articles) -><% } %> + res.render 'index', + title: 'Generator-Express MVC' + articles: articles diff --git a/app/express-example/templates/mvc-coffee/app/models/article.coffee b/app/express-example/templates/mvc-coffee/app/models/article.coffee new file mode 100644 index 0000000..1446f5f --- /dev/null +++ b/app/express-example/templates/mvc-coffee/app/models/article.coffee @@ -0,0 +1,23 @@ +# Example model +<% if(options.database == 'mongodb'){ %> +mongoose = require 'mongoose' +Schema = mongoose.Schema + +ArticleSchema = new Schema( + title: String + url: String + text: String +) + +ArticleSchema.virtual('date') + .get (-> this._id.getTimestamp()) + +mongoose.model 'Article', ArticleSchema<% } %> +<% if(options.database == 'mysql' || options.database == 'postgresql'){ %> +module.exports = (sequelize, DataTypes) -> + + Article = sequelize.define 'Article', + title: DataTypes.STRING, + url: DataTypes.STRING, + text: DataTypes.STRING +<% } %>
\ No newline at end of file diff --git a/app/express-example/templates/mvc-coffee/config/config.coffee b/app/express-example/templates/mvc-coffee/config/config.coffee new file mode 100644 index 0000000..051934c --- /dev/null +++ b/app/express-example/templates/mvc-coffee/config/config.coffee @@ -0,0 +1,42 @@ +path = require 'path' +rootPath = path.normalize __dirname + '/..' +env = process.env.NODE_ENV || 'development' + +config = + development: + root: rootPath + app: + name: '<%= _.slugify(appname) %>' + port: 3000<% if(options.database == 'mongodb'){ %> + db: 'mongodb://localhost/<%= _.slugify(appname) %>-development' + <% } %><% if(options.database == 'mysql'){ %> + db: 'mysql://localhost/<%= _.slugify(appname) %>-development' + <% } %><% if(options.database == 'postgresql'){ %> + db: 'postgres://localhost/<%= _.slugify(appname) %>-development' + <% } %> + + test: + root: rootPath + app: + name: '<%= _.slugify(appname) %>' + port: 3000<% if(options.database == 'mongodb'){ %> + db: 'mongodb://localhost/<%= _.slugify(appname) %>-test' + <% } %><% if(options.database == 'mysql'){ %> + db: 'mysql://localhost/<%= _.slugify(appname) %>-test' + <% } %><% if(options.database == 'postgresql'){ %> + db: 'postgres://localhost/<%= _.slugify(appname) %>-test' + <% } %> + + production: + root: rootPath + app: + name: '<%= _.slugify(appname) %>' + port: 3000<% if(options.database == 'mongodb'){ %> + db: 'mongodb://localhost/<%= _.slugify(appname) %>-production' + <% } %><% if(options.database == 'mysql'){ %> + db: 'mysql://localhost/<%= _.slugify(appname) %>-production' + <% } %><% if(options.database == 'postgresql'){ %> + db: 'postgres://localhost/<%= _.slugify(appname) %>-production' + <% } %> + +module.exports = config[env] diff --git a/app/express-example/templates/mvc-coffee/config/express.coffee b/app/express-example/templates/mvc-coffee/config/express.coffee new file mode 100644 index 0000000..9ca1b1c --- /dev/null +++ b/app/express-example/templates/mvc-coffee/config/express.coffee @@ -0,0 +1,55 @@ +express = require 'express' +glob = require 'glob' + +favicon = require 'serve-favicon' +logger = require 'morgan' +cookieParser = require 'cookie-parser' +bodyParser = require 'body-parser' +compress = require 'compression' +methodOverride = require 'method-override' + +module.exports = (app, config) -> + app.set 'views', config.root + '/app/views' + app.set 'view engine', '<%= options.viewEngine %>' + + # app.use(favicon(config.root + '/public/img/favicon.ico')); + app.use logger 'dev' + app.use bodyParser.json() + app.use bodyParser.urlencoded( + extended: true + ) + app.use cookieParser() + app.use compress() + app.use express.static config.root + '/public' + app.use methodOverride() + + controllers = glob.sync config.root + '/app/controllers/**/*.coffee' + controllers.forEach (controller) -> + require(controller)(app); + + # catch 404 and forward to error handler + app.use (req, res, next) -> + err = new Error 'Not Found' + err.status = 404 + next err + + # error handlers + + # development error handler + # will print stacktrace + if app.get('env') == 'development' + app.use (err, req, res, next) -> + res.status err.status || 500 + res.render 'error', + message: err.message + error: err + title: 'error' + + # production error handler + # no stacktraces leaked to user + app.use (err, req, res, next) -> + res.status err.status || 500 + res.render 'error', + message: err.message + error: {} + title: 'error' diff --git a/app/express-example/templates/mvc-coffee/package.json b/app/express-example/templates/mvc-coffee/package.json new file mode 100644 index 0000000..f5802ac --- /dev/null +++ b/app/express-example/templates/mvc-coffee/package.json @@ -0,0 +1,46 @@ +{ + "name": "<%= _.slugify(appname) %>", + "version": "0.0.1", + "private": true, + "scripts": { + "start": "node app.js" + }, + "dependencies": { + "express": "~4.2.0", + "serve-favicon": "~2.0.1", + "morgan": "~1.1.1", + "cookie-parser": "~1.3.2", + "body-parser": "~1.4.3", + "compression": "~1.0.8", + "method-override": "~2.1.1", + "glob": "~4.0.5"<% if(options.database == 'mongodb'){ %>, + "mongoose": "~3.8.12"<% } %><% if(options.database == 'mysql'){ %>, + "sequelize": "~1.7.9", + "lodash": "~2.4.1", + "mysql": "~2.4.0"<% } %><% if(options.database == 'postgresql'){ %>, + "sequelize": "~1.7.9", + "lodash": "~2.4.1", + "pg": "~3.4.0"<% } %><% if(options.viewEngine == 'jade'){ %>, + "jade": "~1.3.0"<% } %><% if(options.viewEngine == 'ejs'){ %>, + "ejs": "~1.0.0"<% } %> + }, + "devDependencies": {<% if(options.buildTool == 'grunt'){ %> + "grunt": "~0.4.5", + "grunt-develop": "~0.4.0"<% if(options.cssPreprocessor == 'sass'){ %>, + "grunt-contrib-sass": "^0.8.1"<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + "grunt-sass": "^0.16.1"<% } %><% if(options.cssPreprocessor == 'less'){ %>, + "grunt-contrib-less": "^0.12.0"<% } %>, + "grunt-contrib-watch": "~0.6.1", + "grunt-contrib-compass": "~0.9.0", + "request": "~2.36.0", + "time-grunt": "~0.3.2", + "load-grunt-tasks": "~0.6.0", + "coffee-script": "^1.7.1"<% } %><% if(options.buildTool == 'gulp'){ %> + "gulp": "~3.8.8"<% if(options.cssPreprocessor == 'sass'){ %>, + "gulp-ruby-sass": "^0.7.1"<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + "gulp-sass": "^1.2.2"<% } %><% if(options.cssPreprocessor == 'less'){ %>, + "gulp-less": "^1.3.6"<% } %>, + "gulp-nodemon": "~1.0.4", + "gulp-livereload": "~2.1.1"<% } %> + } +} diff --git a/app/express-example/templates/mvc/app.js b/app/express-example/templates/mvc/app.js new file mode 100644 index 0000000..7894745 --- /dev/null +++ b/app/express-example/templates/mvc/app.js @@ -0,0 +1,32 @@ +var express = require('express'), + config = require('./config/config')<% if(options.database == 'none'){ %>;<% } %><% if(options.database == 'mongodb'){ %>, + glob = require('glob'), + mongoose = require('mongoose');<% } %><% if(options.database == 'mysql' || options.database == 'postgresql'){ %>, + db = require('./app/models');<% } %> +<% if(options.database == 'mongodb'){ %> +mongoose.connect(config.db); +var db = mongoose.connection; +db.on('error', function () { + throw new Error('unable to connect to database at ' + config.db); +}); + +var models = glob.sync(config.root + '/app/models/*.js'); +models.forEach(function (model) { + require(model); +});<% } %> +var app = express(); + +require('./config/express')(app, config); +<% if(options.database == 'mysql' || options.database == 'postgresql'){ %> +db.sequelize + .sync() + .complete(function (err) { + if(err){ + throw err[0]; + }else{ + app.listen(config.port); + } + }); +<% } else { %> +app.listen(config.port); +<% } %> diff --git a/app/express-example/templates/mvc/app/controllers/home.js b/app/express-example/templates/mvc/app/controllers/home.js new file mode 100644 index 0000000..277fea4 --- /dev/null +++ b/app/express-example/templates/mvc/app/controllers/home.js @@ -0,0 +1,23 @@ +var express = require('express'), + router = express.Router(),<% if(options.database == 'mongodb'){ %> + mongoose = require('mongoose'), + Article = mongoose.model('Article');<% } %><% if(options.database == 'mysql' || options.database == 'postgresql'){ %> + db = require('../models');<% } %><% if(options.database == 'none'){ %> + Article = require('../models/article');<% } %> + +module.exports = function (app) { + app.use('/', router); +}; + +router.get('/', function (req, res, next) { +<% if(options.database == 'mongodb'){ %> + Article.find(function (err, articles) { + if (err) return next(err);<% } %><% if(options.database == 'mysql' || options.database == 'postgresql'){ %> + db.Article.findAll().success(function (articles) {<% } %><% if(options.database == 'none'){ %> + var articles = [new Article(), new Article()];<% } %> + res.render('index', { + title: 'Generator-Express MVC', + articles: articles + });<% if(options.database !== 'none'){ %> + });<% } %> +}); diff --git a/app/express-example/templates/mvc/app/models/article.js b/app/express-example/templates/mvc/app/models/article.js new file mode 100644 index 0000000..866a3df --- /dev/null +++ b/app/express-example/templates/mvc/app/models/article.js @@ -0,0 +1,38 @@ +// Example model +<% if(options.database == 'mongodb'){ %> +var mongoose = require('mongoose'), + Schema = mongoose.Schema; + +var ArticleSchema = new Schema({ + title: String, + url: String, + text: String +}); + +ArticleSchema.virtual('date') + .get(function(){ + return this._id.getTimestamp(); + }); + +mongoose.model('Article', ArticleSchema);<% } %> +<% if(options.database == 'mysql' || options.database == 'postgresql'){ %> +module.exports = function (sequelize, DataTypes) { + + var Article = sequelize.define('Article', { + title: DataTypes.STRING, + url: DataTypes.STRING, + text: DataTypes.STRING + }); + + return Article; +}; +<% } %><% if(options.database == 'none'){ %> +function Article (opts) { + if(!opts) opts = {}; + this.title = opts.title || ''; + this.url = opts.url || ''; + this.text = opts.text || ''; +} + +module.exports = Article; +<% } %> diff --git a/app/express-example/templates/mvc/config/config.js b/app/express-example/templates/mvc/config/config.js new file mode 100644 index 0000000..92cd1b2 --- /dev/null +++ b/app/express-example/templates/mvc/config/config.js @@ -0,0 +1,49 @@ +var path = require('path'), + rootPath = path.normalize(__dirname + '/..'), + env = process.env.NODE_ENV || 'development'; + +var config = { + development: { + root: rootPath, + app: { + name: '<%= _.slugify(appname) %>' + }, + port: 3000,<% if(options.database == 'mongodb'){ %> + db: 'mongodb://localhost/<%= _.slugify(appname) %>-development' + <% } %><% if(options.database == 'mysql'){ %> + db: 'mysql://localhost/<%= _.slugify(appname) %>-development' + <% } %><% if(options.database == 'postgresql'){ %> + db: 'postgres://localhost/<%= _.slugify(appname) %>-development' + <% } %> + }, + + test: { + root: rootPath, + app: { + name: '<%= _.slugify(appname) %>' + }, + port: 3000,<% if(options.database == 'mongodb'){ %> + db: 'mongodb://localhost/<%= _.slugify(appname) %>-test' + <% } %><% if(options.database == 'mysql'){ %> + db: 'mysql://localhost/<%= _.slugify(appname) %>-test' + <% } %><% if(options.database == 'postgresql'){ %> + db: 'postgres://localhost/<%= _.slugify(appname) %>-test' + <% } %> + }, + + production: { + root: rootPath, + app: { + name: '<%= _.slugify(appname) %>' + }, + port: 3000,<% if(options.database == 'mongodb'){ %> + db: 'mongodb://localhost/<%= _.slugify(appname) %>-production' + <% } %><% if(options.database == 'mysql'){ %> + db: 'mysql://localhost/<%= _.slugify(appname) %>-production' + <% } %><% if(options.database == 'postgresql'){ %> + db: 'postgres://localhost/<%= _.slugify(appname) %>-production' + <% } %> + } +}; + +module.exports = config[env]; diff --git a/app/express-example/templates/mvc/config/express.js b/app/express-example/templates/mvc/config/express.js new file mode 100644 index 0000000..a74ec73 --- /dev/null +++ b/app/express-example/templates/mvc/config/express.js @@ -0,0 +1,57 @@ +var express = require('express'); +var glob = require('glob'); + +var favicon = require('serve-favicon'); +var logger = require('morgan'); +var cookieParser = require('cookie-parser'); +var bodyParser = require('body-parser'); +var compress = require('compression'); +var methodOverride = require('method-override'); + +module.exports = function(app, config) { + app.set('views', config.root + '/app/views'); + app.set('view engine', '<%= options.viewEngine %>'); + + // app.use(favicon(config.root + '/public/img/favicon.ico')); + app.use(logger('dev')); + app.use(bodyParser.json()); + app.use(bodyParser.urlencoded({ + extended: true + })); + app.use(cookieParser()); + app.use(compress()); + app.use(express.static(config.root + '/public')); + app.use(methodOverride()); + + var controllers = glob.sync(config.root + '/app/controllers/*.js'); + controllers.forEach(function (controller) { + require(controller)(app); + }); + + app.use(function (req, res, next) { + var err = new Error('Not Found'); + err.status = 404; + next(err); + }); + + if(app.get('env') === 'development'){ + app.use(function (err, req, res, next) { + res.status(err.status || 500); + res.render('error', { + message: err.message, + error: err, + title: 'error' + }); + }); + } + + app.use(function (err, req, res, next) { + res.status(err.status || 500); + res.render('error', { + message: err.message, + error: {}, + title: 'error' + }); + }); + +}; diff --git a/app/express-example/templates/mvc/package.json b/app/express-example/templates/mvc/package.json new file mode 100644 index 0000000..62eda82 --- /dev/null +++ b/app/express-example/templates/mvc/package.json @@ -0,0 +1,46 @@ +{ + "name": "<%= _.slugify(appname) %>", + "version": "0.0.1", + "private": true, + "scripts": { + "start": "node app.js" + }, + "dependencies": { + "express": "~4.2.0", + "glob": "^4.0.5", + "serve-favicon": "~2.0.1", + "morgan": "~1.1.1", + "cookie-parser": "~1.3.2", + "body-parser": "~1.4.3", + "compression": "~1.0.8", + "method-override": "~2.1.1", + "glob": "~4.0.5"<% if(options.database == 'mongodb'){ %>, + "mongoose": "~3.8.12"<% } %><% if(options.database == 'mysql'){ %>, + "sequelize": "~1.7.9", + "lodash": "~2.4.1", + "mysql": "~2.4.0"<% } %><% if(options.database == 'postgresql'){ %>, + "sequelize": "~1.7.9", + "lodash": "~2.4.1", + "pg": "~3.4.0"<% } %><% if(options.viewEngine == 'jade'){ %>, + "jade": "~1.3.0"<% } %><% if(options.viewEngine == 'ejs'){ %>, + "ejs": "~1.0.0"<% } %> + }, + "devDependencies": {<% if(options.buildTool == 'grunt'){ %> + "grunt": "~0.4.5", + "grunt-develop": "~0.4.0"<% if(options.cssPreprocessor == 'sass'){ %>, + "grunt-contrib-sass": "^0.8.1"<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + "grunt-sass": "^0.16.1"<% } %><% if(options.cssPreprocessor == 'less'){ %>, + "grunt-contrib-less": "^0.12.0"<% } %>, + "grunt-contrib-watch": "~0.6.1", + "grunt-contrib-compass": "~0.9.0", + "request": "~2.36.0", + "time-grunt": "~0.3.2", + "load-grunt-tasks": "~0.6.0"<% } %><% if(options.buildTool == 'gulp'){ %> + "gulp": "~3.8.8"<% if(options.cssPreprocessor == 'sass'){ %>, + "gulp-ruby-sass": "^0.7.1"<% } %><% if(options.cssPreprocessor == 'node-sass'){ %>, + "gulp-sass": "^1.2.2"<% } %><% if(options.cssPreprocessor == 'less'){ %>, + "gulp-less": "^1.3.6"<% } %>, + "gulp-nodemon": "~1.0.4", + "gulp-livereload": "~2.1.1"<% } %> + } +} diff --git a/app/express-example/templates/views/ejs/error.ejs b/app/express-example/templates/views/ejs/error.ejs new file mode 100644 index 0000000..c2d4fa3 --- /dev/null +++ b/app/express-example/templates/views/ejs/error.ejs @@ -0,0 +1,7 @@ +<% include header %> + + <%- message %> + <%- error.status %> + <%- error.stack %> + +<% include footer %>
\ No newline at end of file diff --git a/app/express-example/templates/views/ejs/footer.ejs b/app/express-example/templates/views/ejs/footer.ejs new file mode 100644 index 0000000..691287b --- /dev/null +++ b/app/express-example/templates/views/ejs/footer.ejs @@ -0,0 +1,2 @@ +</body> +</html>
\ No newline at end of file diff --git a/app/express-example/templates/views/ejs/header.ejs b/app/express-example/templates/views/ejs/header.ejs new file mode 100644 index 0000000..0424eb7 --- /dev/null +++ b/app/express-example/templates/views/ejs/header.ejs @@ -0,0 +1,10 @@ +<!doctype html> +<html lang="en"> +<head> + <meta charset="UTF-8"> + <meta name="viewport" content="width=device-width"> + <title><%-title %></title> + <link rel="stylesheet" href="/css/style.css"> + <script src="http://localhost:35729/livereload.js"></script> +</head> +<body> diff --git a/app/express-example/templates/views/ejs/index.ejs b/app/express-example/templates/views/ejs/index.ejs new file mode 100644 index 0000000..306db20 --- /dev/null +++ b/app/express-example/templates/views/ejs/index.ejs @@ -0,0 +1,6 @@ +<% include header %> + + <h1><%-title %></h1> + <p>Welcome to <%-title %></p> + +<% include footer %>
\ No newline at end of file diff --git a/app/express-example/templates/views/jade/error.jade b/app/express-example/templates/views/jade/error.jade new file mode 100644 index 0000000..51ec12c --- /dev/null +++ b/app/express-example/templates/views/jade/error.jade @@ -0,0 +1,6 @@ +extends layout + +block content + h1= message + h2= error.status + pre #{error.stack} diff --git a/app/express-example/templates/views/jade/index.jade b/app/express-example/templates/views/jade/index.jade new file mode 100644 index 0000000..3d63b9a --- /dev/null +++ b/app/express-example/templates/views/jade/index.jade @@ -0,0 +1,5 @@ +extends layout + +block content + h1= title + p Welcome to #{title} diff --git a/app/express-example/templates/views/jade/layout.jade b/app/express-example/templates/views/jade/layout.jade new file mode 100644 index 0000000..31e2f68 --- /dev/null +++ b/app/express-example/templates/views/jade/layout.jade @@ -0,0 +1,12 @@ +doctype html +html(lang='en') + head + meta(charset='UTF-8') + meta(name='viewport', content='width=device-width') + title= title + block css + link(rel='stylesheet', href='/css/style.css') + block js + script(src='http://localhost:35729/livereload.js') + body + block content |
