Circular modules and precompilation errors


#1

I’ve implemented for my own work an optimal linesearch using Optim.jl, and I would like to add it to LineSearches.jl (it’s trivial, but it’s useful for testing). The problem is that the linesearch uses Optim.jl, which itself uses LineSearches.jl. What I tried to do is add my method to a file in LineSearches.jl and adding it to the LineSearches.jl chain. The file looks like this:

import Optim

function exact!()
   Optim.optimize()
end

When I try to test this, I get the following error:

julia> Pkg.test("LineSearches")
INFO: Computing test dependencies for LineSearches...
INFO: No packages to install, update or remove
INFO: Testing LineSearches
WARNING: Module LineSearches with uuid 29474219186615 is missing from the cache.
This may mean module LineSearches does not support precompilation but is imported by a module that does.
ERROR: LoadError: Declaring __precompile__(false) is not allowed in files that are being precompiled.
Stacktrace:
 [1] _require(::Symbol) at ./loading.jl:436
 [2] require(::Symbol) at ./loading.jl:386
 [3] include_from_node1(::String) at ./loading.jl:552
 [4] include(::String) at ./sysimg.jl:14
 [5] anonymous at ./<missing>:2
while loading /home/antoine/.julia/v0.6/Optim/src/Optim.jl, in expression starting on line 8
ERROR: LoadError: LoadError: LoadError: Failed to precompile Optim to /home/antoine/.julia/lib/v0.6/Optim.ji.
Stacktrace:
 [1] compilecache(::String) at ./loading.jl:686
 [2] _require(::Symbol) at ./loading.jl:473
 [3] require(::Symbol) at ./loading.jl:386
 [4] include_from_node1(::String) at ./loading.jl:552
 [5] include(::String) at ./sysimg.jl:14
 [6] include_from_node1(::String) at ./loading.jl:552
while loading /home/antoine/.julia/v0.6/LineSearches/src/exact.jl, in expression starting on line 1
while loading /home/antoine/.julia/v0.6/LineSearches/src/LineSearches.jl, in expression starting on line 23
while loading /home/antoine/.julia/v0.6/LineSearches/test/runtests.jl, in expression starting on line 1

How is this kind of things usually handled?


#2

As in other languages, circular dependencies are not allowed. However, also as in other languages, you can play some games with forward declarations, though it requires some care to do this without invoking method replacement warnings. In fact, if you don’t pre-compile you might be able to get a circular dependency to actually “work” although I wouldn’t recommend it. I suggest you decide on which package you want to be your “base” and get it sorted out.