Module: Liquidscript::Compiler::Base::Helpers
- Included in:
- Liquidscript::Compiler::Base
- Defined in:
- lib/liquidscript/compiler/base/helpers.rb
Defined Under Namespace
Modules: ClassMethods
Class Method Summary collapse
Instance Method Summary collapse
-
#action(act = nil) { ... } ⇒ Proc, Action
Normalizes an action for the hash passed to #expect.
-
#expect(*args) ⇒ Object
The meat and potatos of the compiler.
-
#loop ⇒ void
Performs a loop while the yield returns true.
-
#maybe(*types) ⇒ #type
Shifts a token if its one of the given types; if it's not, it returns the value of #scanner_nil.
-
#peek?(*types) ⇒ Boolean
Checks to see if the next token is of any of the given types.
-
#shift(*types) ⇒ #type
Shift a token over.
Class Method Details
.included(base) ⇒ Object
21 22 23 |
# File 'lib/liquidscript/compiler/base/helpers.rb', line 21 def self.included(base) base.extend ClassMethods end |
Instance Method Details
#action(act = nil) { ... } ⇒ Proc, Action
33 34 35 36 37 38 39 40 41 |
# File 'lib/liquidscript/compiler/base/helpers.rb', line 33 def action(act = nil) if block_given? Proc.new elsif act.is_a? Proc act else @action end end |
#expect(*args) ⇒ Object
The meat and potatos of the compiler. This maps actions to
tokens. In its basic form, it is passed a hash, with the
keys being token types, and the values the corresponding
actions to take. It can be passed individual types, from
which it'll assume the method name (normally,
compile_<type>); or, you can pass it a symbol key, which
is the last part of the method name (i.e., not including
compile_). It will check the next token, and look for the
correct action; if the next token doesn't match any of the
given keys, it checks for the special type :_ (which is
basically a catch-all), and if it still doesn't get it, it
raises an UnexpectedError. From there, it calls the
corresponding block.
If the block or method accepts one argument, it Liquidscript::Compiler::Base#pops the token, and passes it in as an argument. If it accepts no arguments, it doesn't.
134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 |
# File 'lib/liquidscript/compiler/base/helpers.rb', line 134 def expect(*args) hash = normalize_arguments(args) allowable = false block = hash.fetch(peek.type) do hash.fetch(:_) do allowable = true self.allowable.fetch(peek.type) end end out = if block.arity == 1 block.call pop else block.call end if allowable expect(*args) else out end rescue KeyError raise UnexpectedError.new(hash.keys, peek) end |
#loop ⇒ void
This method returns an undefined value.
Performs a loop while the yield returns true. This overwrites the core loop on purpose.
48 49 50 51 52 53 54 |
# File 'lib/liquidscript/compiler/base/helpers.rb', line 48 def loop result = true while result result = yield end end |
#maybe(*types) ⇒ #type
Shifts a token if its one of the given types; if it's not, it returns the value of Liquidscript::Compiler::Base#scanner_nil.
72 73 74 |
# File 'lib/liquidscript/compiler/base/helpers.rb', line 72 def maybe(*types) expect types => action.shift, :_ => action { scanner_nil } end |
#peek?(*types) ⇒ Boolean
Checks to see if the next token is of any of the given
types. Note that the special type :_ does not work here.
82 83 84 |
# File 'lib/liquidscript/compiler/base/helpers.rb', line 82 def peek?(*types) types.any? { |type| peek.type == type } end |
#shift(*types) ⇒ #type
Shift a token over. The given types can be any types. If
the next token's type doesn't match any of the types, then
it will raise an error. In order to shift any token, use
the special type :_.
63 64 65 |
# File 'lib/liquidscript/compiler/base/helpers.rb', line 63 def shift(*types) expect types => action.shift end |