Revision history for DBIO-ClickHouse
0.900004 2026-11-08
First release: the ClickHouse driver for DBIO, over the MySQL wire
protocol (server port 9004) through DBD::mysql or DBD::MariaDB.
* Transport
- DBD::mysql is the standard: it connects to a stock server and to
ClickHouse Cloud; connect with mysql_enable_utf8mb4 => 1 for
character data.
- DBD::MariaDB needs the server to register the character_set_,
collation_ and sql_ custom settings prefixes, so it fits servers
whose config you control (ADR 0001).
- Both DBDs are the access path of DBIO::ClickHouse::Storage, also
under driver_strict. The DSN looks like MySQL's, so a schema pins
the storage with the component or use DBIO 'Schema', -ch.
* Storage
- DBIO::ClickHouse::Storage quotes with backticks, pings with SELECT
1 and answers clickhouse_version.
- Inserts fit a database without identity columns: populate is one
multi-row INSERT, a UUID primary key marked is_auto_increment is
generated client-side, and last_insert_id throws.
- Transactions follow ADR 0003: txn_begin, txn_commit and txn_do run
without a transaction and warn once, txn_rollback throws, and a
scope guard unwinds without a rollback and says so.
- No transactional DDL, IF [NOT] EXISTS and EXISTS queries are
declared; set operations carry an explicit DISTINCT or ALL, rand
is rand(), explain answers the plan (see SET OPERATIONS).
- $schema->deploy runs through DBIO::ClickHouse::Deploy, and
deployment_statements serves the native DDL layer.
- A string that is not a number and an integer outside its column's
type range are refused before they are sent, naming table and
column; a value with the byte 0x1A is stored as written.
- The message of a failed statement names the error code, the type,
the column, the constraint, the table and the position of a syntax
error, and the number of bind values; the values themselves are
replaced by *** wherever the engine quotes them: in the sentence
of the error, in the statement it quotes, in the Column values of
a violated constraint and in the plan of a failed function. This
holds for selects, inserts, the multi-row insert of populate,
update and delete alike; $dbh->errstr keeps the raw text
(ADR 0008).
* SQLMaker
- The resultset attributes final => 1, prewhere => \%cond and
limit_by => { rows => $n, by => $cols } render ClickHouse's
clauses; SELECT ... FOR UPDATE is not written.
* Mutations
- update and delete on resultsets and rows render as mutations
(ALTER TABLE ... UPDATE / DELETE), with mutations_sync => 1 per
statement by default (ADR 0005).
- update and delete return -1, row count unknown; a view, a literal
SQL source or a join as target and an UPDATE without columns are
refused.
* DDL
- DBIO::ClickHouse::DDL maps portable types to Nullable,
LowCardinality, Decimal, DateTime64, Date32, UUID, Bool, Enum8/16
and Array; a type spelled as ClickHouse spells it is written as is.
- clickhouse_table({ engine, order_by, primary_key, partition_by,
settings }) on a result class; the default is ENGINE = MergeTree
ordered by the primary key.
- Canonical index declarations with clickhouse => { type => ... }
become data-skipping indexes in CREATE TABLE.
- install_ddl refuses what ClickHouse cannot build, naming table and
column: unique constraints, foreign key constraints (declare
is_foreign_key_constraint => 0), a non-UUID auto-increment column.
- A source named database.table or database.view is made in that
database, and install refuses a missing database; a view follows
the views it reads, a cycle is refused.
* Introspect
- DBIO::ClickHouse::Introspect reads system.tables, system.columns
and system.data_skipping_indices into the canonical model, with
engine, sorting key, partition key and view definitions.
* Diff and Deploy
- The Diff compares in a scratch database on the same server,
dropped in every case, and writes IF [NOT] EXISTS wherever
ClickHouse parses it, so a re-applied diff changes nothing.
- A change of engine, sorting key, primary key or partition
expression is refused with the rebuild steps.
- Skipping indexes, views, the SETTINGS of new tables and removed
defaults are diffed; a materialized view is refused by name.
- apply and upgrade are those of DBIO::Deploy::Base: a lossy column
change needs allow_destructive, and a narrowing over NULL rows or a
NOT NULL column added over rows is refused before the first
statement.
* Native export
- DBIO::ClickHouse::Native turns a source and its rows into the
columns and row iterator ClickHouse::Encoder takes, and throws for
a value it cannot translate truthfully (ADR 0007).
* Async
- The driver is sync-only (ADR 0006); the forked and immediate
adapters apply.
* Tests
- DBIO::ClickHouse::Test::Conformance answers core's shared DDL, Diff
and Bind case tables offline and against a server, with
DBIO::ClickHouse::Test::Schema as the live fixture.
- Live tests run when DBIO_TEST_CLICKHOUSE_DSN is set, each process
in a database of its own.
* Dependencies
- Requires DBIO 0.900004, Crypt::URandom, DBI, Try::Tiny,
namespace::clean and SQL::Abstract; DBD::mysql and DBD::MariaDB are
recommended, ClickHouse::Encoder is suggested and never loaded.
Keyboard Shortcuts
Global
s
Focus search bar
?
Bring up this help dialog
GitHub
gp
Go to pull requests
gi
Go to GitHub issues (only if GitHub is preferred repository)