Custom Woocommerce email using woocommerce_email_actions hook

Most of my plugins are Woocommerce based, and many use the Woocommerce Class WC_EMAIL to sent out emails. Recently I started getting complaints about emails not being sent. After some troubleshooting, I found that adding the email trigger action was not getting added to the active array. I google around and found a new hook that I can use a filter woocommerce_email_actions. Simple replace
add_filter( 'woocommerce_init', array( $this, 'my_email_actions' ) );
public function my_email_actions() {
add_action( 'class_my_email_send', array( 'WC_Emails', 'send_transactional_email' ), 10, 1 );

add_filter( 'woocommerce_email_actions', array( $this, 'my_email_actions' ) );

public function my_email_actions() {
$email_actions[] = 'class_my_email_send';
return $email_actions;

Updating WordPress Plugin Updating Tested up to Tag

Sometimes we just need to test and update the Tested up to WordPress version tag fro our plugins in the open repositories.

This can be done using SVN directly.

1. Check out the existing version.
svn co

2. Update the tag in README.txt

3. Commit
svn ci -m 'update to WordPress version 4.8.2'


MySQL commands for replace domains and server paths

Useful MySQL commands for replacing domain URL and file path.

UPDATE wp_options SET option_value = replace(option_value, '','');
UPDATE wp_postmeta SET meta_value = replace(meta_value,'','');
UPDATE wp_posts SET post_content = replace(post_content, '', ''), guid = replace(guid, '','');

UPDATE wp_options SET option_value = replace(option_value, '/public_html/awesome','/var/www/awesome');
UPDATE wp_postmeta SET meta_value = replace(meta_value,'/public_html/awesome','/var/www/awesome');
UPDATE wp_posts SET post_content = replace(post_content, '/public_html/awesome','/var/www/awesome'), guid = replace(guid, '/public_html/awesome','/var/www/awesome');

WP-CLI Guide: Install WordPress via SSH

WP-CLI is a very useful utility if you have the luxury of getting a server that comes with it plus ssh. This is very useful for those who need to constantly launch new WordPress sites.

Create a new directory then execute
wp core download

if you get an error "Error: WordPress files seem to already be present here." Add the force flag.
wp core download --path=.

Downloading WordPress 4.8.1 (en_US)...
md5 hash verified: f3dd0e033519aa363eb07e13c6676e3c
Success: WordPress downloaded.

Now configure your config file
wp core config --dbhost=localhost --dbname=forum --dbuser=wordpress --dbpass=wordpress --path=.
Again here –path=. for those who have wordpress install in the root directory.

Success: Generated 'wp-config.php' file.

Install WordPress
wp core install --title=Example --admin_user=supervisor --admin_password=strongpassword --path=.
Error: Can’t select database. We were able to connect to the database server (which means your username and password is okay) but not able to select the `forum` database.

Database ‘forum’ is missing. You need to create the database in MySQL.

After creating the database run the command again.

Success: WordPress installed successfully.


Repair WordPress Table

Recently, one of my WordPress table failed.

WordPress database error Table 'wp_postmeta' is marked as crashed and last (automatic?) repair failed for query

After failing to have it repair by WordPress script, I turn to Mysql command and it worked.

repair table wp_postmeta;

WordPress Virus/Malware removal

Most of us who owns wordpress site will, at certain point of time, experience a hack. I will not cover the basics of such hack or basic common techniques used to remove them.

One of the technique I been using recently that would well, is to enable the debug mode.

The following code, inserted in your wp-config.php file, will log all errors, notices, and warnings to a file called debug.log in the wp-content directory. It will also hide the errors so they do not interrupt page generation.

// Enable WP_DEBUG mode
define( 'WP_DEBUG', true );

// Enable Debug logging to the /wp-content/debug.log file
define( 'WP_DEBUG_LOG', true );

// Disable display of errors and warnings
define( 'WP_DEBUG_DISPLAY', false );
@ini_set( 'display_errors', 0 );

// Use dev versions of core JS and CSS files (only needed if you are modifying these core files)
define( 'SCRIPT_DEBUG', true );

By simply enabling the debug mode, you be able to catch an error ‘headers already sent’, which also points to the file that the code are injected.

Warning: Cannot modify header information - headers already sent by (output started at /some/file.php:12) in /some/file.php on line 23

Since most code are injected on top of your files, you be able to catch the error sent out just by enabling the debug mode.