The benefit is editing library code as freely as application code. If I have to do a separate build/install, and then build/install up the hierarchy, this becomes a significant pain if it's a bit of code which I'm doing a edit/test cycle with.
For example, say I have some procedural noise function (in noiselib) which I'm enhancing, with respect to a particular application (app), and we have this dependency: app > texturelib > noiselib. I'd rather not have this process to iterate with:
<noiselib> make; make install_local
<noiselib> cd ../texturelib
<texturelib> make clean; make; make install_local
<texturelib> cd ../app
<app> make clean; make
Also note the "install_local" as opposed to "install" -- this would be a minor ugliness too. I have applications which rely on more stable versions of the libraries installed system-wide, and infrequently updated. If I'm needing a special install process anyway, why install at all? Seems better to use it in-place.
Creating an "app-local" version of the function in question (extending modules via include) can work, and I do this, but sometimes the changes are more complex or pervasive than a single function -- and you don't always realize the changes are going to escape their initial scope.
I regularly develop libraries in parallel with application code. This was also the case in the large studios I've worked in (games). Typically there are a few tiers of library code -- where a library is common code, rather than rigid code. In practice the library code doesn't change much because other code depends on it and has fixed the interfaces, but when you do work with library code, it's in the context of application and needs the benefit of easy edit/test iteration. I think another view of libraries is much more standalone, with unit-tests to determine correct behavior. Again, this can apply in some cases, but perhaps it's less common with an interactive artsy application like games -- where correctness is more a matter of end-result behavior, rather than something you can build good unit-tests for.
Thank-you for asking, Gabriel... it helped me sort some of this out for myself too! The stumbling blocks I'm encountering have made me feel a bit uncertain -- there's an impedance mismatch which might indicate I'm doing something inappropriate. Now I think I might just be working with a slightly different bias: library as shared code, moreso than rigid code... which might be the assumption the OCaml build ecosystem is working with. I'm not developing/changing library code in a vacuum -- it's with respect to higher level usage and results.
A reflection of the distinction between library use... the ossified libraries (rarely changed, system-wide) are used as packages, while libraries under active development as part of several apps are... not installed, and are included by "use_xxx" of ocamlbuild.
Does this make sense?