Autocomplete for titles via ajax – rework of past post away from like_escape()

Substitute $search = like_escape($_REQUEST['q']); with

$search = $wpdb->esc_like( $_REQUEST['q'] );

(Note assuming $_REQUEST has standard WP magic_quotes_gpc escaping.)

For reference, here’s the exact code I put in “functions.php”:

add_action('wp_enqueue_scripts', 'se_wp_enqueue_scripts');
function se_wp_enqueue_scripts() {
    wp_enqueue_script('suggest');
}

add_action('wp_footer', 'se_wp_head');
function se_wp_head() {
?>
Search: <input id="se_search_element_id" type="text">
<script type="text/javascript">
var se_ajax_url="<?php echo admin_url("admin-ajax.php'); ?>';

jQuery(document).ready(function() {
    jQuery('#se_search_element_id').suggest(se_ajax_url + '?action=se_lookup', {minchars:1});
});
</script>

<?php
}

add_action('wp_ajax_se_lookup', 'se_lookup');
add_action('wp_ajax_nopriv_se_lookup', 'se_lookup');

function se_lookup() {
    global $wpdb;

    $search = $wpdb->esc_like($_REQUEST['q']);

    $query = 'SELECT ID,post_title FROM ' . $wpdb->posts . '
        WHERE post_title LIKE \'' . $search . '%\'
        AND post_type = \'post\'
        AND post_status = \'publish\'
        ORDER BY post_title ASC';
    $rows = $wpdb->get_results($query);
    foreach ($rows as $row) {
        $post_title = $row->post_title;
        $id = $row->ID;
        echo $post_title, "\n";
    }
    wp_die();
}

Note the suggestion box just comes up as a list so would need some styling…