<?php
/**
 * @package   Nicepage Website Builder
 * @author    Nicepage https://www.nicepage.com
 * @copyright Copyright (c) 2016 - 2019 Nicepage
 * @license   http://www.gnu.org/licenses/gpl-2.0.html GNU/GPLv2 or later
 */

namespace NP\Processor;

defined('_JEXEC') or die;

use NP\Builder\PostDataBuilder;
use NP\Builder\SearchDataBuilder;
use NP\Utility\Pagination;
use NP\Utility\GridHelper;
use NP\Models\ContentModelCustomArticles;
use Joomla\CMS\Categories\Categories;
use Joomla\CMS\Router\Route;
use Joomla\CMS\Factory;
use Joomla\CMS\Uri\Uri;
use \JLoader;

JLoader::register('Nicepage_Data_Mappers', JPATH_ADMINISTRATOR . '/components/com_nicepage/tables/mappers.php');

class BlogProcessor
{
    private $_post = array();
    private $_pageId;
    private $_templateData;

    private $_blogList = array();
    private $_blogPosition = 0;
    private $_paginationProps = null;

    private $_metaDataType = '';
    private $_searchBlog = false;
    /**
     * BlogProcessor constructor.
     *
     * @param string $pageId       Page id
     * @param array  $templateData Template data
     */
    public function __construct($pageId = '', $templateData = null)
    {
        $this->_pageId = $pageId;
        $this->_templateData = $templateData;
        if ($this->_templateData && isset($this->_templateData['searchComponent'])) {
            $this->_searchBlog = true;
        }
    }

    /**
     * Process blog
     *
     * @param string $content Content
     *
     * @return string|string[]|null
     */
    public function process($content) {
        if ($this->_templateData
            && !isset($this->_templateData['item'])
            && !isset($this->_templateData['lead_items'])
            && !isset($this->_templateData['searchComponent'])
        ) {
            return $content;
        }
        $content = preg_replace_callback('/<\!--blog-->([\s\S]+?)<\!--\/blog-->/', array(&$this, '_processBlog'), $content);
        $content = preg_replace_callback('/<\!--post_details-->([\s\S]+?)<\!--\/post_details-->/', array(&$this, '_processPost'), $content);

        if (strpos($content, 'none-post-image') !== false) {
            $content = str_replace('u-blog-post', 'u-blog-post u-invisible', $content);
        }
        return $content;
    }

    /**
     * Process one blog
     *
     * @param string $content Content
     *
     * @return int
     */
    public function processBlogByAjaxLoad($content) {
        preg_replace_callback('/<\!--blog-->([\s\S]+?)<\!--\/blog-->/', array(&$this, '_processBlog'), $content);
        $position = Factory::getApplication()->input->get('position', 1);
        $result = array_slice($this->_blogList, $position - 1, 1);
        return count($result) > 0 ? $result[0] : 0;
    }

    /**
     * Process product
     *
     * @param array $postMatch Matches
     *
     * @return string|string[]|null
     */
    private function _processPost($postMatch) {
        $postHtml = $postMatch[1];
        $postOptions = array();
        if (preg_match('/<\!--post_details_options_json--><\!--([\s\S]+?)--><\!--\/post_details_options_json-->/', $postHtml, $matches)) {
            $postOptions = json_decode($matches[1], true);
            $postHtml = str_replace($matches[0], '', $postHtml);
        }
        $blogSource = '';
        if (isset($postOptions['source']) && $postOptions['source']) {
            $blogSource = 'postId:' . $postOptions['source'];
        }
        $posts = $this->_getBlogPosts($blogSource);
        $postHtml = $this->processBlogPost($postHtml, $posts);
        return $postHtml;
    }

    /**
     * Process blog
     *
     * @param array $blogMatch Matches
     *
     * @return string|string[]|null
     */
    private function _processBlog($blogMatch) {
        if ($this->_searchBlog && count($this->_templateData['searchResults']) < 1) {
            return '';
        }
        $blogHtml = $blogMatch[1];
        $blogOptions = array();
        $this->_paginationProps = null;
        $this->_blogPosition += 1;
        if (preg_match('/<\!--blog_options_json--><\!--([\s\S]+?)--><\!--\/blog_options_json-->/', $blogHtml, $matches)) {
            $blogOptions = json_decode($matches[1], true);
            $blogHtml = str_replace($matches[0], '', $blogHtml);
        }
        $blogSourceType = isset($blogOptions['type']) ? $blogOptions['type'] : '';
        if ($blogSourceType === 'Tags') {
            $blogSource = 'tags:' . (isset($blogOptions['tags']) && $blogOptions['tags'] ? $blogOptions['tags'] : '');
        } else {
            $blogSource = isset($blogOptions['source']) && $blogOptions['source'] ? $blogOptions['source'] : '';
        }
        $blogPostCount = isset($blogOptions['count']) ? (int) $blogOptions['count'] : '';
        $posts = $this->_getBlogPosts($blogSource);

        if ($this->_templateData && $this->_templateData['pagination'] && !$this->_searchBlog) {
            $this->_paginationProps = array(
                'templatePagination' => $this->_templateData['pagination']
            );
        }

        if (!$this->_templateData && $blogPostCount && count($posts) > $blogPostCount) {
            $app = Factory::getApplication();
            $limitstart = $app->input->get('offset', 0);
            $pageId = $app->input->get('pageId', $this->_pageId);
            $order = $app->input->get('order', 'rdate');
            $positionOnPage = $app->input->get('position', $this->_blogPosition);
            $this->_paginationProps = array(
                'allPosts' => count($posts),
                'offset' => (int) $limitstart,
                'postsPerPage' => $blogPostCount,
                'order' => $order,
                'pageId' => (int) $pageId,
                'positionOnPage' => $positionOnPage,
                'task' => 'blogposts',
            );
            $posts = array_slice($posts, $limitstart, $blogPostCount);
        }

        $blogHtml = $this->processBlogPost($blogHtml, $posts);
        $blogHtml = preg_replace_callback('/<\!--blog_pagination-->([\s\S]+?)<\!--\/blog_pagination-->/', array(&$this, '_processBlogPagination'), $blogHtml);
        $blogHtml = preg_replace_callback('/<\!--blog_categories_filter_select-->([\s\S]+?)<\!--\/blog_categories_filter_select-->/', array(&$this, '_processCategoriesFilterSelect'), $blogHtml);
        $blogHtml = preg_replace_callback('/<\!--blog_sorting-->([\s\S]+?)<\!--\/blog_sorting-->/', array(&$this, '_processSorting'), $blogHtml);

        $blogGridProps = isset($blogOptions['gridProps']) ? $blogOptions['gridProps'] : array();
        $blogHtml .= GridHelper::buildGridAutoRowsStyles($blogGridProps, count($posts));

        array_push($this->_blogList, $blogHtml);
        return $blogHtml;
    }

    /**
     * Get model categories
     *
     * @return array
     */
    public function getCategories() {
        $cats = array();
        $categories = Categories::getInstance('Content', array());
        $parentCategory   = $categories->get('root', true);
        if ($parentCategory !== null) {
            $children = $parentCategory->getChildren(true);
            foreach ($children as $child) {
                array_push(
                    $cats,
                    array(
                        'categoryId' => $child->parent_id !== 'root' ? $child->parent_id : null,
                        'id' => (string) $child->id,
                        'title' => $child->title,
                    )
                );
            }
        }
        return self::buildTreeCategories($cats);
    }

    /**
     * Build recursivly tree
     *
     * @param array $categories List of categories
     * @param int   $parentId   Parent id of category
     *
     * @return array
     */
    public static function buildTreeCategories($categories, $parentId = 0)
    {
        $input = Factory::getApplication()->input;
        $view = $input->get('view', 'category');
        $catId = $input->get('id', 'blog');
        $result = array();
        if ($parentId === 0) {
            $item = new \stdClass();
            $item->title = 'Featured';
            $item->id = 'featured';
            $item->active = false;
            $item->link = Route::_('index.php?option=com_content&view=featured');
            $item->children = array();
            if ($view === 'featured') {
                $item->selected = true;
            }
            $item->onchangeEvent = 'onchange="window.location.href = this.value;"';
            array_push($result, $item);
        }
        foreach ($categories as $category) {
            $categoryId = $category['categoryId'];
            if (!$parentId && $categoryId) {
                continue;
            }
            if ($parentId && $parentId != $categoryId) {
                continue;
            }
            $item = new \stdClass();
            $item->id = $category['id'];
            $item->title = $category['title'];
            $item->link = Route::_('index.php?option=com_content&view=category&layout=blog&id=' . $category['id']);
            $item->active = false;
            $item->children = self::buildTreeCategories($categories, $category['id']);
            if ($catId === $category['id']) {
                $item->selected = true;
            }
            array_push($result, $item);
        }
        return $result;
    }

    /**
     * Process sorting
     *
     * @param array $sortingMatch Matches
     *
     * @return array|string|string[]|null
     */
    private function _processSorting($sortingMatch) {
        if ($this->_templateData) {
            return '';
        }
        $sortingHtml = $sortingMatch[1];
        $re = '/<\!--blog_sorting_select-->([\s\S]+?)<\!--\/blog_sorting_select-->/';
        return preg_replace_callback($re, array(&$this, '_processSortingSelect'), $sortingHtml);
    }

    /**
     * Process sorting select
     *
     * @param array $selectMatch Matches
     *
     * @return string
     */
    private function _processSortingSelect($selectMatch) {
        $input = Factory::getApplication()->input;
        $order = $input->get('order', 'rdate');
        $sortingValues = array(
            'front' => 'Featured Articles Order',
            'rdate' => 'Most Recent First',
            'date' => 'Oldest First',
            'alpha' => 'Title Alphabetical',
            'ralpha' => 'Title Reverse Alphabetical',
            'author' => 'Author Alphabetical',
            'rauthor' => 'Author Reverse Alphabetica',
            'hits' => 'Most Hits',
            'rhits' => 'Least Hits',
            'random' => 'Random Order',
            'order' => 'Article Order',
            'rorder' => 'Article Reverse Order',
            'vote' => 'Votes descending',
            'rvote' => 'Votes ascending',
            'rank' => 'Ratings descending',
            'rrank' => 'Ratings ascending',
        );
        $selectHtml = $selectMatch[1];
        $selectHtml = preg_replace('/<option[\s\S]+?<\/option>/', '', $selectHtml);
        $optionTemplate = '<option value="[[value]]" [[selected]]>[[content]]</option>';
        $options = '';

        $app = Factory::getApplication();
        $pageId = $app->input->get('pageId', $this->_pageId);
        $positionOnPage = $app->input->get('position', $this->_blogPosition);
        $pageLink = Uri::root(true) . '/index.php?option=com_nicepage&task=blogposts&pageId=' . $pageId . '&position=' . $positionOnPage;
        foreach ($sortingValues as $value => $text) {
            $url = $pageLink . '&order=' . $value;
            $option = str_replace('[[value]]', $url, $optionTemplate);
            $option = str_replace('[[content]]', $text, $option);
            $option = str_replace('[[selected]]', $value == $order ? 'selected="selected"' : '', $option);
            $options .= $option;
        }
        $selectHtml = str_replace('</select>', $options . '</select>', $selectHtml);
        $selectHtml = str_replace('u-select-sorting', 'u-select-sorting u-select-sorting-cms', $selectHtml);
        ob_start();
        ?>
        <script>
            jQuery(function ($) {
                $('.u-select-sorting.u-select-sorting-cms').on('change', function (event) {
                    var s = $(this);
                    var href = s.val();
                    $.post(href).done(function (html) {
                        s.closest('.u-list-control').parent().replaceWith(html);
                    });
                });
            });
        </script>
        <?php
        $script = ob_get_clean();
        return $selectHtml . $script;
    }
    /**
     * Process categories filter
     *
     * @param array $selectMatch Matches
     *
     * @return false|mixed|string
     */
    private function _processCategoriesFilterSelect($selectMatch) {
        $categories = $this->getCategories();
        $selectHtml = $selectMatch[1];
        $selectHtml = preg_replace('/<option[\s\S]+?<\/option>/', '', $selectHtml);
        $optionTemplate = '<option value="[[value]]">[[content]]</option>';
        $options = $this->_getCategoriesFilterOptions($categories, $optionTemplate);
        $selectHtml = str_replace('</select>', $options . '</select>', $selectHtml);
        $selectHtml = str_replace('u-select-categories', 'u-select-categories u-select-categories-cms', $selectHtml);
        ob_start();
        ?>
        <script>
            jQuery(function ($) {
                $('.u-select-categories.u-select-categories-cms').on('change', function (event) {
                    window.location.href = $(this).val();
                });
            });
        </script>
        <?php
        $script = ob_get_clean();
        return $selectHtml . $script;
    }

    /**
     * Build category option
     *
     * @param array  $categories     List of categories
     * @param string $optionTemplate Option html template
     * @param int    $level          Tree level
     *
     * @return string
     */
    private function _getCategoriesFilterOptions($categories, $optionTemplate, $level = 0)
    {
        $result = '';
        foreach ($categories as $category) {
            $value = $category->link;
            $title = str_repeat('--', $level) . ' ' . $category->title;
            $option = str_replace('[[value]]', $value, $optionTemplate);
            $option = str_replace('[[content]]', $title, $option);
            if (isset($category->selected) && $category->selected) {
                $option = str_replace('<option', '<option selected="selected"', $option);
            }
            $result .= $option . "\n";
            if (count($category->children) > 0) {
                $result .= $this->_getCategoriesFilterOptions($category->children, $optionTemplate, $level + 1);
            }
        }
        return $result;
    }

    /**
     * Process pagination
     *
     * @param array $paginationMatch Matches
     *
     * @return false|mixed|string
     */
    private function _processBlogPagination($paginationMatch) {
        if (!$this->_paginationProps) {
            return '';
        }
        $paginationHtml = $paginationMatch[1];
        $paginationStyleOptions = array();
        if (preg_match('/<\!--blog_pagination_options_json--><\!--([\s\S]+?)--><\!--\/blog_pagination_options_json-->/', $paginationHtml, $matches)) {
            $paginationStyleOptions = json_decode($matches[1], true);
        }
        if (isset($this->_paginationProps['templatePagination'])) {
            return Pagination::getTemplatePagination($this->_paginationProps['templatePagination'], $paginationStyleOptions);
        } else {
            $pagination = new Pagination(array('paginationProps' => $this->_paginationProps), $paginationStyleOptions);
            return $pagination->getPagination();
        }
    }

    /**
     * Process blog post
     *
     * @param string $blogHtml Wrapper html
     * @param array  $posts    Post collection
     *
     * @return string|string[]|null
     */
    public function processBlogPost($blogHtml, $posts) {
        $reBlogPost = '/<\!--blog_post-->([\s\S]+?)<\!--\/blog_post-->/';
        preg_match_all($reBlogPost, $blogHtml, $matches, PREG_SET_ORDER);
        $allTemplates = count($matches);
        if ($allTemplates > 0) {
            $postsHtml = '';
            $i = 0;
            while (count($posts) > 0) {
                $tmplIndex = $i % $allTemplates;
                $postHtml = $matches[$tmplIndex][1];
                $this->_post = array_shift($posts);
                $postHtml = preg_replace_callback('/<\!--blog_post_header-->([\s\S]+?)<\!--\/blog_post_header-->/', array(&$this, '_setHeaderData'), $postHtml);
                $postHtml = preg_replace_callback('/<\!--blog_post_content-->([\s\S]+?)<\!--\/blog_post_content-->/', array(&$this, '_setContentData'), $postHtml);
                $postHtml = preg_replace_callback('/<\!--blog_post_image-->([\s\S]+?)<\!--\/blog_post_image-->/', array(&$this, '_setImageData'), $postHtml);
                $postHtml = preg_replace_callback('/<\!--blog_post_readmore-->([\s\S]+?)<\!--\/blog_post_readmore-->/', array(&$this, '_setReadmoreData'), $postHtml);
                $postHtml = preg_replace_callback('/<\!--blog_post_metadata-->([\s\S]+?)<\!--\/blog_post_metadata-->/', array(&$this, '_setMetadataData'), $postHtml);
                $postHtml = preg_replace_callback('/<\!--blog_post_tags-->([\s\S]+?)<\!--\/blog_post_tags-->/', array(&$this, '_setTagsData'), $postHtml);
                $postsHtml .= $postHtml;
                $i++;
            }
            $blogHtml = preg_replace($reBlogPost, $postsHtml, $blogHtml, 1);
            $blogHtml = preg_replace($reBlogPost, '', $blogHtml);
        }
        return $blogHtml;
    }

    /**
     * Get blog post by source
     *
     * @param string $source Source
     * @param int    $count  Post count
     *
     * @return array
     */
    private function _getBlogPosts($source, $count = null) {
        if (!$this->_templateData) {
            return $this->_getPageBlogPosts($source, $count);
        }
        return $this->_getTemplateBlogPosts();
    }

    /**
     * Get template posts
     *
     * @return array
     */
    private function _getTemplateBlogPosts() {
        $type = 'blog';
        if ($this->_searchBlog) {
            $allItems = $this->_templateData['searchResults'];
        } else if (isset($this->_templateData['item'])) {
            $allItems = array($this->_templateData['item']);
            $type = 'post';
        } else {
            $allItems = array_merge($this->_templateData['lead_items'], $this->_templateData['intro_items']);
        }
        $posts = array();
        foreach ($allItems as $key => $item) {
            if ($this->_searchBlog) {
                $options = array(
                    'params' => $this->_templateData['params'],
                    'query' => $this->_templateData['query'],
                );
                $builder = new SearchDataBuilder($item, $options);
            } else {
                $builder = new PostDataBuilder($item, $type);
            }
            $post = $builder->getData();
            array_push($posts, $post);
        }
        return $posts;
    }

    /**
     * Get blog post by source
     *
     * @param string $source Source
     * @param int    $count  Post count
     *
     * @return array
     */
    private function _getPageBlogPosts($source, $count = null) {
        $app = Factory::getApplication();
        $order = $app->input->get('order', '');
        $posts = array();
        $categoryId = '';
        $tags = '';
        $postId = '';
        if ($source) {
            if (preg_match('/^postId:/', $source)) {
                $postId = str_replace('postId:', '', $source);
            } else if (preg_match('/^tags:/', $source)) {
                $tags = str_replace('tags:', '', $source);
            } else {
                $categoryObject = \Nicepage_Data_Mappers::get('category');
                $categoryList = $categoryObject->find(array('title' => $source));
                if (count($categoryList) < 1) {
                    return $posts;
                }
                $categoryId = $categoryList[0]->id;
            }
        }
        // Get recent articles, if $categoryId is empty
        $blog = new ContentModelCustomArticles(array('category_id' => $categoryId, 'tags' => $tags, 'count' => $count, 'postId' => $postId, 'order' => $order));
        return $blog->getPosts($postId ? 'post' : 'blog');
    }


    /**
     * Set header
     *
     * @param string $headerMatch Header match
     *
     * @return mixed|string|string[]|null
     */
    private function _setHeaderData($headerMatch) {
        $headerHtml = $headerMatch[1];
        $headerHtml = preg_replace_callback(
            '/<\!--blog_post_header_content-->([\s\S]+?)<\!--\/blog_post_header_content-->/',
            function ($headerContentMatch) {
                return isset($this->_post['post-header']) ? $this->_post['post-header'] : $headerContentMatch[1];
            },
            $headerHtml
        );
        $headerLink = isset($this->_post['post-header-link']) ? $this->_post['post-header-link'] : '#';
        $headerHtml = preg_replace('/(href=[\'"])([\s\S]+?)([\'"])/', '$1' . $headerLink . '$3', $headerHtml);
        return $headerHtml;
    }

    /**
     * Set content
     *
     * @param string $contentMatch Content match
     *
     * @return mixed|string|string[]|null
     */
    private function _setContentData($contentMatch) {
        $contentHtml = $contentMatch[1];
        $contentHtml = preg_replace_callback(
            '/<\!--blog_post_content_content-->([\s\S]+?)<\!--\/blog_post_content_content-->/',
            function ($contentMatch) {
                return isset($this->_post['post-content']) ? $this->_post['post-content'] : $contentMatch[1];
            },
            $contentHtml
        );
        return $contentHtml;
    }

    /**
     * Set image
     *
     * @param string $imageMatch Image match
     *
     * @return mixed
     */
    private function _setImageData($imageMatch) {
        $imageHtml = $imageMatch[1];
        $isBackgroundImage = strpos($imageHtml, '<div') !== false ? true : false;

        $src = isset($this->_post['post-image'])? $this->_post['post-image'] : '';
        $alt = isset($this->_post['post-alt-image'])? $this->_post['post-alt-image'] : '';

        if (!$src && !$isBackgroundImage) {
            return '<div class="none-post-image" style="display: none;"></div>';
        }

        if ($isBackgroundImage) {
            if (strpos($imageHtml, 'data-bg') !== false) {
                $imageHtml = preg_replace('/(data-bg=[\'"])([\s\S]+?)([\'"])/', '$1url(' . $src . ')$3', $imageHtml);
            } else {
                if (preg_match('/url\(([\s\S]+?)\)/', $imageHtml, $imageUrl) && isset($imageUrl[1])) {
                    $imageHtml = str_replace($imageUrl[1], $src, $imageHtml);
                }
            }
        } else {
            $imageHtml = preg_replace('/(src=[\'"])([\s\S]+?)([\'"])/', '$1' . $src . '$3', $imageHtml);
            $imageHtml = str_replace('alt=""', 'alt="' . $alt . '"', $imageHtml);
        }

        if ($this->_post['post-type'] == 'blog') {
            $link = isset($this->_post['post-header-link']) ? $this->_post['post-header-link'] : '#';
            $imgClass = preg_match('/class=[\'"](.*?)[\'"]/', $imageHtml, $imgClasses) ? $imgClasses[1] : '';
            if (strpos($imageHtml, '<img') !== false) {
                $imageHtml = '<a class="' . $imgClass . '" href="' . $link . '">' . $imageHtml . '</a>';
            } else {
                $imageHtml = str_replace('<div', '<div data-href="' . $link . '"', $imageHtml);
            }
        }

        return $imageHtml;
    }

    /**
     * Set readmore
     *
     * @param string $readmoreMatch Readmre match
     *
     * @return mixed|string|string[]|null
     */
    private function _setReadmoreData($readmoreMatch) {
        $readmoreHtml = $readmoreMatch[1];
        $readmoreHtml = preg_replace_callback(
            '/<\!--blog_post_readmore_content-->([\s\S]+?)<\!--\/blog_post_readmore_content-->/',
            function ($readmoreContentMatch) {
                $cmsText = isset($this->_post['post-readmore-text']) ? $this->_post['post-readmore-text'] : '';
                $userText = $cmsText;
                if (preg_match('/<\!--options_json--><\!--([\s\S]+?)--><\!--\/options_json-->/', $readmoreContentMatch[1], $matches)) {
                    $controlOptions = json_decode($matches[1], true);
                    $defaultText = str_replace($matches[0], '', $readmoreContentMatch[1]);
                    if (isset($controlOptions['content']) && $controlOptions['content']) {
                        $userText = $controlOptions['content'];
                    }
                } else {
                    $defaultText = $readmoreContentMatch[1];
                }
                return $userText ? $userText : $defaultText;
            },
            $readmoreHtml
        );
        $readmoreLink = isset($this->_post['post-readmore-link']) ? $this->_post['post-readmore-link'] : '#';
        $readmoreHtml = preg_replace('/(href=[\'"])([\s\S]+?)([\'"])/', '$1' . $readmoreLink . '$3', $readmoreHtml);
        return $readmoreHtml;
    }

    /**
     * Set metadata
     *
     * @param string $metadataMatch Metadata match
     *
     * @return mixed|string|string[]|null
     */
    private function _setMetadataData($metadataMatch) {
        $metadataHtml = $metadataMatch[1];
        $metaDataTypes = array('date', 'author', 'category', 'comments', 'edit');
        foreach ($metaDataTypes as $type) {
            $this->_metaDataType = $type;
            $metadataHtml = preg_replace_callback(
                '/<\!--blog_post_metadata_' . $this->_metaDataType . '-->([\s\S]+?)<\!--\/blog_post_metadata_' . $this->_metaDataType . '-->/',
                function ($metadataTypeMatch) {
                    return $metadataTypeMatch[1];
                },
                $metadataHtml
            );
            $metadataHtml = preg_replace_callback(
                '/<\!--blog_post_metadata_' . $this->_metaDataType . '_content-->([\s\S]+?)<\!--\/blog_post_metadata_' . $this->_metaDataType . '_content-->/',
                function ($metadataTypeContentMatch) {
                    return isset($this->_post['post-metadata-' . $this->_metaDataType]) ? $this->_post['post-metadata-' . $this->_metaDataType] : $metadataTypeContentMatch[1];
                },
                $metadataHtml
            );
        }
        return $metadataHtml;
    }

    /**
     * Set tags
     *
     * @param string $tagsMatch tags match
     *
     * @return mixed|string|string[]|null
     */
    private function _setTagsData($tagsMatch) {
        $tagsHtml = $tagsMatch[1];
        $tagsHtml = preg_replace_callback(
            '/<\!--blog_post_tags_content-->([\s\S]+?)<\!--\/blog_post_tags_content-->/',
            function ($contentTagsMatch) {
                return isset($this->_post['post-tags']) ? $this->_post['post-tags'] : $contentTagsMatch[1];
            },
            $tagsHtml
        );
        return $tagsHtml;
    }
}
