Managing data¶
The problem¶
Let’s assume the foo executable needs a file named foo.dat
You may want to put foo.dat under version control, and have the foo executable
find the foo.dat file when run:
- from the build dir
- when installed
The solution¶
Here is a possible solution, assuming you have the following layout:
<worktree>
foo
CMakeLists.txt
main.cpp
share
foo
foo.dat
# in CMakeLists.txt
qi_create_bin(foo main.cpp)
# mark this directory as a potential prefix for
# qi::path::findData()
qi_stage_dir()
# create an install rule for foo.dat:
qi_install_data(share/foo/foo.dat SUBFOLDER foo)
// in main.cpp
#include <qi/application.hpp>
#include <qi/path.hpp>
int main(int argc, char* argv[])
{
// Mandatory for qi::path to work:
qi::Application app(argc, argv);
std::string fooPath = qi::path::findData("foo", "foo.dat");
}
How it works¶
When run from the build dir¶
The constructor of qi::Application starts by figuring out the exact path
of the binary currently running.
(For instance, /path/to/build/sdk/bin/foo).
It then sets the SDK prefix to /path/to/build/sdk, then tries to parse
the path.conf in /path/to/build/sdk/share/qi/path.conf.
Every path in this file is added to the list of possible SDK prefixes, recursively.
The path.conf is generated by qibuild configure and contains paths
to every possible SDK prefix (the <build/sdk> folder for every project in the
worktree, and the path to every package in the toolchain).
Then qi_stage_dir() can find out the directory of the CMakeLists.txt it was
called from, and add it at the top of the path.conf file.
When installed¶
When installed, say to /tmp/foo, the SDK prefix will be /tmp/foo, and
since everything is installed to the same destination, qi::path::findData() will
find foo.dat in /tmp/foo/share/foo/foo.dat