Class: Opal::Nodes::TopNode

Inherits:
ScopeNode show all
Defined in:
opal/lib/opal/nodes/top.rb

Overview

Generates code for an entire file, i.e. the base sexp

Instance Attribute Summary

Attributes inherited from ScopeNode

#await_encountered, #block_name, #catch_return, #defs, #gvars, #has_break, #has_retry, #identity, #ivars, #locals, #methods, #mid, #name, #parent, #rescue_else_sexp, #scope_name

Attributes inherited from Base

#compiler, #sexp, #type

Instance Method Summary collapse

Methods inherited from ScopeNode

#accepts_using?, #add_arg, #add_proto_ivar, #add_scope_gvar, #add_scope_ivar, #add_scope_local, #add_scope_temp, #class?, #class_scope?, #collect_refinements_temps, #current_rescue, #def?, #def_in_class?, #defines_lambda, #find_parent_def, #gen_retry_id, #has_local?, #has_rescue_else?, #has_temp?, #identify!, #in_ensure, #in_ensure?, #in_resbody, #in_resbody?, #in_rescue, #in_scope, #in_while?, #initialize, #is_lambda!, #iter?, #lambda?, #lambda_definition?, #module?, #new_refinements_temp, #new_temp, #next_temp, #pop_while, #push_while, #queue_temp, #refinements_temp, #sclass?, #scope_locals, #super_chain, #to_vars, #top?, #top_scope, #uses_block!, #uses_block?

Methods inherited from Base

#add_gvar, #add_ivar, #add_local, #add_temp, #children, children, #class_variable_owner, #class_variable_owner_nesting_level, #comments, #compile_to_fragments, #error, #expr, #expr?, #expr_or_nil, #fragment, handle, handlers, #has_rescue_else?, #helper, #in_ensure, #in_ensure?, #in_resbody, #in_resbody?, #in_rescue, #in_while?, #initialize, #process, #push, #recv, #recv?, #s, #scope, #source_location, #stmt, #stmt?, #top_scope, truthy_optimize?, #unshift, #while_loop, #with_temp, #wrap

Methods included from Helpers

#conditional_send, #current_indent, #empty_line, #indent, #js_falsy, #js_truthy, #js_truthy_optimize, #line, #mid_to_jsid, #property, #valid_name?

Constructor Details

This class inherits a constructor from Opal::Nodes::ScopeNode

Instance Method Details

#add_used_helpersObject



82
83
84
# File 'opal/lib/opal/nodes/top.rb', line 82

def add_used_helpers
  compiler.helpers.to_a.each { |h| add_temp "$#{h} = Opal.#{h}" }
end

#add_used_operatorsObject



86
87
88
89
90
91
92
93
94
# File 'opal/lib/opal/nodes/top.rb', line 86

def add_used_operators
  operators = compiler.operator_helpers.to_a
  operators.each do |op|
    name = Nodes::CallNode::OPERATORS[op]
    line "function $rb_#{name}(lhs, rhs) {"
    line "  return (typeof(lhs) === 'number' && typeof(rhs) === 'number') ? lhs #{op} rhs : lhs['$#{op}'](rhs);"
    line '}'
  end
end

#closingObject



62
63
64
65
66
67
68
69
70
# File 'opal/lib/opal/nodes/top.rb', line 62

def closing
  if compiler.requirable?
    line "};\n"
  elsif compiler.eval?
    line "})(Opal, self);"
  else
    line "});\n"
  end
end

#compileObject



15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
# File 'opal/lib/opal/nodes/top.rb', line 15

def compile
  push version_comment

  in_scope do
    line '"use strict";' if compiler.use_strict?

    body_code = stmt(stmts)
    body_code = [body_code] unless body_code.is_a?(Array)

    if compiler.eval?
      add_temp '$nesting = self.$$is_a_module ? [self] : [self.$$class]'
    else
      add_temp 'self = Opal.top'
      add_temp '$nesting = []'
    end
    add_temp 'nil = Opal.nil'
    add_temp '$$$ = Opal.$$$'
    add_temp '$$ = Opal.$$'

    add_used_helpers
    add_used_operators
    line scope.to_vars

    compile_method_stubs
    compile_irb_vars
    compile_end_construct

    line body_code
  end
  opening
  closing
end

#compile_end_constructObject

Any special END content in code



105
106
107
108
109
110
# File 'opal/lib/opal/nodes/top.rb', line 105

def compile_end_construct
  if content = compiler.eof_content
    line 'var $__END__ = Opal.Object.$new();'
    line "$__END__.$read = function() { return #{content.inspect}; };"
  end
end

#compile_irb_varsObject



76
77
78
79
80
# File 'opal/lib/opal/nodes/top.rb', line 76

def compile_irb_vars
  if compiler.irb?
    line 'if (!Opal.irb_vars) { Opal.irb_vars = {}; }'
  end
end

#compile_method_stubsObject



96
97
98
99
100
101
102
# File 'opal/lib/opal/nodes/top.rb', line 96

def compile_method_stubs
  if compiler.method_missing?
    calls = compiler.method_calls
    stubs = calls.to_a.map { |k| "'$#{k}'" }.join(', ')
    line "Opal.add_stubs([#{stubs}]);" unless stubs.empty?
  end
end

#openingObject



48
49
50
51
52
53
54
55
56
57
58
59
60
# File 'opal/lib/opal/nodes/top.rb', line 48

def opening
  async_prefix = "async " if await_encountered

  if compiler.requirable?
    unshift "Opal.modules[#{Opal::Compiler.module_name(compiler.file).inspect}] = #{async_prefix}function(Opal) {"
  elsif compiler.eval?
    unshift "(#{async_prefix}function(Opal, self) {"
  elsif compiler.esm?
    unshift "export default Opal.queue(#{async_prefix}function(Opal) {"
  else
    unshift "Opal.queue(#{async_prefix}function(Opal) {"
  end
end

#stmtsObject



72
73
74
# File 'opal/lib/opal/nodes/top.rb', line 72

def stmts
  compiler.returns(body)
end

#version_commentObject



112
113
114
# File 'opal/lib/opal/nodes/top.rb', line 112

def version_comment
  "/* Generated by Opal #{Opal::VERSION} */"
end