Building lexy and integrating it in your own projects

The library uses CMake (3.8 or higher) as its build system. It requires a compiler that supports C++17, but works best with C++20. It is tested with GCC 7 and higher, clang 6 and higher, the latest MSVC and clang-cl. Other compilers may work as well.

Basic integration

The recommended way to integrate lexy is using FetchContent. This will automatically download the library and make it available in your CMake project.

FetchContent_Declare(lexy URL

lexy will detect when it is used via FetchContent (or add_subdirectory) and automatically disable project infrastructure like tests or examples. It exposes the following targets:

foonathan::lexy::core (header-only)

lexy’s core library; it is required. It is an INTERFACE target that sets the required include path and C++ standard flags.

foonathan::lexy::file (library)

Link to this library if you want to use lexy::read_file  and other file I/O functions.

foonathan::lexy::unicode (header-only)

Link to this library if you want to use advanced Unicode rules that require the Unicode character database.

foonathan::lexy::ext (header-only)

Link to this library if you want to use the extension headers in lexy_ext/.

foonathan::lexy::experimental (header-only)

Link to this library if you want to use experimental features.

foonathan::lexy (library)

Umbrella target that links to all targets except for foonathan::lexy::experimental.

A minimal CMakeLists.txt that uses lexy can look like this:


FetchContent_Declare(lexy URL

target_sources(lexy_example PRIVATE main.cpp)
target_link_libraries(lexy_example PRIVATE foonathan::lexy)


lexy can be customized by two CMake flags set at build time:


If this option is ON, linking against foonathan::lexy::core (and transitively also foonathan::lexy) sets the flag to enable C++17 for all compilers. If this option is OFF, linking enables C++20 for compilers that support it and C++17 otherwise. It is OFF by default.


This setting defines the file path to the user config header file (see below).

All other configuration happens via the user config header, which is a user-written file that can be used to override many of the automatic compiler detections. If LEXY_USER_CONFIG_HEADER is set, it will use the specified header; otherwise, looks for a header file named lexy_user_config.hpp somewhere in the include search path. This header is then automatically included by lexy and can define macros to customize lexy. Those are:


The encoding that lexy will deduce for char strings. By default, it is lexy::default_encoding , which means any 8bit encoding. It can be overridden to lexy::ascii_encoding  or lexy::utf8_encoding .


Whether or not internal assertions and precondition checks are enabled. By default, they are enabled unless NDEBUG is defined.


Whether or not the compiler supports C++20’s generalized non-type template parameters.


Whether or not the compiler supports consteval.


Whether or not the compiler supports char8_t.


Whether or not the native endianness is little endian.


The compiler specific attribute to force inlining.


The compiler specific attribute for .

Development build

To contribute to lexy, you don’t want to use it as a subdirectory as that disables most targets. Instead, clone the project normally and use CMake directly (i.e. cmake -S /path/to/lexy -B /path/to/build). This requires at least CMake 3.18.

Development target

The special target foonathan::lexy::dev can be used instead of foonathan::lexy::core. It will enable the relevant compiler warnings inside the lexy headers. Link against it in any examples or tests.

It is not part of the umbrella target foonathan::lexy.


Examples are only available if LEXY_BUILD_EXAMPLES is ON (the default). Each example has its own target, e.g. lexy_example_calculator.


Tests are only available if LEXY_BUILD_TESTS is ON (the default). It will automatically fetch doctest and enable_testing().

The following test targets are available:


Tests for all headers in lexy/.


Tests for all headers in lexy_ext/.


Tests for example XXX.

lexy_test_playground, lexy_test_godbolt, lexy_test_godbolt_examples, lexy_test_playground_examples

Compile-only targets that ensure the examples of the documentation all compile.

The minimal workflow to build lexy and run all tests is:

cmake -S /path/to/lexy -B /path/to/build
cd /path/to/build
cmake --build .


Benchmarks are only available if LEXY_BUILD_BENCHMARKS is ON (not the default). It will automatically fetch nanobench and necessary data files. Refer to the benchmarks/ folder for details.


Docs can only be built if LEXY_BUILD_DOCS is ON (not the default). It requires that you have installed hugo, Asciidoctor, and pygments.rb. Docs can be build by two targets:


This will compile the docs and serve the website on localhost.


This will compile the docs into docs/public.

Packaging and installing

lexy also exposes a custom target lexy_package. It will create a file in the build directory containing all source files necessary for downstream users to use lexy.

As subdirectory and if LEXY_ENABLE_INSTALL the library can be installed using cmake --install. This will include the header files, the foonathan::lexy::file library and CMake code to enable find_package().