Below is the list of changes that have just been committed into a local
5.0 repository of antony. When antony does a push these changes will
be propagated to the main repository and, within 24 hours after the
push, to the public repository.
For information on how to access the public repository
see http://dev.mysql.com/doc/mysql/en/installing-source-tree.html
ChangeSet
1.1887 05/07/05 17:00:47 acurtis@stripped +23 -0
table.h, sql_show.cc, sql_parse.cc:
TRIGGERS information schema
sql_yacc.yy:
trigger names are schema scope, not table scope.
SHOW TRIGGERS
sql_trigger.h:
methods to drop all triggers and get trigger details
function to resolve table from trigger name,
sql_trigger.cc:
trigname_file_ext
must check if there are any collisions in the namespace
new methods to drop all triggers.
function to find table from trigger
method to obtain trigger details
sql_table.cc:
Drop all triggers when dropping table
sql_lex.h, mysqld.cc:
SHOW TRIGGERS
errmsg.txt:
New trigger error message and warnings
mysql_priv.h:
new global symbol trigname_file_ext
lex.h:
new TRIGGERS keyword
item.h:
new consts TRG_ACTION_MAX and TRG_EVENT_MAX
handler.cc:
add trigname to list of known exts
view.test, rpl_sp.test, view.result, rpl_sp.result:
remove table name from trigger identifier
trigger.test, trigger.result:
remove table name from trigger identifier
test namespace of trigger
information_schema.test, information_schema.result:
New TRIGGERS view with test
information_schema_db.result:
New TRIGGERS table
sql/table.h
1.102 05/07/05 16:58:23 acurtis@stripped +1 -1
TRIGGERS information schema
sql/sql_yacc.yy
1.406 05/07/05 16:58:23 acurtis@stripped +25 -7
trigger names are schema scope, not table scope.
SHOW TRIGGERS
sql/sql_trigger.h
1.9 05/07/05 16:58:22 acurtis@stripped +10 -0
methods to drop all triggers and get trigger details
function to resolve table from trigger name,
sql/sql_trigger.cc
1.20 05/07/05 16:58:22 acurtis@stripped +288 -0
trigname_file_ext
must check if there are any collisions in the namespace
new methods to drop all triggers.
function to find table from trigger
method to obtain trigger details
sql/sql_table.cc
1.258 05/07/05 16:58:22 acurtis@stripped +10 -12
Drop all triggers when dropping table
sql/sql_show.cc
1.256 05/07/05 16:58:21 acurtis@stripped +115 -0
TRIGGERS information schema
sql/sql_parse.cc
1.442 05/07/05 16:58:21 acurtis@stripped +1 -0
TRIGGERS information schema
sql/sql_lex.h
1.188 05/07/05 16:58:21 acurtis@stripped +1 -0
SHOW TRIGGERS
sql/share/errmsg.txt
1.37 05/07/05 16:58:20 acurtis@stripped +6 -0
New trigger error message and warnings
sql/mysqld.cc
1.479 05/07/05 16:58:20 acurtis@stripped +1 -0
SHOW TRIGGERS
sql/mysql_priv.h
1.324 05/07/05 16:58:20 acurtis@stripped +1 -0
new global symbol trigname_file_ext
sql/lex.h
1.138 05/07/05 16:58:20 acurtis@stripped +1 -0
new TRIGGERS keyword
sql/item.h
1.149 05/07/05 16:58:19 acurtis@stripped +2 -2
new consts TRG_ACTION_MAX and TRG_EVENT_MAX
sql/handler.cc
1.179 05/07/05 16:58:19 acurtis@stripped +1 -0
add trigname to list of known exts
mysql-test/t/view.test
1.78 05/07/05 16:58:19 acurtis@stripped +1 -1
remove table name from trigger identifier
mysql-test/t/trigger.test
1.13 05/07/05 16:58:19 acurtis@stripped +37 -18
remove table name from trigger identifier
test namespace of trigger
mysql-test/t/rpl_sp.test
1.4 05/07/05 16:58:19 acurtis@stripped +1 -1
remove table name from trigger identifier
mysql-test/t/information_schema.test
1.42 05/07/05 16:58:19 acurtis@stripped +41 -0
New TRIGGERS view with test
mysql-test/r/view.result
1.92 05/07/05 16:58:19 acurtis@stripped +1 -1
remove table name from trigger identifier
mysql-test/r/trigger.result
1.9 05/07/05 16:58:18 acurtis@stripped +32 -17
remove table name from trigger identifier
test namespace of trigger
mysql-test/r/rpl_sp.result
1.5 05/07/05 16:58:18 acurtis@stripped +2 -2
remove table name from trigger identifier
mysql-test/r/information_schema_db.result
1.3 05/07/05 16:58:18 acurtis@stripped +2 -0
New TRIGGERS table
mysql-test/r/information_schema.result
1.59 05/07/05 16:58:18 acurtis@stripped +61 -2
New TRIGGERS view with test
# This is a BitKeeper patch. What follows are the unified diffs for the
# set of deltas contained in the patch. The rest of the patch, the part
# that BitKeeper cares about, is below these diffs.
# User: acurtis
# Host: ltantony.xiphis.org
# Root: /usr/home/antony/work2/p2-bug5892.2
--- 1.178/sql/handler.cc 2005-07-04 01:50:00 +01:00
+++ 1.179/sql/handler.cc 2005-07-05 16:58:19 +01:00
@@ -2434,6 +2434,7 @@
known_extensions_id= mysys_usage_id;
found_exts.push_back((char*) triggers_file_ext);
+ found_exts.push_back((char*) trigname_file_ext);
for (types= sys_table_types; types->type; types++)
{
if (*types->value == SHOW_OPTION_YES)
--- 1.148/sql/item.h 2005-07-04 01:50:00 +01:00
+++ 1.149/sql/item.h 2005-07-05 16:58:19 +01:00
@@ -1768,7 +1768,7 @@
*/
enum trg_action_time_type
{
- TRG_ACTION_BEFORE= 0, TRG_ACTION_AFTER= 1
+ TRG_ACTION_BEFORE= 0, TRG_ACTION_AFTER= 1, TRG_ACTION_MAX
};
/*
@@ -1776,7 +1776,7 @@
*/
enum trg_event_type
{
- TRG_EVENT_INSERT= 0 , TRG_EVENT_UPDATE= 1, TRG_EVENT_DELETE= 2
+ TRG_EVENT_INSERT= 0 , TRG_EVENT_UPDATE= 1, TRG_EVENT_DELETE= 2, TRG_EVENT_MAX
};
class Table_triggers_list;
--- 1.137/sql/lex.h 2005-07-01 13:51:49 +01:00
+++ 1.138/sql/lex.h 2005-07-05 16:58:20 +01:00
@@ -497,6 +497,7 @@
{ "TRAILING", SYM(TRAILING)},
{ "TRANSACTION", SYM(TRANSACTION_SYM)},
{ "TRIGGER", SYM(TRIGGER_SYM)},
+ { "TRIGGERS", SYM(TRIGGERS_SYM)},
{ "TRUE", SYM(TRUE_SYM)},
{ "TRUNCATE", SYM(TRUNCATE_SYM)},
{ "TYPE", SYM(TYPE_SYM)},
--- 1.323/sql/mysql_priv.h 2005-07-04 01:24:20 +01:00
+++ 1.324/sql/mysql_priv.h 2005-07-05 16:58:20 +01:00
@@ -1076,6 +1076,7 @@
extern const char *myisam_recover_options_str;
extern const char *in_left_expr_name, *in_additional_cond;
extern const char * const triggers_file_ext;
+extern const char * const trigname_file_ext;
extern Eq_creator eq_creator;
extern Ne_creator ne_creator;
extern Gt_creator gt_creator;
--- 1.478/sql/mysqld.cc 2005-07-04 01:44:31 +01:00
+++ 1.479/sql/mysqld.cc 2005-07-05 16:58:20 +01:00
@@ -5722,6 +5722,7 @@
{"Com_show_status", (char*) offsetof(STATUS_VAR, com_stat[(uint) SQLCOM_SHOW_STATUS]), SHOW_LONG_STATUS},
{"Com_show_storage_engines", (char*) offsetof(STATUS_VAR, com_stat[(uint) SQLCOM_SHOW_STORAGE_ENGINES]), SHOW_LONG_STATUS},
{"Com_show_tables", (char*) offsetof(STATUS_VAR, com_stat[(uint) SQLCOM_SHOW_TABLES]), SHOW_LONG_STATUS},
+ {"Com_show_triggers", (char*) offsetof(STATUS_VAR, com_stat[(uint) SQLCOM_SHOW_TRIGGERS]), SHOW_LONG_STATUS},
{"Com_show_variables", (char*) offsetof(STATUS_VAR, com_stat[(uint) SQLCOM_SHOW_VARIABLES]), SHOW_LONG_STATUS},
{"Com_show_warnings", (char*) offsetof(STATUS_VAR, com_stat[(uint) SQLCOM_SHOW_WARNS]), SHOW_LONG_STATUS},
{"Com_slave_start", (char*) offsetof(STATUS_VAR, com_stat[(uint) SQLCOM_SLAVE_START]), SHOW_LONG_STATUS},
--- 1.187/sql/sql_lex.h 2005-07-01 05:05:36 +01:00
+++ 1.188/sql/sql_lex.h 2005-07-05 16:58:21 +01:00
@@ -57,6 +57,7 @@
SQLCOM_SHOW_PROCESSLIST, SQLCOM_SHOW_MASTER_STAT, SQLCOM_SHOW_SLAVE_STAT,
SQLCOM_SHOW_GRANTS, SQLCOM_SHOW_CREATE, SQLCOM_SHOW_CHARSETS,
SQLCOM_SHOW_COLLATIONS, SQLCOM_SHOW_CREATE_DB, SQLCOM_SHOW_TABLE_STATUS,
+ SQLCOM_SHOW_TRIGGERS,
SQLCOM_LOAD,SQLCOM_SET_OPTION,SQLCOM_LOCK_TABLES,SQLCOM_UNLOCK_TABLES,
SQLCOM_GRANT,
--- 1.441/sql/sql_parse.cc 2005-07-04 01:44:31 +01:00
+++ 1.442/sql/sql_parse.cc 2005-07-05 16:58:21 +01:00
@@ -2104,6 +2104,7 @@
case SCH_TABLE_NAMES:
case SCH_TABLES:
case SCH_VIEWS:
+ case SCH_TRIGGERS:
#ifdef DONT_ALLOW_SHOW_COMMANDS
my_message(ER_NOT_ALLOWED_COMMAND,
ER(ER_NOT_ALLOWED_COMMAND), MYF(0)); /* purecov: inspected */
--- 1.255/sql/sql_show.cc 2005-07-01 05:05:36 +01:00
+++ 1.256/sql/sql_show.cc 2005-07-05 16:58:21 +01:00
@@ -21,6 +21,7 @@
#include "sql_select.h" // For select_describe
#include "repl_failsafe.h"
#include "sp_head.h"
+#include "sql_trigger.h"
#include <my_dir.h>
#ifdef HAVE_BERKELEY_DB
@@ -1687,6 +1688,7 @@
break;
case SQLCOM_SHOW_TABLES:
case SQLCOM_SHOW_TABLE_STATUS:
+ case SQLCOM_SHOW_TRIGGERS:
index_field_values->db_value= lex->current_select->db;
index_field_values->table_value= wild;
break;
@@ -2954,6 +2956,94 @@
}
+static const LEX_STRING trg_timing_type_name[]=
+{
+ { (char *) STRING_WITH_LEN("BEFORE") },
+ { (char *) STRING_WITH_LEN("AFTER") }
+};
+
+static const LEX_STRING trg_event_type_name[]=
+{
+ { (char *) STRING_WITH_LEN("INSERT") },
+ { (char *) STRING_WITH_LEN("UPDATE") },
+ { (char *) STRING_WITH_LEN("DELETE") }
+};
+
+bool store_triggers(THD *thd, TABLE *table, const char *db,
+ const char *tname, LEX_STRING *trigger_name,
+ enum trg_event_type event,
+ enum trg_action_time_type timing,
+ int order,
+ LEX_STRING *trigger_stmt,
+ TIME *created)
+{
+ TIME time;
+ CHARSET_INFO *cs= system_charset_info;
+ restore_record(table, s->default_values);
+ table->field[1]->store(db, strlen(db), cs);
+ table->field[2]->store(trigger_name->str, trigger_name->length, cs);
+ table->field[3]->store(trg_event_type_name[event].str,
+ trg_event_type_name[event].length, cs);
+ table->field[5]->store(db, strlen(db), cs);
+ table->field[6]->store(tname, strlen(tname), cs);
+ table->field[7]->store((longlong)order);
+ table->field[9]->store(trigger_stmt->str, trigger_stmt->length, cs);
+ table->field[10]->store("ROW", 3, cs);
+ table->field[11]->store(trg_timing_type_name[timing].str,
+ trg_timing_type_name[timing].length, cs);
+ table->field[14]->store("OLD", 3, cs);
+ table->field[15]->store("NEW", 3, cs);
+ table->field[16]->store_time(created, MYSQL_TIMESTAMP_DATETIME);
+ return schema_table_store_record(thd, table);
+}
+
+
+static int get_schema_triggers_record(THD *thd, struct st_table_list *tables,
+ TABLE *table, bool res,
+ const char *base_name,
+ const char *file_name)
+{
+ DBUG_ENTER("get_schema_constraints_record");
+ if (res)
+ {
+ if (!tables->view)
+ push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
+ thd->net.last_errno, thd->net.last_error);
+ thd->clear_error();
+ DBUG_RETURN(0);
+ }
+ if (!tables->view && tables->table->triggers)
+ {
+ Table_triggers_list *triggers= tables->table->triggers;
+ int event, timing, order;
+ for (event= TRG_EVENT_INSERT; event < TRG_EVENT_MAX; event++)
+ {
+ for (timing= TRG_ACTION_BEFORE; timing < TRG_ACTION_MAX; timing++)
+ {
+ /* change this following line when we support more than 1 trigger */
+ for (order= 0; order < 1; order++)
+ {
+ LEX_STRING trigger_name;
+ LEX_STRING trigger_stmt;
+ TIME created;
+ if (triggers->get_trigger_info(thd, (enum trg_event_type) event,
+ (enum trg_action_time_type)timing,
+ order, &trigger_name, &trigger_stmt,
+ &created))
+ break;
+ if (store_triggers(thd, table, base_name, file_name, &trigger_name,
+ (enum trg_event_type) event,
+ (enum trg_action_time_type) timing, order,
+ &trigger_stmt, &created))
+ DBUG_RETURN(1);
+ }
+ }
+ }
+ }
+ DBUG_RETURN(res);
+}
+
+
void store_key_column_usage(TABLE *table, const char*db, const char *tname,
const char *key_name, uint key_len,
const char *con_type, uint con_len, longlong idx)
@@ -3838,6 +3928,29 @@
};
+ST_FIELD_INFO triggers_fields_info[]=
+{
+ {"TRIGGER_CATALOG", FN_REFLEN, MYSQL_TYPE_STRING, 0, 1, 0},
+ {"TRIGGER_SCHEMA",NAME_LEN, MYSQL_TYPE_STRING, 0, 0, 0},
+ {"TRIGGER_NAME", NAME_LEN, MYSQL_TYPE_STRING, 0, 0, "Trigger"},
+ {"EVENT_MANIPULATION", 6, MYSQL_TYPE_STRING, 0, 0, "Event"},
+ {"EVENT_OBJECT_CATALOG", FN_REFLEN, MYSQL_TYPE_STRING, 0, 1, 0},
+ {"EVENT_OBJECT_SCHEMA",NAME_LEN, MYSQL_TYPE_STRING, 0, 0, 0},
+ {"EVENT_OBJECT_TABLE", NAME_LEN, MYSQL_TYPE_STRING, 0, 0, "Table"},
+ {"ACTION_ORDER", 4, MYSQL_TYPE_LONG, 0, 0, 0},
+ {"ACTION_CONDITION", 65536, MYSQL_TYPE_STRING, 0, 1, 0},
+ {"ACTION_STATEMENT", 65536, MYSQL_TYPE_STRING, 0, 0, "Statement"},
+ {"ACTION_ORIENTATION", 9, MYSQL_TYPE_STRING, 0, 0, 0},
+ {"ACTION_TIMING", 6, MYSQL_TYPE_STRING, 0, 0, "Timing"},
+ {"ACTION_REFERENCE_OLD_TABLE", NAME_LEN, MYSQL_TYPE_STRING, 0, 1, 0},
+ {"ACTION_REFERENCE_NEW_TABLE", NAME_LEN, MYSQL_TYPE_STRING, 0, 1, 0},
+ {"ACTION_REFERENCE_OLD_ROW", 3, MYSQL_TYPE_STRING, 0, 1, 0},
+ {"ACTION_REFERENCE_NEW_ROW", 3, MYSQL_TYPE_STRING, 0, 1, 0},
+ {"CREATED", 0, MYSQL_TYPE_TIMESTAMP, 0, 0, "Created"},
+ {0, 0, MYSQL_TYPE_STRING, 0, 0, 0}
+};
+
+
ST_FIELD_INFO variables_fields_info[]=
{
{"Variable_name", 80, MYSQL_TYPE_STRING, 0, 0, "Variable_name"},
@@ -3888,6 +4001,8 @@
fill_open_tables, make_old_format, 0, -1, -1, 1},
{"STATUS", variables_fields_info, create_schema_table, fill_status,
make_old_format, 0, -1, -1, 1},
+ {"TRIGGERS", triggers_fields_info, create_schema_table,
+ get_all_tables, make_old_format, get_schema_triggers_record, 5, 6, 0},
{"VARIABLES", variables_fields_info, create_schema_table, fill_variables,
make_old_format, 0, -1, -1, 1},
{0, 0, 0, 0, 0, 0, 0, 0, 0}
--- 1.257/sql/sql_table.cc 2005-07-03 12:17:46 +01:00
+++ 1.258/sql/sql_table.cc 2005-07-05 16:58:22 +01:00
@@ -23,6 +23,7 @@
#include <hash.h>
#include <myisam.h>
#include <my_dir.h>
+#include "sql_trigger.h"
#ifdef __WIN__
#include <io.h>
@@ -272,6 +273,15 @@
{
char *end;
db_type table_type= get_table_type(thd, path);
+
+ if (mysql_drop_all_triggers(thd, db, table->table_name))
+ {
+ push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
+ ER_WARN_TRG_DROP_FAILURE,
+ ER(ER_WARN_TRG_DROP_FAILURE),
+ db, table->table_name);
+ }
+
*(end=fn_ext(path))=0; // Remove extension for delete
error= ha_delete_table(thd, table_type, path, table->table_name,
!dont_log_query);
@@ -288,19 +298,7 @@
/* Delete the table definition file */
strmov(end,reg_ext);
if (!(new_error=my_delete(path,MYF(MY_WME))))
- {
some_tables_deleted=1;
- /*
- Destroy triggers for this table if there are any.
-
- We won't need this as soon as we will have new .FRM format,
- in which we will store trigger definitions in the same .FRM
- files as table descriptions.
- */
- strmov(end, triggers_file_ext);
- if (!access(path, F_OK))
- new_error= my_delete(path, MYF(MY_WME));
- }
error|= new_error;
}
}
--- 1.405/sql/sql_yacc.yy 2005-07-03 12:17:46 +01:00
+++ 1.406/sql/sql_yacc.yy 2005-07-05 16:58:23 +01:00
@@ -38,6 +38,7 @@
#include "sp_pcontext.h"
#include "sp_rcontext.h"
#include "sp.h"
+#include "sql_trigger.h"
#include <myisam.h>
#include <myisammrg.h>
@@ -598,6 +599,7 @@
%token TRAILING
%token TRANSACTION_SYM
%token TRIGGER_SYM
+%token TRIGGERS_SYM
%token TRIM
%token TRUE_SYM
%token TRUNCATE_SYM
@@ -1265,7 +1267,7 @@
}
opt_view_list AS select_init check_option
{}
- | CREATE TRIGGER_SYM ident trg_action_time trg_event
+ | CREATE TRIGGER_SYM sp_name trg_action_time trg_event
ON table_ident FOR_SYM EACH_SYM ROW_SYM
{
LEX *lex= Lex;
@@ -1294,7 +1296,7 @@
bzero((char *)&lex->sp_chistics, sizeof(st_sp_chistics));
lex->sphead->m_chistics= &lex->sp_chistics;
- lex->sphead->m_body_begin= lex->tok_start;
+ lex->sphead->m_body_begin= lex->ptr;
}
sp_proc_stmt
{
@@ -1302,13 +1304,14 @@
sp_head *sp= lex->sphead;
lex->sql_command= SQLCOM_CREATE_TRIGGER;
- sp->init_strings(YYTHD, lex, NULL);
+ sp->init_strings(YYTHD, lex, $3);
/* Restore flag if it was cleared above */
if (sp->m_old_cmq)
YYTHD->client_capabilities |= CLIENT_MULTI_QUERIES;
sp->restore_thd_mem_root(YYTHD);
- lex->ident= $3;
+ lex->name= $3->m_db.str;
+ lex->ident= $3->m_name;
/*
We have to do it after parsing trigger body, because some of
@@ -5902,19 +5905,24 @@
lex->sql_command= SQLCOM_DROP_VIEW;
lex->drop_if_exists= $3;
}
- | DROP TRIGGER_SYM ident '.' ident
+ | DROP TRIGGER_SYM sp_name
{
LEX *lex= Lex;
+ Table_ident *table;
+
+ if (!(table= mysql_table_for_trigger(YYTHD, $3, 0)))
+ YYABORT;
lex->sql_command= SQLCOM_DROP_TRIGGER;
/* QQ: Could we loosen lock type in certain cases ? */
if (!lex->select_lex.add_table_to_list(YYTHD,
- new Table_ident($3),
+ table,
(LEX_STRING*) 0,
TL_OPTION_UPDATING,
TL_WRITE))
YYABORT;
- lex->ident= $5;
+ lex->ident= $3->m_name;
+ lex->name= $3->m_db.str;
}
;
@@ -6279,6 +6287,15 @@
if (prepare_schema_table(YYTHD, lex, 0, SCH_TABLE_NAMES))
YYABORT;
}
+ | opt_full TRIGGERS_SYM opt_db wild_and_where
+ {
+ LEX *lex= Lex;
+ lex->sql_command= SQLCOM_SELECT;
+ lex->orig_sql_command= SQLCOM_SHOW_TRIGGERS;
+ lex->select_lex.db= $3;
+ if (prepare_schema_table(YYTHD, lex, 0, SCH_TRIGGERS))
+ YYABORT;
+ }
| TABLE_SYM STATUS_SYM opt_db wild_and_where
{
LEX *lex= Lex;
@@ -7559,6 +7576,7 @@
| TEMPTABLE_SYM {}
| TEXT_SYM {}
| TRANSACTION_SYM {}
+ | TRIGGERS_SYM {}
| TRUNCATE_SYM {}
| TIMESTAMP {}
| TIMESTAMP_ADD {}
--- 1.101/sql/table.h 2005-07-01 05:05:37 +01:00
+++ 1.102/sql/table.h 2005-07-05 16:58:23 +01:00
@@ -275,7 +275,7 @@
SCH_COLLATION_CHARACTER_SET_APPLICABILITY, SCH_PROCEDURES, SCH_STATISTICS,
SCH_VIEWS, SCH_USER_PRIVILEGES, SCH_SCHEMA_PRIVILEGES, SCH_TABLE_PRIVILEGES,
SCH_COLUMN_PRIVILEGES, SCH_TABLE_CONSTRAINTS, SCH_KEY_COLUMN_USAGE,
- SCH_TABLE_NAMES, SCH_OPEN_TABLES, SCH_STATUS, SCH_VARIABLES
+ SCH_TABLE_NAMES, SCH_OPEN_TABLES, SCH_STATUS, SCH_TRIGGERS, SCH_VARIABLES
};
--- 1.36/sql/share/errmsg.txt 2005-07-01 05:05:35 +01:00
+++ 1.37/sql/share/errmsg.txt 2005-07-05 16:58:20 +01:00
@@ -5360,3 +5360,9 @@
eng "Explicit or implicit commit is not allowed in stored function or trigger."
ER_NO_DEFAULT_FOR_VIEW_FIELD
eng "Field of view '%-.64s.%-.64s' underlying table doesn't have a default value"
+ER_TRG_IN_WRONG_SCHEMA
+ eng "Trigger in wrong schema"
+ER_WARN_TRG_DROP_FAILURE
+ eng "An error occuring while dropping triggers for '%-.64s.%-.64s'"
+ER_WARN_TRG_DUPLICATE
+ eng "Table '%-.64s' has duplicate trigger name: '%-.64s'"
--- 1.91/mysql-test/r/view.result 2005-07-05 09:21:43 +01:00
+++ 1.92/mysql-test/r/view.result 2005-07-05 16:58:19 +01:00
@@ -1245,7 +1245,7 @@
s1
select * from t1;
s1
-drop trigger t1.t1_bi;
+drop trigger t1_bi;
drop view v1;
drop table t1;
create table t1 (s1 tinyint);
--- 1.77/mysql-test/t/view.test 2005-07-05 09:21:43 +01:00
+++ 1.78/mysql-test/t/view.test 2005-07-05 16:58:19 +01:00
@@ -1183,7 +1183,7 @@
insert into v1 values (0);
select * from v1;
select * from t1;
-drop trigger t1.t1_bi;
+drop trigger t1_bi;
drop view v1;
drop table t1;
--- 1.8/mysql-test/r/trigger.result 2005-06-29 07:35:45 +01:00
+++ 1.9/mysql-test/r/trigger.result 2005-07-05 16:58:18 +01:00
@@ -11,13 +11,13 @@
select @a;
@a
1
-drop trigger t1.trg;
+drop trigger trg;
create trigger trg before insert on t1 for each row set @a:=new.i;
insert into t1 values (123);
select @a;
@a
123
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
create table t1 (i int not null, j int);
create trigger trg before insert on t1 for each row
@@ -32,7 +32,7 @@
i j
1 10
2 3
-drop trigger t1.trg|
+drop trigger trg|
drop table t1|
create table t1 (i int not null primary key);
create trigger trg after insert on t1 for each row
@@ -42,7 +42,7 @@
select @a;
@a
2:3:4:5
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
create table t1 (aid int not null primary key, balance int not null default 0);
insert into t1 values (1, 1000), (2,3000);
@@ -64,7 +64,7 @@
aid balance
1 1500
2 3000
-drop trigger t1.trg|
+drop trigger trg|
drop table t1|
create table t1 (i int);
insert into t1 values (1),(2),(3),(4);
@@ -75,7 +75,7 @@
select @total_change;
@total_change
2
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
create table t1 (i int);
insert into t1 values (1),(2),(3),(4);
@@ -86,7 +86,7 @@
select @del_sum;
@del_sum
6
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
create table t1 (i int);
insert into t1 values (1),(2),(3),(4);
@@ -96,7 +96,7 @@
select @del;
@del
1
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
create table t1 (i int, j int);
create trigger trg1 before insert on t1 for each row
@@ -136,9 +136,9 @@
1 20
2 -1
3 20
-drop trigger t1.trg1;
-drop trigger t1.trg2;
-drop trigger t1.trg3;
+drop trigger trg1;
+drop trigger trg2;
+drop trigger trg3;
drop table t1;
create table t1 (id int not null primary key, data int);
create trigger t1_bi before insert on t1 for each row
@@ -183,6 +183,7 @@
(BEFORE_INSERT: new=(id=1, data=5))(BEFORE_UPDATE: old=(id=1, data=4) new=(id=1, data=6))(AFTER_UPDATE: old=(id=1, data=4) new=(id=1, data=6))(BEFORE_INSERT: new=(id=3, data=3))(AFTER_INSERT: new=(id=3, data=3))
drop table t1;
create table t1 (i int);
+create table t3 (i int);
create trigger trg before insert on t1 for each row set @a:= old.i;
ERROR HY000: There is no OLD row in on INSERT trigger
create trigger trg before delete on t1 for each row set @a:= new.i;
@@ -204,14 +205,19 @@
ERROR HY000: Trigger already exists
create trigger trg2 before insert on t1 for each row set @a:=1;
ERROR HY000: Trigger already exists
-drop trigger t1.trg;
-drop trigger t1.trg;
+create trigger trg before insert on t3 for each row set @a:=1;
+ERROR HY000: Trigger already exists
+create trigger trg2 before insert on t3 for each row set @a:=1;
+drop trigger trg2;
+drop trigger trg;
+drop trigger trg;
ERROR HY000: Trigger does not exist
create view v1 as select * from t1;
create trigger trg before insert on v1 for each row set @a:=1;
ERROR HY000: Trigger's 'v1' is view or temporary table
drop view v1;
drop table t1;
+drop table t3;
create temporary table t1 (i int);
create trigger trg before insert on t1 for each row set @a:=1;
ERROR HY000: Trigger's 't1' is view or temporary table
@@ -219,7 +225,7 @@
create table t1 (x1col char);
create trigger tx1 before insert on t1 for each row set new.x1col = 'x';
insert into t1 values ('y');
-drop trigger t1.tx1;
+drop trigger tx1;
drop table t1;
create table t1 (i int) engine=myisam;
insert into t1 values (1), (2);
@@ -230,8 +236,8 @@
select @del_before, @del_after;
@del_before @del_after
3 3
-drop trigger t1.trg1;
-drop trigger t1.trg2;
+drop trigger trg1;
+drop trigger trg2;
drop table t1;
create table t1 (a int);
create trigger trg1 before insert on t1 for each row set new.a= 10;
@@ -248,6 +254,15 @@
create trigger trg1 before insert on t1 for each row set @a:= 1;
drop database mysqltest;
use test;
+create database mysqltest;
+create table mysqltest.t1 (i int);
+create trigger trg1 before insert on mysqltest.t1 for each row set @a:= 1;
+ERROR HY000: Trigger in wrong schema
+use mysqltest;
+create trigger test.trg1 before insert on t1 for each row set @a:= 1;
+ERROR HY000: Trigger in wrong schema
+drop database mysqltest;
+use test;
create table t1 (i int, j int default 10, k int not null, key (k));
create table t2 (i int);
insert into t1 (i, k) values (1, 1);
@@ -461,7 +476,7 @@
1 1
2 2
alter table t1 add primary key (i);
-drop trigger t1.bi;
+drop trigger bi;
insert into t1 values (2, 4) on duplicate key update k= k + 10;
ERROR 42S22: Unknown column 'bt' in 'NEW'
select * from t1;
--- 1.12/mysql-test/t/trigger.test 2005-06-29 07:35:45 +01:00
+++ 1.13/mysql-test/t/trigger.test 2005-07-05 16:58:19 +01:00
@@ -16,13 +16,13 @@
select @a;
insert into t1 values (1);
select @a;
-drop trigger t1.trg;
+drop trigger trg;
# let us test simple trigger reading some values
create trigger trg before insert on t1 for each row set @a:=new.i;
insert into t1 values (123);
select @a;
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
@@ -39,7 +39,7 @@
insert into t1 (i) values (1)|
insert into t1 (i,j) values (2, 3)|
select * from t1|
-drop trigger t1.trg|
+drop trigger trg|
drop table t1|
delimiter ;|
@@ -51,7 +51,7 @@
set @a:="";
insert into t1 values (2),(3),(4),(5);
select @a;
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
# PS doesn't work with multi-row statements
@@ -74,7 +74,7 @@
update t1 set balance=1500|
select @update_failed;
select * from t1|
-drop trigger t1.trg|
+drop trigger trg|
drop table t1|
delimiter ;|
--enable_ps_protocol
@@ -87,7 +87,7 @@
set @total_change:=0;
update t1 set i=3;
select @total_change;
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
# Before delete trigger
@@ -99,7 +99,7 @@
set @del_sum:= 0;
delete from t1 where i <= 3;
select @del_sum;
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
# After delete trigger.
@@ -110,7 +110,7 @@
set @del:= 0;
delete from t1 where i <> 0;
select @del;
-drop trigger t1.trg;
+drop trigger trg;
drop table t1;
# Several triggers on one table
@@ -144,9 +144,9 @@
select @fired;
select * from t1;
-drop trigger t1.trg1;
-drop trigger t1.trg2;
-drop trigger t1.trg3;
+drop trigger trg1;
+drop trigger trg2;
+drop trigger trg3;
drop table t1;
@@ -203,6 +203,7 @@
# Test of wrong column specifiers in triggers
#
create table t1 (i int);
+create table t3 (i int);
--error 1363
create trigger trg before insert on t1 for each row set @a:= old.i;
@@ -222,7 +223,7 @@
#
# Let us test various trigger creation errors
-#
+# Also quickly test table namespace (bug#5892/6182)
#
--error 1146
create trigger trg before insert on t2 for each row set @a:=1;
@@ -232,10 +233,14 @@
create trigger trg after insert on t1 for each row set @a:=1;
--error 1359
create trigger trg2 before insert on t1 for each row set @a:=1;
-drop trigger t1.trg;
+--error 1359
+create trigger trg before insert on t3 for each row set @a:=1;
+create trigger trg2 before insert on t3 for each row set @a:=1;
+drop trigger trg2;
+drop trigger trg;
--error 1360
-drop trigger t1.trg;
+drop trigger trg;
create view v1 as select * from t1;
--error 1361
@@ -243,6 +248,7 @@
drop view v1;
drop table t1;
+drop table t3;
create temporary table t1 (i int);
--error 1361
@@ -260,7 +266,7 @@
create table t1 (x1col char);
create trigger tx1 before insert on t1 for each row set new.x1col = 'x';
insert into t1 values ('y');
-drop trigger t1.tx1;
+drop trigger tx1;
drop table t1;
#
@@ -276,8 +282,8 @@
set @del_before:=0, @del_after:= 0;
delete from t1;
select @del_before, @del_after;
-drop trigger t1.trg1;
-drop trigger t1.trg2;
+drop trigger trg1;
+drop trigger trg2;
drop table t1;
# Test for bug #5859 "DROP TABLE does not drop triggers". Trigger should not
@@ -299,6 +305,19 @@
drop database mysqltest;
use test;
+# Test for bug #8791
+# "Triggers: Allowed to create triggers on a subject table in a different DB".
+create database mysqltest;
+create table mysqltest.t1 (i int);
+--error 1424
+create trigger trg1 before insert on mysqltest.t1 for each row set @a:= 1;
+use mysqltest;
+--error 1424
+create trigger test.trg1 before insert on t1 for each row set @a:= 1;
+drop database mysqltest;
+use test;
+
+
# Test for bug #5860 "Multi-table UPDATE does not activate update triggers"
# We will also test how delete triggers wor for multi-table DELETE.
create table t1 (i int, j int default 10, k int not null, key (k));
@@ -480,7 +499,7 @@
# To test properly code-paths different from those that are used
# in ordinary INSERT we need to drop "before insert" trigger.
alter table t1 add primary key (i);
-drop trigger t1.bi;
+drop trigger bi;
--error 1054
insert into t1 values (2, 4) on duplicate key update k= k + 10;
select * from t1;
--- 1.19/sql/sql_trigger.cc 2005-07-01 05:05:36 +01:00
+++ 1.20/sql/sql_trigger.cc 2005-07-05 16:58:22 +01:00
@@ -1,4 +1,5 @@
#include "mysql_priv.h"
+#include <my_dir.h>
#include "sp_head.h"
#include "sql_trigger.h"
#include "parse_file.h"
@@ -6,6 +7,7 @@
static const LEX_STRING triggers_file_type= {(char *)"TRIGGERS", 8};
const char * const triggers_file_ext= ".TRG";
+const char * const trigname_file_ext= ".TRI";
/*
Table of .TRG file field descriptors.
@@ -42,8 +44,10 @@
*/
bool mysql_create_or_drop_trigger(THD *thd, TABLE_LIST *tables, bool create)
{
+ char path[FN_REFLEN+1];
TABLE *table;
bool result= 0;
+ int fd= -1;
DBUG_ENTER("mysql_create_or_drop_trigger");
@@ -77,6 +81,16 @@
DBUG_RETURN(TRUE);
}
+ /*
+ Trigger must be in the same schema as target table
+ */
+ if (my_strcasecmp(system_charset_info, table->s->db,
+ thd->lex->name ? thd->lex->name : thd->db))
+ {
+ my_error(create ? ER_TRG_IN_WRONG_SCHEMA : ER_TRG_DOES_NOT_EXIST, MYF(0));
+ DBUG_RETURN(TRUE);
+ }
+
if (!table->triggers)
{
if (!create)
@@ -114,10 +128,42 @@
}
VOID(pthread_mutex_lock(&LOCK_open));
+
+ /*
+ Use the filesystem to enforce trigger namespace constraints
+ */
+ if (fn_format_relative_to_data_home(path, thd->lex->ident.str,
+ table->s->db, trigname_file_ext) ||
+ (create && (fd= my_create(path, 0666, O_WRONLY|O_EXCL,MYF(0))) < 0))
+ {
+ VOID(pthread_mutex_unlock(&LOCK_open));
+ my_message(ER_TRG_ALREADY_EXISTS, ER(ER_TRG_ALREADY_EXISTS), MYF(0));
+ DBUG_RETURN(TRUE);
+ }
+ if (create)
+ {
+ int len= strlen(table->s->table_name);
+ if (my_write(fd,(byte*)table->s->table_name, len, MYF(MYF_RW)))
+ {
+ my_close(fd,MYF(0));
+ my_delete(path, MYF(0));
+ VOID(pthread_mutex_unlock(&LOCK_open));
+ DBUG_RETURN(TRUE);
+ }
+ my_close(fd,MYF(0));
+ }
+
result= (create ?
table->triggers->create_trigger(thd, tables):
table->triggers->drop_trigger(thd, tables));
+ if (((create && result) || (!create && !result)) &&
+ my_delete(path, MYF(0)))
+ {
+ sql_print_warning("Could not delete trigger file: '%s', error: %d",
+ path, my_errno);
+ }
+
/* It is sensible to invalidate table in any case */
close_cached_table(thd, table);
VOID(pthread_mutex_unlock(&LOCK_open));
@@ -506,4 +552,246 @@
}
DBUG_RETURN(1);
+}
+
+
+/*
+ Drop all triggers for table.
+
+ SYNOPSIS
+ drop_all_triggers()
+ thd - current thread context (including trigger definition in LEX)
+ tables - table list containing one open table for which trigger is
+ dropped.
+
+ RETURN VALUE
+ False - success
+ True - error
+*/
+bool Table_triggers_list::drop_all_triggers(THD *thd, TABLE_LIST *tables)
+{
+ TABLE *table= tables->table;
+ LEX_STRING *name;
+ List_iterator_fast<LEX_STRING> it_name(names_list);
+ List_iterator<LEX_STRING> it_def(definitions_list);
+ char path[FN_REFLEN];
+ bool errors= 0;
+
+ if (names_list.elements)
+ {
+ while ((name= it_name++))
+ {
+ int fd;
+
+ it_def++;
+ if (fn_format_relative_to_data_home(path, name->str,
+ table->s->db, trigname_file_ext) ||
+ (fd= my_open(path, O_RDONLY, MYF(0))) < 0)
+ {
+ sql_print_warning("Missing trigger file: '%s', error: %d",
+ path, my_errno);
+ }
+ else
+ {
+ char buff[FN_REFLEN+1];
+ int len= (int) my_read(fd, (byte*)buff, sizeof(buff)-1, MYF(0));
+ buff[len]= '\0';
+ my_close(fd,MYF(0));
+ if (my_strcasecmp(system_charset_info, buff, table->s->table_name))
+ {
+ sql_print_warning("Table '%s' has duplicate trigger name: '%s'",
+ table->s->table_name, name->str);
+ errors= 1;
+ }
+ else
+ if (my_delete(path, MYF(0)))
+ {
+ sql_print_warning("Could not delete trigger file: '%s', error: %d",
+ path, my_errno);
+ errors= 1;
+ }
+ }
+
+ /*
+ Again we don't care much about other things required for
+ clean trigger removing since table will be reopened anyway.
+ */
+ it_def.remove();
+ }
+
+ /*
+ TODO: Probably instead of removing .TRG file we should move
+ to archive directory but this should be done as part of
+ parse_file.cc functionality (because we will need it
+ elsewhere).
+ */
+ strxnmov(path, FN_REFLEN-1, mysql_data_home, "/", tables->db, "/",
+ tables->table_name, triggers_file_ext, NullS);
+ path[FN_REFLEN-1]= '\0';
+ unpack_filename(path, path);
+ return my_delete(path, MYF(MY_WME)) || errors;
+ }
+ return 0;
+}
+
+
+bool Table_triggers_list::get_trigger_info(THD *thd, trg_event_type event,
+ trg_action_time_type time_type,
+ int trigger_order,
+ LEX_STRING *trigger_name,
+ LEX_STRING *trigger_stmt,
+ TIME *created)
+{
+ sp_head *body;
+ DBUG_ENTER("get_trigger_info");
+ if (trigger_order == 0 && (body= bodies[event][time_type]))
+ {
+ struct tm tmp_tm;
+ my_time_t time;
+ char path[FN_REFLEN+1];
+ MY_STAT stat_info;
+ int fd;
+
+ *trigger_name= body->m_name;
+ *trigger_stmt= body->m_body;
+ bzero(created, sizeof(TIME));
+
+ if (fn_format_relative_to_data_home(path, body->m_name.str,
+ body->m_db.str, trigname_file_ext) ||
+ (fd= my_open(path, O_RDONLY, MYF(0))) < 0)
+ {
+ sql_print_warning("Could not open trigger file: '%s', error: %d",
+ path, my_errno);
+ push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_NOTE,
+ ER_WARN_TRG_DUPLICATE,
+ "Missing name file for trigger '%s'",
+ body->m_name.str);
+ }
+ else
+ {
+ char name[FN_REFLEN+1];
+ int len= (int) my_read(fd, (byte*)name, sizeof(name)-1, MYF(0));
+ my_close(fd,MYF(0));
+ name[len]= '\0';
+ if (my_strcasecmp(system_charset_info, name, table->s->table_name))
+ {
+ sql_print_warning("Table '%s' has duplicate trigger name: '%s'",
+ table->s->table_name, body->m_name.str);
+ push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_NOTE,
+ ER_TRG_DOES_NOT_EXIST, ER(ER_WARN_TRG_DUPLICATE),
+ table->s->table_name, body->m_name.str);
+ }
+ else
+ {
+ my_stat(path, &stat_info, MYF(0));
+ gmtime_r(&stat_info.st_ctime, &tmp_tm);
+ localtime_to_TIME(created, &tmp_tm);
+ }
+ }
+ DBUG_RETURN(0);
+ }
+ DBUG_RETURN(1);
+}
+
+
+/*
+ Find table identifier from trigger identifier.
+
+ SYNOPSIS
+ mysql_table_for_trigger()
+ thd - current thread context
+ trig - identifier for trigger
+ no_error - set if this should not emit an error message
+
+ RETURN VALUE
+ 0 - error
+*/
+Table_ident *mysql_table_for_trigger(THD *thd, sp_name *trig, bool no_error)
+{
+ const char *db= !trig->m_db.str ? thd->db : trig->m_db.str;
+ char path[FN_REFLEN+1];
+ LEX_STRING name;
+ int fd;
+ DBUG_ENTER("mysql_table_for_trigger");
+
+ if (fn_format_relative_to_data_home(path, trig->m_name.str,
+ db, trigname_file_ext) ||
+ (fd= my_open(path, O_RDONLY, MYF(0))) < 0)
+ {
+ if (!no_error)
+ {
+ my_message(ER_TRG_DOES_NOT_EXIST, ER(ER_TRG_DOES_NOT_EXIST), MYF(0));
+ }
+ DBUG_RETURN(0);
+ }
+ name.length= (int) my_read(fd, (byte*)path, sizeof(path)-1, MYF(0));
+ path[name.length]= '\0';
+ name.str= thd->strdup(path);
+ my_close(fd,MYF(0));
+
+ return trig->m_db.str ?
+ new Table_ident(thd, trig->m_db, name, 0) :
+ new Table_ident(name);
+}
+
+
+/*
+ Drop all triggers for table.
+
+ SYNOPSIS
+ mysql_drop_all_triggers()
+ thd - current thread context
+ db - schema for table
+ name - name for table
+
+ NOTE
+ The calling thread should hold the LOCK_open mutex;
+
+ RETURN VALUE
+ False - success
+ True - error
+*/
+bool mysql_drop_all_triggers(THD *thd, char *db, char *name)
+{
+ TABLE_LIST table_list;
+ TABLE table;
+ char path[FN_REFLEN];
+ bool result= 0;
+ DBUG_ENTER("mysql_drop_all_triggers");
+
+ bzero(&table_list, sizeof(table_list));
+ bzero(&table, sizeof(table));
+ table_list.db= db;
+ table_list.table_name= table_list.alias= name;
+ table_list.table = &table;
+
+ strxnmov(path, sizeof(path)-1, mysql_data_home, "/", db, "/", name, NullS);
+ path[FN_REFLEN-1]= '\0';
+
+ safe_mutex_assert_owner(&LOCK_open);
+
+ if (openfrm(thd, path, name, HA_TRY_READ_ONLY | NO_ERR_ON_NEW_FRM,
+ COMPUTE_TYPES | EXTRA_RECORD, 0, &table))
+ {
+ DBUG_PRINT("info",("failed to load frm"));
+ goto end;
+ }
+ table.s->db= db;
+ if (Table_triggers_list::check_n_load(thd, db, name, &table))
+ {
+ DBUG_PRINT("info",("failed to load triggers"));
+ result= 1;
+ goto end;
+ }
+ if (table.s->tmp_table == NO_TMP_TABLE && table.triggers &&
+ table.triggers->drop_all_triggers(thd, &table_list))
+ {
+ DBUG_PRINT("info",("failed to drop triggers"));
+ result= 1;
+ goto end;
+ }
+ DBUG_PRINT("info",("dropped triggers for %s.%s",db,name));
+end:
+ intern_close_table(&table);
+ DBUG_RETURN(result);
}
--- 1.8/sql/sql_trigger.h 2005-06-07 11:53:03 +01:00
+++ 1.9/sql/sql_trigger.h 2005-07-05 16:58:22 +01:00
@@ -3,6 +3,7 @@
QQ: Will it be merged into TABLE in future ?
*/
+#ifdef _SP_HEAD_H_
class Table_triggers_list: public Sql_alloc
{
/* Triggers as SPs grouped by event, action_time */
@@ -45,6 +46,7 @@
bool create_trigger(THD *thd, TABLE_LIST *table);
bool drop_trigger(THD *thd, TABLE_LIST *table);
+ bool drop_all_triggers(THD *thd, TABLE_LIST *tables);
bool process_triggers(THD *thd, trg_event_type event,
trg_action_time_type time_type,
bool old_row_is_record1)
@@ -96,6 +98,10 @@
return res;
}
+ bool get_trigger_info(THD *thd, trg_event_type event,
+ trg_action_time_type time_type, int trigger_order,
+ LEX_STRING *trigger_name, LEX_STRING *trigger_stmt,
+ TIME *created);
static bool check_n_load(THD *thd, const char *db, const char *table_name,
TABLE *table);
@@ -116,3 +122,7 @@
private:
bool prepare_record1_accessors(TABLE *table);
};
+#endif /* _SP_HEAD_H_ */
+
+Table_ident *mysql_table_for_trigger(THD *thd, sp_name *trig, bool no_error);
+bool mysql_drop_all_triggers(THD *thd, char *db, char *name);
--- 1.4/mysql-test/r/rpl_sp.result 2005-06-19 16:39:02 +01:00
+++ 1.5/mysql-test/r/rpl_sp.result 2005-07-05 16:58:18 +01:00
@@ -237,7 +237,7 @@
a
10
delete from t1;
-drop trigger t1.trg;
+drop trigger trg;
insert into t1 values (1);
select * from t1;
a
@@ -248,7 +248,7 @@
master-bin.000002 # Query 1 # use `mysqltest1`; create trigger trg before insert on t1 for each row set new.a= 10
master-bin.000002 # Query 1 # use `mysqltest1`; insert into t1 values (1)
master-bin.000002 # Query 1 # use `mysqltest1`; delete from t1
-master-bin.000002 # Query 1 # use `mysqltest1`; drop trigger t1.trg
+master-bin.000002 # Query 1 # use `mysqltest1`; drop trigger trg
master-bin.000002 # Query 1 # use `mysqltest1`; insert into t1 values (1)
select * from t1;
a
--- 1.3/mysql-test/t/rpl_sp.test 2005-05-06 17:52:14 +01:00
+++ 1.4/mysql-test/t/rpl_sp.test 2005-07-05 16:58:19 +01:00
@@ -249,7 +249,7 @@
connection master;
delete from t1;
-drop trigger t1.trg;
+drop trigger trg;
insert into t1 values (1);
select * from t1;
--replace_column 2 # 5 #
--- 1.58/mysql-test/r/information_schema.result 2005-07-04 01:42:05 +01:00
+++ 1.59/mysql-test/r/information_schema.result 2005-07-05 16:58:18 +01:00
@@ -48,6 +48,7 @@
COLUMN_PRIVILEGES
TABLE_CONSTRAINTS
KEY_COLUMN_USAGE
+TRIGGERS
columns_priv
db
func
@@ -77,6 +78,7 @@
TABLES TABLES
TABLE_PRIVILEGES TABLE_PRIVILEGES
TABLE_CONSTRAINTS TABLE_CONSTRAINTS
+TRIGGERS TRIGGERS
tables_priv tables_priv
time_zone time_zone
time_zone_leap_second time_zone_leap_second
@@ -94,6 +96,7 @@
TABLES TABLES
TABLE_PRIVILEGES TABLE_PRIVILEGES
TABLE_CONSTRAINTS TABLE_CONSTRAINTS
+TRIGGERS TRIGGERS
tables_priv tables_priv
time_zone time_zone
time_zone_leap_second time_zone_leap_second
@@ -111,6 +114,7 @@
TABLES TABLES
TABLE_PRIVILEGES TABLE_PRIVILEGES
TABLE_CONSTRAINTS TABLE_CONSTRAINTS
+TRIGGERS TRIGGERS
tables_priv tables_priv
time_zone time_zone
time_zone_leap_second time_zone_leap_second
@@ -577,6 +581,7 @@
TABLES
TABLE_PRIVILEGES
TABLE_CONSTRAINTS
+TRIGGERS
create database information_schema;
ERROR HY000: Can't create database 'information_schema'; database exists
use information_schema;
@@ -585,6 +590,7 @@
TABLES TEMPORARY
TABLE_PRIVILEGES TEMPORARY
TABLE_CONSTRAINTS TEMPORARY
+TRIGGERS TEMPORARY
create table t1(a int);
ERROR 42S02: Unknown table 't1' in information_schema
use test;
@@ -596,6 +602,7 @@
TABLES
TABLE_PRIVILEGES
TABLE_CONSTRAINTS
+TRIGGERS
select table_name from tables where table_name='user';
table_name
user
@@ -690,7 +697,7 @@
CREATE VIEW a1 (t_CRASHME) AS SELECT f1 FROM t_crashme GROUP BY f1;
CREATE VIEW a2 AS SELECT t_CRASHME FROM a1;
count(*)
-100
+101
drop view a2, a1;
drop table t_crashme;
select table_schema,table_name, column_name from
@@ -701,6 +708,8 @@
information_schema ROUTINES ROUTINE_DEFINITION
information_schema ROUTINES SQL_MODE
information_schema VIEWS VIEW_DEFINITION
+information_schema TRIGGERS ACTION_CONDITION
+information_schema TRIGGERS ACTION_STATEMENT
select table_name, column_name, data_type from information_schema.columns
where data_type = 'datetime';
table_name column_name data_type
@@ -709,6 +718,7 @@
TABLES CHECK_TIME datetime
ROUTINES CREATED datetime
ROUTINES LAST_ALTERED datetime
+TRIGGERS CREATED datetime
SELECT COUNT(*) FROM INFORMATION_SCHEMA.TABLES A
WHERE NOT EXISTS
(SELECT * FROM INFORMATION_SCHEMA.COLUMNS B
@@ -754,8 +764,57 @@
flush privileges;
SELECT table_schema, count(*) FROM information_schema.TABLES GROUP BY TABLE_SCHEMA;
table_schema count(*)
-information_schema 15
+information_schema 16
mysql 17
+create table t1 (i int, j int);
+create trigger trg1 before insert on t1 for each row
+begin
+if new.j > 10 then
+set new.j := 10;
+end if;
+end|
+create trigger trg2 before update on t1 for each row
+begin
+if old.i % 2 = 0 then
+set new.j := -1;
+end if;
+end|
+create trigger trg3 after update on t1 for each row
+begin
+if new.j = -1 then
+set @fired:= "Yes";
+end if;
+end|
+select TRIGGER_CATALOG, TRIGGER_SCHEMA, TRIGGER_NAME, EVENT_MANIPULATION,
+EVENT_OBJECT_CATALOG, EVENT_OBJECT_SCHEMA, EVENT_OBJECT_TABLE,
+ACTION_ORDER, ACTION_CONDITION, ACTION_STATEMENT,
+ACTION_ORIENTATION, ACTION_TIMING,
+ACTION_REFERENCE_OLD_TABLE, ACTION_REFERENCE_NEW_TABLE,
+ACTION_REFERENCE_OLD_ROW, ACTION_REFERENCE_NEW_ROW
+from information_schema.triggers;
+TRIGGER_CATALOG TRIGGER_SCHEMA TRIGGER_NAME EVENT_MANIPULATION EVENT_OBJECT_CATALOG EVENT_OBJECT_SCHEMA EVENT_OBJECT_TABLE ACTION_ORDER ACTION_CONDITION ACTION_STATEMENT ACTION_ORIENTATION ACTION_TIMING ACTION_REFERENCE_OLD_TABLE ACTION_REFERENCE_NEW_TABLE ACTION_REFERENCE_OLD_ROW ACTION_REFERENCE_NEW_ROW
+NULL test trg1 INSERT NULL test t1 0 NULL
+begin
+if new.j > 10 then
+set new.j := 10;
+end if;
+end ROW BEFORE NULL NULL NULL NULL
+NULL test trg2 UPDATE NULL test t1 0 NULL
+begin
+if old.i % 2 = 0 then
+set new.j := -1;
+end if;
+end ROW BEFORE NULL NULL NULL NULL
+NULL test trg3 UPDATE NULL test t1 0 NULL
+begin
+if new.j = -1 then
+set @fired:= "Yes";
+end if;
+end ROW AFTER NULL NULL NULL NULL
+drop trigger trg1;
+drop trigger trg2;
+drop trigger trg3;
+drop table t1;
create database mysqltest;
create table mysqltest.t1 (f1 int, f2 int);
create table mysqltest.t2 (f1 int);
--- 1.41/mysql-test/t/information_schema.test 2005-07-04 01:42:06 +01:00
+++ 1.42/mysql-test/t/information_schema.test 2005-07-05 16:58:19 +01:00
@@ -504,6 +504,47 @@
#
SELECT table_schema, count(*) FROM information_schema.TABLES GROUP BY TABLE_SCHEMA;
+
+#
+# TRIGGERS table test
+#
+create table t1 (i int, j int);
+
+delimiter |;
+create trigger trg1 before insert on t1 for each row
+begin
+ if new.j > 10 then
+ set new.j := 10;
+ end if;
+end|
+create trigger trg2 before update on t1 for each row
+begin
+ if old.i % 2 = 0 then
+ set new.j := -1;
+ end if;
+end|
+create trigger trg3 after update on t1 for each row
+begin
+ if new.j = -1 then
+ set @fired:= "Yes";
+ end if;
+end|
+delimiter ;|
+# select all the columns except CREATED as that time changes!
+select TRIGGER_CATALOG, TRIGGER_SCHEMA, TRIGGER_NAME, EVENT_MANIPULATION,
+ EVENT_OBJECT_CATALOG, EVENT_OBJECT_SCHEMA, EVENT_OBJECT_TABLE,
+ ACTION_ORDER, ACTION_CONDITION, ACTION_STATEMENT,
+ ACTION_ORIENTATION, ACTION_TIMING,
+ ACTION_REFERENCE_OLD_TABLE, ACTION_REFERENCE_NEW_TABLE,
+ ACTION_REFERENCE_OLD_ROW, ACTION_REFERENCE_NEW_ROW
+ from information_schema.triggers;
+
+drop trigger trg1;
+drop trigger trg2;
+drop trigger trg3;
+drop table t1;
+
+
#
# Bug #10964 Information Schema:Authorization check on privilege tables is improper
#
--- 1.2/mysql-test/r/information_schema_db.result 2005-05-24 11:35:16 +01:00
+++ 1.3/mysql-test/r/information_schema_db.result 2005-07-05 16:58:18 +01:00
@@ -16,11 +16,13 @@
COLUMN_PRIVILEGES
TABLE_CONSTRAINTS
KEY_COLUMN_USAGE
+TRIGGERS
show tables from INFORMATION_SCHEMA like 'T%';
Tables_in_information_schema (T%)
TABLES
TABLE_PRIVILEGES
TABLE_CONSTRAINTS
+TRIGGERS
create database `inf%`;
use `inf%`;
show tables;
| Thread |
|---|
| • bk commit into 5.0 tree (acurtis:1.1887) | antony | 5 Jul |