Skip to content
Snippets Groups Projects
Commit 844375b9 authored by Stefan Galinski's avatar Stefan Galinski :video_game:
Browse files

Merge branch 'task_RemovePageBrowser' into 'master'

[BUGFIX] Fix totally broken page browser implementation, Cleanup code / Remove...

See merge request !33
parents 3c94d831 2a89e47f
No related branches found
No related tags found
1 merge request!33[BUGFIX] Fix totally broken page browser implementation, Cleanup code / Remove...
Showing
with 384 additions and 537 deletions
......@@ -76,8 +76,15 @@ class MigrateNewsCommandController extends Command {
->addArgument('copyPageId', InputArgument::REQUIRED, 'The page id of the template that should be copied')
->addArgument('categoryPid', InputArgument::REQUIRED, 'The page id of the category page')
->addArgument('year', InputArgument::OPTIONAL, 'Only news from that year will be migrated', 2015)
->addArgument('languageMapAsJson', InputArgument::OPTIONAL, 'A json, mapping language ids (old => new). this is needed if the sys_language_uids have changed', '{"3":1,"1":0,"2":2,"0":3}')
->addArgument('categoryMapAsJson', InputArgument::OPTIONAL, 'A json, mapping sys_category ids (old => new).', '{"2":17,"3":16,"4":15,"5":14,"6":14,"7":15,"8":16,"9":17}')
->addArgument(
'languageMapAsJson', InputArgument::OPTIONAL,
'A json, mapping language ids (old => new). this is needed if the sys_language_uids have changed',
'{"3":1,"1":0,"2":2,"0":3}'
)
->addArgument(
'categoryMapAsJson', InputArgument::OPTIONAL, 'A json, mapping sys_category ids (old => new).',
'{"2":17,"3":16,"4":15,"5":14,"6":14,"7":15,"8":16,"9":17}'
)
->addArgument('pId', InputArgument::OPTIONAL, 'Only news from that pid will be migrated', 52);
}
......@@ -86,11 +93,8 @@ class MigrateNewsCommandController extends Command {
*
* @param InputInterface $input
* @param OutputInterface $output
* @return int|void
* @throws IllegalObjectTypeException
* @throws UnknownObjectException
* @return void
* @throws \JsonException
* @throws \TYPO3\CMS\Extbase\Object\Exception
*/
public function execute(InputInterface $input, OutputInterface $output) {
$objectManager = GeneralUtility::makeInstance(ObjectManager::class);
......@@ -108,7 +112,9 @@ class MigrateNewsCommandController extends Command {
$this->languageMap = json_decode($languageMapAsJson, TRUE, 512, JSON_THROW_ON_ERROR);
$this->categoryMap = json_decode($categoryMapAsJson, TRUE, 512, JSON_THROW_ON_ERROR);
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('tx_news_domain_model_news');
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable(
'tx_news_domain_model_news'
);
$queryBuilder->getRestrictions()->removeByType(StartTimeRestriction::class);
$rows = $queryBuilder->select('*')
->from('tx_news_domain_model_news')
......@@ -180,13 +186,21 @@ class MigrateNewsCommandController extends Command {
$persistenceManager->persistAll();
// update content element from the new page
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('tt_content');
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable(
'tt_content'
);
$queryBuilder->getRestrictions()->removeAll();
$queryBuilder->update('tt_content')
->where(
$queryBuilder->expr()->andX(
$queryBuilder->expr()->eq('pid', $queryBuilder->createNamedParameter($newPageId, Connection::PARAM_INT)),
$queryBuilder->expr()->eq('sys_language_uid', $queryBuilder->createNamedParameter($this->languageMap[(int) $row['sys_language_uid']], \PDO::PARAM_INT))
$queryBuilder->expr()->eq(
'pid', $queryBuilder->createNamedParameter($newPageId, Connection::PARAM_INT)
),
$queryBuilder->expr()->eq(
'sys_language_uid', $queryBuilder->createNamedParameter(
$this->languageMap[(int) $row['sys_language_uid']], \PDO::PARAM_INT
)
)
)
)
->set('bodytext', $row['bodytext'], TRUE)
......@@ -207,15 +221,21 @@ class MigrateNewsCommandController extends Command {
*/
private function getMatchingFile(array $row) {
// match old page id with old file reference id
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('sys_file_reference_news_migration');
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable(
'sys_file_reference_news_migration'
);
$queryBuilder->getRestrictions()->removeAll();
$fileReferenceResult = $queryBuilder->select('uid', 'uid_local')
->from('sys_file_reference_news_migration')
->where(
$queryBuilder->expr()->andX(
$queryBuilder->expr()->eq('tablenames', $queryBuilder->createNamedParameter('tx_news_domain_model_news')),
$queryBuilder->expr()->eq(
'tablenames', $queryBuilder->createNamedParameter('tx_news_domain_model_news')
),
$queryBuilder->expr()->eq('fieldname', $queryBuilder->createNamedParameter('fal_media')),
$queryBuilder->expr()->eq('uid_foreign', $queryBuilder->createNamedParameter($row['uid'], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'uid_foreign', $queryBuilder->createNamedParameter($row['uid'], Connection::PARAM_INT)
)
)
)
->execute()->fetch();
......@@ -223,12 +243,16 @@ class MigrateNewsCommandController extends Command {
return NULL;
}
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('sys_file_news_migration');
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable(
'sys_file_news_migration'
);
$queryBuilder->getRestrictions()->removeAll();
$fileResult = $queryBuilder->select('identifier')
->from('sys_file_news_migration')
->where(
$queryBuilder->expr()->eq('uid', $queryBuilder->createNamedParameter($fileReferenceResult['uid_local'], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'uid', $queryBuilder->createNamedParameter($fileReferenceResult['uid_local'], Connection::PARAM_INT)
)
)
->execute()->fetch();
if (!$fileResult) {
......@@ -251,12 +275,16 @@ class MigrateNewsCommandController extends Command {
* @param array $row
*/
private function setMatchingTag(array $row) {
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('sys_category_record_mm_news_migration');
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable(
'sys_category_record_mm_news_migration'
);
$queryBuilder->getRestrictions()->removeAll();
$mmRows = $queryBuilder->select('uid_local', 'sorting_foreign')
->from('sys_category_record_mm_news_migration')
->where(
$queryBuilder->expr()->eq('uid_foreign', $queryBuilder->createNamedParameter($row['uid'], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'uid_foreign', $queryBuilder->createNamedParameter($row['uid'], Connection::PARAM_INT)
)
)
->execute()->fetchAll();
foreach ($mmRows as $mmRow) {
......@@ -293,22 +321,34 @@ class MigrateNewsCommandController extends Command {
// if its the new default, there is no l18n_parent
if ((int) $this->languageMap[(int) $row['sys_language_uid'] === 0]) {
$queryBuilder->where(
$queryBuilder->expr()->eq('uid', $queryBuilder->createNamedParameter($originalContentElement[0], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'uid', $queryBuilder->createNamedParameter($originalContentElement[0], Connection::PARAM_INT)
)
);
} else {
$queryBuilder->where(
$queryBuilder->expr()->eq('l18n_parent', $queryBuilder->createNamedParameter($originalContentElement[0], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'l18n_parent',
$queryBuilder->createNamedParameter($originalContentElement[0], Connection::PARAM_INT)
)
);
}
// look up the correct language id, if they have changed
if (isset($this->languageMap[(int) $row['sys_language_uid']])) {
$queryBuilder->andWhere(
$queryBuilder->expr()->eq('sys_language_uid', $queryBuilder->createNamedParameter($this->languageMap[(int) $row['sys_language_uid']], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'sys_language_uid', $queryBuilder->createNamedParameter(
$this->languageMap[(int) $row['sys_language_uid']], Connection::PARAM_INT
)
)
);
} else {
$queryBuilder->andWhere(
$queryBuilder->expr()->eq('sys_language_uid', $queryBuilder->createNamedParameter($row['sys_language_uid'], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'sys_language_uid',
$queryBuilder->createNamedParameter($row['sys_language_uid'], Connection::PARAM_INT)
)
);
}
$queryBuilder->set('bodytext', $row['bodytext'], TRUE)
......@@ -321,16 +361,24 @@ class MigrateNewsCommandController extends Command {
$result = $queryBuilder->select('title', 'subtitle')
->from('pages')
->where(
$queryBuilder->expr()->eq('uid', $queryBuilder->createNamedParameter($parentId, Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'uid', $queryBuilder->createNamedParameter($parentId, Connection::PARAM_INT)
)
)
->execute()->fetch();
if ($result) {
$queryBuilder->where(
$queryBuilder->expr()->eq('sys_language_uid', $queryBuilder->createNamedParameter($this->languageMap[0], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'sys_language_uid',
$queryBuilder->createNamedParameter($this->languageMap[0], Connection::PARAM_INT)
)
);
$queryBuilder->update('pages')
->andWhere(
$queryBuilder->expr()->eq('l10n_parent', $queryBuilder->createNamedParameter($this->languageMap[0], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'l10n_parent',
$queryBuilder->createNamedParameter($this->languageMap[0], Connection::PARAM_INT)
)
);
$queryBuilder->set('title', $result['title'], TRUE)
->set('subtitle', $result['subtitle'], TRUE)
......@@ -341,7 +389,9 @@ class MigrateNewsCommandController extends Command {
$newTitle = date('Y-m-d', $row['datetime']) . ' - ' . $row['title'];
$queryBuilder->update('pages')
->where(
$queryBuilder->expr()->eq('uid', $queryBuilder->createNamedParameter($parentId, Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'uid', $queryBuilder->createNamedParameter($parentId, Connection::PARAM_INT)
)
)
->set('title', $newTitle, TRUE)
->set('subtitle', $row['title'], TRUE)
......@@ -351,17 +401,28 @@ class MigrateNewsCommandController extends Command {
} else {
$queryBuilder->update('pages')
->where(
$queryBuilder->expr()->eq('l10n_parent', $queryBuilder->createNamedParameter($parentId, Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'l10n_parent', $queryBuilder->createNamedParameter($parentId, Connection::PARAM_INT)
)
);
// finally translate the page title if necessary
if (isset($this->languageMap[(int) $row['sys_language_uid']]) && $this->languageMap[(int) $row['sys_language_uid']] > 0) {
// translate the page title if necessary
if (isset($this->languageMap[(int) $row['sys_language_uid']]) &&
$this->languageMap[(int) $row['sys_language_uid']] > 0
) {
$queryBuilder->andWhere(
$queryBuilder->expr()->eq('sys_language_uid', $queryBuilder->createNamedParameter($this->languageMap[(int) $row['sys_language_uid']], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'sys_language_uid', $queryBuilder->createNamedParameter(
$this->languageMap[(int) $row['sys_language_uid']], Connection::PARAM_INT
)
)
);
} else {
$queryBuilder->andWhere(
$queryBuilder->expr()->eq('sys_language_uid', $queryBuilder->createNamedParameter($row['sys_language_uid'], Connection::PARAM_INT))
$queryBuilder->expr()->eq(
'sys_language_uid',
$queryBuilder->createNamedParameter($row['sys_language_uid'], Connection::PARAM_INT)
)
);
}
$queryBuilder->set('title', date('Y-m-d', $row['datetime']) . ' - ' . $row['title'], TRUE)
......
......@@ -74,15 +74,15 @@ abstract class AbstractController extends ActionController {
/**
* Error Handler
*
* @throws \RuntimeException
* @return void
* @throws \RuntimeException
*/
public function errorAction() {
throw new RuntimeException(parent::errorAction());
}
/**
* Returns the meta data of the given news.
* Returns the metadata of the given news.
*
* @param News $news
* @param Category $category
......@@ -146,7 +146,9 @@ abstract class AbstractController extends ActionController {
if ($singleNewsImage) {
$singleNewsImageObject = $singleNewsImage;
$originalResource = $singleNewsImage->getOriginalResource();
$singleNewsImage = $originalResource->getPublicUrl();
if ($originalResource) {
$singleNewsImage = $originalResource->getPublicUrl();
}
if ($singleNewsImage) {
$singleNewsImage = $GLOBALS['TSFE']->absRefPrefix . $singleNewsImage;
......@@ -183,7 +185,9 @@ abstract class AbstractController extends ActionController {
if ($teaserImage) {
$teaserImageObject = $teaserImage;
$originalResource = $teaserImage->getOriginalResource();
$teaserImage = $originalResource->getPublicUrl();
if ($originalResource) {
$teaserImage = $originalResource->getPublicUrl();
}
if ($teaserImage) {
$teaserImage = $GLOBALS['TSFE']->absRefPrefix . $teaserImage;
......@@ -200,10 +204,10 @@ abstract class AbstractController extends ActionController {
* Calculate the pagination offset
*
* @param int $currentPageBrowserPage
* @param int $newsLimitPerPage
* @param int|null $newsLimitPerPage
* @return int
*/
protected function calculatePaginationOffset(int $currentPageBrowserPage, int $newsLimitPerPage = NULL){
protected function calculatePaginationOffset(int $currentPageBrowserPage, int $newsLimitPerPage = NULL) {
$offset = 0;
$newsPerPage = $newsLimitPerPage ?? (int) $this->settings['newsLimitPerPage'];
if ($currentPageBrowserPage > 0 && $newsPerPage > 0) {
......
......@@ -27,7 +27,6 @@ namespace SGalinski\SgNews\Controller;
***************************************************************/
use SGalinski\SgNews\Utility\BackendNewsUtility;
use TYPO3\CMS\Backend\Clipboard\Clipboard;
use TYPO3\CMS\Backend\Routing\UriBuilder;
use TYPO3\CMS\Backend\Template\Components\ButtonBar;
use TYPO3\CMS\Backend\Template\Components\DocHeaderComponent;
......@@ -66,21 +65,6 @@ class BackendController extends ActionController {
*/
private $rootPageUid = 0;
/**
* Command array on the form [tablename][uid][command] = value.
* This array may get additional data set internally based on clipboard commands send in CB var!
*
* @var array
*/
private $command;
/**
* Clipboard command array. May trigger changes in "cmd"
*
* @var array
*/
private $clipboardCommandArray;
/**
* Currently selected language
*
......@@ -95,17 +79,6 @@ class BackendController extends ActionController {
*/
private $docHeaderComponent;
/**
* Initialize action for all actions
*
* @throws \InvalidArgumentException
*/
public function initializeAction() {
$this->command = GeneralUtility::_GP('cmd');
$this->clipboardCommandArray = GeneralUtility::_GP('CB');
$this->initClipboard();
}
/**
* Initializes the view before invoking an action method.
*
......@@ -234,8 +207,6 @@ class BackendController extends ActionController {
)
->setSetVariables([]);
$buttonBar->addButton($shortcutButton, ButtonBar::BUTTON_POSITION_RIGHT);
$this->docHeaderComponent->getButtonBar();
}
/**
......@@ -265,36 +236,4 @@ class BackendController extends ActionController {
}
$this->docHeaderComponent->getMenuRegistry()->addMenu($languageMenu);
}
/**
* Clipboard pasting and deleting.
*
* @throws \InvalidArgumentException
*/
public function initClipboard() {
if (\is_array($this->clipboardCommandArray)) {
$clipObj = GeneralUtility::makeInstance(Clipboard::class);
$clipObj->initializeClipboard();
if ($this->clipboardCommandArray['paste']) {
$clipObj->setCurrentPad($this->clipboardCommandArray['pad']);
$this->command = $clipObj->makePasteCmdArray(
$this->clipboardCommandArray['paste'],
$this->command,
$this->clipboardCommandArray['update'] ?? NULL
);
}
if ($this->clipboardCommandArray['delete']) {
$clipObj->setCurrentPad($this->clipboardCommandArray['pad']);
$this->command = $clipObj->makeDeleteCmdArray($this->command);
}
if ($this->clipboardCommandArray['el']) {
$this->clipboardCommandArray['setP'] = 'normal';
$clipObj->setCmd($this->clipboardCommandArray);
$clipObj->cleanCurrent();
$clipObj->endClipboard();
}
}
}
}
......@@ -115,7 +115,6 @@ class LatestController extends AbstractController {
}
}
$this->view->assign('newsMetaData', $newsMetaData);
}
......
......@@ -58,14 +58,36 @@ class OverviewController extends AbstractController {
*/
protected $newsRepository;
/**
* @param CategoryRepository $categoryRepository
*/
public function injectCategoryRepository(CategoryRepository $categoryRepository
) {
$this->categoryRepository = $categoryRepository;
}
/**
* @param NewsRepository $newsRepository
*/
public function injectNewsRepository(NewsRepository $newsRepository) {
$this->newsRepository = $newsRepository;
}
/**
* @param TagRepository $tagRepository
*/
public function injectTagRepository(TagRepository $tagRepository) {
$this->tagRepository = $tagRepository;
}
/**
* Initialize the overviewAction to set the currentPageBrowserPage parameter
*
* @throws \TYPO3\CMS\Extbase\Mvc\Exception\InvalidArgumentNameException
*/
public function initializeOverviewAction(){
public function initializeOverviewAction() {
$currentPageBrowserPage = (int) GeneralUtility::_GP('tx_sgnews_pagebrowser')['currentPage'];
if($currentPageBrowserPage > 0){
if ($currentPageBrowserPage > 0) {
$this->request->setArgument('currentPageBrowserPage', $currentPageBrowserPage);
}
}
......@@ -81,7 +103,7 @@ class OverviewController extends AbstractController {
* @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
* @throws \TYPO3\CMS\Extbase\Configuration\Exception\InvalidConfigurationTypeException
*/
public function overviewAction(array $newsFilter = [], $currentPageBrowserPage = 0) {
public function overviewAction(array $newsFilter = [], int $currentPageBrowserPage = 0) {
switch ((int) $this->settings['groupBy']) {
case 1:
$this->overviewWithCategories([], [], $newsFilter, $currentPageBrowserPage);
......@@ -98,10 +120,9 @@ class OverviewController extends AbstractController {
/**
* Highlights the best fitting news in the meta data of the page
*
* @param array $categoryIds
* @param array $tagIds
* @param array|null $categoryIds
* @param array|null $tagIds
* @throws \TYPO3\CMS\Extbase\Persistence\Exception\InvalidQueryException
* @throws \InvalidArgumentException
*/
protected function highlightBestFitNews(array $categoryIds = NULL, array $tagIds = NULL) {
$startTime = (int) $this->settings['starttime'];
......@@ -143,7 +164,7 @@ class OverviewController extends AbstractController {
* @throws \TYPO3\CMS\Extbase\Configuration\Exception\InvalidConfigurationTypeException
*/
protected function overviewWithCategories(
array $newsByCategory = [], array $allNews = [], array $newsFilter = [], $currentPageBrowserPage = 0
array $newsByCategory = [], array $allNews = [], array $newsFilter = [], int $currentPageBrowserPage = 0
) {
$newsLimitPerCategory = (int) $this->settings['newsLimit'];
$this->categoryRepository->setDefaultOrderings(['sorting' => Query::ORDER_ASCENDING]);
......@@ -192,7 +213,7 @@ class OverviewController extends AbstractController {
$categoriesById = [];
$newsMetaData = [];
foreach ($categories as $category) {
/** @var $category Category */
/** @var Category $category */
$categoryId = $category->getUid();
$categoryIdsForSelect = [$categoryId];
$categoryIds[] = $category->getUid();
......@@ -213,13 +234,13 @@ class OverviewController extends AbstractController {
}
foreach ($categoryIdsForSelect as $categoryIdsForSelectId) {
$news = $this->newsRepository->findAllSortedNewsByCategories(
[$categoryIdsForSelectId], $newsLimitPerCategory, $offset, $sortBy, $tagIds, $startTime, $endTime, $sortDirection
[$categoryIdsForSelectId], $newsLimitPerCategory, $offset, $sortBy, $tagIds, $startTime, $endTime,
$sortDirection
);
$newsMetaData[$categoryIdsForSelectId] = [];
foreach ($news as $newsEntry) {
/** @var News $newsEntry */
$categoryId = $newsEntry->getPid();
$category = $categoriesById[$categoryIdsForSelectId];
if (!$category) {
// Category isn't visible.
......@@ -239,9 +260,9 @@ class OverviewController extends AbstractController {
continue;
}
/** @var $category Category */
/** @var Category $category */
if (isset($newsByCategory[$categoryId])) {
/** @var $category Category */
/** @var Category $category */
$newsByCategory[$categoryId]['newsMetaData'] =
array_merge($newsByCategory[$categoryId]['newsMetaData'], $newsMetaData[$categoryId], $newsFilter);
} else {
......@@ -325,7 +346,7 @@ class OverviewController extends AbstractController {
* @throws \TYPO3\CMS\Extbase\Configuration\Exception\InvalidConfigurationTypeException
*/
protected function overviewWithTags(
array $newsByTag = [], array $allNews = [], array $newsFilter = [], $currentPageBrowserPage = 0
array $newsByTag = [], array $allNews = [], array $newsFilter = [], int $currentPageBrowserPage = 0
) {
$startTime = (int) $this->settings['starttime'];
$endTime = (int) $this->settings['endtime'];
......@@ -426,6 +447,7 @@ class OverviewController extends AbstractController {
if (!isset($categoriesById[$categoryId])) {
$categoriesById[$categoryId] = $this->categoryRepository->findByUid($categoryId);
}
/** @var Category $category */
$category = $categoriesById[$categoryId];
if (!$category) {
// Category isn't visible.
......@@ -473,35 +495,13 @@ class OverviewController extends AbstractController {
*
* @throws \TYPO3\CMS\Extbase\Mvc\Exception\InvalidArgumentNameException
*/
public function initializeOverviewWithoutCategoriesAction(){
public function initializeOverviewWithoutCategoriesAction() {
$currentPageBrowserPage = (int) GeneralUtility::_GP('tx_sgnews_pagebrowser')['currentPage'];
if($currentPageBrowserPage > 0){
if ($currentPageBrowserPage > 0) {
$this->request->setArgument('currentPageBrowserPage', $currentPageBrowserPage);
}
}
/**
* @param CategoryRepository $categoryRepository
*/
public function injectCategoryRepository(CategoryRepository $categoryRepository
) {
$this->categoryRepository = $categoryRepository;
}
/**
* @param NewsRepository $newsRepository
*/
public function injectNewsRepository(NewsRepository $newsRepository) {
$this->newsRepository = $newsRepository;
}
/**
* @param TagRepository $tagRepository
*/
public function injectTagRepository(TagRepository $tagRepository) {
$this->tagRepository = $tagRepository;
}
/**
* Renders the news in a paginated list
*
......@@ -515,7 +515,7 @@ class OverviewController extends AbstractController {
* @throws \TYPO3\CMS\Extbase\Configuration\Exception\InvalidConfigurationTypeException
*/
protected function overviewWithoutCategoriesAction(
array $newsMetaData = [], array $newsFilter = NULL, $currentPageBrowserPage = 0
array $newsMetaData = [], array $newsFilter = NULL, int $currentPageBrowserPage = 0
) {
// remember selection of the filter values, if any
$selectedTag = $this->tagRepository->findByUid((int) $newsFilter['tag']);
......@@ -544,7 +544,9 @@ class OverviewController extends AbstractController {
$categoriesById[$category->getUid()] = $category;
$categoryIds[] = $category->getUid();
if ($category->_getProperty('_languageUid') > 0) {
$originalLangCategory = $this->categoryRepository->findOriginalLanguageById($category->getUid());
$originalLangCategory = $this->categoryRepository->findOriginalLanguageById(
$category->getUid()
);
if ($originalLangCategory) {
$categoryIds[] = $originalLangCategory->getUid();
$categoriesById[$originalLangCategory->getUid()] = $originalLangCategory;
......
<?php
namespace SGalinski\SgNews\Controller;
/***************************************************************
* Copyright notice
*
* (c) sgalinski Internet Services (https://www.sgalinski.de)
*
* All rights reserved
*
* This script is part of the TYPO3 project. The TYPO3 project is
* free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 3 of the License, or
* (at your option) any later version.
*
* The GNU General Public License can be found at
* http://www.gnu.org/copyleft/gpl.html.
*
* This script is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* This copyright notice MUST APPEAR in all copies of the script!
***************************************************************/
use TYPO3\CMS\Extbase\Mvc\Controller\ActionController;
/**
* Controller that handles the page browser.
*/
class PageBrowserController extends ActionController {
/**
* @var string
*/
protected $pageParameterName = '';
/**
* @var int
*/
protected $numberOfPages = 0;
/**
* @var int
*/
protected $currentPage = 0;
/**
* @var int
*/
protected $pagesBefore = 0;
/**
* @var int
*/
protected $pagesAfter = 0;
/**
* @var bool
*/
protected $enableMorePages = FALSE;
/**
* @var bool
*/
protected $enableLessPages = FALSE;
/**
* Renders the index view.
*
* @param int $currentPage
* @return void
*/
public function indexAction($currentPage = 0) {
$this->currentPage = (int) $currentPage;
$this->initializeConfiguration();
$this->addDataToView();
}
/**
* Initializes the configuration.
*
* @return void
*/
protected function initializeConfiguration() {
$this->pageParameterName = 'tx_sgnews_pagebrowser[currentPage]';
$this->numberOfPages = (int) $this->settings['numberOfPages'];
$this->pagesBefore = (int) $this->settings['pagesBefore'];
$this->pagesAfter = (int) $this->settings['pagesAfter'];
$this->enableMorePages = (bool) $this->settings['enableMorePages'];
$this->enableLessPages = (bool) $this->settings['enableLessPages'];
}
/**
* Adds the necessary data to the view.
*
* @return void
*/
protected function addDataToView() {
if ($this->numberOfPages <= 1) {
$this->view = NULL;
return;
}
$pageLinks = [];
$start = \max($this->currentPage - $this->pagesBefore, 0);
$end = \min($this->numberOfPages, $this->currentPage + $this->pagesAfter + 1);
for ($i = $start; $i < $end; $i++) {
$pageLinks[] = [
'number' => $i + 1,
'link' => $this->getPageLink($i),
'isCurrentPage' => $i === $this->currentPage,
];
}
$this->view->assignMultiple(
[
'enableLessPages' => $this->enableLessPages,
'enableMorePages' => $this->enableMorePages,
'previousLink' => $this->getPageLink($this->currentPage - 1),
'nextLink' => $this->getPageLink($this->currentPage + 1),
'enableLessPagesLink' => $this->getPageLink($this->currentPage - $this->pagesBefore - 1),
'enableMorePagesLink' => $this->getPageLink($this->currentPage + $this->pagesAfter + 1),
'pageLinks' => $pageLinks,
'prevPageExist' => $this->currentPage > 0,
'showLessPages' => ($this->currentPage - $this->pagesBefore) > 0,
'showNextPages' => ($this->currentPage + $this->pagesAfter + 1) < $this->numberOfPages,
'nextPageExist' => $this->currentPage < ($this->numberOfPages - 1),
]
);
}
/**
* Generates page link. Keeps all current URL parameters except for cHash and tx_pagebrowse_pi1[page].
*
* @param int $page Page number starting from 1
* @return string
*/
protected function getPageLink($page): string {
return $this->uriBuilder->reset()->setAddQueryString(TRUE)
->uriFor('index', ['currentPage' => $page,]);
}
}
......@@ -27,7 +27,6 @@ namespace SGalinski\SgNews\ViewHelpers\Backend;
***************************************************************/
use SGalinski\SgNews\ViewHelpers\AbstractViewHelper;
use TYPO3\CMS\Backend\Clipboard\Clipboard;
use TYPO3\CMS\Backend\Utility\BackendUtility;
use TYPO3\CMS\Core\Imaging\Icon;
use TYPO3\CMS\Core\Imaging\IconFactory;
......@@ -49,7 +48,6 @@ class ControlViewHelper extends AbstractViewHelper {
$this->registerArgument('table', 'string', 'The table to control', TRUE);
$this->registerArgument('row', 'mixed', 'The row of the record', TRUE);
$this->registerArgument('sortingData', 'array', 'The sorting data', FALSE, []);
$this->registerArgument('clipboard', 'bool', 'Use the clipboard', FALSE, FALSE);
}
/**
......@@ -63,7 +61,6 @@ class ControlViewHelper extends AbstractViewHelper {
$table = $this->arguments['table'];
$row = $this->arguments['row'];
$sortingData = $this->arguments['sortingData'];
$clipboard = $this->arguments['clipboard'];
if (!is_array($row)) {
$row = BackendUtility::getRecord($table, $row->getUid());
}
......@@ -84,15 +81,8 @@ class ControlViewHelper extends AbstractViewHelper {
}
$out = $databaseRecordList->makeControl($table, $row);
if ($clipboard) {
$databaseRecordList->MOD_SETTINGS['clipBoard'] = TRUE;
$databaseRecordList->clipObj = GeneralUtility::makeInstance(Clipboard::class);
$databaseRecordList->clipObj->initializeClipboard();
$GLOBALS['SOBE'] = $databaseRecordList;
$out .= $databaseRecordList->makeClip($table, $row);
}
if ($table === 'pages') {
/** @var IconFactory $iconFactory */
$iconFactory = GeneralUtility::makeInstance(IconFactory::class);
$buttonLabel = LocalizationUtility::translate('backend.button.editPageContent', 'SgNews');
$path = '';
......
......@@ -26,9 +26,10 @@ namespace SGalinski\SgNews\ViewHelpers;
* This copyright notice MUST APPEAR in all copies of the script!
***************************************************************/
use TYPO3\CMS\Extbase\Object\ObjectManager;
use TYPO3\CMS\Core\TypoScript\TypoScriptService;
use TYPO3\CMS\Core\Utility\GeneralUtility;
use TYPO3\CMS\Fluid\View\StandaloneView;
use TYPO3Fluid\Fluid\Core\ViewHelper\AbstractViewHelper;
use TYPO3\CMS\Frontend\ContentObject\ContentObjectRenderer;
/**
* View helper that renders a page browser based upon the pagebrowse extension.
......@@ -47,20 +48,6 @@ class PageBrowserViewHelper extends AbstractViewHelper {
*/
protected $escapeOutput = FALSE;
/**
* @var ObjectManager
*/
protected $objectManager;
/**
* Inject the ObjectManager
*
* @param ObjectManager $objectManager
*/
public function injectObjectManager(ObjectManager $objectManager) {
$this->objectManager = $objectManager;
}
/**
* Initialize the ViewHelpers arguments
*/
......@@ -76,13 +63,48 @@ class PageBrowserViewHelper extends AbstractViewHelper {
* @throws \UnexpectedValueException
*/
public function render(): string {
$numberOfPages = $this->arguments['numberOfPages'];
$configuration = $GLOBALS['TSFE']->tmpl->setup['plugin.']['tx_sgnews.']['pagebrowser.'];
$configuration['settings.']['numberOfPages'] = (int) $numberOfPages;
/** @var TypoScriptService $typoScriptService */
$typoScriptService = GeneralUtility::makeInstance(TypoScriptService::class);
$configuration = $typoScriptService->convertTypoScriptArrayToPlainArray(
$GLOBALS['TSFE']->tmpl->setup['plugin.']['tx_sgnews.']
);
$view = GeneralUtility::makeInstance(StandaloneView::class);
$view->setRenderingContext($this->renderingContext);
$view->setTemplateRootPaths($configuration['view']['templateRootPaths']);
$view->setPartialRootPaths($configuration['view']['partialRootPaths']);
$view->setLayoutRootPaths($configuration['view']['layoutRootPaths']);
$view->setTemplate('PageBrowser/Index');
$pageBrowserVars = GeneralUtility::_GP('tx_sgnews_pagebrowser');
if (isset($pageBrowserVars['currentPage']) && (int) $pageBrowserVars['currentPage'] > 0) {
$currentPage = (int) $pageBrowserVars['currentPage'];
} else {
$currentPage = 0;
}
$pageLinks = [];
$start = \max($currentPage - 2, 0);
$end = \min($this->arguments['numberOfPages'], $currentPage + 2);
for ($i = $start; $i < $end; $i++) {
$pageLinks[] = [
'number' => $i + 1,
'page' => $i,
'isCurrentPage' => $i === $currentPage,
];
}
/** @var ContentObjectRenderer $contentObject */
$contentObject = $this->objectManager->get(ContentObjectRenderer::class);
$contentObject->start([]);
return $contentObject->cObjGetSingle('USER', $configuration);
$view->assignMultiple(
[
'enableLessPages' => 1,
'enableMorePages' => 1,
'pageLinks' => $pageLinks,
'currentPage' => $currentPage,
'prevPageExist' => $currentPage > 1,
'showLessPages' => ($currentPage - 1) > 1,
'showNextPages' => ($currentPage + 2) < $this->arguments['numberOfPages'],
'nextPageExist' => $currentPage < $this->arguments['numberOfPages'] - 1,
'numberOfPages' => $this->arguments['numberOfPages']
]
);
return $view->render();
}
}
......@@ -32,7 +32,7 @@
<size>5</size>
<maxitems>99</maxitems>
<foreign_table>pages</foreign_table>
<foreign_table_where>AND doktype = 117 ORDER BY title</foreign_table_where>
<foreign_table_where>AND pages.sys_language_uid IN (-1, 0) AND pages.doktype = 117 ORDER BY pages.title</foreign_table_where>
</config>
</TCEforms>
</settings.categories>
......
......@@ -20,18 +20,4 @@ plugin.tx_sgnews {
# sort direction (DESC / ASC)
sortDirection = DESC
}
pagebrowser.settings {
# Number of page links to show before the current page
pagesBefore = 1
# Number of page links to show before the current page
pagesAfter = 1
# Enables section for "more" pages. This section is shown after links to next pages, normally like three dots (1 2 3 ...). Notice that you can also hide it by emptying corresponding template section.
enableMorePages = 1
# Enables section for "less" pages. This section is shown after links to next pages, normally like three dots (... 1 2 3) Notice that you can also hide it by emptying corresponding template section.
enableLessPages = 1
}
}
......@@ -66,17 +66,14 @@ plugin.tx_sgnews {
view {
templateRootPaths {
0 = {$plugin.tx_sgnews.view.templateRootPath}
1 =
}
partialRootPaths {
0 = {$plugin.tx_sgnews.view.partialRootPath}
1 =
}
layoutRootPaths {
0 = {$plugin.tx_sgnews.view.layoutRootPath}
1 =
}
}
......@@ -121,41 +118,6 @@ plugin.tx_sgnews {
legacy {
enableLegacyFlashMessageHandling = 0
}
pagebrowser = USER
pagebrowser {
userFunc = TYPO3\CMS\Extbase\Core\Bootstrap->run
extensionName = SgNews
pluginName = PageBrowser
vendorName = SGalinski
controller = PageBrowser
action = index
view < plugin.tx_sgnews.view
persistence < plugin.tx_sgnews.persistence
features < plugin.tx_sgnews.features
# cHash can't be generated for pageBrowser call; will cause a 404 error if not set to 0
features.requireCHashArgumentForActionArguments = 0
legacy < plugin.tx_sgnews.legacy
settings {
# Number of page links to show before the current page
pagesBefore = {$plugin.tx_sgnews.pagebrowser.settings.pagesBefore}
# Number of page links to show before the current page
pagesAfter = {$plugin.tx_sgnews.pagebrowser.settings.pagesAfter}
# Enables section for "more" pages. This section is shown after links to next pages, normally like three dots (1 2 3 ...). Notice that you can also hide it by emptying corresponding template section.
enableMorePages = {$plugin.tx_sgnews.pagebrowser.settings.enableMorePages}
# Enables section for "less" pages. This section is shown after links to next pages, normally like three dots (... 1 2 3). Notice that you can also hide it by emptying corresponding template section.
enableLessPages = {$plugin.tx_sgnews.pagebrowser.settings.enableLessPages}
# The number of the pages
numberOfPages = 0
# The current page
currentPage = 0
}
}
}
plugin.tx_sgcomments {
......
......@@ -17,9 +17,12 @@ additional meta information.
## Integration
Before using sg_news, you need to supply your frontend some information on how the extension needs to be integrated into your template.
Before using sg_news, you need to supply your frontend some information on how the extension needs to be integrated into
your template.
As the extension itself provides two new [doktypes](https://docs.typo3.org/typo3cms/CoreApiReference/PageTypes/Index.html), you can simply add a switch case to your Fluid template to provide different rendering paths.
As the extension itself provides two
new [doktypes](https://docs.typo3.org/typo3cms/CoreApiReference/PageTypes/Index.html), you can simply add a switch case
to your Fluid template to provide different rendering paths.
### Example
......@@ -70,24 +73,28 @@ lib.pageTemplate.default {
}
```
In this example we will load the first column for the intro section by default,
and the second column in the backend for the content below that.
In this example we will load the first column for the intro section by default, and the second column in the backend for
the content below that.
The news category (doktype 117) will render by default not the content on the page alone, but also the default category listing.
The news category (doktype 117) will render by default not the content on the page alone, but also the default category
listing.
With our example we don't want the intro section (116) and the default content to be rendered because the extension handles those parts.
With our example we don't want the intro section (116) and the default content to be rendered because the extension
handles those parts.
The single news plugin also needs some additional information so it can get the base content.
By default, it will resolve to the following code if not provided by you:
The single news plugin also needs some additional information so it can get the base content. By default, it will
resolve to the following code if not provided by you:
```TypoScript
lib.mainContent < styles.content.col1
```
### Example integration into your page template
Finally, you need to output the `INTRO` and `CONTENT` variable in your page template:
```HTML
<main>
<!--TYPO3SEARCH_begin-->
<f:if condition="{INTRO}">
......@@ -110,28 +117,28 @@ To enable the author id mapping in TYPO3 9, you need to add this routeEnhancer c
```YAML
routeEnhancers:
NewsByAuthor:
type: Extbase
extension: SgNews
plugin: NewsByAuthor
routes:
- routePath: '/{authorTitle}'
_controller: 'NewsByAuthor::list'
_arguments: { 'authorTitle': authorId }
defaultController: 'NewsByAuthor::list'
aspects:
authorTitle:
type: PersistedAliasMapper
tableName: tx_sgnews_domain_model_author
routeFieldName: path_segment
NewsByAuthor:
type: Extbase
extension: SgNews
plugin: NewsByAuthor
routes:
- routePath: '/{authorTitle}'
_controller: 'NewsByAuthor::list'
_arguments: { 'authorTitle': authorId }
defaultController: 'NewsByAuthor::list'
aspects:
authorTitle:
type: PersistedAliasMapper
tableName: tx_sgnews_domain_model_author
routeFieldName: path_segment
```
### Tags
In addition to categories, multiple tags can be created and specified for each news page.
Tags can be created by adding sys_category records to the root page of the news block (blog).
In order to differentiate each block's tags from the others,
the PageTS value of `TCEFORM.pages.tx_sgnews_tags.PAGE_TSCONFIG_ID`
Tags can be created by adding sys_category records to the root page of the news block (blog). In order to differentiate
each block's tags from the others, the PageTS value of `TCEFORM.pages.tx_sgnews_tags.PAGE_TSCONFIG_ID`
can be set for each of the blocks containing the pid value for the selectable tags.
To make sure that only the correct tags are displayed in the FE, the `plugin.tx_sgnews.settings.tagPid`
......@@ -143,11 +150,13 @@ Add the plugin **News Overview** and optionally the plugin **Latest News** to a
After that you must create sites of type **Category** sites below the blog page level and name them accordingly.
On the next lower page level of each **Category** you can create pages of type **News**.
On these pages you can use all your usual content elements to visualize your news entries belonging to the specific category.
On the next lower page level of each **Category** you can create pages of type **News**. On these pages you can use all
your usual content elements to visualize your news entries belonging to the specific category.
### Plugins
General settings for the plugins can be found in the **Frontend/setup.typoscript** and **Frontend/constants.typoscript** files:
General settings for the plugins can be found in the **Frontend/setup.typoscript** and **Frontend/constants.typoscript**
files:
*setup.typoscript*
......@@ -182,13 +191,16 @@ settings {
This extension comes with several plugins to display and categorize news:
###### News Overview
Provides an overview over all news. Additionally, there is a tab navigation for groups of news.
Plugin options:
- **Group By**: By which aspect should your news be grouped in the tab navigation (none, category, tags)
- **News Limit**: The maximum amount news to be displayed. Further news can be displayed after the user clicks a button.
- **Only news within this page section**: Should only news from subpages be shown, or from all sites in this TYPO3 instance?
- **Group By**: By which aspect should your news be grouped in the tab navigation (none, category, tags)
- **News Limit**: The maximum amount news to be displayed. Further news can be displayed after the user clicks a
button.
- **Only news within this page section**: Should only news from subpages be shown, or from all sites in this TYPO3
instance?
---
......@@ -200,7 +212,8 @@ Plugin options:
- **News Limit per Page**: The maximum amount of news to be shown.
- **Categories**: Here you can select which categories you want to be included (If none are selected, all are shown).
- **Tags**: Here you can select which tags the news entries need to have to be shown here (If none are selected, all are shown).
- **Tags**: Here you can select which tags the news entries need to have to be shown here (If none are selected, all are
shown).
---
......@@ -211,7 +224,9 @@ Provides a new page type **News** in the **Page Module**, that renders the conte
---
###### News Feed
Provides an RSS Feed **news.xml** as a typenum. The typenum is defined in the **Frontend/setup.typoscript** and needs to be included in your TypoScript template:
Provides an RSS Feed **news.xml** as a typenum. The typenum is defined in the **Frontend/setup.typoscript** and needs to
be included in your TypoScript template:
```Typoscript
# news feed as own page type
......@@ -258,7 +273,10 @@ newsFeed {
}
}
```
If you need multiple news feeds with different content, you can duplicate the provided configuration and modify the typenum & parameters like showCategories / showTags:
If you need multiple news feeds with different content, you can duplicate the provided configuration and modify the
typenum & parameters like showCategories / showTags:
```Typoscript
myOtherNewsFeed < newsFeed
myOtherNewsFeed.typeNum = ENTER_YOUR_TYPENUM_HERE
......@@ -266,11 +284,12 @@ myOtherNewsFeed.10.settings.showCategories =
myOtherNewsFeed.10.settings.showTags =
```
---
###### PageBrowser
Automatically adds a pagination to the **News Overview** and **List News** plugins.
You find the settings in the **Fontend/constants.typoscript** configuration file:
Automatically adds a pagination to the **News Overview** and **List News** plugins. You find the settings in the **
Fontend/constants.typoscript** configuration file:
```Typoscript
pagebrowser.settings {
......@@ -292,29 +311,37 @@ pagebrowser.settings {
###### addLike
Automatically adds an AJAX like button to each single news entry.
Make sure that the extension **sg_ajax** is installed, otherwise this feature will be disabled.
If it should be like this, then make sure to remove this button from the sg_news default templates.
Automatically adds an AJAX like button to each single news entry. Make sure that the extension **sg_ajax** is installed,
otherwise this feature will be disabled. If it should be like this, then make sure to remove this button from the
sg_news default templates.
## The Backend Module
After a successful Installation, you have a new module in the "WEB" section of your TYPO3 Backend.
Clicking on it loads the administration panel. Using the drop-down above you can switch between the different languages set up in your TYPO3 installation.
Once you have selected a language, the module will display the news records and tag filter corresponding to that language.
Clicking on it loads the administration panel. Using the drop-down above you can switch between the different languages
set up in your TYPO3 installation. Once you have selected a language, the module will display the news records and tag
filter corresponding to that language.
If you have selected a root-page in the page-tree, the module will display a list of news pages corresponding to this root page, with respect to the current user permissions. Here you can filter the results by Category, Tags or by a search word.
If you have selected a root-page in the page-tree, the module will display a list of news pages corresponding to this
root page, with respect to the current user permissions. Here you can filter the results by Category, Tags or by a
search word.
Selecting a News Category Page in the page-tree, will display the list of news pages in this Category. The same functionality as for the root page, but without the category filter.
Selecting a News Category Page in the page-tree, will display the list of news pages in this Category. The same
functionality as for the root page, but without the category filter.
***Note*** : The search-word filter is language-sensitive.
You can also use the '<img height="20px" width="20px" src="https://camo.githubusercontent.com/cd0d2f12f28169acfbafd1c8bf8f291155f3d210/68747470733a2f2f7261776769742e636f6d2f5459504f332f5459504f332e49636f6e732f6d61737465722f646973742f616374696f6e732f616374696f6e732d646f63756d656e742d6e65772e737667"> Add News Record' and the '<img height="20px" width="20px" src="https://camo.githubusercontent.com/cd0d2f12f28169acfbafd1c8bf8f291155f3d210/68747470733a2f2f7261776769742e636f6d2f5459504f332f5459504f332e49636f6e732f6d61737465722f646973742f616374696f6e732f616374696f6e732d646f63756d656e742d6e65772e737667"> Add News Category' buttons to add News/Cateogry pages under the currelty selected page where available.
You can also use
the '<img height="20px" width="20px" src="https://camo.githubusercontent.com/cd0d2f12f28169acfbafd1c8bf8f291155f3d210/68747470733a2f2f7261776769742e636f6d2f5459504f332f5459504f332e49636f6e732f6d61737465722f646973742f616374696f6e732f616374696f6e732d646f63756d656e742d6e65772e737667">
Add News Record' and
the '<img height="20px" width="20px" src="https://camo.githubusercontent.com/cd0d2f12f28169acfbafd1c8bf8f291155f3d210/68747470733a2f2f7261776769742e636f6d2f5459504f332f5459504f332e49636f6e732f6d61737465722f646973742f616374696f6e732f616374696f6e732d646f63756d656e742d6e65772e737667">
Add News Category' buttons to add News/Cateogry pages under the currelty selected page where available.
### Options for your news list items
For each news item in the paginated result list you have multiple editing/administration options, depending on the logged-in user's permissions.
For each news item in the paginated result list you have multiple editing/administration options, depending on the
logged-in user's permissions.
You can click a list item's title to edit it (language sensitive) or use the menu buttons:
......@@ -348,26 +375,31 @@ You can click a list item's title to edit it (language sensitive) or use the men
<br>
<img height="20px" width="20px" src="https://camo.githubusercontent.com/2ba239d52c48bbcdc9d059a8aeca2eb7eb41a07a/68747470733a2f2f7261776769742e636f6d2f5459504f332f5459504f332e49636f6e732f6d61737465722f646973742f616374696f6e732f616374696f6e732d646f63756d656e742d6f70656e2e737667"> Edit Page Content
You can also handle the localisation of news pages for all the languages in your TYPO3 installation by using the localisation links under each record's title:
You can also handle the localisation of news pages for all the languages in your TYPO3 installation by using the
localisation links under each record's title:
- **full-opacity flag icon** : Edit the existing localisation record
- **half-transparent flag icon with <img height="14px" width="14px" src="https://camo.githubusercontent.com/b10f4d50dc21b152cde15cef5983c139e77b1c34/68747470733a2f2f7261776769742e636f6d2f5459504f332f5459504f332e49636f6e732f6d61737465722f646973742f6f7665726c61792f6f7665726c61792d6e65772e737667"/> overlay** : Create new localisation record
- **half-transparent flag icon
with <img height="14px" width="14px" src="https://camo.githubusercontent.com/b10f4d50dc21b152cde15cef5983c139e77b1c34/68747470733a2f2f7261776769742e636f6d2f5459504f332f5459504f332e49636f6e732f6d61737465722f646973742f6f7665726c61792f6f7665726c61792d6e65772e737667"/>
overlay** : Create new localisation record
***Note*** : The extension also adds a News Module link in the Page Module of News/Category pages
## Migrating tx_news to sg_news
This extension comes with the command controller task **** to migirate tx_news entries to sg_news. The task comes with the following parameters:
This extension comes with the command controller task **** to migirate tx_news entries to sg_news. The task comes with
the following parameters:
- **copyPageId** : You will need a template site, which will be the basis of each new news record. Create your content elements accordingly on this site.
- **copyPageId** : You will need a template site, which will be the basis of each new news record. Create your content
elements accordingly on this site.
- **categoryPid** : This needs to be the category page id, you want your news to be children of.
- **year** : Only news of this year will be migrated
- **languageMapAsJson** : a json string, mapping language ids (old => new). this is needed if the sys_language_uids have changed
- **languageMapAsJson** : a json string, mapping language ids (old => new). this is needed if the sys_language_uids have
changed
- **categoryMapAsJson** : a json string, mapping sys_category ids (old => new).
- **pId** : only news from that pid will be migrated
### Migrating File References
To use your old file references, you need to import your sys_file and sys_file_reference_table as sys_file_news_migration and sys_file_reference
into your database. The Filepaths must not change!
To use your old file references, you need to import your sys_file and sys_file_reference_table as
sys_file_news_migration and sys_file_reference into your database. The Filepaths must not change!
......@@ -87,7 +87,7 @@
</td>
<td nowrap="nowrap" class="col-control">
<f:format.raw>
<sg:backend.control table="pages" row="{singleNews}" clipboard="1" />
<sg:backend.control table="pages" row="{singleNews}" />
</f:format.raw>
</td>
</tr>
......
......@@ -8,9 +8,11 @@
<f:if condition="{prevPageExist}">
<f:then>
<li class="tx-pagebrowse-prev">
<a href="{previousLink}" aria-label="Previous">
<f:variable name="prevPage" value="{currentPage - 1}" />
<f:link.action additionalParams="{tx_sgnews_pagebrowser: {currentPage: prevPage}}"
additionalAttributes="{aria-label: 'Previous'}">
&laquo;
</a>
</f:link.action>
</li>
</f:then>
<f:else>
......@@ -26,9 +28,10 @@
<f:if condition="{enableLessPages} && {showLessPages}">
<li>
<a href="{enableLessPagesLink}">
<f:variable name="lessPage" value="{currentPage - 2}" />
<f:link.action additionalParams="{tx_sgnews_pagebrowser: {currentPage: lessPage}}">
...
</a>
</f:link.action>
</li>
</f:if>
......@@ -46,9 +49,9 @@
</f:then>
<f:else>
<li class="tx-pagebrowse-page">
<a href="{pageLink.link}">
<f:link.action additionalParams="{tx_sgnews_pagebrowser: {currentPage: pageLink.page}}">
{pageLink.number}
</a>
</f:link.action>
</li>
</f:else>
</f:if>
......@@ -56,18 +59,21 @@
<f:if condition="{enableMorePages} && {showNextPages}">
<li>
<a href="{enableMorePagesLink}">
<f:variable name="morePage" value="{currentPage + 2}" />
<f:link.action additionalParams="{tx_sgnews_pagebrowser: {currentPage: morePage}}">
...
</a>
</f:link.action>
</li>
</f:if>
<f:if condition="{nextPageExist}">
<f:then>
<li class="tx-pagebrowse-next">
<a href="{nextLink}" aria-label="Next">
<f:variable name="nextPage" value="{currentPage + 1}" />
<f:link.action additionalParams="{tx_sgnews_pagebrowser: {currentPage: nextPage}}"
additionalAttributes="{aria-label: 'Next'}">
&raquo;
</a>
</f:link.action>
</li>
</f:then>
<f:else>
......
......@@ -10,20 +10,20 @@ export default class ScrollBrowser {
this._element.style.display = 'none';
this._loadingIndicator = this._element.lastElementChild;
if (!this._loadingIndicator) {
return;
return;
}
this.url = document.querySelector('.tx-pagebrowse-next a').getAttribute('href');
this.url = this._element.querySelector('.tx-pagebrowse-next a').getAttribute('href');
window.addEventListener('scroll', this.checkAndLoad.bind(this));
// Initial check
this.checkAndLoad();
}
}
/**
* Checks and loads the next page if required
*/
checkAndLoad() {
checkAndLoad() {
const recordLockedOrNotInPosition = this.lock || !this.checkPosition();
const urlIsInvalid = typeof this.url === 'undefined' || this.url === null || this.url === this.lastUrl;
if (recordLockedOrNotInPosition || urlIsInvalid) {
......@@ -37,9 +37,9 @@ export default class ScrollBrowser {
/**
* Fetches the content of the next page via Ajax
*/
fetchContent() {
fetchContent() {
return new Promise((resolve) => {
const request = new XMLHttpRequest();
const request = new XMLHttpRequest();
request.onreadystatechange = () => {
if (request.readyState === XMLHttpRequest.DONE) {
if (request.status === 200) {
......@@ -53,14 +53,14 @@ export default class ScrollBrowser {
);
request.send();
});
}
}
/**
* Adds fetched DOM nodes to the list
*
* @param {String} response The HTML of the AJAX response
*/
displayNewData(response) {
displayNewData(response) {
const parser = new DOMParser();
const doc = parser.parseFromString(response, 'text/html');
const results = Array.from(doc.querySelectorAll('.tx-sgnews-list'));
......@@ -74,26 +74,27 @@ export default class ScrollBrowser {
if (!resultList) {
resultList = document.querySelector('.tx-sgnews-list');
}
children.forEach((child) => {
resultList.appendChild(child);
});
this._loadingIndicator = resultList.lastElementChild;
if (resultList) {
children.forEach((child) => {
resultList.appendChild(child);
});
this._loadingIndicator = resultList.lastElementChild;
}
});
this.lastUrl = this.url;
this.url = doc.querySelector('.tx-pagebrowse-next a').getAttribute('href');
this.lock = false;
}
}
/**
* Checks the current position of the scrollbar in relation to the position of the load indicator.
*
* @return boolean
*/
checkPosition() {
checkPosition() {
const loadingIndicatorPosition = this._loadingIndicator.getBoundingClientRect();
const windowScrollPosition = window.scrollY;
return (windowScrollPosition > (loadingIndicatorPosition.top - 6000));
}
}
}
# Migration to TYPO3 9
Unfortunately TYPO3 fucked it completely up. There are several issues with translations afterwards that can only be
solved by doing manual work.
## Migrate Tags
All tags must be synchronized with the translated pages as pages_language_overlay was dropped and TYPO3 didn't handled this
properly. If you don't use tags, you are a lucky guy. If you used tags, you can now be lucky. Just execute the
following SQL.
```
# Hole alle Tags von Seiten, welche Übersetzungen haben mit zugehörigem Page-Record der Übersetzung
# UND synchronisiere die neuen Tags für die Übersetzungen
INSERT INTO sys_category_record_mm (uid_local, uid_foreign, tablenames, fieldname, sorting, sorting_foreign)
SELECT sys_category_record_mm.uid_local, pages.uid, 'pages', 'tx_sgnews_tags', sys_category_record_mm.sorting, sys_category_record_mm.sorting_foreign FROM pages, sys_category_record_mm WHERE pages.l10n_parent IN (
SELECT uid_foreign FROM sys_category_record_mm WHERE fieldname = 'tx_sgnews_tags'
) AND sys_category_record_mm.uid_foreign = pages.l10n_parent;
```
## Migrate Images
All images must be resynchronized in all translations as images must always be carefully translated now in ALL records
and not only pages. Unfortunately there is no automatic approach. You must do it on your own. To simplify the process,
you should use mass badge processing offered by TYPO3.
1) Open the list view
2) Open the news category
3) Click on the table and the search icon in the top bar and choose 3 levels
4) All news should be listed for the category (you can also do that for the overview page if all news are grouped below)
5) At the very bottom, choose the higlight and teaser image fields now.
6) Click on the edit icon at the table header for hightlight images
7) Synchronize all images with the provided button and save
8) Do that now also for the teaser images and ALL pagination pages as TYPO3 loads only one page after the other.
# Upgrade from ```8.x.x``` to ```9.x.x```
- Dropped TYPO3 8 support
# Upgrade from ```7.x.x``` to ```8.x.x```
## Migrate the Authors
......@@ -55,6 +59,37 @@ In order for your module bundler to find the ```sgnews``` package, you need to a
}
```
## Version 9 Breaking Changes
## Migration to TYPO3 9
- Dropped TYPO3 8 support
Unfortunately TYPO3 fucked it completely up. There are several issues with translations afterwards that can only be
solved by doing manual work.
### Migrate Tags
All tags must be synchronized with the translated pages as pages_language_overlay was dropped and TYPO3 didn't handled this
properly. If you don't use tags, you are a lucky guy. If you used tags, you can now be lucky. Just execute the
following SQL.
```
# Hole alle Tags von Seiten, welche Übersetzungen haben mit zugehörigem Page-Record der Übersetzung
# UND synchronisiere die neuen Tags für die Übersetzungen
INSERT INTO sys_category_record_mm (uid_local, uid_foreign, tablenames, fieldname, sorting, sorting_foreign)
SELECT sys_category_record_mm.uid_local, pages.uid, 'pages', 'tx_sgnews_tags', sys_category_record_mm.sorting, sys_category_record_mm.sorting_foreign FROM pages, sys_category_record_mm WHERE pages.l10n_parent IN (
SELECT uid_foreign FROM sys_category_record_mm WHERE fieldname = 'tx_sgnews_tags'
) AND sys_category_record_mm.uid_foreign = pages.l10n_parent;
```
### Migrate Images
All images must be resynchronized in all translations as images must always be carefully translated now in ALL records
and not only pages. Unfortunately there is no automatic approach. You must do it on your own. To simplify the process,
you should use mass badge processing offered by TYPO3.
1) Open the list view
2) Open the news category
3) Click on the table and the search icon in the top bar and choose 3 levels
4) All news should be listed for the category (you can also do that for the overview page if all news are grouped below)
5) At the very bottom, choose the higlight and teaser image fields now.
6) Click on the edit icon at the table header for hightlight images
7) Synchronize all images with the provided button and save
8) Do that now also for the teaser images and ALL pagination pages as TYPO3 loads only one page after the other.
{
"name": "sgalinski/sg-news",
"type": "typo3-cms-extension",
"description": "News System",
"homepage": "https://www.sgalinski.de",
"license": [
"GPL-2.0-or-later"
],
"version": "9.3.7",
"support": {
},
"repositories": [
{
"type": "composer",
"url": "https://packages.sgalinski.de/"
}
],
"require": {
"typo3/cms-core": "^9.5.0 || ^10.4.0"
},
"require-dev": {
"roave/security-advisories": "dev-master"
},
"suggest": {
"sgalinski/sg-ajax": "Needed for the like feature",
"sgalinski/sg-comments": "Flexible comments system"
},
"replace": {
"sgalinski/sg_news": "self.version"
},
"extra": {
"typo3/cms": {
"extension-key": "sg_news"
}
},
"autoload": {
"psr-4": {
"SGalinski\\SgNews\\": "Classes/"
}
}
"name": "sgalinski/sg-news",
"type": "typo3-cms-extension",
"description": "News System",
"homepage": "https://www.sgalinski.de",
"license": [
"GPL-2.0-or-later"
],
"version": "9.3.7",
"support": {
},
"repositories": [
{
"type": "composer",
"url": "https://packages.sgalinski.de/"
}
],
"require": {
"typo3/cms-core": "^9.5.0 || ^10.4.0"
},
"suggest": {
"sgalinski/sg-ajax": "Required for the like feature",
"sgalinski/sg-comments": "Flexible comments system"
},
"replace": {
"sgalinski/sg_news": "self.version"
},
"extra": {
"typo3/cms": {
"extension-key": "sg_news"
}
},
"autoload": {
"psr-4": {
"SGalinski\\SgNews\\": "Classes/"
}
}
}
# cat=license; type=string; label=LLL:EXT:sg_news/Resources/Private/Language/locallang.xlf:configuration.licenseKey
key =
......@@ -74,13 +74,6 @@ call_user_func(
['ListByCategory' => '',]
);
\TYPO3\CMS\Extbase\Utility\ExtensionUtility::configurePlugin(
'SGalinski.sg_news',
'PageBrowser',
['PageBrowser' => 'index',],
['PageBrowser' => '',]
);
\TYPO3\CMS\Extbase\Utility\ExtensionUtility::configurePlugin(
'SGalinski.sg_news',
'NewsByAuthor',
......@@ -134,7 +127,7 @@ call_user_func(
\SGalinski\SgNews\Utility\BackendNewsUtility::registerIcons();
\TYPO3\CMS\Core\Utility\ExtensionManagementUtility::addPageTSConfig(
'@import "EXT:sg_news/Configuration/TsConfig/Page/NewContentElementWizard.tsconfig"'
'@import "EXT:sg_news/Configuration/TsConfig/Page/NewContentElementWizard.tsconfig"'
);
// Add upgrade wizards
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment