cObj->data ?? null) ? $this->cObj->data : null; if ($row && (string)($row['CType'] ?? '') === 'vitec_marketshow') { return $this->renderForRecord($row); } // 2) Page-id via v14 request attribute (TSFE->id is often null in JSON cObj context) $pageId = 0; $request = $GLOBALS['TYPO3_REQUEST'] ?? null; if ($request !== null) { $pageInfo = $request->getAttribute('frontend.page.information'); if ($pageInfo !== null) { $pageId = (int)$pageInfo->getId(); } } if ($pageId <= 0) { $pageId = (int)($GLOBALS['TSFE']->id ?? 0); } if ($pageId <= 0) { return ''; } $queryBuilder = GeneralUtility::makeInstance(\TYPO3\CMS\Core\Database\ConnectionPool::class) ->getQueryBuilderForTable('tt_content'); $contentElements = $queryBuilder ->select('*') ->from('tt_content') ->where( $queryBuilder->expr()->eq('pid', $queryBuilder->createNamedParameter($pageId, ParameterType::INTEGER)), $queryBuilder->expr()->eq('CType', $queryBuilder->createNamedParameter('vitec_marketshow', ParameterType::STRING)), $queryBuilder->expr()->eq('deleted', 0), $queryBuilder->expr()->eq('hidden', 0) ) ->executeQuery() ->fetchAllAssociative(); if (empty($contentElements)) { return ''; } return $this->renderForRecord($contentElements[0]); } /** * @param array $contentElement */ public function renderForRecord(array $contentElement): string { try { $pageId = (int)($GLOBALS['TSFE']->id ?? 0); $flexFormService = GeneralUtility::makeInstance(FlexFormService::class); $flexFormData = $flexFormService->convertFlexFormContentToArray($contentElement['pi_flexform'] ?? ''); $settings = $flexFormData['settings'] ?? []; $marketUid = (int)($settings['market'] ?? 0); $layout = (string)($settings['layout'] ?? 'default'); $debugMode = (bool)($settings['debug'] ?? false); // Fallback: route / query parameter (numeric uid only — Market has no slug) if (!$marketUid) { $routeParams = $GLOBALS['TYPO3_REQUEST']->getQueryParams(); $marketParam = $routeParams['tx_vitec_marketshow']['market'] ?? null; if ($marketParam && is_numeric($marketParam)) { $marketUid = (int)$marketParam; } } if (!$marketUid) { return $debugMode ? json_encode(['error' => 'No market selected or found', 'debug' => ['settings' => $settings]]) : ''; } $marketQb = GeneralUtility::makeInstance(ConnectionPool::class) ->getQueryBuilderForTable('tx_vitec_domain_model_market'); $market = $marketQb ->select('*') ->from('tx_vitec_domain_model_market') ->where( $marketQb->expr()->eq('uid', $marketQb->createNamedParameter($marketUid, ParameterType::INTEGER)), $marketQb->expr()->eq('deleted', 0), $marketQb->expr()->eq('hidden', 0) ) ->executeQuery() ->fetchAssociative(); if (!$market) { return $debugMode ? json_encode(['error' => 'Market not found', 'debug' => ['marketUid' => $marketUid]]) : ''; } $response = [ 'market' => $this->serializeMarket($market), 'layout' => $layout, 'settings' => [ 'layout' => $layout, ], ]; if ($debugMode) { $response['debug'] = [ 'pageId' => $pageId, 'marketUid' => $marketUid, 'layout' => $layout, 'settings' => $settings, ]; } return json_encode($response); } catch (\Throwable $e) { return ''; } } /** * @param array $market * @return array */ protected function serializeMarket(array $market): array { $uid = (int)$market['uid']; return [ 'uid' => $uid, 'title' => (string)($market['title'] ?? ''), 'subtitle' => (string)($market['subtitle'] ?? ''), 'teaser' => (string)($market['teaser'] ?? ''), 'description' => (string)($market['description'] ?? ''), 'categories' => $this->getMarketCategories($uid), 'image' => $this->getMarketImage($uid), ]; } /** * Resolve the single image FAL reference for a market (fieldname=image). * * @return array|null */ protected function getMarketImage(int $marketUid): ?array { $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class) ->getQueryBuilderForTable('sys_file_reference'); $fileRefData = $queryBuilder ->select('sfr.uid', 'sfr.title', 'sfr.description', 'sfr.alternative', 'sfr.crop') ->from('sys_file_reference', 'sfr') ->where( $queryBuilder->expr()->eq('sfr.tablenames', $queryBuilder->createNamedParameter('tx_vitec_domain_model_market', ParameterType::STRING)), $queryBuilder->expr()->eq('sfr.fieldname', $queryBuilder->createNamedParameter('image', ParameterType::STRING)), $queryBuilder->expr()->eq('sfr.uid_foreign', $queryBuilder->createNamedParameter($marketUid, ParameterType::INTEGER)), $queryBuilder->expr()->eq('sfr.deleted', 0), $queryBuilder->expr()->eq('sfr.hidden', 0) ) ->orderBy('sfr.sorting_foreign') ->setMaxResults(1) ->executeQuery() ->fetchAssociative(); if (!$fileRefData) { return null; } try { $resourceFactory = GeneralUtility::makeInstance(ResourceFactory::class); $imageService = GeneralUtility::makeInstance(ImageService::class); $fileReference = $resourceFactory->getFileReferenceObject((int)$fileRefData['uid']); $srcset = []; foreach ([400, 800, 1200, 1600] as $width) { $variant = $imageService->applyProcessingInstructions( $fileReference, ['width' => $width, 'crop' => $fileRefData['crop'] ?? null] ); $srcset[] = [ 'url' => $imageService->getImageUri($variant), 'width' => $width, 'descriptor' => $width . 'w', ]; } $default = $imageService->applyProcessingInstructions( $fileReference, ['width' => 800, 'crop' => $fileRefData['crop'] ?? null] ); return [ 'uid' => (int)$fileRefData['uid'], 'url' => $imageService->getImageUri($default), 'title' => $fileRefData['title'] ?? '', 'alternative' => $fileRefData['alternative'] ?? '', 'description' => $fileRefData['description'] ?? '', 'srcset' => $srcset, 'properties' => [ 'width' => $fileReference->getProperty('width'), 'height' => $fileReference->getProperty('height'), 'mimeType' => $fileReference->getProperty('mime_type'), ], ]; } catch (\Exception $e) { return null; } } protected function getMarketCategories(int $marketUid): array { $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class) ->getQueryBuilderForTable('sys_category'); $categories = $queryBuilder ->select('c.uid', 'c.title', 'c.description') ->from('sys_category', 'c') ->join( 'c', 'sys_category_record_mm', 'mm', 'mm.uid_local = c.uid AND mm.tablenames = ' . $queryBuilder->createNamedParameter('tx_vitec_domain_model_market', ParameterType::STRING) . ' AND mm.fieldname = ' . $queryBuilder->createNamedParameter('categories', ParameterType::STRING) ) ->where( $queryBuilder->expr()->eq('mm.uid_foreign', $queryBuilder->createNamedParameter($marketUid, ParameterType::INTEGER)), $queryBuilder->expr()->eq('c.deleted', 0), $queryBuilder->expr()->eq('c.hidden', 0) ) ->orderBy('mm.sorting', 'ASC') ->executeQuery() ->fetchAllAssociative(); return array_map(static function ($cat) { return [ 'uid' => (int)$cat['uid'], 'title' => $cat['title'] ?? '', 'description' => $cat['description'] ?? '', ]; }, $categories); } }