Commit bcc8ba78 authored by kevg's avatar kevg Committed by Aleksey Midenkov

SQL, Tests: versioning for nested queries and CTE [closes #74]

parent c9b2980c
create table emp
(
emp_id int,
name varchar(127),
mgr int
) with system versioning;
insert into emp values (1, 'bill', 0),
(2, 'bill', 1),
(3, 'kate', 1);
set @ts=now(6);
delete from emp;
insert into emp values (4, 'john', 1);
with ancestors as (select * from emp) select * from ancestors;
emp_id name mgr
4 john 1
set @tmp= "with ancestors as (select * from emp) select * from ancestors";
prepare stmt from @tmp;
execute stmt;
emp_id name mgr
4 john 1
drop prepare stmt;
with ancestors as (select * from emp for system_time all) select * from ancestors for system_time all;
emp_id name mgr
1 bill 0
2 bill 1
3 kate 1
4 john 1
set @tmp= "with ancestors as (select * from emp for system_time all) select * from ancestors for system_time all";
prepare stmt from @tmp;
execute stmt;
emp_id name mgr
1 bill 0
2 bill 1
3 kate 1
4 john 1
drop prepare stmt;
with recursive ancestors as (select * from emp) select * from ancestors;
emp_id name mgr
4 john 1
set @tmp= "with recursive ancestors as (select * from emp) select * from ancestors";
prepare stmt from @tmp;
execute stmt;
emp_id name mgr
4 john 1
drop prepare stmt;
select emp_id from (select emp_id from emp where sys_trx_end>'2031-1-1') as tmp;
emp_id
4
set @tmp= "select emp_id from (select emp_id from emp where sys_trx_end>'2031-1-1') as tmp";
prepare stmt from @tmp;
execute stmt;
emp_id
4
drop prepare stmt;
with recursive
ancestors
as
(
select e.emp_id, e.name, e.mgr
from emp as e
where name = 'john'
union
select ee.emp_id, ee.name, ee.mgr
from emp as ee, ancestors as a
where ee.mgr = a.emp_id
)
select * from ancestors;
emp_id name mgr
4 john 1
set @tmp= "
with recursive
ancestors
as
(
select e.emp_id, e.name, e.mgr
from emp as e
where name = 'john'
union
select ee.emp_id, ee.name, ee.mgr
from emp as ee, ancestors as a
where ee.mgr = a.emp_id
)
select * from ancestors
";
prepare stmt from @tmp;
execute stmt;
emp_id name mgr
4 john 1
drop prepare stmt;
with recursive
ancestors
as
(
select e.emp_id, e.name, e.mgr
from emp as e for system_time as of timestamp @ts
where name = 'bill'
union
select ee.emp_id, ee.name, ee.mgr
from emp as ee for system_time as of timestamp @ts, ancestors as a for system_time as of timestamp @ts
where ee.mgr = a.emp_id
)
select * from ancestors for system_time as of timestamp @ts;
emp_id name mgr
1 bill 0
2 bill 1
3 kate 1
set @tmp= "
with recursive
ancestors
as
(
select e.emp_id, e.name, e.mgr
from emp as e for system_time as of timestamp @ts
where name = 'bill'
union
select ee.emp_id, ee.name, ee.mgr
from emp as ee for system_time as of timestamp @ts, ancestors as a for system_time as of timestamp @ts
where ee.mgr = a.emp_id
)
select * from ancestors for system_time as of timestamp @ts;
";
prepare stmt from @tmp;
execute stmt;
emp_id name mgr
1 bill 0
2 bill 1
3 kate 1
drop prepare stmt;
drop table emp;
create table emp
(
emp_id int,
name varchar(127),
mgr int
) with system versioning;
insert into emp values (1, 'bill', 0),
(2, 'bill', 1),
(3, 'kate', 1);
set @ts=now(6);
delete from emp;
insert into emp values (4, 'john', 1);
with ancestors as (select * from emp) select * from ancestors;
set @tmp= "with ancestors as (select * from emp) select * from ancestors";
prepare stmt from @tmp; execute stmt; drop prepare stmt;
with ancestors as (select * from emp for system_time all) select * from ancestors for system_time all;
set @tmp= "with ancestors as (select * from emp for system_time all) select * from ancestors for system_time all";
prepare stmt from @tmp; execute stmt; drop prepare stmt;
with recursive ancestors as (select * from emp) select * from ancestors;
set @tmp= "with recursive ancestors as (select * from emp) select * from ancestors";
prepare stmt from @tmp; execute stmt; drop prepare stmt;
select emp_id from (select emp_id from emp where sys_trx_end>'2031-1-1') as tmp;
set @tmp= "select emp_id from (select emp_id from emp where sys_trx_end>'2031-1-1') as tmp";
prepare stmt from @tmp; execute stmt; drop prepare stmt;
with recursive
ancestors
as
(
select e.emp_id, e.name, e.mgr
from emp as e
where name = 'john'
union
select ee.emp_id, ee.name, ee.mgr
from emp as ee, ancestors as a
where ee.mgr = a.emp_id
)
select * from ancestors;
set @tmp= "
with recursive
ancestors
as
(
select e.emp_id, e.name, e.mgr
from emp as e
where name = 'john'
union
select ee.emp_id, ee.name, ee.mgr
from emp as ee, ancestors as a
where ee.mgr = a.emp_id
)
select * from ancestors
";
prepare stmt from @tmp; execute stmt; drop prepare stmt;
with recursive
ancestors
as
(
select e.emp_id, e.name, e.mgr
from emp as e for system_time as of timestamp @ts
where name = 'bill'
union
select ee.emp_id, ee.name, ee.mgr
from emp as ee for system_time as of timestamp @ts, ancestors as a for system_time as of timestamp @ts
where ee.mgr = a.emp_id
)
select * from ancestors for system_time as of timestamp @ts;
set @tmp= "
with recursive
ancestors
as
(
select e.emp_id, e.name, e.mgr
from emp as e for system_time as of timestamp @ts
where name = 'bill'
union
select ee.emp_id, ee.name, ee.mgr
from emp as ee for system_time as of timestamp @ts, ancestors as a for system_time as of timestamp @ts
where ee.mgr = a.emp_id
)
select * from ancestors for system_time as of timestamp @ts;
";
prepare stmt from @tmp; execute stmt; drop prepare stmt;
drop table emp;
......@@ -10271,7 +10271,8 @@ void Item_cache_row::set_null()
Item_type_holder::Item_type_holder(THD *thd, Item *item)
:Item(thd, item),
Type_handler_hybrid_field_type(item->real_type_handler()),
enum_set_typelib(0)
enum_set_typelib(0),
flags(0)
{
DBUG_ASSERT(item->fixed);
maybe_null= item->maybe_null;
......@@ -10282,6 +10283,12 @@ Item_type_holder::Item_type_holder(THD *thd, Item *item)
if (item->field_type() == MYSQL_TYPE_GEOMETRY)
geometry_type= item->get_geometry_type();
#endif /* HAVE_SPATIAL */
if (item->real_type() == Item::FIELD_ITEM)
{
Item_field *item_field= (Item_field*)item->real_item();
flags|=
(item_field->field->flags & (VERS_SYS_START_FLAG | VERS_SYS_END_FLAG));
}
}
......
......@@ -5892,6 +5892,8 @@ class Item_type_holder: public Item,
Field *make_field_by_type(TABLE *table);
Field::geometry_type get_geometry_type() const { return geometry_type; };
Item* get_copy(THD *thd, MEM_ROOT *mem_root) { return 0; }
uint flags;
};
......
......@@ -713,6 +713,26 @@ bool mysql_derived_prepare(THD *thd, LEX *lex, TABLE_LIST *derived)
cursor= cursor->next_local)
cursor->outer_join|= JOIN_TYPE_OUTER;
}
if ((thd->stmt_arena->is_stmt_prepare() ||
!thd->stmt_arena->is_stmt_execute()) &&
!derived->is_view() && sl->table_list.elements > 0)
{
TABLE_LIST *tl= sl->table_list.first;
if (tl->table && tl->table->versioned())
{
TABLE_SHARE *s= tl->table->s;
const char *db= tl->db;
const char *alias= tl->alias;
Query_arena backup;
Query_arena *arena= thd->activate_stmt_arena_if_needed(&backup);
sl->item_list.push_back(new (thd->mem_root) Item_field(
thd, &sl->context, db, alias, s->vers_start_field()->field_name));
sl->item_list.push_back(new (thd->mem_root) Item_field(
thd, &sl->context, db, alias, s->vers_end_field()->field_name));
if (arena)
thd->restore_active_arena(arena, &backup);
}
}
}
unit->derived= derived;
......
......@@ -807,12 +807,20 @@ int vers_setup_select(THD *thd, TABLE_LIST *tables, COND **where_expr,
Field *fstart= table->table->vers_start_field();
Field *fend= table->table->vers_end_field();
DBUG_ASSERT(slex->parent_lex);
Name_resolution_context *context= slex->parent_lex->current_context();
DBUG_ASSERT(context);
Item *row_start= newx Item_field(thd, context, fstart);
Item *row_end= newx Item_field(thd, context, fend);
Item *row_start= NULL;
Item *row_end= NULL;
if (table->is_derived() && !table->is_recursive_with_table())
{
row_start= newx Item_field(thd, &slex->context, NULL, NULL,
fstart->field_name);
row_end=
newx Item_field(thd, &slex->context, NULL, NULL, fend->field_name);
}
else
{
row_start= newx Item_field(thd, &slex->context, fstart);
row_end= newx Item_field(thd, &slex->context, fend);
}
Item *row_end2= row_end;
if (table->table->versioned_by_sql())
......@@ -16859,6 +16867,14 @@ create_tmp_table(THD *thd, TMP_TABLE_PARAM *param, List<Item> &fields,
sys_trx_end= new_field;
}
}
if (type == Item::TYPE_HOLDER)
{
Item_type_holder *ith= (Item_type_holder*)item;
if (ith->flags & VERS_SYS_START_FLAG)
sys_trx_start= new_field;
else if (ith->flags & VERS_SYS_END_FLAG)
sys_trx_end= new_field;
}
if (type == Item::SUM_FUNC_ITEM)
{
Item_sum *agg_item= (Item_sum *) item;
......
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