我正在使用Curb,一个围绕cURL的红宝石包装。
我想首先说我知道方法缺失等方法可以接受任意数字args和块,如果这样定义:
def method_missing(meth, *args, &block); ... end
*args
是一组参数。
现在,我正在尝试重构我对HTTP GET,POST等方法的调用,通过使用Curb执行以下操作:
req = Curl::Easy.send("http_#{method.to_s}", *args) do |curl| ... end
其中args
可以是1个参数或2个参数,我试图定义如下:
args = [url]
args << data if data
但是当我调用Curl::Easy.send
行时出现错误。
both block arg and actual block given
以下是我尝试访问的方法的一些示例(https://github.com/taf2/curb/blob/master/lib/curl/easy.rb):
def http_get(*args)
c = Curl::Easy.new *args
yield c if block_given?
c.http_get
c
end
def http_put(url, data)
c = Curl::Easy.new url
yield c if block_given?
c.http_put data
c
end
def http_post(*args)
url = args.shift
c = Curl::Easy.new url
yield c if block_given?
c.http_post *args
c
end
def http_delete(*args)
c = Curl::Easy.new *args
yield c if block_given?
c.http_delete
c
end
所有这些都被设置为接受任意数量的参数,除了put。
但是,实际上,对于http_get
,我只需要传递一个URL(在URL中使用查询参数)。所以,我只想为http_get
传递一个参数,为其他传递2个参数。
答案 0 :(得分:0)
如果我理解正确,您希望根据方法的参数数量发送x个参数。以下内容将根据给出的数据起作用。
method_name = "http_#{method.to_s}"
params = Curl::Easy.method(:"#{method_name}").parameters
req = Curl::Easy.send("http_#{method.to_s}", *(args[0..(params.size-1)])) do |curl| ... end```
然而,您提出的错误是当您发送Proc作为参数并传递一个块时,它会按照您的要求执行,但如果没有堆栈跟踪来缩小范围,我不会认为这会解决你的错误。即
irb(main):001:0> def tst(&block)
irb(main):002:1> end
=> nil
irb(main):003:0> arg = Proc.new { }
=> #<Proc:0x00000002cd6930@(irb):3>
irb(main):004:0> tst(&arg) do
irb(main):005:1* end
SyntaxError: (irb):5: both block arg and actual block given
作为旁注,#parameters返回类似[[:rest][:args]]
的内容,并且:rest表示其余参数,因此您可以随时对参数进行更多检查以提供更精细的参数。