-
Notifications
You must be signed in to change notification settings - Fork 107
Coding Rules
#define SNAKE_CASE (1)
namespace snake_case {
// east const
constexpr char const snake_case = 0b00000010;
template <typename UpperCamelCase>
class snake_case {
public:
void snake_case() {
if (condition1) { // whitespace after if and between ) and {
// ...
}
else { // don't } else {
// ...
}
switch (condition2) {
case 1: // case indent level is same as switch
// ...
break;
case 2:
// ...
break;
case 3: {
int local_variable = 1;
// ...
} break;
}
// whitespace after for , & is connected with type not variable, whitespace before and after :
for (auto const& e : collection) {
}
}
template <typename SomethingLong>
std::enable_if_t< // std::enable_if_t is C++14 feature. Use it instead of typename std::enable_if<...>::type
std::is_same< // if the parameters are long, then use this type multi line indent.
SomethingLong,
int
>::value // std::is_same_v is C++17 feature. Don't use it.
>
multi_line_function_template(SomethingLong v) {
// ...
}
private:
int snake_case_; // underscore postfix
};
} // namespace snake_case
Indent is four spaces, please don't use TAB.
If condition has an else clause, condition should be positive. This rule is applied not only MACRO but also normal if-else
.
// OK
#if defined(SOME_CONDITION)
// do A
#else // defined(SOME_CONDITION)
// do B
#endif // defined(SOME_CONDITION)
// NG
#if !defined(SOME_CONDITION)
// do B
#else // !defined(SOME_CONDITION)
// do A
#endif // !defined(SOME_CONDITION)
Immediate invoking lambda expression is more preferred than conditional operator. If the types of return values are different, the lambda expression can declare the return type explicitly.
auto r =
[&]() -> int {
if (cond1 == 0) {
if (cond2 == 0) {
return 100;
}
return 200;
}
return 300;
} ();
Equivalent conditional operator. It is complicated.
int r = cond1 == 0 ? cond2 == 0 ? 100
: 200
: 300;
If the expression is simple enough, you can use conditional operator.
If the lambda expression has long capture list and/or long parameter list, write as follows:
auto lambda =
[.................](.................) {
};
// or
auto lambda =
[.................]
(.................) {
};
If the lambda expression is called in the function, then you can use [&]
capture.
void foo() {
auto lambda = [&] {};
// ...
lambda();
}
However, if the lambda expression is called after the function is finished, then you need to use explicit capture list. It is typical situation on asynchronous API callback.
void foo(int& i) {
auto lambda = [&i] {};
// ...
as::post(ioc, lambda);
}
Please respect the order.
- Basically use the value.
foo f;
. - If the value should be nullable, then use
MQTT_NS::optional
.MQTT_NS::optional<foo> f
. In order to lazy initalize, usef.emplace(...)
. - If there is convincible reason to locate the value to the heap, then use
std::unique_ptr<foo> f
. Don't usestd::shared_ptr<foo>
. - If and only if reference counting pattern is required, then use
std::shared_ptr<foo> f
.
Please use this formatting rule for JSON
- User four white spaces to indent.
- Insert one white space after
:
. - Use one line to add
,
between objects. It helps copy and paste.
{
"key1": [
{
"subkey1": "value1",
"subkey2": ["value2-1", "value2-2"]
}
,
{
"subkey1": "value1",
"subkey2": ["value2-1", "value2-2"]
}
]
,
"key2": [
{
"subkey1": "value1",
"subkey2": ["value2-1", "value2-2"]
}
]
}
When you insert JSON to the C++ code, please use raw string literals as follows:
void foo() {
std::string json_str = R"*(
{
"key1": [
{
"subkey1": "value1",
"subkey2": ["value2-1", "value2-2"]
}
]
}
)*";
std::cout << json_str << std::endl;
}
auth.json
example:
{
"authentication": [
{
"name": "u1",
"method": "sha256",
"salt": "salt",
"digest": "694073aa885f21f4dc23af70b5d2d30dc115dcfc0c5661113ca8bab2373d741d"
}
,
{
"name": "u2",
"method": "client_cert",
"field": "CNAME"
}
,
{
"name": "u2",
"method": "plain_password",
"password": "mypassword"
}
,
{
"name": "anonymous",
"method": "anonymous"
}
]
,
"group": [
{
"name": "@g1",
"members": ["u1", "u2", "anonymous" ]
}
]
,
"authorization": [
{
"topic": "#",
"type": "allow",
"pub": ["@g1"]
}
,
{
"topic": "#",
"type": "deny",
"sub": ["@g1"]
}
,
{
"topic": "sub/#",
"type": "allow",
"sub": ["@g1"],
"pub": ["@g1"]
}
,
{
"topic": "sub/topic1",
"type": "deny",
"sub": ["u1", "anonymous"],
"pub": ["u1", "anonymous"]
}
]
}
When
- Requirements
- Config
- Tutorial
- Authentication and Authorization
- Advanced topics
- Examples
- API Reference
- Versioning Policy
- How to contribute