Home

Awesome

Skeleton for C++ header-only libraries that can be included into other C++ projects. This repository itself is a helper library. To use it for a specific project, edit filenames and tests accordingly.

Build Status codecov

dancing skel

Usage

#include <include/hello_world.hpp>

using namespace hello_world;

// exclaim a string
std::string value = exclaim("hello");
std::clog << value; // => hello!

Test

# build test binaries
make

# run tests
make test

# run bench tests
make bench

The default test binaries will be built in release mode. You can make Debug test binaries as well:

make clean
make debug
make test

Enable additional sanitizers to catch hard-to-find bugs, for example:

export LDFLAGS="-fsanitize=address,undefined,integer"
export CXXFLAGS="-fsanitize=address,undefined,integer"

make

Customize

Easily use this skeleton as a starting off point.

Start new project

# Clone hpp-skel locally

git clone git@github.com:mapbox/hpp-skel.git
cd hpp-skel/

# Create your new repo on GitHub and have the remote repo url handy for liftoff
# Then run the liftoff script from within your local hpp-skel root directory.
#
# This will:
# - prompt you for the new name of your project and the new remote repo url
# - automatically create a new directory for your new project repo
# - create a new branch called "hpp-skel-port" within your new repo directory
# - add, commit, and push that branch to your new repo

./scripts/liftoff.sh

Add custom code

Once your project has ported hpp-skel, follow these steps to integrate your own code:

Setup tests

Since header-only libraries are not normally compiled themselves, to test them you need to #include them in a .cpp file (aka a translation unit) to compile and run their code. We recommend using Catch to make writing this .cpp file easy.

#include <your_header_here.hpp>
#define CATCH_CONFIG_MAIN
#include <catch.hpp>

TEST_CASE("test_my_header")
{
    // Your test logic here
}
// "hello_world" is the namespace
// "exclaim" is the method 

std::string value = hello_world::exclaim("hello");

Benchmarks

This skeleton uses Google Benchmark to measure performance, and includes a couple benchmark tests to get you up and running quickly:

Some notes on Google Benchmark results:

Compiler Optimization

To obtain a true benchmark, it may be necessary to prevent the compiler from optimizing away a value or expression. The skeleton uses Google Benchmark's internal functions to manage this. See https://github.com/google/benchmark#preventing-optimisation for more details.

Publishing

We recommend publishing header files to Mason, the C++ packaging manager. Binaries can be downloaded by project name and version number. In order to publish to Mason you must request the publish via a Pull Request to the scripts/ directory with your project materials.

Mason packages can be downloaded to your project by using the mason install command. This is best set up in a Makefile (example).

Of course, you can always copy and paste this repo into your vendor path for your project. :scissors:

Versioning

This library is semantically versioned using the /include/hello_world/version.cpp file. This defines a number of macros that can be used to check the current major, minor, or patch versions, as well as the full version string.

Here's how a downstream client would check for a particular version to use specific API methods

#if HELLOWORLD_VERSION_MAJOR > 2
// use version 2 api
#else
// use older verion apis
#endif

Here's how to check the version string

std::cout << "version: " << HELLOWORLD_VERSION_STRING << "/n";
// => version: 0.2.0

And lastly, mathematically checking for a specific version:

#if HELLOWORLD_VERSION_CODE > 20001
// use feature provided in v2.0.1
#endif

Contributing and License

Contributors are welcome! :sparkles: This repo exists as a place to gather C++ Header Library knowledge that will benefit the larger community. Please contribute your knowledge if you'd like.

hpp-skel is licensed under CC0. Attribution is not required, but definitely welcome! If your project uses this skeleton, please add the hpp-skel badge to your readme so that others can learn about the resource.

badge

To include the badge, paste this into your README.md file:

[![badge](https://mapbox.s3.amazonaws.com/cpp-assets/hpp-skel-badge_blue.svg)](https://github.com/mapbox/hpp-skel)

See CONTRIBUTING and LICENSE for more info.