Skip to content

Commit

Permalink
Populate type_code
Browse files Browse the repository at this point in the history
  • Loading branch information
Mause committed Jul 13, 2021
1 parent 0c5d616 commit 2936ef3
Show file tree
Hide file tree
Showing 3 changed files with 71 additions and 4 deletions.
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -335,3 +335,6 @@ tools/pythonpkg/tests/userdata1.parquet
# node tests
__nvm

*.vcxproj*
*.cmake
*.sln
47 changes: 46 additions & 1 deletion tools/pythonpkg/src/pyresult.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -264,12 +264,57 @@ py::object DuckDBPyResult::FetchArrowTable() {
return from_batches_func(batches, schema_obj);
}

py::str GetTypeToPython(const LogicalType &type) {
switch (type.id()) {
case LogicalTypeId::BOOLEAN:
return py::str("bool");
case LogicalTypeId::TINYINT:
case LogicalTypeId::SMALLINT:
case LogicalTypeId::INTEGER:
case LogicalTypeId::BIGINT:
case LogicalTypeId::UTINYINT:
case LogicalTypeId::USMALLINT:
case LogicalTypeId::UINTEGER:
case LogicalTypeId::UBIGINT:
case LogicalTypeId::HUGEINT:
case LogicalTypeId::FLOAT:
case LogicalTypeId::DOUBLE:
case LogicalTypeId::DECIMAL: {
return py::str("NUMBER");
}
case LogicalTypeId::VARCHAR:
return py::str("STRING");
case LogicalTypeId::BLOB:
return py::str("BINARY");
case LogicalTypeId::TIMESTAMP:
case LogicalTypeId::TIMESTAMP_MS:
case LogicalTypeId::TIMESTAMP_NS:
case LogicalTypeId::TIMESTAMP_SEC: {
return py::str("DATETIME");
}
case LogicalTypeId::TIME: {
return py::str("Time");
}
case LogicalTypeId::DATE: {
return py::str("Date");
}
case LogicalTypeId::MAP:
case LogicalTypeId::STRUCT:
return py::str("dict");
case LogicalTypeId::LIST: {
return py::str("list");
}
default:
throw std::runtime_error("unsupported type: " + type.ToString());
}
}

py::list DuckDBPyResult::Description() {
py::list desc(result->names.size());
for (idx_t col_idx = 0; col_idx < result->names.size(); col_idx++) {
py::tuple col_desc(7);
col_desc[0] = py::str(result->names[col_idx]);
col_desc[1] = py::none();
col_desc[1] = GetTypeToPython(result->types[col_idx]);
col_desc[2] = py::none();
col_desc[3] = py::none();
col_desc[4] = py::none();
Expand Down
25 changes: 22 additions & 3 deletions tools/pythonpkg/tests/api/test_dbapi10.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,28 @@
# cursor description
from datetime import datetime, date
from pytest import mark


class TestCursorDescription(object):
def test_description(self, duckdb_cursor):
description = duckdb_cursor.execute("SELECT * FROM integers").description
assert description == [('i', None, None, None, None, None, None)]
@mark.parametrize(
"query,column_name,string_type,real_type",
[
["SELECT * FROM integers", "i", "NUMBER", int],
["SELECT * FROM timestamps", "t", "DATETIME", datetime],
["SELECT DATE '1992-09-20';", "CAST(1992-09-20 AS DATE)", "Date", date],
["SELECT '\\xAA'::BLOB;", "\\xAA", "BINARY", bytes],
["SELECT {'x': 1, 'y': 2, 'z': 3}", "struct_pack(1, 2, 3)", "dict", dict],
["SELECT [1, 2, 3]", "list_value(1, 2, 3)", "list", list],
],
)
def test_description(
self, query, column_name, string_type, real_type, duckdb_cursor
):
duckdb_cursor.execute(query)
assert duckdb_cursor.description == [
(column_name, string_type, None, None, None, None, None)
]
assert isinstance(duckdb_cursor.fetchone()[0], real_type)

def test_none_description(self, duckdb_empty_cursor):
assert duckdb_empty_cursor.description is None

0 comments on commit 2936ef3

Please sign in to comment.