• Насколько верны результаты get_ini?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Коллеги, мне кажется Вы забываете об уровнях изоляции.
    PHP ini подгружается не в самом php, а в apache, соответственно при обработке .htaccess он имеет бОльший приоритет.
    Соответственно в ini_get Вы получите те значения, которые действуют в момент вызова ini_get в рамках данного хита.

    Примечание: не все значения можно переопределить в .htaccess (например mbstring.func_overload)
    Ответ написан
    Комментировать
  • Как создать агента в своём модуле?

    gromdron
    @gromdron
    Работаю с Bitrix24
    А в чем собственно вопрос? Делайте как по документации

    1) При установки модуля добавляем агент:
    \CAgent::AddAgent( "\\Your\\Module\\SuperClass::superAgent();", "your.module", "N", 10 * 24 * 3600, "", "Y");

    где
    "\\Your\\Module\\SuperClass::superAgent();" - код php который должен выполняться (точка с запятой в конце строго!!!)
    "your.module" - название вашего модуля
    "N" - периодичность
    10 * 24 * 3600 = периодичность запуска
    '' - первая дата проверки (оставлять пустой)
    "Y" - активность агента

    2) При удалении - очищаем агенты
    \CAgent::RemoveModuleAgents("your.module");
    3) Если файлы располагаются по канонам d7 ( /your.module/lib/superclass.php ), то ничего больше делать не нужно, если старый - то нужно прописать в include.php автолоадер для вашего класса с агентом
    Ответ написан
    2 комментария
  • В ORM Битрикса есть сеттеры и геттеры?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Очень интересная задача.

    Если Вам нужно оперировать только после получения данных, то Вам отлично подойдет механизм "Форматирования значений" из документации по ORM.
    При этом можете использовать сериализацию или json на ваше усмотрение (рекомендую сериализацию - нативнее и есть шанс что в модуле производительности заработает).

    Если у Вас MySQL выше 5,7 версии, можно добавить несколько Expression полей и доставать из JSON ключи так же как и поля. Пока не пробовали данный вариант - руки не доходили.
    Ответ написан
    Комментировать
  • Как изменить значение php_value mbstring.func_overload для определенного сайта на локальном сервере?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Правильно вам коллеги советовали, но я расскажу еще один путь:

    1) Открываем меню в трее: Дополнительно -> Конфигурация -> Apache 2.* (у меня 2.4) (выбираем пункт)
    2) У вас откроется редактор с примерно таким кодом:
    #-----------------------------------------------#
    # Начало блока конфигурации HTTP хоста
    #-----------------------------------------------#
    
    <VirtualHost *:%httpport%>
    
        DocumentRoot    "%hostdir%"
        ServerName      "%host%"
        ServerAlias     "%host%" %aliases%
        ScriptAlias     /cgi-bin/ "%hostdir%/cgi-bin/"
    
    </VirtualHost>

    У меня OpenServer находится на диске E, соответственно путь до папки с битриксом получается такой: E:/OpenServer/OpenServer/domains/dev

    Вписываем волшебный кусочек кода:
    <Directory "E:/OpenServer/OpenServer/domains/dev">
    	AllowOverride All
    	php_admin_value mbstring.func_overload 0
    </Directory>

    Чтобы получилось на подобии этого:
    #-----------------------------------------------#
    # Начало блока конфигурации HTTP хоста
    #-----------------------------------------------#
    
    <VirtualHost *:%httpport%>
    
        DocumentRoot    "%hostdir%"
        ServerName      "%host%"
        ServerAlias     "%host%" %aliases%
        ScriptAlias     /cgi-bin/ "%hostdir%/cgi-bin/"
    	
    	<Directory "e:\openserver\openserver\domains\cli">
    		AllowOverride All
    		php_admin_value mbstring.func_overload 0
    	</Directory>
    	
    	<Directory "E:/OpenServer/OpenServer/domains/dev">
    		AllowOverride All
    		php_admin_value mbstring.func_overload 0
    	</Directory>
    
    </VirtualHost>

    Сохраняем файл

    3) Перезагружаем OpenServer (желтый флажок)

    Примечание: метод работает только в web окружении, в консоли вы будете по-прежнему со значениями из Вашего php.ini файла
    Ответ написан
    5 комментариев
  • Страница без админки не открывается bitrix?

    gromdron
    @gromdron
    Работаю с Bitrix24
    1) Проверяем сервер скриптом bitrix_server_test
    2) Проверяем сервер через встроенную проверку сайта
    3) Отключаем модуль компрессии, если таковой установлен
    Ответ написан
    Комментировать
  • Сортировка getList битрикс. Стоит ли применять фильтр?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Если в инфоблоке несколько тысяч записей, какой запрос CIBlock::getList отработает быстрее, с применением arFilter или выборка всех записей?


    Если брать исходную постановку запроса: для CIBlock::getList без разницы сколько записей в самом инфоблоке, потому как Вы выбираете не элементы, а сами инфоблоки.
    Если речь идет о CIblockElement::getList(), то запрос не корректный.

    1) Для начала нужно понять что Вы делаете с записями. Время запроса сильно не изменится, а вот время обработки результата может "гулять" значительно.
    То есть, если Вы выводите на экран 1 тысячу значений и 1 миллион значений, то время будет существенным.

    2) Затем нужно понять, используете Вы сложный фильтр или простой.
    Например в инфоблоке у Вас 1 тысяча записей. Скажите, проще будет достать все? Или достать все, у которых этот параметр такой, такой или такой, а вот это параметр такой и такой, но только если дата в диапазоне от такого-то до такого-то и сегодня четверг.
    При небольших объемах, выбрать все элементы будет быстрее чем использовать фильтр по элементу, особенно если там есть логические операторы AND/OR, при этом с LIKE, да еще и множественными свойствами по инфоблоку 1.0
    Ответ написан
    Комментировать
  • Где лежат данные для функции showhead в bitrix?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Файл: /bitrix/modules/main/classes/general/main.php
    Строки: ~837 - ~847
    Выдержка кода:
    public function ShowHead($bXhtmlStyle=true)
    	{
    		echo '<meta http-equiv="Content-Type" content="text/html; charset='.LANG_CHARSET.'"'.($bXhtmlStyle? ' /':'').'>'."\n";
    		$this->ShowMeta("robots", false, $bXhtmlStyle);
    		$this->ShowMeta("keywords", false, $bXhtmlStyle);
    		$this->ShowMeta("description", false, $bXhtmlStyle);
    		$this->ShowLink("canonical", null, $bXhtmlStyle);
    		$this->ShowCSS(true, $bXhtmlStyle);
    		$this->ShowHeadStrings();
    		$this->ShowHeadScripts();
    	}


    P.S. Худо-бедно путешествовать по ядру битрикса можно и через онлайн-документацию по ссылке: bxapi.ru/src/?id=166792
    Ответ написан
    6 комментариев
  • Как автоматизировать очистку кэша битрикс?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Увы, очищать папку через cron не лучшая идея. По факту Вы боретесь не с проблемой, а с симптомом.
    Почему разрастается папка кеша?
    1) У Вас очень большой и сложный сайт.
    Например при 10 тысячах товаров в одной категории, если Вы будете пытаться кешировать каждую страницу, то размер будет большой. Предположим на страницу с 10 товарами уходит 10КБ кеша (на самом деле, все зависит от верстки и может достигать и бОльшего размера), тогда общий кеш каталога будет 10КБ * 10 000 = ~100МБ (учетных, на самом деле около 90МБ).
    Теперь посчитаем, что может быть 2 вида отображения: списком или плиткой. Соответственно уже 180МБ. А если товаров не 10 тысяч, а 100 ? А если есть еще и фильтр и его результаты могут быть кешированы? И это мы посчитали только каталог и довольно малый размер кеша.

    Решение: подобрать время кеширования и увеличить дисковое пространство

    2) Неправильно определено время кеширования.
    Например: у Вас ttl кеша стоит 3 месяца. И даже если за 3 месяца на него никто не зашел, он все-равно хранится. Например у Вас очень объемный кеш (что очень плохо), который занимае 500КБ (а иной раз и 1 МБ), получается что этот 1МБ будет хранится на протяжении длительного времени, даже если к нему нет обращения.

    Решение: подобрать время кеширования (возможно где-то стоит уменьшить) и параметры компонентов (возможно что-то не стоит кешировать)

    3) Неправильно настроен кеш собственных или битриксовых компонентов.
    Например есть очень большой пунктик в битриксе с кешем меню - если указать MENU_CACHE_VARS (вроде так пишется, по памяти писал), то он будет под каждый набор параметров создавать кеш. И тогда кеш меню начинает сильно пухнуть и еще и кешироваться на длительное время.

    Решение: нужно проверить параметры кеширования в компонентах. Возможно в своих компонентах переписать или посмотреть на основании чего он формируется

    4) Ошибка с механизмом очищения кеша.
    Например, когда кеш не успевает удаляться, и накапливается. Таким образом происходит дублирование одного и того же кеша в разных компонентах.
    Ответ написан
    Комментировать
  • Какой компонент Битрикс подойдет для отправки заявки в личном кабинете?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Здесь дело не в компоненте, а в способе реализации, которая в свою очередь зависит от редакции.
    Например для Битрикс24 их много. Навскидку варианты следующие:
    1) Универсальный список с бизнес-процессом на нем
    2) Элемент инфоблока с бизнес-процессом на нем (есть и в БУС)
    3) Веб-формы и этапы прохождения (есть и в БУС)
    4) Собственная реализация на инфоблоках
    5) Релаизация на основе собственного кода

    Например если взять вариант 1, то там вообще делать ничего не нужно. Только права правильно настроить и бизнес-процесс описать.
    А вот, например в форме 4 - bitrix:iblock.element.add и собственный код согласования.
    Ответ написан
    Комментировать
  • Как сгруппировать элементы по разделам в Битрикс?

    gromdron
    @gromdron
    Работаю с Bitrix24
    А не пробовали воспользоваться штатной возможностью группировки: arGroupBy (3 параметр в getList, который у вас в значении false)

    Массив полей для группировки элемента. Если поля указаны, то выборка по ним группируется (при этом параметр arSelectFields будет проигнорирован), а в результат добавляется поле CNT - количество сгруппированных элементов. Если указать в качестве arGroupBy пустой массив, то метод вернет количество элементов CNT по фильтру. Группировать можно по полям элемента, а также по значениям его свойств. Для этого в качестве одного из полей группировки необходимо указать PROPERTY_, где PROPERTY_CODE - ID или символьный код свойства.
    Необязательное. По умолчанию false - записи не группируются.


    Группировать по ID секции.
    Ответ написан
    Комментировать
  • Как реализовать настраиваемые виджеты на сайте?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Навскидку, Вы упустили самый интересный вариант:Реализация на базе включаемых областей для страниц.
    Плюсы:
    + Реализация требований на основе стандартной функциональности продукта
    + Гибкие возможности по расширению (вы можете использовать любые компоненты на любых страницах с любыми параметрами)
    + Используете только необходимый минимум без прослоек в виде инфоблоков и бд
    + Простое и понятное управления для разработчика

    Минусы:
    - Без соответствующего интерфейса решение для простых контент редакторов превращается в АД. Если Вы будете сами это все поддерживать, то проблем не возникнет, а вот для других потребуется разработать интерфейс создания включаемой области.
    Ответ написан
    Комментировать
  • Не выполняются агенты на событиях в битрикс 1С?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Для начала:
    1) Выполнялись ли агенты на хитах или на кроне? Может быть кто-то начал перенос агентов на крон и не закончил перенос.
    2) Определены ли константы: BX_CRONTAB_SUPPORT и BX_CRONTAB ? Может быть агенты были на хитах и кто-то определил константы и не перенес на крон. Или наоборот определил константы, без параметров ниже.
    3) Какие значения заданы у agents_use_crontab и check_agents ?
    Ответ написан
    Комментировать
  • Как подключить глобальную переменную $DB в битрикс в отдельном файле?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Покажите код вашего файла.
    Возможно Вы не подключили prolog_before - служебную часть битрикса.
    Делается это следующим образом: в начале скрипта прописывается:
    require $_SERVER["DOCUMENT_ROOT"]."/bitrix/modules/main/include/prolog_before.php";
    Ответ написан
  • Как реализовать голосование за отдельный элемент с помощью инфоблоков в битрикс?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Штатный механизм голосования за элемент инфоблоков не подразумевают запись времени и ip, только факт голосования. Если Вы хотите делать сделать такое голосование, Вам нужно либо создавать опросы, либо использовать свою таблицу.

    Давайте разберемся с Вашей ситуацией:
    создала отдельный файл voting.php в шаблоне компонента

    Скорее всего Вы просто создали файл. И в нем соответственно НЕ подключили служебную часть.
    Я бы рекомендовал Вам использовать ORM Битрикса для такой ситуации (очен....
    Но как быстрое решение, можно и прямой запрос в базу (хотя это будет менее элегантное решение).
    В таком случае код будет выглядеть как-то так:

    <?
    require $_SERVER["DOCUMENT_ROOT"]."/bitrix/modules/main/include/prolog_before.php";
    
    /**
     * Тут можете проверить, что все переменные пришли
     * Я для себя буду использовать переменные:
     * - ELEMENT_ID 
     * - USER_ID
     * 
     * Просто писать факт голосования.
     * В таблицу project_element_vote ( ID, ELEMENT_ID, USER_ID )
     */
    
    global $USER;
    
    /* @var object Объект приложения */
    $oApplication = \Bitrix\Main\Application::getInstance();
    
    /* @var object Объект соединения с БД */
    $oConnection = $oApplication->getConnection();
    
    /* @var object Хелпер для безопасной записи в БД*/
    $oHelper = $oConnection->getSqlHelper();
    
    /* @var object Объект для работы с входящими переменными */
    $oRequest = $oApplication->getContext()->getRequest();
    
    
    if ( $oRequest->isAjaxRequest() && !empty( $oRequest->get('ELEMENT_ID') ) )
    {
    	$iUser    = $USER->GetId();
    	$iElement = $oHelper->forSql( $oRequest->get('ELEMENT_ID') );
    
    	$sql = "INSERT INTO project_element_vote('ELEMENT_ID','USER_ID') VALUES ('{$iElement}','{$iUser}')";
    	$res = $oConnection->query($sql);
    
    	if ( $res )
    	{
    		echo 'ok';
    		die();
    	}
    }
    echo 'bad';
    Ответ написан
    Комментировать
  • PHP 7 Как переделать из preg_replace в preg_replace_callback?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Честно говоря, без говнокода не представляю как сделать подобное.
    Если уж очень топорный вариант. Первое что приходит в голову - либо класс передавать, либо глобал использовать. Глобальные переменные это как-то уж очень через чур, а вот с классом другое дело (выглядит почище, да и для глаз приятнее).

    Навскидку, код, который будет отвечать за вывод будет следующим:
    /* @var string Текст, в котором проводим замену*/
    $str = <<<STRTEXT
    [index:Звездочет]А тут хз что[/index]
    Тут текст [guest]Иванов[/guest]
    STRTEXT;
    
    $oTextParser= (new TextParser($str))
    				->addRule("#\\[index:(.+?)\\](.*?)\\[/index\\]#ies", "indexShow('\\1', '\\2')")
    				->addRule("#\\[guest](.*?)\\[/guest]#ies","checkGuest('\\1')")
    				->parse();
    
    /*
    На выходе хочу получить:
    -------------------------
    Звездочет(А тут хз что)
    Тут текст GUEST(Иванов)
    */
    
    echo "<pre>";
    var_dump($oTextParser->getText());
    echo "</pre>";

    Код функций который я буду использовать:
    function indexShow( $a, $b)
    {
    	return $a."(".$b.")";
    }
    
    function checkGuest( $a )
    {
    	return 'GUEST('.$a.')';	
    }


    Сама реализация:
    class TextParser
    {
    	/* @var string Результат выполнения парсинга */
    	public $parsed;
    
    	/* @var string[] Ассоциативный список правил в формате: регулярка => функция для замены */
    	public $rules = [];
    
    	public function __construct( $text )
    	{
    		$this->parsed = $text;
    	}
    
    	/**
    	 * Добавляет правило работы парсера
    	 * Для использования цепочек возвращает текущий экземпляр
    	 * 
    	 * @param string $regex 
    	 * @param string|callback $func 
    	 * @return TextParser
    	 */
    	public function addRule( $regex, $func )
    	{
    		$this->rules[ $regex ] = $func;
    		return $this;
    	}
    
    	/**
    	 * Выполняет разброр исходного текста
    	 * Для использования цепочек возвращает текущий экземпляр
    	 * 
    	 * @return TextParser
    	 */
    	public function parse()
    	{
    		array_walk(
    			$this->rules,
    			function($function, $regular)
    			{
    				$this->parsed = preg_replace($regular, $function, $this->parsed);
    			}
    		);
    		return $this;
    	}
    
    	/**
    	 * Возвращает результат парсера (или исходный текст, если был вызван до метода parse)
    	 * 
    	 * @return string
    	 */
    	public function getText()
    	{
    		return $this->parsed;
    	}
    
    }


    Естественно, решение имеет свои изъяны и слабые стороны, помимо плохого кода, нельзя будет использовать функции в текущем окружении ($this).
    Ответ написан
    4 комментария
  • Не возвращает на сайт после авторизации через google (laravel) в чём моя ошибка?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Ошибка: Forbidden You don't have permission to access /google/callback on this server.
    Отдается уже Вашим сервером.

    Скорее всего Вы неправильно настроили (или не настроили или недонастроили) - Pretty url (насколько я понял)
    Сверьтесь с документацией - все ли Вы сделали правильно.

    https://laravel.com/docs/5.5#web-server-configuration
    Ответ написан
    Комментировать
  • Какие самые лучшие онлайн курсы по PHP?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Мой коллега, сейчас участвует в программе менторства по Базовому курсу php от HTLM Academia. Не могу говорить за всех, но в качестве данного курса я уверен:
    1) Должная подготовка - php, composer, github , mysql - знания которые вы получите на выходе, плюс понимание как это работает
    2) Работа с ментором позволит устранить узкие места в Вашем коде и если нужно поставит логику на место.

    По специалисту ничего не могу сказать, но из GeekBrains так себе специалисты (был опыт).

    Вообще в мире и у нас сильно котируется только ZCE, а чтобы его сдать не обязательно где-то учиться, можно и на документации.
    Но вообще, рекомендую курсы от html академии + сдача ZCE. На выходе - вы сертифицированный специалист по php с хорошим портфолио на GitHub
    Ответ написан
  • Как в свойстве привязка к пользователю во всплывающем окне были пользователи из определенной группы,?

    gromdron
    @gromdron
    Работаю с Bitrix24
    1) Выносите /bitrix/admin/user_search.php (исходный код, а не ссылку), куда-нибудь в /local/tools/
    2) Делаете класс-наследник от CIBlockPropertyUserID ( /bitrix/modules/main/tools/prop_userid.php )
    3) Перекрываете методы GetUserTypeDescription и (GetPropertyFieldHtml или FindUserIDNew)
    4) Правите в новом файле из п.1 Вашу группу

    Это вариант fix.
    В идеале: в своем наследнике CIBlockPropertyUserID добавить параметром группу пользователей, все запросы дополняете этой группой, а в своем файле user_search.php делаете доп. проверку. Так получается уже отличное свойство.
    Ответ написан
    Комментировать
  • Кто подключал онлайн-кассу в битрикс? Можно ли это сделать без обновления?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Можно ли подключить онлайн кассы для старого Битрикса?
    Да, можно.

    Можно ли подключить онлайн кассы для старого Битрикса, не привлекая разработчика или иных специалистов?
    Нет, нельзя.

    Какие есть варианты кроме обновления?
    1) При помощи разработчиков (заказать) свою реализацию. В этом случае обновлять битрикс не придется, но все проблемы с работой касс будут только головной болью
    2) Можно поискать доступные расширения для битрикса, если производители касс их выпускают. Скорее всего такие модули будут требовать наличие стандартных интеграций, т.е. обновленного битрикса, но чем черт не шутит, может найдете иную реализацию. (я пока таких не встречал).
    В итоге, Вы все равно скорее придете к покупке обновления.
    Ответ написан
    Комментировать
  • Как создать кастомное действие с привязкой к элементу?

    gromdron
    @gromdron
    Работаю с Bitrix24
    Впринципе не сложно.

    Для начала Вы подписываетесь на событие OnAdminListDisplay модуля Main.
    Именно оно отвечает за действие ДО вывода любого списка элементов в административной панели (за исключением под-листов у инфоблоков и модуля производительности).
    На вход оно принимает лишь 1 параметр - экзепляр класса CAdminList (см. /bitrix/modules/main/interface/admin_list.php)

    Чтобы обрабатывать нужную таблицу, нужно ограничить выборку. Т.е. Ваш обработчик будет выглядеть как-то так:

    <?php
    AddEventHandler("main", "OnAdminListDisplay", "MyOnAdminContextMenuShow");
    function MyOnAdminContextMenuShow(&$oAdminList)
    {
        /**
         * $type - тип кода инфоблока, например news, events и т.д.
         * $iblock - идентификатор инфоблока
         * 
         * Если интересует каталог, то вместо tbl_iblock_list_ нужно использовать tbl_product_list_
         */
        if ( $oAdminList->table_id == "tbl_iblock_list_".md5($type.".".$iblock) )
        {
            // полезные действия
        }
    }
    ?>


    Собственно так, мы получаем возможность работать с выводом.
    Для более подробного пояснения лучше прочитать про заказные элементы в административной панели в документации: https://dev.1c-bitrix.ru/api_help/main/general/adm...

    Собственно добавим нужные нам данные для работы. Предположим, я хочу логгировать выделенные элементы на странице, тогда мой код будет выглядеть так:
    AddEventHandler("main", "OnAdminListDisplay", "MyOnAdminContextMenuShow");
    function MyOnAdminContextMenuShow(&$oAdminList)
    {
        /**
         * $type - тип кода инфоблока, например news, events и т.д.
         * $iblock - идентификатор инфоблока
         * 
         * Если интересует каталог, то вместо tbl_iblock_list_ нужно использовать tbl_product_list_
         */
        if ( $oAdminList->table_id == "tbl_iblock_list_".md5("structure.4") )
        {
        	$arActions = $oAdminList->arActions;
    
        	$arActions['alert'] = 'Ругаться!';
    
        	$oAdminList->AddGroupActionTable($arActions);
        }
    }
    
    AddEventHandler("main", "OnAfterEpilog", "iblockAlert");
    
    function iblockAlert()
    {
    	$oRequest = \Bitrix\Main\Application::getInstance()->getContext()->getRequest();
    
    	// Проверяем, что работает только в админке
    	if ( $oRequest->isAdminSection() )
    	{
    		if (
    			// Интересуют только интерактивные запросы
    			$oRequest->get('mode')=='frame'
    			// Где передана переменна IBLOCK_ID
    			&& $oRequest->get('IBLOCK_ID')==4
    			// Соответствующие нашему action
    			&& $oRequest->get('action')=='alert'
    			)
    		{
    			/**
    			 * Вот тут можно сделать что угодно
    			 * Можно получить выделенные ID
    			 * через $oRequest->get('ID')
    			 * Если он пуст, значит действие на всех элементах инфоблока
    			 */
    		}
    	}
    }


    На самом деле параметров гораздо больше - есть еще custom области, которые можно выводить, но суть та же. Если захотите добавить свое поле (я добавлял простой action), то лучше глянуть в исходники и там уже по аналогии разрбраться
    Ответ написан
    3 комментария