Class: Rigor::Plugin::NodeContext
- Inherits:
-
Object
- Object
- Rigor::Plugin::NodeContext
- Defined in:
- lib/rigor/plugin/node_context.rb
Overview
ADR-37 slice 1d — the lexical context of a node, handed to a Base.node_rule block as its fifth argument. Realises the ‘ContextInfo` ADR-2 § “Scope Object” promised: the enclosing class / module, method, and block-DSL nesting that a per-node rule needs but that `Scope` (value/type facts) does not carry.
The engine builds one per matching node from the descent stack (snapshotted, so it is safe to retain). Rules read the bits they need:
node_rule Prism::CallNode do |node, _scope, path, _fc, context|
action = context.enclosing_def&.name # rails-i18n
model = context.enclosing_block(:describe) # shoulda
…
end
‘ancestors` is the full chain, outermost first, EXCLUDING the node itself — the general primitive; the accessors below are conveniences derived from it.
Constant Summary collapse
- EMPTY =
sentinel documented for readers; rules get a real instance
nil
Instance Attribute Summary collapse
-
#ancestors ⇒ Object
readonly
Returns the value of attribute ancestors.
Instance Method Summary collapse
-
#enclosing_block(method_name) ⇒ Object
The innermost enclosing ‘Prism::CallNode` that carries a block and whose method name is `method_name` — e.g.
-
#enclosing_def ⇒ Object
The innermost enclosing ‘Prism::DefNode`, or nil.
-
#enclosing_module ⇒ Object
The innermost enclosing ‘Prism::ClassNode` / `Prism::ModuleNode`, or nil (actionpack uses it to resolve the controller a `before_action` / `render` sits in).
-
#initialize(ancestors) ⇒ NodeContext
constructor
A new instance of NodeContext.
Constructor Details
#initialize(ancestors) ⇒ NodeContext
Returns a new instance of NodeContext.
31 32 33 34 |
# File 'lib/rigor/plugin/node_context.rb', line 31 def initialize(ancestors) @ancestors = ancestors.dup.freeze freeze end |
Instance Attribute Details
#ancestors ⇒ Object (readonly)
Returns the value of attribute ancestors.
29 30 31 |
# File 'lib/rigor/plugin/node_context.rb', line 29 def ancestors @ancestors end |
Instance Method Details
#enclosing_block(method_name) ⇒ Object
The innermost enclosing ‘Prism::CallNode` that carries a block and whose method name is `method_name` — e.g. the `RSpec.describe(Model) do … end` a shoulda matcher sits in. Returns the CallNode (so the caller can read its arguments / receiver), or nil.
55 56 57 58 59 |
# File 'lib/rigor/plugin/node_context.rb', line 55 def enclosing_block(method_name) ancestors.rfind do |n| n.is_a?(Prism::CallNode) && n.block && n.name == method_name end end |
#enclosing_def ⇒ Object
The innermost enclosing ‘Prism::DefNode`, or nil. Its `#name` is the method the node sits in (rails-i18n uses it to expand a lazy `t(’.key’)‘ against the controller action).
39 40 41 |
# File 'lib/rigor/plugin/node_context.rb', line 39 def enclosing_def ancestors.rfind { |n| n.is_a?(Prism::DefNode) } end |
#enclosing_module ⇒ Object
The innermost enclosing ‘Prism::ClassNode` / `Prism::ModuleNode`, or nil (actionpack uses it to resolve the controller a `before_action` / `render` sits in).
46 47 48 |
# File 'lib/rigor/plugin/node_context.rb', line 46 def enclosing_module ancestors.rfind { |n| n.is_a?(Prism::ClassNode) || n.is_a?(Prism::ModuleNode) } end |