MatchTest.php 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174
  1. <?php
  2. /**
  3. * Copyright © Magento, Inc. All rights reserved.
  4. * See COPYING.txt for license details.
  5. */
  6. namespace Magento\Elasticsearch\Test\Unit\SearchAdapter\Query\Builder;
  7. use Magento\Elasticsearch\Model\Adapter\FieldMapperInterface;
  8. use Magento\Elasticsearch\SearchAdapter\Query\Builder\Match as MatchQueryBuilder;
  9. use Magento\Framework\Search\Request\Query\Match as MatchRequestQuery;
  10. use Magento\Framework\TestFramework\Unit\Helper\ObjectManager;
  11. use PHPUnit_Framework_MockObject_MockObject as MockObject;
  12. class MatchTest extends \PHPUnit\Framework\TestCase
  13. {
  14. /**
  15. * @var MatchQueryBuilder
  16. */
  17. private $matchQueryBuilder;
  18. /**
  19. * @inheritdoc
  20. */
  21. protected function setUp()
  22. {
  23. $this->matchQueryBuilder = (new ObjectManager($this))->getObject(
  24. MatchQueryBuilder::class,
  25. [
  26. 'fieldMapper' => $this->getFieldMapper(),
  27. 'preprocessorContainer' => [],
  28. ]
  29. );
  30. }
  31. /**
  32. * Tests that method constructs a correct select query.
  33. * @see MatchQueryBuilder::build
  34. *
  35. * @dataProvider queryValuesInvariantsProvider
  36. *
  37. * @param string $rawQueryValue
  38. * @param string $errorMessage
  39. */
  40. public function testBuild($rawQueryValue, $errorMessage)
  41. {
  42. $this->assertSelectQuery(
  43. $this->matchQueryBuilder->build([], $this->getMatchRequestQuery($rawQueryValue), 'not'),
  44. $errorMessage
  45. );
  46. }
  47. /**
  48. * @link https://dev.mysql.com/doc/refman/5.7/en/fulltext-boolean.html Fulltext-boolean search docs.
  49. *
  50. * @return array
  51. */
  52. public function queryValuesInvariantsProvider()
  53. {
  54. return [
  55. ['query_value', 'Select query field must match simple raw query value.'],
  56. ['query_value+', 'Specifying a trailing plus sign causes InnoDB to report a syntax error.'],
  57. ['query_value-', 'Specifying a trailing minus sign causes InnoDB to report a syntax error.'],
  58. ['query_@value', 'The @ symbol is reserved for use by the @distance proximity search operator.'],
  59. ['query_value+@', 'The @ symbol is reserved for use by the @distance proximity search operator.'],
  60. ];
  61. }
  62. /**
  63. * Tests that method constructs a correct "match" query depending on query value.
  64. *
  65. * @dataProvider matchProvider
  66. *
  67. * @param string $rawQueryValue
  68. * @param string $queryValue
  69. * @param string $match
  70. */
  71. public function testBuildMatchQuery($rawQueryValue, $queryValue, $match)
  72. {
  73. $query = $this->matchQueryBuilder->build([], $this->getMatchRequestQuery($rawQueryValue), 'should');
  74. $expectedSelectQuery = [
  75. 'bool' => [
  76. 'should' => [
  77. [
  78. $match => [
  79. 'some_field' => [
  80. 'query' => $queryValue,
  81. 'boost' => 43,
  82. ],
  83. ],
  84. ],
  85. ],
  86. ],
  87. ];
  88. $this->assertEquals(
  89. $expectedSelectQuery,
  90. $query,
  91. sprintf('Wrong "match" query. Should be processed with "%s"', $match)
  92. );
  93. }
  94. /**
  95. * @return array
  96. */
  97. public function matchProvider()
  98. {
  99. return [
  100. ['query_value', 'query_value', 'match'],
  101. ['"query value"', 'query value', 'match_phrase'],
  102. ];
  103. }
  104. /**
  105. * @param array $selectQuery
  106. * @param string $errorMessage
  107. */
  108. private function assertSelectQuery($selectQuery, $errorMessage)
  109. {
  110. $expectedSelectQuery = [
  111. 'bool' => [
  112. 'must_not' => [
  113. [
  114. 'match' => [
  115. 'some_field' => [
  116. 'query' => 'query_value',
  117. 'boost' => 43,
  118. ],
  119. ],
  120. ],
  121. ],
  122. ],
  123. ];
  124. $this->assertEquals($expectedSelectQuery, $selectQuery, $errorMessage);
  125. }
  126. /**
  127. * Gets fieldMapper mock object.
  128. *
  129. * @return FieldMapperInterface|MockObject
  130. */
  131. private function getFieldMapper()
  132. {
  133. $fieldMapper = $this->getMockBuilder(FieldMapperInterface::class)
  134. ->getMockForAbstractClass();
  135. $fieldMapper->method('getFieldName')
  136. ->with('some_field', ['type' => FieldMapperInterface::TYPE_QUERY])
  137. ->willReturnArgument(0);
  138. return $fieldMapper;
  139. }
  140. /**
  141. * Gets RequestQuery mock object.
  142. *
  143. * @param string $rawQueryValue
  144. * @return MatchRequestQuery|MockObject
  145. */
  146. private function getMatchRequestQuery($rawQueryValue)
  147. {
  148. $matchRequestQuery = $this->getMockBuilder(MatchRequestQuery::class)
  149. ->disableOriginalConstructor()
  150. ->getMock();
  151. $matchRequestQuery->method('getValue')
  152. ->willReturn($rawQueryValue);
  153. $matchRequestQuery->method('getMatches')
  154. ->willReturn([['field' => 'some_field', 'boost' => 42]]);
  155. return $matchRequestQuery;
  156. }
  157. }