Module: Ivar::Macros

Defined in:
lib/ivar/macros.rb

Overview

Provides macros for working with instance variables

Constant Summary collapse

UNSET =

Special flag object to detect when a parameter is not provided

Object.new.freeze

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.extended(base) ⇒ Object

When this module is extended, it adds class methods to the extending class



10
11
12
13
# File 'lib/ivar/macros.rb', line 10

def self.extended(base)
  # Get or create a manifest for this class
  Ivar.get_or_create_manifest(base)
end

Instance Method Details

#ivar(*ivars, value: UNSET, init: nil, reader: false, writer: false, accessor: false, **ivars_with_values) {|varname| ... } ⇒ Object

Declares instance variables that should be considered valid without being explicitly initialized

Yields:

  • (varname)

    Block to generate initial values based on variable name Example: ivar(:@foo, :@bar) { |varname| “#varname default” }



33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
# File 'lib/ivar/macros.rb', line 33

def ivar(*ivars, value: UNSET, init: nil, reader: false, writer: false, accessor: false, **ivars_with_values, &block)
  manifest = Ivar.get_or_create_manifest(self)

  ivar_hash = ivars.map { |ivar| [ivar, value] }.to_h.merge(ivars_with_values)

  ivar_hash.each do |ivar_name, ivar_value|
    raise ArgumentError, "ivars must be symbols (#{ivar_name.inspect})" unless ivar_name.is_a?(Symbol)
    raise ArgumentError, "ivar names must start with @ (#{ivar_name.inspect})" unless /\A@/.match?(ivar_name)

    options = {init:, value: ivar_value, reader:, writer:, accessor:, block:}

    declaration = case init
    when :kwarg, :keyword
      Ivar::ExplicitKeywordDeclaration.new(ivar_name, manifest, options)
    when :arg, :positional
      # TODO: probably fail if a duplicate positional comes in
      #   There aren't any obvious semantics for it.
      Ivar::ExplicitPositionalDeclaration.new(ivar_name, manifest, options)
    when nil
      Ivar::ExplicitDeclaration.new(ivar_name, manifest, options)
    else
      raise ArgumentError, "Invalid init method: #{init.inspect}"
    end
    manifest.add_explicit_declaration(declaration)
  end
end