Uploaded image for project: 'MariaDB Server'
  1. MariaDB Server
  2. MDEV-41573

Partitioning by COLUMNS or KEY on a virtual column changes the query result after an ALTER TABLE changes its expression

    XMLWordPrintable

Details

    Description

      Similar to MDEV-41479, however the patch does not overlap, so adding it as a separate bug.

      --source include/have_partition.inc
       
      CREATE TABLE t1 (a INT, v INT AS (a+1) VIRTUAL) PARTITION BY LIST COLUMNS (v) (PARTITION p0 VALUES IN (2,3,4), PARTITION p1 DEFAULT);
      INSERT INTO t1 (a) VALUES (3);
      # With v = a+2 the row gets v = 5, which belongs in p1
      ALTER TABLE t1 MODIFY v INT AS (a+2) VIRTUAL;
      --let $c= query_get_value(SELECT COUNT(*) AS c FROM t1 WHERE v=5, c, 1)
      if ($c != 1)
      {
        --die The row with v=5 is not found by v=5 after the expression of the LIST COLUMNS column v was changed
      }
      DROP TABLE t1;

      Leads to:

      CS 13.1.0 da18481158c81ca94689702073c3e04aad85a6a3 (Debug, Clang 22.1.8-20260622) Build 18/08/2026

      mysqltest: At line 10: The row with v=5 is not found by v=5 after the expression of the LIST COLUMNS column v was changed

      Partitioning changes the query result. Without partitioning, v=5 finds the row after the same ALTER TABLE. InnoDB gives the same wrong result, and so do RANGE COLUMNS (v), KEY (v) and SUBPARTITION BY KEY (v). With KEY (v) and eight rows, a lookup of each new v value finds 4 of the 8 rows. With PARTITION BY LIST (v), or with ALGORITHM=COPY, the row is found. Optimized builds give the same result.

      MySQL

      +--------+------------------+---------+-------------------+
      | MySQL  | LIST COLUMNS (v) | KEY (v) | RANGE COLUMNS (v) |
      +--------+------------------+---------+-------------------+
      | 5.7.44 | 1 of 1           | 8 of 8  | 1 of 1            |
      | 8.0.36 | 1 of 1           | 8 of 8  | 1 of 1            |
      | 9.1.0  | 1 of 1           | 8 of 8  | 1 of 1            |
      +--------+------------------+---------+-------------------+

      From the code it seems that v is not marked as used by the partitioning. For COLUMNS and KEY partitioning, fix_partition_func() in sql/sql_partition.cc calls handle_list_of_fields() and not fix_fields_part_func(), so post_fix_fields_part_expr_processor does not run and is_in_partitioning_expr() stays false. fill_alter_inplace_info() in sql/sql_table.cc then does not set ALTER_COLUMN_VCOL, and the row is not moved.

      Attachments

        Issue Links

          Activity

            People

              ycp Yuchen Pei
              Roel Roel Van de Paar
              Votes:
              0 Vote for this issue
              Watchers:
              1 Start watching this issue

              Dates

                Created:
                Updated:

                Time Tracking

                  Estimated:
                  Original Estimate - Not Specified
                  Not Specified
                  Remaining:
                  Remaining Estimate - Not Specified
                  Not Specified
                  Logged:
                  Time Spent - 1.25h
                  1.25h

                  Git Integration

                    Error rendering 'com.xiplink.jira.git.jira_git_plugin:git-issue-webpanel'. Please contact your Jira administrators.