Sha256: c327fa70fcd3f1c804996271905a22c10aff1b1e0d150f7495e2a7db21da175c

Contents?: true

Size: 1.66 KB

Versions: 22

Compression:

Stored size: 1.66 KB

Contents

# frozen_string_literal: true

module Orthoses
  class DelegateClass
    module Hook
      def inherited(subclass)
        super
      end
    end

    def initialize(loader)
      @loader = loader
    end

    def call
      require 'delegate'
      ::Class.prepend(Hook)

      inherited = CallTracer.new

      delegate_class_super_map = {}
      delegate_class_tracer = TracePoint.new(:return) do |tp|
        return_value = tp.return_value
        superclass = tp.binding.local_variable_get(:superclass)
        delegate_class_super_map[return_value] = superclass
      end

      store = delegate_class_tracer.enable(target: method(:DelegateClass)) do
        inherited.trace(Hook.instance_method(:inherited)) do
          @loader.call
        end
      end

      store["Class"].body.delete("prepend Orthoses::DelegateClass::Hook")

      inherited.captures.each do |capture|
        superclass = capture.method.receiver
        if delegate_to_class = delegate_class_super_map[superclass]
          subclass = capture.argument[:subclass]
          subclass_name = Utils.module_name(subclass)
          next unless subclass_name

          delegate_to_class_name = Utils.module_name(delegate_to_class)
          next unless delegate_to_class_name

          header = "class #{subclass_name} < ::#{delegate_to_class_name}#{temporary_type_params(delegate_to_class_name)}"
          store[subclass_name].header = header
        end
      end

      store
    end

    def temporary_type_params(name)
      Utils.known_type_params(name)&.then do |params|
        if params.empty?
          nil
        else
          "[#{params.map { :untyped }.join(', ')}]"
        end
      end
    end
  end
end

Version data entries

22 entries across 22 versions & 1 rubygems

Version Path
orthoses-1.17.0 lib/orthoses/delegate_class.rb
orthoses-1.16.0 lib/orthoses/delegate_class.rb
orthoses-1.15.0 lib/orthoses/delegate_class.rb
orthoses-1.14.0 lib/orthoses/delegate_class.rb
orthoses-1.13.0 lib/orthoses/delegate_class.rb
orthoses-1.12.0 lib/orthoses/delegate_class.rb
orthoses-1.11.0 lib/orthoses/delegate_class.rb
orthoses-1.10.0 lib/orthoses/delegate_class.rb
orthoses-1.9.0 lib/orthoses/delegate_class.rb
orthoses-1.8.0 lib/orthoses/delegate_class.rb
orthoses-1.7.0 lib/orthoses/delegate_class.rb
orthoses-1.6.0 lib/orthoses/delegate_class.rb
orthoses-1.5.0 lib/orthoses/delegate_class.rb
orthoses-1.4.0 lib/orthoses/delegate_class.rb
orthoses-1.3.0 lib/orthoses/delegate_class.rb
orthoses-1.2.0 lib/orthoses/delegate_class.rb
orthoses-1.1.0 lib/orthoses/delegate_class.rb
orthoses-1.0.0 lib/orthoses/delegate_class.rb
orthoses-0.11.0 lib/orthoses/delegate_class.rb
orthoses-0.10.0 lib/orthoses/delegate_class.rb