ruby2js 1.15.1 → 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (53) hide show
  1. data/lib/ruby2js.rb +36 -36
  2. data/lib/ruby2js/converter.rb +59 -20
  3. data/lib/ruby2js/converter/arg.rb +1 -1
  4. data/lib/ruby2js/converter/args.rb +1 -1
  5. data/lib/ruby2js/converter/array.rb +3 -4
  6. data/lib/ruby2js/converter/begin.rb +15 -1
  7. data/lib/ruby2js/converter/block.rb +6 -5
  8. data/lib/ruby2js/converter/boolean.rb +1 -1
  9. data/lib/ruby2js/converter/break.rb +1 -1
  10. data/lib/ruby2js/converter/case.rb +27 -7
  11. data/lib/ruby2js/converter/casgn.rb +5 -2
  12. data/lib/ruby2js/converter/class.rb +41 -11
  13. data/lib/ruby2js/converter/const.rb +1 -1
  14. data/lib/ruby2js/converter/cvar.rb +4 -3
  15. data/lib/ruby2js/converter/cvasgn.rb +5 -6
  16. data/lib/ruby2js/converter/def.rb +15 -3
  17. data/lib/ruby2js/converter/defined.rb +1 -1
  18. data/lib/ruby2js/converter/defs.rb +7 -3
  19. data/lib/ruby2js/converter/dstr.rb +3 -3
  20. data/lib/ruby2js/converter/for.rb +7 -10
  21. data/lib/ruby2js/converter/hash.rb +70 -34
  22. data/lib/ruby2js/converter/if.rb +35 -13
  23. data/lib/ruby2js/converter/in.rb +1 -1
  24. data/lib/ruby2js/converter/ivasgn.rb +1 -1
  25. data/lib/ruby2js/converter/kwbegin.rb +20 -20
  26. data/lib/ruby2js/converter/literal.rb +1 -1
  27. data/lib/ruby2js/converter/logical.rb +4 -8
  28. data/lib/ruby2js/converter/next.rb +1 -1
  29. data/lib/ruby2js/converter/nil.rb +1 -1
  30. data/lib/ruby2js/converter/nthref.rb +1 -1
  31. data/lib/ruby2js/converter/opasgn.rb +3 -3
  32. data/lib/ruby2js/converter/regexp.rb +12 -9
  33. data/lib/ruby2js/converter/return.rb +3 -3
  34. data/lib/ruby2js/converter/self.rb +2 -2
  35. data/lib/ruby2js/converter/send.rb +31 -30
  36. data/lib/ruby2js/converter/super.rb +8 -11
  37. data/lib/ruby2js/converter/sym.rb +1 -1
  38. data/lib/ruby2js/converter/undef.rb +9 -2
  39. data/lib/ruby2js/converter/var.rb +1 -1
  40. data/lib/ruby2js/converter/vasgn.rb +13 -5
  41. data/lib/ruby2js/converter/while.rb +2 -1
  42. data/lib/ruby2js/converter/whilepost.rb +2 -1
  43. data/lib/ruby2js/converter/xstr.rb +4 -3
  44. data/lib/ruby2js/execjs.rb +3 -3
  45. data/lib/ruby2js/filter/camelCase.rb +8 -8
  46. data/lib/ruby2js/filter/functions.rb +64 -65
  47. data/lib/ruby2js/filter/react.rb +44 -16
  48. data/lib/ruby2js/filter/require.rb +4 -1
  49. data/lib/ruby2js/filter/underscore.rb +21 -21
  50. data/lib/ruby2js/serializer.rb +347 -0
  51. data/lib/ruby2js/version.rb +3 -3
  52. data/ruby2js.gemspec +3 -3
  53. metadata +3 -2
@@ -7,7 +7,7 @@ module Ruby2JS
7
7
  # resolve anonymous receivers against rbstack
8
8
  receiver ||= @rbstack.map {|rb| rb[name]}.compact.last
9
9
 
10
- "#{ parse receiver }#{ '.' if receiver }#{ name }"
10
+ parse receiver; put '.' if receiver; put name
11
11
  end
12
12
  end
13
13
  end
@@ -5,11 +5,12 @@ module Ruby2JS
5
5
 
6
6
  handle :cvar do |var|
7
7
  if @class_name
8
- var.to_s.sub('@@', "#{parse @class_name}._")
8
+ parse @class_name
9
+ put var.to_s.sub('@@', "._")
9
10
  elsif @prototype
10
- var.to_s.sub('@@', 'this._')
11
+ put var.to_s.sub('@@', 'this._')
11
12
  else
12
- var.to_s.sub('@@', 'this.constructor._')
13
+ put var.to_s.sub('@@', 'this.constructor._')
13
14
  end
14
15
  end
15
16
  end
@@ -6,17 +6,16 @@ module Ruby2JS
6
6
 
7
7
  handle :cvasgn do |var, expression=nil|
8
8
  if @class_name
9
- var = var.to_s.sub('@@', "#{parse @class_name}._")
9
+ parse @class_name
10
+ put var.to_s.sub('@@', "._")
10
11
  elsif @prototype
11
- var = var.to_s.sub('@@', 'this._')
12
+ put var.to_s.sub('@@', 'this._')
12
13
  else
13
- var = var.to_s.sub('@@', 'this.constructor._')
14
+ put var.to_s.sub('@@', 'this.constructor._')
14
15
  end
15
16
 
16
17
  if expression
17
- "#{ var } = #{ parse expression }"
18
- else
19
- var
18
+ put " = "; parse expression
20
19
  end
21
20
  end
22
21
  end
@@ -90,15 +90,27 @@ module Ruby2JS
90
90
 
91
91
  nl = @nl unless body == s(:begin)
92
92
  begin
93
+ if name
94
+ put "function #{name}"
95
+ elsif @prop
96
+ put @prop
97
+ @prop = nil
98
+ else
99
+ put 'function'
100
+ end
101
+
102
+ put '('; parse args; put ") {#{nl}"
103
+
93
104
  next_token, @next_token = @next_token, :return
94
105
  @block_depth += 1 if @block_depth
95
- body = scope body, vars
106
+ mark = output_location
107
+ scope body, vars
96
108
  if @block_this and @block_depth == 1
97
- body = "var self = this#{@sep}#{body}"
109
+ insert mark, "var self = this#{@sep}"
98
110
  @block_this = false
99
111
  end
100
112
 
101
- "function#{ " #{name}" if name }(#{ parse args }) {#{nl}#{ body }#{nl}}"
113
+ put "#{nl}}"
102
114
  ensure
103
115
  @next_token = next_token
104
116
  @block_depth -= 1 if @block_depth
@@ -9,7 +9,7 @@ module Ruby2JS
9
9
 
10
10
  handle :defined?, :undefined? do |var|
11
11
  op = (@ast.type == :defined? ? :"!==" : :===)
12
- "typeof #{ parse var } #{ op } 'undefined'"
12
+ put "typeof "; parse var; put " #{ op } 'undefined'"
13
13
  end
14
14
  end
15
15
  end
@@ -13,19 +13,23 @@ module Ruby2JS
13
13
 
14
14
  def transform_defs(target, method, args, body)
15
15
  if not @ast.is_method? or @ast.type == :defp
16
- s(:prop, target, method.to_s =>
16
+ node = s(:prop, target, method.to_s =>
17
17
  {enumerable: s(:true), configurable: s(:true),
18
18
  get: s(:block, s(:send, nil, :proc), args,
19
19
  s(:autoreturn, body))})
20
20
  elsif method =~ /=$/
21
- s(:prop, target, method.to_s.sub('=', '') =>
21
+ node = s(:prop, target, method.to_s.sub('=', '') =>
22
22
  {enumerable: s(:true), configurable: s(:true),
23
23
  set: s(:block, s(:send, nil, :proc), args,
24
24
  body)})
25
25
  else
26
- s(:send, target, "#{method}=",
26
+ node = s(:send, target, "#{method}=",
27
27
  s(:block, s(:send, nil, :lambda), args, body))
28
28
  end
29
+
30
+ @comments[node] = @comments[@ast] if @comments[@ast]
31
+
32
+ node
29
33
  end
30
34
  end
31
35
  end
@@ -10,7 +10,9 @@ module Ruby2JS
10
10
  # (...))
11
11
 
12
12
  handle :dstr, :dsym do |*children|
13
- children.map! do |child|
13
+ children.each_with_index do |child, index|
14
+ put ' + ' unless index == 0
15
+
14
16
  if child.type == :begin and child.children.length == 1
15
17
  child = child.children.first
16
18
  end
@@ -26,8 +28,6 @@ module Ruby2JS
26
28
  parse child
27
29
  end
28
30
  end
29
-
30
- children.join(' + ')
31
31
  end
32
32
  end
33
33
  end
@@ -12,18 +12,15 @@ module Ruby2JS
12
12
  handle :for do |var, expression, block|
13
13
  begin
14
14
  next_token, @next_token = @next_token, :continue
15
- if expression.type == :irange
16
- "for (var #{parse var} = #{ parse expression.children.first }; " +
17
- "#{ parse var } <= #{ parse expression.children.last }; " +
18
- "#{ parse var }++) {#@nl#{ scope block }#@nl}"
19
- elsif expression.type == :erange
20
- "for (var #{parse var} = #{ parse expression.children.first }; " +
21
- "#{ parse var } < #{ parse expression.children.last }; " +
22
- "#{ parse var }++) {#@nl#{ scope block }#@nl}"
15
+ put "for (var "; parse var
16
+ if [:irange, :erange].include? expression.type
17
+ put ' = '; parse expression.children.first; put '; '; parse var
18
+ (expression.type == :erange ? put(' < ') : put(' <= '))
19
+ parse expression.children.last; put '; '; parse var; puts '++'
23
20
  else
24
- "for (var #{parse var} in #{ parse expression }) " +
25
- "{#@nl#{ scope block }#@nl}"
21
+ put ' in '; parse expression;
26
22
  end
23
+ puts ') {'; scope block; sput '}'
27
24
  ensure
28
25
  @next_token = next_token
29
26
  end
@@ -7,50 +7,86 @@ module Ruby2JS
7
7
  # (str "value")))
8
8
 
9
9
  handle :hash do |*pairs|
10
- pairs.map! do |node|
11
- raise NotImplementedError, "kwsplat" if node.type == :kwsplat
10
+ compact do
11
+ singleton = pairs.length <= 1
12
12
 
13
- begin
14
- block_depth, block_this, block_hash = @block_depth, @block_this, false
15
- left, right = node.children
13
+ (singleton ? put('{') : puts('{'))
16
14
 
17
- if Hash === right or right.type == :block
18
- @block_depth, block_hash = 0, true
15
+ pairs.each_with_index do |node, index|
16
+ raise NotImplementedError, "kwsplat" if node.type == :kwsplat
17
+
18
+ (singleton ? put(', ') : put(",#@ws")) unless index == 0
19
+
20
+ if not @comments[node].empty?
21
+ (puts ''; singleton = false) if singleton
22
+ comments(node).each {|comment| put comment}
19
23
  end
20
24
 
21
- if left.type == :prop
22
- result = []
23
- if right[:get]
24
- result << "get #{left.children[0]}#{
25
- parse(right[:get]).sub(/^function/,'')}"
25
+ begin
26
+ block_depth,block_this,block_hash = @block_depth,@block_this,false
27
+ left, right = node.children
28
+
29
+ if Hash === right or right.type == :block
30
+ @block_depth, block_hash = 0, true
26
31
  end
27
- if right[:set]
28
- result << "set #{left.children[0]}#{
29
- parse(right[:set]).sub(/^function/,'')}"
32
+
33
+ if left.type == :prop
34
+ if right[:get]
35
+ unless @comments[right[:get]].empty?
36
+ (puts ''; singleton = false) if singleton
37
+ comments(right[:get]).each {|comment| put comment}
38
+ end
39
+
40
+ @prop = "get #{left.children[0]}"
41
+ parse(right[:get])
42
+ (singleton ? put(', ') : put(",#@ws")) if right[:set]
43
+ end
44
+
45
+ if right[:set]
46
+ unless @comments[right[:set]].empty?
47
+ (puts ''; singleton = false) if singleton
48
+ comments(right[:set]).each {|comment| put comment}
49
+ end
50
+
51
+ @prop = "set #{left.children[0]}"
52
+ parse(right[:set])
53
+ end
54
+ else
55
+ # hoist get/set comments to definition of property
56
+ if right.type == :hash
57
+ right.children.each do |pair|
58
+ next unless Parser::AST::Node === pair.children.last
59
+ if pair.children.last.type == :block
60
+ if @comments[pair.children.last]
61
+ (puts ''; singleton = false) if singleton
62
+ comments(pair.children.last).each do |comment|
63
+ put comment
64
+ end
65
+ end
66
+ end
67
+ end
68
+ end
69
+
70
+ if
71
+ left.children.first.to_s =~ /\A[a-zA-Z_$][a-zA-Z_$0-9]*\Z/
72
+ then
73
+ put left.children.first
74
+ else
75
+ parse left
76
+ end
77
+
78
+ put ': '; parse right
30
79
  end
31
- result
32
- else
33
- key = parse left
34
- key = $1 if key =~ /\A"([a-zA-Z_$][a-zA-Z_$0-9]*)"\Z/
35
- "#{key}: #{parse right}"
36
- end
37
80
 
38
- ensure
39
- if block_hash
40
- @block_depth = block_depth
41
- @block_this = block_this
81
+ ensure
82
+ if block_hash
83
+ @block_depth = block_depth
84
+ @block_this = block_this
85
+ end
42
86
  end
43
87
  end
44
- end
45
-
46
- pairs.flatten!
47
88
 
48
- if pairs.map {|item| item.length+2}.reduce(&:+).to_i < @width-10
49
- "{#{ pairs.join(', ') }}"
50
- elsif pairs.length == 1
51
- "{#{ pairs.join(', ') }}"
52
- else
53
- "{#@nl#{ pairs.join(",#@ws") }#@nl}"
89
+ (singleton ? put('}') : sput('}'))
54
90
  end
55
91
  end
56
92
  end
@@ -15,23 +15,45 @@ module Ruby2JS
15
15
  then_block ||= s(:nil)
16
16
 
17
17
  if @state == :statement
18
- output = "if (#{ parse condition }) {#@nl#{ scope then_block }#@nl}"
19
- while else_block and else_block.type == :if
20
- condition, then_block, else_block = else_block.children
21
- output << " else if (#{ parse condition }) " +
22
- "{#@nl#{ scope then_block }#@nl}"
23
- end
24
- output << " else {#@nl#{ scope else_block }#@nl}" if else_block
18
+ begin
19
+ scope, @scope = @scope, false
20
+ mark = output_location
25
21
 
26
- # use short form when appropriate
27
- unless output.length>@width-8 or else_block or then_block.type == :begin
28
- output = "if (#{ parse condition }) #{ scope then_block }"
29
- end
22
+ # use short form when appropriate
23
+ unless else_block or then_block.type == :begin
24
+ put "if ("; parse condition; put ') '
25
+ wrap { parse then_block, :statement }
26
+ else
27
+ put "if ("; parse condition; puts ') {'
28
+ parse then_block, :statement
29
+ sput '}'
30
+
31
+ while else_block and else_block.type == :if
32
+ condition, then_block, else_block = else_block.children
33
+ put ' else if ('; parse condition; puts ') {'
34
+ parse then_block, :statement
35
+ sput '}'
36
+ end
30
37
 
31
- output
38
+ if else_block
39
+ puts ' else {'; parse else_block, :statement; sput '}'
40
+ end
41
+ end
42
+
43
+ if scope
44
+ vars = @vars.select {|key, value| value == :pending}.keys
45
+ unless vars.empty?
46
+ insert mark, "var #{vars.join(', ')}#{@sep}"
47
+ vars.each {|var| @vars[var] = true}
48
+ end
49
+ end
50
+ ensure
51
+ @scope = scope
52
+ end
32
53
  else
33
54
  else_block ||= s(:nil)
34
- "(#{ parse condition } ? #{ parse then_block } : #{ parse else_block })"
55
+ put '('; parse condition; put ' ? '; parse then_block
56
+ put ' : '; parse else_block; put ')'
35
57
  end
36
58
  end
37
59
  end
@@ -6,7 +6,7 @@ module Ruby2JS
6
6
  # NOTE: in? is a synthetic
7
7
 
8
8
  handle :in? do |left, right|
9
- "#{ parse left } in #{ parse right }"
9
+ parse left; put " in "; parse right
10
10
  end
11
11
  end
12
12
  end
@@ -5,7 +5,7 @@ module Ruby2JS
5
5
  # (int 1))
6
6
 
7
7
  handle :ivasgn do |var, expression|
8
- "#{ var.to_s.sub('@', 'this._') } = #{ parse expression }"
8
+ put "#{ var.to_s.sub('@', 'this._') } = "; parse expression
9
9
  end
10
10
  end
11
11
  end
@@ -35,51 +35,51 @@ module Ruby2JS
35
35
  body = block
36
36
  end
37
37
 
38
- output = "try {#@nl#{ parse body, :statement }#@nl}"
38
+ if not recovers and not finally
39
+ return parse s(:begin, *children)
40
+ end
41
+
42
+ puts "try {"; parse body, :statement; sput '}'
39
43
 
40
44
  if recovers
41
45
  if recovers.length == 1 and not recovers.first.children.first
42
46
  # single catch with no exception named
43
- output += " catch (#{ parse var }) " +
44
- "{#@nl#{ parse recovers.first.children.last, :statement }#@nl}"
47
+ put " catch ("; parse var; puts ") {"
48
+ parse recovers.first.children.last, :statement; sput '}'
45
49
  else
46
- output += " catch (#{ parse var }) {#@nl"
50
+ put " catch ("; parse var; puts ') {'
47
51
 
48
52
  first = true
49
53
  recovers.each do |recover|
50
54
  exceptions, var, recovery = recover.children
51
55
 
52
56
  if exceptions
53
- tests = exceptions.children.map do |exception|
54
- "#{ parse var} instanceof #{ parse exception }"
55
- end
56
57
 
57
- output += "} else " if not first
58
+ put "} else " if not first
58
59
  first = false
59
60
 
60
- output += "if (#{ tests.join(' || ') }) {#@nl"
61
+ put 'if ('
62
+ exceptions.children.each_with_index do |exception, index|
63
+ put ' || ' unless index == 0
64
+ parse var; put ' instanceof '; parse exception
65
+ end
66
+ puts ') {'
61
67
  else
62
- output += "} else {#@nl"
68
+ puts '} else {'
63
69
  end
64
70
 
65
- output += "#{ parse recovery, :statement }#@nl"
71
+ parse recovery, :statement; puts ''
66
72
  end
67
73
 
68
74
  if recovers.last.children.first
69
- output += "} else {#{@nl}throw #{ parse var }#@nl"
75
+ puts "} else {"; put 'throw '; parse var; puts ''
70
76
  end
71
77
 
72
- output += "}#@nl}"
78
+ puts '}'; put '}'
73
79
  end
74
80
  end
75
81
 
76
- output += " finally {#@nl#{ parse finally, :statement }#@nl}" if finally
77
-
78
- if recovers or finally
79
- output
80
- else
81
- parse s(:begin, *children)
82
- end
82
+ (puts ' finally {'; parse finally, :statement; sput '}') if finally
83
83
  end
84
84
  end
85
85
  end
@@ -6,7 +6,7 @@ module Ruby2JS
6
6
  # (str "1"))
7
7
 
8
8
  handle :int, :float, :str do |value|
9
- value.inspect
9
+ put value.inspect
10
10
  end
11
11
  end
12
12
  end