PNixx / clickhouse-activerecord

A Ruby database ActiveRecord driver for ClickHouse
MIT License
202 stars 100 forks source link

Columns with non-direct default values are returning a boolean after insertion #174

Closed ottony closed 1 month ago

ottony commented 1 month ago

When inserting a new entry with a non-direct default value, such as being generated from other columns, the value of the attribute will be a kind of boolean in the first moment, not the default value as expected.

The value is right on the database, this occurs right after inserting at the instance level.

How to reproduce

Given the following table/model

CREATE TABLE tests (
  id UUID,
  field_a String,
  field_b String,
  derived_field String DEFAULT(field_a || '-' || field_b),
) ENGINE = MergeTree ORDER BY (id)

Inserting a new entry without specifying the derived_field is setting t (True) in the instance attribute and not the concatenation of field_a and field_b as expected.

> test = Test.create(id: SecureRandom.uuid, field_a: 'A', field_b: 'B')
=> #<Test:0x00007c1df223e380 id: "99d08942-9c31-436d-b6f0-72364deb0b90", field_a: "A", field_b: "B", derived_field: "t">

> test.derived_field
=> "t"

After reloading or selecting, the right value is set on the instance.

> test.reload.derived_field
=> "A-B"

Version:

PNixx commented 1 month ago

Now this is impossible https://github.com/ClickHouse/ClickHouse/issues/21697

ottony commented 1 month ago

Thanks for the reference @PNixx

In previous versions, it just returns nil. (clickhouse-activerecord 0.6.1, Rails 6.1.7)

I don't know if we can differentiate this case, but would it be a good idea to enforce the previous behavior of returning nil to not return an unexpected value like "t"?

# clickhouse-activerecord 0.6.1, Rails 6.1.7
> test = Test.create(id: SecureRandom.uuid, field_a: 'A', field_b: 'B')
=> #<Test:0x0000702aa2fbd8e8 id: "ce3a10f6-a141-4bdd-b163-ac24f72a4c34", field_a: "A", field_b: "B", derived_field: nil>

> test.derived_field
=> nil

What do you think?