Cannot set limit to 0 due to falsy reset to default
JellowGerard opened this issue · comments
Description
I have the need to get the total number of documents matching a certain query. However, I don't want to retrieve the matching results, as I don't need them at that point, and they will only slow things down. As such, I set the limit of the DocumentQuery to 0.
Expected behavior
I expect to get no hits, but still the required info on the total hits.
Current behavior
Due to this code: 'limit' => $this->limit ?? null,
, 0 is considered falsy, resulting in the limit to be reset to null.
Environment (please complete the following information):
- OS: MacOS
- Meilisearch version: v.1.0.2
- meilisearch-php version: v1.0.0
I dont think this null coalescing operator does what you experience
<?php
$a = null;
$b = 0;
echo $a ?? "a is null";
echo "\n";
echo $b ?? "b is 0";
echo "\n";
echo $c ?? "c does not exist";
output
a is null
0
c does not exist
You can see it live here
as you see the 0
is not considered falsy (if that is the case you should see that b is 0
in the output.
The null coalescing operator (??) has been added as syntactic sugar for the common case of needing to use a ternary in conjunction with isset(). It returns its first operand if it exists and is not null; otherwise it returns its second operand. doc
the issue is something else.
Hi @JellowGerard, I'm trying to reproduce your issue with a test case:
public function testGetDocumentsWithZero(): void
{
// just adding documents to an index.
$index = $this->createEmptyIndex($this->safeIndexName('movies'));
$response = $index->addDocuments(self::DOCUMENTS);
$index->waitForTask($response['taskUid']);
// requesting as you explained.
$response = $index->getDocuments((new DocumentsQuery())->setLimit(0));
// asserting that I get no document in the results array but still the total.
$this->assertEquals($response->getTotal(), count(self::DOCUMENTS));
$this->assertEquals($response->getResults(), []);
}
And it works as expected. Can you enlighten me on your use case? If you can tweak this code, it could be even better.
Sorry for the late reply. I went over it line by line, and found the root cause of the issue, which is different than I initially thought.
The issue actually lies with the Laravel Scout implementation, rather than the meilisearch-php implementation.
For those of you experiencing similar issues, here is what I found and how to work around it:
In the Scout MeilisearchEngine class, every time you call the performSearch
function, the $searchParams array is set using the array_filter function, which filters out all "empty" values from the array. In this function, it filters out 'hitsPerPage' => 0
, since 0 is considered falsy, meaning melisearch never receives the desired limit of 0.
For my implementation, I fixed this by overwriting the MeilisearchEngine->search function, and providing a second argument for the array_filter function, which specifically checks for null, empty strings, or empty arrays, but leaves zero alone.
tl;dr: not a bug in meilisearch-php after all, but rather an "unwanted feature" in the Laravel Scout implementation of Meilisearch.