如何检测 BasicObject 代理?
How to detect a BasicObject Proxy?
我正在使用 BasicObject 代理,我需要检测我是否传递了实际对象或此类代理。问题是 is_a?
或 class
等方法未定义
module ControllerProxyable
extend ActiveSupport::Concern
included do
attr_reader :controller
delegate :current_user, to: :controller
end
def controller_proxy(controller)
# is_a? actually is NOT defined for a BasicObject causes the following to crash
@controller = if controller.is_a?(ControllerProxy)
controller
else
ControllerProxy.new(controller)
end
end
end
class ControllerProxy < BasicObject
def initialize(controller = nil)
@controller = controller
end
def some_proxy_method
end
# def respond_to and respond_to_missing not relevant here
end
这是我如何使用它的示例:
class Foo
include ControllerProxyable
def initialize(controller: nil)
controller_proxy(controller)
end
def bar
bar ||= Bar.new(controller: controller)
end
end
class Bar
include ControllerProxyable
def initialize(controller: nil)
controller_proxy(controller)
end
end
因此以下内容不起作用
Foo.new(controller: nil).bar.some_proxy_method
如何为代理定义 is_a?
(或实际识别我正在使用代理)?
我实际上找到了 RUby 2 here 的答案。我的问题几乎感觉像是重复的,但就我而言,我说的是 basicObject class 的扩展,而不是修补 BasicObject class 本身
对于这样的用例,这变成:
def controller_proxy(controller)
# Note that is_a? is not defined for a proxy
@controller = if Kernel.instance_method(:class).bind(controller).call <= ServiceControllerProxy
controller
else
ServiceControllerProxy.new(controller)
end
end
Problem is that methods such as is_a?
or class
are not defined
解决问题"some method is not defined"的明显方法是定义方法:
class ControllerProxy
def class; ControllerProxy end
def is_a?(mod)
self.class < mod
end
end
但是!这违背了代理的全部目的,即与真实事物无法区分。更好的方法是 IMO:
class ControllerProxy
def class; Controller end
def is_a?(mod)
Controller < mod
end
end
我正在使用 BasicObject 代理,我需要检测我是否传递了实际对象或此类代理。问题是 is_a?
或 class
等方法未定义
module ControllerProxyable
extend ActiveSupport::Concern
included do
attr_reader :controller
delegate :current_user, to: :controller
end
def controller_proxy(controller)
# is_a? actually is NOT defined for a BasicObject causes the following to crash
@controller = if controller.is_a?(ControllerProxy)
controller
else
ControllerProxy.new(controller)
end
end
end
class ControllerProxy < BasicObject
def initialize(controller = nil)
@controller = controller
end
def some_proxy_method
end
# def respond_to and respond_to_missing not relevant here
end
这是我如何使用它的示例:
class Foo
include ControllerProxyable
def initialize(controller: nil)
controller_proxy(controller)
end
def bar
bar ||= Bar.new(controller: controller)
end
end
class Bar
include ControllerProxyable
def initialize(controller: nil)
controller_proxy(controller)
end
end
因此以下内容不起作用
Foo.new(controller: nil).bar.some_proxy_method
如何为代理定义 is_a?
(或实际识别我正在使用代理)?
我实际上找到了 RUby 2 here 的答案。我的问题几乎感觉像是重复的,但就我而言,我说的是 basicObject class 的扩展,而不是修补 BasicObject class 本身
对于这样的用例,这变成:
def controller_proxy(controller)
# Note that is_a? is not defined for a proxy
@controller = if Kernel.instance_method(:class).bind(controller).call <= ServiceControllerProxy
controller
else
ServiceControllerProxy.new(controller)
end
end
Problem is that methods such as
is_a?
orclass
are not defined
解决问题"some method is not defined"的明显方法是定义方法:
class ControllerProxy
def class; ControllerProxy end
def is_a?(mod)
self.class < mod
end
end
但是!这违背了代理的全部目的,即与真实事物无法区分。更好的方法是 IMO:
class ControllerProxy
def class; Controller end
def is_a?(mod)
Controller < mod
end
end