This took a while to show up and may have been missed.
On Saturday, 28 November 2015 12:19:29 UTC-5, Curtis Vogt wrote: > > I've been working on a package Mocking.jl > <https://github.com/invenia/Mocking.jl> which allows developers to > temporarily overwrite a method in order to facilitate testing. I've got > everything working pretty well with the exception of the creation of a new > macro which is suppose to ensure that Julia doesn't inline or optimize the > call in such a way that the originally specified call can be overwritten: > > julia> function myfunc(filename) > > readall(open(filename)) > > end > > myfunc (generic function with 1 method) > > > julia> myfunc("foo") > > ERROR: SystemError: opening file foo: No such file or directory > > in open at ./iostream.jl:90 > > in myfunc at none:2 > > > julia> Base.open(name::AbstractString) = IOBuffer("bar") > > WARNING: Method definition open(AbstractString) in module Base at > iostream.jl:99 overwritten in module Main at none:1. > > open (generic function with 8 methods) > > > julia> myfunc("foo") # Open call within `myfunc` is not overwritten > > ERROR: SystemError: opening file foo: No such file or directory > > in open at ./iostream.jl:90 > > in myfunc at none:2 > > > I can get this to work correctly with by adjusting the myfunc slightly: > > > julia> function myfunc(filename) > > readall([open([filename]...)]...) > > end > > myfunc (generic function with 1 method) > > > julia> myfunc("foo") > > ERROR: SystemError: opening file foo: No such file or directory > > in open at ./iostream.jl:90 > > in open at iostream.jl:99 > > in myfunc at none:2 > > > julia> Base.open(name::AbstractString) = IOBuffer("bar") > > WARNING: Method definition open(AbstractString) in module Base at > iostream.jl:99 overwritten in module Main at none:1. > > open (generic function with 8 methods) > > > julia> myfunc("foo") > > "bar" > > > But this makes forces people to change their code and make it harder to > read. Not to mention that this is just fooling the compiler into getting > the behaviour I want. I would prefer to use a macro to get this behaviour > and I managed to get the following horrible macro to work: > > > > julia> macro fix(ex) > > name = gensym() > > :(@generated function $name() $ex end; $name()) > > end > > > julia> function myfunc(filename) > > @fix readall(open(filename)) > > end > > myfunc (generic function with 1 method) > > > julia> myfunc("foo") > > ERROR: SystemError: opening file foo: No such file or directory > > in open at ./iostream.jl:90 > > in open at iostream.jl:99 > > in #2###6995 at none:3 > > in myfunc at none:2 > > > julia> Base.open(name::AbstractString) = IOBuffer("bar") > > WARNING: Method definition open(AbstractString) in module Base at > iostream.jl:99 overwritten in module Main at none:1. > > open (generic function with 8 methods) > > > julia> myfunc("foo") > > "bar" > > > Does anyone have any suggestions on how I can improve this macro and get > this behaviour? Bonus points if someone can tell me a good way of > determining if the macro is being called from within a `Pkg.test(...)` > process. >
