wp_list_table bulk actions not working properly
<p>I've been working with the wp_list_table class and creating my custom theme pages with add/edit/delete features on the row options. The problem i am having is with the bulk actions.  The row actions are working just fine. Now here is where it gets weird. </p>

<p>If I am looking at my table in admin and I select the checkbox on a few rows, switch to bulk-delete action, then hit apply, I will not get any post data for those checkboxes.  What I mean by that is the checkboxes are named as an array bulk-delete[] in html. and if I do a print_r($_request); the bulk-delete key is no present.</p>

<p>Now when I select a few checkboxes, and this time NOT switch to bulk-delete I just leave it saying "Bulk Actions", then hit apply, I will get the bulk-delete array but all the keys are empty.</p>

<p>For me totally freaking bazaar.  But I am sure there is something really stupid that I missed. So here is the class in it's entirety. Please let me know what I missed.  </p>

<p>[a secondary issue - I'd like to also show an "Country has been added" success message.  Could you guys point me in the right direction for knowledge to read up on that]</p>

<p>Thanks in advance. </p>

<pre><code>&lt;?php

class country_class {

var $page_name = "lp-manage-countries";


public function __construct(){
    //make sure the wp_list_table class has been loaded
    if (!class_exists('WP_List_Table')) {
        require_once(ABSPATH . 'wp-admin/includes/class-wp-list-table.php');
    }
    add_action( 'admin_post_add_country', array( $this, 'lp_admin_add_country') );
    add_filter('set-screen-option', array( $this, 'lp_save_screen_options') , 10, 3);
    //add_action( 'admin_post_bulk_action', array( $this, 'process_bulk_action') );
}

/**
 * Sets the screen options up for table paging
 */
public function lp_screen_options() {
    $lp_manage_countries_page = "toplevel_page_" . $this-&gt;page_name;
    $screen = get_current_screen();
    // get out of here if we are not on our settings page
    if(!is_object($screen) || $screen-&gt;id != $lp_manage_countries_page)
        return;
    $args = array(
        'label' =&gt; __('Countries per page'),
        'default' =&gt; 25,
        'option' =&gt; 'countries_per_page'
    );
    add_screen_option( 'per_page', $args );
}

/**
 * Saves the screen option to the object class
 */
function lp_save_screen_options($status, $option, $value) {
    if ( 'countries_per_page' == $option ) return $value;
    return $status;
}

/**
 * Installs the page and screen options
 */
public function install_countries_page(){
    //Add the screen options first
    add_action("load-toplevel_page_" . $this-&gt;page_name, array( $this, "lp_screen_options") );
    add_menu_page('LP Countries', 'LP Countries', 'manage_options', 'lp-manage-countries', array($this, 'show_country_page'));
}

public function  lp_admin_add_country(){
    global $wpdb;
    if( isset( $_REQUEST['country_name'] ) and !empty( $_REQUEST['country_name'] )){
        $result = $wpdb-&gt;insert(
            'countries',
            array(
                'name' =&gt; $_REQUEST['country_name']
            )
        );
        if( $result !== false ){
            wp_redirect(admin_url("admin.php?page=" . $this-&gt;page_name) );
            exit;
        }
    }
}

/**
 * Displays the page data
 */
public function show_country_page(){
    if( isset( $_GET['action']) &amp;&amp; ( $_REQUEST['action'] == "add" || $_REQUEST['action'] == "edit" )){
        echo "&lt;div class='wrap'&gt;
            &lt;h1&gt;Add Country&lt;/h1&gt;
            &lt;form action='" . admin_url("admin-post.php", "http") . "' method='post'&gt;
            &lt;input type=\"hidden\" name=\"action\" value=\"add_country\"&gt;
            &lt;table class=\"form-table\"&gt;
            &lt;tbody&gt;
            &lt;tr&gt;
            &lt;th scope=\"row\"&gt;&lt;label for='country_name' xmlns=\"http://www.w3.org/1999/html\"&gt;Country Name:&lt;/label&gt;&lt;/th&gt;
            &lt;td&gt;&lt;input id='country_name' required class='regular-text type='text' value='' name='country_name'&gt;&lt;/input&gt;&lt;/td&gt;
            &lt;/tr&gt;
            &lt;/tbody&gt;
            &lt;/table&gt;
            &lt;p class='submit'&gt;
            &lt;input id='submit' class='button button-primary' type='submit' value='Save Country' name='submit'&gt;&lt;/input&gt;
            &lt;/p&gt;
            &lt;/form&gt;";
    } else {
        echo "&lt;div class=\"wrap\"&gt;
            &lt;h1&gt;Manage Countries&lt;a class=\"page-title-action\" href=\"".admin_url("admin.php?page=".$this-&gt;page_name."&amp;action=add")."\"&gt;Add New&lt;/a&gt;&lt;/h1&gt;
            &lt;form method='post'&gt;";
            //echo "&lt;input type=\"hidden\" name=\"action\" value=\"bulk_action\"&gt;";
        //Prepare Table of elements
        $categories_list_table = new category_list_table();
        $categories_list_table-&gt;prepare_items();
        //Table of elements
        $categories_list_table-&gt;display();
        echo "&lt;/form&gt;";
    }
}

/**
 * Creates the database for this page
 */
public function create_countries_table(){
    global $wpdb;
    $charset = $wpdb-&gt;get_charset_collate();

    $sql = "CREATE TABLE IF NOT EXISTS `countries` (
            `id` int(11) NOT NULL AUTO_INCREMENT,
            `name` varchar(45) NOT NULL,
            `parent_id` int(11) DEFAULT NULL,
            `image` varchar(45) DEFAULT NULL,
            PRIMARY KEY (`id`)
            ) $charset; ";

    $wpdb-&gt;query( $sql );

}

/**
 * removes the page database when uninstalled
 */
public function drop_countries_table(){
    global $wpdb;
    $sql = "DROP TABLE `countries`;";
    $wpdb-&gt;query($sql);
}

}


class category_list_table extends WP_List_Table {

public function __construct(){
    parent::__construct( array(
        'singular' =&gt; 'Country',
        'plural' =&gt; 'Countries',
            'ajax' =&gt; false)
    );
}

public function get_columns(){
    return $columns = array(
        'cb'   =&gt; '&lt;input name="bulk-delete[]" type="checkbox" /&gt;',
        'name' =&gt; __('Name'),
        'parent_id' =&gt; __('Parent ID'),
        'image' =&gt; __('Image')
    );
}

function column_name($item) {
    // create a nonce
    $delete_nonce = wp_create_nonce( 'lp_delete_country' );
    $edit_nonce = wp_create_nonce( 'lp_delete_country' );
    $actions = array(
        'edit' =&gt; sprintf('&lt;a href="?page=%s&amp;action=%s&amp;country=%s&amp;_wpnonce=%s"&gt;Edit&lt;/a&gt;', $_REQUEST['page'], 'edit', $item['id'], $edit_nonce),
        'delete' =&gt; sprintf('&lt;a href="?page=%s&amp;action=%s&amp;country=%s&amp;_wpnonce=%s"&gt;Delete&lt;/a&gt;', $_REQUEST['page'], 'delete', $item['id'], $delete_nonce),
    );
    return sprintf('%1$s %2$s', $item['name'], $this-&gt;row_actions($actions) );
}

public function get_sortable_columns(){
    return $sortable = array(
        'id' =&gt; array('id',false),
        'name' =&gt; array('name',false),
        'parent_id' =&gt; array('parent_id', false),
        'image' =&gt; array('image', false)
    );
}

public function get_hidden_columns( ){
    $screen = get_current_screen();

    if ( is_string( $screen ) )
        $screen = convert_to_screen( $screen );

    return (array) get_user_option( 'manage' . $screen-&gt;id . 'columnshidden' );
}

public function prepare_items(){
    global $wpdb, $_wp_column_headers;

    $screen = get_current_screen();

    /** Process bulk action */
    $this-&gt;process_bulk_action();

    /* Prepare the query */
    $query = "SELECT * FROM `countries`";

    /* Order Parameters */
    $orderby = !empty($_GET["orderby"]) ? mysql_real_escape_string($_GET["orderby"]) : 'ASC';
    $order = !empty($_GET["order"]) ? mysql_real_escape_string($_GET["order"]) : '';
    if(!empty($orderby) &amp; !empty($order)){ $query.=' ORDER BY '.$orderby.' '.$order; }

    /* Pagination Params */
    //Number of elements in your table?
    $totalitems = $wpdb-&gt;query($query); //return the total number of affected rows

    //How many to display per page?
    $perpage = get_user_meta( get_current_user_id() , 'countries_per_page', true);

    if( empty($perpage)){
        $perpage = 25;
    }

    //Which page is this?
    $paged = !empty($_GET["paged"]) ? mysql_real_escape_string($_GET["paged"]) : '';

    //Page Number
    if(empty($paged) || !is_numeric($paged) || $paged&lt;=0 ){ $paged=1; }

    //How many pages do we have in total?
    $totalpages = ceil($totalitems/$perpage);

    //adjust the query to take pagination into account
    if(!empty($paged) &amp;&amp; !empty($perpage)){
        $offset=($paged-1)*$perpage;
        $query.=' LIMIT '.(int)$offset.','.(int)$perpage;
    }

    /* Register pagination */
    $this-&gt;set_pagination_args( array(
        "total_items" =&gt; $totalitems,
        "total_pages" =&gt; $totalpages,
        "per_page" =&gt; $perpage
    )
    );

    /* register the columns */
    $columns = $this-&gt;get_columns();
    $_wp_column_headers[$screen-&gt;id]=$columns;

    /* Get the items */
    $this-&gt;items = $wpdb-&gt;get_results($query, 'ARRAY_A');

    $hidden_columns = $this-&gt;get_hidden_columns();
    $sortable_columns = $this-&gt;get_sortable_columns();
    parent::get_column_info();
    $this-&gt;_column_headers = array( $columns, $hidden_columns, $sortable_columns);
}

public function column_default($item, $column_name) {
    //return $item[$column_name];
    switch ( $column_name ) {
        case 'cb':
        case 'name':
        case 'parent_id':
        case 'image':
            return $item[ $column_name ];
        default:
            return $item[ $column_name ];
    }
}

function no_items() {
    _e( 'No Countries Found.' );
}

function column_cb( $item ) {
    return sprintf(
        '&lt;input type="checkbox" name="bulk-delete[]" value="%s" /&gt;', $item['ID']
    );
}

public function get_bulk_actions() {
    $actions = [
        'bulk-delete' =&gt; 'Delete'
    ];
    return $actions;
}

public function process_bulk_action() {

    $action = $this-&gt;current_action();
    echo "action is [" . $action . "]";
    if( !empty( $action ) ){

        switch ($action){
            case 'delete':
                // In our file that handles the request, verify the nonce.
                $nonce = esc_attr( $_REQUEST['_wpnonce'] );

                if ( ! wp_verify_nonce( $nonce, 'lp_delete_country' ) ) {
                    die( 'Go get a life script kiddies' );
                } else {
                    echo " running delete";
                    self::delete_country( absint( $_GET['country'] ) );
                    wp_redirect( esc_url( add_query_arg() ) );
                    exit;
                }
            case 'edit':
                echo "we should be editing";
            case 'bulk-delete':
                // If the delete bulk action is triggered
                echo "we triggered a bulk delete";
                echo "&lt;pre&gt;";
                print_r( $_REQUEST );
                echo "&lt;/pre&gt;";
                if ( !empty( $_POST['bulk-delete'] ) ) {

                    $delete_ids = esc_sql( $_POST['bulk-delete'] );

                    // loop over the array of record IDs and delete them
                    foreach ( $delete_ids as $id ) {
                        $this-&gt;delete_country( $id );

                    }

                    wp_redirect( esc_url( add_query_arg() ) );
                    exit;
                } else {
                    echo "Fucking empty";
                }

            default:
                echo "&lt;pre&gt;";
                print_r( $_REQUEST );
                echo "&lt;/pre&gt;";
                //quietly exit;
        }
    } else {
        echo "&lt;pre&gt;";
        print_r( $_REQUEST );
        echo "&lt;/pre&gt;";
    }
}

function delete_country( $id ) {
    global $wpdb;
    $wpdb-&gt;delete(
        "countries",
        [ 'id' =&gt; $id ]
    );
}

}
</code></pre>