Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
100.00% covered (success)
100.00%
21 / 21
100.00% covered (success)
100.00%
1 / 1
CRAP
100.00% covered (success)
100.00%
1 / 1
BreadcrumbsHtmlRenderer
100.00% covered (success)
100.00%
21 / 21
100.00% covered (success)
100.00%
1 / 1
6
100.00% covered (success)
100.00%
1 / 1
 render
100.00% covered (success)
100.00%
21 / 21
100.00% covered (success)
100.00%
1 / 1
6
1<?php
2
3/**
4 * Category breadcrumb HTML renderer class
5 *
6 * This Source Code Form is subject to the terms of the Mozilla Public License,
7 * v. 2.0. If a copy of the MPL was not distributed with this file, You can
8 * obtain one at https://mozilla.org/MPL/2.0/.
9 *
10 * @package   phpMyFAQ
11 * @author    Thorsten Rinne <thorsten@phpmyfaq.de>
12 * @copyright 2025 phpMyFAQ Team
13 * @license   https://www.mozilla.org/MPL/2.0/ Mozilla Public License Version 2.0
14 * @link      https://www.phpmyfaq.de
15 * @since     2025-10-18
16 */
17
18declare(strict_types=1);
19
20namespace phpMyFAQ\Category\Navigation;
21
22use phpMyFAQ\Configuration;
23use phpMyFAQ\Link;
24use phpMyFAQ\Link\Util\TitleSlugifier;
25use phpMyFAQ\Strings;
26
27final class BreadcrumbsHtmlRenderer
28{
29    /**
30     * @param array<int, array{id:int, name:string, description:string}> $segments
31     */
32    public function render(Configuration $configuration, array $segments, string $useCssClass = 'breadcrumb'): string
33    {
34        $items = [];
35        foreach ($segments as $index => $segment) {
36            $url = match ($segment['id']) {
37                // Start page → homepage URL
38                -1 => $configuration->getDefaultUrl(),
39                // All-categories overview → dedicated route, not a category URL
40                0 => $configuration->getDefaultUrl() . 'show-categories.html',
41                default => strtr('{base}category/{id}/{slug}.html', [
42                    '{base}' => $configuration->getDefaultUrl(),
43                    '{id}' => (string) $segment['id'],
44                    '{slug}' => TitleSlugifier::slug(Strings::htmlentities($segment['name'])),
45                ]),
46            };
47
48            $oLink = new Link($url, $configuration);
49            $oLink->text = Strings::htmlentities($segment['name']);
50            $oLink->setTitle(Strings::htmlentities($segment['name']));
51            $oLink->tooltip = Strings::htmlentities($segment['description'] ?? '');
52            if (0 === $index) {
53                $oLink->setRelation(rel: 'index');
54            }
55
56            $items[] = sprintf('<li class="breadcrumb-item">%s</li>', $oLink->toHtmlAnchor());
57        }
58
59        return strtr('<ol class="{class}">{items}</ol>', [
60            '{class}' => $useCssClass,
61            '{items}' => implode(separator: '', array: $items),
62        ]);
63    }
64}