WYSIWYG editor in your WordPress theme or plugin

Prior to WordPress 3.3 adding WYSIWYG editor to a frontend page meant you had almost reinvent the wheel. In WordPress 3.3 wp_editor was introduced which made developer/designer’s life whole lot easier. Now you can add the same editor used when you type up a post can be added anywhere in your theme or plugin (frontend or backend).

I stumbled across this function by accident when I was checking why the WYSIWYG editor was not working on one of my plugins on WordPress 3.3 . You also can allow users to  upload images if the user has necessary capabilities using the editor wp_editor adds.

Read all about it on the WordPress Codex . Hope someone will find it useful.

WordPress How To: Monthly,Yearly and Daily Archives for Custom Post Types

For a plugin I was creating I needed Yearly and Monthly archives with my own slug. Even after setting the rewrite rules it was not working. After much debugging and several hours later I finally figured it out. I’ll explain how you could do the same bellow.

Spoiler Alert: For the impatient, it was as simple as removing the old rules that are not setting the post type before adding the new rules 🙂

I’m going to assume that you have already familiar with Custom Post types. If you are not read http://codex.wordpress.org/Post_Types and then come back. Most important are Step 5 and Step 6. Other steps are typical for any plugin or theme using custom post types.

Step 1: Register the post type
Read more about registering custom post types at

register_post_type( 'my_class',
array(
'public' => true,
...
'has_archive' => true,
)
);

Step 2: Add rewrite tags and permalink structure

$event_structure = '/events/%year%/%monthnum%/%my_class%';
$wp_rewrite->add_rewrite_tag("%my_class%", '(.+?)', "my_class=");
$wp_rewrite->add_permastruct('my_class', $event_structure, false);

Step 3: Add post_type_link and rewrite_rules_array filters

add_filter('rewrite_rules_array', 'my_class_add_rewrite_rules');
add_filter('post_type_link', 'my_class_post_type_link', 10, 3);

Step 4: Return a proper permalink

function my_class_post_type_link($permalink, $post_id, $leavename) {
$post = get_post($post_id);

$rewritecode = array(
'%my_class%',
'%year%',
'%monthnum%'
);

if ($post->post_type == 'my_class' && '' != $permalink) {

$ptype = get_post_type_object($post->post_type);

$start = time();
$end = time();

$meta = get_post_custom($post->ID);
// This is where I store when the class starts
if (isset($meta["my_class_start"]) && isset($meta["my_class_start"][0])) {
$start = strtotime($meta["my_class_start"][0]);
}

$year = date('Y', $start);
$month = date('m', $end);

$rewritereplace = array(
($post->post_name == "")?$post->id:$post->post_name,
$year,
$month,
);
$permalink = str_replace($rewritecode, $rewritereplace, $permalink);
} else {
// if they're not using the fancy permalink option
}

return $permalink;
}

Step 5: Add rewrite rules

function my_class_add_rewrite_rules($rules){
$new_rules = array();

// This is the important bit, unsetting the rules
unset($rules['classes/([0-9]{4})/([0-9]{1,2})/?$']);
unset($rules['classes/([0-9]{4})/?$']);

$new_rules['classes/([0-9]{4})/?$'] = 'index.php?year=$matches[1]&post_type=incsub_event';
$new_rules['classes/([0-9]{4})/([0-9]{1,2})/?$'] = 'index.php?year=$matches[1]&monthnum=$matches[2]&post_type=incsub_event';
$new_rules['classes/([0-9]{4})/([0-9]{2})/(.+?)/?$'] = 'index.php?year=$matches[1]&monthnum=$matches[2]&incsub_event=$matches[3]';

return array_merge($new_rules, $rules);
}

Step 6: Don’t forget to flush

add_action('option_rewrite_rules', 'my_class_check_rewrite_rules');
function my_class_check_rewrite_rules($value) {
global $wp_rewrite;

//prevent an infinite loop
if ( ! post_type_exists( 'incsub_event' ) )
return;

if (!is_array($value))
$value = array();

$array_key = 'events/([0-9]{4})/?$';
if ( !array_key_exists($array_key, $value) ) {
$wp_rewrite->flush_rules();
}
$array_key = 'events/([0-9]{4})/([0-9]{1,2})/?$';
if ( !array_key_exists($array_key, $value) ) {
$wp_rewrite->flush_rules();
}
$array_key = 'events/([0-9]{4})/([0-9]{1,2})/(.+?)/?$';
if ( !array_key_exists($array_key, $value) ) {
$wp_rewrite->flush_rules();
}
}

That’s it. Most important steps are Step 5 and Step 6

How to customize a WordPress plugin and upgrade

Sometimes you want to make minor changes to WordPress plugins that no body except your self would want. Then comes the issue of upgrading to new versions of the plugin. git-svn is the perfect tool for this. It has all the cool features of the distributed SCM git and ability to pull from subversion (and push to it as well). Here is how I do it:

  1. Clone the trunk
    git svn clone http://svn.wp-plugins.org/web-invoice/trunk/
    
  2. Make your changes
  3. Commit changes locally
    git commit -a
    
  4. Pull new changes (e.g. new release). Git is very good at merging, you will not have conflicts unless you edit exact same lines in the local version. Still a manual merge shouldn’t be too complicated
    git svn rebase
    

In the example I have taken the svn trunk of Web Invoice WordPress plugin. Hope you find this information useful next time you hack a WordPress plugin.

How to customize Web Invoice e-mail templates

In the latest release of Web Invoice – Invoicing and Billing for WordPress plugin you can customize the e-mails sent to your clients. You can customize the subject as well as the e-mail content. Please bear in mind that Web Invoice only supports plain text e-mails, but you can do wonders with plain text 🙂 .  This can definitely come in handy if you want to localize your invoices or just does not like what comes as default.

Now to get to the point, the e-mail templates are found in ‘Web Invoice’ -> ‘E-mail templates’.  There are three templates,

  • Invoice e-mail – First e-mail your client receives about the invoice
  • Reminder e-mail – E-mail sent when send reminder(s) is selected
  • Receipt e-mail – Sent when the client makes a payment. You also need to set ‘Send Payment Confirmation’ to yes in Settings

All variables are of the format %variable_name. Bellow you will find the list of variables available in the current version.

  • %call_sign – First name + Last name of the client
  • %business_name – Business name as set in the ‘Settings’
  • %recurring – Recurring or not
  • %amount – Amount, with currency symbol and currency formatted
  • %link – Link to the invoice
  • %business_email – Business e-mail as set in the ‘Settings’
  • %subject – Invoice subject
  • %description – Invoice description

You can definitely use the default templates as a guideline for your templates. IMHO, default templaes are awesome 😉

Don’t go away, there is more. You can write your own plugin to add more variables. e.g. you want to use web invoice along with a booking system. In your plugin add a filter for web_invoice_email_variables and add to the global array (variable) $web_invoices_email_variables.

I want to hear what you think about this feature or Web Invoice in general. Please post your ideas and comments in the Web Invoice community forum. Do not forget to subscribe to my RSS feed to get latest news about WordPress plugins and all things web 🙂

Web Invoice exceeds 1000 downloads

Web Invoice – Invoicing and billing for WordPress plugin has exceeded 1000 downloads. It has 1172 dowloads to date. First release of the plugin was made on March 15, 2009 and now in less than 1 month it has more than 1000 downloads.

Web Invoice is ideal for web developers, SEO consultants, general contractors, or anyone with a WordPress blog and clients to bill. If you come under any of the above, you should give Web Invoice a try.

Download or read more about Web Invoice.

How to migrate from WP-Invoice to Web Invoice?

Web Invoice and WP-Invoice are two WordPress plugins that allow sending invoices and bills. Web Invoice is a fork of WP-Invoice with lot of new features that most people will want. In the current release (1.6.2) they are:

  • Send invoice reminders to customers with a secured link back to the
    web invoice
  • Moneybookers, AlertPay or PayPal available if you don’t have a
    credit card processing account
  • Setup recurring billing using Authorize.net’s ARB (Automatic Recurring Billing) feature or Moneybookers
  • Automatically mark invoices paid via Moneybookers as paid (Requires
    merchant status)
  • Automatically mark invoices paid via AlertPay as paid (Requires
    business status)
  • Split gateway support (Your client is given the option of choosing the preferred gateway from the list of gateways you support). e.g PayPal and Moneybookers
  • All user interfaces are internationalized

If you are already using WP-Invoice and would like to leverage these new features, it’s simple. Follow the 3 step process to switch from WP-Invoice to Web Invoice.

  1. Rename the tables invoice_log to web_invoice_log, invoice_main to web_invoice_main, invoice_meta to web_invoice_meta. (Assuming $table_prefix is empty)
  2. Download Web Invoice WordPress plugin and upload it to your server
  3. Activate Web Invoice

That’s all, you can use Web Invoice without losing that you generated with WP-Invoice.

SyntaxHighlighter2 WordPress plugin released

SyntaxHighlighter2 WordPress plugin was released yesterday on WordPress Extend plugin repository. SyntaxHighlighter2 allows you to easily post syntax highlighted code all without loosing it’s formatting or making an manual changes. Main addition is upgrade to SyntaxHighlighter JavaScript 2.0 by Alex Gorbatchev. Also in this release the web master/blogger is given the ability to choose from 6 themes for the SyntaxHighlighter.

If you already using SyntaxHighlighter WordPress plugin and using XHTML, you should upgrade to SyntaxHighlighter2 because SyntaxHighlighter uses invalid XHTML. Bellow you will find the sample WordPress configuration file with SyntaxHighlighter2 🙂 .

<?php
/** 
 * The base configurations of the WordPress.
 *
 * This file has the following configurations: MySQL settings, Table Prefix,
 * Secret Keys, WordPress Language, and ABSPATH. You can find more information by
 * visiting {@link http://codex.wordpress.org/Editing_wp-config.php Editing
 * wp-config.php} Codex page. You can get the MySQL settings from your web host.
 *
 * This file is used by the wp-config.php creation script during the
 * installation. You don't have to use the web site, you can just copy this file
 * to "wp-config.php" and fill in the values.
 *
 * @package WordPress
 */

// ** MySQL settings - You can get this info from your web host ** //
/** The name of the database for WordPress */
define('DB_NAME', 'putyourdbnamehere');

/** MySQL database username */
define('DB_USER', 'usernamehere');

/** MySQL database password */
define('DB_PASSWORD', 'yourpasswordhere');

/** MySQL hostname */
define('DB_HOST', 'localhost');

/** Database Charset to use in creating database tables. */
define('DB_CHARSET', 'utf8');

/** The Database Collate type. Don't change this if in doubt. */
define('DB_COLLATE', '');

/**#@+
 * Authentication Unique Keys.
 *
 * Change these to different unique phrases!
 * You can generate these using the {@link https://api.wordpress.org/secret-key/1.1/ WordPress.org secret-key service}
 *
 * @since 2.6.0
 */
define('AUTH_KEY', 'put your unique phrase here');
define('SECURE_AUTH_KEY', 'put your unique phrase here');
define('LOGGED_IN_KEY', 'put your unique phrase here');
define('NONCE_KEY', 'put your unique phrase here');
/**#@-*/

/**
 * WordPress Database Table prefix.
 *
 * You can have multiple installations in one database if you give each a unique
 * prefix. Only numbers, letters, and underscores please!
 */
$table_prefix  = 'wp_';

/**
 * WordPress Localized Language, defaults to English.
 *
 * Change this to localize WordPress.  A corresponding MO file for the chosen
 * language must be installed to wp-content/languages. For example, install
 * de.mo to wp-content/languages and set WPLANG to 'de' to enable German
 * language support.
 */
define ('WPLANG', '');

/* That's all, stop editing! Happy blogging. */

/** WordPress absolute path to the WordPress directory. */
if ( !defined('ABSPATH') )
	define('ABSPATH', dirname(__FILE__) . '/');

/** Sets up WordPress vars and included files. */
require_once(ABSPATH . 'wp-settings.php');
?>
<?php
/** 
 * The base configurations of the WordPress.
 *
 * This file has the following configurations: MySQL settings, Table Prefix,
 * Secret Keys, WordPress Language, and ABSPATH. You can find more information by
 * visiting {@link http://codex.wordpress.org/Editing_wp-config.php Editing
 * wp-config.php} Codex page. You can get the MySQL settings from your web host.
 *
 * This file is used by the wp-config.php creation script during the
 * installation. You don't have to use the web site, you can just copy this file
 * to "wp-config.php" and fill in the values.
 *
 * @package WordPress
 */

// ** MySQL settings - You can get this info from your web host ** //
/** The name of the database for WordPress */
define('DB_NAME', 'putyourdbnamehere');

/** MySQL database username */
define('DB_USER', 'usernamehere');

/** MySQL database password */
define('DB_PASSWORD', 'yourpasswordhere');

/** MySQL hostname */
define('DB_HOST', 'localhost');

/** Database Charset to use in creating database tables. */
define('DB_CHARSET', 'utf8');

/** The Database Collate type. Don't change this if in doubt. */
define('DB_COLLATE', '');

/**#@+
 * Authentication Unique Keys.
 *
 * Change these to different unique phrases!
 * You can generate these using the {@link https://api.wordpress.org/secret-key/1.1/ WordPress.org secret-key service}
 *
 * @since 2.6.0
 */
define('AUTH_KEY', 'put your unique phrase here');
define('SECURE_AUTH_KEY', 'put your unique phrase here');
define('LOGGED_IN_KEY', 'put your unique phrase here');
define('NONCE_KEY', 'put your unique phrase here');
/**#@-*/

/**
 * WordPress Database Table prefix.
 *
 * You can have multiple installations in one database if you give each a unique
 * prefix. Only numbers, letters, and underscores please!
 */
$table_prefix  = 'wp_';

/**
 * WordPress Localized Language, defaults to English.
 *
 * Change this to localize WordPress.  A corresponding MO file for the chosen
 * language must be installed to wp-content/languages. For example, install
 * de.mo to wp-content/languages and set WPLANG to 'de' to enable German
 * language support.
 */
define ('WPLANG', '');

/* That's all, stop editing! Happy blogging. */

/** WordPress absolute path to the WordPress directory. */
if ( !defined('ABSPATH') )
	define('ABSPATH', dirname(__FILE__) . '/');

/** Sets up WordPress vars and included files. */
require_once(ABSPATH . 'wp-settings.php');
?>

WordPress object cache with memcached backend for vanilla WordPress

WordPress object cache with memcached backend is mainly meant for WPMU and doesn’t work well if you happened to have many vanilla WordPress installations using the same memcached backend like it is pointed out here and here.

I have created a simple patch which you can apply against object-cache.php (downloadable from WordPress plugin repository) or here is the file already patched. The patch prepends the $blog_id to the object key. You will have to specify global variable $blog_id in wp-config.php and give it a unique id (like your blog url).

global $blog_id;
$blog_id = 'mohanjith_net';