0

I needed to add sortable columns to clients wordpress for custom meta data I created so I used a pre_user_query hook

add_action('pre_user_query', 'user_column_orderby');

function user_column_orderby($user_search) {
    global $wpdb, $current_screen;

    if ( 'users' != $current_screen->id )
        return;

    $vars = $user_search->query_vars;

    if('Kön' == $vars['orderby']) {
        $user_search->query_from .= " INNER JOIN {$wpdb->usermeta} m1 ON {$wpdb->users}.ID=m1.user_id AND (m1.meta_key='gender')";
        $user_search->query_orderby = ' ORDER BY UPPER(m1.meta_value) '. $vars['order'];
    } elseif ('Ålder' == $vars['orderby']) {
        $user_search->query_from .= " INNER JOIN {$wpdb->usermeta} m1 ON {$wpdb->users}.ID=m1.user_id AND (m1.meta_key='age')";
        $user_search->query_orderby = ' ORDER BY UPPER(m1.meta_value) '. $vars['order'];
    } elseif ('Distrikt' == $vars['orderby']) {
        $user_search->query_from .= " INNER JOIN {$wpdb->usermeta} m1 ON {$wpdb->users}.ID=m1.user_id AND (m1.meta_key='district')";
        $user_search->query_orderby = ' ORDER BY UPPER(m1.meta_value) '. $vars['order'];
    } elseif ('Kategori' == $vars['orderby']) {
        $user_search->query_from .= " INNER JOIN {$wpdb->usermeta} m1 ON {$wpdb->users}.ID=m1.user_id AND (m1.meta_key='category')";
        $user_search->query_orderby = ' ORDER BY UPPER(m1.meta_value) '. $vars['order'];
    }
}

This works fine if you're on the user screen. But I also added a export to csv button, which calls my export-csv.php file that looks like this:

<?php
$location = $_SERVER['DOCUMENT_ROOT'];
include ($location . '/wp-load.php');

if (current_user_can('manage_options')) {
    header("Content-type: application/force-download");
    header('Content-Disposition: inline; filename="users'.date('YmdHis').'.csv"');

    // WP_User_Query arguments
    $args = array (
        'order'          => 'ASC',
        'orderby'        => 'display_name',
        'fields'         => 'all',
    );

    // The User Query
    $blogusers = get_users( 'orderby=nicename&order=ASC' );
    // Array of WP_User objects.
    foreach ( $blogusers as $user ) {
        //echo '<span>' . esc_html( $user->user_email ) . '</span>';
        print_r($user);
    }
}

Now, the problem I'm having is that my .csv file has a notice:

Notice: Trying to get property of non-object in .../wp-content/themes/mytheme/admin/users_additionals.php on line 133

Which points to the line:

if ( 'users' != $current_screen->id )

in my first code. This happens because I've hooked to the pre_user_query hook, and I'm querying users in my file. Is there a way to suppress this notice (without going to wp-config.php and removing the debug code - this is not the solution, just masking the problem)?

2
  • Loading WordPres in a external file is not a good practice instead you can hook the whole code on some action!
    – Sumit
    Commented Apr 6, 2016 at 9:16
  • Yeah, I was wondering how to do that as well :\ I'm exporting the file by clicking on the button which calls this file. In it are the headers that force the download, I don't know which action to use here. Any advice is helpful
    – dingo_d
    Commented Apr 6, 2016 at 9:53

1 Answer 1

1

'users' != $current_screen->id in your file $current_screen is not set therefore, you are getting warning.

You can pass custom var in your user query and check before running your code.

$blogusers = get_users( 'orderby=nicename&order=ASC&my_filter=1' ); 

Here we are passing my_filter=1 then later we can check in pre_user_query

global $wpdb, $current_screen;

$vars = $user_search->query_vars;

if (isset($current_screen->id) && 'users' != $current_screen->id) {
    return;
} else if (empty($vars['myfilter'])) {
    return;
}

However, loading WordPress in a external file is not a good thing. Instead of external file you can wrap the whole code in a function and hook it on some action where headers are not sent.

Example:

Create a form instead of link e.g.

<form action="" method="POST">
    <input type="hidden" name="myprefix_export_csv" value="1" />
    <input type="submit" value="download" />
</form>

Then check if your custom key is set, if it is then export CSV with your current code.

add_action('init', 'export_csv'); //you can use admin_init as well
function export_csv() {
    if (!empty($_POST['myprefix_export_csv'])) {

        //Send headers
        //Query users
        //print data

        exit();
    }
}

You can also set nonce in form if you think other users can tweak it.

4
  • I need to have a button there, could I use the second code with the AJAX?
    – dingo_d
    Commented Apr 6, 2016 at 10:29
  • I guess NO, you can send file in Ajax response.
    – Sumit
    Commented Apr 6, 2016 at 10:32
  • I've placed the form, but the $_POST is empty on reload and when I click the button to send the form. Any idea why?
    – dingo_d
    Commented Apr 6, 2016 at 10:37
  • 1
    Figured why: <input type="hidden" id="myprefix_export_csv" name="myprefix_export_csv" value="1" /> your input didn't have name set, and you've set the hidden as a name instead of type. Thanks!
    – dingo_d
    Commented Apr 6, 2016 at 10:44

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.