Open svoop opened 5 years ago
Rather than drilling open after_do, I've implemented a barebone callback in my gem doing just the bits I need there:
module MyGem
module Callback
def before(method, &block)
aliased_method = :"__#{method}"
alias_method aliased_method, method
private aliased_method
define_method method do |*args|
updated_args = block.call(self, method, args)
updated_args ||= args
send(aliased_method, *updated_args)
end
end
end
end
Hi there,
thanks for the report. I'll reopen this to keep it in mind for the future. I haven't worked on after_do in a long time but might have some time coming up next year to consider this.
Thanks for providing a usage example. my first instinct was to say "nope" (as it's also not exactly what AOP usually does) but seems like an interesting enough use case that if it was easily supportable I'd happily consider it.
So, thanks :+1:
As of now, it's not possible to manipulate the
args
in the before callback due to the arguments being passed with a splat*args
.However, there are use cases where it would be very useful to do so, most notably when using before callbacks on setter methods. Here's a very simple setter in a gem of mine:
Unfortunately, I'm dealing with very flaky data sources here which is why I have to deal with less than 1% of the data "manually". The least intrusive way to do so are setter callbacks which kick in when
nil
is about to be assigned:This does not work, but I see two ways to make it work:
args
without splatting which is a breaking API change. On the other hand, it should be a step towards supporting keyword arguments (haven't tried this though).throw
to signal the return value of the callback should be used as arguments formethod
(similar to Rails'throw :abort
). This is a non-breaking API change and would look something like this:Would you consider to merge such a feature?