Passed
Push — master ( f63716...615686 )
by Timo
11:21 queued 06:56
created

AbstractModuleController   A

Complexity

Total Complexity 27

Size/Duplication

Total Lines 222
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 12

Test Coverage

Coverage 0%

Importance

Changes 0
Metric Value
wmc 27
lcom 1
cbo 12
dl 0
loc 222
ccs 0
cts 119
cp 0
rs 10
c 0
b 0
f 0

7 Methods

Rating   Name   Duplication   Size   Complexity  
B initializeAction() 0 22 4
B initializeView() 0 24 5
A generateCoreSelectorMenuUsingPageTree() 0 13 4
B generateCoreSelectorMenu() 0 38 5
A switchCoreAction() 0 10 1
B initializeSelectedSolrCoreConnection() 0 21 6
A initializeFirstAvailableSolrCoreConnection() 0 9 2
1
<?php
2
namespace ApacheSolrForTypo3\Solr\Controller\Backend\Search;
3
4
/***************************************************************
5
 *  Copyright notice
6
 *
7
 *  (c) 2010-2017 dkd Internet Service GmbH <[email protected]>
8
 *  All rights reserved
9
 *
10
 *  This script is part of the TYPO3 project. The TYPO3 project is
11
 *  free software; you can redistribute it and/or modify
12
 *  it under the terms of the GNU General Public License as published by
13
 *  the Free Software Foundation; either version 2 of the License, or
14
 *  (at your option) any later version.
15
 *
16
 *  The GNU General Public License can be found at
17
 *  http://www.gnu.org/copyleft/gpl.html.
18
 *
19
 *  This script is distributed in the hope that it will be useful,
20
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
21
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
22
 *  GNU General Public License for more details.
23
 *
24
 *  This copyright notice MUST APPEAR in all copies of the script!
25
 ***************************************************************/
26
27
use ApacheSolrForTypo3\Solr\ConnectionManager;
28
use ApacheSolrForTypo3\Solr\Domain\Site\SiteRepository;
29
use ApacheSolrForTypo3\Solr\Site;
30
use ApacheSolrForTypo3\Solr\SolrService as SolrCoreConnection;
31
use ApacheSolrForTypo3\Solr\System\Mvc\Backend\Component\Exception\InvalidViewObjectNameException;
32
use ApacheSolrForTypo3\Solr\System\Mvc\Backend\Service\ModuleDataStorageService;
33
use ApacheSolrForTypo3\Solr\Utility\StringUtility;
34
use TYPO3\CMS\Backend\Template\Components\Menu\Menu;
35
use TYPO3\CMS\Backend\Utility\BackendUtility;
36
use TYPO3\CMS\Backend\View\BackendTemplateView;
37
use TYPO3\CMS\Core\Authentication\BackendUserAuthentication;
38
use TYPO3\CMS\Core\Messaging\AbstractMessage;
39
use TYPO3\CMS\Core\Utility\GeneralUtility;
40
use TYPO3\CMS\Extbase\Mvc\Controller\ActionController;
41
use TYPO3\CMS\Extbase\Mvc\View\NotFoundView;
42
use TYPO3\CMS\Extbase\Mvc\View\ViewInterface;
43
use TYPO3\CMS\Extbase\Utility\LocalizationUtility;
44
45
/**
46
 * Abstract Module
47
 *
48
 * @property BackendTemplateView $view
49
 */
50
abstract class AbstractModuleController extends ActionController
51
{
52
    /**
53
     * Backend Template Container
54
     *
55
     * @var string
56
     */
57
    protected $defaultViewObjectName = BackendTemplateView::class;
58
59
    /**
60
     * In the pagetree selected page UID
61
     *
62
     * @var int
63
     */
64
    protected $selectedPageUID;
65
66
    /**
67
     * @var Site
68
     */
69
    protected $selectedSite;
70
71
    /**
72
     * @var SolrCoreConnection
73
     */
74
    protected $selectedSolrCoreConnection;
75
76
    /**
77
     * @var Menu
78
     */
79
    protected $coreSelectorMenu = null;
80
81
    /**
82
     * @var ConnectionManager
83
     */
84
    protected $solrConnectionManager = null;
85
86
    /**
87
     * @var ModuleDataStorageService
88
     */
89
    protected $moduleDataStorageService = null;
90
91
    /**
92
     * Initializes the controller and sets needed vars.
93
     */
94
    protected function initializeAction()
95
    {
96
        parent::initializeAction();
97
        $this->configurationManager = GeneralUtility::makeInstance(ConnectionManager::class);
98
        $this->moduleDataStorageService = GeneralUtility::makeInstance(ModuleDataStorageService::class);
99
100
        $this->selectedPageUID = (int)GeneralUtility::_GP('id');
101
        if ($this->request->hasArgument('id')) {
102
            $this->selectedPageUID = (int)$this->request->getArgument('id');
103
        }
104
105
        if ($this->selectedPageUID < 1) {
106
            return;
107
        }
108
109
        try {
110
            $siteRepository = GeneralUtility::makeInstance(SiteRepository::class);
111
            $this->selectedSite = $siteRepository->getSiteByPageId($this->selectedPageUID);
112
        } catch (\InvalidArgumentException $exception) {
113
            return;
114
        }
115
    }
116
117
    /**
118
     * Set up the doc header properly here
119
     *
120
     * @param ViewInterface $view
121
     * @return void
122
     */
123
    protected function initializeView(ViewInterface $view)
124
    {
125
        parent::initializeView($view);
126
        $this->view->assign('pageUID', $this->selectedPageUID);
127
        if ($view instanceof NotFoundView || $this->selectedPageUID < 1) {
128
            return;
129
        }
130
        $this->view->getModuleTemplate()->addJavaScriptCode('mainJsFunctions', '
131
                top.fsMod.recentIds["searchbackend"] = ' . (int)$this->selectedPageUID . ';'
132
        );
133
        if (null === $this->selectedSite) {
134
            return;
135
        }
136
137
        /* @var BackendUserAuthentication $beUser */
138
        $beUser = $GLOBALS['BE_USER'];
139
        $permissionClause = $beUser->getPagePermsClause(1);
140
        $pageRecord = BackendUtility::readPageAccess($this->selectedSite->getRootPageId(), $permissionClause);
141
142
        if (false === $pageRecord) {
143
            throw new \InvalidArgumentException(vsprintf('There is something wrong with permissions for page "%s" for backend user "%s".', [$this->selectedSite->getRootPageId(), $beUser->user['username']]), 1496146317);
144
        }
145
        $this->view->getModuleTemplate()->getDocHeaderComponent()->setMetaInformation($pageRecord);
146
    }
147
148
    /**
149
     * Generates selector menu in backends doc header using selected page from page tree.
150
     *
151
     * @param string|null $uriToRedirectTo
152
     */
153
    public function generateCoreSelectorMenuUsingPageTree(string $uriToRedirectTo = null)
154
    {
155
        if ($this->selectedPageUID < 1 || null === $this->selectedSite) {
156
            return;
157
        }
158
159
        if ($this->view instanceof NotFoundView) {
160
            $this->initializeSelectedSolrCoreConnection();
161
            return;
162
        }
163
164
        $this->generateCoreSelectorMenu($this->selectedSite, $uriToRedirectTo);
165
    }
166
167
    /**
168
     * Generates Core selector Menu for given Site.
169
     *
170
     * @param Site $site
171
     * @param string|null $uriToRedirectTo
172
     * @throws InvalidViewObjectNameException
173
     */
174
    protected function generateCoreSelectorMenu(Site $site, string $uriToRedirectTo = null)
175
    {
176
        if (!$this->view instanceof BackendTemplateView) {
177
            throw new InvalidViewObjectNameException(vsprintf(
178
                'The controller "%s" must use BackendTemplateView to be able to generate menu for backends docheader. \
179
                Please set `protected $defaultViewObjectName = BackendTemplateView::class;` field in your controller.',
180
                [static::class]), 1493804179);
181
        }
182
        $this->view->getModuleTemplate()->setFlashMessageQueue($this->controllerContext->getFlashMessageQueue());
183
184
        $this->coreSelectorMenu = $this->view->getModuleTemplate()->getDocHeaderComponent()->getMenuRegistry()->makeMenu();
185
        $this->coreSelectorMenu->setIdentifier('component_core_selector_menu');
186
187
        if (!isset($uriToRedirectTo)) {
188
            $uriToRedirectTo = $this->uriBuilder->reset()->uriFor();
189
        }
190
191
        $this->initializeSelectedSolrCoreConnection();
192
        $cores = $this->solrConnectionManager->getConnectionsBySite($site);
193
        foreach ($cores as $core) {
194
            $menuItem = $this->coreSelectorMenu->makeMenuItem();
195
            $menuItem->setTitle($core->getPath());
196
            $uri = $this->uriBuilder->reset()->uriFor('switchCore',
197
                [
198
                    'corePath' => $core->getPath(),
199
                    'uriToRedirectTo' => $uriToRedirectTo
200
                ]
201
            );
202
            $menuItem->setHref($uri);
203
204
            if ($core->getPath() == $this->selectedSolrCoreConnection->getPath()) {
205
                $menuItem->setActive(true);
206
            }
207
            $this->coreSelectorMenu->addMenuItem($menuItem);
208
        }
209
210
        $this->view->getModuleTemplate()->getDocHeaderComponent()->getMenuRegistry()->addMenu($this->coreSelectorMenu);
211
    }
212
213
    /**
214
     * Switches used core.
215
     *
216
     * Note: Does not check availability of core in site. All this stuff is done in the generation step.
217
     *
218
     * @param string $corePath
219
     * @param string $uriToRedirectTo
220
     */
221
    public function switchCoreAction(string $corePath, string $uriToRedirectTo)
222
    {
223
        $moduleData = $this->moduleDataStorageService->loadModuleData();
224
        $moduleData->setCore($corePath);
225
226
        $this->moduleDataStorageService->persistModuleData($moduleData);
227
        $message = LocalizationUtility::translate('coreselector_switched_successfully', 'solr', [$corePath]);
228
        $this->addFlashMessage($message);
229
        $this->redirectToUri($uriToRedirectTo);
230
    }
231
232
    /**
233
     * Initializes the solr core connection considerately to the components state.
234
     * Uses and persists default core connection if persisted core in Site does not exist.
235
     *
236
     */
237
    private function initializeSelectedSolrCoreConnection()
238
    {
239
        $moduleData = $this->moduleDataStorageService->loadModuleData();
240
241
        $solrCoreConnections = $this->solrConnectionManager->getConnectionsBySite($this->selectedSite);
242
        $currentSolrCorePath = $moduleData->getCore();
243
        if (empty($currentSolrCorePath)) {
244
            $this->initializeFirstAvailableSolrCoreConnection($solrCoreConnections, $moduleData);
245
            return;
246
        }
247
        foreach ($solrCoreConnections as $solrCoreConnection) {
248
            if ($solrCoreConnection->getPath() == $currentSolrCorePath) {
249
                $this->selectedSolrCoreConnection = $solrCoreConnection;
250
            }
251
        }
252
        if (!$this->selectedSolrCoreConnection instanceof SolrCoreConnection && count($solrCoreConnections) > 0) {
253
            $this->initializeFirstAvailableSolrCoreConnection($solrCoreConnections, $moduleData);
254
            $message = LocalizationUtility::translate('coreselector_switched_to_default_core', 'solr', [$currentSolrCorePath, $this->selectedSite->getLabel(), $this->selectedSolrCoreConnection->getPath()]);
255
            $this->addFlashMessage($message, '', AbstractMessage::NOTICE);
256
        }
257
    }
258
259
    /**
260
     * @param SolrCoreConnection[] $solrCoreConnections
261
     */
262
    private function initializeFirstAvailableSolrCoreConnection(array $solrCoreConnections, $moduleData)
263
    {
264
        if (empty($solrCoreConnections)) {
265
            return;
266
        }
267
        $this->selectedSolrCoreConnection = $solrCoreConnections[0];
268
        $moduleData->setCore($this->selectedSolrCoreConnection->getPath());
269
        $this->moduleDataStorageService->persistModuleData($moduleData);
270
    }
271
}
272