Commit c3ab9712 authored by Igor Babaev's avatar Igor Babaev

Fixed the bug mdev-9719 concerning execution of prepared statements

with window functions. Added the test case for it.
Also allowed to use aliases for set functions in partition and order lists
that are specified in window functions.
parent 72a4969e
...@@ -1177,3 +1177,45 @@ pk c cnt ...@@ -1177,3 +1177,45 @@ pk c cnt
9 2 0 9 2 0
10 2 0 10 2 0
drop table t0, t1; drop table t0, t1;
#
# Window function in grouping query
#
create table t1 (
username varchar(32),
amount int
);
insert into t1 values
('user1',1),
('user1',5),
('user1',3),
('user2',10),
('user2',20),
('user2',30);
select
username,
sum(amount) as s,
rank() over (order by s desc)
from t1
group by username;
username s rank() over (order by s desc)
user1 9 2
user2 60 1
drop table t1;
#
# mdev-9719: Window function in prepared statement
#
create table t1(a int, b int, x char(32));
insert into t1 values (2, 10, 'xx');
insert into t1 values (2, 10, 'zz');
insert into t1 values (2, 20, 'yy');
insert into t1 values (3, 10, 'xxx');
insert into t1 values (3, 20, 'vvv');
prepare stmt from 'select a, row_number() over (partition by a order by b) from t1';
execute stmt;
a row_number() over (partition by a order by b)
2 1
2 2
2 3
3 1
3 2
drop table t1;
...@@ -697,3 +697,48 @@ select ...@@ -697,3 +697,48 @@ select
from t1; from t1;
drop table t0, t1; drop table t0, t1;
--echo #
--echo # Window function in grouping query
--echo #
create table t1 (
username varchar(32),
amount int
);
insert into t1 values
('user1',1),
('user1',5),
('user1',3),
('user2',10),
('user2',20),
('user2',30);
select
username,
sum(amount) as s,
rank() over (order by s desc)
from t1
group by username;
drop table t1;
--echo #
--echo # mdev-9719: Window function in prepared statement
--echo #
create table t1(a int, b int, x char(32));
insert into t1 values (2, 10, 'xx');
insert into t1 values (2, 10, 'zz');
insert into t1 values (2, 20, 'yy');
insert into t1 values (3, 10, 'xxx');
insert into t1 values (3, 20, 'vvv');
prepare stmt from 'select a, row_number() over (partition by a order by b) from t1';
execute stmt;
drop table t1;
...@@ -654,9 +654,10 @@ setup_without_group(THD *thd, Ref_ptr_array ref_pointer_array, ...@@ -654,9 +654,10 @@ setup_without_group(THD *thd, Ref_ptr_array ref_pointer_array,
thd->lex->allow_sum_func&= ~((nesting_map)1 << select->nest_level); thd->lex->allow_sum_func&= ~((nesting_map)1 << select->nest_level);
res= res || setup_group(thd, ref_pointer_array, tables, fields, all_fields, res= res || setup_group(thd, ref_pointer_array, tables, fields, all_fields,
group, hidden_group_fields); group, hidden_group_fields);
thd->lex->allow_sum_func= save_allow_sum_func; thd->lex->allow_sum_func|= (nesting_map)1 << select->nest_level;
res= res || setup_windows(thd, ref_pointer_array, tables, fields, all_fields, res= res || setup_windows(thd, ref_pointer_array, tables, fields, all_fields,
win_specs); win_specs);
thd->lex->allow_sum_func= save_allow_sum_func;
DBUG_RETURN(res); DBUG_RETURN(res);
} }
......
...@@ -79,7 +79,7 @@ Window_frame::check_frame_bounds() ...@@ -79,7 +79,7 @@ Window_frame::check_frame_bounds()
int int
setup_windows(THD *thd, Ref_ptr_array ref_pointer_array, TABLE_LIST *tables, setup_windows(THD *thd, Ref_ptr_array ref_pointer_array, TABLE_LIST *tables,
List<Item> &fields, List<Item> &all_fields, List<Item> &fields, List<Item> &all_fields,
List<Window_spec> win_specs) List<Window_spec> &win_specs)
{ {
Window_spec *win_spec; Window_spec *win_spec;
DBUG_ENTER("setup_windows"); DBUG_ENTER("setup_windows");
...@@ -90,6 +90,8 @@ setup_windows(THD *thd, Ref_ptr_array ref_pointer_array, TABLE_LIST *tables, ...@@ -90,6 +90,8 @@ setup_windows(THD *thd, Ref_ptr_array ref_pointer_array, TABLE_LIST *tables,
We could have avoided it if we had built two separate lists for We could have avoided it if we had built two separate lists for
named and unnamed specifications. named and unnamed specifications.
*/ */
Query_arena *arena, backup;
arena= thd->activate_stmt_arena_if_needed(&backup);
uint i = 0; uint i = 0;
uint elems= win_specs.elements; uint elems= win_specs.elements;
while ((win_spec= it++) && i++ < elems) while ((win_spec= it++) && i++ < elems)
...@@ -100,6 +102,9 @@ setup_windows(THD *thd, Ref_ptr_array ref_pointer_array, TABLE_LIST *tables, ...@@ -100,6 +102,9 @@ setup_windows(THD *thd, Ref_ptr_array ref_pointer_array, TABLE_LIST *tables,
win_specs.push_back(win_spec); win_specs.push_back(win_spec);
} }
} }
if (arena)
thd->restore_active_arena(arena, &backup);
it.rewind(); it.rewind();
List_iterator_fast<Window_spec> itp(win_specs); List_iterator_fast<Window_spec> itp(win_specs);
......
...@@ -130,6 +130,6 @@ class Window_def : public Window_spec ...@@ -130,6 +130,6 @@ class Window_def : public Window_spec
int setup_windows(THD *thd, Ref_ptr_array ref_pointer_array, TABLE_LIST *tables, int setup_windows(THD *thd, Ref_ptr_array ref_pointer_array, TABLE_LIST *tables,
List<Item> &fields, List<Item> &all_fields, List<Item> &fields, List<Item> &all_fields,
List<Window_spec> win_specs); List<Window_spec> &win_specs);
#endif /* SQL_WINDOW_INCLUDED */ #endif /* SQL_WINDOW_INCLUDED */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment