3

For some reason during a user query with a meta filter I have a user who when I print_r the results appears twice in the list...

I have checked the database, just in case there seemed to be duplicate entries but there is only a single value for the user. Also without the meta query the user only appears once.

Code:

$user_query = new WP_User_Query( 
    array(
        'role'       => 'member',
        'orderby'    => 'registered',
        'order'      => 'DESC',
        'meta_query' => array(
             array(
                 'key'   => 'onTrial',
                 'value' => '1',
             ),
        ),
    )
);
echo '<pre>';
print_r($user_query->results);
echo '</pre>';

Outputs (along with many others):

[54] => WP_User Object
    (
        [data] => stdClass Object
            (
                [ID] => 10410
                [user_login] => XXXXXXX@XXXXXXX.co.uk
                [user_pass] => $P$XXXXXXX
                [user_nicename] => XXXXXXX-XXXXXXX
                [user_email] => XXXXXXX@XXXXXXX.co.uk
                [user_url] => 
                [user_registered] => 2016-02-15 10:52:57
                [user_activation_key] => 
                [user_status] => 0
                [display_name] => XXXXXXX XXXXXXX
            )

        [ID] => 10410
        [caps] => Array
            (
                [member] => 1
            )

        [cap_key] => wp_capabilities
        [roles] => Array
            (
                [0] => member
            )

        [allcaps] => Array
            (
                [read] => 
                [no_admin_bar] => 1
                [member] => 1
            )

        [filter] => 
    )

[55] => WP_User Object
    (
        [data] => stdClass Object
            (
                [ID] => 10410
                [user_login] => XXXXXXX@XXXXXXX.co.uk
                [user_pass] => $P$XXXXXXX
                [user_nicename] => XXXXXXX-XXXXXXX
                [user_email] => XXXXXXX@XXXXXXX.co.uk
                [user_url] => 
                [user_registered] => 2016-02-15 10:52:57
                [user_activation_key] => 
                [user_status] => 0
                [display_name] => XXXXXXX XXXXXXX
            )

        [ID] => 10410
        [caps] => Array
            (
                [member] => 1
            )

        [cap_key] => wp_capabilities
        [roles] => Array
            (
                [0] => member
            )

        [allcaps] => Array
            (
                [read] => 
                [no_admin_bar] => 1
                [member] => 1
            )

        [filter] => 
    )

Now I can't show you the details obviously but note the ID and reg time outputted also the array numbers they appear in, [54] and [55]

No one else appears twice.

Thanks in advance - any input appreciated, small or large.

  • 3
    Does the meta_key/value pair exist twice for the same user in the usermeta table by chance? – userabuser Mar 10 '16 at 13:29
  • 1
    That could explain it, since the generated query is joining the user meta table with the users table, without any distinct or group by. – birgire Mar 10 '16 at 13:34
  • Right - yes. Great shout. It appears twice against that user with different umeta_ids despite that particular bit of code using update_user_meta as an insert command. I didn't spot it before as to check I was using foreach( [get_user_meta($profileuser->ID)] as $key => $value) { How will that have happened? – Bysander Mar 10 '16 at 13:39
  • 1
    hmm... typically that would happen if you are using add_user_meta and didn't specify unique. I need to give it some more thought. – userabuser Mar 10 '16 at 13:44
  • I can obviously delete the entry from the database. However I'd like to know how that crept in there in the first place. That particular entry is made by a daily wp_cron. If it's adding multiple values on the user meta then that query sort of breaks down as useless and relies me spotting duplicates manually or using array_unique for everything... Which is annoying. – Bysander Mar 10 '16 at 13:46
3

Try this for kicks...

Solution 1

Note: Does not work with WP_User_Query (?)

add_filter('posts_distinct', 'user_meta_query_distinct');

//your query here...

remove_filter('posts_distinct', 'user_meta_query_distinct');

function user_meta_query_distinct() { 
    return "DISTINCT"; 
}

Solution 2

Can you try adding 'relation' => 'OR' to your meta_query:

$user_query = new WP_User_Query( 
    array(
        'role'       => 'member',
        'orderby'    => 'registered',
        'order'      => 'DESC',
        'meta_query' => array(
             'relation' => 'OR', //should result in a DISTINCT query
             array(
                 'key'   => 'onTrial',
                 'value' => '1',
             ),
        ),
    )
);

See this diff:

https://core.trac.wordpress.org/attachment/ticket/17582/17582.4.diff

if ( 'OR' == $meta_query->relation ) { 
    $this->query_fields = 'DISTINCT ' . $this->query_fields; 
}

Tracked down courtesy of this trac ticket.

See if that works...

  • 1
    I think the posts_distinct only works on WP_Query – birgire Mar 10 '16 at 13:42
  • Yup - the troublesome entry is still there. – Bysander Mar 10 '16 at 13:43
  • @birgire interesting thanks, wasn't quite sure... There's a trac ticket that has rumblings of the same problem: core.trac.wordpress.org/ticket/17582 with a solution albeit not entirely desirable if you read the OP. – userabuser Mar 10 '16 at 13:48
  • 2
    @userabuser Sometimes I wish there would be concistancy among the query classes regarding the sql filters.. It looks like the trac ticket was closed due to inactivity but I'm not sure it should have the "fixed" status ;-) The DISTINCT is added if there's an OR in the meta query aka $this->meta_query->has_or_relation(). – birgire Mar 10 '16 at 14:01
  • @birgire totally agree... Regarding the trac ticket though, I thought it was closed out as a "wontfix" but then later saw it said "fixed" - if you have a look in WP_User_Query it appears that at least somewhere along the line similar code for a relation check === to OR was added that then adds DISTINCT to the SELECT. I wonder... that should still work though right? – userabuser Mar 10 '16 at 14:05

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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