From 42fe11c7a6908dece0a52fedd3205b89a9619ad8 Mon Sep 17 00:00:00 2001 From: adsc-cloudtec Date: Mon, 16 Oct 2017 13:38:15 +0200 Subject: [PATCH 1/5] Added a section about paging the search results (#112) --- Resources/docs/searching.rst | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/Resources/docs/searching.rst b/Resources/docs/searching.rst index 5e180d09..d3d34974 100644 --- a/Resources/docs/searching.rst +++ b/Resources/docs/searching.rst @@ -80,6 +80,18 @@ when represented as JSON: "score": 0.39123123123123 } +Search results are paged. By default, only the first page is returned and a page contains 10 results. This can be +controlled on the SearchQuery like this: + +.. code-block:: php + + createSearch('My Article') + ->setLimit(100) // A page now contains 100 results + ->setOffset(1) // Return the second page of results + ->execute(); + Indexing and deindexing ----------------------- From 837bcc197881be3f2509d1fa33c43dcc2000dad0 Mon Sep 17 00:00:00 2001 From: Johannes Wachter Date: Fri, 13 Apr 2018 15:27:27 +0200 Subject: [PATCH 2/5] Fixed travis tests (#117) * fixed travis tests * fixed style-ci --- Behat/SearchManagerContext.php | 2 +- Command/ReindexCommand.php | 4 ++-- DependencyInjection/Compiler/ConverterPass.php | 1 + Search/Adapter/ElasticSearchAdapter.php | 6 ++++++ Search/Adapter/TestAdapter.php | 1 + Search/Adapter/ZendLuceneAdapter.php | 11 +++++++++-- Search/AdapterInterface.php | 3 --- Search/Decorator/LocalizationDecorator.php | 2 +- Search/Decorator/PrefixDecorator.php | 2 +- Search/Event/HitEvent.php | 1 + .../MassiveSearchExpressionLanguage.php | 2 +- Search/Metadata/Driver/XmlDriver.php | 2 +- Search/Metadata/Provider/DefaultProvider.php | 1 - Search/ObjectToDocumentConverter.php | 8 ++++---- Search/QueryHit.php | 2 ++ Search/SearchEvents.php | 5 +++++ Search/SearchQuery.php | 1 + Tests/Resources/TestBundle/EntityDist/Car.php | 6 ++++++ Tests/Resources/TestBundle/EntityDist/Contact.php | 3 +++ .../TestBundle/EventSubscriber/TestSubscriber.php | 3 +++ Tests/Resources/TestBundle/Product.php | 6 ++++++ Tests/Unit/Search/Metadata/ClassMetadataTest.php | 2 +- Tests/Unit/Search/Metadata/FieldEvaluatorTest.php | 1 - .../ReIndex/Provider/DoctrineOrmProviderTest.php | 1 - Tests/Unit/Search/SearchManagerTest.php | 2 +- Tests/travis.php.ini | 2 +- 26 files changed, 58 insertions(+), 22 deletions(-) diff --git a/Behat/SearchManagerContext.php b/Behat/SearchManagerContext.php index b6685289..fd4a54d0 100644 --- a/Behat/SearchManagerContext.php +++ b/Behat/SearchManagerContext.php @@ -171,7 +171,7 @@ private function doIndexTheFollowingObjects($className, PyStringNode $string) foreach ($objectsData as $objectData) { $object = new $this->entityClasses[$className](); foreach ($objectData as $key => $value) { - if (is_string($value) && ($date = \DateTime::createFromFormat('Y-m-d', $value)) !== false) { + if (is_string($value) && false !== ($date = \DateTime::createFromFormat('Y-m-d', $value))) { $value = $date; } $object->$key = $value; diff --git a/Command/ReindexCommand.php b/Command/ReindexCommand.php index 0d1dee30..0e3b33ee 100644 --- a/Command/ReindexCommand.php +++ b/Command/ReindexCommand.php @@ -98,7 +98,7 @@ public function execute(InputInterface $input, OutputInterface $output) $startTime = microtime(true); - if ($this->env !== 'prod') { + if ('prod' !== $this->env) { $output->writeln( $formatterHelper->formatBlock( sprintf( @@ -197,7 +197,7 @@ private function reindexClass( while (true) { $objects = $provider->provide($classFqn, $offset, $batchSize); - if (count($objects) === 0) { + if (0 === count($objects)) { $provider->cleanUp($classFqn); $this->resumeManager->setCheckpoint($providerName, $classFqn, $count); $progress->finish(); diff --git a/DependencyInjection/Compiler/ConverterPass.php b/DependencyInjection/Compiler/ConverterPass.php index 0a727626..b3a0e054 100644 --- a/DependencyInjection/Compiler/ConverterPass.php +++ b/DependencyInjection/Compiler/ConverterPass.php @@ -21,6 +21,7 @@ class ConverterPass implements CompilerPassInterface { const SERVICE_ID = 'massive_search.converter'; + const TAG_NAME = 'massive_search.converter'; /** diff --git a/Search/Adapter/ElasticSearchAdapter.php b/Search/Adapter/ElasticSearchAdapter.php index a44e35f4..e9ee66f0 100644 --- a/Search/Adapter/ElasticSearchAdapter.php +++ b/Search/Adapter/ElasticSearchAdapter.php @@ -28,13 +28,19 @@ class ElasticSearchAdapter implements AdapterInterface { const ID_FIELDNAME = '__id'; + const INDEX_FIELDNAME = '__index'; + const CLASS_TAG = '__class'; const URL_FIELDNAME = '__url'; + const TITLE_FIELDNAME = '__title'; + const DESCRIPTION_FIELDNAME = '__description'; + const LOCALE_FIELDNAME = '__locale'; + const IMAGE_URL = '__image_url'; /** diff --git a/Search/Adapter/TestAdapter.php b/Search/Adapter/TestAdapter.php index 5d178633..cc7c54a6 100644 --- a/Search/Adapter/TestAdapter.php +++ b/Search/Adapter/TestAdapter.php @@ -23,6 +23,7 @@ class TestAdapter implements AdapterInterface { protected $documents = []; + protected $factory; public function __construct(Factory $factory) diff --git a/Search/Adapter/ZendLuceneAdapter.php b/Search/Adapter/ZendLuceneAdapter.php index 56f8555d..bf1cef85 100644 --- a/Search/Adapter/ZendLuceneAdapter.php +++ b/Search/Adapter/ZendLuceneAdapter.php @@ -33,14 +33,21 @@ class ZendLuceneAdapter implements AdapterInterface { const ID_FIELDNAME = '__id'; + const INDEX_FIELDNAME = '__index'; + const CLASS_TAG = '__class'; + const AGGREGATED_INDEXED_CONTENT = '__content'; const URL_FIELDNAME = '__url'; + const TITLE_FIELDNAME = '__title'; + const LOCALE_FIELDNAME = '__locale'; + const DESCRIPTION_FIELDNAME = '__description'; + const IMAGE_URL = '__image_url'; /** @@ -114,13 +121,13 @@ public function index(Document $document, $indexName) $type = $field->getType(); $value = $field->getValue(); - if ($type === Field::TYPE_NULL) { + if (Field::TYPE_NULL === $type) { continue; } // Zend Lucene does not support "types". We should allow other "types" once they // are properly implemented in at least one other adapter. - if ($type !== Field::TYPE_STRING && $type !== Field::TYPE_ARRAY) { + if (Field::TYPE_STRING !== $type && Field::TYPE_ARRAY !== $type) { throw new \InvalidArgumentException( sprintf( 'Search field type "%s" is not known. Known types are: %s', diff --git a/Search/AdapterInterface.php b/Search/AdapterInterface.php index 885eb9c7..a4bdd78b 100644 --- a/Search/AdapterInterface.php +++ b/Search/AdapterInterface.php @@ -63,9 +63,6 @@ public function getStatus(); */ public function listIndexes(); - /** - * {@inheritdoc} - */ public function flush(array $indexNames); /** diff --git a/Search/Decorator/LocalizationDecorator.php b/Search/Decorator/LocalizationDecorator.php index d74816d7..e6ef9be3 100644 --- a/Search/Decorator/LocalizationDecorator.php +++ b/Search/Decorator/LocalizationDecorator.php @@ -86,7 +86,7 @@ public function isVariant($indexName, $decoratedIndexName, array $options = []) */ private function removeLocale($decoratedIndexName) { - if (preg_match('/(.*)(-.*-i18n)/', $decoratedIndexName, $matches) === 0) { + if (0 === preg_match('/(.*)(-.*-i18n)/', $decoratedIndexName, $matches)) { return $decoratedIndexName; } diff --git a/Search/Decorator/PrefixDecorator.php b/Search/Decorator/PrefixDecorator.php index 594fc7b3..5526526b 100644 --- a/Search/Decorator/PrefixDecorator.php +++ b/Search/Decorator/PrefixDecorator.php @@ -82,7 +82,7 @@ public function isVariant($indexName, $decoratedIndexName, array $options = []) */ private function removePrefix($decoratedIndexName) { - if (strpos($decoratedIndexName, $this->prefix . '_') === 0) { + if (0 === strpos($decoratedIndexName, $this->prefix . '_')) { $decoratedIndexName = substr($decoratedIndexName, strlen($this->prefix) + 1); return $decoratedIndexName; diff --git a/Search/Event/HitEvent.php b/Search/Event/HitEvent.php index b6f2b0a1..6058e373 100644 --- a/Search/Event/HitEvent.php +++ b/Search/Event/HitEvent.php @@ -18,6 +18,7 @@ class HitEvent extends Event { protected $hit; + protected $metadata; public function __construct(QueryHit $hit, ClassMetadata $metadata) diff --git a/Search/ExpressionLanguage/MassiveSearchExpressionLanguage.php b/Search/ExpressionLanguage/MassiveSearchExpressionLanguage.php index f17d6452..76f489d1 100644 --- a/Search/ExpressionLanguage/MassiveSearchExpressionLanguage.php +++ b/Search/ExpressionLanguage/MassiveSearchExpressionLanguage.php @@ -69,7 +69,7 @@ function ($elements, $expression) { throw new \Exception('Map function does not support compilation'); }, function (array $values, $elements, $expression) { - if (count($elements) === 0) { + if (0 === count($elements)) { return []; } diff --git a/Search/Metadata/Driver/XmlDriver.php b/Search/Metadata/Driver/XmlDriver.php index 1c1a925d..7ec96eeb 100644 --- a/Search/Metadata/Driver/XmlDriver.php +++ b/Search/Metadata/Driver/XmlDriver.php @@ -64,7 +64,7 @@ public function loadMetadataFromFile(\ReflectionClass $class, $file) )); } - if (count($xml->children()) == 0) { + if (0 == count($xml->children())) { throw new \InvalidArgumentException(sprintf('No mapping in file "%s"', $file)); } diff --git a/Search/Metadata/Provider/DefaultProvider.php b/Search/Metadata/Provider/DefaultProvider.php index e7c98896..99b9c172 100644 --- a/Search/Metadata/Provider/DefaultProvider.php +++ b/Search/Metadata/Provider/DefaultProvider.php @@ -13,7 +13,6 @@ use Massive\Bundle\SearchBundle\Search\Document; use Massive\Bundle\SearchBundle\Search\Metadata\ProviderInterface; -use Metadata\MetadataFactory; use Metadata\MetadataFactoryInterface; /** diff --git a/Search/ObjectToDocumentConverter.php b/Search/ObjectToDocumentConverter.php index 85d720f1..67a52434 100644 --- a/Search/ObjectToDocumentConverter.php +++ b/Search/ObjectToDocumentConverter.php @@ -153,7 +153,7 @@ private function populateDocument($document, $object, $fieldMapping, $prefix = ' $mapping ); - if ($mapping['type'] == 'complex') { + if ('complex' == $mapping['type']) { if (!isset($mapping['mapping'])) { throw new \InvalidArgumentException( sprintf( @@ -185,7 +185,7 @@ private function populateDocument($document, $object, $fieldMapping, $prefix = ' $type = $mapping['type']; $value = $this->fieldEvaluator->getValue($object, $mapping['field']); - if ($type !== Field::TYPE_STRING && $type !== Field::TYPE_ARRAY) { + if (Field::TYPE_STRING !== $type && Field::TYPE_ARRAY !== $type) { $value = $this->converterManager->convert($value, $type); if (is_null($value)) { @@ -197,7 +197,7 @@ private function populateDocument($document, $object, $fieldMapping, $prefix = ' } } - if ($value !== null && false === is_scalar($value) && false === is_array($value)) { + if (null !== $value && false === is_scalar($value) && false === is_array($value)) { throw new \InvalidArgumentException( sprintf( 'Search field "%s" resolved to not supported type "%s". Only scalar (single) or array values can be indexed.', @@ -207,7 +207,7 @@ private function populateDocument($document, $object, $fieldMapping, $prefix = ' ); } - if ($mapping['type'] !== 'complex') { + if ('complex' !== $mapping['type']) { $document->addField( $this->factory->createField( $prefix . $fieldName, diff --git a/Search/QueryHit.php b/Search/QueryHit.php index 8446ba81..204ec9a0 100644 --- a/Search/QueryHit.php +++ b/Search/QueryHit.php @@ -17,7 +17,9 @@ class QueryHit implements \JsonSerializable { protected $document; + protected $score; + protected $id; /** diff --git a/Search/SearchEvents.php b/Search/SearchEvents.php index 18af169c..e9257098 100644 --- a/Search/SearchEvents.php +++ b/Search/SearchEvents.php @@ -17,9 +17,14 @@ class SearchEvents { const SEARCH = 'massive_search.search'; + const HIT = 'massive_search.hit'; + const PRE_INDEX = 'massive_search.pre_index'; + const INDEX_REBUILD = 'massive_search.index_rebuild'; + const INDEX = 'massive_search.index'; + const DEINDEX = 'massive_search.deindex'; } diff --git a/Search/SearchQuery.php b/Search/SearchQuery.php index 7c0ff245..48f94ac2 100644 --- a/Search/SearchQuery.php +++ b/Search/SearchQuery.php @@ -18,6 +18,7 @@ class SearchQuery { // constants for search order const SORT_ASC = 'asc'; + const SORT_DESC = 'desc'; /** diff --git a/Tests/Resources/TestBundle/EntityDist/Car.php b/Tests/Resources/TestBundle/EntityDist/Car.php index 731589d0..3801c3d5 100644 --- a/Tests/Resources/TestBundle/EntityDist/Car.php +++ b/Tests/Resources/TestBundle/EntityDist/Car.php @@ -14,10 +14,16 @@ class Car { public $id; + public $title; + public $body; + public $numberOfWheels; + public $cost; + public $date; + public $image; } diff --git a/Tests/Resources/TestBundle/EntityDist/Contact.php b/Tests/Resources/TestBundle/EntityDist/Contact.php index 2e515caf..370d140a 100644 --- a/Tests/Resources/TestBundle/EntityDist/Contact.php +++ b/Tests/Resources/TestBundle/EntityDist/Contact.php @@ -14,7 +14,10 @@ class Contact { public $id; + public $title; + public $emails; + public $addresses; } diff --git a/Tests/Resources/TestBundle/EventSubscriber/TestSubscriber.php b/Tests/Resources/TestBundle/EventSubscriber/TestSubscriber.php index 3d42e4bb..2e68b6d2 100644 --- a/Tests/Resources/TestBundle/EventSubscriber/TestSubscriber.php +++ b/Tests/Resources/TestBundle/EventSubscriber/TestSubscriber.php @@ -19,10 +19,13 @@ class TestSubscriber implements EventSubscriberInterface { public $hitDocument; + public $documentReflection; + public $nbHits = 0; public $preIndexDocument; + public $preIndexMetadata; public static function getSubscribedEvents() diff --git a/Tests/Resources/TestBundle/Product.php b/Tests/Resources/TestBundle/Product.php index cbdbae3d..88e66e87 100644 --- a/Tests/Resources/TestBundle/Product.php +++ b/Tests/Resources/TestBundle/Product.php @@ -14,11 +14,17 @@ class Product { public $id; + public $title; + public $body; + public $date; + public $url; + public $locale; + public $image; public function getId() diff --git a/Tests/Unit/Search/Metadata/ClassMetadataTest.php b/Tests/Unit/Search/Metadata/ClassMetadataTest.php index c8f11566..0616558b 100644 --- a/Tests/Unit/Search/Metadata/ClassMetadataTest.php +++ b/Tests/Unit/Search/Metadata/ClassMetadataTest.php @@ -33,7 +33,7 @@ public function setUp() } /** - * @expectedException InvalidArgumentException + * @expectedException \InvalidArgumentException * @expectedExceptionMessage Context name "foo_context" has already been registered */ public function testAddIndexExisting() diff --git a/Tests/Unit/Search/Metadata/FieldEvaluatorTest.php b/Tests/Unit/Search/Metadata/FieldEvaluatorTest.php index c831a412..0d67db8a 100644 --- a/Tests/Unit/Search/Metadata/FieldEvaluatorTest.php +++ b/Tests/Unit/Search/Metadata/FieldEvaluatorTest.php @@ -19,7 +19,6 @@ use Massive\Bundle\SearchBundle\Search\ObjectToDocumentConverter; use Massive\Bundle\SearchBundle\Tests\Resources\TestBundle\Product; use Prophecy\Argument; -use Symfony\Component\ExpressionLanguage\ExpressionLanguage; class FieldEvaluatorTest extends \PHPUnit_Framework_TestCase { diff --git a/Tests/Unit/Search/ReIndex/Provider/DoctrineOrmProviderTest.php b/Tests/Unit/Search/ReIndex/Provider/DoctrineOrmProviderTest.php index 8ad8b43c..c2b0c97c 100644 --- a/Tests/Unit/Search/ReIndex/Provider/DoctrineOrmProviderTest.php +++ b/Tests/Unit/Search/ReIndex/Provider/DoctrineOrmProviderTest.php @@ -16,7 +16,6 @@ use Doctrine\ORM\EntityManagerInterface; use Doctrine\ORM\EntityRepository; use Doctrine\ORM\Mapping\ClassMetadata as OrmClassMetadata; -use Doctrine\ORM\Query; use Doctrine\ORM\QueryBuilder; use Massive\Bundle\SearchBundle\Search\Metadata\ClassMetadata as SearchClassMetadata; use Massive\Bundle\SearchBundle\Search\Reindex\Provider\DoctrineOrmProvider; diff --git a/Tests/Unit/Search/SearchManagerTest.php b/Tests/Unit/Search/SearchManagerTest.php index dd929dd7..d7b3a5ec 100644 --- a/Tests/Unit/Search/SearchManagerTest.php +++ b/Tests/Unit/Search/SearchManagerTest.php @@ -121,7 +121,7 @@ public function testIndexNonObject() } /** - * @expectedException Massive\Bundle\SearchBundle\Search\Exception\MetadataNotFoundException + * @expectedException \Massive\Bundle\SearchBundle\Search\Exception\MetadataNotFoundException * @expectedExceptionMessage There is no search mapping */ public function testIndexNoMetadata() diff --git a/Tests/travis.php.ini b/Tests/travis.php.ini index 92a5ffdc..8a15b626 100644 --- a/Tests/travis.php.ini +++ b/Tests/travis.php.ini @@ -1 +1 @@ -memory_limit = 2048M +memory_limit = 4096M From 1c11f17e640421046a5535f79e45ca864dd79017 Mon Sep 17 00:00:00 2001 From: Pascal Date: Tue, 17 Apr 2018 16:08:06 +0200 Subject: [PATCH 3/5] Updated Elastic Search dev-Dependency (#115) Fixes #114 --- CHANGELOG.md | 3 ++- composer.json | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 1039070c..fe1fb7e5 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,8 +2,9 @@ CHANGELOG ========= * dev-master + * ENHANCEMENT #114 Updated elasticsearch dependency * ENHANCEMENT #111 Increased php memory_limit and fixed elasticsearch-installation for travis - + * 0.16.2 (2017-06-16) * HOTFIX #3406 (Sulu) Modified ElasticSearchAdapter search function, removed size paramter once limit is empty diff --git a/composer.json b/composer.json index b0532fe3..47a26f38 100644 --- a/composer.json +++ b/composer.json @@ -18,7 +18,7 @@ "zendframework/zend-stdlib": "2.3.1 as 2.0.0rc5", "zendframework/zendsearch": "2.*@dev", - "elasticsearch/elasticsearch": "^2.1", + "elasticsearch/elasticsearch": "^2.1||^6.0", "symfony-cmf/testing": "^1.3", "symfony/symfony": "~2.7||~3.0", "matthiasnoback/symfony-dependency-injection-test": "0.7.*", From 4e48a1002666d808449e047c973ad6ae8629d954 Mon Sep 17 00:00:00 2001 From: Pierre du Plessis Date: Mon, 28 May 2018 13:54:45 +0200 Subject: [PATCH 4/5] Update queryBuilder with result of custom repository method --- Search/Reindex/Provider/DoctrineOrmProvider.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Search/Reindex/Provider/DoctrineOrmProvider.php b/Search/Reindex/Provider/DoctrineOrmProvider.php index 7ab46e96..97a66071 100644 --- a/Search/Reindex/Provider/DoctrineOrmProvider.php +++ b/Search/Reindex/Provider/DoctrineOrmProvider.php @@ -94,6 +94,8 @@ public function provide($classFqn, $offset, $maxResults) return $this->sliceEntities($offset, $maxResults); } + + $queryBuilder = $result; } $queryBuilder->setFirstResult($offset); From df8a58c5f1f2e2e7b4a28a16781a1a18b9e401f1 Mon Sep 17 00:00:00 2001 From: Pierre du Plessis Date: Mon, 28 May 2018 14:08:55 +0200 Subject: [PATCH 5/5] Remove whitespace --- Search/Reindex/Provider/DoctrineOrmProvider.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Search/Reindex/Provider/DoctrineOrmProvider.php b/Search/Reindex/Provider/DoctrineOrmProvider.php index 97a66071..53181246 100644 --- a/Search/Reindex/Provider/DoctrineOrmProvider.php +++ b/Search/Reindex/Provider/DoctrineOrmProvider.php @@ -94,7 +94,7 @@ public function provide($classFqn, $offset, $maxResults) return $this->sliceEntities($offset, $maxResults); } - + $queryBuilder = $result; }