Class: Johnson::Visitors::EcmaVisitor

Inherits:
Object
  • Object
show all
Defined in:
lib/johnson/visitors/ecma_visitor.rb

Instance Method Summary collapse

Constructor Details

#initializeEcmaVisitor

Returns a new instance of EcmaVisitor.



4
5
6
# File 'lib/johnson/visitors/ecma_visitor.rb', line 4

def initialize
  @depth = 0
end

Instance Method Details

#accept(target) ⇒ Object



306
307
308
# File 'lib/johnson/visitors/ecma_visitor.rb', line 306

def accept(target)
  target.accept(self)
end

#visit_ArrayLiteral(o) ⇒ Object



49
50
51
# File 'lib/johnson/visitors/ecma_visitor.rb', line 49

def visit_ArrayLiteral(o)
  "[#{o.value.map { |x| x.accept(self) }.join(', ')}]"
end

#visit_BracketAccess(o) ⇒ Object



117
118
119
# File 'lib/johnson/visitors/ecma_visitor.rb', line 117

def visit_BracketAccess(o)
  "#{o.left.accept(self)}[#{o.right.accept(self)}]"
end

#visit_Case(o) ⇒ Object



199
200
201
# File 'lib/johnson/visitors/ecma_visitor.rb', line 199

def visit_Case(o)
  "case #{o.left.accept(self)}: #{o.right.accept(self)}"
end

#visit_Catch(o) ⇒ Object



140
141
142
# File 'lib/johnson/visitors/ecma_visitor.rb', line 140

def visit_Catch(o)
  "catch(#{o.cond.accept(self)}) #{o.b_else.accept(self)}"
end

#visit_Comma(o) ⇒ Object



70
71
72
# File 'lib/johnson/visitors/ecma_visitor.rb', line 70

def visit_Comma(o)
  "#{o.value.map { |x| x.accept(self) }.join(', ') }"
end

#visit_Default(o) ⇒ Object



203
204
205
# File 'lib/johnson/visitors/ecma_visitor.rb', line 203

def visit_Default(o)
  "default: #{o.right.accept(self)}"
end

#visit_Delete(o) ⇒ Object



144
145
146
# File 'lib/johnson/visitors/ecma_visitor.rb', line 144

def visit_Delete(o)
  "delete #{o.value.accept(self)}"
end

#visit_DotAccessor(o) ⇒ Object



212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
# File 'lib/johnson/visitors/ecma_visitor.rb', line 212

def visit_DotAccessor(o)
  stmt =
    if o.right.is_a?(Nodes::Function)
      "(#{o.right.accept(self)})"
    else
      "#{o.right.accept(self)}"
    end

  rhs = o.left.accept(self)
  if rhs =~ /\A\w+$/
    stmt << ".#{rhs}"
  else
    stmt << "['#{rhs}']"
  end
  stmt
end

#visit_DoWhile(o) ⇒ Object



125
126
127
128
# File 'lib/johnson/visitors/ecma_visitor.rb', line 125

def visit_DoWhile(o)
  semi = o.left.is_a?(Nodes::SourceElements) ? '' : ';'
  "do #{o.left.accept(self)}#{semi} while(#{o.right.accept(self)})"
end

#visit_Export(o) ⇒ Object



148
149
150
# File 'lib/johnson/visitors/ecma_visitor.rb', line 148

def visit_Export(o)
  "export #{o.value.map { |x| x.accept(self) }.join(', ')}"
end

#visit_For(o) ⇒ Object



26
27
28
29
30
# File 'lib/johnson/visitors/ecma_visitor.rb', line 26

def visit_For(o)
  "for(#{o.init ? o.init.accept(self) : ' '};" \
    " #{o.cond && o.cond.accept(self)};" \
    " #{o.update && o.update.accept(self)}) #{o.body.accept(self)}"
end

#visit_ForIn(o) ⇒ Object



32
33
34
# File 'lib/johnson/visitors/ecma_visitor.rb', line 32

def visit_ForIn(o)
  "for(#{o.in_cond.accept(self)}) #{o.body.accept(self)}"
end

#visit_Function(o) ⇒ Object



89
90
91
# File 'lib/johnson/visitors/ecma_visitor.rb', line 89

def visit_Function(o)
  "function#{o.name && ' '}#{o.name}(#{o.arguments.join(', ')}) #{o.body.accept(self)}"
end

#visit_FunctionCall(o) ⇒ Object



59
60
61
62
63
64
65
66
67
68
# File 'lib/johnson/visitors/ecma_visitor.rb', line 59

def visit_FunctionCall(o)
  rest = o.value.slice(1..-1)
  stmt =
    if o.value.first.is_a?(Nodes::Function)
      "(#{o.value.first.accept(self)})"
    else
      "#{o.value.first.accept(self)}"
    end
  "#{stmt}(#{rest && rest.map { |x| x.accept(self) }.join(', ')})"
end

#visit_GetterProperty(o) ⇒ Object



229
230
231
# File 'lib/johnson/visitors/ecma_visitor.rb', line 229

def visit_GetterProperty(o)
  "get #{o.left.accept(self)}#{o.right.accept(self).gsub(/function/, '')}"
end

#visit_If(o) ⇒ Object



80
81
82
83
84
85
86
87
# File 'lib/johnson/visitors/ecma_visitor.rb', line 80

def visit_If(o)
  semi = ''
  semi = ';' if o.b_else && !o.b_then.is_a?(Nodes::SourceElements)

  stmt = "if(#{o.cond.accept(self)}) #{o.b_then.accept(self)}#{semi}"
  stmt += " else #{o.b_else.accept(self)}" if o.b_else
  stmt
end

#visit_Import(o) ⇒ Object



152
153
154
# File 'lib/johnson/visitors/ecma_visitor.rb', line 152

def visit_Import(o)
  "import #{o.value.map { |x| x.accept(self) }.join(', ')}"
end

#visit_Label(o) ⇒ Object Also known as: visit_Property



207
208
209
# File 'lib/johnson/visitors/ecma_visitor.rb', line 207

def visit_Label(o)
  "#{o.left.accept(self)}: #{o.right.accept(self)}"
end

#visit_LetStatement(o) ⇒ Object



45
46
47
# File 'lib/johnson/visitors/ecma_visitor.rb', line 45

def visit_LetStatement(o)
  "let #{o.value.map { |x| x.accept(self) }.join(', ')}"
end

#visit_LexicalScope(o) ⇒ Object



121
122
123
# File 'lib/johnson/visitors/ecma_visitor.rb', line 121

def visit_LexicalScope(o)
  "#{o.right.accept(self)}"
end

#visit_New(o) ⇒ Object



53
54
55
56
57
# File 'lib/johnson/visitors/ecma_visitor.rb', line 53

def visit_New(o)
  rest = o.value.slice(1..-1)
  "new #{o.value.first.accept(self)}"\
    "(#{rest && rest.map { |x| x.accept(self) }.join(', ')})"
end

#visit_ObjectLiteral(o) ⇒ Object



237
238
239
240
241
# File 'lib/johnson/visitors/ecma_visitor.rb', line 237

def visit_ObjectLiteral(o)
  indent {
    "{ #{o.value.map { |x| x.accept(self) }.join(",\n#{indent}")} }"
  }
end

#visit_Parenthesis(o) ⇒ Object



183
184
185
# File 'lib/johnson/visitors/ecma_visitor.rb', line 183

def visit_Parenthesis(o)
  "(#{o.value.accept(self)})"
end

#visit_Return(o) ⇒ Object



164
165
166
# File 'lib/johnson/visitors/ecma_visitor.rb', line 164

def visit_Return(o)
  "return#{o.value && ' '}#{o.value && o.value.accept(self)}"
end

#visit_SetterProperty(o) ⇒ Object



233
234
235
# File 'lib/johnson/visitors/ecma_visitor.rb', line 233

def visit_SetterProperty(o)
  "set #{o.left.accept(self)}#{o.right.accept(self).gsub(/function/, '')}"
end

#visit_SourceElements(o) ⇒ Object



8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
# File 'lib/johnson/visitors/ecma_visitor.rb', line 8

def visit_SourceElements(o)
  newline = o.value.length > 0 ? "\n" : ' '
  (@depth == 0 ? '' : "{#{newline}") +
    indent {
      o.value.map { |x|
        code = x.accept(self)
        semi = case x
               when Nodes::Function, Nodes::While, Nodes::If, Nodes::Try, Nodes::Switch, Nodes::Case, Nodes::Default, Nodes::For, Nodes::ForIn
                 code =~ /\}\Z/ ? '' : ';'
               else
                 ';'
               end
        "#{indent}#{code}#{semi}"
      }.join("\n")
    } +
    (@depth == 0 ? '' : "#{newline}}")
end

#visit_String(o) ⇒ Object



93
94
95
96
97
98
99
100
101
102
# File 'lib/johnson/visitors/ecma_visitor.rb', line 93

def visit_String(o)
  h = {
    "\b"  => '\b',
    "\t"  => '\t',
    "\n"  => '\n',
    "\f"  => '\f',
    "\r"  => '\r',
  }
  "\"#{o.value.gsub(/[\\]/, '\\\\\\').gsub(/"/, '\"').gsub(/[\b\t\n\f\r]/) { |m| h[m] }}\""
end

#visit_Switch(o) ⇒ Object



195
196
197
# File 'lib/johnson/visitors/ecma_visitor.rb', line 195

def visit_Switch(o)
  "switch(#{o.left.accept(self)}) #{o.right.accept(self)}"
end

#visit_Ternary(o) ⇒ Object



36
37
38
39
# File 'lib/johnson/visitors/ecma_visitor.rb', line 36

def visit_Ternary(o)
  "#{o.cond.accept(self)} ? #{o.b_then.accept(self)} : " \
    "#{o.b_else.accept(self)}"
end

#visit_Throw(o) ⇒ Object



156
157
158
# File 'lib/johnson/visitors/ecma_visitor.rb', line 156

def visit_Throw(o)
  "throw #{o.value.accept(self)}"
end

#visit_Try(o) ⇒ Object



130
131
132
133
134
135
136
137
138
# File 'lib/johnson/visitors/ecma_visitor.rb', line 130

def visit_Try(o)
  stmt = "try #{o.cond.accept(self)}"
  o.b_then.each do |node|
    stmt << " #{node.accept(self)}"
  end if o.b_then
  stmt << "#{o.b_else && ' finally '}" \
    "#{o.b_else && o.b_else.accept(self)}" if o.b_else
  stmt
end

#visit_Typeof(o) ⇒ Object



168
169
170
# File 'lib/johnson/visitors/ecma_visitor.rb', line 168

def visit_Typeof(o)
  "typeof #{o.value.accept(self)}"
end

#visit_VarStatement(o) ⇒ Object



41
42
43
# File 'lib/johnson/visitors/ecma_visitor.rb', line 41

def visit_VarStatement(o)
  "var #{o.value.map { |x| x.accept(self) }.join(', ')}"
end

#visit_Void(o) ⇒ Object



160
161
162
# File 'lib/johnson/visitors/ecma_visitor.rb', line 160

def visit_Void(o)
  "void #{o.value.accept(self)}"
end

#visit_While(o) ⇒ Object



187
188
189
# File 'lib/johnson/visitors/ecma_visitor.rb', line 187

def visit_While(o)
  "while(#{o.left.accept(self)}) #{o.right.accept(self)}"
end

#visit_With(o) ⇒ Object



191
192
193
# File 'lib/johnson/visitors/ecma_visitor.rb', line 191

def visit_With(o)
  "with(#{o.left.accept(self)}) #{o.right.accept(self)}"
end