Efficient way of saving plugin options

I’m considering the saving of options for a plugin I’m developing. The first obvious candidate is the wp_options table.

While reading the Pro WP Plugin Development book I came across this:

Read More

Every option saved adds a new record in WordPress ’ option table. You can simply store several
options at once, in one array: This avoids cluttering the database and updates the values in one single MySQL query for greater efficiency and speed.

On the other hand, I also imagine that if the plugin has a lot of settings it may hinder performance to store everything in one array. Would it therefore make sense to split options into separate records in such cases?

Third option I can think of is to create custom tables to store the plugin settings, as I’ve seen some plugins do this as well.

What are the rules/guidelines to decide which way to go?

Related posts

Leave a Reply

2 comments

  1. Store the options in a single array and write your plugin as a class. Load the options in the constructor and save it as a member variable and you’ll have access to it everywhere in the plugin.

  2. Use the settings API. It’s awesome!
    Here’s how you do it step by step.

    <?php
    /*
     * Add the admin page
     */
    add_action('admin_menu', 'wpse61431_admin_page');
    function wpse61431_admin_page(){
        add_menu_page('wpse61431 Settings', 'wpse61431', 'administrator', 'wpse61431-settings', 'wpse61431_admin_page_callback');
    }
    
    /*
     * Register the settings
     */
    add_action('admin_init', 'wpse61431_register_settings');
    function wpse61431_register_settings(){
        //this will save the option in the wp_options table as 'wpse61431_settings'
        //the third parameter is a function that will validate your input values
        register_setting('wpse61431_settings', 'wpse61431_settings', 'wpse61431_settings_validate');
    }
    
    function wpse61431_settings_validate($args){
        //$args will contain the values posted in your settings form, you can validate them as no spaces allowed, no special chars allowed or validate emails etc.
        if(!isset($args['wpse61431_email']) || !is_email($args['wpse61431_email'])){
            //add a settings error because the email is invalid and make the form field blank, so that the user can enter again
            $args['wpse61431_email'] = '';
        add_settings_error('wpse61431_settings', 'wpse61431_invalid_email', 'Please enter a valid email!', $type = 'error');   
        }
    
        //make sure you return the args
        return $args;
    }
    
    //Display the validation errors and update messages
    /*
     * Admin notices
     */
    add_action('admin_notices', 'wpse61431_admin_notices');
    function wpse61431_admin_notices(){
       settings_errors();
    }
    
    //The markup for your plugin settings page
    function wpse61431_admin_page_callback(){ ?>
        <div class="wrap">
        <h2>wpse61431 Settings</h2>
        <form action="options.php" method="post"><?php
            settings_fields( 'wpse61431_settings' );
            do_settings_sections( __FILE__ );
    
            //get the older values, wont work the first time
            $options = get_option( 'wpse61431_settings' ); ?>
            <table class="form-table">
                <tr>
                    <th scope="row">Email</th>
                    <td>
                        <fieldset>
                            <label>
                                <input name="wpse61431_settings[wpse61431_email]" type="text" id="wpse61431_email" value="<?php echo (isset($options['wpse61431_email']) && $options['wpse61431_email'] != '') ? $options['wpse61431_email'] : ''; ?>"/>
                                <br />
                                <span class="description">Please enter a valid email.</span>
                            </label>
                        </fieldset>
                    </td>
                </tr>
            </table>
            <input type="submit" value="Save" />
        </form>
    </div>
    <?php }
    ?>
    

    This is a working code, the mark up can be whatever you want, make sure you retain the settings_fields and do_settings_sections call! The input field’s names should also be the way I mentioned.

    For detailed information, read this awesome series on wp tutsplus.