Блоги Подключаем React + Babel в Diafan.CMS

28 октября

Всем привет. Как - то захотелось мне в новом проекте на диафане подключить React, и подключить его так, чтобы в каждом модуле был свой файл .jsx который тянется из папки modules/shop/js автоматом на страницу, так же как обычные файлы js ( modules/shop/js/shop.show_block.js ).

Мне пришлось решить такие вопросы:

  • Во первых, пришлось найти где в ядре Diafan.CMS лежит логика, которая находит и подключает js файлы модулей.

  • Во вторых, нужно эти подключаемые файлы с React правильно скормить в верстку.

Решаем первый вопрос.

Файл, в котором находится логика подключения js файлов модулей лежит в папке includes/template.php, нас интересует функция

public function js($name='',$module=''){
    /* some code */
}

Внутри функции есть код, который имплементирует логику подключения js файла:

$path = 'modules/'.$module.'/js/'.$module.$name.'.js';
if(Custom::exists($path))
{
    $this->diafan->_site->js_view[] = $path;
}

После него я добавляю свой, где указываю что мой файл с React будет лежать в файле таким же именем, но с расширением .jsx

$path1 = 'modules/'.$module.'/js/'.$module.$name.'.jsx';
if(Custom::exists($path1))
{
    $this->diafan->_site->js_view[] = $path1;
}

с первым вопросом разобрались.

P.S. Для бородатых, не вносите правки в файлы ядра на прямую, работайте с ядром через кастомизацию.

Решаем второй вопрос.

Логика вывода скриптов на страницу реализована через шаблонный тег <include name="show_js"> Для того, чтобы правильно подключить наши .jsx файлы нужно скормить их Babel. Поэтому, нам нужно немного поправить этот файл ( для тех кто еще новичок и не шарит где он лежит, то он лежит themes/functions/show_js.php ). Находим в этом файле такие строки:

$js_view = array();
foreach($this->diafan->_site->js_view as $path)
{

И меняем их вот так:

$js_view = array();

?>
<!-- Наши библиотеки для работы с React -->
<script crossorigin src="https://unpkg.com/react@16/umd/react.production.min.js"></script>
<script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/babel-standalone/6.26.0/babel.min.js"></script>
<!-- Наши библиотеки для работы с React -->
<?

foreach($this->diafan->_site->js_view as $path)
{
    // мы проверяем путь к скрипту, и определяем React файлы по расширению .jsx
    if( strpos($path,'.jsx') ) {
        // Тут мы формируем путь к файлу с учетом кастомизации, темы.
        $path = BASE_PATH.Custom::path($path);
        ?>
            <!-- обратите внимание, что атрибут [type="text/babel"]
            скармливает наш скрипт React в Babel  -->
            <script type="text/babel" src="<?=$path;?>"></script>
        <?
        // заканчиваем текущую итерацию цикла, required -> else bug !)
        continue;
    }

Что мы тут сделали? Мы подключили библиотеки React и Babel, и скормили наши скрипты .jsx в Babel.

Hello world

Отлично, с подключением мы разобрались. Давайте теперь попробуем создать что-то на React. В файле themes/site_start.php добавляем шаблонный в body код:

<insert name="show_block" id="1">
<div id="root"></div>

Под этот блок, файл с React должен лежать тут: modules/site/js/site.show_block.jsx В файле добавьте простенький код:

class Greetings extends React.Component
{
    render()
    {
        return (<div>Hello react</div>);
    }
}

ReactDOM.render(
    <Greetings/>,
    document.getElementById('root')
);

Ура!!! У нас получилось )

Нет, еще не все )

Прикольно, но оказывается, что мы можем в Diafan.CMS выносить отдельно файлы с js только для блоков, но не модулей. Давайте это исправим )

Для этого, нам нужно вернуться к файлу includes/template.php и вместо первых изменений сделать такие:

        $path = 'modules/'.$module.'/js/'.$module.$name.'.js';
        if(Custom::exists($path))
        {
            $this->diafan->_site->js_view[] = $path;
        }

        $path1 = 'modules/'.$module.'/js/'.$module.$name.'.jsx';
        if(Custom::exists($path1))
        {
            $this->diafan->_site->js_view[] = $path1;
        }

        $path2 = 'modules/'.$module.'/js/'.$module.'.jsx';
        if(Custom::exists($path2))
        {
            $this->diafan->_site->js_view[] = $path2;
        }

Все, теперь душа спокойна ) Мы с вами можем создавать файлы modules/js/site.jsx, modules/js/shop.jsx и так далее. Эти файлы будут всегда крепится к модулям, что нам и нужно )

У блоков свой код, у модулей свой. А что делать с шаблонами страниц?

Пока подключайте вручную, то что я придумал для шаблонов страниц будет в следующей статье, а вы оставляйте комментарии, вопросы )

Да, кстати, разработчики Diafan.CMS а как оставлять комменты к блогам? )