Search code examples
c++clang-format

Include order of forward headers with clang-format


clang-format has IncludeIsMainRegex to determine if several files share the same main header, in order to place this #include directive first. Neat enough.

I almost always use forward declaration headers of this style: "entity_fwd.hpp", "entity.hpp", and "entity.cpp". Additionally also an "entity_test.cpp", which should use the "entity.hpp" header. "entity.hpp", however, should use "entity_fwd.hpp" as its main header.

So, what I actually need is a way to specify additional headers as main, instead of additional source files using the same main header.

Has anyone found a way to make clang-format do this?

EDIT: OK, so a little more context. Suppose I have this header, called entity_fwd.hpp:

class Entity;
class Player;
class MOB;

bool collisionTest(Entity const & e1, Entity const & e2);

I then have a normal definition header, entity.hpp:

#include "entity_fwd.hpp"
#include "world.hpp"
#include <vector>

class Entity {
public:
    Entity(Entity const &) = delete;
    virtual bool isAlive() const;
    ...
};

...

And finally an implementation file, entity.cpp:

#include "entity.hpp"

bool collisionTest(Entity const & e1, Entity const & e2) {
    ...
}

bool Entity::isAlive() const {
    ...
}

...

For entity.cpp clang-format knows that entity.hpp is the main header for that file, based on the stem of the header's filename; the term main header is clang-format's terminology. The main header will be placed first in the list of includes.

For entity.hpp the main header should be entity_fwd.hpp. I can use IncludeCategories with a regex '_fwd.h(pp)?"$' to sort entity_fwd.hpp first, but that will place all _fwd headers first, where only entity_fwd.hpp should get special treatment.


Solution

  • The most recent documentation for clang-format shows a new style option IncludeIsMainSourceRegex, which appears to be what you need. This isn't in version 10.0.0, so you'll need to find a clang-format version newer than that.