merged in Trevor Burnham's recursive coffee compilation, with some adjustments...
This commit is contained in:
parent
c051daee2f
commit
d64b8fd9d8
121
lib/command.js
121
lib/command.js
|
@ -1,5 +1,5 @@
|
||||||
(function(){
|
(function(){
|
||||||
var BANNER, CoffeeScript, SWITCHES, _a, base, compile_options, compile_script, compile_scripts, compile_stdio, exec, fs, is_watched, lint, option_parser, options, optparse, parse_options, path, print_tokens, sources, spawn, usage, version, watch, write_js;
|
var BANNER, CoffeeScript, SWITCHES, _a, compile_options, compile_script, compile_scripts, compile_stdio, exec, fs, lint, option_parser, options, optparse, parse_options, path, print_tokens, sources, spawn, usage, version, watch, write_js;
|
||||||
// The `coffee` utility. Handles command-line compilation of CoffeeScript
|
// The `coffee` utility. Handles command-line compilation of CoffeeScript
|
||||||
// into various forms: saved into `.js` files or printed to stdout, piped to
|
// into various forms: saved into `.js` files or printed to stdout, piped to
|
||||||
// [JSLint](http://javascriptlint.com/) or recompiled every time the source is
|
// [JSLint](http://javascriptlint.com/) or recompiled every time the source is
|
||||||
|
@ -16,12 +16,10 @@
|
||||||
// The help banner that is printed when `coffee` is called without arguments.
|
// The help banner that is printed when `coffee` is called without arguments.
|
||||||
BANNER = 'coffee compiles CoffeeScript source files into JavaScript.\n\nUsage:\n coffee path/to/script.coffee';
|
BANNER = 'coffee compiles CoffeeScript source files into JavaScript.\n\nUsage:\n coffee path/to/script.coffee';
|
||||||
// The list of all the valid option flags that `coffee` knows how to handle.
|
// The list of all the valid option flags that `coffee` knows how to handle.
|
||||||
SWITCHES = [['-c', '--compile', 'compile to JavaScript and save as .js files'], ['-i', '--interactive', 'run an interactive CoffeeScript REPL'], ['-o', '--output [DIR]', 'set the directory for compiled JavaScript'], ['-w', '--watch', 'watch scripts for changes, and recompile'], ['-p', '--print', 'print the compiled JavaScript to stdout'], ['-m', '--monitor', 'show a message every time a script is compiled'], ['-l', '--lint', 'pipe the compiled JavaScript through JSLint'], ['-s', '--stdio', 'listen for and compile scripts over stdio'], ['-e', '--eval', 'compile a string from the command line'], ['--no-wrap', 'compile without the top-level function wrapper'], ['-t', '--tokens', 'print the tokens that the lexer produces'], ['-n', '--nodes', 'print the parse tree that Jison produces'], ['-v', '--version', 'display CoffeeScript version'], ['-h', '--help', 'display this help message']];
|
SWITCHES = [['-c', '--compile', 'compile to JavaScript and save as .js files'], ['-i', '--interactive', 'run an interactive CoffeeScript REPL'], ['-o', '--output [DIR]', 'set the directory for compiled JavaScript'], ['-w', '--watch', 'watch scripts for changes, and recompile'], ['-p', '--print', 'print the compiled JavaScript to stdout'], ['-l', '--lint', 'pipe the compiled JavaScript through JSLint'], ['-s', '--stdio', 'listen for and compile scripts over stdio'], ['-e', '--eval', 'compile a string from the command line'], ['--no-wrap', 'compile without the top-level function wrapper'], ['-t', '--tokens', 'print the tokens that the lexer produces'], ['-n', '--nodes', 'print the parse tree that Jison produces'], ['-v', '--version', 'display CoffeeScript version'], ['-h', '--help', 'display this help message']];
|
||||||
// Top-level objects shared by all the functions.
|
// Top-level objects shared by all the functions.
|
||||||
options = {};
|
options = {};
|
||||||
sources = [];
|
sources = [];
|
||||||
base = '';
|
|
||||||
is_watched = {};
|
|
||||||
option_parser = null;
|
option_parser = null;
|
||||||
// Run `coffee` by parsing passed options and determining what action to take.
|
// Run `coffee` by parsing passed options and determining what action to take.
|
||||||
// Many flags cause us to divert before compiling anything. Flags passed after
|
// Many flags cause us to divert before compiling anything. Flags passed after
|
||||||
|
@ -60,62 +58,48 @@
|
||||||
// compile them. If a directory is passed, recursively compile all source
|
// compile them. If a directory is passed, recursively compile all source
|
||||||
// files in it and all subdirectories.
|
// files in it and all subdirectories.
|
||||||
compile_scripts = function compile_scripts() {
|
compile_scripts = function compile_scripts() {
|
||||||
var compile, run;
|
var _b, _c, _d, _e, base, compile, source;
|
||||||
compile = function compile(source) {
|
_b = []; _d = sources;
|
||||||
if (is_watched[source]) {
|
for (_c = 0, _e = _d.length; _c < _e; _c++) {
|
||||||
return null;
|
source = _d[_c];
|
||||||
}
|
_b.push((function() {
|
||||||
return path.exists(source, function(exists) {
|
base = source;
|
||||||
if (!(exists)) {
|
compile = function compile(source) {
|
||||||
throw new Error(("File not found: " + source));
|
return path.exists(source, function(exists) {
|
||||||
}
|
if (!(exists)) {
|
||||||
return fs.stat(source, function(err, stats) {
|
throw new Error(("File not found: " + source));
|
||||||
if (stats.isDirectory()) {
|
}
|
||||||
return fs.readdir(source, function(err, files) {
|
return fs.stat(source, function(err, stats) {
|
||||||
var _b, _c, _d, _e, file;
|
if (stats.isDirectory()) {
|
||||||
_b = []; _d = files;
|
return fs.readdir(source, function(err, files) {
|
||||||
for (_c = 0, _e = _d.length; _c < _e; _c++) {
|
var _f, _g, _h, _i, file;
|
||||||
file = _d[_c];
|
_f = []; _h = files;
|
||||||
_b.push(compile(path.join(source, file)));
|
for (_g = 0, _i = _h.length; _g < _i; _g++) {
|
||||||
|
file = _h[_g];
|
||||||
|
_f.push(compile(path.join(source, file)));
|
||||||
|
}
|
||||||
|
return _f;
|
||||||
|
});
|
||||||
|
} else if (path.extname(source) === '.coffee') {
|
||||||
|
fs.readFile(source, function(err, code) {
|
||||||
|
return compile_script(source, code, base);
|
||||||
|
});
|
||||||
|
if (options.watch) {
|
||||||
|
return watch(source, base);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return _b;
|
|
||||||
});
|
});
|
||||||
} else if (source === base || path.extname(source) === '.coffee') {
|
});
|
||||||
if (options.monitor) {
|
};
|
||||||
puts('Compiling ' + source);
|
return compile(source);
|
||||||
}
|
})());
|
||||||
fs.readFile(source, function(err, code) {
|
|
||||||
return compile_script(source, code);
|
|
||||||
});
|
|
||||||
if (options.watch) {
|
|
||||||
return watch(source);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
});
|
|
||||||
};
|
|
||||||
run = function run() {
|
|
||||||
var _b, _c, _d, _e, source;
|
|
||||||
_b = []; _d = sources;
|
|
||||||
for (_c = 0, _e = _d.length; _c < _e; _c++) {
|
|
||||||
source = _d[_c];
|
|
||||||
_b.push((function() {
|
|
||||||
base = source;
|
|
||||||
return compile(source);
|
|
||||||
})());
|
|
||||||
}
|
|
||||||
return _b;
|
|
||||||
};
|
|
||||||
run();
|
|
||||||
if (options.watch) {
|
|
||||||
return setInterval(run, 500);
|
|
||||||
}
|
}
|
||||||
|
return _b;
|
||||||
};
|
};
|
||||||
// Compile a single source script, containing the given code, according to the
|
// Compile a single source script, containing the given code, according to the
|
||||||
// requested options. Both compile_scripts and watch_scripts share this method
|
// requested options. If evaluating the script directly sets `__filename`,
|
||||||
// in common. If evaluating the script directly sets `__filename`, `__dirname`
|
// `__dirname` and `module.filename` to be correct relative to the script's path.
|
||||||
// and `module.filename` to be correct relative to the script's path.
|
compile_script = function compile_script(source, code, base) {
|
||||||
compile_script = function compile_script(source, code) {
|
|
||||||
var code_opts, js, o;
|
var code_opts, js, o;
|
||||||
o = options;
|
o = options;
|
||||||
code_opts = compile_options(source);
|
code_opts = compile_options(source);
|
||||||
|
@ -131,7 +115,7 @@
|
||||||
if (o.print) {
|
if (o.print) {
|
||||||
return print(js);
|
return print(js);
|
||||||
} else if (o.compile) {
|
} else if (o.compile) {
|
||||||
return write_js(source, js);
|
return write_js(source, js, base);
|
||||||
} else if (o.lint) {
|
} else if (o.lint) {
|
||||||
return lint(js);
|
return lint(js);
|
||||||
}
|
}
|
||||||
|
@ -162,8 +146,7 @@
|
||||||
// Watch a source CoffeeScript file using `fs.watchFile`, recompiling it every
|
// Watch a source CoffeeScript file using `fs.watchFile`, recompiling it every
|
||||||
// time the file is updated. May be used in combination with other options,
|
// time the file is updated. May be used in combination with other options,
|
||||||
// such as `--lint` or `--print`.
|
// such as `--lint` or `--print`.
|
||||||
watch = function watch(source) {
|
watch = function watch(source, base) {
|
||||||
is_watched[source] = true;
|
|
||||||
return fs.watchFile(source, {
|
return fs.watchFile(source, {
|
||||||
persistent: true,
|
persistent: true,
|
||||||
interval: 500
|
interval: 500
|
||||||
|
@ -171,25 +154,33 @@
|
||||||
if (curr.mtime.getTime() === prev.mtime.getTime()) {
|
if (curr.mtime.getTime() === prev.mtime.getTime()) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
if (options.monitor) {
|
if (options.compile) {
|
||||||
puts('Recompiling ' + source);
|
puts(("Compiled " + source));
|
||||||
}
|
}
|
||||||
return fs.readFile(source, function(err, code) {
|
return fs.readFile(source, function(err, code) {
|
||||||
return compile_script(source, code);
|
return compile_script(source, code, base);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
// Write out a JavaScript source file with the compiled code. By default, files
|
// Write out a JavaScript source file with the compiled code. By default, files
|
||||||
// are written out in `cwd` as `.js` files with the same name, but the output
|
// are written out in `cwd` as `.js` files with the same name, but the output
|
||||||
// directory can be customized with `--output`.
|
// directory can be customized with `--output`.
|
||||||
write_js = function write_js(source, js) {
|
write_js = function write_js(source, js, base) {
|
||||||
var dir, filename, js_path, src_dir;
|
var base_dir, compile, dir, filename, js_path, src_dir;
|
||||||
filename = path.basename(source, path.extname(source)) + '.js';
|
filename = path.basename(source, path.extname(source)) + '.js';
|
||||||
src_dir = path.dirname(source);
|
src_dir = path.dirname(source);
|
||||||
dir = options.output ? path.join(options.output, src_dir.substring(base.length)) : src_dir;
|
base_dir = src_dir.substring(base.length);
|
||||||
|
dir = options.output ? path.join(options.output, base_dir) : src_dir;
|
||||||
js_path = path.join(dir, filename);
|
js_path = path.join(dir, filename);
|
||||||
return exec(("mkdir -p " + dir), function(error, stdout, stderr) {
|
compile = function compile() {
|
||||||
return fs.writeFile(js_path, js);
|
return fs.writeFile(js_path, js);
|
||||||
|
};
|
||||||
|
return path.exists(dir, function(exists) {
|
||||||
|
if (exists) {
|
||||||
|
return compile();
|
||||||
|
} else {
|
||||||
|
return exec(("mkdir -p " + dir), compile);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
// Pipe compiled JS through JSLint (requires a working `jsl` command), printing
|
// Pipe compiled JS through JSLint (requires a working `jsl` command), printing
|
||||||
|
|
|
@ -26,7 +26,6 @@ SWITCHES: [
|
||||||
['-o', '--output [DIR]', 'set the directory for compiled JavaScript']
|
['-o', '--output [DIR]', 'set the directory for compiled JavaScript']
|
||||||
['-w', '--watch', 'watch scripts for changes, and recompile']
|
['-w', '--watch', 'watch scripts for changes, and recompile']
|
||||||
['-p', '--print', 'print the compiled JavaScript to stdout']
|
['-p', '--print', 'print the compiled JavaScript to stdout']
|
||||||
['-m', '--monitor', 'show a message every time a script is compiled']
|
|
||||||
['-l', '--lint', 'pipe the compiled JavaScript through JSLint']
|
['-l', '--lint', 'pipe the compiled JavaScript through JSLint']
|
||||||
['-s', '--stdio', 'listen for and compile scripts over stdio']
|
['-s', '--stdio', 'listen for and compile scripts over stdio']
|
||||||
['-e', '--eval', 'compile a string from the command line']
|
['-e', '--eval', 'compile a string from the command line']
|
||||||
|
@ -40,8 +39,6 @@ SWITCHES: [
|
||||||
# Top-level objects shared by all the functions.
|
# Top-level objects shared by all the functions.
|
||||||
options: {}
|
options: {}
|
||||||
sources: []
|
sources: []
|
||||||
base: ''
|
|
||||||
is_watched: {}
|
|
||||||
option_parser: null
|
option_parser: null
|
||||||
|
|
||||||
# Run `coffee` by parsing passed options and determining what action to take.
|
# Run `coffee` by parsing passed options and determining what action to take.
|
||||||
|
@ -67,34 +64,25 @@ exports.run: ->
|
||||||
# compile them. If a directory is passed, recursively compile all source
|
# compile them. If a directory is passed, recursively compile all source
|
||||||
# files in it and all subdirectories.
|
# files in it and all subdirectories.
|
||||||
compile_scripts: ->
|
compile_scripts: ->
|
||||||
compile: (source) ->
|
for source in sources
|
||||||
return if is_watched[source]
|
base: source
|
||||||
path.exists source, (exists) ->
|
compile: (source) ->
|
||||||
throw new Error "File not found: $source" unless exists
|
path.exists source, (exists) ->
|
||||||
fs.stat source, (err, stats) ->
|
throw new Error "File not found: $source" unless exists
|
||||||
if stats.isDirectory()
|
fs.stat source, (err, stats) ->
|
||||||
fs.readdir source, (err, files) ->
|
if stats.isDirectory()
|
||||||
for file in files
|
fs.readdir source, (err, files) ->
|
||||||
compile path.join(source, file)
|
for file in files
|
||||||
else if source == base or path.extname(source) == '.coffee'
|
compile path.join(source, file)
|
||||||
puts 'Compiling ' + source if options.monitor
|
else if path.extname(source) is '.coffee'
|
||||||
fs.readFile source, (err, code) -> compile_script(source, code)
|
fs.readFile source, (err, code) -> compile_script(source, code, base)
|
||||||
watch(source) if options.watch
|
watch source, base if options.watch
|
||||||
|
compile source
|
||||||
run: ->
|
|
||||||
for source in sources
|
|
||||||
base = source
|
|
||||||
compile(source)
|
|
||||||
|
|
||||||
run()
|
|
||||||
if options.watch
|
|
||||||
setInterval run, 500
|
|
||||||
|
|
||||||
# Compile a single source script, containing the given code, according to the
|
# Compile a single source script, containing the given code, according to the
|
||||||
# requested options. Both compile_scripts and watch_scripts share this method
|
# requested options. If evaluating the script directly sets `__filename`,
|
||||||
# in common. If evaluating the script directly sets `__filename`, `__dirname`
|
# `__dirname` and `module.filename` to be correct relative to the script's path.
|
||||||
# and `module.filename` to be correct relative to the script's path.
|
compile_script: (source, code, base) ->
|
||||||
compile_script: (source, code) ->
|
|
||||||
o: options
|
o: options
|
||||||
code_opts: compile_options source
|
code_opts: compile_options source
|
||||||
try
|
try
|
||||||
|
@ -104,7 +92,7 @@ compile_script: (source, code) ->
|
||||||
else
|
else
|
||||||
js: CoffeeScript.compile code, code_opts
|
js: CoffeeScript.compile code, code_opts
|
||||||
if o.print then print js
|
if o.print then print js
|
||||||
else if o.compile then write_js source, js
|
else if o.compile then write_js source, js, base
|
||||||
else if o.lint then lint js
|
else if o.lint then lint js
|
||||||
catch err
|
catch err
|
||||||
if o.watch then puts err.message else throw err
|
if o.watch then puts err.message else throw err
|
||||||
|
@ -122,23 +110,24 @@ compile_stdio: ->
|
||||||
# Watch a source CoffeeScript file using `fs.watchFile`, recompiling it every
|
# Watch a source CoffeeScript file using `fs.watchFile`, recompiling it every
|
||||||
# time the file is updated. May be used in combination with other options,
|
# time the file is updated. May be used in combination with other options,
|
||||||
# such as `--lint` or `--print`.
|
# such as `--lint` or `--print`.
|
||||||
watch: (source) ->
|
watch: (source, base) ->
|
||||||
is_watched[source] = true
|
|
||||||
fs.watchFile source, {persistent: true, interval: 500}, (curr, prev) ->
|
fs.watchFile source, {persistent: true, interval: 500}, (curr, prev) ->
|
||||||
return if curr.mtime.getTime() is prev.mtime.getTime()
|
return if curr.mtime.getTime() is prev.mtime.getTime()
|
||||||
puts 'Recompiling ' + source if options.monitor
|
puts "Compiled $source" if options.compile
|
||||||
fs.readFile source, (err, code) -> compile_script(source, code)
|
fs.readFile source, (err, code) -> compile_script(source, code, base)
|
||||||
|
|
||||||
# Write out a JavaScript source file with the compiled code. By default, files
|
# Write out a JavaScript source file with the compiled code. By default, files
|
||||||
# are written out in `cwd` as `.js` files with the same name, but the output
|
# are written out in `cwd` as `.js` files with the same name, but the output
|
||||||
# directory can be customized with `--output`.
|
# directory can be customized with `--output`.
|
||||||
write_js: (source, js) ->
|
write_js: (source, js, base) ->
|
||||||
filename: path.basename(source, path.extname(source)) + '.js'
|
filename: path.basename(source, path.extname(source)) + '.js'
|
||||||
src_dir: path.dirname(source)
|
src_dir: path.dirname source
|
||||||
dir: if options.output then \
|
base_dir: src_dir.substring base.length
|
||||||
path.join options.output, src_dir.substring(base.length) else src_dir
|
dir: if options.output then path.join options.output, base_dir else src_dir
|
||||||
js_path: path.join dir, filename
|
js_path: path.join dir, filename
|
||||||
exec "mkdir -p $dir", (error, stdout, stderr) -> fs.writeFile js_path, js
|
compile: -> fs.writeFile js_path, js
|
||||||
|
path.exists dir, (exists) ->
|
||||||
|
if exists then compile() else exec "mkdir -p $dir", compile
|
||||||
|
|
||||||
# Pipe compiled JS through JSLint (requires a working `jsl` command), printing
|
# Pipe compiled JS through JSLint (requires a working `jsl` command), printing
|
||||||
# any errors or warnings that arise.
|
# any errors or warnings that arise.
|
||||||
|
|
Loading…
Reference in New Issue