1
0
mirror of https://github.com/MariaDB/server.git synced 2025-07-30 16:24:05 +03:00

Bug #26242 UPDATE with subquery and triggers failing with cluster tables

In certain cases AFTER UPDATE/DELETE triggers on NDB tables that referenced
subject table didn't see the results of operation which caused invocation
of those triggers. In other words AFTER trigger invoked as result of update
(or deletion) of particular row saw version of this row before update (or
deletion).

The problem occured because NDB handler in those cases postponed actual
update/delete operations to be able to perform them later as one batch.

This fix solves the problem by disabling this optimization for particular
operation if subject table has AFTER trigger for this operation defined.
To achieve this we introduce two new flags for handler::extra() method:
HA_EXTRA_DELETE_CANNOT_BATCH and HA_EXTRA_UPDATE_CANNOT_BATCH.
These are called if there exists AFTER DELETE/UPDATE triggers during a
statement that potentially can generate calls to delete_row()/update_row().
This includes multi_delete/multi_update statements as well as insert statements
that do delete/update as part of an ON DUPLICATE statement.
This commit is contained in:
mskold/marty@mysql.com/linux.site
2007-04-04 12:50:39 +02:00
parent 6ac9a28ef0
commit 625a2629f0
11 changed files with 416 additions and 8 deletions

View File

@ -209,7 +209,19 @@ bool mysql_delete(THD *thd, TABLE_LIST *table_list, COND *conds,
thd->proc_info="updating";
if (table->triggers)
{
table->triggers->mark_fields_used(thd, TRG_EVENT_DELETE);
if (table->triggers->has_triggers(TRG_EVENT_DELETE,
TRG_ACTION_AFTER))
{
/*
The table has AFTER DELETE triggers that might access to subject table
and therefore might need delete to be done immediately. So we turn-off
the batching.
*/
(void) table->file->extra(HA_EXTRA_DELETE_CANNOT_BATCH);
}
}
while (!(error=info.read_record(&info)) && !thd->killed &&
!thd->net.report_error)
@ -526,7 +538,19 @@ multi_delete::initialize_tables(JOIN *join)
else
normal_tables= 1;
if (tbl->triggers)
{
tbl->triggers->mark_fields_used(thd, TRG_EVENT_DELETE);
if (tbl->triggers->has_triggers(TRG_EVENT_DELETE,
TRG_ACTION_AFTER))
{
/*
The table has AFTER DELETE triggers that might access to subject
table and therefore might need delete to be done immediately.
So we turn-off the batching.
*/
(void) tbl->file->extra(HA_EXTRA_DELETE_CANNOT_BATCH);
}
}
}
else if ((tab->type != JT_SYSTEM && tab->type != JT_CONST) &&
walk == delete_tables)