- `.from(t1, t2)` produces an unconditional join if you forget to add a condition in the .where()
sqlpp11 therefore now deprecates unconditional joins.
- more often than not, writing something like `where(name == "doe")`, you
meant to write `where(t.name == "doe")`. It is hard to find bugs when
the former expression compiles because you happen to have a variable
`name` in the current scope as well.
sqlpp11 therefore now deprecates `.where(bool)` and disallows
raw bool values boolean expression like `something and bool`
wrap bools in sqlpp::value(), if you REALLY want a bool value here
Ok, that sounds weird...
Earlier, each node in the SQL tree had a struct containing all recursive
traits. This is now gone. It only contains a reference to all sub nodes
and its own specific traits.
traits are shorter and easier to identify by using tags in a variadic
template
recursive traits can be automatically derived, which makes it much
easier to add new traits to be handed through the expression tree.
The serializer has partial specializations for all templates. It is a
good basis if the connector/database requires strings close to the
standard.
The interpreter is unspecialized (and uses a static assert to say so).
It is a good basis if the connector/database requires a different
interpretation, e.g. re-writing the expression tree.
The interpretable_t implements three methods for interpretation:
serializing with the sqlpp::serializer_context, serializing with the
database's serialization context and interpretation with the database's
interpretation context.
The code is much easier to read, the optimizer should take care of
pretty much everything, AND it copiles even faster without the code
being riddled with std::forward and std::decay
This namespace is for things the developer will not get in touch with
(normally) but the vendor might need to use for specialization of the
interpreter.
This separation is not fully completed yet, some changes will have to
follow...