Infinidat / infi.clickhouse_fdw

A PostgreSQL foreign data wrapper for ClickHouse
BSD 3-Clause "New" or "Revised" License
54 stars 4 forks source link

Nullable() Columns Not Supported #3

Open nsscan opened 6 years ago

nsscan commented 6 years ago

Clickhouse has support for Nullable() columns but the FDW reports that it rejects these columns when configuring tables.

Python Clickhouse driver supports Nullable(), so should be something possible to add to the FDW.

nsscan commented 6 years ago

Before trying to work on this, Is it possible to add nullable support using a very simple patch to main.py ? Or is there additional handling required?

--- main.py 2018-01-14 15:51:13.748060669 -0500
+++ main.py2    2018-01-15 08:02:01.660986297 -0500
@@ -52,7 +52,20 @@
     'Int8':         1,
     'Int16':        2,
     'Int32':        4,
-    'Int64':        8
+    'Int64':        8,
+    'Nullable(Date)':         2,
+    'Nullable(DateTime)':     4,
+    'Nullable(Float32)':      4,
+    'Nullable(Float64)':      8,
+    'Nullable(UInt8)':        1,
+    'Nullable(UInt16)':       2,
+    'Nullable(UInt32)':       4,
+    'Nullable(UInt64)':       8,
+    'Nullable(Int8)':         1,
+    'Nullable(Int16)':        2,
+    'Nullable(Int32)':        4,
+    'Nullable(Int64)':        8
+
 }

@@ -70,6 +83,19 @@
     'UInt32':       'bigint',        # ditto
     'UInt64':       'numeric(20,0)', # ditto
     'String':       'varchar',
+    'Nullable(Date)':         'date',
+    'Nullable(DateTime)':     'timestamp',
+    'Nullable(Float32)':      'real',
+    'Nullable(Float64)':      'double precision',
+    'Nullable(Int8)':         'smallint',      # there's no single-byte integer type
+    'Nullable(Int16)':        'smallint',
+    'Nullable(Int32)':        'integer',
+    'Nullable(Int64)':        'bigint',
+    'Nullable(UInt8)':        'smallint',      # there are no unsigned types, so use a type that's large enough
+    'Nullable(UInt16)':       'integer',       # ditto
+    'Nullable(UInt32)':       'bigint',        # ditto
+    'Nullable(UInt64)':       'numeric(20,0)', # ditto
+    'Nullable(String)':       'varchar',
 }
ishirav commented 6 years ago

This should work, but I think the ColumnDefinition (main.py:196) should also specify NULL so that postgres will expect NULLs in that column.

nsscan commented 6 years ago

Thanks for the really quick response. I'll try to set up a build environment and try this. I'll report back.

nsscan commented 6 years ago

@ishirav Trying to load my build and load my version in PostgreSQL I get

ImportError: No module named clickhouse_fdw.main

If a direct message is easier, feel free to email me on my public profile email. Thanks.