3.8. Triggers

Triggers overview

Triggers provide advanced users with the ability to write their own PHP scripts for such things as validating user input, and to have their code executed at the appropriate time. Triggers are files that are included via an  include() statement and conditionally executed by phpMyEdit.class.php. SQL triggers are included before or after insert, update, or delete of record. FORM triggers are included before displaying the form that will allow the corresponding operation, or after the user canceled this form.

For SQL triggers, the operation sequence is this: before, main, after. If any operation fails, not only should the next operation(s) not be executed, but the previous ones are 'rolled back' as if they never happened. If a database is not able to do this, it is not 'transaction-safe'.

Triggers are risky in basic MySQL as there is no native transaction support. It is not transaction-safe by default. There are transaction-safe table types in MySQL that can be conditionally built (see MySQL-Max), but phpMyEdit is currently not set up to support real transactions. What that means is that if an operation fails, the database may be left in an intermediate and invalid state.

The programmer must understand and accept these risks prior to using the phpMyEdit triggers mechanism. If the triggers are used, they execute within the namespace or scope of the phpMyEdit class.

Triggers must return true or false to indicate success or failure.

Triggers types

There are following types of phpMyEdit triggers:

If 'pre' triggers fail, users are sent back to the list, except for the 'update' case, where users are sent back to view page if the pre-update trigger fails.

Trigger examples

Example 3-21. Select triggers

 // Before displaying the view page 
$opts['triggers']'select']['pre']    = 'categories.TSP.inc'; // After canceling the view page 
$opts['triggers']'select']['cancel'] = 'categories.TSC.inc';

Example 3-22. Insert triggers

 // Before displaying the add/copy page 
$opts['triggers']'insert']['pre']    = 'categories.TIP.inc'; // After requesting save or more in the add/copy page 
$opts['triggers']'insert']['before'] = 'categories.TIB.inc'; 
$opts['triggers']'insert']['after']  = 'categories.TIA.inc'; // After canceling the add/copy page 
$opts['triggers']'insert']['cancel'] = 'categories.TIC.inc';

Example 3-23. Update triggers

 // Before displaying the edit page 
$opts['triggers']['update']['pre']    = 'categories.TUP.inc'; // After requesting save or apply in the edit page 
$opts['triggers']['update']['before'] = 'categories.TUB.inc'; 
$opts['triggers']['update']['after']  = 'categories.TUA.inc'; // After canceling the edit page 
$opts['triggers']['update']['cancel'] = 'categories.TUC.inc';

Example 3-24. Delete triggers

 // Before displaying the delete page 
$opts['triggers']'delete']['pre']    = 'categories.TDP.inc'; // After requesting delete in the delete page 
$opts['triggers']'delete']['before'] = 'categories.TDB.inc'; 
$opts['triggers']'delete']['after']  = 'categories.TDA.inc'; // After canceling the delete page 
$opts['triggers']'delete']['cancel'] = 'categories.TDC.inc';

Please note that ['select']['after'] and ['select']['before'] triggers currently do not exist.

In the following sample are steps during a View, Edit, Apply and Cancel operation described. All involved triggers return true.

Triggers variables

In every trigger file you have available following usable variables. Some of them affect only a particular action.

$this   object reference
$this->dbh   initialized MySQL database handle
$this->key   primary key name
$this->key_type   primary key type
$this->key_delim   primary key deliminator
$this->rec   primary key value (update and delete only)
$newvals   associative array of new values (update and insert only)
$oldvals   associative array of old values (update and delete only)
$changed   array of keys with changed values

There are also other variables available. For example every class property can be accessed using $this object reference. All variables occur in 'before' triggers as well as in 'after' triggers. Only class properties occurs in 'pre' and 'cancel' triggers currently.

It is recommended to use the $this->myQuery() method in order to perform database queries for fetching additional data or doing inserts or updates to other database tables.

Chained triggers

You may set several triggers for the same operation. This allows to isolate code, to share more easily triggers between multiple calling scripts and to reuse code produced by another phpMyEdit users.

The order triggers are executed in is important. It is set by the keys of the chained triggers. As soon as one of the chained trigger fail, the overall return value is set to false, and following triggers are not executed. If none of chained triggers failed, then the return value is true.

Example 3-25. Chained update before triggers

$opts['triggers']'update']['before'][1] = 'lock.TUA.inc'; 
$opts['triggers']'update']['before'][0] = 'check.TUB.inc';

In this example, when the user clicks on the Save button during editing a record, check.TUB.inc will be run first. If it returns true, then lock.TUB.inc will be run as well. If one of these triggers fails, update of the database won't be performed, just like if a simple ['update']['before'] trigger failed. Note that although the overall return value of 'cancel' triggers does not inluence phpMyEdit behavior, the return value of each chained trigger is important.

Bootstrap phpMyEdit PHP Form Generator