Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

MongoDB PHP driver: Query for Distinct records with Limit and Skip

Tags:

php

mongodb

I saw previous questions on this. But none of them are based on latest driver.

So far my code is like below:

$mongo = new MongoDB\Driver\Manager("mongodb://localhost:27017");
$regex1 = new MongoDB\BSON\Regex("^[A-z]","i");
$filter = ['searchcontent.name' => $regex1];
$options = [
   'limit' => 50,
   'skip' => 0
];

$query = new MongoDB\Driver\Query($filter, $options);
$rows = $mongo->executeQuery('webdb.search', $query);

foreach($rows as $r){    
    echo "<br/>".$r->searchcontent->name."<br/>";
}

This code is returning duplicates as I have duplicates in my database. I want to implement distinct on this. I read official documentation, but not able to find anything.

I tried like this:

$options = [
   'limit' => 50,
   'skip' => 0,
'distinct'=>'searchcontent.name'
];

But it did not work for me. Please help.

Edit:

PHP official documentation have a distinct example with executeCommand().

But the problem is I am not able to use limit and skip with this code.

Summary:

I want a query which will contain limit,skip and distinct.

A solution with executeCommand() or with executeQuery() or anything else will work for me.

like image 931
Arijit Avatar asked Feb 01 '17 13:02

Arijit


1 Answers

You can use aggregation pipeline and use $group for distinct records.

$mongo = new MongoDB\Driver\Manager("mongodb://localhost:27017");
$regex1 = new MongoDB\BSON\Regex("^[A-z]","i");

$pipeline = [
    [ '$match' => ['searchcontent.name' => $regex1] ],
    [ '$group' => ['_id' => '$searchcontent.name'] ],
    [ '$limit' => 50 ],
    [ '$skip' => 10 ],
];

$aggregate = new \MongoDB\Driver\Command([
   'aggregate' => 'search', 
   'pipeline' => $pipeline
]);

$cursor = $mongo->executeCommand('webdb', $aggregate);

foreach($cursor as $key => $document) {
    var_dump($document);
}

Alternatively, you should install the library through composer which provides similar syntax as old api.

$collection = (new MongoDB\Client)->webdb->search;

$cursor = $collection->aggregate([
    [ '$match' => ['searchcontent.name' => $regex1] ],
    [ '$group' => ['_id' => '$searchcontent.name'] ],
    [ '$limit' => 50 ],
    [ '$skip' => 10 ],
]);

foreach($cursor as $key => $document) {
    var_dump($document);
}
like image 87
s7vr Avatar answered Sep 17 '22 23:09

s7vr