<?php
// +-------------------------------------------------+
// © 2002-2004 PMB Services / www.sigb.net pmb@sigb.net et contributeurs (voir www.sigb.net)
// +-------------------------------------------------+
// $Id: RssView.php,v 1.4 2023/06/29 09:49:48 qvarin Exp $

namespace Pmb\DSI\Models\View\RssView;

use Pmb\Common\Helper\Helper;
use Pmb\DSI\Models\Item\Item;
use Pmb\DSI\Models\View\RootView;

class RssView extends RootView
{
    public const TEMPLATE_CLASSES = [
        TYPE_NOTICE => "Pmb\DSI\Models\View\RssView\EntitiesTemplates\RecordTemplate",
        TYPE_CMS_ARTICLE => "Pmb\DSI\Models\View\RssView\EntitiesTemplates\ArticleTemplate",
        TYPE_CMS_SECTION => "Pmb\DSI\Models\View\RssView\EntitiesTemplates\SectionTemplate",
        TYPE_DSI_DIFFUSION => "Pmb\DSI\Models\View\RssView\EntitiesTemplates\DiffusionTemplate",
        TYPE_DOCWATCH => "Pmb\DSI\Models\View\RssView\EntitiesTemplates\ItemWatchTemplate",
        // @todo faire les autorités
        // TYPE_AUTHOR => "author",
        // TYPE_CATEGORY => "category",
        // TYPE_PUBLISHER => "publisher",
        // TYPE_COLLECTION => "collection",
        // TYPE_SUBCOLLECTION => "subcollection",
        // TYPE_SERIE => "serie",
        // TYPE_TITRE_UNIFORME => "work",
        // TYPE_INDEXINT => "indexint",
        // TYPE_EXPL => "expl",
        // TYPE_EXPLNUM => "explnum",
        // TYPE_CMS_SECTION => "section",
        // TYPE_CONCEPT => "concept",
    ];

    protected function buildTemplate(array $items, int $entityId, int $limit, string $context)
    {
        global $use_opac_url_base, $charset;
        $use_opac_url_base = 1;

        if (! isset($this->settings->entityType)) {
            return "";
        }

        if (empty($items)) {
            return "";
        }

        if ($context !== 'history') {
            $this->filterData($items, $entityId);
            $this->limitData($items, $limit);
        }

        $this->formatData($items);

        $content = "";
        foreach ($items as $entity) {
            $content .= "
        <item>
            <title>".htmlspecialchars($entity['title'], ENT_QUOTES, $charset)."</title>
            <pubDate>".htmlspecialchars($entity['pubDate'], ENT_QUOTES, $charset)."</pubDate>
            <link>".htmlspecialchars($entity['link'], ENT_QUOTES, $charset)."</link>
            <description>".htmlspecialchars($entity['description'], ENT_QUOTES, $charset)."</description>
        </item>";
        }
        return $content;
    }

    protected function generateContext(Item $item, int $entityId, int $limit, string $context)
    {
        global $pmb_bdd_version;

        $structure = [
            "settings" => $this->settings,
            "buildDate" => date("D, d M Y H:i:s O"),
            "version" => $pmb_bdd_version,
            "entityId" => $entityId,
            "items" => []
        ];

        if (! isset($this->settings->entityType)) {
            return json_encode($structure);
        }

        $data = $this->getDataFromContext($item, $context);
        if (empty($data)) {
            return json_encode($structure);
        }

        $this->filterData($data, $entityId);
        $this->limitData($data, $limit);

        // On recupere que les id
        $structure["items"] = array_keys($data);

        return json_encode($structure);
    }

    public function render(Item $item, int $entityId, int $limit, string $context)
    {
        if (defined('GESTION')) {
            return $this->generateContext($item, $entityId, $limit, $context);
        } else {
            $items = $this->getDataFromContext($item, $context);
            return str_replace(
                '!!items!!',
                trim($this->buildTemplate($items, $entityId, $limit, $context)),
                $this->getBaseTemplate()
            );
        }
    }

    public function buildXML(array $items)
    {
        return str_replace(
            '!!items!!',
            trim($this->buildTemplate($items, 0, 0, "history")),
            $this->getBaseTemplate()
        );
    }

    public function preview(Item $item, int $entityId, int $limit, string $context)
    {
        return "";
    }

    protected function getBaseTemplate(array $context = [])
    {
        global $pmb_bdd_version, $opac_url_base, $charset;

        $version = $context['version'] ?? $pmb_bdd_version;
        $buildDate = $context['buildDate'] ?? date("D, d M Y H:i:s O");

        return '
<?xml version="1.0" encoding="'. $charset .'" ?>
<!-- RSS generated by PMB on '.addslashes(date("D, d/m/Y H:i:s")).' -->
<rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/">
    <channel>
        <title>'. htmlspecialchars($this->getSetting('rssName', ''), ENT_QUOTES, $charset) .'</title>
        <link>'. htmlspecialchars($opac_url_base, ENT_QUOTES, $charset) .'</link>
        <description>'. htmlspecialchars($this->getSetting('rssDescription', ''), ENT_QUOTES, $charset) .'</description>
        <lastBuildDate>' . addslashes($buildDate).'</lastBuildDate>
        <docs>http://backend.userland.com/rss</docs>
        <generator>PMB Version '.$version.'</generator>
        !!items!!
    </channel>
</rss>';
    }

    /**
     * Permet de fournir des donnees pour le formulaire
     *
     * @return array
     */
    public function getFormData()
    {
        $templates = [];

        foreach (static::TEMPLATE_CLASSES as $entityType => $class) {
            $templates[$entityType] = call_user_func(array($class, 'getTemplates'));
        }

        return array_merge(
            parent::getFormData(),
            [
                "templates" => $templates,
            ]
        );
    }

    protected function formatData(&$data, $type = null, $namespace = null)
    {
        $rssAdditionalData = $this->getSetting('rssAdditionalData') ?? new \StdClass();
        $tplTitle = $this->getSetting('rssEntityName') ?? null;
        $tplDescription = $this->getSetting('rssEntityDescription') ?? null;
        $tplLink = $this->getSetting('rssEntityLink') ?? null;

        // Ne pas utilise $value
        foreach ($data as $id => $value) {
            $classname = static::TEMPLATE_CLASSES[$this->getSetting('entityType')] ?? null;
            if (!empty($classname)) {
                $instance = new $classname($id, $rssAdditionalData);
                $data[$id] = [
                    'title' => $instance->getTitle($tplTitle),
                    'pubDate' => $instance->getPubDate(),
                    'link' => $instance->getLink($tplLink),
                    'description' => $instance->getDescription($tplDescription),
                ];
            } else {
                $data[$id] = [
                    'title' => '',
                    'pubDate' => '',
                    'link' => '',
                    'description' => '',
                ];
            }
        }
    }

    public function rebuildContext(object &$context)
    {
        $this->settings = $context->settings;

        // on remet le tableau en id => value
        $context->items = array_flip($context->items);
    }
}
