mirror of
https://github.com/jashkenas/coffeescript.git
synced 2022-11-09 12:23:24 -05:00
unifying all of the server-side evaluation under CoffeeScript.run -- this means that __filename and __dirname and relative requires should work from all angles under Node.js
This commit is contained in:
parent
0bc7719572
commit
06b50ecb98
9 changed files with 43 additions and 27 deletions
5
Cakefile
5
Cakefile
|
@ -73,6 +73,5 @@ task 'test', 'run the CoffeeScript language test suite', ->
|
||||||
puts '\033[0;32mpassed ' + test_count + ' tests in ' + time + ' seconds\033[0m'
|
puts '\033[0;32mpassed ' + test_count + ' tests in ' + time + ' seconds\033[0m'
|
||||||
fs.readdir 'test', (err, files) ->
|
fs.readdir 'test', (err, files) ->
|
||||||
for file in files
|
for file in files
|
||||||
fs.readFile 'test/' + file, (err, source) ->
|
fs.readFile 'test/' + file, (err, code) ->
|
||||||
js: coffee.compile source
|
coffee.run code, file
|
||||||
process.compile js, file
|
|
|
@ -52,7 +52,7 @@
|
||||||
throw new Error("Cakefile not found in " + (process.cwd()));
|
throw new Error("Cakefile not found in " + (process.cwd()));
|
||||||
}
|
}
|
||||||
args = process.argv.slice(2, process.argv.length);
|
args = process.argv.slice(2, process.argv.length);
|
||||||
eval(coffee.compile(fs.readFileSync('Cakefile')));
|
coffee.run(fs.readFileSync('Cakefile'), 'Cakefile');
|
||||||
oparse = new optparse.OptionParser(switches);
|
oparse = new optparse.OptionParser(switches);
|
||||||
if (!(args.length)) {
|
if (!(args.length)) {
|
||||||
return print_tasks();
|
return print_tasks();
|
||||||
|
|
|
@ -34,6 +34,15 @@
|
||||||
exports.nodes = function nodes(code) {
|
exports.nodes = function nodes(code) {
|
||||||
return parser.parse(lexer.tokenize(code));
|
return parser.parse(lexer.tokenize(code));
|
||||||
};
|
};
|
||||||
|
// Compile and execute a string of CoffeeScript (on the server), correctly
|
||||||
|
// setting `__filename`, `__dirname`, and relative `require()`.
|
||||||
|
exports.run = function run(code, source, options) {
|
||||||
|
var __dirname, __filename;
|
||||||
|
__filename = source;
|
||||||
|
__dirname = path.dirname(source);
|
||||||
|
module.filename = source;
|
||||||
|
return eval(exports.compile(code, options));
|
||||||
|
};
|
||||||
// The real Lexer produces a generic stream of tokens. This object provides a
|
// The real Lexer produces a generic stream of tokens. This object provides a
|
||||||
// thin wrapper around it, compatible with the Jison API. We can then pass it
|
// thin wrapper around it, compatible with the Jison API. We can then pass it
|
||||||
// directly as a "Jison lexer".
|
// directly as a "Jison lexer".
|
||||||
|
|
|
@ -80,13 +80,15 @@
|
||||||
// in common. If evaluating the script directly sets `__filename`, `__dirname`
|
// in common. If evaluating the script directly sets `__filename`, `__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) {
|
compile_script = function compile_script(source, code) {
|
||||||
var __dirname, __filename, js, o;
|
var js, o;
|
||||||
o = options;
|
o = options;
|
||||||
try {
|
try {
|
||||||
if (o.tokens) {
|
if (o.tokens) {
|
||||||
return print_tokens(CoffeeScript.tokens(code));
|
return print_tokens(CoffeeScript.tokens(code));
|
||||||
} else if (o.nodes) {
|
} else if (o.nodes) {
|
||||||
return puts(CoffeeScript.nodes(code).toString());
|
return puts(CoffeeScript.nodes(code).toString());
|
||||||
|
} else if (o.run) {
|
||||||
|
return CoffeeScript.run(code, source, compile_options());
|
||||||
} else {
|
} else {
|
||||||
js = CoffeeScript.compile(code, compile_options());
|
js = CoffeeScript.compile(code, compile_options());
|
||||||
if (o.compile) {
|
if (o.compile) {
|
||||||
|
@ -95,11 +97,6 @@
|
||||||
return lint(js);
|
return lint(js);
|
||||||
} else if (o.print || o.eval) {
|
} else if (o.print || o.eval) {
|
||||||
return print(js);
|
return print(js);
|
||||||
} else {
|
|
||||||
__filename = source;
|
|
||||||
__dirname = path.dirname(source);
|
|
||||||
module.filename = source;
|
|
||||||
return eval(js);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
|
@ -199,8 +196,10 @@
|
||||||
// Use the [OptionParser module](optparse.html) to extract all options from
|
// Use the [OptionParser module](optparse.html) to extract all options from
|
||||||
// `process.argv` that are specified in `SWITCHES`.
|
// `process.argv` that are specified in `SWITCHES`.
|
||||||
parse_options = function parse_options() {
|
parse_options = function parse_options() {
|
||||||
|
var o;
|
||||||
option_parser = new optparse.OptionParser(SWITCHES, BANNER);
|
option_parser = new optparse.OptionParser(SWITCHES, BANNER);
|
||||||
options = option_parser.parse(process.argv);
|
o = (options = option_parser.parse(process.argv));
|
||||||
|
options.run = !(o.compile || o.print || o.lint || o.eval);
|
||||||
return sources = options.arguments.slice(2, options.arguments.length);
|
return sources = options.arguments.slice(2, options.arguments.length);
|
||||||
};
|
};
|
||||||
// The compile-time options to pass to the CoffeeScript compiler.
|
// The compile-time options to pass to the CoffeeScript compiler.
|
||||||
|
|
14
lib/repl.js
14
lib/repl.js
|
@ -1,5 +1,5 @@
|
||||||
(function(){
|
(function(){
|
||||||
var CoffeeScript, prompt, quit, run;
|
var CoffeeScript, prompt, run;
|
||||||
// A very simple Read-Eval-Print-Loop. Compiles one line at a time to JavaScript
|
// A very simple Read-Eval-Print-Loop. Compiles one line at a time to JavaScript
|
||||||
// and evaluates it. Good for simple tests, or poking around the **Node.js** API.
|
// and evaluates it. Good for simple tests, or poking around the **Node.js** API.
|
||||||
// Using it looks like this:
|
// Using it looks like this:
|
||||||
|
@ -9,19 +9,21 @@
|
||||||
// Our prompt.
|
// Our prompt.
|
||||||
prompt = 'coffee> ';
|
prompt = 'coffee> ';
|
||||||
// Quick alias for quitting the REPL.
|
// Quick alias for quitting the REPL.
|
||||||
quit = function quit() {
|
process.mixin({
|
||||||
return process.exit(0);
|
quit: function quit() {
|
||||||
};
|
return process.exit(0);
|
||||||
|
}
|
||||||
|
});
|
||||||
// The main REPL function. **run** is called every time a line of code is entered.
|
// The main REPL function. **run** is called every time a line of code is entered.
|
||||||
// Attempt to evaluate the command. If there's an exception, print it out instead
|
// Attempt to evaluate the command. If there's an exception, print it out instead
|
||||||
// of exiting.
|
// of exiting.
|
||||||
run = function run(code) {
|
run = function run(code) {
|
||||||
var val;
|
var val;
|
||||||
try {
|
try {
|
||||||
val = eval(CoffeeScript.compile(code, {
|
val = CoffeeScript.run(code, 'repl', {
|
||||||
no_wrap: true,
|
no_wrap: true,
|
||||||
globals: true
|
globals: true
|
||||||
}));
|
});
|
||||||
if (val !== undefined) {
|
if (val !== undefined) {
|
||||||
p(val);
|
p(val);
|
||||||
}
|
}
|
||||||
|
|
|
@ -46,7 +46,7 @@ exports.run: ->
|
||||||
path.exists 'Cakefile', (exists) ->
|
path.exists 'Cakefile', (exists) ->
|
||||||
throw new Error("Cakefile not found in ${process.cwd()}") unless exists
|
throw new Error("Cakefile not found in ${process.cwd()}") unless exists
|
||||||
args: process.argv[2...process.argv.length]
|
args: process.argv[2...process.argv.length]
|
||||||
eval coffee.compile fs.readFileSync 'Cakefile'
|
coffee.run fs.readFileSync('Cakefile'), 'Cakefile'
|
||||||
oparse: new optparse.OptionParser switches
|
oparse: new optparse.OptionParser switches
|
||||||
return print_tasks() unless args.length
|
return print_tasks() unless args.length
|
||||||
options: oparse.parse(args)
|
options: oparse.parse(args)
|
||||||
|
|
|
@ -35,6 +35,14 @@ exports.tokens: (code) ->
|
||||||
exports.nodes: (code) ->
|
exports.nodes: (code) ->
|
||||||
parser.parse lexer.tokenize code
|
parser.parse lexer.tokenize code
|
||||||
|
|
||||||
|
# Compile and execute a string of CoffeeScript (on the server), correctly
|
||||||
|
# setting `__filename`, `__dirname`, and relative `require()`.
|
||||||
|
exports.run: (code, source, options) ->
|
||||||
|
__filename: source
|
||||||
|
__dirname: path.dirname source
|
||||||
|
module.filename: source
|
||||||
|
eval exports.compile code, options
|
||||||
|
|
||||||
# The real Lexer produces a generic stream of tokens. This object provides a
|
# The real Lexer produces a generic stream of tokens. This object provides a
|
||||||
# thin wrapper around it, compatible with the Jison API. We can then pass it
|
# thin wrapper around it, compatible with the Jison API. We can then pass it
|
||||||
# directly as a "Jison lexer".
|
# directly as a "Jison lexer".
|
||||||
|
|
|
@ -78,16 +78,12 @@ compile_script: (source, code) ->
|
||||||
try
|
try
|
||||||
if o.tokens then print_tokens CoffeeScript.tokens code
|
if o.tokens then print_tokens CoffeeScript.tokens code
|
||||||
else if o.nodes then puts CoffeeScript.nodes(code).toString()
|
else if o.nodes then puts CoffeeScript.nodes(code).toString()
|
||||||
|
else if o.run then CoffeeScript.run code, source, compile_options()
|
||||||
else
|
else
|
||||||
js: CoffeeScript.compile code, compile_options()
|
js: CoffeeScript.compile code, compile_options()
|
||||||
if o.compile then write_js source, js
|
if o.compile then write_js source, js
|
||||||
else if o.lint then lint js
|
else if o.lint then lint js
|
||||||
else if o.print or o.eval then print js
|
else if o.print or o.eval then print js
|
||||||
else
|
|
||||||
__filename: source
|
|
||||||
__dirname: path.dirname source
|
|
||||||
module.filename: source
|
|
||||||
eval 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
|
||||||
|
|
||||||
|
@ -142,8 +138,9 @@ print_tokens: (tokens) ->
|
||||||
# `process.argv` that are specified in `SWITCHES`.
|
# `process.argv` that are specified in `SWITCHES`.
|
||||||
parse_options: ->
|
parse_options: ->
|
||||||
option_parser: new optparse.OptionParser SWITCHES, BANNER
|
option_parser: new optparse.OptionParser SWITCHES, BANNER
|
||||||
options: option_parser.parse(process.argv)
|
o: options: option_parser.parse(process.argv)
|
||||||
sources: options.arguments[2...options.arguments.length]
|
options.run: not (o.compile or o.print or o.lint or o.eval)
|
||||||
|
sources: options.arguments[2...options.arguments.length]
|
||||||
|
|
||||||
# The compile-time options to pass to the CoffeeScript compiler.
|
# The compile-time options to pass to the CoffeeScript compiler.
|
||||||
compile_options: ->
|
compile_options: ->
|
||||||
|
|
|
@ -11,14 +11,16 @@ CoffeeScript: require 'coffee-script'
|
||||||
prompt: 'coffee> '
|
prompt: 'coffee> '
|
||||||
|
|
||||||
# Quick alias for quitting the REPL.
|
# Quick alias for quitting the REPL.
|
||||||
quit: -> process.exit(0)
|
process.mixin {
|
||||||
|
quit: -> process.exit(0)
|
||||||
|
}
|
||||||
|
|
||||||
# The main REPL function. **run** is called every time a line of code is entered.
|
# The main REPL function. **run** is called every time a line of code is entered.
|
||||||
# Attempt to evaluate the command. If there's an exception, print it out instead
|
# Attempt to evaluate the command. If there's an exception, print it out instead
|
||||||
# of exiting.
|
# of exiting.
|
||||||
run: (code) ->
|
run: (code) ->
|
||||||
try
|
try
|
||||||
val: eval CoffeeScript.compile code, {no_wrap: true, globals: true}
|
val: CoffeeScript.run code, 'repl', {no_wrap: true, globals: true}
|
||||||
p val if val isnt undefined
|
p val if val isnt undefined
|
||||||
catch err
|
catch err
|
||||||
puts err.stack or err.toString()
|
puts err.stack or err.toString()
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue