This repository has been archived by the owner on Nov 6, 2019. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Cakefile
208 lines (185 loc) · 5.24 KB
/
Cakefile
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
# Based on Cakefile Template.
files = [
'lib'
'src'
]
fs = require 'fs'
{print} = require 'util'
{spawn, exec} = require 'child_process'
try
which = require('which').sync
catch err
if process.platform.match(/^win/)?
console.log 'WARNING: the which module is required for windows\ntry: npm install which'
which = null
# ANSI Terminal Colors
bold = '\x1b[0;1m'
green = '\x1b[0;32m'
reset = '\x1b[0m'
red = '\x1b[0;31m'
###*
* Build
* Builds Source. Can watch.
###
task 'build', 'compile source', (o) -> build o, -> log ":)", green
###*
* Watch
* Builds and watches.
###
task 'watch', 'short for [cake --watch build]', (o) -> (o.watch = true) and build o, -> log ":-)", green
###*
* Start
* Run the application. Can watch.
###
task 'start', 'start the app', (o) -> build -> (if o.watch then nodemon else start) o, -> log ":D", green
###*
* Test
* Runs your test suite. Can watch.
###
task 'test', 'run tests', (o) -> build -> mocha o, -> log ":)", green
###*
* Clean
* Cleans up generated js files.
###
task 'clean', 'clean generated files', -> clean -> log ";)", green
###*
* Watch
* Watch option for build, start or test.
###
option '-w', '--watch', 'set build, start, or test in watching mode (ex: [cake -w test])'
# Internal Functions
#
# ## *walk*
#
# **given** string as dir which represents a directory in relation to local directory
# **and** callback as done in the form of (err, results)
# **then** recurse through directory returning an array of files
#
# Examples
#
# ``` coffeescript
# walk 'src', (err, results) -> console.log results
# ```
walk = (dir, done) ->
results = []
fs.readdir dir, (err, list) ->
return done(err, []) if err
pending = list.length
return done(null, results) unless pending
for name in list
file = "#{dir}/#{name}"
try
stat = fs.statSync file
catch err
stat = null
if stat?.isDirectory()
walk file, (err, res) ->
results.push name for name in res
done(null, results) unless --pending
else
results.push file
done(null, results) unless --pending
# ## *log*
#
# **given** string as a message
# **and** string as a color
# **and** optional string as an explanation
# **then** builds a statement and logs to console.
#
log = (message, color, explanation) -> console.log color + message + reset + ' ' + (explanation or '')
# ## *launch*
#
# **given** string as a cmd
# **and** optional array and option flags
# **and** optional callback
# **then** spawn cmd with options
# **and** pipe to process stdout and stderr respectively
# **and** on child process exit emit callback if set and status is 0
launch = (cmd, options=[], callback) ->
cmd = which(cmd) if which
app = spawn cmd, options
app.stdout.pipe(process.stdout)
app.stderr.pipe(process.stderr)
app.on 'exit', (status) -> callback?() if status is 0
# ## *build*
#
# **given** optional object as argv
# **and** optional function as callback
# **then** invoke launch passing coffee command
# **and** defaulted options to compile src to app
build = (argv, callback) ->
if typeof argv is 'function'
callback = argv
argv = {}
options = ['-c', '-b']
options.push '-w' if 'watch' of argv
options = options.concat ['-o', files...]
launch './node_modules/coffee-script/bin/coffee', options, callback
# ## *start*
#
# **given** optional object as argv
# **and** optional function as callback
# **then** invoke launch passing node command
start = (argv, callback) ->
if typeof argv is 'function'
callback = argv
argv = {}
options = ['lib/index.js']
log 'Running application', green
launch 'node', options, callback
# ## *nodemon*
#
# **given** optional object as argv
# **and** optional function as callback
# **then** invoke launch passing nodemon command
# **and** defaulted options to watch lib/*
nodemon = (argv, callback) ->
if typeof argv is 'function'
callback = argv
argv = {}
options = ['-w', 'lib/']
launch './node_modules/nodemon/bin/nodemon.js', options, callback
# ## *unlinkIfCoffeeFile*
#
# **given** string as file
# **and** file ends in '.coffee'
# **then** convert '.coffee' to '.js'
# **and** remove the result
unlinkIfCoffeeFile = (file) ->
if file.match /\.coffee$/
fs.unlink file.replace('src','lib').replace(/\.coffee$/, '.js'), ->
true
else false
# ## *clean*
#
# **given** optional function as callback
# **then** loop through files variable
# **and** call unlinkIfCoffeeFile on each
clean = (callback) ->
try
for file in files
unless unlinkIfCoffeeFile file
walk file, (err, results) ->
for f in results
unlinkIfCoffeeFile f
callback?()
catch err
# ## *mocha*
#
# **given** optional command line arguments
# **and** optional function as callback
# **then** invoke launch passing mocha command
mocha = (argv, callback) ->
if typeof argv is 'function'
callback = argv
argv = {}
options = ['--recursive', '--compilers', 'coffee:coffee-script/register', '--require', 'must']
# Decide which output method to use based on whether we're watching or not.
if 'watch' of argv
options.push '--reporter'
options.push 'list'
options.push '--watch'
else
options.push '--reporter'
options.push 'spec'
launch './node_modules/mocha/bin/_mocha', options, callback