This repository has been archived by the owner. It is now read-only.
Permalink
Browse files

Use ExecJS

  • Loading branch information...
josh committed Mar 10, 2011
1 parent 779c03b commit 4a4bb56dca40b59bd61705ac47d31b072bec1458
Showing with 9 additions and 150 deletions.
  1. +1 −1 coffee-script.gemspec
  2. +7 −125 lib/coffee_script.rb
  3. +1 −24 test/test_coffee_script.rb
View
@@ -17,7 +17,7 @@ Gem::Specification.new do |s|
]
s.add_dependency 'coffee-script-source'
- s.add_development_dependency 'therubyracer'
+ s.add_dependency 'execjs'
s.authors = ['Jeremy Ashkenas', 'Joshua Peek', 'Sam Stephenson']
s.email = 'josh@joshpeek.com'
View
@@ -1,20 +1,17 @@
-require 'json'
-require 'tempfile'
-
+require 'execjs'
require 'coffee_script/source'
module CoffeeScript
- class Error < ::StandardError; end
- class EngineError < Error; end
- class CompilationError < Error; end
+ EngineError = ExecJS::RuntimeError
+ CompilationError = ExecJS::ProgramError
module Source
def self.path
@path ||= ENV['COFFEESCRIPT_SOURCE_PATH'] || bundled_path
end
def self.path=(path)
- @contents = @version = @bare_option = nil
+ @contents = @version = @bare_option = @context = nil
@path = path
end
@@ -29,126 +26,17 @@ def self.version
def self.bare_option
@bare_option ||= contents.match(/noWrap/) ? 'noWrap' : 'bare'
end
- end
-
- module ExternalEngine
- class << self
- def compile(command, script, options)
- yield f = Tempfile.open("coffee.js")
- f.puts compile_js(script, options)
- f.close
-
- execute("#{command} #{f.path}")
- ensure
- f.close! if f
- end
-
- def execute(command)
- out = `#{command}`.chomp
- if $?.success?
- status, result = out[0, 1], out[1..-1]
- if status == "+"
- result
- else
- raise CompilationError, result[/^(?:Error: )?(.*)/, 1]
- end
- else
- raise EngineError, out
- end
- end
-
- def compile_js(script, options)
- options = options[:bare] ? "{#{Source.bare_option} : true}" : "{}"
- <<-JS
- try {
- print('+' + CoffeeScript.compile(#{script.to_json}, #{options}));
- } catch (e) {
- print('-' + e);
- }
- JS
- end
- end
- end
-
- module Engines
- module JavaScriptCore
- BIN = "/System/Library/Frameworks/JavaScriptCore.framework/Versions/A/Resources/jsc"
-
- class << self
- def supported?
- File.exist?(BIN)
- end
-
- def compile(script, options = {})
- ExternalEngine.compile(BIN, script, options) do |f|
- f.puts "load(#{Source.path.to_json});"
- end
- end
- end
- end
-
- module Node
- class << self
-
- def binary
- @binary ||= `sh -c "which nodejs node"`.split("\n").first
- end
-
- def binary=(value)
- @binary = value.nil? ? nil : value.to_s
- end
-
- def supported?
- binary
- end
-
- def compile(script, options = {})
- ExternalEngine.compile(binary, script, options) do |f|
- f.puts Source.contents
- f.puts "var CoffeeScript = this.CoffeeScript, print = console.log;"
- end
- end
- end
- end
-
- module V8
- class << self
- def supported?
- require 'v8'
- true
- rescue LoadError
- false
- end
-
- def compile(script, options = {})
- coffee_module['compile'].call(script, Source.bare_option => options[:bare])
- rescue ::V8::JSError => e
- raise CompilationError, e.message
- end
- private
- def coffee_module
- @coffee_module ||= build_coffee_module
- end
-
- def build_coffee_module
- context = ::V8::Context.new
- context.eval(Source.contents)
- context['CoffeeScript']
- rescue ::V8::JSError => e
- raise EngineError, e.message
- end
- end
+ def self.context
+ @context ||= ExecJS.compile(contents)
end
end
class << self
def engine
- @engine ||= nil
end
def engine=(engine)
- @engine = engine
end
def version
@@ -166,13 +54,7 @@ def compile(script, options = {})
options[:bare] = false
end
- engine.compile(script, options)
+ Source.context.call("CoffeeScript.compile", script, options)
end
end
-
- self.engine ||= [
- Engines::V8,
- Engines::Node,
- Engines::JavaScriptCore
- ].detect(&:supported?)
end
View
@@ -2,7 +2,7 @@
require 'test/unit'
require 'stringio'
-module CoffeeScriptTests
+class TestCoffeeScript < Test::Unit::TestCase
def test_compile
assert_equal "(function() {\n puts('Hello, World!');\n}).call(this);\n",
CoffeeScript.compile("puts 'Hello, World!'\n")
@@ -40,33 +40,10 @@ def test_compilation_error
end
end
- def test_error_messages_omit_leading_error_string
- assert_exception_does_not_match(/^Error: /) { CoffeeScript.compile("unless") } # parse error
- assert_exception_does_not_match(/^Error: /) { CoffeeScript.compile("function") } # syntax error
- end
-
def assert_exception_does_not_match(pattern)
yield
flunk "no exception raised"
rescue Exception => e
assert_no_match pattern, e.message
end
end
-
-CoffeeScript::Engines.constants.each do |const|
- engine = CoffeeScript::Engines.const_get(const)
- unless engine.supported?
- warn "*** skipping #{const} tests"
- next
- end
-
- instance_eval <<-RUBY, __FILE__, __LINE__ + 1
- class Test#{const} < Test::Unit::TestCase
- include CoffeeScriptTests
-
- def setup
- CoffeeScript.engine = CoffeeScript::Engines::#{const}
- end
- end
- RUBY
-end

0 comments on commit 4a4bb56

Please sign in to comment.