Completed
Push — EZP-31644 ( 2e0a1e...93bb44 )
by
unknown
19:12
created

CreateIndexCommand::execute()   B

Complexity

Conditions 5
Paths 2

Size

Total Lines 58

Duplication

Lines 13
Ratio 22.41 %

Importance

Changes 0
Metric Value
cc 5
nc 2
nop 2
dl 13
loc 58
rs 8.6052
c 0
b 0
f 0

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
/**
4
 * This file is part of the eZ Publish Kernel package.
5
 *
6
 * @copyright Copyright (C) eZ Systems AS. All rights reserved.
7
 * @license For full copyright and license information view LICENSE file distributed with this source code.
8
 */
9
namespace eZ\Bundle\EzPublishLegacySearchEngineBundle\Command;
10
11
use Symfony\Bundle\FrameworkBundle\Command\ContainerAwareCommand;
12
use Symfony\Component\Console\Helper\ProgressHelper;
13
use Symfony\Component\Console\Input\InputInterface;
14
use Symfony\Component\Console\Output\OutputInterface;
15
use Symfony\Component\Console\Input\InputArgument;
16
use eZ\Publish\SPI\Persistence\Content;
17
use eZ\Publish\SPI\Persistence\Content\ContentInfo;
18
use eZ\Publish\Core\Persistence\Database\DatabaseHandler;
19
use eZ\Publish\Core\Base\Exceptions\NotFoundException;
20
use eZ\Publish\Core\Search\Legacy\Content\Handler as SearchHandler;
21
use RuntimeException;
22
use PDO;
23
24
/**
25
 * @deprecated since 6.7, use ezplatform:reindex command instead.
26
 *
27
 * Console command ezplatform:create_sql_search_index indexes content objects for legacy search
28
 * engine.
29
 */
30
class CreateIndexCommand extends ContainerAwareCommand
31
{
32
    /**
33
     * @var \eZ\Publish\Core\Search\Legacy\Content\Handler
34
     */
35
    private $searchHandler;
36
37
    /**
38
     * @var \eZ\Publish\SPI\Persistence\Handler
39
     */
40
    private $persistenceHandler;
41
42
    /**
43
     * @var \eZ\Publish\Core\Persistence\Database\DatabaseHandler
44
     */
45
    private $databaseHandler;
46
47
    /**
48
     * @var \Psr\Log\LoggerInterface
49
     */
50
    private $logger;
51
52
    /**
53
     * Initialize objects required by {@see execute()}.
54
     *
55
     * @param InputInterface $input
56
     * @param OutputInterface $output
57
     */
58
    public function initialize(InputInterface $input, OutputInterface $output)
59
    {
60
        parent::initialize($input, $output);
61
        $this->logger = $this->getContainer()->get('logger');
62
        $this->searchHandler = $this->getContainer()->get('ezpublish.spi.search');
63
        $this->persistenceHandler = $this->getContainer()->get('ezpublish.api.persistence_handler');
64
        $this->databaseHandler = $this->getContainer()->get('ezpublish.connection');
65
66
        if (!$this->searchHandler instanceof SearchHandler) {
67
            throw new RuntimeException(
68
                'Expected to find Legacy Search Engine but found something else.' .
69
                "Did you forget to configure the repository with 'legacy' search engine?"
70
            );
71
        }
72
    }
73
74
    /**
75
     * {@inheritdoc}
76
     */
77
    protected function configure()
78
    {
79
        $this
80
            ->setName('ezplatform:create_sql_search_index')
81
            ->setDescription('Indexes the configured database for the legacy search engine')
82
            ->addArgument('bulk_count', InputArgument::OPTIONAL, 'Number of Content objects indexed at once', 5)
83
            ->setHelp(
84
                <<<EOT
85
The command <info>%command.name%</info> indexes content objects for the legacy search engine.
86
EOT
87
            );
88
    }
89
90
    /**
91
     * {@inheritdoc}
92
     */
93
    protected function execute(InputInterface $input, OutputInterface $output)
94
    {
95
        @trigger_error(
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
96
            sprintf('%s is deprecated since 6.7. Use ezplatform:reindex command instead', $this->getName()),
97
            E_USER_DEPRECATED
98
        );
99
100
        $bulkCount = $input->getArgument('bulk_count');
101
        // Indexing Content
102
        $totalCount = $this->getContentObjectsTotalCount(
103
            $this->databaseHandler, ContentInfo::STATUS_PUBLISHED
104
        );
105
106
        $query = $this->databaseHandler->createSelectQuery();
107
        $query->select('id', 'current_version')
108
            ->from('ezcontentobject')
109
            ->where($query->expr->eq('status', ContentInfo::STATUS_PUBLISHED));
110
111
        $stmt = $query->prepare();
112
        $stmt->execute();
113
114
        $this->searchHandler->purgeIndex();
115
116
        $output->writeln('Indexing Content...');
117
118
        /* @var \Symfony\Component\Console\Helper\ProgressHelper $progress */
119
        $progress = $this->getHelperSet()->get('progress');
120
        $progress->start($output, $totalCount);
121
        $i = 0;
122
        do {
123
            $contentObjects = [];
124 View Code Duplication
            for ($k = 0; $k <= $bulkCount; ++$k) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
125
                if (!$row = $stmt->fetch(PDO::FETCH_ASSOC)) {
126
                    break;
127
                }
128
                try {
129
                    $contentObjects[] = $this->persistenceHandler->contentHandler()->load(
130
                        $row['id'],
131
                        $row['current_version']
132
                    );
133
                } catch (NotFoundException $e) {
134
                    $this->logWarning($output, $progress, "Could not load current version of Content with id ${row['id']}, so skipped for indexing. Full exception: " . $e->getMessage());
135
                }
136
            }
137
138
            $this->searchHandler->bulkIndex(
139
                $contentObjects,
140
                function (Content $content, NotFoundException $e) use ($output, $progress) {
141
                    $this->logWarning($output, $progress, 'Content with id ' . $content->versionInfo->id . ' has missing data, so skipped for indexing. Full exception: ' . $e->getMessage()
142
                    );
143
                }
144
            );
145
146
            $progress->advance($k);
147
        } while (($i += $bulkCount) < $totalCount);
148
149
        $progress->finish();
150
    }
151
152
    /**
153
     * Get content objects total count.
154
     *
155
     * @param \eZ\Publish\Core\Persistence\Database\DatabaseHandler $databaseHandler
156
     * @param int $contentObjectStatus ContentInfo constant
157
     *
158
     * @return int
159
     */
160
    private function getContentObjectsTotalCount(DatabaseHandler $databaseHandler, $contentObjectStatus)
161
    {
162
        $query = $databaseHandler->createSelectQuery();
163
        $query->select('count(id)')
164
            ->from('ezcontentobject')
165
            ->where($query->expr->eq('status', $contentObjectStatus));
166
        $stmt = $query->prepare();
167
        $stmt->execute();
168
        $totalCount = $stmt->fetchColumn();
169
170
        return $totalCount;
171
    }
172
173
    /**
174
     * Log warning while progress helper is running.
175
     *
176
     * @param \Symfony\Component\Console\Output\OutputInterface $output
177
     * @param \Symfony\Component\Console\Helper\ProgressHelper $progress
178
     * @param $message
179
     */
180
    private function logWarning(OutputInterface $output, ProgressHelper $progress, $message)
181
    {
182
        $progress->clear();
183
        // get rid of padding (side effect of displaying progress bar)
184
        $output->write("\r");
185
        $this->logger->warning($message);
186
        $progress->display();
187
    }
188
}
189