ydb-platform / ydb

YDB is an open source Distributed SQL Database that combines high availability and scalability with strong consistency and ACID transactions
https://ydb.tech
Apache License 2.0
3.69k stars 501 forks source link

TPC-DS q23 fails with OptUseFinalizeByKey #5475

Open zverevgeny opened 3 weeks ago

zverevgeny commented 3 weeks ago

Дело в том, что в таблице store_sales в колонках ss_customer_sk и ss_sold_date_sk могут быть NULL. А они являются ключами джоина. В JoinDict в случае Inner join мы требуем, чтобы ключи джоина были не NULL.

Tony-Romanov commented 3 weeks ago

Где тест, или как это воспроизводить?

zverevgeny commented 1 week ago

@Darych, допиши сюда, пожалуйста, минимальный пример воспроизводящий ошибку

Darych commented 1 week ago
PRAGMA dq.HashJoinMode = "grace";
pragma dq.ComputeActorType="sync";
pragma dq.OptLLVM="off";
PRAGMA s3.UseBlocksSource="true";
pragma dq.MaxTasksPerStage="1";
pragma config.flags="LLVM_OFF";
pragma dq.UseFinalizeByKey="true";
pragma AnsiOptionalAs="1";

$max_store_sales =
 (select max(csales) tpcds_cmax
  from (select sum(ss_quantity*ss_sales_price) csales
        from bindings.store_sales as store_sales
            cross join bindings.customer as customer
            cross join bindings.date_dim as date_dim
        where
        -- ss_customer_sk is not null and ss_sold_date_sk is not null
        and ss_customer_sk = c_customer_sk
         and ss_sold_date_sk = d_date_sk
        group by customer.c_customer_sk) x);

 select customer.c_customer_sk c_customer_sk,sum(ss_quantity*ss_sales_price) ssales
  from bindings.store_sales as store_sales
      cross join bindings.customer as customer
  where ss_customer_sk = c_customer_sk
  group by customer.c_customer_sk
  having sum(ss_quantity*ss_sales_price) > (95/100.0) * $max_store_sales;

Собрал покороче пример на котором воспроизводится проблема. Биндинги из TPC-DS Лог с проблемой прикреплен run_failed.log

Если в примере запроса расскоментить строку с фильтром на NOT NULL, то запрос проходит. Лог прикреплен как run.log

Дело в том, что в таблице store_sales в колонках ss_customer_sk и ss_sold_date_sk могут быть NULL. А они являются ключами джоина. В JoinDict в случае Inner join мы требуем, чтобы ключи джоина были не NULL. run.log run_failed.log bindings.json

Tony-Romanov commented 1 week ago

Понятней не стало. Чем это воспроизводится? Можно в виде теста куда-то в github положить?

Tony-Romanov commented 1 week ago

Получилось запустить на dqrun и запрос успешно отработал.

yumkam commented 1 week ago

q23 или q23 с FinalizeByKey? Только что проверил, https://gist.github.com/yumkam/72a58da03d56b0ef21ab9d90155c4ff2 валится

Tony-Romanov commented 1 week ago

Взял это запрос и эти биндинги и всё отработло. Не понимаю что я не так делаю.

Tony-Romanov commented 1 week ago

И ещё не понятно откуда вообще может браться JoinDict? После перехода на GraceJoin он уже не должен возникать вообще никогда.

yumkam commented 1 week ago

Можно сравнить логи, plan, ast и результат. Я добавил в gist для падающего (-fbk) и не падающего (-no-fbk) вариантов.

Tony-Romanov commented 1 week ago

Там нечего сравнивать ибо JoinDict вообще не должен возникать никогда, даже если отработал правильно. Надо подебажить оптимайзер и посмотреть почему он возник. А gateways.cfg можно сюда положить?

yumkam commented 1 week ago

Почти не отличается от dqrun/examples/gateways.conf. Добавил в gist.

yumkam commented 6 days ago

А какие опции сборки у dqrun? Если release, то там отключены assert, и он просто молча проглатывает багу (бага при этом остаётся багой: JoinDict не умеет отрабатывать NULL и само его применение является ошибкой). (В relwithdebinfo, не только отладочная информация, но и, внезапно, assert не отключены)