![]() Server : Apache System : Linux server2.corals.io 4.18.0-348.2.1.el8_5.x86_64 #1 SMP Mon Nov 15 09:17:08 EST 2021 x86_64 User : corals ( 1002) PHP Version : 7.4.33 Disable Function : exec,passthru,shell_exec,system Directory : /home/corals/cartforge.co/vendor/magento/module-search/Model/ResourceModel/ |
<?php /** * Copyright © Magento, Inc. All rights reserved. * See COPYING.txt for license details. */ namespace Magento\Search\Model\ResourceModel; use Magento\Framework\DB\Helper\Mysql\Fulltext; use Magento\Framework\Exception\LocalizedException; use Magento\Framework\Model\ResourceModel\Db\AbstractDb; use Magento\Store\Model\Store; use Magento\Store\Model\StoreManagerInterface; /** * Synonym Reader resource model */ class SynonymReader extends AbstractDb { /** * @var \Magento\Framework\DB\Helper\Mysql\Fulltext $fullTextSelect */ private $fullTextSelect; /** * @var StoreManagerInterface */ protected $storeManager; /** * @param \Magento\Framework\Model\ResourceModel\Db\Context $context * @param \Magento\Store\Model\StoreManagerInterface $storeManager * @param \Magento\Framework\DB\Helper\Mysql\Fulltext $fulltext * @param string $connectionName */ public function __construct( \Magento\Framework\Model\ResourceModel\Db\Context $context, \Magento\Store\Model\StoreManagerInterface $storeManager, \Magento\Framework\DB\Helper\Mysql\Fulltext $fulltext, $connectionName = null ) { parent::__construct($context, $connectionName); $this->fullTextSelect = $fulltext; $this->storeManager = $storeManager; } /** * Custom load model: Get data by user query phrase * * @param \Magento\Search\Model\SynonymReader $object * @param string $phrase * @return $this */ public function loadByPhrase(\Magento\Search\Model\SynonymReader $object, $phrase) { $rows = $this->queryByPhrase($phrase !== null ? strtolower($phrase) : ''); $synsPerScope = $this->getSynRowsPerScope($rows); if (!empty($synsPerScope[\Magento\Store\Model\ScopeInterface::SCOPE_STORES])) { $object->setData($synsPerScope[\Magento\Store\Model\ScopeInterface::SCOPE_STORES]); } elseif (!empty($synsPerScope[\Magento\Store\Model\ScopeInterface::SCOPE_WEBSITES])) { $object->setData($synsPerScope[\Magento\Store\Model\ScopeInterface::SCOPE_WEBSITES]); } else { $object->setData($synsPerScope[\Magento\Framework\App\Config\ScopeConfigInterface::SCOPE_TYPE_DEFAULT]); } $this->_afterLoad($object); return $this; } /** * Get all synonyms as an array * * @param int $storeViewId * @return array * @throws LocalizedException */ public function getAllSynonymsForStoreViewId(int $storeViewId): array { $connection = $this->getConnection(); $storeIdField = $connection ->quoteIdentifier(sprintf('%s.%s', $this->getMainTable(), 'store_id')); $select = $connection ->select() ->from($this->getMainTable(), 'synonyms') ->where($storeIdField . ' IN (?)', [Store::DEFAULT_STORE_ID, $storeViewId]); return $connection->fetchCol($select); } /** * Init resource data * * @return void */ protected function _construct() { $this->_init('search_synonyms', 'group_id'); } /** * A helper function to query by phrase and get results * * @param string $phrase * @return array */ private function queryByPhrase($phrase) { $phrase = $this->fullTextSelect->removeSpecialCharacters($phrase); $matchQuery = $this->fullTextSelect->getMatchQuery( ['synonyms' => 'synonyms'], $this->escapePhrase($phrase), Fulltext::FULLTEXT_MODE_BOOLEAN ); $query = $this->getConnection()->select()->from( $this->getMainTable() )->where($matchQuery); return $this->getConnection()->fetchAll($query); } /** * Cut trailing plus or minus sign, and @ symbol, using of which causes InnoDB to report a syntax error. * * @see https://dev.mysql.com/doc/refman/5.7/en/fulltext-boolean.html * @param string $phrase * @return string */ private function escapePhrase(string $phrase): string { return preg_replace('/@+|[@+-]+$|[<>]/', '', $phrase); } /** * A private helper function to retrieve matching synonym groups per scope * * @param array $rows * @return array */ private function getSynRowsPerScope($rows) { $synRowsForStoreView = []; $synRowsForWebsite = []; $synRowsForDefault = []; // The synonyms configured for current store view gets highest priority. Second highest is current website // scope. If there were no store view and website specific synonyms then at last 'default' (All store views) // will be considered. foreach ($rows as $row) { if ($this->isSynRowForStoreView($row)) { // Check for current store view $synRowsForStoreView[] = $row; } elseif (empty($synRowsForStoreView) && $this->isSynRowForWebsite($row)) { // Check for current website $synRowsForWebsite[] = $row; } elseif (empty($synRowsForStoreView) && empty($synRowsForWebsite) && $this->isSynRowForDefaultScope($row)) { // Check for all store views (i.e. global/default config) $synRowsForDefault[] = $row; } } $synsPerScope[\Magento\Store\Model\ScopeInterface::SCOPE_STORES] = $synRowsForStoreView; $synsPerScope[\Magento\Store\Model\ScopeInterface::SCOPE_WEBSITES] = $synRowsForWebsite; $synsPerScope[\Magento\Framework\App\Config\ScopeConfigInterface::SCOPE_TYPE_DEFAULT] = $synRowsForDefault; return $synsPerScope; } /** * A helper method to check if the synonym group row is for the current store view * * @param array $row * @return bool */ private function isSynRowForStoreView($row) { $storeViewId = $this->storeManager->getStore()->getId(); return ($row['store_id'] === $storeViewId); } /** * A helper method to check if the synonym group row is for the current website * * @param array $row * @return bool */ private function isSynRowForWebsite($row) { $websiteId = $this->storeManager->getStore()->getWebsiteId(); return (($row['website_id'] === $websiteId) && ($row['store_id'] == 0)); } /** * A helper method to check if the synonym group row is for all store views (default or global scope) * * @param array $row * @return bool */ private function isSynRowForDefaultScope($row) { return (($row['website_id'] == 0) && ($row['store_id'] == 0)); } }