Support for DECIMAL in Clickhouse

v2.x-clickhouse230726
René Cannaò 3 years ago
parent bf87d8d911
commit 8686c3150c

@ -62,6 +62,36 @@
using namespace clickhouse;
std::string dec128_to_pchar(Int128 value, size_t scale) {
// code borrowed from https://github.com/bderleta/php-clickhouse/blob/master/conversions.h
bool sign = (value < 0);
char buffer48[48];
char* s = &buffer48[47];
size_t w = 0;
*(--s) = 0;
if (sign)
value = -value;
while (value) {
Int128 v = value;
v %= 10;
char c = (char)v;
*(--s) = c + '0';
if ((++w) == scale)
*(--s) = '.';
value /= 10;
}
while (w < scale) {
*(--s) = '0';
if ((++w) == scale)
*(--s) = '.';
}
if (w == scale)
*(--s) = '0';
if (sign)
*(--s) = '-';
return std::string(s);
}
__thread MySQL_Session * clickhouse_thread___mysql_sess;
inline void ClickHouse_to_MySQL(const Block& block) {
@ -99,7 +129,7 @@ inline void ClickHouse_to_MySQL(const Block& block) {
#endif // CXX17
}
if (cc >= clickhouse::Type::Code::Int8 && cc <= clickhouse::Type::Code::Float64) {
if (cc >= clickhouse::Type::Code::Int8 && cc <= clickhouse::Type::Code::Decimal128) {
bool _unsigned = false;
uint16_t flags = is_null | 128;
@ -151,6 +181,14 @@ inline void ClickHouse_to_MySQL(const Block& block) {
size = 22;
decimals = 31;
break;
case clickhouse::Type::Code::Decimal:
case clickhouse::Type::Code::Decimal32:
case clickhouse::Type::Code::Decimal64:
case clickhouse::Type::Code::Decimal128:
type = MYSQL_TYPE_NEWDECIMAL;
size = 32;
decimals = 31;
break;
default:
_unsigned = false;
flags = 128;
@ -237,6 +275,15 @@ inline void ClickHouse_to_MySQL(const Block& block) {
case clickhouse::Type::Code::Float64:
s=std::to_string(block[i]->As<ColumnFloat64>()->At(r));
break;
case clickhouse::Type::Code::Decimal:
case clickhouse::Type::Code::Decimal32:
case clickhouse::Type::Code::Decimal64:
case clickhouse::Type::Code::Decimal128:
{
size_t scale = block[i]->Type()->As<DecimalType>()->GetScale();
s = dec128_to_pchar(block[i]->As<ColumnDecimal>()->At(r), scale);
}
break;
case clickhouse::Type::Code::Enum8:
s=block[i]->As<ColumnEnum8>()->NameAt(r);;
break;

@ -253,6 +253,8 @@ std::vector<query_spec> queries_set1 {
std::make_tuple<std::string, int>("SELECT NULL AS a", 0, 1),
std::make_tuple<std::string, int>("SELECT NULL+2 AS a, 'hello', NULL+1, 'world', NULL AS b", 0, 1),
std::make_tuple<std::string, int>("SELECT CONCAT('AAA',NULL)", 0, 1),
std::make_tuple<std::string, int>("SELECT CAST(-1234.1234, 'Decimal32(3)')", 0, 1),
std::make_tuple<std::string, int>("SELECT CAST(1000.0, 'Decimal128(3)')", 0, 1),
std::make_tuple<std::string, int>("DROP TABLE IF EXISTS table1", 0, -1),
std::make_tuple<std::string, int>("CREATE TABLE table1 (CounterID INT, EventDate DATE, col1 INT) ENGINE=MergeTree(EventDate, (CounterID, EventDate), 8192)", 0, -1),
std::make_tuple<std::string, int>("CREATE TABLE table1 (CounterID INT, EventDate DATE, col1 INT) ENGINE=MergeTree(EventDate, (CounterID, EventDate), 8192)", 1148, -1), // the second time it must fails

Loading…
Cancel
Save