h8 0.2.2 → 0.2.3

Sign up to get free protection for your applications and to get access to all the features.
data/spec/coffee_spec.rb CHANGED
@@ -23,6 +23,56 @@ describe 'coffeescript' do
23
23
  H8::Coffee.eval(Cs_0).should == Res_0
24
24
  H8::Context.eval(H8::Coffee.compile Cs_0).should == Res_0
25
25
  H8::Context.eval(H8::Coffee.compile Cs_0).should == Res_0
26
+ H8::Context.new.coffee(Cs_0).should == Res_0
27
+ end
28
+
29
+ it 'should report syntax errors' do
30
+ script = <<-END
31
+ # Started: ok
32
+ square = (x) -> x*x
33
+ # so far so good but then...
34
+ baljkhl9399-^&
35
+ # above is bad
36
+ END
37
+ # pending
38
+ expect(->{
39
+ H8::Coffee.compile script, file_name: 'test.coffee'
40
+ }).to raise_error(H8::JsError) { |e| e.to_s.should =~ /test.coffee\:4/ }
41
+ end
42
+
43
+ it 'should report exceptions' do
44
+ src = <<-END
45
+ fnb = ->
46
+ throw new Error 'lets check'
47
+ fna = ->
48
+ fnb()
49
+ CoffeeScript.getSourceMap = (name) ->
50
+ puts "DUMMUY \#{name}"
51
+ undefined
52
+
53
+ # fna()
54
+ puts globalsIncluded
55
+ END
56
+ script = <<-END
57
+ function require(name) {
58
+ puts("REQ! "+name);
59
+ }
60
+ var res = CoffeeScript.compile(src, {sourceMap: true, filename: 'inner.coffee'});
61
+ //var sourceMaps = { 'inner.coffee' : res.sourceMap }
62
+ // puts("Compiled ok",JSON.stringify(CoffeeScript.sourceMaps));
63
+ // CoffeeScript.sourceMaps['inner'] = res.sourceMap
64
+ eval(res.js);
65
+ END
66
+ cxt = H8::Coffee.new.context
67
+ cxt[:puts] = -> (*args) { puts args.join(' ') }
68
+ cxt[:src] = src
69
+ # cxt[:src] = 'return "hello"'
70
+ begin
71
+ res = cxt.eval script, file_name: 'extest.coffee'
72
+ p res
73
+ rescue Exception=>e
74
+ puts e
75
+ end
26
76
  end
27
77
 
28
78
  end
@@ -0,0 +1,72 @@
1
+ require 'spec_helper'
2
+ require 'h8/command'
3
+ require 'stringio'
4
+
5
+ describe 'cli' do
6
+
7
+ before :each do
8
+ @out = StringIO.new '', 'w'
9
+ @err = StringIO.new '', 'w'
10
+ @command = H8::Command.new out: @out, err: @err
11
+ end
12
+
13
+ def output
14
+ @out.string
15
+ end
16
+
17
+ def errors
18
+ @err.string
19
+ end
20
+
21
+ def run *args
22
+ @out.string = ''
23
+ @err.string = ''
24
+ @command.run *(['-e'] + args)
25
+ output
26
+ end
27
+
28
+ def make_path *path_components
29
+ File.expand_path(File.join(File.dirname(__FILE__), *path_components))
30
+ end
31
+
32
+ it 'should print usage' do
33
+ expect(-> { @command.run }).to raise_error(RuntimeError, "Must provide at least one file")
34
+ expect(@command.usage =~ /Usage:/).to be_truthy
35
+ # puts @command.usage
36
+ end
37
+
38
+ it 'should print' do
39
+ run 'print "hello"; console.log "world"; console.error "life sucks!"'
40
+ output.should == "hello\nworld\n"
41
+ errors.should == "life sucks!\n"
42
+ end
43
+
44
+ it 'should read files' do
45
+ path = make_path '../lib/h8/coffee-script.js'
46
+ length = "#{open(path).read.length}\n"
47
+ run("print open('#{path}').read().length").should == length
48
+ run("open('#{path}', 'r', (f) -> puts (" "+f.read().length) )").should == length
49
+ end
50
+
51
+ it 'should run tests' do
52
+ begin
53
+ @command.run make_path('coffee/cli_tests.coffee')
54
+ rescue
55
+ puts "Error: #{$!}\n#{$!.backtrace.join("\n")}"
56
+ end
57
+ log = @out.string.lines
58
+ failed = log[-1] !~ /All tests passed/
59
+ err = @err.string.strip
60
+ if err != ''
61
+ puts '----------- Tests Error output ---------------'
62
+ puts @err.string
63
+ end
64
+ if log.length > 1
65
+ puts '---------------- Tests output --------------------'
66
+ puts log[0..-2].join('')
67
+ puts '--------------- End tests output -----------------'
68
+ end
69
+ failed and fail 'cli_tests.coffee failed'
70
+ end
71
+ end
72
+
data/spec/context_spec.rb CHANGED
@@ -94,6 +94,27 @@ describe 'context' do
94
94
  c.eval script
95
95
  end
96
96
 
97
+ it 'should have coffee generators' do
98
+ script = <<-End
99
+ f = (base) ->
100
+ count = base;
101
+ end = base + 3;
102
+ print "F is calleed, \#{count}"
103
+ while count < end
104
+ r = yield count++
105
+ # print "yield returned \#{r}"
106
+ print 'we try'
107
+ g = f(100)
108
+ print g.next().value
109
+ print g.next().value
110
+ print g.next().value
111
+ print g.next().value
112
+ End
113
+ c = H8::Context.new
114
+ c[:print] = -> (*args) { args.join(' ') }
115
+ c.coffee script
116
+ end
117
+
97
118
  it 'should work in many threads' do
98
119
  # pending
99
120
  sum = 0
@@ -125,5 +146,4 @@ describe 'context' do
125
146
  }
126
147
  end
127
148
 
128
-
129
149
  end
data/spec/js_gate_spec.rb CHANGED
@@ -83,6 +83,44 @@ describe 'js_gate' do
83
83
  obj.foo.should == 'bar'
84
84
  end
85
85
 
86
+ it 'should keep alive references to js objects' do
87
+ cxt = H8::Context.new
88
+ jobj = cxt.eval 'var obj={foo: "bar"}; obj;'
89
+ jobj.foo.should == 'bar'
90
+ cxt.eval 'var obj = {foo: "buzz"};'
91
+ GC.start
92
+ cxt.javascript_gc()
93
+ jobj.foo.should == 'bar'
94
+ jobj.foo.should == 'bar'
95
+ wobj = WeakRef.new jobj
96
+ jobj = nil
97
+ GC.start
98
+ expect(wobj.weakref_alive?).not_to be_truthy
99
+ cxt.javascript_gc()
100
+ cxt = nil
101
+ GC.start
102
+ end
103
+
104
+ it 'should keep alive references to ruby objects' do
105
+ robj = 4096.times.map { |n| "-- #{n} --"}
106
+ wobj = WeakRef.new robj
107
+ cxt = H8::Context.new
108
+ cxt[:obj] = robj
109
+ GC.start
110
+ cxt.javascript_gc
111
+ expect(wobj.weakref_alive?).to be_truthy
112
+ robj = nil
113
+ GC.start
114
+ cxt.javascript_gc
115
+ expect(wobj.weakref_alive?).to be_truthy
116
+ cxt.eval 'obj = null;'
117
+ cxt[:obj] = 'nope'
118
+ cxt.javascript_gc
119
+ GC.start
120
+ # pending # Why weakref is not freeed here?
121
+ # expect(wobj.weakref_alive?).to be_falsey
122
+ end
123
+
86
124
  it 'should convert simple types to ruby' do
87
125
  res = H8::Context.eval("({ 'foo': 'bar', 'bar': 122, pi: 3.1415 });")
88
126
  r = res.foo.to_ruby
@@ -189,7 +227,21 @@ describe 'js_gate' do
189
227
  expect(-> {
190
228
  res.doAdd(10, 1).should == 111
191
229
  }).to raise_error(H8::JsError) { |e|
192
- e.message.should == "Uncaught Error: Test error"
230
+ e.message.should =~ /Test error/
231
+ }
232
+ end
233
+
234
+ it 'should properly show syntax errors' do
235
+ script = <<-End
236
+ // Good line
237
+ var x = 112;
238
+ kjljl44; // bad line
239
+ 122; // good line
240
+ End
241
+ expect(->{
242
+ H8::Context.new.eval script, file_name: 'test.js'
243
+ }).to raise_error(H8::JsError) { |e|
244
+ e.message.should =~ /at test\.js\:3\:7/
193
245
  }
194
246
  end
195
247
 
@@ -0,0 +1,67 @@
1
+ require 'spec_helper'
2
+ require 'h8'
3
+ require 'h8/pargser'
4
+
5
+ describe 'pargser' do
6
+
7
+ it 'should parse keys' do
8
+ parser = H8::Pargser.new "-a -b -v value! other data".split
9
+ parser.key('-a', doc: 'flag to perform a action') {
10
+ @a_called = true
11
+ }
12
+ .key('-c', '-b') {
13
+ @b_called = true
14
+ }
15
+ .key('--some', default: 'test') { |v|
16
+ @defvalue = v
17
+ }
18
+ .key('-v', needs_value: true) { |v|
19
+ @v = v
20
+ }
21
+ expect(-> { parser.key('-a') }).to raise_error(H8::Pargser::Error)
22
+
23
+ passed = []
24
+ rest = parser.parse { |a| passed << a }
25
+ rest.should == passed
26
+ rest.should == ['other', 'data']
27
+
28
+ @a_called.should be_truthy
29
+ @b_called.should be_true
30
+ @v.should == 'value!'
31
+ @defvalue.should == 'test'
32
+
33
+ doc = "\t-a\n\t\tflag to perform a action\n\t-c,-b\n\t--some value (default: test)\n\t-v value (optional)"
34
+ parser.keys_doc.should == doc
35
+ end
36
+
37
+ it 'should detect required keys' do
38
+ parser = H8::Pargser.new ['hello']
39
+ parser.key('-c', needs_value: true) {}
40
+ expect(-> { parser.parse }).to raise_error(H8::Pargser::Error, 'Required key is missing: -c')
41
+ end
42
+
43
+ it 'should detect strange keys' do
44
+ parser = H8::Pargser.new '-l hello'.split
45
+ expect(->{ parser.parse }).to raise_error(H8::Pargser::Error, 'Unknown key -l')
46
+ end
47
+
48
+ it 'should pass data that looks like keys' do
49
+ res = H8::Pargser.new('-- -a --b'.split).parse
50
+ res.should == ['-a', '--b']
51
+ end
52
+
53
+ it 'should provide empty defaults' do
54
+ parser = H8::Pargser.new('hello'.split)
55
+ @t == 'wrong'
56
+ parser.key('-t', default: nil) { |val|
57
+ @t = val
58
+ }
59
+ parser.key('-q', default: false) { |val|
60
+ @q = val
61
+ }
62
+ parser.parse.should == ['hello']
63
+ @t.should == nil
64
+ @q.should == false
65
+ end
66
+
67
+ end
@@ -66,8 +66,24 @@ describe 'ruby gate' do
66
66
  nil
67
67
  }
68
68
  cxt.eval('fn();').should == nil
69
+ cxt.eval('""+fn()').should == 'null'
69
70
  end
70
71
 
72
+ it 'should convert strings to native string' do
73
+ cxt = H8::Context.new
74
+ cxt[:str] = src = "Пример строки"
75
+ res = 'ПРИМЕР СТРОКИ'
76
+ cxt.eval('str.toLocaleUpperCase()').should == res
77
+ up = cxt.eval('fn = function(t) { return t.toLocaleUpperCase(); }')
78
+ up.call(src).should == res
79
+ end
80
+
81
+ # it 'should convert arrays' do
82
+ # cxt = H8::Context.new
83
+ # cxt[:arr] = [1,100,2,200]
84
+ # p cxt.eval('typeof arr')
85
+ # end
86
+
71
87
  it 'should pass through ruby objects across js code' do
72
88
  class MyObject
73
89
  attr :some_val
@@ -150,6 +166,7 @@ describe 'ruby gate' do
150
166
  e.name.should == 'Error'
151
167
  e.message.should =~ /test/
152
168
  e.javascript_backtrace.should =~ /at bad \(eval\:4\:17\)/
169
+ e.to_s.should =~ /at bad \(eval\:4\:17\)/
153
170
  end
154
171
  end
155
172
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: h8
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.2
4
+ version: 0.2.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - sergeych
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-01-02 00:00:00.000000000 Z
11
+ date: 2015-01-06 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -72,7 +72,8 @@ description: |2
72
72
  integration where objects can be passed between different languages several times.
73
73
  email:
74
74
  - real.sergeych@gmail.com
75
- executables: []
75
+ executables:
76
+ - h8
76
77
  extensions:
77
78
  - ext/h8/extconf.rb
78
79
  extra_rdoc_files: []
@@ -83,6 +84,13 @@ files:
83
84
  - LICENSE.txt
84
85
  - README.md
85
86
  - Rakefile
87
+ - benchmark/big.txt
88
+ - benchmark/knightsmove.coffee
89
+ - benchmark/knigthsmove.rb
90
+ - benchmark/process_text.coffee
91
+ - benchmark/text_process.rb
92
+ - benchmark/tools.rb
93
+ - bin/h8
86
94
  - ext/.DS_Store
87
95
  - ext/h8/.cproject
88
96
  - ext/h8/.project
@@ -101,16 +109,22 @@ files:
101
109
  - ext/h8/ruby_gate.h
102
110
  - hybrid8.gemspec
103
111
  - lib/h8.rb
104
- - lib/h8/coffee-script.js
105
112
  - lib/h8/coffee.rb
113
+ - lib/h8/command.rb
106
114
  - lib/h8/context.rb
107
115
  - lib/h8/errors.rb
116
+ - lib/h8/pargser.rb
108
117
  - lib/h8/tools.rb
109
118
  - lib/h8/value.rb
110
119
  - lib/h8/version.rb
120
+ - lib/scripts/coffee-script.js
121
+ - lib/scripts/globals.coffee
122
+ - spec/coffee/cli_tests.coffee
111
123
  - spec/coffee_spec.rb
124
+ - spec/command_spec.rb
112
125
  - spec/context_spec.rb
113
126
  - spec/js_gate_spec.rb
127
+ - spec/pargser_spec.rb
114
128
  - spec/ruby_gate_spec.rb
115
129
  - spec/spec_helper.rb
116
130
  - spec/threading_spec.rb
@@ -140,9 +154,12 @@ signing_key:
140
154
  specification_version: 4
141
155
  summary: Minimalistic and fast Ruby <--> V8 integration
142
156
  test_files:
157
+ - spec/coffee/cli_tests.coffee
143
158
  - spec/coffee_spec.rb
159
+ - spec/command_spec.rb
144
160
  - spec/context_spec.rb
145
161
  - spec/js_gate_spec.rb
162
+ - spec/pargser_spec.rb
146
163
  - spec/ruby_gate_spec.rb
147
164
  - spec/spec_helper.rb
148
165
  - spec/threading_spec.rb