All Products
Search
Document Center

ApsaraDB RDS:Compatibility of DuckDB-based analytical instances

Last Updated:Jun 04, 2026

This topic describes the compatibility of DuckDB-based analytical instances provided by ApsaraDB RDS for MySQL.

Note

The following compatibility notes all require enabling the duckdb_sql_normalization parameter.

Supported data types

The following table lists only the data types where DuckDB-based analytical instances differ from MySQL.

Type

MySQL data type

Compatibility

String types

CHAR, VARCHAR

Only UTF-8 character sets and collations are supported.

Time types

TIME

A DuckDB-based analytical instance supports a range of '00:00:00'~'23:59:59', with a data format of 'HH:MM:SS'.

MySQL supports the range '-838:59:59'~'838:59:59'. Because the two differ in their supported ranges, if the data is outside the range supported by the DuckDB-based analytical instance, query results may be inconsistent.

DATE

DuckDB-based analytical instances support a range from '0001-01-01' to '9999-12-31', with a data format of 'YYYY-MM-DD'.

For the range '0000-00-00' to '0001-01-01', MySQL supports it but DuckDB does not, so query results may be inconsistent.

DATETIME

The supported range for DuckDB-based analytical instances is 0001-01-01 00:00:00.000000 UTC to 9999-12-31 00:00:00.999999 UTC in the YYYY-MM-DD HH:MM:SS.MS format.

For data in the range '0000-00-00 00:00:00' to '0001-01-01 00:00:00', MySQL supports it but DuckDB does not, which may lead to inconsistent query results.

Spatial data types

GEOMETRY, POINT, LINESTRING, POLYGON, MULTIPOINT, MULTILINESTRING, MULTIPOLYGON, GEOMETRYCOLLECTION

Incompatible

Limits on SELECT statements

  • Character set conversion

    For character set conversion functions, regardless of the target character set, all conversions are standardized to the utf8mb4 character set and handed off to DuckDB for execution. For example:

    SELECT convert(id using gbk) FROM t1;
    SELECT cast(id AS CHAR CHARACTER SET utf8mb4) FROM t1;
  • Interval unit

    The following interval units are not supported:

    YEAR_MONTH, DAY_HOUR, HOUR_MINUTE, DAY_MINUTE, HOUR_SECOND, DAY_SECOND, SECOND_MICROSECOND, HOUR_MICROSECOND, DAY_MICROSECOND, MINUTE_SECOND, MINUTE_MICROSECOND, SQL_TSI_HOUR
  • Subqueries

    Non-scalar subqueries with equality conditions are not supported. Example:

    SELECT * FROM t1 WHERE (id, col1) = (SELECT id, col1 FROM t1);
  • BINARY(num) type conversion

    Explicit conversion to the BINARY(num) data type is not supported, and the specified bit length will be ignored. Example:

    SELECT CAST('abc' AS binary(1));
  • UNSIGNED type conversion

    Explicit conversion to the UNSIGNED data type is not supported. For example:

    SELECT CAST(1 AS UNSIGNED);

Data type conversion issues

For optimal execution efficiency, DuckDB-based analytical instances use strict type constraints during execution. When a query is executed, the system automatically performs type conversions based on the context. This type of conversion is called implicit type conversion. For scenarios where conversion cannot be completed implicitly, you must use the CAST or CONVERT function to explicitly specify the type conversion to ensure that the query executes correctly.

Rules for implicit type conversion in functions

Note
  • / indicates that no implicit conversion is involved. ✔️ indicates that implicit conversion is supported. ✖️ indicates that implicit conversion is not supported.

  • Regular string types refer to the following MySQL data types: CHAR, VARCHAR, TINYTEXT, TEXT, MEDIUMTEXT, LONGTEXT, JSON, SET, and ENUM.

  • Binary string types refer to the following MySQL data types: BINARY, VARBINARY, BIT, TINYBLOB, BLOB, MEDIUMBLOB, and LONGBLOB.

  • Conversion from an integer type with a larger value range to an integer type with a smaller value range is not supported.

Conversion to basic scalar types

Source type

Implicit conversion to basic scalar types

String literal

Numeric literal

Basic scalar

String literal

/

✖️

Numeric literal

✖️

/

Value

BOOLEAN

✖️

✖️

Integer types

✖️

✖️

FLOAT

✖️

✖️

DOUBLE

✖️

✖️

DECIMAL

✖️

✖️

String

Regular string

✖️

✖️

Binary string

✖️

✖️

Date and time

YEAR

✖️

✖️

DATE

✖️

✖️

TIME

✖️

✖️

DATETIME

✖️

✖️

TIMESTAMP

✖️

✖️

Conversion to numeric types

Source type

Implicit conversion to numeric types

BOOLEAN

Integer types

FLOAT

DOUBLE

DECIMAL

Basic scalar

String literal

✖️

✖️

✖️

✔️

✖️

Numeric literal

✖️

✔️

✔️

✔️

✔️

Numeric

BOOLEAN

/

✖️

✖️

✖️

✖️

Integer types

✖️

/

✔️

✔️

✔️

FLOAT

✖️

✔️: Only conversion to BIGINT is supported.

/

✔️

✖️

DOUBLE

✖️

✔️: Only conversion to BIGINT is supported.

✖️

/

✖️

DECIMAL

✖️

✔️

✔️

✔️

/

String

Regular string

✖️

✖️

✖️

✔️

✖️

Binary string

✖️

✖️

✖️

✖️

✖️

Date and time

YEAR

✖️

✔️

✔️

✔️

✔️

DATE

✖️

✖️

✖️

✔️

✖️

TIME

✖️

✖️

✖️

✔️

✖️

DATETIME

✖️

✖️

✖️

✔️

✖️

TIMESTAMP

✖️

✖️

✖️

✔️

✖️

Conversion to string types

Source type

Implicit conversion to string types

Regular string

Binary string

Basic scalar

String literal

✔️

✖️

Numeric literal

✖️

✖️

Numeric

BOOLEAN

✖️

✖️

Integer types

✔️

✖️

FLOAT

✔️

✖️

DOUBLE

✔️

✖️

DECIMAL

✔️

✖️

String

Regular string

/

✖️

Binary string

✖️

/

Date and time

YEAR

✔️

✖️

DATE

✔️

✖️

TIME

✔️

✖️

DATETIME

✔️

✖️

TIMESTAMP

✔️

✖️

Conversion to date and time types

Source type

Implicit conversion to date and time types

YEAR

DATE

TIME

DATETIME

TIMESTAMP

Basic scalar

String literal

✖️

✖️

✖️

✖️

✖️

Numeric literal

✔️

✖️

✖️

✖️

✖️

value

BOOLEAN

✖️

✖️

✖️

✖️

✖️

Integer types

✖️

✖️

✖️

✖️

✖️

FLOAT

✖️

✖️

✖️

✖️

✖️

DOUBLE

✖️

✖️

✖️

✖️

✖️

DECIMAL

✖️

✖️

✖️

✖️

✖️

String

Regular string

✖️

✖️

✖️

✖️

✖️

Binary string

✖️

✖️

✖️

✖️

✖️

Date and time

YEAR

/

✖️

✖️

✖️

✖️

DATE

✖️

/

✖️

✔️

✔️

TIME

✖️

✖️

/

✔️

✔️

DATETIME

✖️

✖️

✖️

/

✔️

TIMESTAMP

✖️

✖️

✖️

✔️

/

Rules for implicit type conversion in comparisons

DuckDB-based analytical instances have stricter and more consistent rules for type conversion and comparison. However, this behavior may differ from that of MySQL in some scenarios:

  • Implicit conversion from string to date: When a string is implicitly converted to a date, if the string format cannot be correctly parsed into a valid date value, the SQL query fails and reports an error.

  • Comparison rules between integer types: When different integer types are compared, DuckDB-based analytical instances convert them to the integer type with the larger value range.

  • Type conversion order for multiple-operand expressions: For multiple-operand expressions such as col1 in (col2, col3, col4, ...), col1 between col2 and col3, coalesce(col1, col2, col3, ...), type conversion is performed in sequence.

  • Compatibility difference for the YEAR type: In DuckDB-based analytical instances, the YEAR type is converted to the INTEGER type for comparison, which may cause incompatibility with MySQL. Example:

    CREATE TABLE t1 (id YEAR PRIMARY KEY);
    INSERT INTO t1 VALUES (1980);
    SELECT * FROM t1 WHERE id BETWEEN 70 AND 90;
    
    # MySQL query result
    +------+
    | id   |
    +------+
    | 1980 |
    +------+
    
    # DuckDB-based analytical instance query result
    Empty set.
  • String conversion rules for the Boolean type: DuckDB-based analytical instances support the conversion of six strings ('1', '0', 'yes', 'no', 'true', and 'false') to the BOOLEAN type. An attempt to convert any other string results in an error. MySQL converts '1' to true and all other strings to false. Therefore, the following SQL statement may return inconsistent results:

    CREATE TABLE t1 (id INT PRIMARY KEY);
    INSERT INTO t1 VALUES (1);
    SELECT id FROM t1 WHERE 'true';
    
    # MySQL query result
    Empty set
    
    # DuckDB-based analytical instance query result
    +------+
    | id   |
    +------+
    |    1 |
    +------+

Note
  • When data of different types is compared, the system converts the data to a common type for comparison based on the rules in the following tables. If a comparison between types is not supported (✖️), an error is reported.

  • Regular string types refer to the following MySQL data types: CHAR, VARCHAR, TINYTEXT, TEXT, MEDIUMTEXT, LONGTEXT, JSON, SET, and ENUM.

  • Binary string types refer to the following MySQL data types: BINARY, VARBINARY, BIT, TINYBLOB, BLOB, MEDIUMBLOB, and LONGBLOB.

Comparison with basic scalar types

Source type

Comparison with basic scalar types

String literal

Numeric literal

Basic scalar

String literal

String

Numeric literal

Numeric literal

Numeric literal

Larger-range numeric type

Value

BOOLEAN

BOOLEAN

Larger-range numeric type

Integer types

Integer types

Larger-range numeric type

FLOAT

FLOAT

Larger-range numeric type

DOUBLE

DOUBLE

Larger-range numeric type

DECIMAL

DECIMAL

Larger-range numeric type

String

Regular string

Regular string

Numeric literal

Binary string

Binary string

✖️

Date and time

YEAR

YEAR

Larger-range numeric type

DATE

DATETIME

✖️

TIME

TIME

✖️

DATETIME

DATETIME

✖️

TIMESTAMP

TIMESTAMP

✖️

Comparison with numeric types

Source type

Comparison with numeric types

BOOLEAN

Integer types

FLOAT

DOUBLE

DECIMAL

Basic scalar

String literal

BOOLEAN

Integer types

FLOAT

DOUBLE

DECIMAL

Numeric literal

Larger-range numeric type

Larger-range numeric type

Larger-range numeric type

Larger-range numeric type

Larger-range numeric type

Numeric

BOOLEAN

BOOLEAN

Integer types

FLOAT (inequality comparison ✖️)

DOUBLE (inequality comparison ✖️)

DECIMAL (inequality comparison ✖️)

Integer types

Integer types

Integer types

FLOAT

DOUBLE

DECIMAL

FLOAT

FLOAT (inequality comparison ✖️)

FLOAT

FLOAT

DOUBLE

FLOAT

DOUBLE

DOUBLE (inequality comparison ✖️)

DOUBLE

DOUBLE

DOUBLE

DOUBLE

DECIMAL

DECIMAL (inequality comparison ✖️)

DECIMAL

FLOAT

DOUBLE

DECIMAL

String

Regular string

BOOLEAN

Integer types

FLOAT

DOUBLE

DECIMAL

Binary string

✖️

✖️

✖️

✖️

✖️

Date and time

YEAR

INTEGER

Larger-range integer type

FLOAT

DOUBLE

DECIMAL

DATE

✖️

✖️

✖️

DOUBLE

✖️

TIME

✖️

✖️

✖️

DOUBLE

✖️

DATETIME

✖️

✖️

✖️

DOUBLE

✖️

TIMESTAMP

✖️

✖️

✖️

DOUBLE

✖️

Comparison with string types

Source type

Comparison with string types

Regular string

Binary string

Basic scalar

String literal

Regular string

Binary string

Numeric literal

Numeric literal

✖️

Numeric

BOOLEAN

BOOLEAN

✖️

Integer types

Integer types

✖️

FLOAT

FLOAT

✖️

DOUBLE

DOUBLE

✖️

DECIMAL

DECIMAL

✖️

String

Regular string

Regular string

Binary string

Binary string

Binary string

Binary string

Date and time

YEAR

INTEGER

✖️

DATE

DATE

✖️

TIME

TIME

✖️

DATETIME

DATETIME

✖️

TIMESTAMP

TIMESTAMP

✖️

Comparison with date and time types

Source type

Comparison with date and time types

YEAR

DATE

TIME

DATETIME

TIMESTAMP

Basic scalar

String literal

YEAR

DATETIME

TIME

DATETIME

TIMESTAMP

Numeric literal

Larger-range numeric type

✖️

✖️

✖️

✖️

Numeric

BOOLEAN

INTEGER

✖️

✖️

✖️

✖️

Integer types

Larger-range integer type

✖️

✖️

✖️

✖️

FLOAT

FLOAT

✖️

✖️

✖️

✖️

DOUBLE

DOUBLE

DOUBLE

DOUBLE

DOUBLE

DOUBLE

DECIMAL

DECIMAL

✖️

✖️

✖️

✖️

String

Regular string

INTEGER

DATE

TIME

DATETIME

TIMESTAMP

Binary string

✖️

✖️

✖️

✖️

✖️

Date and time

YEAR

INTEGER

✖️

✖️

✖️

✖️

DATE

✖️

DATE

✖️

DATETIME

TIMESTAMP

TIME

✖️

✖️

TIME

✖️

✖️

DATETIME

✖️

DATETIME

✖️

DATETIME

DATETIME

TIMESTAMP

✖️

TIMESTAMP

✖️

DATETIME

TIMESTAMP

Potential inconsistencies in query results

Numeric operations

  • Comparisons of floating-point numbers may be incompatible. Example:

    CREATE TABLE t1 (id FLOAT PRIMARY KEY);
    INSERT INTO t1 VALUES (1.22), (1.23), (1.24);
    SELECT * FROM t1 WHERE t1.id > 1.23;
    
    # MySQL query result
    +------+
    | id   |
    +------+
    | 1.23 |
    | 1.24 |
    +------+
    
    # DuckDB-based analytical instance query result
    +------+
    | id   |
    +------+
    | 1.24 |
    +------+
  • The results of complex operations on floating-point numbers may be inconsistent due to floating-point errors.

  • When an operation is performed between integer and DECIMAL types, the result must not exceed the value range of the type. Otherwise, an overflow error may cause the execution to fail.

    CREATE TABLE t1 (id TINYINT PRIMARY KEY);
    INSERT INTO t1 VALUES (100);
    SELECT id * 2 FROM t1;
    
    # MySQL query result
    +--------+
    | id * 2 |
    +--------+
    |    200 |
    +--------+
    
    # DuckDB-based analytical instance query result
    ERROR 7577 (HY000): [DuckDB] Out of Range Error: Overflow in multiplication of INT8 (100 * 2)!.

Inconsistent results caused by collation rules

utf8mb4_0900_xx series collations are incompatible when comparing certain symbol characters. For example:

CREATE TABLE t1 ( id varchar(20) COLLATE utf8mb4_0900_ai_ci PRIMARY KEY );
INSERT INTO t1 VALUES ('!'), ('_');
SELECT * FROM t1 ORDER BY id;

# MySQL query result
+----+
| id |
+----+
| _  |
| !  |
+----+

# DuckDB-based analytical instance query result
+----+
| id |
+----+
| !  |
| _  |
+----+

Handling of NULL values in vector subqueries with IN

In DuckDB-based analytical instances, the handling of NULL values in vector subqueries with IN may be incompatible with MySQL. Example:

CREATE TABLE t1 (id INT PRIMARY KEY, col1 INT);
INSERT INTO t1 VALUES (1, 1), (2, 2);
CREATE TABLE t2 (id INT PRIMARY KEY, col1 INT);
INSERT INTO t2 VALUES (1, NULL);

select (id, col1) in (select id, col1 from t2) from t1;

# MySQL query result
+-----------------------------------------+
| (id, col1) in (select id, col1 from t2) |
+-----------------------------------------+
|                                    NULL |
|                                       0 |
+-----------------------------------------+

# DuckDB-based analytical instance query result
+-----------------------------------------+
| (id, col1) in (select id, col1 from t2) |
+-----------------------------------------+
|                                    NULL |
|                                    NULL |
+-----------------------------------------+

For the data (2, 2), no matching item for the vector prefix exists in the IN clause. In this case, MySQL returns 0, whereas the DuckDB-based analytical instance returns NULL.

Limits on functions

The following table lists only the functions where DuckDB-based analytical instances differ from MySQL.

Aggregate functions

Function name

Supported

Limits

BIT_AND

Yes

String, DECIMAL, and date types are not supported.

BIT_OR

Yes

String, DECIMAL, and date types are not supported.

BIT_XOR

Yes

String, DECIMAL, and date types are not supported.

JSON_ARRAYAGG

No

/

Numeric functions

Numeric functions do not support the BOOLEAN type.

Function name

Supported

Limits

CONV()

No

/

CRC32()

No

/

TRUNCATE()

No

/

String functions

MySQL DuckDB strictly distinguishes between binary strings (such as BLOB and VARBINARY) and strings (such as VARCHAR, TEXT, and JSON). Therefore, the following usage limits for string functions apply only to string inputs, not binary string inputs. Some functions that can accept binary strings as input include the following: CONCAT(), CONCAT_WS(), LENGTH(), MID(), OCTET_LENGTH(), REPEAT(), and TO_BASE64(). Unless otherwise specified, these functions have no usage restrictions.

Function name

Supported

Limits

BIN()

Yes

In MySQL, BIN('') returns NULL, while DuckDB-based analytical instances return '0'.

CHAR()

No

/

ELT()

No

/

EXPORT_SET()

No

/

FIND_IN_SET()

Yes

The first parameter of this function must be of the string type. A non-string type may produce results that are inconsistent with MySQL.

FORMAT()

No

/

FROM_BASE64()

Yes

This function reports an error if base64 decoding fails.

LIKE

Yes

LIKE is not affected by collation rules.

LOAD_FILE()

No

/

MAKE_SET()

No

/

MATCH()

No

/

NOT LIKE

Yes

NOT LIKE is not affected by collation rules.

OCT()

Yes

In MySQL, OCT('') returns NULL, while DuckDB-based analytical instances return '0'.

QUOTE()

No

/

SOUNDEX()

No

/

SOUND LIKE

No

/

UNHEX()

Yes

An error is reported if the function encounters a non-hexadecimal digit.

WEIGHT_STRING()

No

/

Date functions

Function name

Supported

Limits

ADDTIME()

Yes

If the return value exceeds the value range of time-type data for the DuckDB-based analytical instance, inconsistent results will occur.

DATE_FORMAT()

Yes

%X, %V, and %u are not supported.

GET_FORMAT()

No

/

PERIOD_ADD()

Yes

Years greater than 9999 are not supported.

PERIOD_DIFF()

Yes

Years greater than 9999 are not supported.

SEC_TO_TIME()

Yes

If the return value exceeds the value range of the time data type for the DuckDB-based analytical instance, inconsistent results may occur.

STR_TO_DATE()

Yes

  • %X, %V, and %u are not supported.

  • If a format specifier is not correctly matched, NULL is returned.

SUBTIME()

Yes

If the return value is outside the value range of the time-type data for a DuckDB-based analytical instance, inconsistent results may occur.

TIME_TO_SEC()

Yes

The DAY TIME format is not supported. For example: select time_to_sec('1 12:00:00');.

TIMEDIFF()

No

/

JSON functions

Function name

Supported?

Limits

JSON_ARRAY_APPEND()

No

/

JSON_ARRAY_INSERT()

No

/

JSON_INSERT()

No

/

JSON_MERGE()

No

/

JSON_MERGE_PATCH()

Yes

The field order in the merged JSON object may be different from that in MySQL.

JSON_MERGE_PRESERVE()

No

/

JSON_REMOVE()

No

/

JSON_REPLACE()

No

/

JSON_SCHEMA_VALID()

No

/

JSON_SCHEMA_VALIDATION_REPORT()

No

/

JSON_SEARCH()

No

/

JSON_SET()

No

/

JSON_STORAGE_FREE()

No

/

JSON_STORAGE_SIZE()

No

/

JSON_TABLE()

No

/

JSON_TYPE()

No

/

Window functions

Function name

Supported

Limits

JSON_ARRAYAGG

No

/

JSON_OBJECTAGG

No

/